PeeringDB API v3

Date: 2026-09-18 · Status: DRAFT — first call for comments and review

Audience: PeeringDB users, tool authors and the Product Committee. Feedback: API v3 tracking issue #625.

The key words MUST, MUST NOT, SHOULD and MAY are interpreted as described in RFC 2119.

API v3 is the start of modernizing the PeeringDB API. Its first release is a deliberately small building block that leaves later steps open. Changes to v2 are outside this document's scope.

Summary

Goals and principles

PeeringDB API v3 is a public, read-only API designed to be served from multiple locations. It launches alongside the current API, called v2 here, with flat objects and incremental sync. Daily snapshots provide the bulk and fallback path.

OpenAPI will define queries, responses, errors and compatibility. Access and rate-limit policy will be decided before implementation.

Principle What it means for consumers
Minimal by design The first release covers known common reads; features are added as real consumer needs appear.
Public data only Every caller MUST receive the same public data; keys MUST NOT change which data is visible.
Read-only Writes remain on v2.
Flat objects Base objects contain their own fields and related IDs, without depth; relation endpoints and composites provide useful curl-able one-liners (Appendix C).
Bounded lists Every list MUST be paginated; unbounded results are unavailable.
Strict queries Unknown fields, parameters and operators MUST produce errors instead of being ignored.
Cacheable reads Public reads MUST be cacheable and usable by browser applications, without a session-dependent view.
Eventual consistency Public views MUST converge on the same dataset state.

Not in the first release, on purpose

  • Writes.
  • Authenticated or per-key data views.
  • depth expansion.
  • Ranked full-text search.
  • Spatial and distance queries.

Request additions in peeringdb#625 — API v3. Additions are non-breaking, so existing integrations keep working as v3 grows.

Service targets

v3 has the following availability and freshness targets. Freshness measures the time from a source change to a latest-data response, including cache delay; it excludes daily snapshots, historical traversals, third-party mirrors and a client's own polling interval. Responses MUST identify their dataset version, and a version endpoint MUST report source freshness.

Measure Target
Availability At least 99.95%
Normal freshness 99% of changes visible within one minute
Freshness ceiling 15 minutes for latest-data responses, including cached responses

Missing a freshness target SHOULD raise an alert and MUST NOT cause an outage or stop serving data; the ceiling is an alerting target, not a serving cutoff.

Public data and withdrawal

v3 MUST exclude restricted and non-public data. Public consumers see active objects, contacts marked Public and public IX-F member-list URLs; restricted contacts, restricted IX-F member-list URLs and non-active objects are absent. The current public field set stays, including public contact details, notes and precise coordinates.

PeeringDB MUST publish a retention window for older data it serves and provide emergency removal. This policy covers PeeringDB-served copies, not copies third parties already hold.

What changes and what stays

v3 starts with limited search: name and ASN lookup. PeeringDB will measure how often search is used and re-evaluate its scope as usage develops.

Writes, private data and distance queries remain on v2; whether v3 ever gains writes is outside this release. Authentication remains the sole purpose of the separate authentication service; its work is tracked in #1968.

Existing dump URLs are unchanged by this work.

Decisions to be made

  1. Website scope and priority. The recommendation is a new single-page website that reflects API v3 use and measures how and what people use on v2 and v3, including users who stay on v2 and users who adopt v3.

    A — Develop the website as a companion project; its priority is undecided and adoption can proceed separately.

    B — Include it in the first API release; ties the API launch to the website work.

    C — Leave website requirements out; risks an API that does not meet the site's needs.

    Recommendation: A, with the new single-page website and usage measurements above.

  2. Schema changes for the first release. Decide whether to complete the agreed schema changes before the first v3 release.

    A — Include them in the first release; consumers and incremental sync start with the agreed schema.

    B — Defer changes until after launch; makes the first migration smaller but requires later client updates and compatibility work.

    Recommendation: A, include schema changes in the first release, keeping features small while settling the data shape up front.

Schema changes

Several changes are already givens and will not delay launch. The Product Committee (PC) SHOULD decide the field and object changes separately, with community input, so they can be folded into the initial v3 release. Appendices F and G collect that discussion; an issue request does not commit a field change to the release.

Including the changes in the first release gives consumers one schema migration and lets incremental sync start with that schema. Changes after launch require further client updates and a compatibility rule for lists, snapshots and deltas, so consumers never silently interpret incompatible data under the wrong schema.

Closing

