Skip to content

Commit

Permalink
Make route classes work stand alone
Browse files Browse the repository at this point in the history
  • Loading branch information
razor-x committed Sep 21, 2023
1 parent c2ad768 commit 2a9ad4a
Show file tree
Hide file tree
Showing 5 changed files with 76 additions and 54 deletions.
23 changes: 23 additions & 0 deletions src/lib/seam/connect/axios.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import axios, { type Axios } from 'axios'

import { getAuthHeaders } from './auth.js'
import {
isSeamHttpOptionsWithClientSessionToken,
type SeamHttpOptions,
} from './client-options.js'

export const createAxiosClient = (
options: Required<SeamHttpOptions>,
): Axios => {
// TODO: axiosRetry? Allow options to configure this if so
return axios.create({
baseURL: options.endpoint,
withCredentials: isSeamHttpOptionsWithClientSessionToken(options),
...options.axiosOptions,
headers: {
...getAuthHeaders(options),
...options.axiosOptions.headers,
// TODO: User-Agent
},
})
}
57 changes: 9 additions & 48 deletions src/lib/seam/connect/client.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import axios, { type Axios } from 'axios'
import type { Axios } from 'axios'

import { getAuthHeaders } from './auth.js'
import { createAxiosClient } from './axios.js'
import {
InvalidSeamHttpOptionsError,
isSeamHttpOptionsWithApiKey,
Expand All @@ -9,8 +9,9 @@ import {
type SeamHttpOptionsWithApiKey,
type SeamHttpOptionsWithClientSessionToken,
} from './client-options.js'
import { LegacyWorkspaces } from './legacy/workspaces.js'
import { Workspaces } from './routes/workspaces.js'
import { LegacyWorkspacesHttp } from './legacy/workspaces.js'
import { parseOptions } from './parse-options.js'
import { WorkspacesHttp } from './routes/workspaces.js'

export class SeamHttp {
client: Axios
Expand All @@ -20,18 +21,7 @@ export class SeamHttp {
constructor(apiKeyOrOptions: string | SeamHttpOptions) {
const options = parseOptions(apiKeyOrOptions)
this.#legacy = options.enableLegacyMethodBehaivor

// TODO: axiosRetry? Allow options to configure this if so
this.client = axios.create({
baseURL: options.endpoint,
withCredentials: isSeamHttpOptionsWithClientSessionToken(options),
...options.axiosOptions,
headers: {
...getAuthHeaders(options),
...options.axiosOptions.headers,
// TODO: User-Agent
},
})
this.client = createAxiosClient(options)
}

static fromApiKey(
Expand Down Expand Up @@ -66,37 +56,8 @@ export class SeamHttp {
// Better to implement error handling and wrapping in an error handler.
// makeRequest

get workspaces(): Workspaces {
const workspaces = new Workspaces(this.client)
if (this.#legacy) return new LegacyWorkspaces(this.client)
return workspaces
}
}

const parseOptions = (
apiKeyOrOptions: string | SeamHttpOptions,
): Required<SeamHttpOptions> => {
const options =
typeof apiKeyOrOptions === 'string'
? { apiKey: apiKeyOrOptions }
: apiKeyOrOptions

const endpoint =
options.endpoint ??
globalThis.process?.env?.['SEAM_ENDPOINT'] ??
globalThis.process?.env?.['SEAM_API_URL'] ??
'https://connect.getseam.com'

const apiKey =
'apiKey' in options
? options.apiKey
: globalThis.process?.env?.['SEAM_API_KEY']

return {
...options,
...(apiKey != null ? { apiKey } : {}),
endpoint,
axiosOptions: options.axiosOptions ?? {},
enableLegacyMethodBehaivor: false,
get workspaces(): WorkspacesHttp {
if (this.#legacy) return new LegacyWorkspacesHttp(this.client)
return new WorkspacesHttp(this.client)
}
}
4 changes: 2 additions & 2 deletions src/lib/seam/connect/legacy/workspaces.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import type { RouteRequestParams, RouteResponse } from '@seamapi/types/connect'
import type { SetNonNullable } from 'type-fest'

import { Workspaces } from 'lib/seam/connect/routes/workspaces.js'
import { WorkspacesHttp } from 'lib/seam/connect/routes/workspaces.js'

export class LegacyWorkspaces extends Workspaces {
export class LegacyWorkspacesHttp extends WorkspacesHttp {
override async get(
params: WorkspacesGetParams = {},
): Promise<WorkspacesGetResponse['workspace']> {
Expand Down
28 changes: 28 additions & 0 deletions src/lib/seam/connect/parse-options.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import type { SeamHttpOptions } from './client-options.js'
export const parseOptions = (
apiKeyOrOptions: string | SeamHttpOptions,
): Required<SeamHttpOptions> => {
const options =
typeof apiKeyOrOptions === 'string'
? { apiKey: apiKeyOrOptions }
: apiKeyOrOptions

const endpoint =
options.endpoint ??
globalThis.process?.env?.['SEAM_ENDPOINT'] ??
globalThis.process?.env?.['SEAM_API_URL'] ??
'https://connect.getseam.com'

const apiKey =
'apiKey' in options
? options.apiKey
: globalThis.process?.env?.['SEAM_API_KEY']

return {
...options,
...(apiKey != null ? { apiKey } : {}),
endpoint,
axiosOptions: options.axiosOptions ?? {},
enableLegacyMethodBehaivor: false,
}
}
18 changes: 14 additions & 4 deletions src/lib/seam/connect/routes/workspaces.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,22 @@
import type { RouteRequestParams, RouteResponse } from '@seamapi/types/connect'
import type { Axios } from 'axios'
import { Axios } from 'axios'
import type { SetNonNullable } from 'type-fest'

export class Workspaces {
import { createAxiosClient } from 'lib/seam/connect/axios.js'
import type { SeamHttpOptions } from 'lib/seam/connect/client-options.js'
import { parseOptions } from 'lib/seam/connect/parse-options.js'

export class WorkspacesHttp {
client: Axios

constructor(client: Axios) {
this.client = client
constructor(apiKeyOrOptionsOrClient: Axios | string | SeamHttpOptions) {
if (apiKeyOrOptionsOrClient instanceof Axios) {
this.client = apiKeyOrOptionsOrClient
return
}

const options = parseOptions(apiKeyOrOptionsOrClient)
this.client = createAxiosClient(options)
}

async get(
Expand Down

0 comments on commit 2a9ad4a

Please sign in to comment.