TypeScript SDKv1.0

TypeScript SDK Reference

Full type-safe access to the Tapas API. Every response field is typed, every error is catchable, and every integration pattern is documented with working examples.

npm install @tapas-ai/sdk

Installation

Install via your preferred package manager. The SDK ships with TypeScript types included — no @types package needed.

Terminal
bash
npm install @tapas-ai/sdk
# or
yarn add @tapas-ai/sdk
# or
pnpm add @tapas-ai/sdk
Minimum requirements: TypeScript 4.7+, Node.js 18+, or any modern browser with fetch support.

Type Reference

All interfaces and types exported by @tapas-ai/sdk. Copy this block into your project to use Tapas types without installing the SDK.

types.ts
typescript
// ─────────────────────────────────────────────────────────────────
// Core types exported from @tapas-ai/sdk
// ─────────────────────────────────────────────────────────────────

export type RoutingMethod = 'cosine' | 'smart-router' | 'hybrid';
export type ResponseMode  = 'cache' | 'llm';

/** Full response returned by every Tapas query */
export interface TapasResponse {
  /** How the answer was served: 'cache' (LEM) or 'llm' (full inference) */
  mode:             ResponseMode;
  /** Whether Low Energy Mode was active for this query */
  lemMode:          boolean;
  /** Full prose answer — populated in LLM mode */
  answer:           string;
  /** Bullet-point list — populated in cache / LEM mode */
  bullets:          string[] | null;
  /** Matched knowledge category name (e.g. "Quantum Computing") */
  category:         string;
  /** Top-level domain slug (e.g. "science_technology") */
  domain:           string;
  /** Cosine similarity score 0–1 between query and cached entry */
  confidence:       number;
  /** Classification method used to route this query */
  routingMethod:    RoutingMethod;
  /** Watt-hours consumed by this query */
  energyWhUsed:     number;
  /** Watt-hours saved vs. full GPU inference */
  energyWhSaved:    number;
  /** End-to-end latency in milliseconds */
  responseTimeMs:   number;
  /** Cache entry ID — null when served by LLM */
  cachedResponseId: string | null;
}

/** Options accepted by askTapas() and the TapasClient */
export interface TapasAskOptions {
  /** The user's question */
  query:    string;
  /** Enable Low Energy Mode — returns bullet points from cache */
  lemMode?: boolean;
  /** Hint the router to a specific domain slug */
  domain?:  string;
}

/** Configuration for TapasClient */
export interface TapasClientConfig {
  apiKey:   string;
  baseUrl?: string; // defaults to 'https://tapas.one'
  timeout?: number; // ms, defaults to 10000
}

TapasClient

The primary SDK entry point. Initialise once at the module level and reuse across your application. The client handles retries, timeouts, and API key injection automatically.

tapas-client.ts
typescript
import { TapasClient } from '@tapas-ai/sdk';

// Initialise once — reuse across your app
const tapas = new TapasClient({
  apiKey:  process.env.TAPAS_API_KEY!,
  baseUrl: 'https://tapas.one',
  timeout: 8000,
});

// ── Basic query ──────────────────────────────────────────────────
const response = await tapas.ask({
  query:   'How does quantum computing work?',
  lemMode: true,
});

if (response.mode === 'cache') {
  // Served from semantic cache — 0.001 Wh used
  console.log('Routing:',  response.routingMethod, '@', response.confidence.toFixed(2));
  console.log('Latency:',  response.responseTimeMs, 'ms');
  console.log('Saved:',    response.energyWhSaved.toFixed(3), 'Wh');
  (response.bullets ?? []).forEach(b => console.log('•', b));
} else {
  // Full LLM inference — 3.0 Wh used
  console.log('Answer:',   response.answer);
  console.log('Category:', response.category, '|', response.domain);
}
OptionTypeDefaultDescription
apiKeystringYour Tapas API key (required)
baseUrlstringhttps://tapas.oneOverride for self-hosted instances
timeoutnumber10000Request timeout in milliseconds

Fetch Helper

Prefer not to install a package? Copy this zero-dependency typed helper directly into your project. It uses the native fetch API and returns a fully typed TapasResponse.

