Skip to main content

Crate monovm_whois

Crate monovm_whois 

Source
Expand description

Domain WHOIS and RDAP lookups, with availability detection you can audit.

use monovm_whois::WhoisClient;

let client = WhoisClient::new()?;
let lookup = client.lookup("example.com")?;

println!("{} is {}", lookup.domain, lookup.availability());
if let Some(record) = &lookup.record {
    println!("registrar: {:?}", record.registrar);
    println!("expires:   {:?}", record.expires);
}

§The problem this crate is about

WHOIS has no status codes. A registry answering “that domain is free”, one answering “you are querying too fast”, and one answering “I do not serve that suffix” all send prose over the same socket, and every one of them can contain the word available. Libraries in this space overwhelmingly resolve that ambiguity the same way — anything that is not recognisably a record is treated as availability — which means a rate-limited registry reports its entire zone as free to register.

This crate never does that. A response that cannot be interpreted produces Error::Inconclusive, a refusal produces Error::Refused, and neither is ever an Availability. There is deliberately no Availability::Unknown, because an uncertain answer that renders as “available” is the one outcome a caller must not be handed.

§How it is put together

Six layers, each with one job and no knowledge of the others:

LayerResponsibilityKey abstraction
domainValidated values — a name, a suffix, a verdictDomainName, Tld
registryWhich registry serves a suffix, and how to reach itRegistryProvider
transportTalking to servers. The only I/O in the crateTransport
cacheNot asking twiceResponseCache
detectDeciding what a response saidAvailabilityRule
parserTurning a record into dataRecordParser

client composes them. Every layer is a trait with a bundled implementation, so a caller can replace any one of them — a private registry list, a transport over a proxy, a Redis cache, an extra detection rule for a registry that words things unusually — without forking the crate.

§What you get

  • Coverage. 872 curated suffixes plus IANA’s RDAP bootstrap registry, for over 1600 in total.
  • RDAP. A full RFC 9083 client and typed model, used as a fallback when port 43 refuses and preferred when Preference::Rdap is set. RDAP’s 404 makes availability a fact rather than an inference.
  • Structured records. WhoisRecord with typed dates, statuses, name servers and contacts, instead of the server’s raw text.
  • Referral chasing. Thin registries answer with a pointer to the registrar; following it is the difference between knowing a domain is taken and knowing who holds it.
  • Auditable verdicts. Every answer names the rule that produced it and why, and WhoisClient::explain shows what every rule thought.
  • Rate limiting, retries and caching, composed as transport decorators.
  • Both runtimes. WhoisClient and AsyncWhoisClient.

§Features

FeatureDefaultGives you
blockingyesWhoisClient and the synchronous transports
rdapyesRDAP over HTTPS, and the typed rdap model
parseryesWhoisRecord and record parsing
asyncnoAsyncWhoisClient and the Tokio transports
iana-bootstrapnoRefreshing the RDAP registry from IANA at runtime
clinoThe monovm-whois command line tool
mocknoMockTransport, for your own tests

§A note on what a verdict means

Availability detection over WHOIS is inference, and this crate is explicit about how much. Every Verdict carries a Confidence: Definitive for a structured RDAP answer, High for wording curated for that specific registry, Medium for a pattern that generalises, Low for the one inference drawn from absence of evidence. A caller who needs certainty can require Definitive and use Preference::RdapOnly.

Re-exports§

pub use domain::Availability;
pub use domain::DomainName;
pub use domain::SuffixSplit;
pub use domain::Tld;
pub use error::DomainError;
pub use error::Error;
pub use error::Refusal;
pub use error::Result;
pub use client::Explanation;
pub use client::Lookup;
pub use client::Preference;
pub use client::ReferralPolicy;
pub use client::CheckReport;async or blocking
pub use client::Checker;blocking
pub use client::WhoisClient;blocking
pub use client::WhoisClientBuilder;blocking
pub use client::AsyncChecker;async
pub use client::AsyncWhoisClient;async
pub use client::AsyncWhoisClientBuilder;async
pub use parser::Contact;parser
pub use parser::WhoisRecord;parser

Modules§

cache
Caching responses, so a repeated question costs nothing.
client
The facade: one object that ties the other layers together.
detect
Deciding what a response actually said.
domain
Value objects: the vocabulary the rest of the crate is written in.
error
The error type returned by every fallible operation in this crate.
parserparser
Turning a response into a WhoisRecord.
rdaprdap
The RDAP response model of RFC 9083.
registry
Which registry serves which suffix, and how to reach it.
transport
Talking to servers: the only part of the crate that performs I/O.

Constants§

VERSION
The crate version, from Cargo.toml.

Functions§

availabilityblocking
The availability of one domain, with a default client.
is_availableblocking
Whether one domain is free to register, with a default client.
lookupblocking
Look one domain up with a default client.