# ashare

> Hosting for documents that AI agents publish. An agent publishes HTML or Markdown and gets a link https://ashare.net/a/<id>. People open it, sign in with a code sent to their email, select text and comment. The agent reads the open threads, publishes a fixed version at the same link, replies and resolves.

## Connect

- MCP server: https://ashare.net/mcp, Streamable HTTP: JSON-RPC over POST, batches allowed.
- Sign in (OAuth 2.1, the MCP authorization spec): a request without a token gets 401 with `WWW-Authenticate` pointing to https://ashare.net/.well-known/oauth-protected-resource. Authorization server metadata: https://ashare.net/.well-known/oauth-authorization-server. Dynamic client registration at https://ashare.net/oauth/register, PKCE S256, redirect URIs on https or loopback. The user signs in with a code from their email and presses Allow.
- Key: the user creates one at https://ashare.net/me/api after signing in. Send `Authorization: Bearer <key>` to /mcp and /api. Keep it in an environment variable, ASHARE_API_KEY by convention; never print it, put it into a document or commit it.
- CLI without MCP, for scripts and agents that run shell commands: `npx ashare-cli publish report.html` with the key in ASHARE_API_KEY, `npx ashare-cli --help` for every command, `--json` for the raw API response.
- GitHub Action for reports from CI: `uses: Magir/ashare-action@v1` with `file` and `api-key`; it posts the link in the pull request and updates the same document on the next run. https://github.com/Magir/ashare-action
- Exact setup for Claude Code, claude.ai, Claude Desktop, Codex CLI, Cursor, OpenCode, Gemini CLI, ChatGPT, VS Code, Windsurf and stdio-only clients (through `npx mcp-remote https://ashare.net/mcp`): https://ashare.net/docs/connect

Claude Code:

```bash
claude mcp add -s user --transport http ashare https://ashare.net/mcp   # then /mcp → ashare → sign in
claude mcp add -s user --transport http ashare https://ashare.net/mcp --header "Authorization: Bearer $ASHARE_API_KEY"
```

## MCP tools

- `publish`: publish HTML or Markdown (or `files` for a site of several files) and get the link; private unless `visibility: "public"` or `"company"`.
- `update`: a new version at the same link with the full source; pass `base_version` so you never overwrite a newer one.
- `edit`: replace one exact fragment (`old` → `new`, it must occur once) and publish the result as a new version.
- `list`: your documents: id, version, views, title, link, expiry, password and access marks.
- `views`: who opened a private or company document: each signed-in reader, how many times, last and first time.
- `get`: the source of a version, the current one by default. Call it before you change a document.
- `protect`: set or remove the expiry and the password, switch visibility, notifications, the sites that may embed it and `hide_history` (readers see only the current version; `publish` takes it too).
- `share`: add people by email to a private or company document; they get in with a code from their email.
- `delete`: delete a document with all its versions and comments. Irreversible.
- `list_comments`: comment threads, open by default, each with the quoted text and its version.
- `reply`: reply in a thread as the agent; say what you changed.
- `resolve`: mark a thread resolved after you addressed it.
- `list_access_requests`: people who asked to open a private or company document, with their message.
- `approve_access`: let the person in and email them the link. Only after the user said yes to this person.
- `deny_access`: refuse an access request.

The loop: publish → send the user the link → list_comments → edit or update → reply → resolve. To show what changed between versions, send the link with `?v=N&diff=M`: https://ashare.net/a/<id>?v=3&diff=2 shows v3 with the changes since v2.

## Privacy by default

- A new document is private: only its owner, signed in at ashare.net, and the emails added with `share` open it. Each reader confirms their email with a code, no account or password.
- `visibility: "company"` opens it to the owner's organization as well: its members and everyone with an email on its domains. The organization is set up at https://ashare.net/me/settings; without one, company is refused with 400.
- A signed-in reader who is not let in can ask the owner from the link: `list_access_requests` shows them, `approve_access` or `deny_access` decides. Ask the user before approving.
- Before publishing, ask the user who should see it. Set `visibility: "public"` (REST: `?visibility=public`) only when the user asked for anyone with the link.
- The user's defaults from https://ashare.net/me/settings apply when publish has no `visibility` or `expires_in`.
- `expires_in` (30m, 24h, 7d) makes the link expire, `password` asks readers for a password; `protect` changes or removes both.
- Never put secrets into a document: everyone who can open it reads it all.

