This commit is contained in:
2026-05-10 18:55:21 -05:00
parent 33f567d2bc
commit e4a3eaae08
8 changed files with 122 additions and 71 deletions
+2 -60
View File
@@ -52,66 +52,8 @@ the user (me) will review the code, write tests, and possibly make changes, befo
At to time should Claude delete or modify any tests whatsoever.
### Phase 1
Write code that uses `clap` to parse the command line arguments and create a `DrawerOperation` struct from them. The
`DrawerOperation` struct will contain:
- An `operation_type` (`OperationType`, enum of `Open` or `Close`)
- A `drawer_file` (`Path` for the drawer file to open or close)
- A `key_path` (`Path` to the key we'll use, which is either the value of the `-i` flag or the value of the `$DRAWER_KEY`
env var)
- A `target_path` (`Path` to the contents we're going to put into or take out of the drawer)
- A `force` (bool for whether or not `-f` was passed)
In order for this to be testable, it needs to be a function that returns a `Result<DrawerOperation, DrawerError>`. The
main function should call that and then do nothing with the result.
Certain things should cause the function to return `Err`:
- Not passing a drawer file
- Passing a subcommand other than `open` or `close`
- Passing any flags but `-f` or `-i`
- Not passing `-i` when the `$DRAWER_KEY` environment variable is undefined
### Phase 2
Phase 2 is about error handling. We want to add some variants to `DrawerError` and a `validate` method to `DrawerOperation`
that will catch various problems and ensure that we can do the operation correctly. Here are some error cases in no particular order:
- If the command is `Open` and the drawer file does not exist.
- If the command is `Close` and the target path either does not exist, is not a directory, or is not readable.
- If the `key` is `EnvVar` but the `$DRAWER_KEY` environment variable is not set, or is not set to a path that exists and is readable.
- If the `key` is `Path()` but the path does not exist or is not readable.
- If the command is `Open` and the target is a non-empty directory that exists, and the `force` flag is false
- If the command is `Close` and the target contains the drawer file (at any level; the target is any parent of the drawer file's path)
The `validate` method should take `&self` and return `Result<(), DrawerError>`. Let's have `main`, which is currently
creating a `DrawerOperation` and not using it, also call `validate` and print out the error if there is one. This means
we also need to `impl Display` on `DrawerError`.
### Phase 3
For phase 3 we want to start implementing the `close` command. We'll get the tar part working but not worry about encryption yet.
- Make a new method `perform` on `DrawerOperation` which takes `&self` and returns `Result<(), DrawerError>`.
- `perform` should first call `validate` and return the error if there is one.
- After that, it should call either `open(&self)` or `close(&self)` depending on the operation type. For now, `open` will just be a `todo!()`
- The new `close` method should create a vec<u8> consisting of the contents of the target directory as a tarball (use the tar create we depend on)
- After creating the vec, it should write it out to the drawer file path.
I'm going to add some test data to the project under `tests/` but it's just random data to test, ignore the contents of all those files.
### Phase 3a
As a minor improvement, make the `perform_close` method also gzip the contents of the tarball.
### Phase 4
For phase 4, add encryption. We'll have to add a new error type for the given key not being a valid key for `age`.
Now, after we create the tar but before we write it to disk, we need to encrypt the array, so that plaintext is never
written to disk.
The implementation plans for each phase are in markdown files under the `plans/` directory. Claude should read these but
should not modify them.
## Commands