From 92210b2f9cbfd930dfb7fcc8c6464a8d0c89bda7 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 02:35:00 +0000 Subject: [PATCH 01/14] chore(docs): grammar improvements --- SECURITY.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/SECURITY.md b/SECURITY.md index 92a473f..97e18f0 100644 --- a/SECURITY.md +++ b/SECURITY.md @@ -16,11 +16,11 @@ before making any information public. ## Reporting Non-SDK Related Security Issues If you encounter security issues that are not directly related to SDKs but pertain to the services -or products provided by Contextual AI please follow the respective company's security reporting guidelines. +or products provided by Contextual AI, please follow the respective company's security reporting guidelines. ### Contextual AI Terms and Policies -Please contact support@contextual.ai for any questions or concerns regarding security of our services. +Please contact support@contextual.ai for any questions or concerns regarding the security of our services. --- From bf8c320845e3781558b5c89c2d0dfda127138d13 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Wed, 28 May 2025 03:43:34 +0000 Subject: [PATCH 02/14] chore: improve publish-npm script --latest tag logic --- bin/publish-npm | 30 +++++++++++++++++++++++------- 1 file changed, 23 insertions(+), 7 deletions(-) diff --git a/bin/publish-npm b/bin/publish-npm index 4c21181..2505dec 100644 --- a/bin/publish-npm +++ b/bin/publish-npm @@ -4,19 +4,35 @@ set -eux npm config set '//registry.npmjs.org/:_authToken' "$NPM_TOKEN" -# Build the project yarn build - -# Navigate to the dist directory cd dist -# Get the version from package.json +# Get latest version from npm +# +# If the package doesn't exist, yarn will return +# {"type":"error","data":"Received invalid response from npm."} +# where .data.version doesn't exist so LAST_VERSION will be an empty string. +LAST_VERSION="$(yarn info --json 2> /dev/null | jq -r '.data.version')" + +# Get current version from package.json VERSION="$(node -p "require('./package.json').version")" -# Extract the pre-release tag if it exists +# Check if current version is pre-release (e.g. alpha / beta / rc) +CURRENT_IS_PRERELEASE=false if [[ "$VERSION" =~ -([a-zA-Z]+) ]]; then - # Extract the part before any dot in the pre-release identifier - TAG="${BASH_REMATCH[1]}" + CURRENT_IS_PRERELEASE=true + CURRENT_TAG="${BASH_REMATCH[1]}" +fi + +# Check if last version is a stable release +LAST_IS_STABLE_RELEASE=true +if [[ -z "$LAST_VERSION" || "$LAST_VERSION" =~ -([a-zA-Z]+) ]]; then + LAST_IS_STABLE_RELEASE=false +fi + +# Use a corresponding alpha/beta tag if there already is a stable release and we're publishing a prerelease. +if $CURRENT_IS_PRERELEASE && $LAST_IS_STABLE_RELEASE; then + TAG="$CURRENT_TAG" else TAG="latest" fi From 39783f455c8d9d669d42a0671b239b51a196f743 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Wed, 4 Jun 2025 03:57:59 +0000 Subject: [PATCH 03/14] chore(docs): use top-level-await in example snippets --- README.md | 38 +++++++++++++------------------------- 1 file changed, 13 insertions(+), 25 deletions(-) diff --git a/README.md b/README.md index db698e4..4d38e40 100644 --- a/README.md +++ b/README.md @@ -24,13 +24,9 @@ const client = new ContextualAI({ apiKey: process.env['CONTEXTUAL_API_KEY'], // This is the default and can be omitted }); -async function main() { - const createAgentOutput = await client.agents.create({ name: 'Example' }); +const createAgentOutput = await client.agents.create({ name: 'Example' }); - console.log(createAgentOutput.id); -} - -main(); +console.log(createAgentOutput.id); ``` ### Request & Response types @@ -45,12 +41,8 @@ const client = new ContextualAI({ apiKey: process.env['CONTEXTUAL_API_KEY'], // This is the default and can be omitted }); -async function main() { - const params: ContextualAI.AgentCreateParams = { name: 'Example' }; - const createAgentOutput: ContextualAI.CreateAgentOutput = await client.agents.create(params); -} - -main(); +const params: ContextualAI.AgentCreateParams = { name: 'Example' }; +const createAgentOutput: ContextualAI.CreateAgentOutput = await client.agents.create(params); ``` Documentation for each method, request param, and response field are available in docstrings and will appear on hover in most modern editors. @@ -103,19 +95,15 @@ a subclass of `APIError` will be thrown: ```ts -async function main() { - const createAgentOutput = await client.agents.create({ name: 'Example' }).catch(async (err) => { - if (err instanceof ContextualAI.APIError) { - console.log(err.status); // 400 - console.log(err.name); // BadRequestError - console.log(err.headers); // {server: 'nginx', ...} - } else { - throw err; - } - }); -} - -main(); +const createAgentOutput = await client.agents.create({ name: 'Example' }).catch(async (err) => { + if (err instanceof ContextualAI.APIError) { + console.log(err.status); // 400 + console.log(err.name); // BadRequestError + console.log(err.headers); // {server: 'nginx', ...} + } else { + throw err; + } +}); ``` Error codes are as follows: From 9855ea41c55355a17d1a6282bc8d158b72da2f63 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Sat, 14 Jun 2025 02:27:54 +0000 Subject: [PATCH 04/14] =?UTF-8?q?fix:=20publish=20script=20=E2=80=94=20han?= =?UTF-8?q?dle=20NPM=20errors=20correctly?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bin/publish-npm | 34 +++++++++++++++++++++++++++------- 1 file changed, 27 insertions(+), 7 deletions(-) diff --git a/bin/publish-npm b/bin/publish-npm index 2505dec..fa2243d 100644 --- a/bin/publish-npm +++ b/bin/publish-npm @@ -7,15 +7,35 @@ npm config set '//registry.npmjs.org/:_authToken' "$NPM_TOKEN" yarn build cd dist +# Get package name and version from package.json +PACKAGE_NAME="$(jq -r -e '.name' ./package.json)" +VERSION="$(jq -r -e '.version' ./package.json)" + # Get latest version from npm # -# If the package doesn't exist, yarn will return -# {"type":"error","data":"Received invalid response from npm."} -# where .data.version doesn't exist so LAST_VERSION will be an empty string. -LAST_VERSION="$(yarn info --json 2> /dev/null | jq -r '.data.version')" - -# Get current version from package.json -VERSION="$(node -p "require('./package.json').version")" +# If the package doesn't exist, npm will return: +# { +# "error": { +# "code": "E404", +# "summary": "Unpublished on 2025-06-05T09:54:53.528Z", +# "detail": "'the_package' is not in this registry..." +# } +# } +NPM_INFO="$(npm view "$PACKAGE_NAME" version --json 2>/dev/null || true)" + +# Check if we got an E404 error +if echo "$NPM_INFO" | jq -e '.error.code == "E404"' > /dev/null 2>&1; then + # Package doesn't exist yet, no last version + LAST_VERSION="" +elif echo "$NPM_INFO" | jq -e '.error' > /dev/null 2>&1; then + # Report other errors + echo "ERROR: npm returned unexpected data:" + echo "$NPM_INFO" + exit 1 +else + # Success - get the version + LAST_VERSION=$(echo "$NPM_INFO" | jq -r '.') # strip quotes +fi # Check if current version is pre-release (e.g. alpha / beta / rc) CURRENT_IS_PRERELEASE=false From 122895d96bcc6de97dc918dca7b62d8ababb0af5 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Sat, 14 Jun 2025 02:41:49 +0000 Subject: [PATCH 05/14] chore(internal): make base APIResource abstract --- scripts/build | 2 +- src/resource.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/scripts/build b/scripts/build index d4a6875..dba69bb 100755 --- a/scripts/build +++ b/scripts/build @@ -28,7 +28,7 @@ fi node scripts/utils/make-dist-package-json.cjs > dist/package.json # build to .js/.mjs/.d.ts files -npm exec tsc-multi +./node_modules/.bin/tsc-multi # copy over handwritten .js/.mjs/.d.ts files cp src/_shims/*.{d.ts,js,mjs,md} dist/_shims cp src/_shims/auto/*.{d.ts,js,mjs} dist/_shims/auto diff --git a/src/resource.ts b/src/resource.ts index 7f9b100..adf0750 100644 --- a/src/resource.ts +++ b/src/resource.ts @@ -2,7 +2,7 @@ import type { ContextualAI } from './index'; -export class APIResource { +export abstract class APIResource { protected _client: ContextualAI; constructor(client: ContextualAI) { From 4375198ddd324eadac0053fbf0e9284f0686f6a5 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Tue, 17 Jun 2025 04:01:32 +0000 Subject: [PATCH 06/14] feat(client): add support for endpoint-specific base URLs --- src/core.ts | 15 +++++++++++---- src/index.ts | 8 ++++++++ tests/index.test.ts | 22 ++++++++++++++++++++++ 3 files changed, 41 insertions(+), 4 deletions(-) diff --git a/src/core.ts b/src/core.ts index 57e9e88..8c08fb6 100644 --- a/src/core.ts +++ b/src/core.ts @@ -170,6 +170,7 @@ export class APIPromise extends Promise { export abstract class APIClient { baseURL: string; + #baseURLOverridden: boolean; maxRetries: number; timeout: number; httpAgent: Agent | undefined; @@ -179,18 +180,21 @@ export abstract class APIClient { constructor({ baseURL, + baseURLOverridden, maxRetries = 2, timeout = 60000, // 1 minute httpAgent, fetch: overriddenFetch, }: { baseURL: string; + baseURLOverridden: boolean; maxRetries?: number | undefined; timeout: number | undefined; httpAgent: Agent | undefined; fetch: Fetch | undefined; }) { this.baseURL = baseURL; + this.#baseURLOverridden = baseURLOverridden; this.maxRetries = validatePositiveInteger('maxRetries', maxRetries); this.timeout = validatePositiveInteger('timeout', timeout); this.httpAgent = httpAgent; @@ -300,7 +304,7 @@ export abstract class APIClient { { retryCount = 0 }: { retryCount?: number } = {}, ): { req: RequestInit; url: string; timeout: number } { const options = { ...inputOptions }; - const { method, path, query, headers: headers = {} } = options; + const { method, path, query, defaultBaseURL, headers: headers = {} } = options; const body = ArrayBuffer.isView(options.body) || (options.__binaryRequest && typeof options.body === 'string') ? @@ -310,7 +314,7 @@ export abstract class APIClient { : null; const contentLength = this.calculateContentLength(body); - const url = this.buildURL(path!, query); + const url = this.buildURL(path!, query, defaultBaseURL); if ('timeout' in options) validatePositiveInteger('timeout', options.timeout); options.timeout = options.timeout ?? this.timeout; const httpAgent = options.httpAgent ?? this.httpAgent ?? getDefaultAgent(url); @@ -503,11 +507,12 @@ export abstract class APIClient { return new PagePromise(this, request, Page); } - buildURL(path: string, query: Req | null | undefined): string { + buildURL(path: string, query: Req | null | undefined, defaultBaseURL?: string | undefined): string { + const baseURL = (!this.#baseURLOverridden && defaultBaseURL) || this.baseURL; const url = isAbsoluteURL(path) ? new URL(path) - : new URL(this.baseURL + (this.baseURL.endsWith('/') && path.startsWith('/') ? path.slice(1) : path)); + : new URL(baseURL + (baseURL.endsWith('/') && path.startsWith('/') ? path.slice(1) : path)); const defaultQuery = this.defaultQuery(); if (!isEmptyObj(defaultQuery)) { @@ -792,6 +797,7 @@ export type RequestOptions< query?: Req | undefined; body?: Req | null | undefined; headers?: Headers | undefined; + defaultBaseURL?: string | undefined; maxRetries?: number; stream?: boolean | undefined; @@ -813,6 +819,7 @@ const requestOptionsKeys: KeysEnum = { query: true, body: true, headers: true, + defaultBaseURL: true, maxRetries: true, stream: true, diff --git a/src/index.ts b/src/index.ts index f17be44..b476f78 100644 --- a/src/index.ts +++ b/src/index.ts @@ -178,6 +178,7 @@ export class ContextualAI extends Core.APIClient { super({ baseURL: options.baseURL!, + baseURLOverridden: baseURL ? baseURL !== 'https://api.contextual.ai/v1' : false, timeout: options.timeout ?? 60000 /* 1 minute */, httpAgent: options.httpAgent, maxRetries: options.maxRetries, @@ -197,6 +198,13 @@ export class ContextualAI extends Core.APIClient { generate: API.Generate = new API.Generate(this); parse: API.Parse = new API.Parse(this); + /** + * Check whether the base URL is set to its default. + */ + #baseURLOverridden(): boolean { + return this.baseURL !== 'https://api.contextual.ai/v1'; + } + protected override defaultQuery(): Core.DefaultQuery | undefined { return this._options.defaultQuery; } diff --git a/tests/index.test.ts b/tests/index.test.ts index 90855ce..3266e41 100644 --- a/tests/index.test.ts +++ b/tests/index.test.ts @@ -188,6 +188,28 @@ describe('instantiate client', () => { const client = new ContextualAI({ apiKey: 'My API Key' }); expect(client.baseURL).toEqual('https://api.contextual.ai/v1'); }); + + test('in request options', () => { + const client = new ContextualAI({ apiKey: 'My API Key' }); + expect(client.buildURL('/foo', null, 'http://localhost:5000/option')).toEqual( + 'http://localhost:5000/option/foo', + ); + }); + + test('in request options overridden by client options', () => { + const client = new ContextualAI({ apiKey: 'My API Key', baseURL: 'http://localhost:5000/client' }); + expect(client.buildURL('/foo', null, 'http://localhost:5000/option')).toEqual( + 'http://localhost:5000/client/foo', + ); + }); + + test('in request options overridden by env variable', () => { + process.env['CONTEXTUAL_AI_BASE_URL'] = 'http://localhost:5000/env'; + const client = new ContextualAI({ apiKey: 'My API Key' }); + expect(client.buildURL('/foo', null, 'http://localhost:5000/option')).toEqual( + 'http://localhost:5000/env/foo', + ); + }); }); test('maxRetries option is correctly set', () => { From 23d5fa79636f991e3d4ff7a454ee973bb1fc2691 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Tue, 17 Jun 2025 06:46:58 +0000 Subject: [PATCH 07/14] chore(ci): enable for pull requests --- .github/workflows/ci.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index af03700..ac025bc 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -7,6 +7,10 @@ on: - 'integrated/**' - 'stl-preview-head/**' - 'stl-preview-base/**' + pull_request: + branches-ignore: + - 'stl-preview-head/**' + - 'stl-preview-base/**' jobs: lint: From b50e9f1b6306889aff9ee34fb2d29dcad6d8c3f7 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Tue, 24 Jun 2025 04:41:57 +0000 Subject: [PATCH 08/14] refactor(types): replace Record with mapped types --- src/resources/datastores/documents.ts | 4 ++-- src/resources/users.ts | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/resources/datastores/documents.ts b/src/resources/datastores/documents.ts index f1c7b2a..b99fc48 100644 --- a/src/resources/datastores/documents.ts +++ b/src/resources/datastores/documents.ts @@ -181,7 +181,7 @@ export interface DocumentMetadata { */ status: 'pending' | 'processing' | 'retrying' | 'completed' | 'failed' | 'cancelled'; - custom_metadata?: Record; + custom_metadata?: { [key: string]: boolean | number | string }; /** * Timestamp of when the document was modified in ISO format. @@ -282,7 +282,7 @@ export interface DocumentIngestParams { } export interface DocumentSetMetadataParams { - custom_metadata?: Record; + custom_metadata?: { [key: string]: boolean | number | string }; } Documents.DocumentMetadataDocumentsPage = DocumentMetadataDocumentsPage; diff --git a/src/resources/users.ts b/src/resources/users.ts index 8339bf6..3edbb31 100644 --- a/src/resources/users.ts +++ b/src/resources/users.ts @@ -59,7 +59,7 @@ export interface InviteUsersResponse { * Details of the errors occurred while inviting users, where keys are the emails * and values are the error messages */ - error_details: Record; + error_details: { [key: string]: string }; /** * List of emails of the invited users From 2339044a28b8491311eb984fbe0f5b2497e57b32 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Fri, 27 Jun 2025 02:37:18 +0000 Subject: [PATCH 09/14] =?UTF-8?q?fix(ci):=20release-doctor=20=E2=80=94=20r?= =?UTF-8?q?eport=20correct=20token=20name?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bin/check-release-environment | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bin/check-release-environment b/bin/check-release-environment index c2bca0c..e4b6d58 100644 --- a/bin/check-release-environment +++ b/bin/check-release-environment @@ -3,7 +3,7 @@ errors=() if [ -z "${NPM_TOKEN}" ]; then - errors+=("The CONTEXTUAL_AI_NPM_TOKEN secret has not been set. Please set it in either this repository's secrets or your organization secrets") + errors+=("The NPM_TOKEN secret has not been set. Please set it in either this repository's secrets or your organization secrets") fi lenErrors=${#errors[@]} From da8f41a626313a61f8eec1ccb52834021ec5c134 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Sat, 28 Jun 2025 08:36:18 +0000 Subject: [PATCH 10/14] chore(ci): only run for pushes and fork pull requests --- .github/workflows/ci.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index ac025bc..873463c 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -17,6 +17,7 @@ jobs: timeout-minutes: 10 name: lint runs-on: ${{ github.repository == 'stainless-sdks/sunrise-node' && 'depot-ubuntu-24.04' || 'ubuntu-latest' }} + if: github.event_name == 'push' || github.event.pull_request.head.repo.fork steps: - uses: actions/checkout@v4 @@ -35,6 +36,7 @@ jobs: timeout-minutes: 5 name: build runs-on: ${{ github.repository == 'stainless-sdks/sunrise-node' && 'depot-ubuntu-24.04' || 'ubuntu-latest' }} + if: github.event_name == 'push' || github.event.pull_request.head.repo.fork permissions: contents: read id-token: write @@ -70,6 +72,7 @@ jobs: timeout-minutes: 10 name: test runs-on: ${{ github.repository == 'stainless-sdks/sunrise-node' && 'depot-ubuntu-24.04' || 'ubuntu-latest' }} + if: github.event_name == 'push' || github.event.pull_request.head.repo.fork steps: - uses: actions/checkout@v4 From 427168601652284f4f664680cd66302d4ac5485a Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 3 Jul 2025 04:10:46 +0000 Subject: [PATCH 11/14] chore: mention unit type in timeout docs --- src/index.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/index.ts b/src/index.ts index b476f78..5392a01 100644 --- a/src/index.ts +++ b/src/index.ts @@ -95,6 +95,8 @@ export interface ClientOptions { * * Note that request timeouts are retried by default, so in a worst-case scenario you may wait * much longer than this timeout before the promise succeeds or fails. + * + * @unit milliseconds */ timeout?: number | undefined; From 70fe78dada5b43beb40a5efb9d371cdcb2ac8ea0 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 3 Jul 2025 05:03:16 +0000 Subject: [PATCH 12/14] fix(client): don't send `Content-Type` for bodyless methods --- src/core.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core.ts b/src/core.ts index 8c08fb6..6a7521d 100644 --- a/src/core.ts +++ b/src/core.ts @@ -217,7 +217,7 @@ export abstract class APIClient { protected defaultHeaders(opts: FinalRequestOptions): Headers { return { Accept: 'application/json', - 'Content-Type': 'application/json', + ...(['head', 'get'].includes(opts.method) ? {} : { 'Content-Type': 'application/json' }), 'User-Agent': this.getUserAgent(), ...getPlatformHeaders(), ...this.authHeaders(opts), From cfbf5bc81cb65347306a63f6901c0682f2a827cf Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 10 Jul 2025 04:42:54 +0000 Subject: [PATCH 13/14] chore: make some internal functions async --- src/core.ts | 8 +++++--- tests/index.test.ts | 24 ++++++++++++------------ 2 files changed, 17 insertions(+), 15 deletions(-) diff --git a/src/core.ts b/src/core.ts index 6a7521d..0824fa9 100644 --- a/src/core.ts +++ b/src/core.ts @@ -299,10 +299,10 @@ export abstract class APIClient { return null; } - buildRequest( + async buildRequest( inputOptions: FinalRequestOptions, { retryCount = 0 }: { retryCount?: number } = {}, - ): { req: RequestInit; url: string; timeout: number } { + ): Promise<{ req: RequestInit; url: string; timeout: number }> { const options = { ...inputOptions }; const { method, path, query, defaultBaseURL, headers: headers = {} } = options; @@ -450,7 +450,9 @@ export abstract class APIClient { await this.prepareOptions(options); - const { req, url, timeout } = this.buildRequest(options, { retryCount: maxRetries - retriesRemaining }); + const { req, url, timeout } = await this.buildRequest(options, { + retryCount: maxRetries - retriesRemaining, + }); await this.prepareRequest(req, { url, options }); diff --git a/tests/index.test.ts b/tests/index.test.ts index 3266e41..1c96dbd 100644 --- a/tests/index.test.ts +++ b/tests/index.test.ts @@ -26,13 +26,13 @@ describe('instantiate client', () => { apiKey: 'My API Key', }); - test('they are used in the request', () => { - const { req } = client.buildRequest({ path: '/foo', method: 'post' }); + test('they are used in the request', async () => { + const { req } = await client.buildRequest({ path: '/foo', method: 'post' }); expect((req.headers as Headers)['x-my-default-header']).toEqual('2'); }); - test('can ignore `undefined` and leave the default', () => { - const { req } = client.buildRequest({ + test('can ignore `undefined` and leave the default', async () => { + const { req } = await client.buildRequest({ path: '/foo', method: 'post', headers: { 'X-My-Default-Header': undefined }, @@ -40,8 +40,8 @@ describe('instantiate client', () => { expect((req.headers as Headers)['x-my-default-header']).toEqual('2'); }); - test('can be removed with `null`', () => { - const { req } = client.buildRequest({ + test('can be removed with `null`', async () => { + const { req } = await client.buildRequest({ path: '/foo', method: 'post', headers: { 'X-My-Default-Header': null }, @@ -240,20 +240,20 @@ describe('request building', () => { const client = new ContextualAI({ apiKey: 'My API Key' }); describe('Content-Length', () => { - test('handles multi-byte characters', () => { - const { req } = client.buildRequest({ path: '/foo', method: 'post', body: { value: '—' } }); + test('handles multi-byte characters', async () => { + const { req } = await client.buildRequest({ path: '/foo', method: 'post', body: { value: '—' } }); expect((req.headers as Record)['content-length']).toEqual('20'); }); - test('handles standard characters', () => { - const { req } = client.buildRequest({ path: '/foo', method: 'post', body: { value: 'hello' } }); + test('handles standard characters', async () => { + const { req } = await client.buildRequest({ path: '/foo', method: 'post', body: { value: 'hello' } }); expect((req.headers as Record)['content-length']).toEqual('22'); }); }); describe('custom headers', () => { - test('handles undefined', () => { - const { req } = client.buildRequest({ + test('handles undefined', async () => { + const { req } = await client.buildRequest({ path: '/foo', method: 'post', body: { value: 'hello' }, From 6f3e85f2f9ba09e3097adfe5cece47b4070842a7 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 10 Jul 2025 04:43:11 +0000 Subject: [PATCH 14/14] release: 0.8.0 --- .release-please-manifest.json | 2 +- CHANGELOG.md | 32 ++++++++++++++++++++++++++++++++ package.json | 2 +- src/version.ts | 2 +- 4 files changed, 35 insertions(+), 3 deletions(-) diff --git a/.release-please-manifest.json b/.release-please-manifest.json index e7ca613..64f3cdd 100644 --- a/.release-please-manifest.json +++ b/.release-please-manifest.json @@ -1,3 +1,3 @@ { - ".": "0.7.0" + ".": "0.8.0" } diff --git a/CHANGELOG.md b/CHANGELOG.md index 8a3c2da..631ecf9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,37 @@ # Changelog +## 0.8.0 (2025-07-10) + +Full Changelog: [v0.7.0...v0.8.0](https://github.com/ContextualAI/contextual-client-node/compare/v0.7.0...v0.8.0) + +### Features + +* **client:** add support for endpoint-specific base URLs ([4375198](https://github.com/ContextualAI/contextual-client-node/commit/4375198ddd324eadac0053fbf0e9284f0686f6a5)) + + +### Bug Fixes + +* **ci:** release-doctor — report correct token name ([2339044](https://github.com/ContextualAI/contextual-client-node/commit/2339044a28b8491311eb984fbe0f5b2497e57b32)) +* **client:** don't send `Content-Type` for bodyless methods ([70fe78d](https://github.com/ContextualAI/contextual-client-node/commit/70fe78dada5b43beb40a5efb9d371cdcb2ac8ea0)) +* publish script — handle NPM errors correctly ([9855ea4](https://github.com/ContextualAI/contextual-client-node/commit/9855ea41c55355a17d1a6282bc8d158b72da2f63)) + + +### Chores + +* **ci:** enable for pull requests ([23d5fa7](https://github.com/ContextualAI/contextual-client-node/commit/23d5fa79636f991e3d4ff7a454ee973bb1fc2691)) +* **ci:** only run for pushes and fork pull requests ([da8f41a](https://github.com/ContextualAI/contextual-client-node/commit/da8f41a626313a61f8eec1ccb52834021ec5c134)) +* **docs:** grammar improvements ([92210b2](https://github.com/ContextualAI/contextual-client-node/commit/92210b2f9cbfd930dfb7fcc8c6464a8d0c89bda7)) +* **docs:** use top-level-await in example snippets ([39783f4](https://github.com/ContextualAI/contextual-client-node/commit/39783f455c8d9d669d42a0671b239b51a196f743)) +* improve publish-npm script --latest tag logic ([bf8c320](https://github.com/ContextualAI/contextual-client-node/commit/bf8c320845e3781558b5c89c2d0dfda127138d13)) +* **internal:** make base APIResource abstract ([122895d](https://github.com/ContextualAI/contextual-client-node/commit/122895d96bcc6de97dc918dca7b62d8ababb0af5)) +* make some internal functions async ([cfbf5bc](https://github.com/ContextualAI/contextual-client-node/commit/cfbf5bc81cb65347306a63f6901c0682f2a827cf)) +* mention unit type in timeout docs ([4271686](https://github.com/ContextualAI/contextual-client-node/commit/427168601652284f4f664680cd66302d4ac5485a)) + + +### Refactors + +* **types:** replace Record with mapped types ([b50e9f1](https://github.com/ContextualAI/contextual-client-node/commit/b50e9f1b6306889aff9ee34fb2d29dcad6d8c3f7)) + ## 0.7.0 (2025-05-13) Full Changelog: [v0.6.0...v0.7.0](https://github.com/ContextualAI/contextual-client-node/compare/v0.6.0...v0.7.0) diff --git a/package.json b/package.json index 7837a69..ce28838 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "contextual-client", - "version": "0.7.0", + "version": "0.8.0", "description": "The official TypeScript library for the Contextual AI API", "author": "Contextual AI ", "types": "dist/index.d.ts", diff --git a/src/version.ts b/src/version.ts index d9da9f7..23f967c 100644 --- a/src/version.ts +++ b/src/version.ts @@ -1 +1 @@ -export const VERSION = '0.7.0'; // x-release-please-version +export const VERSION = '0.8.0'; // x-release-please-version