5fa30414d7
Distinguish invalid KeePass requests from backend failures in the Python bridge, improve nested group path resolution, and add coverage for nested group creation plus payload forwarding.
114 lines
3.2 KiB
Markdown
114 lines
3.2 KiB
Markdown
# ts-pykeepass-wrapper
|
|
|
|
TypeScript wrapper around `pykeepass` for reading and modifying KeePass `.kdbx` files.
|
|
|
|
## Overview
|
|
|
|
This project uses:
|
|
- TypeScript as the public API
|
|
- Python as the runtime backend
|
|
- `pykeepass` to read and update KeePass databases
|
|
|
|
The TypeScript layer launches a Python bridge per request and exchanges JSON through stdin/stdout.
|
|
|
|
## Requirements
|
|
|
|
- Node.js or Bun
|
|
- Python 3
|
|
- `pykeepass` installed in the Python environment used by the bridge (the project provides `bun run setup:python`)
|
|
- The bridge defaults to `.venv/bin/python3`, or you can override with `PYTHON_PATH`
|
|
|
|
## Python setup
|
|
|
|
Install `pykeepass` in the Python environment used by the bridge:
|
|
|
|
```bash
|
|
bun run setup:python
|
|
```
|
|
|
|
If you prefer manual installation:
|
|
|
|
```bash
|
|
python3 -m venv .venv && .venv/bin/pip install pykeepass
|
|
```
|
|
|
|
The bridge also works with a project-local virtual environment such as `.venv`.
|
|
|
|
## Usage
|
|
|
|
```ts
|
|
import { openKeePassDatabase } from "./src/keepass";
|
|
|
|
const db = openKeePassDatabase("tests/fixtures/data.kdbx", {
|
|
password: "123",
|
|
});
|
|
|
|
const entries = await db.listEntries();
|
|
console.log(entries);
|
|
```
|
|
|
|
## Example
|
|
|
|
Run the example using the bundled data fixture credentials:
|
|
|
|
```bash
|
|
bun run src/example.ts
|
|
```
|
|
|
|
## API
|
|
|
|
### `openKeePassDatabase(path, options)`
|
|
|
|
Creates a database wrapper.
|
|
|
|
#### Options
|
|
- `password`: KeePass master password
|
|
- `keyFile`: optional key file path
|
|
|
|
### `listEntries()`
|
|
Returns all entries in the database, with every entry field exposed by the bridge (`title`, `username`, `password`, `url`, `notes`, `groupPath`, `otp` when present).
|
|
|
|
### `findEntries(query)`
|
|
Finds entries by partial match and returns the full entry objects.
|
|
|
|
### `listGroups()`
|
|
Returns all groups, including their names and paths.
|
|
|
|
### `createEntry(entry)`
|
|
Creates a new entry in the target database and persists it immediately.
|
|
|
|
#### Entry input
|
|
- `title`: entry title
|
|
- `username`: optional username
|
|
- `password`: optional password
|
|
- `url`: optional URL
|
|
- `notes`: optional notes
|
|
- `groupPath`: optional target group path
|
|
|
|
`groupPath` is resolved as an existing group path when possible. Nested paths such as `Folder1/SubFolder` are supported when the target group exists.
|
|
|
|
### `createGroup(group)`
|
|
Creates a new group and persists it immediately.
|
|
|
|
#### Group input
|
|
- `name`: group name
|
|
- `path`: optional parent group path
|
|
|
|
`path` is resolved as an existing parent group path when possible, including nested paths.
|
|
|
|
### `save()`
|
|
Persists the current database state.
|
|
|
|
### `close()`
|
|
No-op for now.
|
|
|
|
## Notes
|
|
|
|
- The bridge currently launches a Python process per call.
|
|
- This is simple and robust for a first version.
|
|
- Errors from the Python bridge are propagated to the TypeScript API, including invalid or empty output. Bridge failures are normalized to distinguish invalid requests and backend errors.
|
|
- A persistent Python process can be added later if needed.
|
|
- Write operations currently open, modify, and save the database per command.
|
|
- Bundled fixtures include `tests/fixtures/data.kdbx` and `tests/fixtures/empty.kdbx`; the companion JSON file stores the password and expected content for tests/examples.
|
|
- Integration tests validate the bundled `data.kdbx` entry-by-entry and group-by-group against `tests/fixtures/data.kdbx.json`, and may skip cleanly when `pykeepass` is unavailable.
|