reserve
Find a domain name you can actually register.
reserve checks names across domain extensions grouped the way people actually think about them — by industry, by region, by how widely they are used. Filter the list, sort it, page through it, and sweep it. Answers come from the registry itself, and a lookup that cannot be answered is reported as unknown rather than guessed.
Documentation: reserve.devops.bd
$ reserve extensions --group tech --page-size 6
EXTENSION RANK KIND USED FOR
com 1 generic business, tech, shop
net 4 generic tech, business
xyz 7 generic tech, creative, crypto
co 21 country Colombia · business, tech · often used off-label
site 30 generic tech, creative
app 35 generic tech
1-6 of 35 extensions · page 1 of 6 · sorted by popularity (most used first)
next: --page 2 | --all-pages
How it decides
Three sources are tried in order, and only the first two can prove a name is free.
- The registry's structured service. Authoritative. A "no such object" answer is a fact, not an inference. Covers about 1,200 extensions.
- The registry's text service on port 43. The only thing that answers for many country extensions, including Bangladesh's own.
reservebundles a table of 883 servers generated from IANA's own records, plus servers verified by live query that IANA does not publish. - DNS. Fast, and only ever proves a name is in use. A name absent from DNS may be registered and simply never delegated, so DNS alone never produces an "available" verdict.
Pick one with --source registry, --source text, or --source dns. The default tries all three.
$ reserve hisab --tld com.bd,net.bd,org.bd,com,dev,io
+ hisab.co.bd AVAILABLE text 545ms
- hisab.com TAKEN registry 1391ms
- hisab.com.bd TAKEN text 420ms
- hisab.dev TAKEN registry 553ms
- hisab.io TAKEN registry 1269ms
+ hisab.net.bd AVAILABLE text 1538ms
2 available 4 taken 0 unknown (6 checked)
Why it exists
Most availability checkers give you a flat list of extensions and a yes or no. Two things go wrong with that.
The first is scale. There are more than 1,400 delegated extensions. A flat list is unusable, and sweeping all of them wastes the registry's patience and yours. reserve groups them so you can ask for the twenty-five that matter to a software company, or the country zones for South Asia, without hand-writing a list.
The second is coverage. Bangladesh's .bd has no structured service and IANA publishes no server for it, so most tools report it as unanswerable. reserve carries the working server and answers every .bd zone, at both the second and third level.
The third is honesty. Registries throttle bulk clients, and the older text protocol carries no status codes at all — a refusal arrives as ordinary text down the same socket as a real answer. Tools that cannot tell the difference report the whole zone as free the moment they get throttled. reserve treats every unanswerable lookup as unknown, with the reason attached, and never as available.
Picking extensions
Extensions are grouped four ways. reserve groups lists them all.
- By industry —
tech,shop,business,media,finance,health,education,food,travel,realestate,legal,crypto,creative,nonprofit - By region —
south-asia,southeast-asia,east-asia,europe,north-america,latin-america,africa,middle-east,oceania - By popularity —
top-10,top-25,top-50,top-100, ranked by how many names are actually registered in each zone - Hand-picked —
popular,classic,country-codes,domain-hacks,all,everything
Group membership is computed from extension metadata rather than stored as a list, so a group can never drift out of step with the data behind it. Groups combine — ask for two and you get the union of both.
Naming what to check
A name carrying a dot is a domain you are asking about directly, so it is checked as given whatever extensions the run selected. A list file takes one entry per line, commas also separate, # starts a comment, blank lines are skipped, and duplicates are dropped.
The picker
Run reserve with a name and no extensions, at a terminal, and it opens a picker instead of guessing:
┌ Groups ──────────────────────┐┌ Extensions (35 chosen) - active ─────────┐
│ By industry ││ [x] com 1 generic │
│ tech 35 ││ [x] net 4 generic │
│ shop 15 ││ [x] xyz 7 generic │
│ By region ││ [ ] dev 59 generic │
│ south-asia 29 ││ [ ] app 35 generic │
└──────────────────────────────┘└──────────────────────────────────────────┘
tab pane · space toggle · / search · a all · n none · enter go · q quit
Arrow keys or j/k move, tab switches pane, space toggles one extension or a whole group, / searches by extension, country, or industry, a selects everything shown, n clears, enter runs the sweep, q quits.
It never opens where there is nobody to answer: piped input, --no-input, or naming any extension all skip it, so a script behaves the same every time. --interactive forces it open.
Filtering
Filters narrow whatever you selected. They all combine.
--search <TEXT>matches the extension, its country, and its industries--industry <KEY>and--region <KEY>narrow to a sector or a part of the world--cctldkeeps only two-letter country extensions--depth second|thirdseparates plain extensions from multi-label ones such asco.uk--length 2,-3,4-, or2-4filters by length, measured on the delegated label--exclude <EXT>drops an extension from whatever else was chosen--include-restrictedadds zones the public cannot register under, hidden by default
Restricted zones are carried in the catalog but excluded from a sweep by default, so a free name in a zone nobody can buy is never offered to you as available.
Sorting and paging
Each field runs the direction that reads best for it unless you say otherwise. Popularity counts down; length and name count up. An extension with no rank always sorts to the bottom whichever direction you choose, so reversing a sort never floats unknown data to the top.
Results are paged to whatever your terminal fits, so a sweep across hundreds of extensions never scrolls away.
Seeing more
The where-to-buy links are prefilled searches in a fixed order, not an offer and not a claim that a given registrar carries that extension. Their pages will say.
Saving results
Files are written to a temporary file and renamed into place, so an interrupted run never leaves a half-written file. An unknown result is always written to its own file, so a lookup that could not be answered is never filed among the available ones.
Pointing at your own servers
By default a supplied list overlays the built-in one, so your entries win for the extensions they name and everything else still works. --servers-replace replaces it instead, which is how you reach an internal zone that has no public entry at all.
When nothing the tool already knows about answers, it asks IANA who serves that extension today, which repairs a built-in host that has gone stale. That extra lookup is cached per extension for the run, and --no-referral turns it off.
On prices
reserve deliberately shows no prices.
There is no single price for a domain extension. Comparing two of the most transparent registrars across the 405 extensions both of them price, the same extension differs by anywhere from 66 percent below to 39 percent above. Registry premium names sit outside every published list and can cost thousands. Figures exclude taxes, which depend on where you are. Wholesale prices move on scheduled dates.
A price column would imply a precision that does not exist. Check the price at the registrar you actually intend to buy from.
Reading a text answer
The older protocol has no status codes. "Not registered", "you are asking too fast", and "I do not serve that extension" all arrive as ordinary prose down the same socket, which is why tools built on it report whole zones as free the moment they get throttled.
reserve gathers every signal in an answer and then weighs them, rather than taking the first phrase that matches. That matters on real registries: one answers a taken name with Domain Status: Error followed by Message: Domain already registered, and a first-match rule calls a plainly registered name unknown. Matching is also negation-aware, because a registry that answers Available or Not Available will otherwise have every taken name in its zone reported as free.
A registry that says a specific name is blocked or reserved is reported as such, not as available and not as an error.
Pacing
A sweep across hundreds of extensions can hammer a small number of servers, because one operator often answers for hundreds of extensions from a single endpoint. reserve paces itself per registry host, never per extension — a per-extension limiter would multiply the real request rate by the number of extensions in the sweep and earn an immediate block.
- a global cap on lookups in flight
- a per-registry token bucket and concurrency cap, seeded from each operator's published limit where one exists and a cautious default where none does
- a breaker that stops asking a registry that has started refusing, waits, then sends a single probe before resuming
- backoff drawn uniformly from zero up to a ceiling that doubles with each refusal, so requests that fail together do not retry together
- a registry's own stated retry delay honoured as given, capped so a mistaken hint cannot stall a run
Pass --cautious to hold every endpoint to the cautious limit.
Commands
Exit codes
Scripts branch on these. They are a contract and do not change meaning within a major version.
0— the command succeeded; for a sweep, at least one name is available1— the sweep ran and nothing is available2— the arguments were wrong4— the network could not be reached5— a file could not be written130— the run was interrupted
Every failure also carries a stable identifier, printed as code: group.unknown, so a script can branch without parsing prose.
Output
Results go to stdout. Progress, warnings, and errors go to stderr, so a pipe receives only data. When stdout is not a terminal the decoration is dropped and the output stays parseable. A closed pipe ends the run quietly instead of panicking.
Colour follows the usual conventions in order: an explicit --color flag wins, then NO_COLOR, then FORCE_COLOR and CLICOLOR_FORCE, then a dumb terminal, then whether the stream is a terminal at all. Colours come from the sixteen named terminal colours, so retheming your terminal rethemes the tool. Meaning is never carried by colour alone — a symbol or a word always carries it too.
Building
Rust 1.88 or newer. Shell completions and man pages are generated at build time from the same command definition the parser uses, so they cannot drift from the real flags.
The catalog
The extension catalog is generated, not hand-edited, so every entry carries the same fields.
Ranks and registration counts are second-level zone counts. A zone count is not the same as a registry's own figure, because a registered-but-undelegated name never appears in the zone. Country extensions that register at the third level, such as .bd and .lk, are undercounted by any zone walk, so their rank is left blank rather than stated wrongly.
Contributing
Issues and pull requests are welcome at devops-infinity/reserve. Security reports go through the process in SECURITY.md rather than a public issue.
Licence
MIT. See LICENSE.