> ## Documentation Index
> Fetch the complete documentation index at: https://docs.xquik.com/llms.txt
> Use this file to discover all available pages before exploring further.

# t.co link resolver API for X (Twitter) short links

> Resolve up to 100 t.co links in 1 call. Get the URL each X short link leads to, in the order sent. Pay 1 credit per resolved link. Unknown links are free.

<Panel>
  <Tabs defaultTabIndex={0} sync={false}>
    <Tab title="200" id="response-x-resolve-links-200">
      ```json theme={null}
      {
        "links": [
          {
            "url": "https://t.co/Xe1nm2pkSX",
            "resolvedUrl": "https://go.nasa.gov/3VcvAQn"
          }
        ],
        "unprocessedUrls": []
      }
      ```
    </Tab>

    <Tab title="400" id="response-x-resolve-links-400">
      ```json theme={null}
      {
        "error": "invalid_input",
        "message": "Invalid input. Check the request body."
      }
      ```
    </Tab>

    <Tab title="401" id="response-x-resolve-links-401">
      ```json theme={null}
      {
        "error": "unauthenticated",
        "message": "Authentication required."
      }
      ```
    </Tab>

    <Tab title="402" id="response-x-resolve-links-402">
      ```json theme={null}
      {
        "error": "insufficient_credits",
        "message": "Insufficient credits. Top up or subscribe to continue."
      }
      ```
    </Tab>

    <Tab title="424" id="response-x-resolve-links-424">
      ```json theme={null}
      {
        "error": "x_api_unavailable",
        "message": "X data source temporarily unavailable. Try again later."
      }
      ```
    </Tab>

    <Tab title="429" id="response-x-resolve-links-429">
      ```json theme={null}
      {
        "error": "rate_limit_exceeded",
        "message": "Too many requests. Try again later.",
        "retryAfter": 60
      }
      ```
    </Tab>

    <Tab title="502" id="response-x-resolve-links-502">
      ```json theme={null}
      {
        "error": "x_api_unavailable",
        "message": "X data source temporarily unavailable. Try again later."
      }
      ```
    </Tab>

    <Tab title="503" id="response-x-resolve-links-503">
      ```json theme={null}
      {
        "error": "x_api_unavailable",
        "message": "Xquik is busy right now. Retry shortly."
      }
      ```
    </Tab>
  </Tabs>
</Panel>

<blockquote className="agent-llms-directive">
  For the complete documentation index, see <a href="/llms.txt">llms.txt</a>.
</blockquote>

<Callout icon="coins" color="#5c3327">
  **1 credit per resolved link** · [All plans](https://xquik.com/#pricing) from \$0.00012/credit
</Callout>

Resolve links returns the URL each t.co link leads to.
Send 1 to 100 links in 1 call. The endpoint is `GET /api/v1/x/links/resolve`.

<CodeGroup>
  ```bash cURL theme={null}
  curl -G https://xquik.com/api/v1/x/links/resolve \
    --data-urlencode "urls=https://t.co/Xe1nm2pkSX,https://t.co/QQGjcE6KKq" \
    -H "x-api-key: xq_your_api_key_here" | jq
  ```

  ```javascript Node.js theme={null}
  const params = new URLSearchParams({
    urls: ["https://t.co/Xe1nm2pkSX", "https://t.co/QQGjcE6KKq"].join(","),
  });
  const response = await fetch(`https://xquik.com/api/v1/x/links/resolve?${params}`, {
    headers: { "x-api-key": "xq_your_api_key_here" },
  });
  const { links, unprocessedUrls } = await response.json();
  const targets = Object.fromEntries(links.map((link) => [link.url, link.resolvedUrl ?? null]));

  process.stdout.write(`${JSON.stringify({ targets, unprocessedUrls })}\n`);
  ```

  ```python Python theme={null}
  import json
  import requests

  response = requests.get(
      "https://xquik.com/api/v1/x/links/resolve",
      params={"urls": "https://t.co/Xe1nm2pkSX,https://t.co/QQGjcE6KKq"},
      headers={"x-api-key": "xq_your_api_key_here"},
  )
  body = response.json()
  targets = {link["url"]: link.get("resolvedUrl") for link in body["links"]}
  print(json.dumps({"targets": targets, "unprocessed_urls": body["unprocessedUrls"]}))
  ```
</CodeGroup>

Use `GET /x/links/resolve` when you hold t.co links and need their targets.
X shortens every link in a post to a t.co link.
Xquik reads where each link points and never opens the target page.

## Resolve links in bulk

Collect the t.co links from tweet text, bios, or your own logs.
Send up to 100 in 1 call, separated by commas.
`links` comes back in the order sent, with each link once.

A link t.co does not have comes back without `resolvedUrl`. It costs nothing.
Each resolved link costs 1 credit.

A link X does not answer for in time comes back in `unprocessedUrls`.
It costs nothing. Send it again in your next call.

`resolvedUrl` is the address the link's author set. Xquik does not check it.
Check a target before you open it.

Tweets already carry their links' targets in `entities.urls[].expanded_url`.
Read them with [Get tweet](/api-reference/x/get-tweet) when you hold the tweet ID.

## Query parameters

<ParamField query="urls" type="string" required>
  1 to 100 links of the form `https://t.co/Xe1nm2pkSX`, separated by commas. Any other link returns `400 invalid_input`.
</ParamField>

## Headers

<ParamField header="x-api-key" type="string">
  Full account key. Sessions and OAuth also work.
</ParamField>

