TypeScript SDK
Build with the official Forecite TypeScript / Node.js SDK.
The official TypeScript SDK gives you a single typed surface across the Forecite
scored feed, the Verdict Engine, reference data, webhooks, and the realtime
stream. It runs in Node.js and any modern runtime with fetch and WebSocket.
Beta
The TypeScript SDK is in beta while we harden the surface ahead of a stable
1.0. Method names and shapes may still change.
One Forecite client exposes every resource as a namespace — forecite.feeds,
forecite.providers, forecite.score, forecite.stream — all authenticated
with a single API key.
Quickstart
Install the package
npm install @forecite/sdkCreate a client
Pass your fc_live_… key (get one from the API keys
page). Keep it server-side.
import { Forecite } from "@forecite/sdk"
const forecite = new Forecite(process.env.FORECITE_API_KEY!)Fetch scored feeds
const { data, next_cursor } = await forecite.feeds.list({
symbol: "NVDA",
actionability: true,
limit: 10,
})
for (const item of data) {
console.log(item.title, item.scoring.sentiment_score)
}SDK patterns
The client uses consistent patterns for configuration, pagination, and errors across every resource.
Response models
Reads return typed models with snake_case fields matching the API. A feed item
carries the source artifact plus its Verdict Engine scoring block:
interface FeedItem {
id: string
title: string | null
link: string | null
source: string
published_at: string
scraped_at: string
scoring: {
actionability: boolean | null
actionability_comment: string | null
sentiment_score: number | null // 0–10 (5 = neutral)
sentiment_comment: string | null
}
symbols: { symbol: string; exchange: string | null }[]
}Environment configuration
Production is the default. Pass baseUrl / wsUrl to target local dev or a
custom deployment.
const forecite = new Forecite({
apiKey: process.env.FORECITE_API_KEY!,
baseUrl: "http://localhost:3000/api",
wsUrl: "ws://localhost:8080",
})Pagination
List endpoints return { data, next_cursor }. Pass next_cursor back as
cursor to page; a null cursor means you've reached the end.
let cursor: string | null | undefined
do {
const page = await forecite.feeds.list({ limit: 100, cursor })
for (const item of page.data) handle(item)
cursor = page.next_cursor
} while (cursor)Error handling
Every failed request throws a ForeciteError carrying the HTTP status and the
API's code / message.
import { Forecite, ForeciteError } from "@forecite/sdk"
try {
const page = await forecite.feeds.list({ limit: 10 })
} catch (err) {
if (err instanceof ForeciteError) {
if (err.status === 429) {
// Rate limited — retry with backoff.
} else if (err.status === 401) {
// Bad or missing API key.
}
}
throw err
}Feed data
Read the scored feed — list with filters, or fetch a single item by id.
// Filtered list — actionable NVDA items, most bullish first
const { data } = await forecite.feeds.list({
symbol: "NVDA",
actionability: true,
sentiment_min: 7,
})
// One item with full per-symbol detail
const item = await forecite.feeds.get("0b3f2c1e-…")Available filters: since / until (ISO 8601), symbol, exchange,
aggregator, actionability, sentiment_min / sentiment_max, limit,
cursor.
Discovery
Browse the reference data that powers the feed's filters.
const providers = await forecite.providers.list()
const one = await forecite.providers.get(providers[0].id)const sources = await forecite.sources.list() // string[]
const activity = await forecite.sources.get("globenewswire")const symbols = await forecite.symbols.list({ limit: 500 })
const nvda = await forecite.symbols.get("NVDA")Scoring
Run the Verdict Engine on your own text. Pass an artifact and optional scoring options.
const verdict = await forecite.score(
{
type: "filing",
title: "Acme cuts FY guide on softening demand",
body: "Acme Corp lowered its full-year revenue outlook…",
related_symbols: ["ACME"],
},
{ model: "pro", score_sentiment: "if_actionable" },
)
console.log(verdict.actionability.score, verdict.sentiment?.short_direction)Realtime streams
Subscribe to the scored feed over WebSocket. The stream auto-reconnects and can replay a snapshot of the latest matching items before going live.
const stream = forecite.stream(
{ filters: { symbols: ["NVDA", "TSLA"], actionable: true }, snapshot: 10 },
{
onWelcome: ({ tier }) => console.log("connected:", tier),
onFeed: (item, { snapshot }) => {
console.log(snapshot ? "backfill" : "live", item.title)
},
onQuotaExceeded: ({ message }) => console.warn(message),
onError: (err) => console.error(err),
},
)
// stream.ping() — app-level keepalive
// stream.close() — stop and disable reconnectWebSocket runtime
A global WebSocket is required — Node 22+, a browser, or a polyfill.
Account
Inspect the authenticated key and its usage.
const key = await forecite.me() // tier, limits
const usage = await forecite.usage({ days: 14 }) // daily feed vs. score usageWebhooks
Manage outbound webhook endpoints.
const hook = await forecite.webhooks.create({
url: "https://example.com/forecite",
description: "prod",
})
await forecite.webhooks.list()
await forecite.webhooks.update(hook.id, { enabled: false })
await forecite.webhooks.delete(hook.id)Changelog
0.1.2
- First public beta of
@forecite/sdk. - Typed clients for feeds, scoring, discovery, account, webhooks.
- Auto-reconnecting realtime feed stream with snapshot replay.