tapas-fetch.ts
typescript
// Zero-dependency fetch helper (no SDK required)
async function askTapas(
  options: TapasAskOptions,
  baseUrl = 'https://tapas.one'
): Promise<TapasResponse> {
  const url = baseUrl + '/api/trpc/query.ask';
  const res = await fetch(url, {
    method:  'POST',
    headers: { 'Content-Type': 'application/json' },
    body:    JSON.stringify({ json: options }),
  });
  if (!res.ok) throw new Error('Tapas API error: ' + res.status);
  const data = await res.json();
  return data.result.data as TapasResponse;
}

Error Handling

The SDK exports typed error classes so you can handle rate limits, network failures, and API errors distinctly without string-matching error messages.

error-handling.ts
typescript
import { TapasError, TapasRateLimitError, TapasNetworkError } from '@tapas-ai/sdk';

try {
  const response = await tapas.ask({ query: 'What is inflation?', lemMode: true });
  console.log(response.bullets);
} catch (err) {
  if (err instanceof TapasRateLimitError) {
    // HTTP 429 — back off and retry
    console.warn('Rate limited. Retry after:', err.retryAfter, 'ms');
  } else if (err instanceof TapasNetworkError) {
    // Network timeout or DNS failure
    console.error('Network error:', err.message);
  } else if (err instanceof TapasError) {
    // All other Tapas API errors
    console.error('Tapas error', err.statusCode, err.message);
  } else {
    throw err; // Re-throw unknown errors
  }
}

React Hook

A drop-in useTapas() hook for React applications. Manages loading, error, and response state — copy it directly into your hooks/ directory.

hooks/useTapas.ts
typescript
// hooks/useTapas.ts
import { useState, useCallback } from 'react';
import type { TapasResponse, TapasAskOptions } from '@tapas-ai/sdk';

interface UseTapasState {
  data:     TapasResponse | null;
  loading:  boolean;
  error:    string | null;
}

export function useTapas() {
  const [state, setState] = useState<UseTapasState>({
    data: null, loading: false, error: null,
  });

  const ask = useCallback(async (options: TapasAskOptions) => {
    setState(s => ({ ...s, loading: true, error: null }));
    try {
      const res = await fetch('/api/trpc/query.ask', {
        method:  'POST',
        headers: { 'Content-Type': 'application/json' },
        body:    JSON.stringify({ json: options }),
      });
      const json = await res.json();
      setState({ data: json.result.data, loading: false, error: null });
    } catch (e) {
      setState(s => ({ ...s, loading: false, error: String(e) }));
    }
  }, []);

  return { ...state, ask };
}

// ── Usage in a component ─────────────────────────────────────────
export function AskBox() {
  const { data, loading, error, ask } = useTapas();

  return (
    <div>
      <button
        onClick={() => ask({ query: 'What is inflation?', lemMode: true })}
        disabled={loading}
      >
        {loading ? 'Asking…' : 'Ask Tapas'}
      </button>

      {error && <p className="text-red-500">{error}</p>}

      {data?.mode === 'cache' && (
        <ul>
          {(data.bullets ?? []).map((b, i) => <li key={i}>• {b}</li>)}
        </ul>
      )}

      {data?.mode === 'llm' && <p>{data.answer}</p>}
    </div>
  );
}

Batch Queries

Use Promise.all to fire multiple queries concurrently. Each query is independently cached — batch requests multiply your energy savings.

batch-example.ts
typescript
// Process multiple queries concurrently
const queries = [
  'What is inflation?',
  'How does CRISPR work?',
  'Explain index funds',
];

const results = await Promise.all(
  queries.map(query => tapas.ask({ query, lemMode: true }))
);

const totalSaved = results.reduce((sum, r) => sum + r.energyWhSaved, 0);
console.log(`Batch: ${results.length} queries, ${totalSaved.toFixed(3)} Wh saved`);
results.forEach((r, i) => {
  console.log(`[${i + 1}] ${r.mode === 'cache' ? '⚡ cache' : '🤖 llm'} — ${r.category}`);
});

Ready to integrate?

Try the live chat interface or explore all 160 knowledge categories.