13 min readMigration

Migrate From TinyURL: What Moves, What Stays, What Breaks

Migrate from TinyURL with a plan: what you can export, which tinyurl.com links you can't redirect, CSV mapping, import, DNS cutover and verification.

Ana Kowalska
Marketing solutions engineering

To migrate from TinyURL, first sort your links into two piles: links on a domain you own, and links on tinyurl.com. The first pile moves cleanly, because you change one DNS record and the old URLs keep working. The second pile cannot be redirected by you at all, because TinyURL owns the domain. You can copy the destinations into Elido, but every place a tinyurl.com/xxxx link was published has to be updated by hand.

The second thing to know before you start: right now the dependable way to move is a file. Export through TinyURL's documented GET /urls/available call, reduce the result to destination, slug, title, and load it with Elido's bulk import. Elido also ships a one-click TinyURL importer, but it calls an endpoint that isn't in TinyURL's published API, so we treat it as unverified until a planned fix lands. This guide covers both routes and the full journey: from export to analytics, with the cutover and rollback in between. TinyURL facts are from its own blog and OpenAPI spec, accessed 2026-10-01 and 2026-10-02.

For a feature-by-feature verdict on whether to switch at all, read Elido vs TinyURL or the wider TinyURL alternatives roundup.

Ownership of the hostname decides everything. A short link is two things: a hostname and a code. You can carry a code anywhere, but you can only make a link keep working if you control the hostname.

Link typeWho controls the redirectWhat you can do
tinyurl.com/xxxx, created without an accountTinyURLNothing to the old link. Re-create the destination in Elido and replace the old link wherever it was published
tinyurl.com/your-alias, created in an accountTinyURLEdit the destination inside TinyURL on a paid plan, or import the alias to Elido under a new hostname and update every placement
go.yourbrand.com/xxxx (custom domain)YouPoint the hostname at Elido and import the aliases. Old URLs keep working
Diagram: links on your own domain move to Elido with a DNS change, while tinyurl.com links stay on TinyURL and must be replaced where they were published

The honest version for the first two rows: once you stop paying TinyURL, those links keep resolving as long as TinyURL keeps them, and you have no way to see clicks, change them, or redirect them. Some teams leave them alone on purpose. I think that's the right call for old, low-traffic links.

The Elido TinyURL to Elido migration page with the connect, options and import steps for a one-shot bulk import of existing links

TinyURL gives you one documented way to list your links: the API. Its OpenAPI spec (accessed 2026-10-02) defines listing as GET /urls/{type}, where type is available or archived, with optional from and to datetimes and a search filter that takes an alias: or tag: prefix. The call needs a bearer token. TinyURL's own article on listing links describes the same endpoint and says the type is the only mandatory input.

What the spec doesn't give you matters just as much. It defines no page or per_page parameters and no rate limits. So for a large account, narrow each request with from/to windows (a month at a time, say) and write every response to disk before doing anything else:

# One window at a time; inspect the first response by hand before scripting further
curl -s -H "Authorization: Bearer $TINYURL_TOKEN" \
  "https://api.tinyurl.com/urls/available?from=2025-01-01T00:00:00Z&to=2025-02-01T00:00:00Z" \
  > tinyurl-2025-01.json

We haven't verified the live response shape (the spec leaves unclear whether it carries a list or a single object), so open one file and look before you write a parser. Run the same call against /urls/archived if you want archived links too.

Three limits shape the rest of the plan:

  • No account, no list. TinyURL states that links created without signing in cannot be managed or deleted. There's no per-user record, so there's nothing to export.
  • The free plan is read-only. Per TinyURL's free plan page, editing and deleting links, click analytics, custom domains and bulk creation all sit behind paid plans.
  • Analytics aren't in the list. Click history is on you. Screenshot it or report it out of TinyURL before you cancel. We couldn't find a documented CSV export button in TinyURL's help centre, so this guide doesn't promise one.

Step 2: Map TinyURL Data to a File Elido Accepts

