Notyfi trackers API
The trackers API from Notyfi — 6 operation(s) for trackers.
The trackers API from Notyfi — 6 operation(s) for trackers.
openapi: 3.1.0
info:
title: Notyfi account trackers API
version: 1.2.0
description: 'Track anything in a sentence and get notified the moment it happens -- by email, REST API, or MCP. Authenticate every request with a Notyfi API key (`Authorization: Bearer notyfi_mk_...`). Manage keys in your dashboard.'
servers:
- url: https://api.notyfi.com
security:
- bearerAuth: []
- apiKeyAuth: []
tags:
- name: trackers
paths:
/api/v1/trackers:
post:
tags:
- trackers
summary: Create a Notyfi tracker
description: Product-named alias of feed-request creation; returns the canonical ``public_id``.
operationId: create_tracker_api_v1_trackers_post
parameters:
- name: X-Notyfi-ID-Token
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Notyfi-Id-Token
- name: Idempotency-Key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Idempotency-Key
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequestCreate'
responses:
'201':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequest'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Principal request limit or rolling tracker-creation limit; honour Retry-After.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'403':
description: The API key lacks the feeds:write capability required for tracker mutations.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'402':
description: The requested delivery cadence requires Pro.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'409':
description: Active tracker plan limit, verified-account requirement, or Idempotency-Key body conflict.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Invalid body, cadence, or Idempotency-Key.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
get:
tags:
- trackers
summary: List the caller's Notyfi trackers
operationId: list_trackers_api_v1_trackers_get
parameters:
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
responses:
'200':
description: Successful Response
content:
application/json:
schema:
type: array
items:
$ref: '#/components/schemas/FeedRequest'
title: Response List Trackers Api V1 Trackers Get
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
/api/v1/trackers/{public_id}:
get:
tags:
- trackers
summary: Get one tracker by opaque public id
operationId: get_tracker_api_v1_trackers__public_id__get
parameters:
- name: public_id
in: path
required: true
schema:
type: string
pattern: ^fr_[A-Za-z0-9_-]{22}$
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
title: Public Id
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
responses:
'200':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequest'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Feed request not found (or owned by another tenant).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'410':
description: The owned tracker was soft-deleted (code 'feed_deleted').
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
delete:
tags:
- trackers
summary: Archive a tracker by opaque public id
operationId: archive_tracker_api_v1_trackers__public_id__delete
parameters:
- name: public_id
in: path
required: true
schema:
type: string
pattern: ^fr_[A-Za-z0-9_-]{22}$
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
title: Public Id
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
responses:
'200':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequest'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'403':
description: The API key lacks the feeds:write capability required for tracker mutations.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Feed request not found (or owned by another tenant).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'409':
description: Illegal lifecycle transition -- ratify/decline is only legal while the request is in state 'spec_ready'.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
/api/v1/trackers/{public_id}/progress:
get:
tags:
- trackers
summary: Get tracker research/build progress by opaque public id
operationId: get_tracker_progress_api_v1_trackers__public_id__progress_get
parameters:
- name: public_id
in: path
required: true
schema:
type: string
pattern: ^fr_[A-Za-z0-9_-]{22}$
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
title: Public Id
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
responses:
'200':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequestProgress'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Feed request not found (or owned by another tenant).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'410':
description: The owned tracker was soft-deleted (code 'feed_deleted').
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
/api/v1/trackers/{public_id}/events:
get:
tags:
- trackers
summary: List a live tracker's canonical events by opaque public id
operationId: list_tracker_events_api_v1_trackers__public_id__events_get
parameters:
- name: public_id
in: path
required: true
schema:
type: string
pattern: ^fr_[A-Za-z0-9_-]{22}$
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
title: Public Id
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
- name: limit
in: query
required: false
schema:
type: integer
maximum: 200
minimum: 1
default: 50
title: Limit
- name: cursor
in: query
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Cursor
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
responses:
'200':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/Page_FeedEvent_'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Feed request not found (or owned by another tenant).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'410':
description: The owned tracker was soft-deleted (code 'feed_deleted').
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
/api/v1/trackers/{public_id}/delivery:
patch:
tags:
- trackers
summary: Update tracker delivery by opaque public id
operationId: update_tracker_delivery_api_v1_trackers__public_id__delivery_patch
parameters:
- name: public_id
in: path
required: true
schema:
type: string
pattern: ^fr_[A-Za-z0-9_-]{22}$
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
title: Public Id
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
- name: X-Notyfi-ID-Token
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Notyfi-Id-Token
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/FeedDeliveryUpdate'
responses:
'200':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequest'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'403':
description: The API key lacks the feeds:write capability required for tracker mutations.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Feed request not found (or owned by another tenant).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'410':
description: The owned tracker was soft-deleted (code 'feed_deleted').
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'402':
description: Cadence requires Pro.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'409':
description: Verified account email is required.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
/api/v1/trackers/{public_id}/retry:
post:
tags:
- trackers
summary: Retry a stalled tracker by opaque public id
operationId: retry_tracker_api_v1_trackers__public_id__retry_post
parameters:
- name: public_id
in: path
required: true
schema:
type: string
pattern: ^fr_[A-Za-z0-9_-]{22}$
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
title: Public Id
description: Opaque tracker id returned by create/list (not the internal database id or feed slug).
- name: authorization
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Authorization
- name: x-api-key
in: header
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: X-Api-Key
responses:
'200':
description: Successful Response
content:
application/json:
schema:
$ref: '#/components/schemas/FeedRequest'
'401':
description: Missing or invalid credentials (auth enabled).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limit exceeded (per-principal fixed window). Honour the Retry-After + X-RateLimit-* headers.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'403':
description: The API key lacks the feeds:write capability required for tracker mutations.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Feed request not found (or owned by another tenant).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'410':
description: The owned tracker was soft-deleted (code 'feed_deleted').
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'409':
description: Not retryable -- the request is not in state 'researching'/'building', or its run still looks ACTIVE (recent activity on the staleness clock; retry unlocks after inactivity).
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'503':
description: The retry was accepted but the dispatch queue is unconfigured/unavailable -- nothing was re-queued (code 'dispatch_unavailable'); try again shortly.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'422':
description: Validation Error
content:
application/json:
schema:
$ref: '#/components/schemas/HTTPValidationError'
components:
schemas:
FeedProgressEntry:
properties:
ts:
anyOf:
- type: string
- type: 'null'
title: Ts
description: ISO-8601 UTC stamp when the line was appended.
line:
type: string
title: Line
description: The human-readable progress line.
type: object
required:
- line
title: FeedProgressEntry
description: 'One legible line in a feed request''s LIVE research trail (append-only): a UTC timestamp + the
human-readable line (''probed <url> -> socrata 5 rows OK'', ''excluded <url>: robots'', ''dry-run:
extracted N in-scope'', ''spec_ready: slug=... -> attached'').'
TimestampsBlock:
properties:
occurred_at:
type: string
title: Occurred At
description: The event-time field (REQUIRED).
as_of:
anyOf:
- type: string
- type: 'null'
title: As Of
description: The revision-time field (evolving events); null = none.
order_by:
anyOf:
- type: string
- type: 'null'
title: Order By
description: The feed-ordering field; null = occurred_at (the default).
additionalProperties: false
type: object
required:
- occurred_at
title: TimestampsBlock
description: The feed's timestamp roles. All three name datetime-typed fields in ``fields``.
FeedRequestState:
type: string
enum:
- submitted
- researching
- spec_ready
- ratified
- declined
- refused
- building
- live
- archived
- quarantined
title: FeedRequestState
description: 'Where a feed request is in its lifecycle. USER-visible: submitted -> researching ->
spec_ready -> {ratified, declined} -> building -> live; ``refused`` is the honest-refusal
outcome (research found no adequate source backbone -- the Coverage Report says why);
``archived`` is the SOFT DELETE ("REMOVE FROM WORKSPACE") that stops serving/polling but KEEPS all
the feed''s work and RESERVES its slug. Any visible state can be archived; archived is terminal.
``quarantined`` is the CONTENT-POLICY hold: a create whose query trips moderation is recorded here
instead of researched/served (``refusal_reason`` carries the policy message); reversible to
archived (purge) or submitted (release a false positive).'
ValidationError:
properties:
loc:
items:
anyOf:
- type: string
- type: integer
type: array
title: Location
msg:
type: string
title: Message
type:
type: string
title: Error Type
input:
title: Input
ctx:
type: object
title: Context
type: object
required:
- loc
- msg
- type
title: ValidationError
FeedScope:
properties:
event_definition:
type: string
minLength: 1
title: Event Definition
description: The ratified one-paragraph definition of what counts as an event.
acceptance_examples:
items:
$ref: '#/components/schemas/AcceptanceExample'
type: array
title: Acceptance Examples
description: In/out scope examples (~20 at ratification) -- the boundary, made testable.
geography:
anyOf:
- type: string
- type: 'null'
title: Geography
description: Geographic/filter bound (ZIPs, borough/block ranges, ...); null = unbounded.
freshness_expectation:
anyOf:
- type: string
- type: 'null'
title: Freshness Expectation
description: The user's freshness expectation in plain words ('daily', 'within a week').
additionalProperties: false
type: object
required:
- event_definition
title: FeedScope
description: 'The ratified scope: what an EVENT is, the in/out examples, and the geographic/freshness bounds.'
WriteMode:
type: string
enum:
- upsert
- append
title: WriteMode
Error:
properties:
error:
$ref: '#/components/schemas/ErrorBody'
type: object
required:
- error
title: Error
description: The single error response shape for every 4xx/5xx on the contract.
example:
error:
code: not_found
message: lead not found
LifecycleBlock:
properties:
status_field:
type: string
title: Status Field
description: The status field name (must exist in fields).
terminal_states:
items:
type: string
type: array
minItems: 1
title: Terminal States
description: Status values that mean the event is finished.
additionalProperties: false
type: object
required:
- status_field
- terminal_states
title: LifecycleBlock
description: 'End-state declaration: when status_field lands in terminal_states the event is finished.'
EntityRole:
type: string
enum:
- subject
- counterparty
- intermediary
- successor
title: EntityRole
description: Semantic entity typing for role='entity' fields (acquirer/target, buyer/seller, ...).
BillingCadence:
type: string
enum:
- instant
- hourly
- daily
- weekly
title: BillingCadence
FeedMonitorState:
properties:
current_value:
anyOf:
- type: string
- type: 'null'
title: Current Value
description: The most recent reading the observe fetch saw (single-value kinds; canonical string form).
observed_at:
anyOf:
- type: string
- type: 'null'
title: Observed At
description: When that reading was taken (ISO-8601 UTC).
checked_at:
anyOf:
- type: string
- type: 'null'
title: Checked At
description: When the feed last checked its source, successful or not (ISO-8601 UTC).
type: object
title: FeedMonitorState
description: 'The LIVE MONITOR READ for an observe feed (feed_monitor_state, 2026-07-19): the
current value the last check saw + when it was seen + when the feed last checked at
all. Deliberately OUTSIDE the event/revision pipeline (a quiet check advances
checked_at without revising anything), so the monitor card can show ''Current Value''
and ''Last checked'' truthfully. Detail reads only; null for non-observe feeds and
feeds that have not ticked since the state table shipped.'
Page_FeedEvent_:
properties:
items:
items:
$ref: '#/components/schemas/FeedEvent'
type: array
title: Items
description: The page of results.
next_cursor:
anyOf:
- type: string
- type: 'null'
title: Next Cursor
description: Opaque cursor for the next page; null at end.
total:
type: integer
title: Total
description: Count of items in this response (approximate).
default: 0
type: object
title: Page[FeedEvent]
example:
items: []
total: 0
EnginePin:
properties:
version:
type: string
title: Version
description: Registry name of the pinned engine ('legacy', 'opus-tuned', ...) -- validated against crawler.engines.ENGINES.
config_version:
type: integer
minimum: 1.0
title: Config Version
description: 'The engine''s config_version at pin time (provenance: which tuning of the recipe produced this feed''s current state).'
default: 1
overrides:
anyOf:
- additionalProperties: true
type: object
- type: 'null'
title: Overrides
description: 'Per-feed engine overrides, validated against the PINNED engine''s declared lever set (search engines: model, web_search_tool, max_uses, max_tokens, max_turns, backfill_days, prompt_addendum; watch-observe declares its own observe-shaped set). null = the engine''s registry defaults.'
additionalProperties: false
type: object
required:
- version
title: EnginePin
description: 'Which acquisition-engine recipe runs this feed''s search stage, pinned per feed.
The pin is what makes engine rollouts safe: a spec without one (everything compiled
before the registry) resolves to the FROZEN legacy recipe, so shipping a new image never
moves an existing feed. ``overrides`` is the per-feed manual-augmentation surface --
keys AND value coercibility are validated against the PINNED ENGINE''s declared lever set
(``Engine.override_keys``; config shapes differ per engine) so a typo''d augmentation
fails at attach-spec, never silently at run time.'
FieldType:
type: string
enum:
- string
- number
- integer
- boolean
- datetime
- enum
- url
- string_list
- number_list
- entity_list
title: FieldType
description: The closed value-type vocabulary of a schema field.
ErrorBody:
properties:
code:
type: string
title: Code
description: Stable machine-readable error code.
message:
type: string
title: Message
description: Human-readable detail.
request_id:
anyOf:
- type: string
- type: 'null'
title: Request Id
description: Correlation id, when available.
type: object
required:
- code
- message
title: ErrorBody
SourceFormat:
type: string
enum:
- rss
- api
- socrata
- csv
- search
- observe
- html
title: SourceFormat
description: 'How a source is fetched/parsed. rss/api/socrata/csv/search/observe are MACHINE-READABLE
(v0-includable catalog rows, zero codegen; an observe source is a FROZEN compile-time
target in config[''observe''], fetched by the pinned watch-observe engine); html is not
(v1 scraper codegen).'
AcceptanceExample:
properties:
text:
type: string
minLength: 1
title: Text
description: A concrete candidate item, in plain words.
included:
type: boolean
title: Included
description: True = inside the ratified scope; False = explicitly out.
additionalProperties: false
type: object
required:
- text
- included
title: AcceptanceExample
description: 'One in/out scope example: a concrete candidate item + whether the ratified scope includes it.
The ~20 of these ARE the executable definition of the feed''s boundary (the scope gate''s test set).'
UncertaintyBias:
type: string
enum:
- under-merge
- over-merge
title: UncertaintyBias
description: 'The DECLARED dedup cost asymmetry the adjudication prompts encode (documentation that is
load-bearing in prompt TEXT, never branched on -- mirrors IdentityPattern.uncertainty_bias).'
HTTPValidationError:
properties:
detail:
items:
$ref: '#/components/schemas/ValidationError'
type: array
title: Detail
type: object
title: HTTPValidationError
FeedDeliveryUpdate:
properties:
cadence:
anyOf:
- $ref: '#/components
# --- truncated at 32 KB (66 KB total) ---
# Full source: https://raw.githubusercontent.com/api-evangelist/notyfi/refs/heads/main/openapi/notyfi-trackers-api-openapi.yml