<ParamField header="Authorization" type="string">
  `Bearer xq_your_guest_key_here` for `paid_reads`.
</ParamField>

## Response

### 200 OK

<ResponseField name="links" type="object[]">
  Resolved links in the order sent.
  **Link object fields.**

  <ResponseField name="url" type="string">
    The t.co link, as `https://t.co/<code>`.
  </ResponseField>

  <ResponseField name="resolvedUrl" type="string">
    Target URL, as the link's author set it. Absent for a link t.co does not have.
  </ResponseField>
</ResponseField>

<ResponseField name="unprocessedUrls" type="string[]">
  Links not read, in the order sent. X did not answer for them in time, or available credits ran out. Send them again.
</ResponseField>

```json theme={null}
{
  "links": [
    {
      "url": "https://t.co/Xe1nm2pkSX",
      "resolvedUrl": "https://go.nasa.gov/3VcvAQn"
    },
    {
      "url": "https://t.co/QQGjcE6KKq",
      "resolvedUrl": "https://twitter.com/NASA/status/2102882545427714266/photo/1"
    }
  ],
  "unprocessedUrls": []
}
```

### 400 Invalid input

```json theme={null}
{
  "error": "invalid_input",
  "message": "Send urls as 1 to 100 links of the form https://t.co/Xe1nm2pkSX, separated by commas."
}
```

`urls` is missing, holds over 100 links, or holds a link in another form. Send each link as `https://t.co/` and its code.

### 401 Unauthenticated

```json theme={null}
{ "error": "unauthenticated" }
```

Missing or invalid API key. Check the `x-api-key` header value.

### 402 Payment required

Account keys get account options. Guest keys get guest top-up only.
No checkout starts automatically. Confirm any payment action.

### 502 X API unavailable

```json theme={null}
{ "error": "x_api_unavailable" }
```

The read service returned an error. Retry after a short delay.

### 503 Service busy

```json theme={null}
{ "error": "x_api_unavailable" }
```

X answered none of the links in time, or Xquik is busy. Wait for the `Retry-After` header, then send the same links again. The request costs nothing.

### 429 Rate limit exceeded

```json theme={null}
{ "error": "rate_limit_exceeded", "retryAfter": 60 }
```

You exceeded your tier rate limit. Wait for the `Retry-After` header before retrying.

### 424 Dependency failed

```json theme={null}
{ "error": "x_api_unavailable" }
```

The normalized v1 response contract can return 424 when the read service is unavailable.

## t.co link resolver API questions

### How do I resolve a t.co link with an API?

Call `GET /x/links/resolve` with the link in `urls`.
The response holds the target in `links[0].resolvedUrl`.

### How many t.co links can I resolve in 1 call?

Send 1 to 100 links, separated by commas. Repeated links count once.

### Which link forms does the endpoint accept?

Only `https://t.co/` followed by the link's code.
Other sites, `http://` links, and links without `https://` return `400 invalid_input`.

### How much does resolving a t.co link cost?

Each resolved link costs 1 credit. A link t.co does not have costs nothing.
A link X does not answer for costs nothing. A refused or failed request costs nothing.

### What happens when X does not answer for a link?

The call still returns the links that resolved.
The unanswered links come back in `unprocessedUrls`. Send them again.

### Does Xquik visit the target page?

No. Xquik reads where the t.co link points and stops there.

### Does this replace X's official API?

No. This page documents Xquik, an independent third-party service.
It does not document X's official API.

<Note>
  **Next steps.** [Get tweet](/api-reference/x/get-tweet) reads a tweet with its links' targets, or [Search Tweets](/api-reference/x/search-tweets) finds tweets that share a link.
</Note>

<div className="related-api-links">
  <Accordion title="Related tweet, reply & media APIs" icon="link">
    * Tweets: [Get tweet](/api-reference/x/get-tweet) · [Batch tweets](/api-reference/x/batch-tweets) · [Tweet thread](/api-reference/x/tweet-thread) · [Hidden replies](/api-reference/x/tweet-hidden-replies) · [Translate tweet](/api-reference/x/tweet-translation) · [Embed tweet](/api-reference/x/tweet-embed) · [Resolve links](/api-reference/x/resolve-links) · [Tweet subtitles](/api-reference/x/tweet-subtitles) · [X Article](/api-reference/x/get-article)
    * Engagement: [Tweet replies](/api-reference/x/tweet-replies) · [Quote tweets](/api-reference/x/tweet-quotes) · [Likers](/api-reference/x/favoriters) · [Reposters](/api-reference/x/retweeters) · [Check repost](/api-reference/x/tweet-repost-check)
    * Profiles: [User tweets](/api-reference/x/user-tweets) · [Batch user tweets](/api-reference/x/batch-user-tweets) · [User replies](/api-reference/x/user-replies) · [User likes](/api-reference/x/user-likes) · [User media](/api-reference/x/user-media) · [User highlights](/api-reference/x/user-highlights) · [User articles](/api-reference/x/user-articles)
    * Feeds: [List tweets](/api-reference/x/list-tweets) · [Trends](/api-reference/x/trends) · [Trend locations](/api-reference/x/trend-locations) · [Search Spaces](/api-reference/x/search-spaces) · [Get Space](/api-reference/x/get-space) · [Space replay](/api-reference/x/space-replay) · [Get broadcast](/api-reference/x/get-broadcast) · [Hashflags](/api-reference/x/hashflags) · [Search places](/api-reference/x/search-places) · [Download media](/api-reference/x/download-media)
  </Accordion>
</div>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.