Whatever you pulled out of TinyURL, reduce it to the same three fields:

  • TinyURL long URL becomes destination (the link's target).
  • TinyURL alias becomes slug. Leave it blank for links on tinyurl.com that you want fresh codes for.
  • TinyURL title or description becomes title.

TinyURL calls them aliases, Elido calls them slugs. Same thing: the characters after the host. If your target domain is empty, aliases carry over unchanged.

Elido's links page has a bulk tab and a CSV tab, and both read lines in the form url, slug, title. In the CSV tab, the first line is dropped when it doesn't contain an http(s):// URL, so a header row is safe. Lines starting with # are ignored in the paste box. Custom slugs are letters, numbers and hyphens, so check aliases with any other characters before you upload; rows that fail are listed with a reason.

destination,slug,title
https://acme.com/spring-sale,spring-sale,Spring Sale
https://acme.com/pricing,,Pricing page

If you used TinyURL tags, keep them. They won't fit the three-column CSV, but the API route below takes them.

Step 3: Import Into Elido

There are two routes in. The file route works today. The built-in importer exists but is unverified.

The dependable route: CSV, bulk paste or the bulk API

The dashboard bulk and CSV tabs process up to 100 links per batch, so split a larger file into chunks. The bulk import help page walks through the form, and the Google Sheets bulk import walkthrough is handy if you cleaned the export in a spreadsheet.

The workspace API takes the same shape as JSON. POST /v1/workspaces/{workspace_id}/links/bulk accepts a domain_id and up to 100 links, each with destination_url and optional slug, title and tags. Each row is processed on its own, so one bad row doesn't fail the batch, and the response tells you which rows errored. Add a tag such as imported:tinyurl yourself so you can filter the batch later. API and SDKs has the client libraries.

The built-in TinyURL importer, and its known bug

Elido has a one-click TinyURL importer, described on the migrate from TinyURL page. You paste a TinyURL API token, pick the Elido domain the links should land on, and choose a conflict strategy. The problem is the first HTTP call. The worker builds this request:

GET https://api.tinyurl.com/aliases?page=1&per_page=100
Authorization: Bearer <token>

and expects {"data": [{alias, url, title, tags}], "meta": {"total", "has_more"}} back. TinyURL's spec has no /aliases path; alias operations live under /alias/{domain}/{alias}, and listing is /urls/{type}. So that pagination contract was never taken from TinyURL. Our unit test serves a hand-written response in the assumed shape and passes, which proves the parser matches our assumption and nothing about TinyURL. We haven't run it against a live account, because that needs a paid TinyURL plan. Don't plan a migration around it yet.

The fix is planned: switch to /urls/available (with /urls/archived behind a flag), page through from/to windows, parse defensively, and test against a real captured response. After that, pagination and the real per-request limit need re-measuring against a live account, since the spec gives neither.

Elido dashboard integrations page in a demo workspace, where migration sources are started

The integrations page in a DEMO workspace with synthetic data. The TinyURL migration is started from here.

What the importer does once it has a page

Everything past the HTTP call doesn't depend on the endpoint question, and this part we can state from the code.

  • Start. POST with token, target_domain_id and optional conflict_strategy. The handler rejects an empty token, a missing domain and any strategy outside suffix, skip, fail, then answers 202 with the job and runs the worker in the background, detached from the request.
  • Per link. A row without a URL or without an alias counts as failed with a reason. Otherwise the alias becomes the slug, destination and title are copied (title truncated to 200 characters), and tags are copied with imported:tinyurl appended.
  • Progress. Counters flush to the job row every 50 links. At most 1,000 error rows are logged per job.
  • Auth and rate errors. A 401 or 403 fails the job with a "check the bearer token" message, and a 429 fails it as rate-limited. There's no retry or backoff: the job stops.

The token goes from the request body to the background job and nowhere else. The job row doesn't record it, and nothing is encrypted at rest because nothing is stored. The request body is read with a 4 KB limit. The code doesn't validate the key or check the plan before starting, so a bad one shows up as a failed job after the first request, not as a form error. Earlier versions of our docs described a preflight check against a domains endpoint; that step doesn't exist in the code, and TinyURL's spec has no such path either.

Conflict rules and caps

Before each insert the worker does one indexed lookup for the domain and slug pair:

  • suffix (default) tries alias-2, alias-3, up to alias-50, and fails the row if all are taken.
  • skip leaves the existing Elido link alone and logs the source row.
  • fail fails the job at the first conflict.

Every run is capped at 50,000 links and 30 minutes. Two behaviours are worth knowing. When the 50,000 cap is hit, the loop simply stops and the job completes; it doesn't fail, so compare the final counts with your source total. When the 30-minute budget runs out, the job is marked failed with the number imported so far.

Elido links list in a demo workspace with short links, destinations, tags, 30-day clicks and status

The links list in a DEMO workspace. Imported links carry the imported:tinyurl tag, so you can filter a batch for review.

Testing the importer safely

Whenever the endpoint is fixed, or if you try the importer yourself before then, do it small. Create a throwaway workspace, add an empty domain, and run the job with the fail strategy first. An empty domain means no conflicts, so any failure is a parsing or auth problem rather than a collision. Then compare three numbers: the source count in TinyURL, the total the job reports, and the imported plus skipped plus failed counters. Because the worker takes meta.total from the response it expects, a mismatch between total and your real count is the first sign the response shape differs from what the parser assumes. Filter by imported:tinyurl, open ten links at random, and check destination, slug and title against TinyURL.

Starting a fresh Elido workspace for this takes a couple of minutes; create a free account and add your domain first so it's ready when the import finishes.

Step 4: Cut Over Your Custom Domain

If you run a branded hostname on TinyURL, you're in the easy case. TinyURL's branded domain setup is a CNAME or similar DNS change on a domain you already own, so the same lever works in reverse. Note that the importer doesn't create the domain for you or read a TinyURL domain field. A branded hostname is its own step.

Order matters, because DNS is the last step and the only one visitors feel:

  1. Lower the record's TTL a day ahead, so the switch lands fast.
  2. Add the hostname to Elido under Domains and let it verify. The add a domain guide has the exact records, and DNS verification troubleshooting covers the typos behind most stuck "Pending" states.
  3. Import the aliases onto that hostname while visitors still reach TinyURL.
  4. Spot-check the imported slugs against the live hostname's old behaviour.
  5. Change the DNS record. From that moment the hostname resolves to Elido and every old URL on it follows.

Keep the hostname DNS-only, with no CDN proxy in front, because certificate issuance can fail behind one. The wider setup is in custom domains for short links and on the custom domains feature page.

Step 5: Keep Your 301 Redirects Intact

On your own domain the URL doesn't change, so there's nothing to bridge: the same path now answers from Elido. What you protect is the redirect semantics. Redirect status codes are defined in RFC 9110; a permanent redirect tells browsers and search engines the target is stable, and switching long-lived links to temporary changes how they're cached and credited. Read 301 vs 302 redirects for the SEO and caching side.

For tinyurl.com links there's no 301 you can add, because the redirect is TinyURL's. The best you can do is make sure the destination behind the old link stays alive, and replace the link wherever you can reach it. The Bitly migration playbook shows how a 301 bridge works when you do own the old hostname.

Step 6: Verify the Migration

Migration is done when every placement of a link points at something you control. Use this list in order.

  1. Freeze new links in TinyURL. Create anything new in Elido from now on.
  2. Archive the TinyURL export files and any reports, with the date.
  3. Filter the imported batch in Elido by the imported:tinyurl tag.
  4. Compare counts: imported plus skipped plus failed should equal your source row count.
  5. Fix the failures. Every failed row comes with a reason, usually an invalid URL or a bad slug character.
  6. Test the top links. Take your 50 most important links and request each one:
curl -s -o /dev/null -w "%{http_code} %{redirect_url}\n" https://go.yourbrand.com/spring-sale
  1. Compare destination to source for those 50. Match the final URL, including UTM parameters.
  2. Re-test after DNS from a network that didn't cache the old record.
  3. Update tinyurl.com placements. Search email archives, social bios, ad platforms and print for tinyurl.com, and replace what you can.

For the surfaces you can't reach, accept the loss. Old printed QR codes and forgotten posts will keep pointing at TinyURL, and that's true of every shortener migration. The Bitly migration playbook has a stricter verification pass if you want one.

Step 7: Plan Your Rollback

Keep TinyURL for a month if you can, and watch for stragglers before cancelling a paid plan. While TinyURL still serves your branded hostname's links, rollback is one DNS change back to the old record, and the low TTL makes it quick.

Inside Elido, the imported:tinyurl tag is the handle for undoing a batch: filter, then bulk-edit or delete. If an importer run dies mid-way (a deploy or crash stops it, and a sweep every five minutes flips jobs with no progress for 30 minutes to failed), there's no saved cursor, so you restart the job. Re-running is safe under suffix or skip, but suffix will create -2 copies of links the first run already wrote, so prefer skip for a re-run.

Step 8: Set Analytics Expectations

Click history doesn't come across by either route. The importer reads link fields only, and a CSV has no click column. New clicks count from the moment a link is live in Elido, which for a custom domain means from the DNS change. Expect a short window where some visitors still reach TinyURL from cached records.

Also left behind: QR styling and templates, plus anything created without an account. If you track campaigns, carry your UTM conventions across now; UTM parameters explained is a good refresher.

What You Gain by Moving

You leave with links on a hostname you own, so the next migration, if there is one, is a DNS change instead of a project. You also get analytics that start at cutover and a tag you can query. The pricing page lists the plans, and the two posts linked at the top cover the head-to-head and the wider field.

Frequently asked questions

Can I redirect my tinyurl.com links to a new short link?

No. You do not own tinyurl.com, so only TinyURL can change where a tinyurl.com/xxxx code points. On a paid plan you can edit the destination inside TinyURL, but you cannot point it at a domain-level redirect of your own. The fix is to replace the old link wherever you published it.

How do I export my links from TinyURL?

Use the TinyURL API with a token from a paid account. TinyURL's OpenAPI spec lists links through GET /urls/available and GET /urls/archived, with optional from, to and search filters. Links created without signing in belong to no account, so there is nothing to list.

Does the Elido TinyURL importer work today?

Treat it as unverified. The worker requests a /aliases path that is not in TinyURL's OpenAPI spec (accessed 2026-10-02), so the dependable route right now is exporting through /urls/available and loading the result with Elido's CSV or bulk import. A fix to the importer is planned.

Do I lose my click history when I leave TinyURL?

Yes, for practical purposes. Elido imports destination, alias, title and tags, not click events. Export any reports you need from TinyURL before you cancel, and expect new clicks in Elido to start counting from cutover.

Can I keep my TinyURL custom domain?

Yes, because you own it. Add the hostname to Elido, import the aliases onto it, then change the DNS record at your registrar. Old links on that domain keep working because the hostname now points at Elido instead of TinyURL.

Can I migrate from a free TinyURL account?

Not automatically. Listing links needs an API token, and TinyURL puts editing, analytics, custom domains and bulk creation behind paid plans. On the free plan you rebuild a list of destinations yourself and bulk-create them in Elido.

Try Elido

Paste a URL, get a working short link

No signup. Link lives for 30 days. Sign up to keep it forever.

No signup needed. Sign up free for 50 links a month.

Try Elido

EU-hosted URL shortener with custom domains, deep analytics, and an open API. Free tier - no credit card.

Tags
migrate from tinyurl
tinyurl export
leave tinyurl
tinyurl custom domain migration
bulk import short links
tinyurl pro api

Continue reading