{"_id":"@amtp/protocol","_rev":"5-8ebe37e8af92394bf02d4ba33320fb25","name":"@amtp/protocol","dist-tags":{"latest":"1.0.6"},"versions":{"1.0.1":{"name":"@amtp/protocol","version":"1.0.1","keywords":["amtp","protocol","agents","markdown","http","web","api","semantic","rfc"],"author":{"name":"AMTP Contributors"},"license":"MIT","_id":"@amtp/protocol@1.0.1","maintainers":[{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"}],"homepage":"https://github.com/amtp/protocol#readme","bugs":{"url":"https://github.com/amtp/protocol/issues"},"dist":{"shasum":"93a6dd66fdc4c6e9809eb590f398a5aa9f648686","tarball":"https://registry.npmjs.org/@amtp/protocol/-/protocol-1.0.1.tgz","fileCount":53,"integrity":"sha512-hVPVAmHosi2ignEEkbAZDh34fe1Wwb9NWghGfMi3Bcqi/qRZuPej2ZP7xlVMVuxbHWXjmEhhqsGStl043SKITA==","signatures":[{"sig":"MEQCIAfngimYxJ7SENNs78tWPlmKpc/+hSrycdgDL7O7JgKDAiATIQed6kbBEIW756mSqmeFdafTekpcOPsIX47keaQwfQ==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":383139},"main":"dist/index.js","types":"dist/index.d.ts","engines":{"npm":">=9.0.0","node":">=18.0.0"},"gitHead":"9d4bb4e969aef1d22d22252d791162055863ef3d","scripts":{"dev":"tsc --watch","amtp":"ts-node bin/amtp.ts","docs":"typedoc --out docs src/","lint":"eslint src/**/*.ts","test":"jest","bench":"ts-node bench/bench.ts","build":"tsc","client":"ts-node src/client/examples/basic-client.ts","server":"ts-node src/server/examples/basic-server.ts","crawler":"ts-node src/crawler/examples/basic-crawler.ts","validate":"npm run type-check && npm run build && npm test","test:watch":"jest --watch","type-check":"tsc --noEmit","server:saas":"ts-node src/server/examples/saas-dashboard-server.ts","test:coverage":"jest --coverage","security-audit":"npm audit"},"_npmUser":{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"},"repository":{"url":"git+https://github.com/amtp/protocol.git","type":"git"},"_npmVersion":"11.9.0","description":"AMTP: Agent Markdown Transfer Protocol - HTTP for the Agentic Web","directories":{},"_nodeVersion":"24.14.0","dependencies":{"cors":"^2.8.5","express":"^4.18.2","sqlite3":"^6.0.1","compression":"^1.7.4"},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^29.5.0","chalk":"^5.6.2","eslint":"^8.40.0","fastify":"^5.8.5","ts-jest":"^29.1.0","ts-node":"^10.9.1","typedoc":"^0.24.0","bcryptjs":"^2.4.3","commander":"^14.0.3","supertest":"^7.2.2","typescript":"^5.0.0","@types/jest":"^29.5.0","@types/node":"^20.0.0","jsonwebtoken":"^9.0.0","@types/bcrypt":"^6.0.0","@types/express":"^4.17.17","@types/supertest":"^7.2.0","@types/compression":"^1.8.1","@types/jsonwebtoken":"^9.0.10","@typescript-eslint/parser":"^5.59.0","@typescript-eslint/eslint-plugin":"^5.59.0"},"_npmOperationalInternal":{"tmp":"tmp/protocol_1.0.1_1779512269812_0.22954225300962006","host":"s3://npm-registry-packages-npm-production"}},"1.0.2":{"name":"@amtp/protocol","version":"1.0.2","keywords":["amtp","protocol","agents","markdown","http","web","api","semantic","rfc"],"author":{"name":"AMTP Contributors"},"license":"MIT","_id":"@amtp/protocol@1.0.2","maintainers":[{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"}],"homepage":"https://github.com/sumeetingenuity/amtp#readme","bugs":{"url":"https://github.com/sumeetingenuity/amtp/issues"},"dist":{"shasum":"4a8b2a02f2571d3e6ece2ee09f77b98c27425637","tarball":"https://registry.npmjs.org/@amtp/protocol/-/protocol-1.0.2.tgz","fileCount":53,"integrity":"sha512-I49wmxoBLb3DIj55Mga6vkzS+wh5Vx62GpQKdDyQW7YYHP+OCSYS7r9DJscztmEGi7Uqj0/phmhubGV6r5JmNw==","signatures":[{"sig":"MEQCIG3+vcHAZKIJrkqLiShE5K+64vQNv8haFbbuZ+8CW15BAiBfqaMJjmM2CvMs7+OxF6qrQn9K+wkDNNbqxVe2gnXO1g==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":383190},"main":"dist/index.js","types":"dist/index.d.ts","engines":{"npm":">=9.0.0","node":">=18.0.0"},"gitHead":"e57f3b9c6d40131ee5bca94b290a60deb6244e89","scripts":{"dev":"tsc --watch","amtp":"ts-node bin/amtp.ts","docs":"typedoc --out docs src/","lint":"eslint src/**/*.ts","test":"jest","bench":"ts-node bench/bench.ts","build":"tsc","client":"ts-node src/client/examples/basic-client.ts","server":"ts-node src/server/examples/basic-server.ts","crawler":"ts-node src/crawler/examples/basic-crawler.ts","validate":"npm run type-check && npm run build && npm test","test:watch":"jest --watch","type-check":"tsc --noEmit","server:saas":"ts-node src/server/examples/saas-dashboard-server.ts","test:coverage":"jest --coverage","security-audit":"npm audit"},"_npmUser":{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"},"repository":{"url":"git+https://github.com/sumeetingenuity/amtp.git","type":"git"},"_npmVersion":"11.9.0","description":"AMTP: Agent Markdown Transfer Protocol - HTTP for the Agentic Web","directories":{},"_nodeVersion":"24.14.0","dependencies":{"cors":"^2.8.5","express":"^4.18.2","sqlite3":"^6.0.1","compression":"^1.7.4"},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^29.5.0","chalk":"^5.6.2","eslint":"^8.40.0","fastify":"^5.8.5","ts-jest":"^29.1.0","ts-node":"^10.9.1","typedoc":"^0.24.0","bcryptjs":"^2.4.3","commander":"^14.0.3","supertest":"^7.2.2","typescript":"^5.0.0","@types/jest":"^29.5.0","@types/node":"^20.0.0","jsonwebtoken":"^9.0.0","@types/bcrypt":"^6.0.0","@types/express":"^4.17.17","@types/supertest":"^7.2.0","@types/compression":"^1.8.1","@types/jsonwebtoken":"^9.0.10","@typescript-eslint/parser":"^5.59.0","@typescript-eslint/eslint-plugin":"^5.59.0"},"_npmOperationalInternal":{"tmp":"tmp/protocol_1.0.2_1779512542261_0.5163942240287684","host":"s3://npm-registry-packages-npm-production"}},"1.0.3":{"name":"@amtp/protocol","version":"1.0.3","keywords":["amtp","protocol","agents","markdown","http","web","api","semantic","rfc"],"author":{"name":"AMTP Contributors"},"license":"MIT","_id":"@amtp/protocol@1.0.3","maintainers":[{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"}],"homepage":"https://github.com/sumeetingenuity/amtp#readme","bugs":{"url":"https://github.com/sumeetingenuity/amtp/issues"},"dist":{"shasum":"602346027f559805eccd4259786cc3a466d64048","tarball":"https://registry.npmjs.org/@amtp/protocol/-/protocol-1.0.3.tgz","fileCount":56,"integrity":"sha512-G0jcdU/DGuYFNKBEFKJ90Ic1T3N0TamP32P2C0j1Cl7e/1BYYaXNLazbvDZL2opx53Rl5EQjcaF/MA24bK5CiQ==","signatures":[{"sig":"MEYCIQDyUOV0/HczZ45IJfSbwgESvqkoOKcIfUoGx0rSXZPebwIhAOSS+gnQn73Wv8DmvrQq6+Ri3zMiFYb/y60zsLjZjg4L","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":395388},"main":"dist/index.js","types":"dist/index.d.ts","engines":{"npm":">=9.0.0","node":">=18.0.0"},"gitHead":"5fdd48f0a59c95fc7fbddebabd14ac8601f0d5fc","scripts":{"dev":"tsc --watch","amtp":"ts-node bin/amtp.ts","docs":"typedoc --out docs src/","lint":"eslint src/**/*.ts","test":"jest","bench":"ts-node bench/bench.ts","build":"tsc","client":"ts-node src/client/examples/basic-client.ts","server":"ts-node src/server/examples/basic-server.ts","crawler":"ts-node src/crawler/examples/basic-crawler.ts","validate":"npm run type-check && npm run build && npm test","test:watch":"jest --watch","type-check":"tsc --noEmit","server:saas":"ts-node src/server/examples/saas-dashboard-server.ts","test:coverage":"jest --coverage","security-audit":"npm audit"},"_npmUser":{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"},"repository":{"url":"git+https://github.com/sumeetingenuity/amtp.git","type":"git"},"_npmVersion":"11.9.0","description":"AMTP: Agent Markdown Transfer Protocol - HTTP for the Agentic Web","directories":{},"_nodeVersion":"24.14.0","dependencies":{"cors":"^2.8.5","express":"^4.18.2","sqlite3":"^6.0.1","compression":"^1.7.4"},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^29.5.0","chalk":"^5.6.2","eslint":"^8.40.0","fastify":"^5.8.5","ts-jest":"^29.1.0","ts-node":"^10.9.1","typedoc":"^0.24.0","bcryptjs":"^2.4.3","commander":"^14.0.3","supertest":"^7.2.2","typescript":"^5.0.0","@types/jest":"^29.5.0","@types/node":"^20.0.0","jsonwebtoken":"^9.0.0","@types/bcrypt":"^6.0.0","@types/express":"^4.17.17","@types/supertest":"^7.2.0","@types/compression":"^1.8.1","@types/jsonwebtoken":"^9.0.10","@typescript-eslint/parser":"^5.59.0","@typescript-eslint/eslint-plugin":"^5.59.0"},"_npmOperationalInternal":{"tmp":"tmp/protocol_1.0.3_1779548716667_0.8585787212384588","host":"s3://npm-registry-packages-npm-production"}},"1.0.5":{"name":"@amtp/protocol","version":"1.0.5","keywords":["amtp","protocol","agents","markdown","http","web","api","semantic","rfc"],"author":{"name":"AMTP Contributors"},"license":"MIT","_id":"@amtp/protocol@1.0.5","maintainers":[{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"}],"homepage":"https://github.com/sumeetingenuity/amtp#readme","bugs":{"url":"https://github.com/sumeetingenuity/amtp/issues"},"dist":{"shasum":"0064377a5987b908ce8787a7e502d0ad73f490ce","tarball":"https://registry.npmjs.org/@amtp/protocol/-/protocol-1.0.5.tgz","fileCount":62,"integrity":"sha512-A3tNGDYlJjW1A1u6xAMQ2WzdSkxNHp6XlbD8NfT9DOJx+5ox9nBp8HGlW+/vSbgIe4x62NZ7EETw8pB/uX5ODg==","signatures":[{"sig":"MEYCIQCd/UL2qv4B+eE/nEpbBNHYwdGvvx+/rAn8I0rxoFp9YQIhAMx/rXmWW/9NfqPbGRjOTruUT9FaZVDhKXAgzn4TffNh","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":409716},"main":"dist/index.js","types":"dist/index.d.ts","engines":{"npm":">=9.0.0","node":">=18.0.0"},"gitHead":"8bbe258a478635e34a2dfee23211176a792016af","scripts":{"dev":"tsc --watch","amtp":"ts-node bin/amtp.ts","docs":"typedoc --out docs src/","lint":"eslint src/**/*.ts","test":"jest","bench":"ts-node bench/bench.ts","build":"tsc","client":"ts-node src/client/examples/basic-client.ts","server":"ts-node src/server/examples/basic-server.ts","crawler":"ts-node src/crawler/examples/basic-crawler.ts","validate":"npm run type-check && npm run build && npm test","test:watch":"jest --watch","type-check":"tsc --noEmit","server:saas":"ts-node src/server/examples/saas-dashboard-server.ts","test:coverage":"jest --coverage","security-audit":"npm audit"},"_npmUser":{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"},"repository":{"url":"git+https://github.com/sumeetingenuity/amtp.git","type":"git"},"_npmVersion":"11.9.0","description":"AMTP: Agent Markdown Transfer Protocol - HTTP for the Agentic Web","directories":{},"_nodeVersion":"24.14.0","dependencies":{"cors":"^2.8.5","express":"^4.18.2","sqlite3":"^6.0.1","compression":"^1.7.4"},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^29.5.0","chalk":"^5.6.2","eslint":"^8.40.0","fastify":"^5.8.5","ts-jest":"^29.1.0","ts-node":"^10.9.1","typedoc":"^0.24.0","bcryptjs":"^2.4.3","commander":"^14.0.3","supertest":"^7.2.2","typescript":"^5.0.0","@types/jest":"^29.5.0","@types/node":"^20.0.0","jsonwebtoken":"^9.0.0","@types/bcrypt":"^6.0.0","@types/express":"^4.17.17","@types/supertest":"^7.2.0","@types/compression":"^1.8.1","@types/jsonwebtoken":"^9.0.10","@typescript-eslint/parser":"^5.59.0","@typescript-eslint/eslint-plugin":"^5.59.0"},"_npmOperationalInternal":{"tmp":"tmp/protocol_1.0.5_1779608276809_0.1358323719315404","host":"s3://npm-registry-packages-npm-production"}},"1.0.6":{"name":"@amtp/protocol","version":"1.0.6","description":"AMTP: Agent Markdown Transfer Protocol - HTTP for the Agentic Web","main":"dist/index.js","types":"dist/index.d.ts","publishConfig":{"access":"public"},"scripts":{"build":"tsc","dev":"tsc --watch","test":"jest","test:watch":"jest --watch","test:coverage":"jest --coverage","lint":"eslint src/**/*.ts","type-check":"tsc --noEmit","validate":"npm run type-check && npm run build && npm test","security-audit":"npm audit","server":"ts-node src/server/examples/basic-server.ts","server:saas":"ts-node src/server/examples/saas-dashboard-server.ts","client":"ts-node src/client/examples/basic-client.ts","crawler":"ts-node src/crawler/examples/basic-crawler.ts","docs":"typedoc --out docs src/","bench":"ts-node bench/bench.ts","amtp":"ts-node bin/amtp.ts"},"keywords":["amtp","protocol","agents","markdown","http","web","api","semantic","rfc"],"author":{"name":"AMTP Contributors"},"license":"MIT","dependencies":{"compression":"^1.7.4","cors":"^2.8.5","express":"^4.18.2","sqlite3":"^6.0.1"},"devDependencies":{"@types/bcrypt":"^6.0.0","@types/compression":"^1.8.1","@types/express":"^4.17.17","@types/jest":"^29.5.0","@types/jsonwebtoken":"^9.0.10","@types/node":"^20.0.0","@types/supertest":"^7.2.0","@typescript-eslint/eslint-plugin":"^5.59.0","@typescript-eslint/parser":"^5.59.0","bcryptjs":"^2.4.3","chalk":"^5.6.2","commander":"^14.0.3","eslint":"^8.40.0","fastify":"^5.8.5","jest":"^29.5.0","jsonwebtoken":"^9.0.0","supertest":"^7.2.2","ts-jest":"^29.1.0","ts-node":"^10.9.1","typedoc":"^0.24.0","typescript":"^5.0.0"},"engines":{"node":">=18.0.0","npm":">=9.0.0"},"repository":{"type":"git","url":"git+https://github.com/sumeetingenuity/amtp.git"},"bugs":{"url":"https://github.com/sumeetingenuity/amtp/issues"},"homepage":"https://github.com/sumeetingenuity/amtp#readme","gitHead":"99d1ffa4693192bd862a4da62a1e0dc6180db0ff","_id":"@amtp/protocol@1.0.6","_nodeVersion":"24.14.0","_npmVersion":"11.9.0","dist":{"integrity":"sha512-K0BLoEWRhFBvYKorniEzy6jtR8AF8pMTHg0heLrcnVkNDflkEKi717gzgn5SNmt3nR7axj0KguSg8EhthVfNQg==","shasum":"fb117c612fc1e97ea8ec10fd6c0b52c5d3036fc8","tarball":"https://registry.npmjs.org/@amtp/protocol/-/protocol-1.0.6.tgz","fileCount":62,"unpackedSize":409716,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEUCIQCybgq6b05662bUT2NpuAq3qFnRWiyU2hz0mTSJDHQMiwIgCMsie1F9lQLhqhyy9uYySP+JWL3n32jkQ9WjxH4Ehp8="}]},"_npmUser":{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"},"directories":{},"maintainers":[{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/protocol_1.0.6_1779609759057_0.3385669767455899"},"_hasShrinkwrap":false}},"time":{"created":"2026-05-23T04:57:49.620Z","modified":"2026-05-24T08:02:39.340Z","1.0.1":"2026-05-23T04:57:49.961Z","1.0.2":"2026-05-23T05:02:22.444Z","1.0.3":"2026-05-23T15:05:16.818Z","1.0.5":"2026-05-24T07:37:56.956Z","1.0.6":"2026-05-24T08:02:39.218Z"},"bugs":{"url":"https://github.com/sumeetingenuity/amtp/issues"},"author":{"name":"AMTP Contributors"},"license":"MIT","homepage":"https://github.com/sumeetingenuity/amtp#readme","keywords":["amtp","protocol","agents","markdown","http","web","api","semantic","rfc"],"repository":{"type":"git","url":"git+https://github.com/sumeetingenuity/amtp.git"},"description":"AMTP: Agent Markdown Transfer Protocol - HTTP for the Agentic Web","maintainers":[{"name":"sumeetingenuity","email":"sumeetingenuity@gmail.com"}],"readme":"# AMTP: Agent Markdown Transfer Protocol\n\n**HTTP for the Agentic Web**\n\nA production-grade, markdown-first protocol for AI agents and headless browsers to interact with web services without requiring DOM rendering, CSS engines, or JavaScript execution.\n\n## 🎯 Vision\n\nEnable AI agents to browse the web efficiently by providing:\n\n- **Semantic Markdown** instead of HTML\n- **Deterministic Structure** for machine parsing\n- **Token Efficiency** for LLM consumption\n- **Hypermedia Navigation** built-in\n- **Streaming Updates** in real-time\n- **Session Awareness** for stateful workflows\n- **Action-First Design** with zero DOM clicks\n\n## ⚡ Quick Start\n\n### Installation\n\n```bash\nnpm install @amtp/protocol\n```\n\n### Using the Agent Client\n\n```typescript\nimport { AMTPClient } from \"@amtp/protocol\";\n\nconst client = new AMTPClient({\n  baseUrl: \"https://example.com\",\n  capabilities: [\"actions\", \"streaming\", \"forms\"],\n});\n\n// Fetch a page\nconst page = await client.getPage(\"/products/mbp-14\");\nconsole.log(page.title); // \"MacBook Pro 14\"\"\n\n// Execute an action\nconst result = await client.executeAction(\"buy\", {\n  productId: \"mbp-14\",\n  quantity: 1,\n  paymentMethod: \"credit_card\",\n});\n\n// Submit a form\nawait client.submitForm(checkoutForm, {\n  email: \"user@example.com\",\n  address: \"123 Main St\",\n});\n\n// Stream real-time updates\nclient.streamUpdates(\"/api/stream/order\", (update) => {\n  console.log(\"Order status:\", update);\n});\n```\n\n### Building an AMTP Server\n\n```typescript\nimport { AMTPServer } from \"@amtp/protocol\";\n\nconst server = new AMTPServer({\n  port: 3000,\n  enableCORS: true,\n  enableCompression: true,\n});\n\nserver.register(\"GET\", \"/products/:id\", async (req, res) => {\n  const productId = req.params.id;\n  const product = await fetchProduct(productId);\n\n  const amtpDoc = {\n    type: \"document\",\n    title: product.name,\n    actions: [\n      { id: \"buy\", label: \"BUY\", method: \"POST\", endpoint: \"/api/buy\" },\n    ],\n    links: [\n      { text: \"Reviews\", url: `/products/${productId}/reviews` },\n    ],\n  };\n\n  res.json(amtpDoc);\n});\n\nserver.start();\n```\n\n### Authenticated Agents (Website Chatbot)\n\nFor website chatbots and agents that act on behalf of logged-in users, AMTP\nauto-bridges your existing web auth — no separate token ceremony for end users.\n\n```typescript\nimport { AMTPServer, WebSessionAdapter, SessionManager } from \"@amtp/protocol\";\n\nconst server = new AMTPServer({ port: 3000 });\n\nconst adapter = new WebSessionAdapter({\n  sessionManager: server.getSessionManager(),\n  resolveUser: (req) => {\n    // req.user is populated by Passport, Express session, JWT, etc.\n    if (!req.user) return null;\n    return {\n      id: req.user.id,\n      username: req.user.displayName,\n      role: req.user.role,\n      // Only fields you project here reach the agent — never raw secrets\n    };\n  },\n});\n\n// Mount AFTER your auth middleware (Passport, session, etc.)\nserver.useWebSession(adapter);\n\nserver.register(\"POST\", \"/api/orders\", (req, res) => {\n  const session = (req as any).amtpContext?.session;\n  // session.userId is the authenticated user —\n  // no token config needed from the end user\n  res.json({ userId: session.userId });\n});\n\nserver.start();\n```\n\n### Crawling AMTP Sites\n\n```typescript\nimport { AMTPCrawler } from \"@amtp/protocol\";\n\nconst crawler = new AMTPCrawler({\n  baseUrl: \"https://example.com\",\n  maxPages: 10000,\n  maxDepth: 5,\n});\n\nconst pages = await crawler.crawl();\nconsole.log(`Crawled ${pages.length} pages`);\n\n// Search the index\nconst results = crawler.search(\"macbook pro\");\n```\n\n### Migrating Existing Backends to AMTP\n\nAdd AMTP to your existing Express/Fastify backend without rewriting routes.\nDefine a data-to-AMTP schema, wrap your handler — agents get AMTP markdown,\nbrowsers get HTML, API clients get JSON — all from one route.\n\n```typescript\nimport { amtp } from \"@amtp/protocol\";\n\n// 1. Define how your data maps to AMTP\nconst ProductPage = amtp.define<Product>({\n  title: (p) => p.name,\n  description: (p) => `$${p.price} · ${p.inStock ? \"In Stock\" : \"Out of Stock\"}`,\n  fields: [\n    { label: \"Category\", value: (p) => p.category },\n    { label: \"Rating\", value: (p) => `${p.rating}/5` },\n  ],\n  actions: [\n    { id: \"BUY\", label: \"Buy\", method: \"POST\", endpoint: (p) => `/api/products/${p.id}/buy\" },\n    { id: \"REVIEWS\", label: \"Reviews\", method: \"GET\", endpoint: (p) => `/products/${p.id}/reviews\" },\n  ],\n});\n\n// 2. Wrap your route handler — agents discover actions, browsers see HTML\nrouter.get(\"/products/:id\", amtp.route(ProductPage, async (req) => {\n  return await db.findOne(req.params.id);\n}));\n\n// No migration? Use amtp.respond() inside existing res.json() handlers:\nrouter.get(\"/products/:id\", async (req, res) => {\n  const product = await db.findOne(req.params.id);\n  res.json(product);\n  // Later, add one line:\n  // if (req.headers.accept?.includes(\"amtp\")) amtp.respond(res, product, ProductPage);\n});\n```\n\n### Cross-Origin Agent Delegation (OAuth 2.0)\n\nFor the future where users interact with any website through a single agent\n(ChatGPT, Claude, DeepSeek, etc.), AMTP supports OAuth 2.0 delegation:\n\n**Server** — advertises auth requirements via the `amtp-auth` block:\n\n```markdown\n# My Orders\n\n[VIEW_ORDER] [CANCEL_ORDER]\n\n```amtp-auth\n{\n  \"provider\": \"example\",\n  \"authorizationUrl\": \"https://example.com/oauth/authorize\",\n  \"tokenUrl\": \"https://example.com/oauth/token\",\n  \"scopes\": [\"orders:read\", \"orders:write\"],\n  \"pkce\": true,\n  \"introspectionUrl\": \"/amtp/auth/introspect\"\n}\n```\n```\n\n**Agent** — discovers the auth block, redirects the user to authorize, then\nuses the Bearer token for authenticated requests:\n\n```typescript\nimport { AMTPAuthService } from \"@amtp/protocol\";\n\nconst authService = new AMTPAuthService({\n  sessionManager: server.getSessionManager(),\n  verifier: {\n    verify: async (token) => {\n      const payload = jwt.verify(token, process.env.JWT_SECRET!);\n      return {\n        userId: payload.sub,\n        username: payload.username,\n        scopes: (payload.scope || \"\").split(\" \"),\n      };\n    },\n  },\n});\n\n// Mounts auth middleware + registers POST /amtp/auth/introspect\nserver.useAuthService(authService);\n\n// Protected route — requires \"orders:read\" scope\nserver.register(\"GET\", \"/api/orders\", (req, res) => {\n  const session = (req as any).amtpContext?.session;\n  if (!session?.capabilities.includes(\"orders:read\")) {\n    return res.status(403).json({ error: \"insufficient scope\" });\n  }\n  res.json({ orders: fetchOrders(session.userId) });\n});\n```\n\n**Security model:**\n- Actions declare required scopes via `authScope` (e.g. `authScope: \"orders:write\"`)\n- `PermissionGuard` checks the session's capabilities against the action's `authScope`\n- Token verification is pluggable — JWT, opaque tokens, or custom verifiers\n- No raw tokens or secrets are ever exposed to the AMTP context\n\n## 📚 Documentation\n\n### Core Specifications\n- [**AMTP RFC** - Full Protocol Specification](./spec/AMTP-RFC.md)\n- [**Markdown Grammar** - Formal EBNF Grammar](./spec/MARKDOWN-GRAMMAR.md)\n- [**Advanced Features** - Sessions, Streaming, Security](./spec/ADVANCED-FEATURES.md)\n\n### Implementations\n- [**Server Implementation** - Express middleware & server](./src/server/)\n- [**Client SDK** - Agent client library](./src/client/)\n- [**Crawler** - Website crawler & indexer](./src/crawler/)\n\n### Examples & Reference\n- [**Real-World Examples** - E-commerce, SaaS, search](./reference-implementations/EXAMPLES.md)\n- [**TypeScript Types** - Protocol type definitions](./src/types/amtp.types.ts)\n\n## 🏗️ Project Structure\n\n```\nAMTP/\n├── spec/\n│   ├── AMTP-RFC.md                 # Full RFC specification\n│   ├── MARKDOWN-GRAMMAR.md         # Markdown grammar & parsing\n│   ├── ADVANCED-FEATURES.md        # Sessions, streaming, security\n│   └── protocols/                  # Protocol versions\n├── src/\n│   ├── types/\n│   │   └── amtp.types.ts           # TypeScript type definitions\n│   ├── server/\n│   │   ├── amtp-server.ts          # Express server & middleware\n│   │   ├── web-session-adapter.ts  # Web auth → AMTP session bridge\n│   │   └── markdown-parser.ts      # AMTP markdown parser\n│   ├── client/\n│   │   └── amtp-client.ts          # Agent client SDK\n│   └── crawler/\n│       └── amtp-crawler.ts         # Website crawler & indexer\n├── reference/\n│   ├── server/                     # Runnable demo server (for developers)\n│   └── client/                     # Runnable demo client (for developers)\n├── reference-implementations/\n│   └── EXAMPLES.md                 # Real-world examples\n├── docs/                           # Additional documentation\n└── README.md                       # This file\n```\n\n## 🎨 Key Concepts\n\n### 1. Markdown-First\n\nPages are semantic markdown, not HTML:\n\n```markdown\n# MacBook Pro 14\"\n\nPrice: $1,999\nIn Stock: Yes\n\n## Actions\n\n[BUY] [ADD_TO_CART] [SAVE_FOR_LATER]\n\n## Specifications\n\n| Component | Spec |\n|-----------|------|\n| CPU | M3 Pro |\n| RAM | 18GB |\n```\n\n### 2. Action-Native\n\nSemantic actions instead of DOM clicks:\n\n```json\n{\n  \"action\": \"buy\",\n  \"parameters\": {\n    \"productId\": \"mbp-14\",\n    \"quantity\": 1,\n    \"paymentMethod\": \"credit_card\"\n  }\n}\n```\n\n### 3. Content Negotiation\n\nSame URL serves multiple formats:\n\n```http\nGET /products/mbp-14\nAccept: text/amtp+markdown → Markdown response (for agents)\nAccept: text/html → HTML response (for browsers)\nAccept: application/json → JSON API response (for clients)\n```\n\n### 4. Session-Aware\n\nSessions persist state across requests:\n\n```http\nX-Session-ID: sess_abc123\n→ Maintains cart, auth, preferences, workflow state\n```\n\n### 5. Streaming Support\n\nReal-time updates via SSE, WebSocket, or HTTP streams:\n\n```\nGET /api/stream/order/ord_123\n→ Streams: order_shipped, out_for_delivery, delivered, etc.\n```\n\n## 🔐 Security\n\nAMTP includes built-in security features:\n\n- **Input Validation** - Type, format, range, injection prevention\n- **Authentication** - Session tokens, JWT, Bearer tokens, API keys\n- **Auto-Session Bridge** - Derives AMTP sessions from existing web auth; raw `req.user` is never exposed to agents/LLMs\n- **Authorization** - Permission-based action execution\n- **CSRF Protection** - Token-based protection\n- **Rate Limiting** - Per-agent, per-action rate limits\n- **Encryption** - HTTPS only, encrypted sensitive data\n\n## 📊 Performance\n\nAMTP optimizes for:\n\n- **Low Latency** - No DOM rendering, direct semantic response\n- **Token Efficiency** - ~90% less tokens than HTML for LLMs\n- **Network Efficiency** - Gzip compression, chunked transfer\n- **Cacheability** - Standard HTTP caching headers\n- **Scalability** - Stateless servers, horizontal scaling\n\nTypical Response Times:\n- Product page: 50-100ms\n- Form submission: 200-500ms\n- Checkout flow: 1-3 seconds\n\n## 🤖 Agent Capabilities\n\nAgents can declare capabilities:\n\n```http\nX-AMTP-Capabilities: actions,streaming,forms,tools,pagination,multimodal\n```\n\nServer adapts response:\n- ✅ Actions: Always available\n- ✅ Streaming: SSE, WebSocket, HTTP streams\n- ✅ Forms: Complex field types and validation\n- ✅ Tools: External API integration\n- ✅ Pagination: Cursor, offset, infinite scroll\n- ✅ Multimodal: Images, videos, documents\n\n## 📈 Roadmap\n\n### v1.0 (Current)\n- ✅ Core protocol\n- ✅ Markdown grammar\n- ✅ Action system\n- ✅ Forms & navigation\n- ✅ Session management\n- ✅ Basic streaming\n- ✅ Type definitions\n- ✅ Reference implementations\n\n### v1.1 (Q3 2024)\n- [ ] Multimedia support\n- [ ] Natural language descriptions\n- [ ] Advanced filtering\n- [ ] Batch operations\n\n### v2.0 (Q4 2024)\n- [ ] Multi-agent coordination\n- [ ] Distributed sessions\n- [ ] Advanced caching\n- [ ] Webhook support\n\n### v3.0 (Q1 2025)\n- [ ] Voice interface\n- [ ] Mobile optimization\n- [ ] Blockchain integration\n- [ ] Federated identity\n\n## 🔗 Comparisons\n\n| Aspect | HTML | JSON API | GraphQL | AMTP |\n|--------|------|----------|---------|------|\n| **Machine-Readable** | ❌ | ✅ | ✅ | ✅ |\n| **Navigation Built-in** | ✅ | ❌ | ❌ | ✅ |\n| **Hypermedia** | ✅ | ❌ | ❌ | ✅ |\n| **LLM-Friendly** | ❌ | ⚠️ | ⚠️ | ✅ |\n| **Token Efficient** | ❌ | ⚠️ | ⚠️ | ✅ |\n| **Low Latency** | ❌ | ✅ | ⚠️ | ✅ |\n| **Cacheable** | ✅ | ✅ | ❌ | ✅ |\n| **Browser Compatible** | ✅ | ❌ | ❌ | ✅* |\n\n*Via content negotiation\n\n## 🚀 Getting Started\n\n### For Server Developers\n\n```bash\n# 1. Install SDK\nnpm install @amtp/protocol\n\n# 2. Follow server implementation guide\n# See: src/server/amtp-server.ts\n\n# 3. Register routes\n# See: reference-implementations/EXAMPLES.md\n\n# 4. Deploy with Express\nnpm start\n```\n\n### For Agent Developers\n\n```bash\n# 1. Install SDK\nnpm install @amtp/protocol\n\n# 2. Create client\nconst client = new AMTPClient({ baseUrl: \"...\" });\n\n# 3. Build workflows\n# See: src/client/amtp-client.ts\n\n# 4. Run agent\nnpm run agent\n```\n\n### For Search/Crawlers\n\n```bash\n# 1. Build crawler\nconst crawler = new AMTPCrawler({ baseUrl: \"...\" });\n\n# 2. Crawl website\nawait crawler.crawl();\n\n# 3. Index results\n# See: src/crawler/amtp-crawler.ts\n```\n\n## 📝 License\n\nMIT License - See LICENSE file\n\n## 🤝 Contributing\n\nContributions welcome! Please:\n\n1. Review the RFC specification\n2. Check existing implementations\n3. Follow TypeScript conventions\n4. Add tests for new features\n5. Submit pull request with description\n\n## 📧 Contact\n\nQuestions or ideas? Open an issue or discussion.\n\n---\n\n**AMTP is the protocol for the agentic web.**\n\n*Designed for AI agents, built on web standards, compatible with everything.*\n\n### Stay Updated\n\n- ⭐ Star this repository\n- 🔔 Watch for releases\n- 💬 Join discussions\n- 📮 Subscribe to updates\n\n---\n\n**Made with ❤️ for the future of agent-web interactions**\n","readmeFilename":"README.md"}