This is the first call for feedback on the v3 contract; send comments and concrete use cases to issue #625. The next revision will address that feedback and the remaining decisions, with field and object changes reviewed separately by the PC with community input. OpenAPI will then specify the exact requests and responses.

Appendices

A. Operators and filtering

The API v3 path is undecided; /v3/ is an example prefix only. Example paths, parameter spelling, header names and JSON shapes are illustrative pending OpenAPI. The operator set below is decided; supported field/type combinations and exact value encodings remain undecided.

Operator Meaning Qualification
Equality Exact match Case-sensitive for strings by default; exact query spelling pending OpenAPI
lt, lte Less than, less than or equal Supported fields and types to be specified
gt, gte Greater than, greater than or equal Supported fields and types to be specified
in Match any listed value At most 500 values; list encoding undecided
contains Substring match Strings; case-sensitive
startswith Prefix match Strings; case-sensitive
iexact Case-insensitive equality Strings only
icontains Case-insensitive substring Strings only
istartswith Case-insensitive prefix Strings only

Ordering operators and in have no case-insensitive variants. Unicode normalization, case and diacritic handling MUST mean the same thing everywhere; the exact rules remain undecided. OpenAPI MUST also settle null versus absent, duplicate parameters, filter composition, timestamp precision/time zone and default ordering.

Unknown parameters, fields and unsupported operators MUST return 400 rather than being ignored. Errors use RFC 9457 problem details, application/problem+json; their exact fields will be in OpenAPI. Public responses permit browser access with Access-Control-Allow-Origin: *.

A list traversal MUST read one dataset version or receive an explicit restart requirement. Lists use 250 records per page by default, with a maximum of 1,000, and omit total counts; consumers finish the traversal to establish completeness.

Illustrative requests; angle-bracketed values are placeholders, not literal query values:

GET /v3/net/<net-id>
GET /v3/net?asn=<asn>
GET /v3/fac?city__istartswith=<city-prefix>
GET /v3/netixlan?net_id=<net-id>

B. Object types and references

These are the current object types and verified v2 reference names. They do not promise that every current object or field will be preserved in v3; proposed folds and renames appear in Appendix F.

Object Meaning Current related IDs (v2, verified)
org Organization
fac Facility org_id, campus_id
ix Internet exchange org_id
ixlan Exchange LAN ix_id
ixpfx Exchange LAN prefix ixlan_id
net Network org_id
netfac Network at a facility net_id, fac_id
netixlan Network on an exchange LAN net_id, ixlan_id, ix_id; optional facility references net_side_id, ix_side_id
poc Network contact net_id
campus Campus org_id
carrier Carrier org_id
carrierfac Carrier at a facility carrier_id, fac_id
ixfac Exchange at a facility ix_id, fac_id

Base responses contain their own fields and related IDs, without nested related objects. Composites and relation endpoints cover common requests for related data.

C. Relation endpoints and composites

v3 will provide curl-able relation endpoints and composites for common one-liners: a network with its exchange presences, an exchange with its members, or a facility with its occupants. The initial set will be chosen from user requests and MAY land in a second v3 phase; its scope and paths are undecided. These endpoints replace common uses of depth without requiring consumers to assemble several lists themselves, and their responses MUST remain bounded.

D. Daily snapshots

Daily snapshots already exist at public.peeringdb.com and are updated once a day. They provide the bulk, bootstrap and fallback path, with the dataset version included in every file. This existing service needs better documentation.

E. Incremental sync

v3 MUST offer delta sync. A client polling at a tight interval, for example every five minutes, MUST be able to keep a fresh copy; deletions and withdrawals MUST be visible in the delta. Daily snapshots provide the bootstrap and fallback path. OpenAPI will define the requests used for delta sync.

Schema changes (to be decided separately by the PC)

The schema changes and linked issues below will be reviewed and decided separately by the PC.

F. Schema changes by object

This list separates requirements from proposals and issue requests. A request's presence here does not set its release date, and a change to the public representation need not change the stored data model. Renames with no agreed destination say target undecided.

