Skip to content

Commit 9cc6c55

Browse files
chore: make some internal functions async
1 parent 5afe643 commit 9cc6c55

File tree

2 files changed

+32
-29
lines changed

2 files changed

+32
-29
lines changed

src/client.ts

Lines changed: 17 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -311,7 +311,7 @@ export class BaseAnthropic {
311311
* Create a new client instance re-using the same options given to the current client with optional overriding.
312312
*/
313313
withOptions(options: Partial<ClientOptions>): this {
314-
return new (this.constructor as any as new (props: ClientOptions) => typeof this)({
314+
const client = new (this.constructor as any as new (props: ClientOptions) => typeof this)({
315315
...this._options,
316316
baseURL: this.baseURL,
317317
maxRetries: this.maxRetries,
@@ -324,6 +324,7 @@ export class BaseAnthropic {
324324
authToken: this.authToken,
325325
...options,
326326
});
327+
return client;
327328
}
328329

329330
/**
@@ -357,18 +358,18 @@ export class BaseAnthropic {
357358
);
358359
}
359360

360-
protected authHeaders(opts: FinalRequestOptions): NullableHeaders | undefined {
361-
return buildHeaders([this.apiKeyAuth(opts), this.bearerAuth(opts)]);
361+
protected async authHeaders(opts: FinalRequestOptions): Promise<NullableHeaders | undefined> {
362+
return buildHeaders([await this.apiKeyAuth(opts), await this.bearerAuth(opts)]);
362363
}
363364

364-
protected apiKeyAuth(opts: FinalRequestOptions): NullableHeaders | undefined {
365+
protected async apiKeyAuth(opts: FinalRequestOptions): Promise<NullableHeaders | undefined> {
365366
if (this.apiKey == null) {
366367
return undefined;
367368
}
368369
return buildHeaders([{ 'X-Api-Key': this.apiKey }]);
369370
}
370371

371-
protected bearerAuth(opts: FinalRequestOptions): NullableHeaders | undefined {
372+
protected async bearerAuth(opts: FinalRequestOptions): Promise<NullableHeaders | undefined> {
372373
if (this.authToken == null) {
373374
return undefined;
374375
}
@@ -515,7 +516,9 @@ export class BaseAnthropic {
515516

516517
await this.prepareOptions(options);
517518

518-
const { req, url, timeout } = this.buildRequest(options, { retryCount: maxRetries - retriesRemaining });
519+
const { req, url, timeout } = await this.buildRequest(options, {
520+
retryCount: maxRetries - retriesRemaining,
521+
});
519522

520523
await this.prepareRequest(req, { url, options });
521524

@@ -597,7 +600,7 @@ export class BaseAnthropic {
597600
} with status ${response.status} in ${headersTime - startTime}ms`;
598601

599602
if (!response.ok) {
600-
const shouldRetry = this.shouldRetry(response);
603+
const shouldRetry = await this.shouldRetry(response);
601604
if (retriesRemaining && shouldRetry) {
602605
const retryMessage = `retrying, ${retriesRemaining} attempts remaining`;
603606

@@ -715,7 +718,7 @@ export class BaseAnthropic {
715718
}
716719
}
717720

718-
private shouldRetry(response: Response): boolean {
721+
private async shouldRetry(response: Response): Promise<boolean> {
719722
// Note this is not a standard header.
720723
const shouldRetryHeader = response.headers.get('x-should-retry');
721724

@@ -806,18 +809,18 @@ export class BaseAnthropic {
806809
return defaultTime;
807810
}
808811

809-
buildRequest(
812+
async buildRequest(
810813
inputOptions: FinalRequestOptions,
811814
{ retryCount = 0 }: { retryCount?: number } = {},
812-
): { req: FinalizedRequestInit; url: string; timeout: number } {
815+
): Promise<{ req: FinalizedRequestInit; url: string; timeout: number }> {
813816
const options = { ...inputOptions };
814817
const { method, path, query, defaultBaseURL } = options;
815818

816819
const url = this.buildURL(path!, query as Record<string, unknown>, defaultBaseURL);
817820
if ('timeout' in options) validatePositiveInteger('timeout', options.timeout);
818821
options.timeout = options.timeout ?? this.timeout;
819822
const { bodyHeaders, body } = this.buildBody({ options });
820-
const reqHeaders = this.buildHeaders({ options: inputOptions, method, bodyHeaders, retryCount });
823+
const reqHeaders = await this.buildHeaders({ options: inputOptions, method, bodyHeaders, retryCount });
821824

822825
const req: FinalizedRequestInit = {
823826
method,
@@ -833,7 +836,7 @@ export class BaseAnthropic {
833836
return { req, url, timeout: options.timeout };
834837
}
835838

836-
private buildHeaders({
839+
private async buildHeaders({
837840
options,
838841
method,
839842
bodyHeaders,
@@ -843,7 +846,7 @@ export class BaseAnthropic {
843846
method: HTTPMethod;
844847
bodyHeaders: HeadersLike;
845848
retryCount: number;
846-
}): Headers {
849+
}): Promise<Headers> {
847850
let idempotencyHeaders: HeadersLike = {};
848851
if (this.idempotencyHeader && method !== 'get') {
849852
if (!options.idempotencyKey) options.idempotencyKey = this.defaultIdempotencyKey();
@@ -863,7 +866,7 @@ export class BaseAnthropic {
863866
: undefined),
864867
'anthropic-version': '2023-06-01',
865868
},
866-
this.authHeaders(options),
869+
await this.authHeaders(options),
867870
this._options.defaultHeaders,
868871
bodyHeaders,
869872
options.headers,

tests/index.test.ts

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -26,22 +26,22 @@ describe('instantiate client', () => {
2626
apiKey: 'my-anthropic-api-key',
2727
});
2828

29-
test('they are used in the request', () => {
30-
const { req } = client.buildRequest({ path: '/foo', method: 'post' });
29+
test('they are used in the request', async () => {
30+
const { req } = await client.buildRequest({ path: '/foo', method: 'post' });
3131
expect(req.headers.get('x-my-default-header')).toEqual('2');
3232
});
3333

34-
test('can ignore `undefined` and leave the default', () => {
35-
const { req } = client.buildRequest({
34+
test('can ignore `undefined` and leave the default', async () => {
35+
const { req } = await client.buildRequest({
3636
path: '/foo',
3737
method: 'post',
3838
headers: { 'X-My-Default-Header': undefined },
3939
});
4040
expect(req.headers.get('x-my-default-header')).toEqual('2');
4141
});
4242

43-
test('can be removed with `null`', () => {
44-
const { req } = client.buildRequest({
43+
test('can be removed with `null`', async () => {
44+
const { req } = await client.buildRequest({
4545
path: '/foo',
4646
method: 'post',
4747
headers: { 'X-My-Default-Header': null },
@@ -357,7 +357,7 @@ describe('instantiate client', () => {
357357
});
358358

359359
describe('withOptions', () => {
360-
test('creates a new client with overridden options', () => {
360+
test('creates a new client with overridden options', async () => {
361361
const client = new Anthropic({
362362
baseURL: 'http://localhost:5000/',
363363
maxRetries: 3,
@@ -382,7 +382,7 @@ describe('instantiate client', () => {
382382
expect(newClient.constructor).toBe(client.constructor);
383383
});
384384

385-
test('inherits options from the parent client', () => {
385+
test('inherits options from the parent client', async () => {
386386
const client = new Anthropic({
387387
baseURL: 'http://localhost:5000/',
388388
defaultHeaders: { 'X-Test-Header': 'test-value' },
@@ -397,7 +397,7 @@ describe('instantiate client', () => {
397397
// Test inherited options remain the same
398398
expect(newClient.buildURL('/foo', null)).toEqual('http://localhost:5001/foo?test-param=test-value');
399399

400-
const { req } = newClient.buildRequest({ path: '/foo', method: 'get' });
400+
const { req } = await newClient.buildRequest({ path: '/foo', method: 'get' });
401401
expect(req.headers.get('x-test-header')).toEqual('test-value');
402402
});
403403

@@ -451,8 +451,8 @@ describe('request building', () => {
451451
const client = new Anthropic({ apiKey: 'my-anthropic-api-key' });
452452

453453
describe('custom headers', () => {
454-
test('handles undefined', () => {
455-
const { req } = client.buildRequest({
454+
test('handles undefined', async () => {
455+
const { req } = await client.buildRequest({
456456
path: '/foo',
457457
method: 'post',
458458
body: { value: 'hello' },
@@ -487,8 +487,8 @@ describe('default encoder', () => {
487487
}
488488
}
489489
for (const jsonValue of [{}, [], { __proto__: null }, new Serializable(), new Collection(['item'])]) {
490-
test(`serializes ${util.inspect(jsonValue)} as json`, () => {
491-
const { req } = client.buildRequest({
490+
test(`serializes ${util.inspect(jsonValue)} as json`, async () => {
491+
const { req } = await client.buildRequest({
492492
path: '/foo',
493493
method: 'post',
494494
body: jsonValue,
@@ -511,7 +511,7 @@ describe('default encoder', () => {
511511
asyncIterable,
512512
]) {
513513
test(`converts ${util.inspect(streamValue)} to ReadableStream`, async () => {
514-
const { req } = client.buildRequest({
514+
const { req } = await client.buildRequest({
515515
path: '/foo',
516516
method: 'post',
517517
body: streamValue,
@@ -524,7 +524,7 @@ describe('default encoder', () => {
524524
}
525525

526526
test(`can set content-type for ReadableStream`, async () => {
527-
const { req } = client.buildRequest({
527+
const { req } = await client.buildRequest({
528528
path: '/foo',
529529
method: 'post',
530530
body: new Response('a\nb\nc\n').body,

0 commit comments

Comments
 (0)