Merged
Conversation
The use of `Deref` was incorrect, as this trait is meant to implement smart pointers and get support for implicit coercion / automatic deref. What we really wanted was to use `AsRef`, and require explicit `.as_ref()` conversions as call site when needed.
Now that we have `AsRef<[u8; Self::KEY_SIZE]>`, we don't really need `as_bytes()` anymore, since `as_ref()` already covers it.
Since this method is strongly tied to reading a key from the right source (stdin, env, param) for the `cmd_unlock` command, and thus strongly tied to the command line parsing, this make more sense to put this in `commands/unlock.rs` rather than as a method on the `key::Key` model object.
To avoid having to refer to it as `key::Key` in the implementations every time
For consistency with the order in which the methods and traits are declared in the type implementation and group them by theme
To avoid having to refer to it as `repo::Repo` in the implementations every time
e.g. most functions that do something with a `Key` need only to borrow the `Key` (e.g. to print its value) without taking ownership of it. Same for functions that take should take `&str` instead of `String` to only borrow it
To make tests easier to write, and because it is idiomatic and makes semantic sense for such a wrapper type anyway
- Allows the `#[command] Unlock`'s `#[arg] key_source: KeySource` to be more explicit in its type - Uses `impl std::str::FromStr for KeySource` to parse `"-"`/`"env:…"`/`"…"` strings into the right `KeySource` variant (which is more semantically correct than using `From<&str>` here because this is semantically more about parsing/interpreting an argument than about conversion) - Use `impl From<KeySource> for Key` to build/load a `Key` from a `KeySource`
iangmaia
reviewed
Dec 15, 2025
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
from_xyzmethods to use theFrom<XYZ>andTryFrom<XYZ>traits, which is the idiomatic Rust way of implementing such conversion.Dereftrait (which is meant only to be used to implement smart pointers with implicit/automatic dereferencing, while what we really wanted wasAsRefto get a reference to the underlying array of bytes.enum KeySourceto better represent the 3 possible supported sources for the argument tounlock(StdIn,EnvVar,ArgumentValue) with an explicit typeReview
I'd suggest to review this PR commit-by-commit, as each one tackles an individual refactor
Deref➡️AsRef<[u8; Self::KEY_SIZE]>as_bytes()➡️as_ref()from_bytes()➡️From<[u8; Self::KEY_SIZE]>bytes_to_key()➡️TryFrom<&[u8]>from_file()➡️TryFrom<&Path>from_base64()➡️TryFrom<&str>to_base64()➡️DisplayRepo::from_repository➡️TryFrom<Repository>enum KeySourcetype to represent the different sources supported for the key in theunlockcommandread_from_source()fromkey.rstocommands/unlock.rs, since it's related to parsing command line argumentsread_from_source()with dedicatedenum KeySourceto use ascmd_unlockparameter type; thenimpl FromStr for KeySourceto implement string-representation parsing semantics, andimpl From<KeySource> for Keyto build/load aKeyfrom aKeySourcevariant.This was also the occasion to move some stuff around:
Keyunit tests, so that they are grouped in the same order as the methods they are testingKeyimplementPartialEq, Eq(which makesassert_eq!easier to use in tests in particular)use crate::key➡️use crate::key::Key, so we can just useKeyinstead ofkey::Keyin codeuse crate::repo➡️use crate::repo::Repo, so we can just useRepoinstead ofrepo::Repoin codeTesting
CI being green should be enough for testing this