Commit Graph

20 Commits

Author SHA1 Message Date
Joseph O'Brien
aadb1570a3 refactor: formalize FileStore and IdentitySource ports in notfiles
- Create FileStore trait in crates/notfiles/src/ports.rs capturing all file I/O
  operations (read, write, rename, remove, metadata, symlink, etc.)
- Create FileStoreImpl adapter in crates/notfiles/src/adapters/fs.rs wrapping std::fs
- Update linker.rs State::load/save and link_package/unlink_package to accept
  FileStore parameter for dependency injection
- Create IdentitySource port in crates/notsecrets/src/ports.rs
- Move IdentitySource trait from sources/mod.rs to ports.rs, maintain backward
  compatibility via re-export
- Update all source implementations to import from ports
- Update lib.rs in both crates to re-export ports
- Pass FileStoreImpl through call chain in main.rs and lib.rs public API

Maintains 100% backward compatible public API; FileStore dependency is internal.
2026-04-12 16:35:53 -04:00
Joseph O'Brien
19e74b4a1b security: audit Command call sites; confirm no argument injection
Closes #18

All six Command::new call sites audited:
- bitwarden.rs (sh -c): shell string is a hardcoded literal; no user data.
- bitwarden.rs (bw unlock): all args hardcoded.
- bitwarden.rs (bw get): item_name and session passed as discrete .args() elements; no shell.
- nothooks/runner.rs (nu/sh/etc): interp and script path passed as discrete args; no shell.
- notstrap/repo.rs (git clone): url and dest passed as discrete .arg() calls; no shell.
- notfiles/tests/integration.rs: test harness with hardcoded args only.

Added SAFETY comments on the three sites that handle user-controlled config values.
2026-04-11 23:52:40 -04:00
Joseph O'Brien
3e7135a398 fix(notfiles): save state on partial link failure; skip re-copy of unchanged files
Closes #8, closes #9
2026-04-11 23:40:32 -04:00
Joseph O'Brien
11d329c5a2 security: fix Bitwarden password exposure and ChaCha nonce hardening
Issue 12: pass bw unlock password via stdin (--passwordstdin) instead of
as a CLI arg, preventing it from appearing in /proc/<pid>/cmdline or ps output.

Issue 11: replace Nonce::default() (all-zero) with the first 12 bytes of the
16-byte random payload nonce. The key-nonce pair was already unique per message
(HKDF salt), but using an explicit non-zero nonce removes the latent risk of
accidental key reuse and makes the safety invariant self-documenting.

Closes #11, closes #12
2026-04-11 23:38:41 -04:00
Joseph O'Brien
b5a27108d0 feat(notgraph): heatmap coloring, symbol counts, per-crate module graphs, cycle callouts 2026-04-02 20:53:07 -04:00
Joseph O'Brien
f80ea02f07 feat(notsecrets): migrate sources to IdentitySource trait, add resolve_identities, remove legacy API
- Replace AgeKeySource+retrieve() with IdentitySource+load() returning Box<dyn Identity>
- Rewrite bitwarden/file/prompt sources to implement new trait
- Add resolve_identities() public API with partial-success semantics
- Delete _legacy.rs and remove legacy re-exports from lib.rs
- Update integration tests to use new API

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 21:16:39 -04:00
Joseph O'Brien
e388d75cf1 feat(notsecrets): Decryptor — identity-driven age decryption with MAC verification
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 21:06:55 -04:00
Joseph O'Brien
9863af6b45 feat(notsecrets): Encryptor — multi-recipient age encryption 2026-04-01 21:02:57 -04:00
Joseph O'Brien
545a45b3d3 feat(notsecrets): EncryptedIdentity stub — passphrase-protected identity file 2026-04-01 20:57:22 -04:00
Joseph O'Brien
a0fe6f7128 feat(notsecrets): SSH RSA identity and recipient (OAEP-SHA256) 2026-04-01 20:55:42 -04:00
Joseph O'Brien
566501cb42 feat(notsecrets): SSH Ed25519 identity and recipient 2026-04-01 20:53:59 -04:00
Joseph O'Brien
b899198e98 feat(notsecrets): scrypt identity and recipient (passphrase-based) 2026-04-01 20:51:40 -04:00
Joseph O'Brien
6202c5dfe9 feat(notsecrets): X25519 identity and recipient with wrap/unwrap
Implements ECDH key wrapping via HKDF-SHA256 + ChaCha20Poly1305,
bech32 encode/decode for age1... recipients and AGE-SECRET-KEY-1... identities.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 20:49:31 -04:00
Joseph O'Brien
2476daafa6 feat(notsecrets): age wire format parser/serializer with unit tests 2026-04-01 20:47:00 -04:00
Joseph O'Brien
34d9e3d677 feat(notsecrets): scaffold age-native domain types and trait ports
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 20:44:05 -04:00
Joseph O'Brien
55d68ee92f fix: address security findings from devkit-review (#1–#7)
notsecrets:
- install_age_key_at: create key file with mode 0600 via OpenOptions,
  eliminating TOCTOU window where file was transiently world-readable (#3)
- sops_args: extract arg-builder and add -- separator before path,
  preventing leading-dash flag injection (#2)
- use .context() instead of .with_context(closure) for string literal (#7)

notstrap:
- extract parse_env_line: validates env lines before set_var — rejects
  null bytes (#4) and blocks dangerous keys (LD_PRELOAD, PATH, etc.) (#5)
- wire parse_env_line into injection loop; errors abort the step cleanly
- correct SAFETY comment: documents single-threaded invariant and notes
  that subsequent spawns inherit injected env (#6)

Tests: 12 new tests covering all fixes; workspace grows from 44 to 56 passing.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 15:00:47 -04:00
Joseph O'Brien
403bcc4436 fix: address blocking sentinel findings (unsafe SAFETY comment, unwrap panics)
Some checks failed
Public Repo Readiness / Check Public Repo Readiness (push) Failing after 4s
2026-04-01 08:59:28 -04:00
Joseph O'Brien
0ff89234e8 chore: add dual MIT/Apache-2.0 license, update Cargo.toml and README
Some checks failed
Public Repo Readiness / Check Public Repo Readiness (push) Failing after 4s
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-31 22:00:10 -04:00
Joseph O'Brien
6e78778543 feat(notsecrets): add age key retrieval with bw/file/prompt sources 2026-03-31 17:26:10 -04:00
Joseph O'Brien
6b0bd3beb6 feat(notcore): add shared types, config, paths, error crate
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-31 17:17:35 -04:00