The Ruby reference implementation of the AI2Web protocol - for Rails, Sinatra, Rack, or plain Ruby. Mirrors @ai2web/core.
gem install ai2web
# or add to your Gemfile:
gem "ai2web"require"ai2web"manifest=Ai2Web.ai2web(name: "Example Store",url: "https://example.com",type: "ecommerce").capability("content").capability("commerce",endpoint: "/ai2w/products",checkout: true).transports(mcp: {enabled: true,endpoint: "/ai2w/mcp"},rest: {enabled: true}).auth(methods: %w[noneoauth2],oauth2: {pkce: true,scopes: ["checkout"]}).consent(requires_user_approval_for: ["purchase"]).contact(support: "help@example.com").buildresult=Ai2Web.validate(manifest)# { score: 90+, tier: "Standard", ... }# Serve every AI2Web route from one call (framework-agnostic):res=Ai2Web.handle({manifest: manifest},request.method,request.path,body,origin)# => { status:, headers:, body: } -- render body as JSON (or text for /llms.txt)Inputs may use symbol or string keys - the builder normalises to the string-keyed JSON the
spec defines, so validate also works directly on a JSON.parsed manifest.
| Module | Entry points |
|---|---|
Ai2Web::Manifest | Ai2Web.ai2web(site) - fluent capability-model builder |
Ai2Web::Validator | Ai2Web.validate(manifest) + AI Readiness scoring (spec §9/§11) |
Ai2Web::Negotiator | Ai2Web.negotiate(manifest, agent) capability negotiation (spec §5) |
Ai2Web::Server | Ai2Web.handle(opts, method, path, body, origin) framework-agnostic router |
Ai2Web::Safety | Ai2Web.safe_public_url?(url) / .assert_safe_public_url!(url) SSRF guard |
Ai2Web::Schema | Ai2Web.validate_schema(value, schema) action input validation |
Ai2Web::Export | Ai2Web.to_llms_txt(m) / .to_agent_json(m) projections (RFC-0015) |
The builder also carries the v0.2 optional modules - .governance(...), .usage_policy(...),
.legal(...), .agent_identity(...), .knowledge(...) - and actions accept intent and
bindings. All are additive: a minimal manifest stays valid without them.
res=Ai2Web.handle({manifest: MANIFEST,actions: {"track_order"=>->(body){track(body)}}},env["REQUEST_METHOD"],env["PATH_INFO"],parsed_body,request_origin)body=res[:body].is_a?(String) ? res[:body] : JSON.generate(res[:body])[res[:status],res[:headers],[body]]handle routes /ai2w, /.well-known/ai2w, /llms.txt, /.well-known/agent.json (+ /agent.json),
/ai2w/negotiate, /ai2w/actions/:name and capability modules /ai2w/:name, validating action
input against each action's declared input_schema unless you pass validate_input: false.
ruby test/run.rb # dependency-free; includes the shared conformance contractRequires Ruby 3.0+. Zero runtime dependencies.
MIT.