import {z} from 'zod' export type GetApiWorkspaceDataSourcesDataSourceArgs = {workspace: string, data_source: string}; export type GetApiWorkspaceDataSourcesDataSourceOptions = {baseUrl?: string | undefined, accessTokenAuth?: {username: string, password: string} | undefined, fetch?: typeof fetch | undefined}; export const dataSourceCustomAttributes = z.object({standard_sql: z.boolean().optional()}); export const link = z.object({href: z.string(), templated: z.boolean().optional()}); export const dataSourceLinks = z.object({self: link, creator: link, account: link, permissions: link.optional(), web: link, web_home: link}); export const dataSourceEmbeds = z.unknown(); export const dataSource = z.object({id: z.number().int(), name: z.string(), description: z.string(), token: z.string(), adapter: z.enum(["jdbc:athena", "jdbc:bigquery", "jdbc:databricks", "jdbc:dbtmetrics", "jdbc:denodo", "jdbc:druid", "jdbc:hive", "jdbc:impala", "jdbc:mysql", "jdbc:oracle", "jdbc:oracleadb", "jdbc:postgresql", "jdbc:trino", "jdbc:presto", "jdbc:clickhouse", "jdbc:redshift", "jdbc:snowflake", "jdbc:spark", "jdbc:sqlserver", "jdbc:treasuredata", "jdbc:vertica", "jdbc:salesforce", "jdbc:dbtsemanticlayer", "jdbc:looker", "jdbc:arrowflightsql", "jdbc:modedatasets"]), created_at: z.string(), updated_at: z.string(), has_expensive_schema_updates: z.boolean(), public: z.boolean(), asleep: z.boolean(), queryable: z.boolean(), soft_deleted: z.boolean(), display_name: z.string(), account_id: z.number().int().optional(), account_username: z.string().optional(), organization_token: z.string().optional(), organization_plan_code: z.string().optional(), database: z.string(), host: z.string(), port: z.string(), ssl: z.boolean(), username: z.string(), provider: z.string(), vendor: z.string(), ldap: z.boolean(), warehouse: z.string(), bridged: z.boolean(), adapter_version: z.string(), custom_attributes: dataSourceCustomAttributes, ssl_trusted_cert: z.string().optional(), default_access_level: z.string().optional(), _links: dataSourceLinks, _embedded: dataSourceEmbeds.optional()}); export const validateResponse = async ( schema: { readonly '~standard': { readonly validate: (value: unknown) => ({ readonly value: Output; readonly issues?: undefined } | { readonly issues: ReadonlyArray<{ readonly message: string; readonly path?: ReadonlyArray | undefined }> }) | Promise<{ readonly value: Output; readonly issues?: undefined } | { readonly issues: ReadonlyArray<{ readonly message: string; readonly path?: ReadonlyArray | undefined }> }> } }, value: unknown ): Promise => { const result = await schema['~standard'].validate(value) if (result.issues !== undefined) { const detail = result.issues .map(({ message, path }) => path?.length ? `${path.map((segment) => String(typeof segment === 'object' ? segment.key : segment)).join('.')}: ${message}` : message ) .join('; ') throw new Error(`Response does not match the schema: ${detail}`, { cause: { issues: result.issues } }) } return result.value }; /** * Get a data source * * GET /{workspace}/data_sources/{data_source} */ export const getApiWorkspaceDataSourcesDataSource = async (args: GetApiWorkspaceDataSourcesDataSourceArgs, options?: GetApiWorkspaceDataSourcesDataSourceOptions) => { const {baseUrl = "https://modeanalytics.com/api", fetch: fetchFn = fetch, accessTokenAuth} = options ?? {} const query = new URLSearchParams() const headers = new Headers() headers.set('accept', "application/hal+json") if (accessTokenAuth !== undefined) headers.set('authorization', `Basic ${btoa(`${accessTokenAuth.username}:${accessTokenAuth.password}`)}`) const url = `${baseUrl.replace(/\/+$/, '')}/${encodeURIComponent(String(args.workspace))}/data_sources/${encodeURIComponent(String(args.data_source))}${query.size > 0 ? `?${query}` : ''}` const res = await fetchFn(url, {method: "GET", headers}) if (!res.ok) throw new Error(`Request failed with status ${res.status}`, {cause: {status: res.status, body: await res.text()}}) return validateResponse(dataSource, await res.json()) };