typed-tasks
Version:
A type-safe abstraction for Google Cloud Tasks
149 lines (148 loc) • 6.51 kB
text/typescript
import { z } from "zod";
import * as firebase_functions_tasks0 from "firebase-functions/tasks";
import { CloudTasksClient } from "@google-cloud/tasks";
import { MemoryOption } from "firebase-functions";
import { RateLimits, RetryConfig, TaskQueueOptions } from "firebase-functions/v2/tasks";
//#region src/types.d.ts
/** Type definition for a task handler function returned by createHandler */
type TaskHandlerFunction = ReturnType<typeof firebase_functions_tasks0.onTaskDispatched>;
/** Error message for queue names with invalid format */
type QueueNameErrorMessage = "Error: Queue names must be camelCase. Underscores (_) are not allowed by GCP Cloud Tasks, and hyphens (-) cannot be used in JavaScript variable names.";
/** Type utility to check if a string contains hyphens or underscores */
type IsCamelCase<S extends string> = S extends `${string}_${string}` | `_${string}` | `${string}-${string}` ? false : true;
/** Type guard to validate queue names are camelCase */
type ValidateQueueName<S extends string> = IsCamelCase<S> extends true ? S : QueueNameErrorMessage;
/** Record of schema types for each task */
type SchemaRecord = Record<string, z.ZodType>;
/**
* Options for configuring the scheduler - these are options that apply to how
* the task is scheduled, not how it's executed
*/
type TaskSchedulerOptions = {
/**
* When specified, the task will use a time window-based deduplication
* strategy. Tasks with the same name will be deduplicated within the
* specified time window. The value specifies the size of the time window in
* seconds.
*/
deduplicationWindowSeconds?: number;
/**
* When true, the task will automatically derive a taskName using an MD5 hash
* of the payload data, eliminating the need to explicitly provide a taskName.
* If deduplicationWindowSeconds is greater than 0, useDeduplication is
* implicitly true even if not specified.
*/
useDeduplication?: boolean;
};
/**
* Options for configuring a Task handler These options apply to the function
* that executes the task, not how it's scheduled
*/
type TaskHandlerOptions = Omit<TaskQueueOptions, "region"> & {
/**
* Memory allocation for the function Redeclared here for better
* documentation, but uses the same type
*/
memory?: MemoryOption;
/**
* Rate limiting configuration for the queue This is passed directly to the
* onTaskDispatched function
*/
rateLimits?: RateLimits;
/**
* Retry configuration for the queue This is passed directly to the
* onTaskDispatched function
*/
retryConfig?: RetryConfig;
};
/** Utility type to extract schema from TaskDefinition */
type ExtractSchema<T> = T extends z.ZodType ? T : T extends {
schema: z.ZodType;
} ? T["schema"] : never;
/**
* Task definition can be either:
*
* 1. A direct Zod schema
* 2. An object with schema and optional scheduler options
*/
type TaskDefinition = z.ZodType | {
schema: z.ZodType;
options?: TaskSchedulerOptions;
};
/** Record of task definitions for each task with enforced camelCase keys */
type TaskDefinitionRecord<QueueName extends string> = { [K in QueueName]: K extends `${string}_${string}` | `_${string}` | `${string}-${string}` ? never : TaskDefinition };
/**
* Type to extract the payload type for a given task using the task definition's
* schema
*/
type TaskPayload<Defs extends TaskDefinitionRecord<string>, T extends keyof Defs & string> = z.infer<ExtractSchema<Defs[T]>>;
/** Options for scheduling a task */
type TaskScheduleOptions = {
/** Optional name for the task, enabling deduplication */
taskName?: string;
/** Optional delay in seconds before the task should be executed */
delaySeconds?: number;
};
/** Type for the object-based handler parameters */
type TaskHandlerConfig<Schema extends z.ZodType> = {
/** Name of the queue */
queueName: string;
/** Handler-specific options (memory, timeout, etc.) */
options?: TaskHandlerOptions;
/** Function that processes the task */
handler: (payload: z.infer<Schema>) => Promise<void>;
};
/** Type definition for a typed Tasks client */
type TypedTasksClient<Defs extends TaskDefinitionRecord<string>> = {
/**
* Creates a type-safe scheduler function for the specified task
*
* @param queueName - The name of the queue to schedule tasks on
* @returns A function that schedules tasks with the following parameters:
*
* - Data: The payload data that conforms to the task's schema
* - Options: Optional configuration including taskName for deduplication and
* delaySeconds for custom delays. When taskName is not provided and
* deduplication is enabled (either via useDeduplication or
* deduplicationWindowSeconds), a taskName will be automatically
* generated from the payload data using MD5 hash.
*/
createScheduler: <T extends keyof Defs & string>(queueName: T) => (data: z.infer<ExtractSchema<Defs[T]>>, options?: TaskScheduleOptions) => Promise<void>;
/** Creates a type-safe handler function for processing tasks */
createHandler: <T extends keyof Defs & string>(config: {
queueName: T;
options?: TaskHandlerOptions;
handler: (payload: z.infer<ExtractSchema<Defs[T]>>) => Promise<void>;
}) => TaskHandlerFunction;
};
//#endregion
//#region src/factory.d.ts
/**
* Creates a type-safe Tasks client for handling and scheduling tasks with
* schema validation
*
* @param options - Options object containing client configuration
* @param options.tasksClient - Google Cloud Tasks client instance
* @param options.taskDefinitions - Object containing schema and options for
* each task
* @param options.projectId - GCP project ID
* @param options.region - GCP region for the Cloud Tasks
* @param options.options - Optional configuration options for all tasks
* @returns Type-safe Tasks client with scheduler and handler factories
*/
declare function createTypedTasks<TaskDefs extends TaskDefinitionRecord<string>>({
client,
definitions,
projectId,
region,
options
}: {
client: CloudTasksClient;
definitions: TaskDefs;
projectId: string;
region: string;
options?: TaskHandlerOptions;
}): TypedTasksClient<TaskDefs>;
//#endregion
export { ExtractSchema, IsCamelCase, QueueNameErrorMessage, SchemaRecord, TaskDefinition, TaskDefinitionRecord, TaskHandlerConfig, TaskHandlerFunction, TaskHandlerOptions, TaskPayload, TaskScheduleOptions, TaskSchedulerOptions, TypedTasksClient, ValidateQueueName, createTypedTasks };
//# sourceMappingURL=index.d.mts.map