Skip to content

feat: add core factory, token shape, and supporting microcrates#22

Merged
EffortlessSteven merged 4 commits into
mainfrom
feat/core-factory-and-token-shape
Feb 24, 2026
Merged

feat: add core factory, token shape, and supporting microcrates#22
EffortlessSteven merged 4 commits into
mainfrom
feat/core-factory-and-token-shape

Conversation

@EffortlessSteven

Copy link
Copy Markdown
Member

Summary

  • Core factory (uselesskey-core-factory): Extracts the deterministic/random artifact generation engine with get_or_init caching into its own crate, decoupling it from the monolithic uselesskey-core
  • Token shape (uselesskey-core-token-shape): Extracts token generation primitives (API key, bearer, OAuth access token) into a focused microcrate with its own tests and BDD steps
  • Supporting microcrates: Adds uselesskey-core-hash, uselesskey-core-jwk-shape, uselesskey-core-jwk-builder, uselesskey-core-jwks-order, uselesskey-core-keypair-material, uselesskey-core-negative-pem, uselesskey-core-x509-negative — each decomposing a piece of core into a focused, independently testable unit
  • Fuzz targets: New fuzz targets for core factory cache, core hash, keypair material, negative PEM, token shape, X.509 negative, JWK shape, and JWKS ordering

Changes

  • crates/uselesskey-core-factory/ — new crate: Factory with deterministic seed derivation + DashMap cache
  • crates/uselesskey-core-token-shape/ — new crate: token generation primitives (API key, bearer, OAuth)
  • crates/uselesskey-core-hash/ — new crate: BLAKE3 hashing helpers (hash32, Hasher, write_len_prefixed)
  • crates/uselesskey-core-jwk-shape/ — new crate: typed JWK models (PublicJwk, AnyJwk, Jwks)
  • crates/uselesskey-core-jwk-builder/ — new crate: JwksBuilder for constructing JWKS sets
  • crates/uselesskey-core-jwks-order/ — new crate: kid-sorted stable ordering (KidSorted, HasKid)
  • crates/uselesskey-core-keypair-material/ — new crate: Pkcs8SpkiKeyMaterial extraction
  • crates/uselesskey-core-negative-pem/ — new crate: CorruptPem variants and PEM corruption logic
  • crates/uselesskey-core-x509-negative/ — new crate: X509Negative and ChainNegative types
  • crates/uselesskey-core/ — slimmed down, now re-exports from microcrates
  • crates/uselesskey-core-jwk/ — slimmed down, delegates to shape/builder/order crates
  • crates/uselesskey-core-negative/ — slimmed down, delegates to negative-pem crate
  • crates/uselesskey-core-token/ — slimmed down, delegates to token-shape crate
  • crates/uselesskey-core-x509/ — negative module delegates to x509-negative crate
  • crates/uselesskey-bdd-steps/ — new BDD steps for core-factory and core-token-shape
  • crates/uselesskey-bdd/features/ — new feature files for core-factory and core-token-shape
  • fuzz/ — 8 new fuzz targets covering the new microcrates
  • xtask/src/plan.rs — updated dependency graph for PR scoping

Evidence

  • Commits: 4
  • Tests: 730 passed, 0 failed
  • Lint: clean (clippy with -D warnings, rustfmt)
  • Files: 100 changed, +5687/-2138 lines

Test Plan

  • cargo xtask test — all 730 tests pass
  • cargo xtask clippy — zero warnings
  • cargo xtask fmt — clean
  • cargo xtask bdd — BDD tests (run in CI with --release for RSA perf)
  • cargo xtask feature-matrix — feature matrix verification (run in CI)
  • cargo xtask fuzz — fuzz the 8 new targets

Unknowns

  • BDD tests for core-factory and core-token-shape were not run locally (requires --release build for RSA keygen performance)
  • Fuzz targets were not exercised beyond compilation — they should be run in CI
  • The fuzz/Cargo.lock is included; confirm this is desired for reproducibility

…stness testing

