A few months ago, I had a simple question: why is it so hard for AI agents to get reliable, structured product prices?
LLMs can reason about almost anything — but ask one "what's the cheapest Raspberry Pi 5 right now?" and it either hallucinates a number or admits it doesn't know. The data exists on marketplaces. The problem is the bridge between that data and the agent.
So I built AgentShare — a price infrastructure API designed specifically for AI agents, not human users.
How it fits together (one picture)
Rough pipeline: crawl & normalize → store with timestamps → REST API → MCP tools. The API is the stable contract; crawlers and coverage can evolve behind it. That separation is what lets an agent depend on shapes and freshness instead of scraping HTML on every turn.
The core idea
Most price comparison tools are built for browsers: ads, affiliate banners, SEO-optimized pages. An agent doesn't need any of that. It needs:
- Structured JSON, not HTML to parse
- Freshness signals, not just a number
- Predictable error shapes it can act on
- A stable interface it can call repeatedly
AgentShare is built around those four things.
What it looks like in practice
Security: treat X-API-Key like any secret — environment variables or a secrets manager, not committed files or screenshots. The examples below use YOUR_KEY as a placeholder.
curl -H "X-API-Key: YOUR_KEY" \
"https://agentshare.dev/api/v1/offers/best?q=nvidia+jetson+orin"
Example response (abbreviated):
{
"status": "ok",
"data": {
"best_offer": {
"price": 4875000,
"source": "tiki",
"availability": true,
"crawled_at": "2026-04-15T02:00:20Z",
"data_age_seconds": 86400,
"freshness_status": "stale"
},
"summary": "Best price at Tiki — 4,875,000₫"
},
"meta": {
"remaining_requests": 99,
"freshness_status": "stale"
}
}
Every response includes freshness_status — fresh, stale, or expired — so the agent can decide whether to caveat its answer or ask for a refresh.
Quota: responses expose remaining_requests in meta on supported routes. The free tier is 100 requests per month with no credit card; plan agent behavior (retries, caching) accordingly.
When auth or limits bite: missing or invalid keys typically yield 401; exceeding quota often yields 429 with a clear message — your agent should backoff and surface that to the user instead of looping.
MCP support
If you're building with Claude Desktop, Cursor, or any MCP-compatible client, you can connect AgentShare as a tool server in one step:
{
"mcpServers": {
"agentshare": {
"command": "npx",
"args": [
"-y", "mcp-remote",
"https://agentshare.dev/mcp",
"--header", "X-API-Key: YOUR_KEY"
]
}
}
}
Keep the key out of version-controlled config: use your client's env substitution or local overrides if available.
Tools exposed: price_search, best_offer, best_offer_under_budget, service_meta.
Each tool returns two content blocks: a one-line human-readable summary and a full JSON payload — so the agent has both a quick answer and machine-parseable data in the same response.
Three technical decisions worth sharing
1. Freshness metadata is not optional
A price from six days ago is not the same as a price from two hours ago. An agent recommending a product without knowing data age is doing the user a disservice.
Every response includes crawled_at, data_age_seconds, and freshness_status. The agent can use this to decide whether to add a caveat, trigger a refresh, or tell the user this price is a few days old.
2. "Not found" is not one problem — it's two
Early on, a missing product returned a generic NOT_FOUND error. An agent receiving that has no idea what to do next.
Now the API distinguishes:
{
"status": "no_data",
"reason": "out_of_coverage",
"coverage_url": "https://agentshare.dev/coverage",
"suggestions": ["similar product A", "similar product B"]
}
{
"status": "no_data",
"reason": "pending_crawl",
"estimated_available": "2026-04-22T00:00:00Z"
}
-
out_of_coverage→ the agent redirects or tells the user clearly. -
pending_crawl→ the agent knows to try again later.
3. The async deadlock I almost shipped
FastMCP handler calling the REST API with requests.get() — synchronously — inside an async handler on a single Uvicorn worker. The tool call would hang for exactly 120 seconds before failing.
Root cause: the synchronous HTTP call blocked the event loop, which meant the inbound REST request never got processed, which meant the MCP tool call waited forever.
Fix: move all API calls inside MCP tools to asyncio.to_thread() so requests runs on a thread pool, freeing the event loop.
If you're building MCP servers with FastMCP on a single worker, watch out for this pattern.
Current focus areas
I'm honest about what's covered well versus what's still being built.
High quality, updated regularly:
- AI edge hardware: Raspberry Pi, NVIDIA Jetson, Orange Pi, Google Coral, Rockchip SBCs
- Mini PCs: Intel NUC, Beelink, GMKtec
- Components: SSD, RAM, power supplies, cooling
- Robotics: kits, servo motors, arms, LiPo/LiFePO4 battery packs
Expanding (beta — data may be incomplete):
- Mobile phones, tablets, general consumer electronics
The focus list reflects what matters most to people building AI agents locally — the folks running LLMs on edge hardware or sourcing parts for robot projects.
Full coverage spec: agentshare.dev/coverage
What I'd genuinely like feedback on
- Response shape — is the current JSON easy to work with in your agent framework, or are there fields you'd add or remove?
- Freshness thresholds — how old is "too old" for a price recommendation in your use case?
- Coverage gaps — what hardware or component categories are you looking for that aren't covered yet?
Try it
- Docs: agentshare.dev/docs
- Free tier: 100 requests/month, no credit card required
- OpenAPI spec: agentshare.dev/openapi.json
- Agent discovery: agentshare.dev/agent.json
This is a solo project, shipped in public — I build iteratively and rely heavily on good tooling (including AI-assisted development) to move fast. If the approach helps what you're building, or something is broken or confusing, I'd genuinely like to know.
Top comments (0)