Publish agent work with durable, private links.
Tunly turns generated files, static builds, and live localhost apps into review links with access controls, immutable versions, and machine-readable verification.
Inline comments, replies, resolution, and anchor navigation.
Public, account, email, domain, password, or guest.
Claude and Codex use tunly.agent.v1 JSON.
1. Start
Install the small CLI for your machine, then connect once in a browser. You do not need to copy an API key.
curl -fsSL https://tunly.io/install.sh | sh
tunly version
tunly login
tunly auth status
The installer supports macOS, Linux, and Windows on arm64 and amd64. It downloads the small gzip archive for your machine, verifies SHA256 before decompression, and installs tunly on your PATH. On Windows use irm https://tunly.io/install.ps1 | iex.
Manual downloads are also available:
curl -fLO https://tunly.io/downloads/tunly-darwin-arm64.gz
curl -fLO https://tunly.io/downloads/tunly-darwin-arm64.gz.sha256
shasum -a 256 -c tunly-darwin-arm64.gz.sha256
gzip -dc tunly-darwin-arm64.gz > tunly
chmod +x tunly
sudo install -m 0755 tunly /usr/local/bin/tunly
Replace darwin-arm64 with darwin-amd64, linux-arm64, linux-amd64, windows-arm64.exe, or windows-amd64.exe for another platform. Homebrew support is planned after this binary installer path is proven.
Raw binaries remain available for compatibility with older installers; new installs use the smaller .gz assets.
2. Publish
Use static artifacts when you want durable review output that keeps working after the agent exits.
tunly publish review.html --account
tunly publish ./dist --account
tunly publish report.html --json --public
- Latest URL: stable review entry point for the current ready revision.
- Version URL: immutable evidence URL under
/versions/.... - Scanning: unsafe paths and private key material are rejected before storage.
Published HTML and live Links use the isolated u.tunly.io origin, while login, dashboard, and API stay on tunly.io. Historical tunly.io/<slug> and usercontent.tunly.io/<slug> bookmarks redirect to the same stable Link. Private-Link login returns through a one-time server-side handoff, so publisher HTML never receives the dashboard cookie or bearer token.
3. Review HTML like a shared document
Enable review when publishing an HTML design doc, report, or agent-generated plan:
tunly publish design.html --review --account
# Open the returned review_url, not the raw latest_url.
- Select text in the document to start a comment thread.
- Reply, edit, resolve, and reopen without changing the published HTML bytes.
- In view follows the comments anchored in the current screen.
- All comments scans every thread on this Revision in document order.
- Show in document jumps to the verified text anchor and focuses it.
The Link creator sees the top-right Share button and current access state on ordinary published HTML as well as Review HTML. They can choose Only me, Team, or Anyone with the link, then copy the Latest URL or pin it to the current Revision. Review mode places Share beside Comments and the signed-in account avatar. The avatar and its menu are rendered on Tunly's control origin so publisher HTML cannot inspect the user's profile.
The Link creator opens Activity from the avatar menu. It summarizes views and visitors for 7, 30, or 90 days and lists recent access time, Revision, access path, document path, and coarse device details. Activity is owner-only, privacy-minimized, best-effort product analytics—not a compliance audit log.
Comments belong to the stable Link, while their source Revision remains immutable evidence. Publishing an update keeps the same Review URL and projects every root onto the new Revision as exact, moved, changed, orphaned, needs re-anchor, or manual. The original quote is retained even when the source text is removed.
Use Review Inbox in the dashboard for unread, unresolved, orphaned, owned, and participated threads. Link revision history shows immutable versions, comment-placement health, an on-demand bounded HTML text diff, and safe promotion of a ready historical artifact without changing the Latest URL.
4. Choose privacy
Pick the access mode before sharing. Do not default to public for customer, business, security, or unreleased work.
| Mode | Flag | Use when |
|---|---|---|
| Public | --public | The artifact is safe for the open web. |
| Only me | Share panel | Only the Link creator should open it. |
| Account/team | --account or --team | Signed-in namespace viewers should access it. |
--allow-email person@example.com | A named reviewer needs access. | |
| Domain | --allow-domain example.com | A signed-in account with Google's verified Workspace hd claim should access it. A raw matching email suffix is never enough. |
| Password | --password ... | The user approved password sharing. |
| Guest | --guest | A guest-token flow is intended. |
Protected latest URLs, version URLs, assets, live routes, and offline states resolve through the same access evaluator. Every non-public browser Link requires Tunly login, preserves the original URL through sign-in, and returns through a short-lived one-time handoff for the final permission check. The isolated content origin receives only its own HttpOnly viewer cookie. A signed-in viewer without permission sees a clear no-access page; assets and API/CLI clients are not redirected to HTML login pages.
One identity can belong to multiple Namespaces. Owners invite an exact verified email from Members; recipients sign in, accept the expiring invitation, and switch Namespace from the shared dashboard scope selector.
5. Use agent JSON
OpenClaw can use the same one-time browser/device approval through tunly login, then call agent commands and parse JSON events instead of terminal prose. The official CLI is the supported execution path.
export TUNLY_AGENT_NAME=claude-code
export TUNLY_AGENT_RUN_ID=run-$(date +%Y%m%d%H%M%S)
tunly agent publish review.html --review --json --account \
--idempotency-key "$TUNLY_AGENT_RUN_ID"
tunly agent status --json
tunly agent stop --json
Successful publish events include namespace_id, link_id, revision_id, latest_url, version_url, delivery_mode, state, and access_mode. A --review publish also includes review_url and review_version_url.
6. Publish a live preview
Use live previews when reviewers need an interactive running app.
tunly publish 3000 --account
tunly agent publish 3000 --json --guest
A live preview exposes whatever is listening on that local port. Point it at the intended app only and choose a private access mode unless the demo is public.
7. Inspect and replay locally
While a live tunnel runs, open http://127.0.0.1:4040 for the Local Console.
tunly inspect list
tunly inspect get <request-id>
tunly inspect curl <request-id>
tunly replay <request-id>
Request evidence is stored locally as bounded JSON snapshots under ~/.tunly/evidence-v1. Safe curl output redacts sensitive headers and token-like values.
Agent skill template
Use the official tunly-artifact-share Skill with OpenClaw, or copy the template below into Claude Code, Codex, or a team playbook when agents should publish review artifacts through Tunly.
# SKILL.md
name: tunly-artifact-share
description: Publish Claude, Codex, or local agent output to Tunly as durable latest links and immutable version links, with HTML review, comments, sharing, privacy controls, and publish-to-serve verification.
Use this skill when:
- You created an HTML review page, architecture plan, QA report, release note, screenshot report, or static build that someone should review in a browser.
- You need a stable latest URL plus an immutable evidence URL.
- You need account, email, domain, password, guest, or public sharing controls.
Prerequisites:
- The user has or can create a Tunly account.
- OpenClaw should install the official CLI from https://tunly.io/install.sh and authenticate with tunly login or TUNLY_API_KEY for CI.
Workflow:
1. Build or identify the reviewable artifact. Do not publish secrets, credentials, local databases, or dependency directories.
2. Choose access mode deliberately: --account, --allow-email, --allow-domain, --password, --guest, or --public.
3. For HTML review, publish with agent JSON and --review:
tunly agent publish review.html --review --json --account --idempotency-key "$TUNLY_AGENT_RUN_ID"
4. Parse the tunly.agent.v1 event and capture latest_url, version_url, review_url, review_version_url, link_id, revision_id, namespace_id, delivery_mode, state, and access_mode.
5. Verify publish-to-serve before reporting success.
6. Give reviewers review_url. They can comment on selected text, reply, resolve or reopen threads, and continue using the same URL after updates. The Link creator sees Share state on ordinary and Review HTML; Review also provides owner-only Activity. Collaborators use /app/inbox and Link revision history for ongoing work. Treat u.tunly.io as canonical; historical tunly.io and usercontent.tunly.io Link paths redirect safely. Non-public browser links require Tunly login and return through Tunly's one-time handoff—never copy a cookie or bearer token into publisher HTML.
Final response:
Published with Tunly.
Latest: <latest_url>
Version: <version_url or "n/a">
Review: <review_url or "n/a">
Review version: <review_version_url or "n/a">
Access: <access_mode>
Verified: <short verification result>
The full source copy is also kept in docs/claude-skill-template.md.
Troubleshooting
| Symptom | Fix |
|---|---|
API key required | Run tunly login, or set TUNLY_API_KEY for CI. |
503 origin_offline | The live agent is not attached. Start the app and publish the port again. |
artifact_scan_rejected | Remove private keys, unsafe paths, or ignored secret files from the bundle. |
403 forbidden | The API key lacks access to the namespace, route, or protected link. |
| Domain viewer is denied | Sign in with Google Workspace. Tunly requires the provider-verified hosted-domain claim; a password account or typed same-domain email is not sufficient. |
| Agent cannot parse output | Use tunly agent publish ... --json. Human logs are on stderr; stdout is NDJSON. |
Check /health for control-plane status and include request IDs from tunly inspect when asking for help.