Status Meaning
Decided in the design A requirement of v3 in this document.
Proposed A recommendation that remains undecided.
Issue request, undecided A change requested for discussion, without a decision here.
Confirmed in tracker; v3.0 scope undecided #625 lists the removal as confirmed, but this draft has not settled its inclusion in v3.0.
org
  • Review: floor/suite; the v2 summary favors suite and deprecates floor — issue request, undecided (#1482, v3 deferral).
  • Rename: address1address; address2extended-address — issue request, undecided (#255).
  • New field: po-box — issue request, undecided (#255).
  • Object split: move address details into a location object, an alternative to inline address fields — issue request, undecided (#255).
  • Rename: countrygeography was proposed; target undecided — issue request, undecided (#552, closure without agreement).
  • Rename/drop: merge aka and name_long into one alias field; API target undecided — issue request, undecided (#1488).
fac
  • Drop: npanxx; the final drop summary does not include clli — issue request, undecided (#895).
  • Drop: rencode — issue request, undecided (#431).
  • Rename: address1address; address2extended-address — issue request, undecided (#255).
  • New field: po-box, empty for facilities in the issue's proposal — issue request, undecided (#255).
  • Object split: address details into a location object, including physical/delivery address distinctions — issue request, undecided (#255, #1407).
  • Rename: countrygeography was proposed; target undecided — issue request, undecided (#552).
  • Rename/drop: merge aka and name_long into one alias field; API target undecided — issue request, undecided (#1488).
  • Type change (reference values): return campus_id as null when the campus is excluded from public data; not necessarily a database type change — Proposed.
ix
  • Drop: media — issue request, undecided (#487, #1555).
  • Drop: proto_unicast, proto_multicast, proto_ipv6 — issue request, undecided (#810).
  • Object fold: absorb ixlan into ix — issue request, undecided (#609, django-peeringdb#55).
  • New fields/object fold: replace separate ixpfx objects with prefixlist4 and prefixlist6 on ix, allowing multiple prefixes — issue request, undecided (#609, v3 deferral).
  • Rename: countrygeography was proposed; target undecided — issue request, undecided (#552).
  • Rename/drop: merge aka and name_long into one alias field; API target undecided — issue request, undecided (#1488).
ixlan
  • Drop: dot1q_support — confirmed in tracker; v3.0 scope undecided (#903, #625).
  • Object fold: remove the separate IXLAN object in favor of IX — issue request, undecided (#609).
  • Type change (client-library relationship): one IXLAN per IX; distinct from removing the HTTP API object — issue request, undecided (django-peeringdb#55, summary).
  • Drop (conditional public projection): omit ixf_ixp_member_list_url when its visibility is not Public — Proposed; public-only access is decided in the design.
ixpfx
  • Drop: in_dfz — issue request, undecided (#761).
  • Object fold: replace separate prefix objects with IX prefix lists, prefixlist4 and prefixlist6 — issue request, undecided (#609).
net
  • Drop: info_type in favor of existing multi-select info_types; not a new v3 field — confirmed in tracker; v3.0 scope undecided (#1357, #625).
  • Review: info_traffic; the issue retained it with help text before the tracker called for review — issue request, undecided (#594, #625).
  • Review: all info_ fields for relevance and naming; individual changes and targets undecided — issue request, undecided (#625).
  • Rename: irr_as_set, target undecided — issue request, undecided (#625 comment linking PR #854).
  • New field: read-only global BFD-support boolean aggregated from connection flags; target undecided — issue request, undecided (#1331).
  • Drop (expanded representation): nested org in base responses; retain related IDs — decided in the design; resolves the shape difference in #1217.
netfac
  • Review: copied name, city, country; the issue body identifies them on netfac, but its v3 removal comment reverses netfac/ixfac, leaving the intended object ambiguous — issue request, undecided (#166 body, v3 comment).
netixlan
  • Drop: duplicated ASN; the v3 comment calls it local_asn, while a later summary identifies netixlan.asn and a read-only view of the network ASN as the interim change — issue request, undecided (#1671 v3 comment, clarification).
poc
  • Drop (public projection only): omit contact records whose visible is not Public, including references exposing their IDs — Proposed; public-only access is decided in the design.
campus
  • Type change (response shape): minimal pending-campus records as an alternative to clearing facility references; not the default proposal — Proposed.
carrier
  • Rename/drop: merge aka and name_long into one alias field; API target undecided — issue request, undecided (#1488).
carrierfac
  • No object-specific v3 field change identified; flat representations apply — decided in the design.
ixfac
  • Review: copied name, city, country; the v3 comment names ixfac, while the final v2 summary adds those fields to it — issue request, undecided (#166 v3 comment, v2 summary).
Cross-object
  • Address model: align the postal address fields with ISO 19160 per the gap analysis — issue request, undecided (#1797; predecessor #1127).
  • Drop: implicit nested related objects from base responses; scalar fields and related IDs remain — decided in the design.
  • Type change (enum values, not primitive types): discuss lowercasing all enum values; no enum-by-enum mapping — issue request, undecided (#625).
  • Type change (reference values): null references whose targets are outside public data, with minimal-parent records as an alternative — Proposed.
  • Drop (public projection only): pending/deleted rows and fields outside an explicit public-field list; not database field removals — Proposed.
  • New fields (snapshot metadata): dataset version, schema/projection version, complete file list, per-file sizes and hashes; field names undecided — decided in the design.
  • New field (each snapshot file): dataset version; field name undecided — Proposed.
  • New fields (response/version metadata): served dataset version plus a version endpoint reporting source freshness; names undecided — decided in the design.

G. Linked issues and coverage

Covered means the requirement is decided in this draft; listed, undecided means its adoption is unresolved. The two tracker-confirmed removals use the status defined in Appendix F. The final two rows capture requests made in #625 comments rather than in separately linked issues.

Issue Ask Coverage
#487 Drop IX media Listed, undecided — F: ix
#895 Drop facility npanxx Listed, undecided — F: fac; clli was excluded from the final issue summary
django-peeringdb#55 IX–IXLAN one-to-one relation; discuss removing IXLAN Listed, undecided — F: ixlan; library relation and API object fold are separate asks
#595 Establish a v3 planning tracker Covered — #625 is the tracking issue
#609 Fold IXLAN and prefix lists into IX Listed, undecided — F: ix/ixlan/ixpfx; the create-response fix shipped on v2
#255 Restructure organization/facility addresses Listed, undecided — F: org/fac; floor/suite additions shipped on v2
#552 Rename country and accept the new query name Rename listed, undecided — F: org/fac/ix; query-alias behavior unspecified
#761 Drop prefix in_dfz Listed, undecided — F: ixpfx
#1217 Resolve single/list nested-organization inconsistency Covered — flat objects without depth, B/C; nested expansion is not retained
#1331 Add a network-wide BFD aggregate Listed, undecided — F: net; per-IP support shipped on v2
#1407 Address objects and duplicate-facility policy Address change listed, undecided — F: fac; duplicate policy unspecified
#1488 Merge aka and name_long Listed, undecided — F: org/fac/ix/carrier
#166 Review copied facility name/city/country Listed, undecided — F: netfac/ixfac; issue comments disagree about the object
#594 Review dropping info_traffic Listed, undecided — F: net; previously retained with help text
#903 Drop dot1q_support Confirmed in tracker; v3.0 scope undecided — F: ixlan
#1357 Drop info_type for info_types Confirmed in tracker; v3.0 scope undecided — F: net
#431 Drop facility rencode Listed, undecided — F: fac
#810 Drop IX protocol flags Listed, undecided — F: ix
#1555 Drop IX media Listed, undecided — F: ix; same field as #487
#1671 Remove duplicated connection ASN Listed, undecided — F: netixlan; local_asn wording clarified as netixlan.asn later in the issue
#1482 Review organization floor/suite drops Listed, undecided — F: org
#854 (PR) Review irr_as_set naming Listed, undecided — F: net; rename ask is in #625's linking comment
#1797 Address schema gap analysis against ISO 19160 Listed, undecided — F: cross-object; added address reference, not a #625 cross-reference
#1127 Standardized addresses supporting floor/suite Listed, undecided — F: cross-object; predecessor to #1797
#625: enums Lowercase enum values Listed, undecided — F: cross-object
#625: info fields Review all info_ fields for relevance and naming Listed, undecided — F: net

H. Glossary

Term Meaning
v2 The current, unversioned PeeringDB API at /api/.
Flat object An object's own fields plus related IDs, without nested related objects.
Snapshot A complete public dataset at one consistent state.
Dataset version An identifier for a particular state of the public data.
Schema version An identifier for the fields and shapes used to represent that data.
Public projection The rows and fields PeeringDB includes in its public dataset.
Delta sync Updating a local copy using the changes since an earlier sync.
Withdrawal Removing a row or field from public data, including after deletion or a visibility change.
Relation endpoint A list of objects related to a specified object.
Composite A documented response containing several related objects or lists.
IX-F member-list URL An exchange's URL for its IX-F member-list data; its visibility can be restricted.
Active An object with status: ok, as opposed to pending or deleted.
Pending An object with status: pending; excluded from v3 public data.
Restricted A record or field whose visibility is not Public and therefore requires permission to read.
Retention window The published period during which older data remains available.
Traversal Reading successive pages until a list is complete.
Eventual consistency Public views converge on the same dataset state as changes propagate.
PC PeeringDB Product Committee.