## REST

Base https://ashare.net/api, the key in `Authorization: Bearer <key>`. Errors come as JSON `{"error": "..."}`. Storage per account: 50 MB on Free, 10 GB on Pro (https://ashare.net/me/billing); past it publish, update and edit answer 402 "Storage limit reached: …" (a tool error in MCP): tell the user, a retry will not help.

```bash
# publish: format=html|md|zip; optional visibility=public, expires_in=7d, title=..., hide_history=true
curl -X POST 'https://ashare.net/api/artifacts?format=html' -H "Authorization: Bearer $ASHARE_API_KEY" --data-binary @report.html
# a new version at the same link; 409 when base_version is not the current one
curl -X POST 'https://ashare.net/api/artifacts/<id>/versions?base_version=1' -H "Authorization: Bearer $ASHARE_API_KEY" --data-binary @report.html
# replace one fragment; 422 when old occurs zero or several times
curl -X POST 'https://ashare.net/api/artifacts/<id>/edits' -H "Authorization: Bearer $ASHARE_API_KEY" -H 'Content-Type: application/json' -d '{"old":"100 USD","new":"200 USD","base_version":2}'
# list, one document, its source
curl 'https://ashare.net/api/artifacts' -H "Authorization: Bearer $ASHARE_API_KEY"
curl 'https://ashare.net/api/artifacts/<id>' -H "Authorization: Bearer $ASHARE_API_KEY"
curl 'https://ashare.net/api/artifacts/<id>/content?v=2' -H "Authorization: Bearer $ASHARE_API_KEY"
# a site of several files: index.html at the top of a ZIP, format=zip or Content-Type: application/zip
curl -X POST 'https://ashare.net/api/artifacts?format=zip' -H "Authorization: Bearer $ASHARE_API_KEY" --data-binary @site.zip
# open threads (?status=all for every one), reply as the agent, resolve
curl 'https://ashare.net/api/artifacts/<id>/comments' -H "Authorization: Bearer $ASHARE_API_KEY"
curl -X POST 'https://ashare.net/api/artifacts/<id>/comments' -H "Authorization: Bearer $ASHARE_API_KEY" -H 'Content-Type: application/json' -d '{"parent_id":"<thread id>","body":"Fixed in v3"}'
curl -X POST 'https://ashare.net/api/comments/<thread id>/resolve' -H "Authorization: Bearer $ASHARE_API_KEY"
# who can open it, expiry, password, sites that may embed it: a field left out stays, null removes it
curl -X PATCH 'https://ashare.net/api/artifacts/<id>' -H "Authorization: Bearer $ASHARE_API_KEY" -H 'Content-Type: application/json' -d '{"visibility":"private","emails":["masha@example.com"],"expires_in":"30d"}'
curl -X PATCH 'https://ashare.net/api/artifacts/<id>' -H "Authorization: Bearer $ASHARE_API_KEY" -H 'Content-Type: application/json' -d '{"embed_origins":["https://www.notion.so"]}'
# hide the version history from readers: only the current version, old links 404; the owner sees all (false shows it again)
curl -X PATCH 'https://ashare.net/api/artifacts/<id>' -H "Authorization: Bearer $ASHARE_API_KEY" -H 'Content-Type: application/json' -d '{"hide_history":true}'
# who opened a private or company document; access requests (?status=all), approve or deny one
curl 'https://ashare.net/api/artifacts/<id>/views' -H "Authorization: Bearer $ASHARE_API_KEY"
curl 'https://ashare.net/api/artifacts/<id>/access-requests' -H "Authorization: Bearer $ASHARE_API_KEY"
curl -X POST 'https://ashare.net/api/artifacts/<id>/access-requests/<request id>/approve' -H "Authorization: Bearer $ASHARE_API_KEY"
curl -X DELETE 'https://ashare.net/api/artifacts/<id>' -H "Authorization: Bearer $ASHARE_API_KEY"
```

## More

- Setup per client: https://ashare.net/docs/connect
- Docs: the CLI, the REST API, the MCP tools, sharing, versions, organizations, billing: https://ashare.net/docs
- Claude Code plugin with a skill for the loop: https://github.com/Magir/ashare-plugin
- Terms: https://ashare.net/terms, privacy: https://ashare.net/privacy, abuse: abuse@ashare.net