This commit introduces a new fuzz target in `core_keypair_material.rs` that tests various corruptions of PKCS#8 private keys and SPKI public keys. The fuzz target utilizes a sample key material and checks for handling of bad headers, footers, base64 encoding issues, and extra blank lines. Additionally, it verifies the ability to write the keys back to PEM format and ensures that the key ID is not empty.
…neration

- Added `uselesskey-core-factory` crate for managing artifact generation and caching.
- Implemented `Factory` struct with methods for random and deterministic modes.
- Added caching mechanism to avoid redundant computations.
- Introduced tests for cache behavior, type mismatches, and reentrancy.
- Integrated factory into existing crates and updated dependencies.
- Added BDD steps and feature tests for core factory behavior.
- Created `uselesskey-core-jwk-builder` crate for JWKS composition with deterministic ordering.
- Added property tests for JWKS builder to ensure correct ordering and insertion behavior.
- Implemented fuzzing for factory cache behavior to ensure stability under random inputs.
…itives

- Introduced `uselesskey-core-token-shape` crate to provide low-level token shape generation primitives.
- Implemented functions to generate API keys, bearer tokens, and OAuth access tokens.
- Added tests to ensure stability and correctness of token generation.
- Created README documentation outlining the purpose and usage of the crate.

feat: add uselesskey-core-x509-negative crate for X.509 negative fixture policies

- Introduced `uselesskey-core-x509-negative` crate to manage negative fixture policies for X.509 certificates.
- Implemented various negative certificate and chain variants, including expired and not-yet-valid certificates.
- Added tests to verify the behavior of negative variants and their application to specifications.
- Created README documentation detailing the responsibilities and usage of the crate.

test: add fuzzing targets for various crates

- Added fuzzing targets for `core_hash`, `core_negative_pem`, `core_token_shape`, `core_x509_negative`, `jwk_shape`, and `jwks_order` to enhance robustness.
- Implemented tests to ensure stability and correctness of generated outputs under various input conditions.
Fix proptest char::range API (takes two chars, not a range), temporary
value lifetime in negative-pem tests, clippy redundant-locals and
manual-map warnings, and run rustfmt across all new crates.
Copilot AI review requested due to automatic review settings February 24, 2026 19:40
@gemini-code-assist

Copy link
Copy Markdown

Warning

You have reached your daily quota limit. Please wait up to 24 hours and I will start processing your requests again!

@coderabbitai

coderabbitai Bot commented Feb 24, 2026

Copy link
Copy Markdown

Warning

Rate limit exceeded

@EffortlessSteven has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 0 minutes and 46 seconds before requesting another review.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

📥 Commits

Reviewing files that changed from the base of the PR and between d146300 and be06ee4.

⛔ Files ignored due to path filters (2)
  • Cargo.lock is excluded by !**/*.lock
  • fuzz/Cargo.lock is excluded by !**/*.lock
