Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Stream to buffer #44

Open
mmajcica opened this issue Jul 4, 2022 · 0 comments
Open

Stream to buffer #44

mmajcica opened this issue Jul 4, 2022 · 0 comments

Comments

@mmajcica
Copy link

mmajcica commented Jul 4, 2022

Hi,

we are having some small issues with using the library, maybe it is not directly connected to the library itself but may be an improvement point.

Loading the library expects to receive an ArrayBuffer. However, we are dealing with streams because we are downloading our kbdx file.

Initially, we were doing the following, downloading the file to the disk, then reading it to the buffer. It works well. Following the code used:

    async getDatabase(url: string): Promise<string> {
        const sampleFilePath = Path.join(
            tmpdir(),
            `keepass.${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.kdbx`,
        );

        const file: NodeJS.WritableStream = fs.createWriteStream(sampleFilePath);
        const response = await this.httpClient.get(url);
        const stream = response.message.pipe(file);

        const promise = new Promise((resolve, reject) => {
            stream.on('finish', () => {
                resolve(true);
            });
            stream.on('error', reject);
        });

        await promise;

        return sampleFilePath;
    }

const dbPath = await this.getDatabase(argv.url);
const keepassDb = fs.readFileSync(dbPath).buffer;
const db = await kdbxweb.Kdbx.load(keepassDb, credentials);

Now we are not allowed anymore to persist things on a disk and we need to manage all of the things in memory. That is not a big issue as our DB file is only around 200kb and it will not grow.

We changed the code to the following:

    async getDatabase(url: string): Promise<Buffer> {
        const response: IHttpClientResponse = await this.httpClient.get(url);

        return new Promise<Buffer>(async (resolve, reject) => {
            const chunks = [];
            response.message
                .on('data', function (data: Buffer) {
                    chunks.push(data);
                })
                .on('end', async function () {
                    const buffer: Buffer = Buffer.concat(chunks);

                    resolve(buffer);
                })
                .on('error', function (err) {
                    reject(err);
                });
        });
    }

const dbBuffer = await this.getDatabase(argv.url);
const db = await kdbxweb.Kdbx.load(dbBuffer, credentials);

However, this does not work, we do get an exception saying KdbxError: Error InvalidArg: data.

Do you have any idea why this may not work? Is there an example of how to get a stream into the buffer that will be accepted by kdbxweb?

Would it be possible to have a possibility to load a DB direclty from a stream?

Thank you in advance.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant