@teez-sdk/teez-b2c-api
v4.0.0
Published
TypeScript SDK for Teez B2C API
Readme
@teez-sdk/teez-b2c-api
Typed SDK for the Teez B2C API built around operation definitions, valibot schemas, runtime validation, and an operation catalog that can be reused for SDK, MCP, and documentation generation.
Use createTeezClient() for the full client, or createTeezClientFromOperations(...) to assemble a smaller client from selected operation groups for better tree-shaking.
Installation
npm install @teez-sdk/teez-b2c-apiRuntime requirements:
- Node.js 20.9+ when relying on the built-in global
fetch - or any runtime where
fetch,Request,Response, andHeadersare available - or a custom
fetchimplementation passed viacreateTeezClient({ fetch })
Quick Start
import { createTeezClient } from "@teez-sdk/teez-b2c-api";
const client = createTeezClient({
language: "kz",
timeout: 5_000,
});
const featureFlags = await client.featureFlags.list();
const suggestions = await client.products.autocomplete({
search: "sam",
});
const searchResults = await client.products.list({
query: suggestions[0]?.name ?? "samsung",
pageNumber: 1,
pageSize: 10,
});Operations without an input section can be called without arguments:
await client.categories.list();
await client.promo.list();
await client.featureFlags.list();Operations with input schemas always require an object, even when all fields are optional:
await client.products.getSortOptions({});
await client.banners.list({});Operations whose successful response uses emptyResponse() resolve with undefined:
await client.auth.login({
phone: "+77071234567",
});
await client.favorites.add.request({
body: [12345],
});Auth Flow
Use auth.login to send the OTP code, auth.verify to exchange it for tokens, then create an authenticated client with the returned accessToken:
import { createTeezClient } from "@teez-sdk/teez-b2c-api";
const publicClient = createTeezClient();
await publicClient.auth.login({
phone: "+77071234567",
});
const { accessToken, refreshToken } = await publicClient.auth.verify({
phone: "+77071234567",
otpCode: "1234",
});
const authClient = createTeezClient({
token: accessToken,
});
const profile = await authClient.auth.checkToken();refreshToken is returned by the API, but this SDK does not currently provide a refresh-token operation. Persist it only if your application uses it outside the SDK.
Client Shapes and Tree-Shaking
createTeezClient() gives you the complete SDK with every operation group attached.
Create the full client:
import { createTeezClient } from "@teez-sdk/teez-b2c-api";
const client = createTeezClient();If your application only needs part of the API, prefer createTeezClientFromOperations(...). It lets bundlers drop unused operation groups instead of pulling in the full operation catalog:
import {
authOperations,
createTeezClientFromOperations,
} from "@teez-sdk/teez-b2c-api";
const authClient = createTeezClientFromOperations({
auth: authOperations,
});
await authClient.auth.login({
phone: "+77071234567",
});This is the recommended entry point when bundle size matters, for example in browser apps that only use a few Teez domains.
Configuration
interface TeezClientConfig {
baseUrl?: string;
token?: string;
appVersion?: string;
language?: "ru" | "kz";
timeout?: number;
headers?: HeadersInit;
fetch?: typeof globalThis.fetch;
}Defaults:
baseUrl:https://b2c-api.teez.kzappVersion:"200"language:"ru"timeout:30_000
Notes:
tokenbecomes anAuthorization: Bearer ...header.appVersionis used for bothUser-AgentandX-App-Version.headersare merged on top of the SDK defaults.fetchdefaults toglobalThis.fetch; pass your own implementation when the runtime does not provide one.- Kazakh is standardized as
"kz"in request config and typed responses.
If you need the fully separated request shape instead of the flattened convenience call, use .request(...):
await client.products.list.request({
query: {
pageNumber: 1,
pageSize: 10,
},
});Runtime Validation
Every operation validates:
- input before the request is sent
- success payloads after the response is received
- error response bodies before they are attached to
TeezApiError.parsedBody
The package keeps its valibot schemas as internal validation details. Public type exports stay at the operation level:
import {
productsListOperation,
type ProductsListRequest,
type ProductsListRequestParts,
type ProductsListSuccessResponse,
} from "@teez-sdk/teez-b2c-api";FooRequest follows the preferred client call shape, so flattenable operations use the top-level object passed to client.foo.bar(...). FooRequestParts matches client.foo.bar.request(...).
Generated schema-derived model types are intentionally not part of the package contract. If an application needs its own domain models, define them locally.
Operation Catalog
The SDK exposes the grouped operation catalog, a flat list, and name lookup helpers:
import {
getTeezOperation,
teezOperationList,
teezOperations,
} from "@teez-sdk/teez-b2c-api";
const operation = getTeezOperation("products.list");
console.log(operation.auth);
console.log(operation.safety);
console.log(operation.summary);
console.log(operation.description);
console.log(teezOperationList.length);
console.log(teezOperations.products.list === operation);Operations are the main source of truth for:
- HTTP method and request mapping
- input and output schemas
- auth requirements
- read/write safety metadata
- MCP and doc-generation metadata
Error Handling
The SDK throws dedicated error classes:
TeezApiErrorfor non-2xx responsesTeezNetworkErrorfor transport failuresTeezTimeoutErrorfor aborted requests due to timeoutTeezValidationErrorfor input, output, or error-body schema mismatches
TeezApiError keeps transport metadata and may also include a typed parsedBody when the matching error response in responses defines a schema.
import {
getOperationApiError,
skuGetReviewAvailableOperation,
TeezApiError,
TeezTimeoutError,
} from "@teez-sdk/teez-b2c-api";
try {
await client.sku.getReviewAvailable({
skuId: 12345,
});
} catch (error) {
if (error instanceof TeezTimeoutError) {
console.error("Request timed out");
} else if (error instanceof TeezApiError) {
console.error(error.status, error.message);
const apiError = getOperationApiError(
error,
skuGetReviewAvailableOperation,
);
if (apiError != undefined) {
console.error(apiError.parsedBody.message);
}
}
}Auth Notes
Live probes without a token confirmed these operations require authentication:
auth.checkTokenfavorites.addfavorites.getIdsfavorites.removepromocodes.validatesku.getReviewAvailableusers.registerDeviceusers.updateLanguage
Public read-only operations such as banners.list, categories.*, collections.*, featureFlags.list, products.*, promo.list, shops.*, sku.get, sku.getCollections, and sku.getSimilar were successfully exercised without a token.
Package Exports
The package exports:
createTeezClient,createTeezClientFromOperations,createRuntimeteezOperations,teezOperationList,teezOperationsByName,getTeezOperation- operation definitions for every endpoint
- type aliases from
types.ts - shared contracts and filter schemas such as
apiErrorResponseSchema,filterSchema,rangeFilterSchema, andcategoryFilterSchema
Development
Run these commands from packages/teez-b2c-api. From the repository root, append -w @teez-sdk/teez-b2c-api.
npm run generate:types
npm run typecheck
npm run typecheck:test
npm run test
npm run lint
npm run test:coverage
npm run buildLicense
MIT