📒 Files selected for processing (98)
  • Cargo.toml
  • crates/uselesskey-bdd-steps/Cargo.toml
  • crates/uselesskey-bdd-steps/src/lib.rs
  • crates/uselesskey-bdd-steps/src/steps/core_factory_steps.rs
  • crates/uselesskey-bdd-steps/src/steps/core_id_steps.rs
  • crates/uselesskey-bdd-steps/src/steps/core_keypair_steps.rs
  • crates/uselesskey-bdd-steps/src/steps/core_negative_steps.rs
  • crates/uselesskey-bdd-steps/src/steps/core_token_shape_steps.rs
  • crates/uselesskey-bdd/Cargo.toml
  • crates/uselesskey-bdd/features/core-factory.feature
  • crates/uselesskey-bdd/features/core-id.feature
  • crates/uselesskey-bdd/features/core-token-shape.feature
  • crates/uselesskey-bdd/features/jwks.feature
  • crates/uselesskey-core-factory/Cargo.toml
  • crates/uselesskey-core-factory/README.md
  • crates/uselesskey-core-factory/src/lib.rs
  • crates/uselesskey-core-factory/tests/factory_integration.rs
  • crates/uselesskey-core-factory/tests/factory_prop.rs
  • crates/uselesskey-core-hash/Cargo.toml
  • crates/uselesskey-core-hash/README.md
  • crates/uselesskey-core-hash/src/lib.rs
  • crates/uselesskey-core-hash/tests/hash_integration.rs
  • crates/uselesskey-core-id/Cargo.toml
  • crates/uselesskey-core-id/src/lib.rs
  • crates/uselesskey-core-jwk-builder/Cargo.toml
  • crates/uselesskey-core-jwk-builder/README.md
  • crates/uselesskey-core-jwk-builder/src/lib.rs
  • crates/uselesskey-core-jwk-builder/tests/jwk_prop.rs
  • crates/uselesskey-core-jwk-builder/tests/jwks_builder_integration.rs
  • crates/uselesskey-core-jwk-shape/Cargo.toml
  • crates/uselesskey-core-jwk-shape/README.md
  • crates/uselesskey-core-jwk-shape/src/lib.rs
  • crates/uselesskey-core-jwk-shape/tests/integration.rs
  • crates/uselesskey-core-jwk/Cargo.toml
  • crates/uselesskey-core-jwk/README.md
  • crates/uselesskey-core-jwk/src/lib.rs
  • crates/uselesskey-core-jwk/tests/facade_integration.rs
  • crates/uselesskey-core-jwks-order/Cargo.toml
  • crates/uselesskey-core-jwks-order/README.md
  • crates/uselesskey-core-jwks-order/src/lib.rs
  • crates/uselesskey-core-jwks-order/tests/order_integration.rs
  • crates/uselesskey-core-jwks-order/tests/order_prop.rs
  • crates/uselesskey-core-keypair-material/Cargo.toml
  • crates/uselesskey-core-keypair-material/README.md
  • crates/uselesskey-core-keypair-material/src/lib.rs
  • crates/uselesskey-core-keypair-material/tests/material_integration.rs
  • crates/uselesskey-core-keypair/Cargo.toml
  • crates/uselesskey-core-keypair/README.md
  • crates/uselesskey-core-keypair/src/lib.rs
  • crates/uselesskey-core-negative-pem/Cargo.toml
  • crates/uselesskey-core-negative-pem/README.md
  • crates/uselesskey-core-negative-pem/src/lib.rs
  • crates/uselesskey-core-negative-pem/tests/integration.rs
  • crates/uselesskey-core-negative/Cargo.toml
  • crates/uselesskey-core-negative/README.md
  • crates/uselesskey-core-negative/src/lib.rs
  • crates/uselesskey-core-token-shape/Cargo.toml
  • crates/uselesskey-core-token-shape/README.md
  • crates/uselesskey-core-token-shape/src/lib.rs
  • crates/uselesskey-core-token-shape/tests/integration.rs
  • crates/uselesskey-core-token/Cargo.toml
  • crates/uselesskey-core-token/src/lib.rs
  • crates/uselesskey-core-token/tests/integration.rs
  • crates/uselesskey-core-x509-derive/Cargo.toml
  • crates/uselesskey-core-x509-derive/src/lib.rs
  • crates/uselesskey-core-x509-negative/Cargo.toml
  • crates/uselesskey-core-x509-negative/README.md
  • crates/uselesskey-core-x509-negative/src/lib.rs
  • crates/uselesskey-core-x509-negative/tests/integration.rs
  • crates/uselesskey-core-x509-negative/tests/prop.rs
  • crates/uselesskey-core-x509/Cargo.toml
  • crates/uselesskey-core-x509/README.md
  • crates/uselesskey-core-x509/src/negative.rs
  • crates/uselesskey-core/Cargo.toml
  • crates/uselesskey-core/src/derive.rs
  • crates/uselesskey-core/src/factory.rs
  • crates/uselesskey-core/src/factory_tests.rs
  • crates/uselesskey-core/src/lib.rs
  • crates/uselesskey-ecdsa/Cargo.toml
  • crates/uselesskey-ecdsa/src/keypair.rs
  • crates/uselesskey-ed25519/Cargo.toml
  • crates/uselesskey-ed25519/src/keypair.rs
  • crates/uselesskey-feature-grid/src/lib.rs
  • crates/uselesskey-jwk/Cargo.toml
  • crates/uselesskey-jwk/src/lib.rs
  • crates/uselesskey-rsa/Cargo.toml
  • crates/uselesskey-rsa/src/keypair.rs
  • fuzz/Cargo.toml
  • fuzz/fuzz_targets/core_factory_cache.rs
  • fuzz/fuzz_targets/core_hash.rs
  • fuzz/fuzz_targets/core_keypair_material.rs
  • fuzz/fuzz_targets/core_negative_pem.rs
  • fuzz/fuzz_targets/core_token_shape.rs
  • fuzz/fuzz_targets/core_x509_negative.rs
  • fuzz/fuzz_targets/jwk_shape.rs
  • fuzz/fuzz_targets/jwks_order.rs
  • xtask/src/main.rs
  • xtask/src/plan.rs
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feat/core-factory-and-token-shape

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR decomposes the monolithic uselesskey-core crate into focused, independently testable microcrates. The refactoring extracts factory caching, token generation, JWK models, keypair material handling, negative fixture helpers, and hashing utilities into dedicated crates while maintaining backward compatibility through facade re-exports.

