1. Send one request
The Blinkhop API lives at https://api.blinkhop.com/v1. To shorten a URL, send it to the /links endpoint:
POST/v1/links
curl https://api.blinkhop.com/v1/links \
-H "Content-Type: application/json" \
-d '{"url": "https://example.com/a/very/long/link"}'
That’s the whole setup. There is no key to create, no account and nothing to install. The same request works from any language that can send HTTP:
const res = await fetch("https://api.blinkhop.com/v1/links", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ url: "https://example.com/a/very/long/link" }),
});
const link = await res.json();
console.log(link.short_url); // https://zou.sh/7Kp2x
import requests
r = requests.post(
"https://api.blinkhop.com/v1/links",
json={"url": "https://example.com/a/very/long/link"},
timeout=10,
)
print(r.json()["short_url"]) # https://zou.sh/7Kp2x
2. Read the response
A successful call returns the link as JSON:
{
"id": "lnk_7Kp2x",
"code": "7Kp2x",
"short_url": "https://zou.sh/7Kp2x",
"url": "https://example.com/a/very/long/link",
"qr_url": "https://zou.sh/7Kp2x/qr",
"preview_url": "https://zou.sh/7Kp2x+",
"clicks": 0,
"created_at": "2026-10-11T14:02:11Z"
}
| Field | Description |
|---|---|
short_url |
The link to share. It redirects to url with an HTTP 302. |
code |
The part after zou.sh/. Lookups ignore letter case. |
url |
The destination, normalized (a missing https:// is added). |
qr_url |
A print-ready SVG QR code of the short link. |
preview_url |
A public page that shows the destination and the click count before anyone visits. |
clicks |
Human clicks so far. Bots and link previews are not counted. |
created_at |
Creation time, ISO 8601 in UTC. |
The status code tells you what happened. 201 Created means a new link. 200 OK means the same URL had already been shortened without a custom ending, so you get the existing link back. Retrying a request never creates duplicates.
3. Choose the ending
Add an alias to pick the ending yourself:
curl https://api.blinkhop.com/v1/links \
-H "Content-Type: application/json" \
-d '{"url": "https://example.com/spring", "alias": "spring-sale"}'
Endings use 3 to 40 letters, numbers, dashes or underscores, and start with a letter or a number. They are unique regardless of letter case: zou.sh/Spring-Sale and zou.sh/spring-sale are the same link. If the ending is taken or reserved, the API answers 409 with the code alias_taken, so you can suggest another one.
4. Get only the link
Add ?format=text and the API returns the short URL as plain text, which is handy in shell scripts:
curl -s "https://api.blinkhop.com/v1/links?format=text" \
--data-urlencode "url=https://example.com/report?quarter=q3&year=2026"
# https://zou.sh/q8Hn4
The API also accepts form-encoded bodies, as above. Use --data-urlencode so that & and ? inside your URL survive the trip.
5. Handle errors and limits
Errors come back as JSON with a stable code, a readable message and, when it applies, the field at fault:
{
"error": {
"code": "invalid_url",
"message": "That does not look like a valid URL.",
"field": "url"
}
}
Branch on code, not on message: messages may be reworded, codes won’t. The most common ones:
| HTTP | Code | When |
|---|---|---|
| 400 | missing_url |
The request has no url. |
| 422 | invalid_url |
The URL is malformed, not http(s), or points to a private address. |
| 422 | unsafe_destination |
The domain is on our phishing and malware blocklist. |
| 409 | alias_taken |
The custom ending is taken or reserved. |
| 429 | rate_limited |
Too many links in a short time. Wait Retry-After seconds. |
Without a key you can create 20 links per minute and 300 per day per IP address. Every response from POST /links carries X-RateLimit-Limit, X-RateLimit-Remaining and X-RateLimit-Reset headers, and a 429 adds Retry-After. API keys with higher limits come with accounts, which are in early access.
6. Call it from a web page
The API sends Access-Control-Allow-Origin: *, so you can call it straight from the browser, with no proxy. Nothing secret is involved, since no key is needed:
document.querySelector("#share").addEventListener("click", async () => {
const res = await fetch("https://api.blinkhop.com/v1/links", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ url: location.href }),
});
const { short_url } = await res.json();
await navigator.clipboard.writeText(short_url);
});
Next steps
- Read the API reference for every endpoint: bulk creation, link lookup, the link expander and reports.
- Copy ready-made code samples for Node.js, Python, Go, PHP, PowerShell, Google Sheets and more.
- Let your AI assistant do it: connect the MCP server to Claude, ChatGPT, Cursor or VS Code.
- Import the OpenAPI spec into Postman, Insomnia or your code generator.