You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: README.md
+57-51Lines changed: 57 additions & 51 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,24 +1,29 @@
1
1
# Vein 💎
2
2
3
-
A fast, intelligent RubyGems proxy/mirror server. Part of the ore ecosystem alongside [ore-light](https://github.com/contriboss/ore-light).
3
+
A fast, intelligent multi-ecosystem package proxy/mirror server (RubyGems, crates.io, npm; Python next).
4
+
5
+
**Single endpoint:** Bundler and Ore point to the same Vein URL. The same base URL can also serve Cargo (sparse index + crate downloads) and npm (metadata + tarballs) via path/header detection. Upstream configuration applies to RubyGems only; crates.io and npm use fixed upstreams.
4
6
5
7
## What is Vein?
6
8
7
-
Vein is a **smart caching proxy** for RubyGems that:
9
+
Vein is a **smart caching proxy** for multiple package ecosystems that:
8
10
9
-
- Proxies rubygems.org with local caching
10
-
- Serves gems from local cache when available
11
-
- Only fetches from upstream on cache miss
11
+
- Proxies RubyGems via a configurable upstream
12
+
- Mirrors crates.io (sparse index + crate downloads) with caching
13
+
- Proxies npm registry metadata and tarballs with caching
14
+
- Serves cached artifacts from local storage on repeat requests
15
+
- Runs in cache-only mode when no RubyGems upstream is configured
12
16
- Built on Rama (modular service framework)
13
-
-Zero configuration - just works™
17
+
-Minimal configuration - just works for common setups
14
18
15
19
## Why Vein?
16
20
17
21
-**Blazing Fast**: High-performance proxy with Rama
18
-
-**Smart Caching**: Proxy once, serve forever from local cache
19
-
-**Supply Chain Protection**: Optional quarantine delays for new gem versions
20
-
-**Minimal Config**: Works out of the box, configure only what you need
22
+
-**Smart Caching**: Cache artifacts once and serve locally thereafter
23
+
-**Supply Chain Protection**: Quarantine system (RubyGems today; expanding across ecosystems)
24
+
-**Minimal Config**: Cache-only by default; enable RubyGems upstream when needed
21
25
-**Simple Deployment**: Single binary, no complex dependencies
26
+
-**Multi-registry endpoint**: RubyGems + crates.io + npm on one base URL
22
27
-**Ore Integration**: Works seamlessly with ore-light's fallback mechanism
23
28
24
29
## Quick Start
@@ -41,31 +46,32 @@ cargo build --release
41
46
```
42
47
Client Request → Vein → Local Cache?
43
48
├─ Hit → Serve from filesystem
44
-
└─ Miss → Fetch from rubygems.org
49
+
└─ Miss → Fetch from upstream (RubyGems / crates.io / npm)
45
50
├─ Cache locally
46
51
└─ Serve to client
47
52
```
48
53
49
-
**Permanent Caching**: Once a gem is cached, it's served locally forever. No re-fetching.
54
+
**Permanent Caching**: Artifact files (gems, crates, npm tarballs) are cached on first fetch and served locally thereafter. Index/metadata endpoints are cached with TTL + revalidation.
50
55
51
-
**Simple Architecture**: SQLite for metadata + filesystem for gem files.
56
+
**Simple Architecture**: SQLite (default) or PostgreSQL for metadata + filesystem for cached artifacts (default storage root: `./cache`).
-[x] Filesystem storage (default `./cache/` with per-ecosystem subfolders)
58
63
-[x] Smart cache resolver
59
64
-[x] Stream-through caching (cache while serving)
60
65
-[x] SHA256 verification
61
66
-[x] Minimal configuration
62
67
-[x] Docker image
63
-
-[x]Gem name/version/platform parsing
68
+
-[x]Package name/version/platform parsing
64
69
-[x] Request logging with metrics
65
70
-[x] Cache revalidation on corruption
66
-
-[x] Legacy API rejection (with monitoring)
67
-
-[x] CycloneDX SBOM extraction with admin preview & download API
68
-
-[x] Quarantine system (supply chain attack protection)
71
+
-[x] crates.io sparse index + crate download caching
72
+
-[x] npm registry metadata + tarball caching
73
+
-[x] CycloneDX SBOM extraction with admin preview & download API (RubyGems today; expanding)
74
+
-[x] Quarantine system (supply chain attack protection, RubyGems today; expanding)
69
75
70
76
### Usage
71
77
@@ -77,16 +83,16 @@ host = "0.0.0.0"
77
83
port = 8346
78
84
79
85
[upstream]
80
-
url = "https://rubygems.org"
86
+
url = "https://rubygems.org" # RubyGems only (crates.io + npm are fixed upstreams)
81
87
82
88
[storage]
83
-
path = "./gems"
89
+
path = "./cache"
84
90
85
91
[database]
86
92
path = "./vein.db"
87
93
TOML
88
94
89
-
# Start the proxy (streams uncached gems through Rama)
95
+
# Start the proxy (streams uncached artifacts through Rama)
90
96
cargo run -- serve --config vein.toml
91
97
92
98
# Inspect cache statistics
@@ -95,12 +101,16 @@ cargo run -- stats --config vein.toml
95
101
96
102
### CycloneDX SBOM access
97
103
104
+
**Scope:** SBOMs are currently generated for cached RubyGems. The roadmap is to extend SBOM generation to all supported ecosystems (crates.io, npm, and Python).
105
+
98
106
-**Admin dashboard**: start `make admin` then browse to `http://127.0.0.1:9400/catalog/<gem>?version=<version>` to preview the generated SBOM and download the JSON directly from the UI.
99
107
-**Proxy endpoint**: any client can fetch the SBOM without the admin UI by calling `GET /.well-known/vein/sbom?name=<gem>&version=<version>[&platform=<platform>]` against the running Vein proxy. The response is a CycloneDX 1.5 document with `Content-Type: application/json` and a download-friendly filename. Omit the `platform` query for default `ruby` builds; supply it for native variants (e.g. `arm64-darwin`).
100
108
- SBOMs are generated automatically the first time a gem is cached and refreshed whenever the gem is re-fetched.
101
109
102
110
### Quarantine (Supply Chain Protection)
103
111
112
+
**Scope:** Quarantine is currently applied to RubyGems metadata/index responses. The roadmap is to apply the same protection to crates.io, npm, and Python.
113
+
104
114
Vein can delay new gem versions from appearing in Bundler's index, giving the community time to catch malicious packages before they reach your CI/CD.
105
115
106
116
**How it works:**
@@ -121,15 +131,18 @@ Vein can delay new gem versions from appearing in Bundler's index, giving the co
121
131
enabled = true
122
132
default_delay_days = 3
123
133
skip_weekends = true# Don't release on Sat/Sun
134
+
business_hours_only = true# Only release during business hours
124
135
release_hour_utc = 10# Release at 10:00 UTC
125
136
126
137
# Per-gem overrides (glob patterns supported)
127
138
[[delay_policy.gems]]
128
-
pattern = "rails*"
139
+
name = "rails*"
140
+
pattern = true
129
141
delay_days = 7# Extra scrutiny for Rails ecosystem
130
142
131
143
[[delay_policy.gems]]
132
-
pattern = "internal-*"
144
+
name = "internal-*"
145
+
pattern = true
133
146
delay_days = 0# Trust internal gems
134
147
135
148
# Pin specific versions for immediate availability
Together they provide a complete, modern Ruby dependency management ecosystem:
360
366
- ore-light handles dependency resolution and installation
@@ -380,7 +386,7 @@ Vein is built on [Rama](https://github.com/plabayo/rama), a modular service fram
380
386
381
387
**Project Status**: Vein is a **side project** and will remain free and open source. It is not commercialized.
382
388
383
-
**HTTP Features**: Intentionally basic. Vein does what it needs to do: proxy, cache, serve gems. No plans to add complex HTTP features or enterprise-grade capabilities.
389
+
**HTTP Features**: Intentionally basic. Vein does what it needs to do: proxy, cache, serve packages. No plans to add complex HTTP features or enterprise-grade capabilities.
384
390
385
391
**Need More?** Companies requiring additional features (advanced routing, auth, monitoring, protocol extensions) should **hire Plabayo directly** to extend Vein:
386
392
- Extensions can be public (contributed upstream) or private (internal forks)
0 commit comments