Changes:

  • Extracted core factory caching engine into uselesskey-core-factory with deterministic seed derivation
  • Split token generation primitives into uselesskey-core-token-shape (API key, bearer, OAuth)
  • Created 6 supporting microcrates: hash, JWK shape/builder/order, keypair material, negative PEM, X.509 negative
  • Added 8 new fuzz targets and BDD features for isolated testing of the new microcrates
  • Updated dependency graph in xtask and publish ordering to reflect new crate structure

Reviewed changes

Copilot reviewed 98 out of 100 changed files in this pull request and generated no comments.

Show a summary per file
File Description
xtask/src/plan.rs Updated dependency graph tests for new microcrates
xtask/src/main.rs Updated publish order to include new crates
fuzz/fuzz_targets/*.rs 8 new fuzz targets for microcrates
fuzz/Cargo.toml Added dependencies and targets for new fuzz tests
crates/uselesskey-core-factory/ New crate: Factory with cache and seed derivation
crates/uselesskey-core-token-shape/ New crate: Token generation primitives
crates/uselesskey-core-hash/ New crate: BLAKE3 hashing helpers
crates/uselesskey-core-jwk-shape/ New crate: JWK model types
crates/uselesskey-core-jwk-builder/ New crate: JwksBuilder for JWKS composition
crates/uselesskey-core-jwks-order/ New crate: kid-sorted stable ordering
crates/uselesskey-core-keypair-material/ New crate: PKCS#8/SPKI key material helpers
crates/uselesskey-core-negative-pem/ New crate: PEM corruption helpers
crates/uselesskey-core-x509-negative/ New crate: X.509 negative fixture types
crates/uselesskey-core/src/factory.rs Delegates to uselesskey-core-factory
crates/uselesskey-core-token/src/lib.rs Facade re-exporting uselesskey-core-token-shape
crates/uselesskey-core-jwk/src/lib.rs Facade re-exporting uselesskey-core-jwk-shape
crates/uselesskey-core-keypair/src/lib.rs Facade re-exporting uselesskey-core-keypair-material
crates/uselesskey-bdd/features/*.feature New BDD features for core-factory and core-token-shape
crates/uselesskey-bdd-steps/src/steps/*.rs New BDD step implementations
Cargo.toml Workspace members and dependencies for new crates

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: be06ee4a3d

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

assert!(!dbg.contains(secret));
}
}
pub use uselesskey_core_jwk_shape::*;

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Re-export JwksBuilder from core JWK compatibility facade

This facade now only re-exports uselesskey_core_jwk_shape::*, which drops JwksBuilder from the uselesskey-core-jwk public API even though this crate is described as a compatibility layer; downstream code that previously imported uselesskey_core_jwk::JwksBuilder will fail to compile after this change unless they migrate crates immediately.

Useful? React with 👍 / 👎.

uk-default = ["uselesskey/default"]
uk-all = ["uselesskey/full", "uk-rsa", "uk-ecdsa", "uk-ed25519", "uk-hmac", "uk-pgp", "uk-x509", "uk-jwk", "uk-token", "uk-jwt", "uk-core-id", "uk-core-seed", "uk-core-kid", "uk-core-keypair", "uk-core-negative", "uk-core-sink", "uk-aws-lc-rs", "uk-rustls", "uk-tonic", "uk-ring", "uk-rustcrypto"]
uk-core-id = ["dep:uselesskey-core-id"]
uk-all = ["uselesskey/full", "uk-rsa", "uk-ecdsa", "uk-ed25519", "uk-hmac", "uk-pgp", "uk-x509", "uk-jwk", "uk-token", "uk-jwt", "uk-core-id", "uk-core-seed", "uk-core-factory", "uk-core-kid", "uk-core-keypair", "uk-core-negative", "uk-core-sink", "uk-aws-lc-rs", "uk-rustls", "uk-tonic", "uk-ring", "uk-rustcrypto"]

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Include core-token-shape in uk-all feature bundle

The uk-all feature list omits uk-core-token-shape, so enabling uselesskey-bdd-steps/uk-all does not actually enable all core BDD step sets and silently skips token-shape coverage; this creates inconsistent behavior between uk-all and the documented expectation that it enables the full matrix.

Useful? React with 👍 / 👎.

Comment thread xtask/src/plan.rs
Comment on lines 150 to +153
match crate_name {
"uselesskey-core-seed" => &["uselesskey-core-id"],
"uselesskey-core-id" => &["uselesskey-core-cache", "uselesskey-core"],
"uselesskey-core-kid" => &["uselesskey-core-keypair", "uselesskey-hmac"],
"uselesskey-core-keypair" => &["uselesskey-rsa", "uselesskey-ecdsa", "uselesskey-ed25519"],
"uselesskey-core-kid" => &["uselesskey-core-keypair-material", "uselesskey-hmac"],

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Add missing core-factory dependency edge in PR planner

The PR impact graph has no dependents entry for uselesskey-core-factory, even though uselesskey-core depends on it (crates/uselesskey-core/Cargo.toml), so changes limited to uselesskey-core-factory will not mark uselesskey-core (or its downstream crates) as impacted and cargo xtask pr can skip tests that should run.

Useful? React with 👍 / 👎.

@EffortlessSteven EffortlessSteven merged commit 13e201b into main Feb 24, 2026
7 of 8 checks passed
@EffortlessSteven EffortlessSteven deleted the feat/core-factory-and-token-shape branch February 24, 2026 20:01
EffortlessSteven added a commit that referenced this pull request May 11, 2026
Shipper 0.3.0-rc.2 emits the publish plan in alphabetical-looking order
rather than topological order (EffortlessMetrics/shipper#173). With
\`uselesskey-aws-lc-rs\` at position 1 and \`uselesskey-core\` at #2,
shipper's linear walk fails immediately because cargo publish of
aws-lc-rs requires uselesskey-ecdsa (#22) and other deps to already be
on crates.io.

The owner of shipper will fix this in the next patch. Until then,
revert both \`release.yml\` and \`publish-retry.yml\` to use
\`cargo xtask publish\`. The PUBLISH_CRATES order is correct after #565,
and the test-helper dev-dep fix in #569 removes the cargo verification
gap that the original cargo xtask path also tripped over.

Keep \`.shipper/\` in \`.gitignore\` and the existing \`Quality gate\` /
\`Publish preflight\` / \`Publish dry-run\` steps in preflight job —
those are unaffected by the shipper revert and still useful.

After this PR merges, retag v0.7.0 on the new main HEAD and let
\`release.yml\` run end-to-end. shipper#173 stays open for the next
release cycle.
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

Successfully merging this pull request may close these issues.

2 participants