Include created_at in compact index /info endpoint#6380
Include created_at in compact index /info endpoint#6380marcbest wants to merge 4 commits intorubygems:masterfrom
Conversation
|
📝 We need to pick rubygems/compact_index#183 into this PR after merging #6404 |
d780667 to
eff42b2
Compare
|
@hsbt where are we at with the cooldown discussion on RubyGems CLI? Is this work going ahead? Any idea on timeline? |
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## master #6380 +/- ##
==========================================
- Coverage 97.06% 94.50% -2.56%
==========================================
Files 494 494
Lines 10502 10562 +60
==========================================
- Hits 10194 9982 -212
- Misses 308 580 +272 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
|
@colby-swandale ruby/rubygems#9113 is only place that. But I haven't decided how to implement the cooldown option/configuration yet. |
dcab294 to
5abddbb
Compare
|
We need to handle https://rubygems.org/gems/gem_server_conformance/ for this PR. I will do that at another pull request. |
7fc5b6c to
86e960d
Compare
|
@jenshenny before this merges, I think we need a rollout plan that accounts for a full compact index regeneration, which as far as I know hasn't happened since the initial population. |
Pass the version's created_at timestamp to CompactIndex::GemVersion so it is included in the /info response. The timestamp is formatted as ISO 8601 UTC. This enables Bundler clients to read publication dates from the compact index directly, avoiding separate V1 API calls per gem when implementing supply chain security features like min_age checks. Depends on rubygems/compact_index adding created_at as an optional 8th field to the GemVersion struct.
Add a created_at field to the GemVersion struct so that the /info endpoint can include the publication timestamp for each gem version. When present, created_at is appended to the requirements section of the info line. When nil, the field is omitted for backwards compatibility.
Port the rspec tests from rubygems/compact_index#183 to minitest, covering created_at presence, coexistence with other fields, and nil omission. Co-Authored-By: Claude Opus 4.6 (1M context) <[email protected]>
26c1374 to
d071c63
Compare
The compact index info endpoint now includes created_at timestamps, so the expected output in tests needs to account for this by dynamically including each version's created_at value. Co-Authored-By: Claude Opus 4.6 (1M context) <[email protected]>
d071c63 to
64ae839
Compare
|
Now all of related tests are fixed. |
Problem
Supply chain attacks targeting package registries are a growing concern. Other package managers have already shipped minimum age features — npm, pnpm, and yarn all allow users to reject recently published versions during resolution.
Bundler currently has no equivalent. Adding one requires knowing when each gem version was published, but the compact index has no publication timestamp. Without it, clients must make a separate V1 API call per gem (
/api/v1/versions/<gem>.json) — adding seconds of latency and hitting the RubyGems.org rate limit (10 req/s) on projects with 50+ gems.The compact index
/infoendpoint already carries all the version data Bundler needs during resolution — exceptcreated_at.Solution
Pass the version's
created_at(already in the SQL query) toCompactIndex::GemVersion.newas the 8th argument, formatted as ISO 8601 UTC.Before:
After:
The
created_atcolumn is already selected in therequirements_and_dependenciesquery, included in theGROUP BY, and used forORDER BY. It just wasn't being passed through.Info line output
Old clients ignore unknown requirement fields, so this is fully backwards compatible.
Dependencies
Requires rubygems/compact_index#183 — adds
created_atas an optional 8th field toGemVersionstruct.