import {z} from 'zod' export type GetApiApprovalWorkflowsConditionModelsV2Options = {baseUrl?: string | undefined, bearerAuth?: string | undefined, fetch?: typeof fetch | undefined}; export const approvalWorkflowType = z.enum(["JOURNAL_ENTRY", "CONTRACT", "INVOICE", "BILL", "CHARGE", "CHARGE_REVERSAL", "REIMBURSEMENT"]); export const approvalWorkflowConditionLogic = z.enum(["AND", "OR"]); export const approvalWorkflowNumericOperator = z.enum(["GREATER_THAN", "GREATER_THAN_OR_EQUALS", "LESS_THAN", "LESS_THAN_OR_EQUALS", "EQUALS"]); export const currencyCode = z.string(); export const roundedMonetaryAmount = z.object({amount: z.string(), currency: currencyCode}); export const approvalWorkflowMonetaryThreshold = z.object({type: z.string(), amount: roundedMonetaryAmount}); export const approvalWorkflowNumericThreshold = z.object({type: z.string(), value: z.string()}); export const approvalWorkflowAmountThreshold = z.discriminatedUnion("type", [approvalWorkflowMonetaryThreshold, approvalWorkflowNumericThreshold]); export const approvalWorkflowAmountCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowNumericOperator, threshold: approvalWorkflowAmountThreshold}); export const approvalWorkflowEqualityOperator = z.enum(["EQUALS", "NOT_EQUALS"]); export const approvalWorkflowSubsidiaryCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator, subsidiary_id: z.string()}); export const approvalWorkflowCreatedByUserCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator, user_id: z.string()}); export const approvalWorkflowAuraAssistedCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator}); export const approvalWorkflowUiSubmittedCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator}); export const approvalWorkflowApiSubmittedCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator}); export const approvalWorkflowMcpSubmittedCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator}); export const approvalWorkflowFieldCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator, field_id: z.string(), field_value_id: z.string()}); export const approvalWorkflowCollectionOperator = z.enum(["ANY_OF", "NONE_OF"]); export const approvalWorkflowAccountCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowCollectionOperator, account_ids: z.array(z.string())}); export const approvalWorkflowSourceType = z.enum(["MANUAL", "SYSTEM", "ALL"]); export const approvalWorkflowSourceTypeCondition = z.object({id: z.string(), condition_type: z.string(), source_type: approvalWorkflowSourceType}); export const approvalWorkflowVendorCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowEqualityOperator, vendor_id: z.string()}); export const approvalWorkflowCustomerCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowCollectionOperator, customer_ids: z.array(z.string())}); export const approvalWorkflowProvider = z.enum(["AIRBASE", "AWS", "AZURE", "BREX", "CHARGEBEE", "CIN7", "CSV_IMPORT", "CSV_UPLOAD", "CUSTOMER_CUSTOM", "CUSTOMER_HISTORICAL", "DEEL", "DIVVY", "EBIZ", "EXPENSIFY", "FINCH", "FLOAT", "GCP", "HUBSPOT", "HYPERLINE", "JPM", "MAXIO", "METRONOME", "NAVAN", "NEXTCLERK", "ORB", "ORDWAY", "PAYPAL", "PLAID", "POSTSCRIPT", "RAMP", "RIPPLING", "SALESFORCE", "SEQUENCE", "SOLVIMON", "SPHERE", "STRIPE", "STRIPE_BABELFISH_EXTERNAL_ID", "STRIPE_TEAM_ID", "TABS", "TRABA", "DIRECT"]); export const approvalWorkflowProviderCondition = z.object({id: z.string(), condition_type: z.string(), operator: approvalWorkflowCollectionOperator, providers: z.array(approvalWorkflowProvider)}); export const approvalWorkflowOperation = z.enum(["CREATE", "UPDATE"]); export const approvalWorkflowOperationCondition = z.object({id: z.string(), condition_type: z.string(), operation: approvalWorkflowOperation}); export const approvalWorkflowCondition = z.discriminatedUnion("condition_type", [approvalWorkflowAmountCondition, approvalWorkflowSubsidiaryCondition, approvalWorkflowCreatedByUserCondition, approvalWorkflowAuraAssistedCondition, approvalWorkflowUiSubmittedCondition, approvalWorkflowApiSubmittedCondition, approvalWorkflowMcpSubmittedCondition, approvalWorkflowFieldCondition, approvalWorkflowAccountCondition, approvalWorkflowSourceTypeCondition, approvalWorkflowVendorCondition, approvalWorkflowCustomerCondition, approvalWorkflowProviderCondition, approvalWorkflowOperationCondition]); export const approvalWorkflowConditionGroup: z.ZodType = z.object({logic: approvalWorkflowConditionLogic, conditions: z.array(approvalWorkflowCondition), groups: z.array(z.lazy(() => approvalWorkflowConditionGroup)).optional()}); export const approvalWorkflowUserLayer = z.object({id: z.string(), order: z.number().int().gte(1), approver_type: z.string(), require_all: z.boolean(), approver_user_ids: z.array(z.string())}); export const approvalWorkflowRoleLayer = z.object({id: z.string(), order: z.number().int().gte(1), approver_type: z.string(), require_all: z.boolean(), role_ids: z.array(z.string())}); export const approvalWorkflowLayer = z.discriminatedUnion("approver_type", [approvalWorkflowUserLayer, approvalWorkflowRoleLayer]); export const approvalWorkflowMethod = z.enum(["IN_APP", "EMAIL", "SLACK"]); export const approvalWorkflowSubmissionSource = z.enum(["UI", "INTERNAL_API", "PUBLIC_API", "MCP", "CSV", "PROVIDER_IMPORT", "SCHEDULED_SYNC", "REIMPORT", "AURA", "SAMPLE_DATA", "SCHEDULED"]); export const approvalWorkflowSubmissionSources = z.array(approvalWorkflowSubmissionSource); export const approvalValueTextV2 = z.object({type: z.string(), value: z.string()}); export const approvalValueEnumV2 = z.object({type: z.string(), value: z.string()}); export const approvalValueReferenceV2 = z.object({type: z.string(), value: z.string()}); export const approvalValueDecimalV2 = z.object({type: z.string(), value: z.string()}); export const approvalValueBooleanV2 = z.object({type: z.string(), value: z.boolean()}); export const approvalValueDateV2 = z.object({type: z.string(), value: z.string()}); export const approvalValueMoneyV2 = z.object({type: z.string(), amount: z.string(), currency: z.string(), basis: z.enum(["ORIGINAL", "ACCOUNTING"])}); export const approvalValueV2 = z.discriminatedUnion("type", [approvalValueTextV2, approvalValueEnumV2, approvalValueReferenceV2, approvalValueDecimalV2, approvalValueBooleanV2, approvalValueDateV2, approvalValueMoneyV2]); export const approvalOperandScalarV2 = z.object({kind: z.string(), value: approvalValueV2}); export const approvalOperandValuesV2 = z.object({kind: z.string(), values: z.array(approvalValueV2)}); export const approvalOperandV2 = z.discriminatedUnion("kind", [approvalOperandScalarV2, approvalOperandValuesV2]); export const approvalExpressionPredicateV2 = z.object({id: z.string(), kind: z.string(), fieldId: z.string(), operator: z.enum(["EQUALS", "NOT_EQUALS", "IN", "NOT_IN", "GREATER_THAN", "GREATER_THAN_OR_EQUALS", "LESS_THAN", "LESS_THAN_OR_EQUALS", "CONTAINS", "NOT_CONTAINS", "STARTS_WITH", "ENDS_WITH", "IS_PRESENT", "IS_MISSING"]), operand: approvalOperandV2.optional(), textCase: z.enum(["SENSITIVE", "INSENSITIVE"])}); export const approvalExpressionGroupV2 = z.object({id: z.string(), kind: z.string(), logic: z.enum(["AND", "OR"]), children: z.array(z.lazy(() => approvalExpressionV2))}); export const approvalExpressionCollectionV2 = z.object({id: z.string(), kind: z.string(), collectionId: z.string(), quantifier: z.enum(["ANY", "ALL", "NONE"]), expression: z.lazy(() => approvalExpressionV2)}); export const approvalExpressionV2: z.ZodType = z.discriminatedUnion("kind", [approvalExpressionPredicateV2, approvalExpressionGroupV2, approvalExpressionCollectionV2]); export const approvalRuleV2 = z.object({version: z.literal(2), expression: approvalExpressionV2}); export const approvalWorkflowModelV2 = z.object({id: z.string(), name: z.string(), type: approvalWorkflowType, active: z.boolean(), priority: z.number().int(), condition_group: approvalWorkflowConditionGroup.optional(), approval_layers: z.array(approvalWorkflowLayer), methods: z.array(approvalWorkflowMethod), submission_sources: approvalWorkflowSubmissionSources.nullable().optional(), updated_at: z.string(), condition_model_version: z.literal(2), rule: approvalRuleV2.optional(), deadline_days: z.number().int().nullable().optional()}); export const approvalWorkflowModelsV2 = z.object({approval_workflows: z.array(approvalWorkflowModelV2)}); 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 }; /** * List legacy and expanded approval workflows * * GET /approval-workflows/condition-models/v2 */ export const getApiApprovalWorkflowsConditionModelsV2 = async (options?: GetApiApprovalWorkflowsConditionModelsV2Options) => { const {baseUrl = "https://api.rillet.com", fetch: fetchFn = fetch, bearerAuth} = options ?? {} const query = new URLSearchParams() const headers = new Headers() headers.set('accept', "application/json") if (bearerAuth !== undefined) headers.set('authorization', `Bearer ${bearerAuth}`) const url = `${baseUrl.replace(/\/+$/, '')}/approval-workflows/condition-models/v2${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(approvalWorkflowModelsV2, await res.json()) };