diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 5964b7a54..e34cf74d2 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -31,7 +31,6 @@ jobs: - services - jobs - database-jobs - - database-jobs-v1 - uuid - types - stamps diff --git a/packages/database-jobs-v1/.npmignore b/packages/database-jobs-v1/.npmignore deleted file mode 100644 index cf8a45548..000000000 --- a/packages/database-jobs-v1/.npmignore +++ /dev/null @@ -1,2 +0,0 @@ -__tests__ -jest.config.js diff --git a/packages/database-jobs-v1/LICENSE b/packages/database-jobs-v1/LICENSE deleted file mode 100644 index 7b18c9183..000000000 --- a/packages/database-jobs-v1/LICENSE +++ /dev/null @@ -1,22 +0,0 @@ -The MIT License (MIT) - -Copyright (c) 2025 Dan Lynch -Copyright (c) 2025 Constructive - -Permission is hereby granted, free of charge, to any person obtaining a copy -of this software and associated documentation files (the "Software"), to deal -in the Software without restriction, including without limitation the rights -to use, copy, modify, merge, publish, distribute, sublicense, and/or sell -copies of the Software, and to permit persons to whom the Software is -furnished to do so, subject to the following conditions: - -The above copyright notice and this permission notice shall be included in all -copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE -SOFTWARE. diff --git a/packages/database-jobs-v1/Makefile b/packages/database-jobs-v1/Makefile deleted file mode 100644 index d6e1dee21..000000000 --- a/packages/database-jobs-v1/Makefile +++ /dev/null @@ -1,6 +0,0 @@ -EXTENSION = pgpm-database-jobs -DATA = sql/pgpm-database-jobs--0.15.3.sql - -PG_CONFIG = pg_config -PGXS := $(shell $(PG_CONFIG) --pgxs) -include $(PGXS) diff --git a/packages/database-jobs-v1/README.md b/packages/database-jobs-v1/README.md deleted file mode 100644 index 1015d10e3..000000000 --- a/packages/database-jobs-v1/README.md +++ /dev/null @@ -1,363 +0,0 @@ -# @pgpm/database-jobs - -

- -

- -

- - - - - -

- -Database-specific job handling and queue management. - -## Overview - -`@pgpm/database-jobs` provides a complete PostgreSQL-based background job processing system with persistent queues, scheduled jobs, and worker management. This package implements a robust job queue system entirely within PostgreSQL, enabling reliable background task processing with features like job locking, retries, priorities, and cron-style scheduling. - -## Features - -- **Persistent Job Queue**: Store jobs in PostgreSQL with ACID guarantees -- **Job Scheduling**: Cron-style and rule-based job scheduling -- **Worker Management**: Multiple workers with job locking and expiry -- **Priority Queue**: Process jobs by priority and run time -- **Automatic Retries**: Configurable retry attempts with exponential backoff -- **Job Keys**: Upsert semantics for idempotent job creation -- **Queue Management**: Named queues with independent locking -- **Notifications**: PostgreSQL LISTEN/NOTIFY for real-time job processing - -## Installation - -If you have `pgpm` installed: - -```bash -pgpm install @pgpm/database-jobs -pgpm deploy -``` - -This is a quick way to get started. The sections below provide more detailed installation options. - -### Prerequisites - -```bash -# Install pgpm CLI -npm install -g pgpm - -# Start local Postgres (via Docker) and export env vars -pgpm docker start -eval "$(pgpm env)" -``` - -> **Tip:** Already running Postgres? Skip the Docker step and just export your `PG*` environment variables. - -### **Add to an Existing Package** - -```bash -# 1. Install the package -pgpm install @pgpm/database-jobs - -# 2. Deploy locally -pgpm deploy -``` - -### **Add to a New Project** - -```bash -# 1. Create a workspace -pgpm init workspace - -# 2. Create your first module -cd my-workspace -pgpm init - -# 3. Install a package -cd packages/my-module -pgpm install @pgpm/database-jobs - -# 4. Deploy everything -pgpm deploy --createdb --database mydb1 -``` - -## Core Concepts - -### Jobs Table - -The `app_jobs.jobs` table stores active jobs with the following key fields: -- `id`: Unique job identifier -- `database_id`: Database/tenant identifier -- `task_identifier`: Job type/handler name -- `payload`: JSON data for the job -- `priority`: Lower numbers = higher priority (default: 0) -- `run_at`: When the job should run -- `attempts`: Current attempt count -- `max_attempts`: Maximum retry attempts (default: 25) -- `locked_by`: Worker ID that locked this job -- `locked_at`: When the job was locked -- `key`: Optional unique key for upsert semantics - -### Scheduled Jobs Table - -The `app_jobs.scheduled_jobs` table stores recurring jobs with cron-style or rule-based scheduling. - -### Job Queues Table - -The `app_jobs.job_queues` table tracks queue statistics and locking state. - -## Usage - -### Adding Jobs - -```sql --- Add a simple job -SELECT app_jobs.add_job( - db_id := '5b720132-17d5-424d-9bcb-ee7b17c13d43'::uuid, - identifier := 'send_email', - payload := '{"to": "user@example.com", "subject": "Hello"}'::json -); - --- Add a job with priority and delayed execution -SELECT app_jobs.add_job( - db_id := '5b720132-17d5-424d-9bcb-ee7b17c13d43'::uuid, - identifier := 'generate_report', - payload := '{"report_id": 123}'::json, - run_at := now() + interval '1 hour', - priority := 10, - max_attempts := 5 -); - --- Add a job with a unique key (upsert semantics) -SELECT app_jobs.add_job( - db_id := '5b720132-17d5-424d-9bcb-ee7b17c13d43'::uuid, - identifier := 'daily_summary', - payload := '{"date": "2025-01-15"}'::json, - job_key := 'daily_summary_2025_01_15', - queue_name := 'reports' -); -``` - -### Getting Jobs (Worker Side) - -```sql --- Worker fetches next available job -SELECT * FROM app_jobs.get_job( - worker_id := 'worker-1', - task_identifiers := ARRAY['send_email', 'generate_report'], - job_expiry := interval '4 hours' -); - --- Returns NULL if no jobs available --- Returns job row if job was successfully locked -``` - -### Completing Jobs - -```sql --- Mark job as complete -SELECT app_jobs.complete_job( - worker_id := 'worker-1', - job_id := 123 -); -``` - -### Failing Jobs - -```sql --- Mark job as failed (will retry if attempts < max_attempts) -SELECT app_jobs.fail_job( - worker_id := 'worker-1', - job_id := 123, - error_message := 'Connection timeout' -); -``` - -### Scheduled Jobs - -```sql --- Schedule a job with cron-style timing -INSERT INTO app_jobs.scheduled_jobs ( - database_id, - task_identifier, - payload, - schedule_info -) VALUES ( - '5b720132-17d5-424d-9bcb-ee7b17c13d43'::uuid, - 'cleanup_old_data', - '{"days": 30}'::json, - '{ - "hour": [2], - "minute": [0], - "dayOfWeek": [0, 1, 2, 3, 4, 5, 6] - }'::json -); - --- Schedule a job with a rule (every minute for 3 minutes) -SELECT app_jobs.add_scheduled_job( - db_id := '5b720132-17d5-424d-9bcb-ee7b17c13d43'::uuid, - identifier := 'heartbeat', - payload := '{}'::json, - schedule_info := json_build_object( - 'start', now() + interval '10 seconds', - 'end', now() + interval '3 minutes', - 'rule', '*/1 * * * *' - ) -); - --- Run a scheduled job (creates a job in the jobs table) -SELECT * FROM app_jobs.run_scheduled_job(scheduled_job_id := 1); -``` - -## Functions Reference - -### app_jobs.add_job(...) - -Adds a new job to the queue or updates an existing job if a key is provided. - -**Parameters:** -- `db_id` (uuid): Database/tenant identifier -- `identifier` (text): Job type/handler name -- `payload` (json): Job data (default: `{}`) -- `job_key` (text): Optional unique key for upsert (default: NULL) -- `queue_name` (text): Optional queue name (default: random UUID) -- `run_at` (timestamptz): When to run (default: now()) -- `max_attempts` (integer): Maximum retries (default: 25) -- `priority` (integer): Job priority (default: 0) - -**Returns:** `app_jobs.jobs` row - -**Behavior:** -- If `job_key` is provided and exists, updates the job (if not locked) -- If job is locked, removes the key and creates a new job -- Triggers notifications for workers - -### app_jobs.get_job(...) - -Fetches and locks the next available job for a worker. - -**Parameters:** -- `worker_id` (text): Unique worker identifier -- `task_identifiers` (text[]): Optional filter for job types (default: NULL = all) -- `job_expiry` (interval): How long before locked jobs expire (default: 4 hours) - -**Returns:** `app_jobs.jobs` row or NULL - -**Behavior:** -- Selects jobs by priority, run_at, and id -- Locks the job and its queue -- Increments attempt counter -- Uses `FOR UPDATE SKIP LOCKED` for concurrency - -### app_jobs.complete_job(...) - -Marks a job as successfully completed and removes it from the queue. - -**Parameters:** -- `worker_id` (text): Worker that processed the job -- `job_id` (bigint): Job identifier - -**Returns:** `app_jobs.jobs` row - -### app_jobs.fail_job(...) - -Marks a job as failed and schedules retry if attempts remain. - -**Parameters:** -- `worker_id` (text): Worker that processed the job -- `job_id` (bigint): Job identifier -- `error_message` (text): Error description (default: NULL) - -**Returns:** `app_jobs.jobs` row - -**Behavior:** -- Records error message -- Unlocks the job for retry if attempts < max_attempts -- Permanently fails if max_attempts reached - -### app_jobs.add_scheduled_job(...) - -Creates a scheduled job with cron-style or rule-based timing. - -**Parameters:** -- `db_id` (uuid): Database/tenant identifier -- `identifier` (text): Job type/handler name -- `payload` (json): Job data -- `schedule_info` (json): Scheduling configuration -- `job_key` (text): Optional unique key -- `queue_name` (text): Optional queue name -- `max_attempts` (integer): Maximum retries -- `priority` (integer): Job priority - -**Returns:** `app_jobs.scheduled_jobs` row - -### app_jobs.run_scheduled_job(...) - -Executes a scheduled job by creating a job in the jobs table. - -**Parameters:** -- `scheduled_job_id` (bigint): Scheduled job identifier - -**Returns:** `app_jobs.jobs` row - -## Job Processing Pattern - -```sql --- Worker loop (simplified) -LOOP - -- 1. Get next job - SELECT * FROM app_jobs.get_job('worker-1', ARRAY['my_task']); - - -- 2. Process job - -- ... application logic ... - - -- 3. Mark as complete or failed - IF success THEN - SELECT app_jobs.complete_job('worker-1', job_id); - ELSE - SELECT app_jobs.fail_job('worker-1', job_id, error_msg); - END IF; -END LOOP; -``` - -## Triggers and Automation - -The package includes several triggers for automatic management: - -- **timestamps**: Automatically sets created_at/updated_at -- **notify_worker**: Sends LISTEN/NOTIFY events when jobs are added -- **increase_job_queue_count**: Updates queue statistics on insert -- **decrease_job_queue_count**: Updates queue statistics on delete/update - -## Dependencies - -- PGPM roles (anonymous, authenticated, administrator) -- `@pgpm/verify`: Verification utilities for database objects - -## Testing - -```bash -pnpm test -``` - -The test suite validates: -- Job creation and retrieval -- Scheduled job creation with cron and rule-based timing -- Job key upsert semantics -- Worker locking and concurrency - -## Related Tooling - -* [pgpm](https://github.com/constructive-io/constructive/tree/main/packages/pgpm): **🖥️ PostgreSQL Package Manager** for modular Postgres development. Works with database workspaces, scaffolding, migrations, seeding, and installing database packages. -* [pgsql-test](https://github.com/constructive-io/constructive/tree/main/packages/pgsql-test): **📊 Isolated testing environments** with per-test transaction rollbacks—ideal for integration tests, complex migrations, and RLS simulation. -* [supabase-test](https://github.com/constructive-io/constructive/tree/main/packages/supabase-test): **🧪 Supabase-native test harness** preconfigured for the local Supabase stack—per-test rollbacks, JWT/role context helpers, and CI/GitHub Actions ready. -* [graphile-test](https://github.com/constructive-io/constructive/tree/main/packages/graphile-test): **🔐 Authentication mocking** for Graphile-focused test helpers and emulating row-level security contexts. -* [pgsql-parser](https://github.com/constructive-io/pgsql-parser): **🔄 SQL conversion engine** that interprets and converts PostgreSQL syntax. -* [libpg-query-node](https://github.com/constructive-io/libpg-query-node): **🌉 Node.js bindings** for `libpg_query`, converting SQL into parse trees. -* [pg-proto-parser](https://github.com/constructive-io/pg-proto-parser): **📦 Protobuf parser** for parsing PostgreSQL Protocol Buffers definitions to generate TypeScript interfaces, utility functions, and JSON mappings for enums. - -## Disclaimer - -AS DESCRIBED IN THE LICENSES, THE SOFTWARE IS PROVIDED "AS IS", AT YOUR OWN RISK, AND WITHOUT WARRANTIES OF ANY KIND. - -No developer or entity involved in creating this software will be liable for any claims or damages whatsoever associated with your use, inability to use, or your interaction with other users of the code, including any direct, indirect, incidental, special, exemplary, punitive or consequential damages, or loss of profits, cryptocurrencies, tokens, or anything else of value. diff --git a/packages/database-jobs-v1/__tests__/__snapshots__/jobs.test.ts.snap b/packages/database-jobs-v1/__tests__/__snapshots__/jobs.test.ts.snap deleted file mode 100644 index 78807f7ca..000000000 --- a/packages/database-jobs-v1/__tests__/__snapshots__/jobs.test.ts.snap +++ /dev/null @@ -1,19 +0,0 @@ -// Jest Snapshot v1, https://jestjs.io/docs/snapshot-testing - -exports[`scheduled jobs schedule jobs 1`] = ` -{ - "attempts": 0, - "database_id": "5b720132-17d5-424d-9bcb-ee7b17c13d43", - "id": "1", - "key": null, - "last_error": null, - "locked_at": null, - "locked_by": null, - "max_attempts": 25, - "payload": { - "just": "run it", - }, - "priority": 0, - "task_identifier": "my_job", -} -`; diff --git a/packages/database-jobs-v1/__tests__/jobs.test.ts b/packages/database-jobs-v1/__tests__/jobs.test.ts deleted file mode 100644 index 453de4c04..000000000 --- a/packages/database-jobs-v1/__tests__/jobs.test.ts +++ /dev/null @@ -1,138 +0,0 @@ -import { getConnections, PgTestClient } from 'pgsql-test'; - -let pg: PgTestClient; -let teardown: () => Promise; - -const database_id = '5b720132-17d5-424d-9bcb-ee7b17c13d43'; -const objs: Record = {}; - -describe('scheduled jobs', () => { - beforeAll(async () => { - ({ pg, teardown } = await getConnections()); - }); - - afterAll(async () => { - await teardown(); - }); - - it('schedule jobs by cron', async () => { - const result = await pg.one( - `INSERT INTO app_jobs.scheduled_jobs (database_id, task_identifier, schedule_info) - VALUES ($1, $2, $3) - RETURNING *`, - [ - database_id, - 'my_job', - { - hour: Array.from({ length: 23 }, (_, i) => i), - minute: [0, 15, 30, 45], - dayOfWeek: Array.from({ length: 6 }, (_, i) => i) - } - ] - ); - objs.scheduled1 = result; - }); - - it('schedule jobs by rule', async () => { - const start = new Date(Date.now() + 10000); // 10s from now - const end = new Date(start.getTime() + 180000); // +3min - - const result = await pg.one( - `INSERT INTO app_jobs.scheduled_jobs (database_id, task_identifier, payload, schedule_info) - VALUES ($1, $2, $3, $4) - RETURNING *`, - [ - database_id, - 'my_job', - { just: 'run it' }, - { start, end, rule: '*/1 * * * *' } - ] - ); - objs.scheduled2 = result; - }); - - it('schedule jobs', async () => { - const [result] = await pg.any( - `SELECT * FROM app_jobs.run_scheduled_job($1)`, - [objs.scheduled2.id] - ); - - const { queue_name, run_at, created_at, updated_at, ...obj } = result; - expect(obj).toMatchSnapshot(); - }); - - it('schedule jobs with keys', async () => { - const start = new Date(Date.now() + 10000); // 10s - const end = new Date(start.getTime() + 180000); // +3min - - const [result] = await pg.any( - `SELECT * FROM app_jobs.add_scheduled_job( - db_id := $1::uuid, - identifier := $2::text, - payload := $3::json, - schedule_info := $4::json, - job_key := $5::text, - queue_name := $6::text, - max_attempts := $7::integer, - priority := $8::integer - )`, - [ - database_id, - 'my_job', - { just: 'run it' }, - { start, end, rule: '*/1 * * * *' }, - 'new_key', - null, - 25, - 0 - ] - ); - - const { - queue_name, - run_at, - created_at, - updated_at, - schedule_info: sch, - start: s1, - end: d1, - ...obj - } = result; - - const [result2] = await pg.any( - `SELECT * FROM app_jobs.add_scheduled_job( - db_id := $1, - identifier := $2, - payload := $3, - schedule_info := $4, - job_key := $5, - queue_name := $6, - max_attempts := $7, - priority := $8 - )`, - [ - database_id, - 'my_job', - { just: 'run it' }, - { start, end, rule: '*/1 * * * *' }, - 'new_key', - null, - 25, - 0 - ] - ); - - const { - queue_name: qn, - created_at: ca, - updated_at: ua, - schedule_info: sch2, - start: s, - end: e, - ...obj2 - } = result2; - - console.log('First insert:', obj); - console.log('Duplicate insert (job_key conflict):', obj2); - }); -}); \ No newline at end of file diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/helpers/json_build_object_apply.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/helpers/json_build_object_apply.sql deleted file mode 100644 index 2a8352488..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/helpers/json_build_object_apply.sql +++ /dev/null @@ -1,28 +0,0 @@ --- Deploy schemas/app_jobs/helpers/json_build_object_apply to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE FUNCTION app_jobs.json_build_object_apply (arguments text[]) - RETURNS json - AS $$ -DECLARE - arg text; - _sql text; - _res json; - args text[]; -BEGIN - _sql = 'SELECT json_build_object('; - FOR arg IN - SELECT - unnest(arguments) - LOOP - args = array_append(args, format('''%s''', arg)); - END LOOP; - _sql = _sql || format('%s);', array_to_string(args, ',')); - EXECUTE _sql INTO _res; - RETURN _res; -END; -$$ -LANGUAGE 'plpgsql'; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/add_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/add_job.sql deleted file mode 100644 index 1645b1a5a..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/add_job.sql +++ /dev/null @@ -1,106 +0,0 @@ --- Deploy schemas/app_jobs/procedures/add_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/tables/job_queues/table - -BEGIN; -CREATE FUNCTION app_jobs.add_job ( - db_id uuid, - identifier text, - payload json DEFAULT '{}' ::json, - job_key text DEFAULT NULL, - queue_name text DEFAULT NULL, - run_at timestamptz DEFAULT now(), - max_attempts integer DEFAULT 25, - priority integer DEFAULT 0 -) - RETURNS app_jobs.jobs - AS $$ -DECLARE - v_job app_jobs.jobs; -BEGIN - -- Bake actor_id into payload - payload := (coalesce(payload, '{}'::json)::jsonb || jsonb_build_object('actor_id', jwt_public.current_user_id()))::json; - - IF job_key IS NOT NULL THEN - -- Upsert job - INSERT INTO app_jobs.jobs ( - database_id, - task_identifier, - payload, - queue_name, - run_at, - max_attempts, - key, - priority - ) VALUES ( - db_id, - identifier, - coalesce(payload, - '{}'::json), - queue_name, - coalesce(run_at, now()), - coalesce(max_attempts, 25), - job_key, - coalesce(priority, 0) - ) - ON CONFLICT (key) - DO UPDATE SET - task_identifier = EXCLUDED.task_identifier, - payload = EXCLUDED.payload, - queue_name = EXCLUDED.queue_name, - max_attempts = EXCLUDED.max_attempts, - run_at = EXCLUDED.run_at, - priority = EXCLUDED.priority, - -- always reset error/retry state - attempts = 0, last_error = NULL - WHERE - jobs.locked_at IS NULL - RETURNING - * INTO v_job; - - -- If upsert succeeded (insert or update), return early - - IF NOT (v_job IS NULL) THEN - RETURN v_job; - END IF; - - -- Upsert failed -> there must be an existing job that is locked. Remove - -- existing key to allow a new one to be inserted, and prevent any - -- subsequent retries by bumping attempts to the max allowed. - - UPDATE - app_jobs.jobs - SET - KEY = NULL, - attempts = jobs.max_attempts - WHERE - KEY = job_key; - END IF; - - INSERT INTO app_jobs.jobs ( - database_id, - task_identifier, - payload, - queue_name, - run_at, - max_attempts, - priority - ) VALUES ( - db_id, - identifier, - payload, - queue_name, - run_at, - max_attempts, - priority - ) - RETURNING * INTO v_job; - - RETURN v_job; -END; -$$ -LANGUAGE 'plpgsql' VOLATILE SECURITY DEFINER; - -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/add_scheduled_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/add_scheduled_job.sql deleted file mode 100644 index 1cc20d055..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/add_scheduled_job.sql +++ /dev/null @@ -1,97 +0,0 @@ --- Deploy schemas/app_jobs/procedures/add_scheduled_job to pg - --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; - -CREATE FUNCTION app_jobs.add_scheduled_job( - db_id uuid, - identifier text, - payload json DEFAULT '{}'::json, - schedule_info json DEFAULT '{}'::json, - job_key text DEFAULT NULL, - queue_name text DEFAULT NULL, - max_attempts integer DEFAULT 25, - priority integer DEFAULT 0 -) - RETURNS app_jobs.scheduled_jobs - AS $$ -DECLARE - v_job app_jobs.scheduled_jobs; -BEGIN - IF job_key IS NOT NULL THEN - - -- Upsert job - INSERT INTO app_jobs.scheduled_jobs ( - database_id, - task_identifier, - payload, - queue_name, - schedule_info, - max_attempts, - key, - priority - ) VALUES ( - db_id, - identifier, - coalesce(payload, '{}'::json), - queue_name, - schedule_info, - coalesce(max_attempts, 25), - job_key, - coalesce(priority, 0) - ) - ON CONFLICT (key) - DO UPDATE SET - task_identifier = EXCLUDED.task_identifier, - payload = EXCLUDED.payload, - queue_name = EXCLUDED.queue_name, - max_attempts = EXCLUDED.max_attempts, - schedule_info = EXCLUDED.schedule_info, - priority = EXCLUDED.priority - WHERE - scheduled_jobs.locked_at IS NULL - RETURNING - * INTO v_job; - - -- If upsert succeeded (insert or update), return early - - IF NOT (v_job IS NULL) THEN - RETURN v_job; - END IF; - - -- Upsert failed -> there must be an existing scheduled job that is locked. Remove - -- and allow a new one to be inserted - - DELETE FROM - app_jobs.scheduled_jobs - WHERE - KEY = job_key; - END IF; - - INSERT INTO app_jobs.scheduled_jobs ( - database_id, - task_identifier, - payload, - queue_name, - schedule_info, - max_attempts, - priority - ) VALUES ( - db_id, - identifier, - payload, - queue_name, - schedule_info, - max_attempts, - priority - ) RETURNING * INTO v_job; - RETURN v_job; -END; -$$ -LANGUAGE 'plpgsql' -VOLATILE -SECURITY DEFINER; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/complete_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/complete_job.sql deleted file mode 100644 index afafdbb2b..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/complete_job.sql +++ /dev/null @@ -1,32 +0,0 @@ --- Deploy schemas/app_jobs/procedures/complete_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/tables/job_queues/table - -BEGIN; -CREATE FUNCTION app_jobs.complete_job (worker_id text, job_id bigint) - RETURNS app_jobs.jobs - LANGUAGE plpgsql - AS $$ -DECLARE - v_row app_jobs.jobs; -BEGIN - DELETE FROM app_jobs.jobs - WHERE id = job_id - RETURNING - * INTO v_row; - IF v_row.queue_name IS NOT NULL THEN - UPDATE - app_jobs.job_queues - SET - locked_by = NULL, - locked_at = NULL - WHERE - queue_name = v_row.queue_name - AND locked_by = worker_id; - END IF; - RETURN v_row; -END; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/complete_jobs.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/complete_jobs.sql deleted file mode 100644 index 1b14dffc5..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/complete_jobs.sql +++ /dev/null @@ -1,19 +0,0 @@ --- Deploy schemas/app_jobs/procedures/complete_jobs to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/job_queues/table --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.complete_jobs (job_ids bigint[]) - RETURNS SETOF app_jobs.jobs - LANGUAGE sql - AS $$ - DELETE FROM app_jobs.jobs - WHERE id = ANY (job_ids) - AND (locked_by IS NULL - OR locked_at < NOW() - interval '4 hours') - RETURNING - *; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/do_notify.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/do_notify.sql deleted file mode 100644 index 82d92525a..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/do_notify.sql +++ /dev/null @@ -1,16 +0,0 @@ --- Deploy schemas/app_jobs/procedures/do_notify to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE FUNCTION app_jobs.do_notify () - RETURNS TRIGGER - AS $$ -BEGIN - PERFORM - pg_notify(TG_ARGV[0], ''); - RETURN NEW; -END; -$$ -LANGUAGE plpgsql; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/fail_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/fail_job.sql deleted file mode 100644 index a5b38c686..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/fail_job.sql +++ /dev/null @@ -1,41 +0,0 @@ --- Deploy schemas/app_jobs/procedures/fail_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/tables/job_queues/table - -BEGIN; -CREATE FUNCTION app_jobs.fail_job (worker_id text, job_id bigint, error_message text) - RETURNS app_jobs.jobs - LANGUAGE plpgsql - STRICT - AS $$ -DECLARE - v_row app_jobs.jobs; -BEGIN - UPDATE - app_jobs.jobs - SET - last_error = error_message, - run_at = greatest (now(), run_at) + (exp(least (attempts, 10))::text || ' seconds')::interval, - locked_by = NULL, - locked_at = NULL - WHERE - id = job_id - AND locked_by = worker_id - RETURNING - * INTO v_row; - IF v_row.queue_name IS NOT NULL THEN - UPDATE - app_jobs.job_queues - SET - locked_by = NULL, - locked_at = NULL - WHERE - queue_name = v_row.queue_name - AND locked_by = worker_id; - END IF; - RETURN v_row; -END; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/get_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/get_job.sql deleted file mode 100644 index 9c37d9c94..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/get_job.sql +++ /dev/null @@ -1,92 +0,0 @@ --- Deploy schemas/app_jobs/procedures/get_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/job_queues/table --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.get_job (worker_id text, task_identifiers text[] DEFAULT NULL, job_expiry interval DEFAULT '4 hours') - RETURNS app_jobs.jobs - LANGUAGE plpgsql - AS $$ -DECLARE - v_job_id bigint; - v_queue_name text; - v_row app_jobs.jobs; - v_now timestamptz = now(); -BEGIN - - IF worker_id IS NULL THEN - RAISE exception 'INVALID_WORKER_ID'; - END IF; - - -- - - SELECT - jobs.queue_name, - jobs.id INTO v_queue_name, - v_job_id - FROM - app_jobs.jobs - WHERE (jobs.locked_at IS NULL - OR jobs.locked_at < (v_now - job_expiry)) - AND (jobs.queue_name IS NULL - OR EXISTS ( - SELECT - 1 - FROM - app_jobs.job_queues - WHERE - job_queues.queue_name = jobs.queue_name - AND (job_queues.locked_at IS NULL - OR job_queues.locked_at < (v_now - job_expiry)) - FOR UPDATE - SKIP LOCKED)) - AND run_at <= v_now - AND attempts < max_attempts - AND (task_identifiers IS NULL - OR task_identifier = ANY (task_identifiers)) - ORDER BY - priority ASC, - run_at ASC, - id ASC - LIMIT 1 - FOR UPDATE - SKIP LOCKED; - - -- - - IF v_job_id IS NULL THEN - RETURN NULL; - END IF; - - -- - - IF v_queue_name IS NOT NULL THEN - UPDATE - app_jobs.job_queues - SET - locked_by = worker_id, - locked_at = v_now - WHERE - job_queues.queue_name = v_queue_name; - END IF; - - -- - - UPDATE - app_jobs.jobs - SET - attempts = attempts + 1, - locked_by = worker_id, - locked_at = v_now - WHERE - id = v_job_id - RETURNING - * INTO v_row; - - -- - RETURN v_row; -END; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/get_scheduled_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/get_scheduled_job.sql deleted file mode 100644 index b8fa5a664..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/get_scheduled_job.sql +++ /dev/null @@ -1,61 +0,0 @@ --- Deploy schemas/app_jobs/procedures/get_scheduled_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.get_scheduled_job (worker_id text, task_identifiers text[] DEFAULT NULL) - RETURNS app_jobs.scheduled_jobs - LANGUAGE plpgsql - AS $$ -DECLARE - v_job_id bigint; - v_row app_jobs.scheduled_jobs; -BEGIN - - -- - - IF worker_id IS NULL THEN - RAISE exception 'INVALID_WORKER_ID'; - END IF; - - -- - - SELECT - scheduled_jobs.id INTO v_job_id - FROM - app_jobs.scheduled_jobs - WHERE (scheduled_jobs.locked_at IS NULL) - AND (task_identifiers IS NULL - OR task_identifier = ANY (task_identifiers)) - ORDER BY - priority ASC, - id ASC - LIMIT 1 - FOR UPDATE - SKIP LOCKED; - - -- - - IF v_job_id IS NULL THEN - RETURN NULL; - END IF; - - -- - - UPDATE - app_jobs.scheduled_jobs - SET - locked_by = worker_id, - locked_at = NOW() - WHERE - id = v_job_id - RETURNING - * INTO v_row; - - -- - - RETURN v_row; -END; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/permanently_fail_jobs.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/permanently_fail_jobs.sql deleted file mode 100644 index 3c7328062..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/permanently_fail_jobs.sql +++ /dev/null @@ -1,24 +0,0 @@ --- Deploy schemas/app_jobs/procedures/permanently_fail_jobs to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/job_queues/table --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.permanently_fail_jobs (job_ids bigint[], error_message text DEFAULT NULL) - RETURNS SETOF app_jobs.jobs - LANGUAGE sql - AS $$ - UPDATE - app_jobs.jobs - SET - last_error = coalesce(error_message, 'Manually marked as failed'), - attempts = max_attempts - WHERE - id = ANY (job_ids) - AND (locked_by IS NULL - OR locked_at < NOW() - interval '4 hours') - RETURNING - *; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/release_jobs.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/release_jobs.sql deleted file mode 100644 index 2fd063367..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/release_jobs.sql +++ /dev/null @@ -1,34 +0,0 @@ --- Deploy schemas/app_jobs/procedures/release_jobs to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/tables/job_queues/table - -BEGIN; -CREATE FUNCTION app_jobs.release_jobs (worker_id text) - RETURNS void - AS $$ -DECLARE -BEGIN - -- clear the job - UPDATE - app_jobs.jobs - SET - locked_at = NULL, - locked_by = NULL, - attempts = GREATEST (attempts - 1, 0) - WHERE - locked_by = worker_id; - -- clear the queue - UPDATE - app_jobs.job_queues - SET - locked_at = NULL, - locked_by = NULL - WHERE - locked_by = worker_id; -END; -$$ -LANGUAGE 'plpgsql' -VOLATILE; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/release_scheduled_jobs.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/release_scheduled_jobs.sql deleted file mode 100644 index ec66b60a1..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/release_scheduled_jobs.sql +++ /dev/null @@ -1,26 +0,0 @@ --- Deploy schemas/app_jobs/procedures/release_scheduled_jobs to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.release_scheduled_jobs (worker_id text, ids bigint[] DEFAULT NULL) - RETURNS void - AS $$ -DECLARE -BEGIN - -- clear the scheduled job - UPDATE - app_jobs.scheduled_jobs s - SET - locked_at = NULL, - locked_by = NULL - WHERE - locked_by = worker_id - AND (ids IS NULL - OR s.id = ANY (ids)); -END; -$$ -LANGUAGE 'plpgsql' -VOLATILE; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/reschedule_jobs.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/reschedule_jobs.sql deleted file mode 100644 index b39d884db..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/reschedule_jobs.sql +++ /dev/null @@ -1,26 +0,0 @@ --- Deploy schemas/app_jobs/procedures/reschedule_jobs to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; --- NOTE this should be renamed to reset_jobs to avoid confusion of scheduled jobs -CREATE FUNCTION app_jobs.reschedule_jobs (job_ids bigint[], run_at timestamptz DEFAULT NULL, priority integer DEFAULT NULL, attempts integer DEFAULT NULL, max_attempts integer DEFAULT NULL) - RETURNS SETOF app_jobs.jobs - LANGUAGE sql - AS $$ - UPDATE - app_jobs.jobs - SET - run_at = coalesce(reschedule_jobs.run_at, jobs.run_at), - priority = coalesce(reschedule_jobs.priority, jobs.priority), - attempts = coalesce(reschedule_jobs.attempts, jobs.attempts), - max_attempts = coalesce(reschedule_jobs.max_attempts, jobs.max_attempts) - WHERE - id = ANY (job_ids) - AND (locked_by IS NULL - OR locked_at < NOW() - interval '4 hours') - RETURNING - *; -$$; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/run_scheduled_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/run_scheduled_job.sql deleted file mode 100644 index 41c258b35..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/procedures/run_scheduled_job.sql +++ /dev/null @@ -1,78 +0,0 @@ --- Deploy schemas/app_jobs/procedures/run_scheduled_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.run_scheduled_job (id bigint, job_expiry interval DEFAULT '1 hours') - RETURNS app_jobs.jobs - AS $$ -DECLARE - j app_jobs.jobs; - last_id bigint; - lkd_by text; -BEGIN - -- check last scheduled - SELECT - last_scheduled_id - FROM - app_jobs.scheduled_jobs s - WHERE - s.id = run_scheduled_job.id INTO last_id; - - -- if it's been scheduled check if it's been run - - IF (last_id IS NOT NULL) THEN - SELECT - locked_by - FROM - app_jobs.jobs js - WHERE - js.id = last_id - AND (js.locked_at IS NULL -- never been run - OR js.locked_at >= (NOW() - job_expiry) - -- still running within a safe interval -) INTO lkd_by; - IF (FOUND) THEN - RAISE EXCEPTION 'ALREADY_SCHEDULED'; - END IF; - END IF; - - -- insert new job - INSERT INTO app_jobs.jobs ( - database_id, - queue_name, - task_identifier, - payload, - priority, - max_attempts, - key - ) SELECT - database_id, - queue_name, - task_identifier, - payload, - priority, - max_attempts, - key - FROM - app_jobs.scheduled_jobs s - WHERE - s.id = run_scheduled_job.id - RETURNING - * INTO j; - -- update the scheduled job - UPDATE - app_jobs.scheduled_jobs s - SET - last_scheduled = NOW(), - last_scheduled_id = j.id - WHERE - s.id = run_scheduled_job.id; - RETURN j; -END; -$$ -LANGUAGE 'plpgsql' -VOLATILE; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/schema.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/schema.sql deleted file mode 100644 index 86a5b4eeb..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/schema.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Deploy schemas/app_jobs/schema to pg -BEGIN; -CREATE SCHEMA IF NOT EXISTS app_jobs; -GRANT USAGE ON SCHEMA app_jobs TO administrator; -ALTER DEFAULT PRIVILEGES IN SCHEMA app_jobs GRANT EXECUTE ON FUNCTIONS TO administrator; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index 6f0fc3be9..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,12 +0,0 @@ --- Deploy schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator to pg - --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/job_queues/table - -BEGIN; - --- TODO make sure to require any policies on this table! - -GRANT SELECT, INSERT, UPDATE, DELETE ON TABLE app_jobs.job_queues TO administrator; - -COMMIT; diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql deleted file mode 100644 index cc78f18a5..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Deploy schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/job_queues/table - -BEGIN; -CREATE INDEX job_queues_locked_by_idx ON app_jobs.job_queues (locked_by); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/table.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/table.sql deleted file mode 100644 index dd003c348..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/job_queues/table.sql +++ /dev/null @@ -1,19 +0,0 @@ --- Deploy schemas/app_jobs/tables/job_queues/table to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE TABLE app_jobs.job_queues ( - queue_name text NOT NULL PRIMARY KEY, - job_count int DEFAULT 0 NOT NULL, - locked_at timestamptz, - locked_by text -); - -COMMENT ON TABLE app_jobs.job_queues IS 'Queue metadata: tracks job counts and locking state for each named queue'; -COMMENT ON COLUMN app_jobs.job_queues.queue_name IS 'Unique name identifying this queue'; -COMMENT ON COLUMN app_jobs.job_queues.job_count IS 'Number of pending jobs in this queue'; -COMMENT ON COLUMN app_jobs.job_queues.locked_at IS 'Timestamp when this queue was locked for batch processing'; -COMMENT ON COLUMN app_jobs.job_queues.locked_by IS 'Identifier of the worker that currently holds the queue lock'; - -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index 11a3ac344..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,12 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator to pg - --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; - --- TODO make sure to require any policies on this table! - -GRANT SELECT, INSERT, UPDATE, DELETE ON TABLE app_jobs.jobs TO administrator; - -COMMIT; diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql deleted file mode 100644 index d41680373..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE INDEX jobs_locked_by_idx ON app_jobs.jobs (locked_by); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql deleted file mode 100644 index 78b03ff13..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE INDEX priority_run_at_id_idx ON app_jobs.jobs (priority, run_at, id); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/table.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/table.sql deleted file mode 100644 index 48ea7c146..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/table.sql +++ /dev/null @@ -1,43 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/table to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE TABLE app_jobs.jobs ( - id bigserial PRIMARY KEY, - database_id uuid NOT NULL, - queue_name text DEFAULT (public.gen_random_uuid ()) ::text, - task_identifier text NOT NULL, - payload json DEFAULT '{}' ::json NOT NULL, - priority integer DEFAULT 0 NOT NULL, - run_at timestamptz DEFAULT now() NOT NULL, - attempts integer DEFAULT 0 NOT NULL, - max_attempts integer DEFAULT 25 NOT NULL, - key text, - last_error text, - locked_at timestamptz, - locked_by text, - CHECK (length(key) < 513), - CHECK (length(task_identifier) < 127), - CHECK (max_attempts > 0), - CHECK (length(queue_name) < 127), - CHECK (length(locked_by) > 3), - UNIQUE (key) -); - -COMMENT ON TABLE app_jobs.jobs IS 'Background job queue with database scoping: each row is a pending or in-progress task for a specific database'; -COMMENT ON COLUMN app_jobs.jobs.id IS 'Auto-incrementing job identifier'; -COMMENT ON COLUMN app_jobs.jobs.database_id IS 'Database this job belongs to, for multi-tenant job isolation'; -COMMENT ON COLUMN app_jobs.jobs.queue_name IS 'Name of the queue this job belongs to; used for worker routing and concurrency control'; -COMMENT ON COLUMN app_jobs.jobs.task_identifier IS 'Identifier for the task type (maps to a worker handler function)'; -COMMENT ON COLUMN app_jobs.jobs.payload IS 'JSON payload of arguments passed to the task handler'; -COMMENT ON COLUMN app_jobs.jobs.priority IS 'Execution priority; lower numbers run first (default 0)'; -COMMENT ON COLUMN app_jobs.jobs.run_at IS 'Earliest time this job should be executed; used for delayed/scheduled execution'; -COMMENT ON COLUMN app_jobs.jobs.attempts IS 'Number of times this job has been attempted so far'; -COMMENT ON COLUMN app_jobs.jobs.max_attempts IS 'Maximum retry attempts before the job is considered permanently failed'; -COMMENT ON COLUMN app_jobs.jobs.key IS 'Optional unique deduplication key; prevents duplicate jobs with the same key'; -COMMENT ON COLUMN app_jobs.jobs.last_error IS 'Error message from the most recent failed attempt'; -COMMENT ON COLUMN app_jobs.jobs.locked_at IS 'Timestamp when a worker locked this job for processing'; -COMMENT ON COLUMN app_jobs.jobs.locked_by IS 'Identifier of the worker that currently holds the lock'; - -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql deleted file mode 100644 index c87bf7bce..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql +++ /dev/null @@ -1,45 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.tg_decrease_job_queue_count () - RETURNS TRIGGER - AS $$ -DECLARE - v_new_job_count int; -BEGIN - UPDATE - app_jobs.job_queues - SET - job_count = job_queues.job_count - 1 - WHERE - queue_name = OLD.queue_name - RETURNING - job_count INTO v_new_job_count; - IF v_new_job_count <= 0 THEN - DELETE FROM app_jobs.job_queues - WHERE queue_name = OLD.queue_name - AND job_count <= 0; - END IF; - RETURN OLD; -END; -$$ -LANGUAGE 'plpgsql' -VOLATILE; - -CREATE TRIGGER decrease_job_queue_count_on_delete - AFTER DELETE ON app_jobs.jobs - FOR EACH ROW - WHEN ((OLD.queue_name IS NOT NULL)) - EXECUTE PROCEDURE app_jobs.tg_decrease_job_queue_count (); - --- only a person would do this... -CREATE TRIGGER decrease_job_queue_count_on_update - AFTER UPDATE OF queue_name ON app_jobs.jobs - FOR EACH ROW - WHEN (((NEW.queue_name IS DISTINCT FROM OLD.queue_name) AND (OLD.queue_name IS NOT NULL))) - EXECUTE PROCEDURE app_jobs.tg_decrease_job_queue_count (); - -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql deleted file mode 100644 index b25b3f1a7..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql +++ /dev/null @@ -1,32 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table - -BEGIN; -CREATE FUNCTION app_jobs.tg_increase_job_queue_count () - RETURNS TRIGGER - AS $$ -BEGIN - INSERT INTO app_jobs.job_queues (queue_name, job_count) - VALUES (NEW.queue_name, 1) - ON CONFLICT (queue_name) - DO UPDATE SET - job_count = job_queues.job_count + 1; - RETURN NEW; -END; -$$ -LANGUAGE 'plpgsql' -VOLATILE; -CREATE TRIGGER _500_increase_job_queue_count_on_insert - AFTER INSERT ON app_jobs.jobs - FOR EACH ROW - WHEN ((NEW.queue_name IS NOT NULL)) - EXECUTE PROCEDURE app_jobs.tg_increase_job_queue_count (); --- only a person would do this -CREATE TRIGGER _500_increase_job_queue_count_on_update - AFTER UPDATE OF queue_name ON app_jobs.jobs - FOR EACH ROW - WHEN (((NEW.queue_name IS DISTINCT FROM OLD.queue_name) AND (NEW.queue_name IS NOT NULL))) - EXECUTE PROCEDURE app_jobs.tg_increase_job_queue_count (); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql deleted file mode 100644 index 9e6cec54c..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql +++ /dev/null @@ -1,13 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/triggers/notify_worker to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/procedures/do_notify --- requires: schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count - -BEGIN; -CREATE TRIGGER _900_notify_worker - AFTER INSERT ON app_jobs.jobs - FOR EACH ROW - EXECUTE PROCEDURE app_jobs.do_notify ('jobs:insert'); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/timestamps.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/timestamps.sql deleted file mode 100644 index b26296953..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/jobs/triggers/timestamps.sql +++ /dev/null @@ -1,20 +0,0 @@ --- Deploy schemas/app_jobs/tables/jobs/triggers/timestamps to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/jobs/table --- requires: schemas/app_jobs/triggers/tg_update_timestamps - -BEGIN; -ALTER TABLE app_jobs.jobs - ADD COLUMN created_at timestamptz; -ALTER TABLE app_jobs.jobs - ALTER COLUMN created_at SET DEFAULT NOW(); -ALTER TABLE app_jobs.jobs - ADD COLUMN updated_at timestamptz; -ALTER TABLE app_jobs.jobs - ALTER COLUMN updated_at SET DEFAULT NOW(); -CREATE TRIGGER _100_update_jobs_modtime_tg - BEFORE UPDATE OR INSERT ON app_jobs.jobs - FOR EACH ROW - EXECUTE PROCEDURE app_jobs.tg_update_timestamps (); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index 914166bd4..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,12 +0,0 @@ --- Deploy schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator to pg - --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; - --- TODO make sure to require any policies on this table! - -GRANT SELECT, INSERT, UPDATE, DELETE ON TABLE app_jobs.scheduled_jobs TO administrator; - -COMMIT; diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql deleted file mode 100644 index d222737ff..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Deploy schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; -CREATE INDEX scheduled_jobs_locked_by_idx ON app_jobs.scheduled_jobs (locked_by); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql deleted file mode 100644 index 9bd548796..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Deploy schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table - -BEGIN; -CREATE INDEX scheduled_jobs_priority_id_idx ON app_jobs.scheduled_jobs (priority, id); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/table.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/table.sql deleted file mode 100644 index 75d81c9e3..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/table.sql +++ /dev/null @@ -1,43 +0,0 @@ --- Deploy schemas/app_jobs/tables/scheduled_jobs/table to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE TABLE app_jobs.scheduled_jobs ( - id bigserial PRIMARY KEY, - database_id uuid NOT NULL, - queue_name text DEFAULT (public.gen_random_uuid ()) ::text, - task_identifier text NOT NULL, - payload json DEFAULT '{}' ::json NOT NULL, - priority integer DEFAULT 0 NOT NULL, - max_attempts integer DEFAULT 25 NOT NULL, - key text, - locked_at timestamptz, - locked_by text, - schedule_info json NOT NULL, - last_scheduled timestamptz, - last_scheduled_id bigint, - CHECK (length(key) < 513), - CHECK (length(task_identifier) < 127), - CHECK (max_attempts > 0), - CHECK (length(queue_name) < 127), - CHECK (length(locked_by) > 3), - UNIQUE (key) -); - -COMMENT ON TABLE app_jobs.scheduled_jobs IS 'Recurring/cron-style job definitions with database scoping: each row spawns jobs on a schedule for a specific database'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.id IS 'Auto-incrementing scheduled job identifier'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.database_id IS 'Database this scheduled job belongs to, for multi-tenant isolation'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.queue_name IS 'Name of the queue spawned jobs are placed into'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.task_identifier IS 'Task type identifier for spawned jobs'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.payload IS 'JSON payload passed to each spawned job'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.priority IS 'Priority assigned to spawned jobs (lower = higher priority)'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.max_attempts IS 'Max retry attempts for spawned jobs'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.key IS 'Optional unique deduplication key'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.locked_at IS 'Timestamp when the scheduler locked this record for processing'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.locked_by IS 'Identifier of the scheduler worker holding the lock'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.schedule_info IS 'JSON schedule configuration (e.g. cron expression, interval)'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.last_scheduled IS 'Timestamp when a job was last spawned from this schedule'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.last_scheduled_id IS 'ID of the last job spawned from this schedule'; - -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql deleted file mode 100644 index 51e17d4c0..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql +++ /dev/null @@ -1,12 +0,0 @@ --- Deploy schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/tables/scheduled_jobs/table --- requires: schemas/app_jobs/procedures/do_notify - -BEGIN; -CREATE TRIGGER _900_notify_scheduled_job - AFTER INSERT ON app_jobs.scheduled_jobs - FOR EACH ROW - EXECUTE PROCEDURE app_jobs.do_notify ('scheduled_jobs:insert'); -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_fields.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_fields.sql deleted file mode 100644 index a83a8b833..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_fields.sql +++ /dev/null @@ -1,50 +0,0 @@ --- Deploy schemas/app_jobs/triggers/tg_add_job_with_fields to pg --- requires: schemas/app_jobs/schema --- requires: schemas/app_jobs/helpers/json_build_object_apply - -BEGIN; -CREATE FUNCTION app_jobs.trigger_job_with_fields () - RETURNS TRIGGER - AS $$ -DECLARE - arg text; - fn text; - i int; - args text[]; -BEGIN - FOR i IN - SELECT - * - FROM - generate_series(1, TG_NARGS) g (i) - LOOP - IF (i = 1) THEN - fn = TG_ARGV[i - 1]; - ELSE - args = array_append(args, TG_ARGV[i - 1]); - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - EXECUTE format('SELECT ($1).%s::text', TG_ARGV[i - 1]) - USING NEW INTO arg; - END IF; - IF (TG_OP = 'DELETE') THEN - EXECUTE format('SELECT ($1).%s::text', TG_ARGV[i - 1]) - USING OLD INTO arg; - END IF; - args = array_append(args, arg); - END IF; - END LOOP; - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), fn, app_jobs.json_build_object_apply (args)); - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - RETURN NEW; - END IF; - IF (TG_OP = 'DELETE') THEN - RETURN OLD; - END IF; -END; -$$ -LANGUAGE plpgsql -VOLATILE -SECURITY DEFINER; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_row.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_row.sql deleted file mode 100644 index bb619156b..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_row.sql +++ /dev/null @@ -1,26 +0,0 @@ --- Deploy schemas/app_jobs/triggers/tg_add_job_with_row to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE FUNCTION app_jobs.tg_add_job_with_row () - RETURNS TRIGGER - AS $$ -BEGIN - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), TG_ARGV[0], to_json(NEW)); - RETURN NEW; - END IF; - IF (TG_OP = 'DELETE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), TG_ARGV[0], to_json(OLD)); - RETURN OLD; - END IF; -END; -$$ -LANGUAGE plpgsql -VOLATILE -SECURITY DEFINER; -COMMENT ON FUNCTION app_jobs.tg_add_job_with_row IS E'Useful shortcut to create a job on insert or update. Pass the task name as the trigger argument, and the record data will automatically be available on the JSON payload.'; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql deleted file mode 100644 index faf7c78d3..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql +++ /dev/null @@ -1,27 +0,0 @@ --- Deploy schemas/app_jobs/triggers/tg_add_job_with_row_id to pg - --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE FUNCTION app_jobs.tg_add_job_with_row_id () - RETURNS TRIGGER - AS $$ -BEGIN - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), tg_argv[0], json_build_object('id', NEW.id)); - RETURN NEW; - END IF; - IF (TG_OP = 'DELETE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), tg_argv[0], json_build_object('id', OLD.id)); - RETURN OLD; - END IF; -END; -$$ -LANGUAGE plpgsql -VOLATILE -SECURITY DEFINER; -COMMENT ON FUNCTION app_jobs.tg_add_job_with_row_id IS E'Useful shortcut to create a job on insert or update. Pass the task name as the trigger argument, and the record id will automatically be available on the JSON payload.'; -COMMIT; - diff --git a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_update_timestamps.sql b/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_update_timestamps.sql deleted file mode 100644 index e74c4abfc..000000000 --- a/packages/database-jobs-v1/deploy/schemas/app_jobs/triggers/tg_update_timestamps.sql +++ /dev/null @@ -1,21 +0,0 @@ --- Deploy schemas/app_jobs/triggers/tg_update_timestamps to pg --- requires: schemas/app_jobs/schema - -BEGIN; -CREATE FUNCTION app_jobs.tg_update_timestamps () - RETURNS TRIGGER - AS $$ -BEGIN - IF TG_OP = 'INSERT' THEN - NEW.created_at = NOW(); - NEW.updated_at = NOW(); - ELSIF TG_OP = 'UPDATE' THEN - NEW.created_at = OLD.created_at; - NEW.updated_at = greatest (now(), OLD.updated_at + interval '1 millisecond'); - END IF; - RETURN NEW; -END; -$$ -LANGUAGE 'plpgsql'; -COMMIT; - diff --git a/packages/database-jobs-v1/jest.config.js b/packages/database-jobs-v1/jest.config.js deleted file mode 100644 index e20e7efb5..000000000 --- a/packages/database-jobs-v1/jest.config.js +++ /dev/null @@ -1,15 +0,0 @@ -/** @type {import('ts-jest').JestConfigWithTsJest} */ -module.exports = { - preset: 'ts-jest', - testEnvironment: 'node', - - // Match both __tests__ and colocated test files - testMatch: ['**/?(*.)+(test|spec).{ts,tsx,js,jsx}'], - - // Ignore build artifacts and type declarations - testPathIgnorePatterns: ['/dist/', '\\.d\\.ts$'], - modulePathIgnorePatterns: ['/dist/'], - watchPathIgnorePatterns: ['/dist/'], - - moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx', 'json', 'node'], -}; diff --git a/packages/database-jobs-v1/package.json b/packages/database-jobs-v1/package.json deleted file mode 100644 index eb7d458f0..000000000 --- a/packages/database-jobs-v1/package.json +++ /dev/null @@ -1,37 +0,0 @@ -{ - "name": "@pgpm/database-jobs-v1", - "version": "0.21.0", - "description": "Database-specific job handling and queue management", - "author": "Dan Lynch ", - "contributors": [ - "Constructive " - ], - "keywords": [ - "postgresql", - "pgpm", - "jobs", - "queue" - ], - "publishConfig": { - "access": "public" - }, - "scripts": { - "bundle": "pgpm package", - "test": "jest", - "test:watch": "jest --watch" - }, - "devDependencies": { - "pgpm": "^4.16.6" - }, - "dependencies": { - "@pgpm/verify": "workspace:*" - }, - "repository": { - "type": "git", - "url": "https://github.com/constructive-io/pgpm-modules" - }, - "homepage": "https://github.com/constructive-io/pgpm-modules", - "bugs": { - "url": "https://github.com/constructive-io/pgpm-modules/issues" - } -} diff --git a/packages/database-jobs-v1/pgpm-database-jobs-v1.control b/packages/database-jobs-v1/pgpm-database-jobs-v1.control deleted file mode 100644 index 3754fe24d..000000000 --- a/packages/database-jobs-v1/pgpm-database-jobs-v1.control +++ /dev/null @@ -1,8 +0,0 @@ -# pgpm-database-jobs-v1 extension -comment = 'pgpm-database-jobs-v1 extension' -default_version = '0.15.5' -module_pathname = '$libdir/pgpm-database-jobs-v1' -requires = 'plpgsql,pgcrypto,pgpm-verify' -relocatable = false -superuser = false - diff --git a/packages/database-jobs-v1/pgpm.plan b/packages/database-jobs-v1/pgpm.plan deleted file mode 100644 index 76ce5034c..000000000 --- a/packages/database-jobs-v1/pgpm.plan +++ /dev/null @@ -1,38 +0,0 @@ -%syntax-version=1.0.0 -%project=pgpm-database-jobs-v1 -%uri=pgpm-database-jobs-v1 -schemas/app_jobs/schema [pgpm-verify:@0.1.0] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/schema -schemas/app_jobs/triggers/tg_update_timestamps [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/triggers/tg_update_timestamps -schemas/app_jobs/triggers/tg_add_job_with_row_id [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/triggers/tg_add_job_with_row_id -schemas/app_jobs/triggers/tg_add_job_with_row [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/triggers/tg_add_job_with_row -schemas/app_jobs/helpers/json_build_object_apply [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/helpers/json_build_object_apply -schemas/app_jobs/triggers/tg_add_job_with_fields [schemas/app_jobs/schema schemas/app_jobs/helpers/json_build_object_apply] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/triggers/tg_add_job_with_fields -schemas/app_jobs/tables/scheduled_jobs/table [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/scheduled_jobs/table -schemas/app_jobs/procedures/do_notify [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/do_notify -schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table schemas/app_jobs/procedures/do_notify] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job -schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx -schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx -schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator -schemas/app_jobs/tables/jobs/table [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/table -schemas/app_jobs/tables/jobs/triggers/timestamps [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/triggers/tg_update_timestamps] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/triggers/timestamps -schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count -schemas/app_jobs/tables/jobs/triggers/notify_worker [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/procedures/do_notify schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/triggers/notify_worker -schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count -schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx -schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx -schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator -schemas/app_jobs/tables/job_queues/table [schemas/app_jobs/schema] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/job_queues/table -schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx [schemas/app_jobs/schema schemas/app_jobs/tables/job_queues/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx -schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator [schemas/app_jobs/schema schemas/app_jobs/tables/job_queues/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator -schemas/app_jobs/procedures/run_scheduled_job [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/run_scheduled_job -schemas/app_jobs/procedures/reschedule_jobs [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/reschedule_jobs -schemas/app_jobs/procedures/release_scheduled_jobs [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/release_scheduled_jobs -schemas/app_jobs/procedures/release_jobs [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/tables/job_queues/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/release_jobs -schemas/app_jobs/procedures/permanently_fail_jobs [schemas/app_jobs/schema schemas/app_jobs/tables/job_queues/table schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/permanently_fail_jobs -schemas/app_jobs/procedures/get_scheduled_job [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/get_scheduled_job -schemas/app_jobs/procedures/get_job [schemas/app_jobs/schema schemas/app_jobs/tables/job_queues/table schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/get_job -schemas/app_jobs/procedures/fail_job [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/tables/job_queues/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/fail_job -schemas/app_jobs/procedures/complete_jobs [schemas/app_jobs/schema schemas/app_jobs/tables/job_queues/table schemas/app_jobs/tables/jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/complete_jobs -schemas/app_jobs/procedures/complete_job [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/tables/job_queues/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/complete_job -schemas/app_jobs/procedures/add_scheduled_job [schemas/app_jobs/schema schemas/app_jobs/tables/scheduled_jobs/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/add_scheduled_job -schemas/app_jobs/procedures/add_job [schemas/app_jobs/schema schemas/app_jobs/tables/jobs/table schemas/app_jobs/tables/job_queues/table] 2025-08-26T23:57:41Z pgpm # add schemas/app_jobs/procedures/add_job diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/helpers/json_build_object_apply.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/helpers/json_build_object_apply.sql deleted file mode 100644 index b1778898c..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/helpers/json_build_object_apply.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/helpers/json_build_object_apply from pg - -BEGIN; - -DROP FUNCTION app_jobs.json_build_object_apply; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/add_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/add_job.sql deleted file mode 100644 index 44a65ae8d..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/add_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/add_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.add_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/add_scheduled_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/add_scheduled_job.sql deleted file mode 100644 index 882a98f9d..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/add_scheduled_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/add_scheduled_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.add_scheduled_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/complete_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/complete_job.sql deleted file mode 100644 index 7c0ea9dfa..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/complete_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/complete_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.complete_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/complete_jobs.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/complete_jobs.sql deleted file mode 100644 index 3db9150e3..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/complete_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/complete_jobs from pg - -BEGIN; - -DROP FUNCTION app_jobs.complete_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/do_notify.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/do_notify.sql deleted file mode 100644 index 58a8138a1..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/do_notify.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/do_notify from pg - -BEGIN; - -DROP FUNCTION app_jobs.do_notify; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/fail_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/fail_job.sql deleted file mode 100644 index ed96e401e..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/fail_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/fail_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.fail_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/get_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/get_job.sql deleted file mode 100644 index 469f6b4da..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/get_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/get_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.get_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/get_scheduled_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/get_scheduled_job.sql deleted file mode 100644 index f41f8fdb4..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/get_scheduled_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/get_scheduled_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.get_scheduled_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/permanently_fail_jobs.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/permanently_fail_jobs.sql deleted file mode 100644 index f0299ea82..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/permanently_fail_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/permanently_fail_jobs from pg - -BEGIN; - -DROP FUNCTION app_jobs.permanently_fail_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/release_jobs.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/release_jobs.sql deleted file mode 100644 index 8ece69ef1..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/release_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/release_jobs from pg - -BEGIN; - -DROP FUNCTION app_jobs.release_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/release_scheduled_jobs.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/release_scheduled_jobs.sql deleted file mode 100644 index a16e6e9a4..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/release_scheduled_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/release_scheduled_jobs from pg - -BEGIN; - -DROP FUNCTION app_jobs.release_scheduled_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/reschedule_jobs.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/reschedule_jobs.sql deleted file mode 100644 index 34a441716..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/reschedule_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/reschedule_jobs from pg - -BEGIN; - -DROP FUNCTION app_jobs.reschedule_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/run_scheduled_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/run_scheduled_job.sql deleted file mode 100644 index 77886fc04..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/procedures/run_scheduled_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/procedures/run_scheduled_job from pg - -BEGIN; - -DROP FUNCTION app_jobs.run_scheduled_job; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/schema.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/schema.sql deleted file mode 100644 index 2b238d0fe..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/schema.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/schema from pg - -BEGIN; - -DROP SCHEMA app_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index 06a833789..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator from pg - -BEGIN; - -REVOKE SELECT, INSERT, UPDATE, DELETE ON TABLE app_jobs.job_queues FROM administrator; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql deleted file mode 100644 index 20290a2a1..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx from pg - -BEGIN; - -DROP INDEX app_jobs.job_queues_locked_by_idx; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/table.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/table.sql deleted file mode 100644 index 79c62cbcc..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/job_queues/table.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/job_queues/table from pg - -BEGIN; - -DROP TABLE app_jobs.job_queues; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index c67b07e27..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator from pg - -BEGIN; - -REVOKE SELECT, INSERT, UPDATE, DELETE ON TABLE app_jobs.jobs FROM administrator; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql deleted file mode 100644 index f26cb13e2..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx from pg - -BEGIN; - -DROP INDEX app_jobs.jobs_locked_by_idx; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql deleted file mode 100644 index 24fa09ac6..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx from pg - -BEGIN; - -DROP INDEX app_jobs.priority_run_at_id_idx; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/table.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/table.sql deleted file mode 100644 index b4156ad3e..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/table.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/table from pg - -BEGIN; - -DROP TABLE app_jobs.jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql deleted file mode 100644 index bf4f88c6f..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count from pg -BEGIN; -DROP TRIGGER decrease_job_queue_count_on_delete ON app_jobs.jobs; -DROP TRIGGER decrease_job_queue_count_on_update ON app_jobs.jobs; -DROP FUNCTION app_jobs.tg_decrease_job_queue_count; -COMMIT; - diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql deleted file mode 100644 index 5098a6517..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count from pg -BEGIN; -DROP TRIGGER _500_increase_job_queue_count_on_insert ON app_jobs.jobs; -DROP TRIGGER _500_increase_job_queue_count_on_update ON app_jobs.jobs; -DROP FUNCTION app_jobs.tg_increase_job_queue_count; -COMMIT; - diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql deleted file mode 100644 index 612a02874..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql +++ /dev/null @@ -1,5 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/triggers/notify_worker from pg -BEGIN; -DROP TRIGGER _900_notify_worker ON app_jobs.jobs; -COMMIT; - diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/timestamps.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/timestamps.sql deleted file mode 100644 index 7dc2f048c..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/jobs/triggers/timestamps.sql +++ /dev/null @@ -1,9 +0,0 @@ --- Revert schemas/app_jobs/tables/jobs/triggers/timestamps from pg -BEGIN; -ALTER TABLE app_jobs.jobs - DROP COLUMN created_at; -ALTER TABLE app_jobs.jobs - DROP COLUMN updated_at; -DROP TRIGGER _100_update_jobs_modtime_tg ON app_jobs.jobs; -COMMIT; - diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index 0990e98d6..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator from pg - -BEGIN; - -REVOKE SELECT, INSERT, UPDATE, DELETE ON TABLE app_jobs.scheduled_jobs FROM administrator; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql deleted file mode 100644 index 5ff1e6d50..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx from pg - -BEGIN; - -DROP INDEX app_jobs.scheduled_jobs_locked_by_idx; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql deleted file mode 100644 index be4b58783..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx from pg - -BEGIN; - -DROP INDEX app_jobs.scheduled_jobs_priority_id_idx; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/table.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/table.sql deleted file mode 100644 index 3a06f0da8..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/table.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/tables/scheduled_jobs/table from pg - -BEGIN; - -DROP TABLE app_jobs.scheduled_jobs; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql deleted file mode 100644 index 5c1852c7a..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Revert schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job from pg - -BEGIN; - -DROP TRIGGER _900_notify_scheduled_job ON app_jobs.scheduled_jobs; - - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_fields.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_fields.sql deleted file mode 100644 index 5384edfc3..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_fields.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/triggers/tg_add_job_with_fields from pg - -BEGIN; - -DROP FUNCTION app_jobs.trigger_job_with_fields; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_row.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_row.sql deleted file mode 100644 index 9d6b68a2c..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_row.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/triggers/tg_add_job_with_row from pg - -BEGIN; - -DROP FUNCTION app_jobs.tg_add_job_with_row; - -COMMIT; diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql deleted file mode 100644 index 1f0fb04be..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql +++ /dev/null @@ -1,5 +0,0 @@ --- Revert schemas/app_jobs/triggers/tg_add_job_with_row_id from pg -BEGIN; -DROP FUNCTION app_jobs.tg_add_job_with_row_id; -COMMIT; - diff --git a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_update_timestamps.sql b/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_update_timestamps.sql deleted file mode 100644 index 37378b148..000000000 --- a/packages/database-jobs-v1/revert/schemas/app_jobs/triggers/tg_update_timestamps.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Revert schemas/app_jobs/triggers/tg_update_timestamps from pg - -BEGIN; - -DROP FUNCTION app_jobs.tg_update_timestamps; - -COMMIT; diff --git a/packages/database-jobs-v1/sql/pgpm-database-jobs--0.15.3.sql b/packages/database-jobs-v1/sql/pgpm-database-jobs--0.15.3.sql deleted file mode 100644 index 73c98278a..000000000 --- a/packages/database-jobs-v1/sql/pgpm-database-jobs--0.15.3.sql +++ /dev/null @@ -1,805 +0,0 @@ -\echo Use "CREATE EXTENSION pgpm-database-jobs" to load this file. \quit -CREATE SCHEMA IF NOT EXISTS app_jobs; - -GRANT USAGE ON SCHEMA app_jobs TO administrator; - -ALTER DEFAULT PRIVILEGES IN SCHEMA app_jobs - GRANT EXECUTE ON FUNCTIONS TO administrator; - -CREATE FUNCTION app_jobs.tg_update_timestamps() RETURNS trigger AS $EOFCODE$ -BEGIN - IF TG_OP = 'INSERT' THEN - NEW.created_at = NOW(); - NEW.updated_at = NOW(); - ELSIF TG_OP = 'UPDATE' THEN - NEW.created_at = OLD.created_at; - NEW.updated_at = greatest (now(), OLD.updated_at + interval '1 millisecond'); - END IF; - RETURN NEW; -END; -$EOFCODE$ LANGUAGE plpgsql; - -CREATE FUNCTION app_jobs.tg_add_job_with_row_id() RETURNS trigger AS $EOFCODE$ -BEGIN - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), tg_argv[0], json_build_object('id', NEW.id)); - RETURN NEW; - END IF; - IF (TG_OP = 'DELETE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), tg_argv[0], json_build_object('id', OLD.id)); - RETURN OLD; - END IF; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE SECURITY DEFINER; - -COMMENT ON FUNCTION app_jobs.tg_add_job_with_row_id IS 'Useful shortcut to create a job on insert or update. Pass the task name as the trigger argument, and the record id will automatically be available on the JSON payload.'; - -CREATE FUNCTION app_jobs.tg_add_job_with_row() RETURNS trigger AS $EOFCODE$ -BEGIN - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), TG_ARGV[0], to_json(NEW)); - RETURN NEW; - END IF; - IF (TG_OP = 'DELETE') THEN - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), TG_ARGV[0], to_json(OLD)); - RETURN OLD; - END IF; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE SECURITY DEFINER; - -COMMENT ON FUNCTION app_jobs.tg_add_job_with_row IS 'Useful shortcut to create a job on insert or update. Pass the task name as the trigger argument, and the record data will automatically be available on the JSON payload.'; - -CREATE FUNCTION app_jobs.json_build_object_apply(arguments text[]) RETURNS pg_catalog.json AS $EOFCODE$ -DECLARE - arg text; - _sql text; - _res json; - args text[]; -BEGIN - _sql = 'SELECT json_build_object('; - FOR arg IN - SELECT - unnest(arguments) - LOOP - args = array_append(args, format('''%s''', arg)); - END LOOP; - _sql = _sql || format('%s);', array_to_string(args, ',')); - EXECUTE _sql INTO _res; - RETURN _res; -END; -$EOFCODE$ LANGUAGE plpgsql; - -CREATE FUNCTION app_jobs.trigger_job_with_fields() RETURNS trigger AS $EOFCODE$ -DECLARE - arg text; - fn text; - i int; - args text[]; -BEGIN - FOR i IN - SELECT - * - FROM - generate_series(1, TG_NARGS) g (i) - LOOP - IF (i = 1) THEN - fn = TG_ARGV[i - 1]; - ELSE - args = array_append(args, TG_ARGV[i - 1]); - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - EXECUTE format('SELECT ($1).%s::text', TG_ARGV[i - 1]) - USING NEW INTO arg; - END IF; - IF (TG_OP = 'DELETE') THEN - EXECUTE format('SELECT ($1).%s::text', TG_ARGV[i - 1]) - USING OLD INTO arg; - END IF; - args = array_append(args, arg); - END IF; - END LOOP; - PERFORM - app_jobs.add_job (jwt_private.current_database_id(), fn, app_jobs.json_build_object_apply (args)); - IF (TG_OP = 'INSERT' OR TG_OP = 'UPDATE') THEN - RETURN NEW; - END IF; - IF (TG_OP = 'DELETE') THEN - RETURN OLD; - END IF; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE SECURITY DEFINER; - -CREATE TABLE app_jobs.scheduled_jobs ( - id bigserial PRIMARY KEY, - database_id uuid NOT NULL, - queue_name text DEFAULT (public.gen_random_uuid())::text, - task_identifier text NOT NULL, - payload pg_catalog.json DEFAULT '{}'::json NOT NULL, - priority int DEFAULT 0 NOT NULL, - max_attempts int DEFAULT 25 NOT NULL, - key text, - locked_at timestamptz, - locked_by text, - schedule_info pg_catalog.json NOT NULL, - last_scheduled timestamptz, - last_scheduled_id bigint, - CHECK (length(key) < 513), - CHECK (length(task_identifier) < 127), - CHECK (max_attempts > 0), - CHECK (length(queue_name) < 127), - CHECK (length(locked_by) > 3), - UNIQUE (key) -); - -COMMENT ON TABLE app_jobs.scheduled_jobs IS 'Recurring/cron-style job definitions with database scoping: each row spawns jobs on a schedule for a specific database'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.id IS 'Auto-incrementing scheduled job identifier'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.database_id IS 'Database this scheduled job belongs to, for multi-tenant isolation'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.queue_name IS 'Name of the queue spawned jobs are placed into'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.task_identifier IS 'Task type identifier for spawned jobs'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.payload IS 'JSON payload passed to each spawned job'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.priority IS 'Priority assigned to spawned jobs (lower = higher priority)'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.max_attempts IS 'Max retry attempts for spawned jobs'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.key IS 'Optional unique deduplication key'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.locked_at IS 'Timestamp when the scheduler locked this record for processing'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.locked_by IS 'Identifier of the scheduler worker holding the lock'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.schedule_info IS 'JSON schedule configuration (e.g. cron expression, interval)'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.last_scheduled IS 'Timestamp when a job was last spawned from this schedule'; -COMMENT ON COLUMN app_jobs.scheduled_jobs.last_scheduled_id IS 'ID of the last job spawned from this schedule'; - -CREATE FUNCTION app_jobs.do_notify() RETURNS trigger AS $EOFCODE$ -BEGIN - PERFORM - pg_notify(TG_ARGV[0], ''); - RETURN NEW; -END; -$EOFCODE$ LANGUAGE plpgsql; - -CREATE TRIGGER _900_notify_scheduled_job - AFTER INSERT - ON app_jobs.scheduled_jobs - FOR EACH ROW - EXECUTE PROCEDURE app_jobs.do_notify('scheduled_jobs:insert'); - -CREATE INDEX scheduled_jobs_priority_id_idx ON app_jobs.scheduled_jobs (priority, id); - -CREATE INDEX scheduled_jobs_locked_by_idx ON app_jobs.scheduled_jobs (locked_by); - -GRANT SELECT, INSERT, UPDATE, DELETE ON app_jobs.scheduled_jobs TO administrator; - -CREATE TABLE app_jobs.jobs ( - id bigserial PRIMARY KEY, - database_id uuid NOT NULL, - queue_name text DEFAULT (public.gen_random_uuid())::text, - task_identifier text NOT NULL, - payload pg_catalog.json DEFAULT '{}'::json NOT NULL, - priority int DEFAULT 0 NOT NULL, - run_at timestamptz DEFAULT now() NOT NULL, - attempts int DEFAULT 0 NOT NULL, - max_attempts int DEFAULT 25 NOT NULL, - key text, - last_error text, - locked_at timestamptz, - locked_by text, - CHECK (length(key) < 513), - CHECK (length(task_identifier) < 127), - CHECK (max_attempts > 0), - CHECK (length(queue_name) < 127), - CHECK (length(locked_by) > 3), - UNIQUE (key) -); - -COMMENT ON TABLE app_jobs.jobs IS 'Background job queue with database scoping: each row is a pending or in-progress task for a specific database'; -COMMENT ON COLUMN app_jobs.jobs.id IS 'Auto-incrementing job identifier'; -COMMENT ON COLUMN app_jobs.jobs.database_id IS 'Database this job belongs to, for multi-tenant job isolation'; -COMMENT ON COLUMN app_jobs.jobs.queue_name IS 'Name of the queue this job belongs to; used for worker routing and concurrency control'; -COMMENT ON COLUMN app_jobs.jobs.task_identifier IS 'Identifier for the task type (maps to a worker handler function)'; -COMMENT ON COLUMN app_jobs.jobs.payload IS 'JSON payload of arguments passed to the task handler'; -COMMENT ON COLUMN app_jobs.jobs.priority IS 'Execution priority; lower numbers run first (default 0)'; -COMMENT ON COLUMN app_jobs.jobs.run_at IS 'Earliest time this job should be executed; used for delayed/scheduled execution'; -COMMENT ON COLUMN app_jobs.jobs.attempts IS 'Number of times this job has been attempted so far'; -COMMENT ON COLUMN app_jobs.jobs.max_attempts IS 'Maximum retry attempts before the job is considered permanently failed'; -COMMENT ON COLUMN app_jobs.jobs.key IS 'Optional unique deduplication key; prevents duplicate jobs with the same key'; -COMMENT ON COLUMN app_jobs.jobs.last_error IS 'Error message from the most recent failed attempt'; -COMMENT ON COLUMN app_jobs.jobs.locked_at IS 'Timestamp when a worker locked this job for processing'; -COMMENT ON COLUMN app_jobs.jobs.locked_by IS 'Identifier of the worker that currently holds the lock'; - -ALTER TABLE app_jobs.jobs - ADD COLUMN created_at timestamptz; - -ALTER TABLE app_jobs.jobs - ALTER COLUMN created_at SET DEFAULT now(); - -ALTER TABLE app_jobs.jobs - ADD COLUMN updated_at timestamptz; - -ALTER TABLE app_jobs.jobs - ALTER COLUMN updated_at SET DEFAULT now(); - -CREATE TRIGGER _100_update_jobs_modtime_tg - BEFORE INSERT OR UPDATE - ON app_jobs.jobs - FOR EACH ROW - EXECUTE PROCEDURE app_jobs.tg_update_timestamps(); - -CREATE FUNCTION app_jobs.tg_increase_job_queue_count() RETURNS trigger AS $EOFCODE$ -BEGIN - INSERT INTO app_jobs.job_queues (queue_name, job_count) - VALUES (NEW.queue_name, 1) - ON CONFLICT (queue_name) - DO UPDATE SET - job_count = job_queues.job_count + 1; - RETURN NEW; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE; - -CREATE TRIGGER _500_increase_job_queue_count_on_insert - AFTER INSERT - ON app_jobs.jobs - FOR EACH ROW - WHEN (new.queue_name IS NOT NULL) - EXECUTE PROCEDURE app_jobs.tg_increase_job_queue_count(); - -CREATE TRIGGER _500_increase_job_queue_count_on_update - AFTER UPDATE OF queue_name - ON app_jobs.jobs - FOR EACH ROW - WHEN (new.queue_name IS DISTINCT FROM old.queue_name - AND new.queue_name IS NOT NULL) - EXECUTE PROCEDURE app_jobs.tg_increase_job_queue_count(); - -CREATE TRIGGER _900_notify_worker - AFTER INSERT - ON app_jobs.jobs - FOR EACH ROW - EXECUTE PROCEDURE app_jobs.do_notify('jobs:insert'); - -CREATE FUNCTION app_jobs.tg_decrease_job_queue_count() RETURNS trigger AS $EOFCODE$ -DECLARE - v_new_job_count int; -BEGIN - UPDATE - app_jobs.job_queues - SET - job_count = job_queues.job_count - 1 - WHERE - queue_name = OLD.queue_name - RETURNING - job_count INTO v_new_job_count; - IF v_new_job_count <= 0 THEN - DELETE FROM app_jobs.job_queues - WHERE queue_name = OLD.queue_name - AND job_count <= 0; - END IF; - RETURN OLD; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE; - -CREATE TRIGGER decrease_job_queue_count_on_delete - AFTER DELETE - ON app_jobs.jobs - FOR EACH ROW - WHEN (old.queue_name IS NOT NULL) - EXECUTE PROCEDURE app_jobs.tg_decrease_job_queue_count(); - -CREATE TRIGGER decrease_job_queue_count_on_update - AFTER UPDATE OF queue_name - ON app_jobs.jobs - FOR EACH ROW - WHEN (new.queue_name IS DISTINCT FROM old.queue_name - AND old.queue_name IS NOT NULL) - EXECUTE PROCEDURE app_jobs.tg_decrease_job_queue_count(); - -CREATE INDEX priority_run_at_id_idx ON app_jobs.jobs (priority, run_at, id); - -CREATE INDEX jobs_locked_by_idx ON app_jobs.jobs (locked_by); - -GRANT SELECT, INSERT, UPDATE, DELETE ON app_jobs.jobs TO administrator; - -CREATE TABLE app_jobs.job_queues ( - queue_name text NOT NULL PRIMARY KEY, - job_count int DEFAULT 0 NOT NULL, - locked_at timestamptz, - locked_by text -); - -COMMENT ON TABLE app_jobs.job_queues IS 'Queue metadata: tracks job counts and locking state for each named queue'; -COMMENT ON COLUMN app_jobs.job_queues.queue_name IS 'Unique name identifying this queue'; -COMMENT ON COLUMN app_jobs.job_queues.job_count IS 'Number of pending jobs in this queue'; -COMMENT ON COLUMN app_jobs.job_queues.locked_at IS 'Timestamp when this queue was locked for batch processing'; -COMMENT ON COLUMN app_jobs.job_queues.locked_by IS 'Identifier of the worker that currently holds the queue lock'; - -CREATE INDEX job_queues_locked_by_idx ON app_jobs.job_queues (locked_by); - -GRANT SELECT, INSERT, UPDATE, DELETE ON app_jobs.job_queues TO administrator; - -CREATE FUNCTION app_jobs.run_scheduled_job(id bigint, job_expiry interval DEFAULT '1 hours') RETURNS app_jobs.jobs AS $EOFCODE$ -DECLARE - j app_jobs.jobs; - last_id bigint; - lkd_by text; -BEGIN - -- check last scheduled - SELECT - last_scheduled_id - FROM - app_jobs.scheduled_jobs s - WHERE - s.id = run_scheduled_job.id INTO last_id; - - -- if it's been scheduled check if it's been run - - IF (last_id IS NOT NULL) THEN - SELECT - locked_by - FROM - app_jobs.jobs js - WHERE - js.id = last_id - AND (js.locked_at IS NULL -- never been run - OR js.locked_at >= (NOW() - job_expiry) - -- still running within a safe interval -) INTO lkd_by; - IF (FOUND) THEN - RAISE EXCEPTION 'ALREADY_SCHEDULED'; - END IF; - END IF; - - -- insert new job - INSERT INTO app_jobs.jobs ( - database_id, - queue_name, - task_identifier, - payload, - priority, - max_attempts, - key - ) SELECT - database_id, - queue_name, - task_identifier, - payload, - priority, - max_attempts, - key - FROM - app_jobs.scheduled_jobs s - WHERE - s.id = run_scheduled_job.id - RETURNING - * INTO j; - -- update the scheduled job - UPDATE - app_jobs.scheduled_jobs s - SET - last_scheduled = NOW(), - last_scheduled_id = j.id - WHERE - s.id = run_scheduled_job.id; - RETURN j; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE; - -CREATE FUNCTION app_jobs.reschedule_jobs(job_ids bigint[], run_at timestamptz DEFAULT NULL, priority int DEFAULT NULL, attempts int DEFAULT NULL, max_attempts int DEFAULT NULL) RETURNS SETOF app_jobs.jobs LANGUAGE sql AS $EOFCODE$ - UPDATE - app_jobs.jobs - SET - run_at = coalesce(reschedule_jobs.run_at, jobs.run_at), - priority = coalesce(reschedule_jobs.priority, jobs.priority), - attempts = coalesce(reschedule_jobs.attempts, jobs.attempts), - max_attempts = coalesce(reschedule_jobs.max_attempts, jobs.max_attempts) - WHERE - id = ANY (job_ids) - AND (locked_by IS NULL - OR locked_at < NOW() - interval '4 hours') - RETURNING - *; -$EOFCODE$; - -CREATE FUNCTION app_jobs.release_scheduled_jobs(worker_id text, ids bigint[] DEFAULT NULL) RETURNS void AS $EOFCODE$ -DECLARE -BEGIN - -- clear the scheduled job - UPDATE - app_jobs.scheduled_jobs s - SET - locked_at = NULL, - locked_by = NULL - WHERE - locked_by = worker_id - AND (ids IS NULL - OR s.id = ANY (ids)); -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE; - -CREATE FUNCTION app_jobs.release_jobs(worker_id text) RETURNS void AS $EOFCODE$ -DECLARE -BEGIN - -- clear the job - UPDATE - app_jobs.jobs - SET - locked_at = NULL, - locked_by = NULL, - attempts = GREATEST (attempts - 1, 0) - WHERE - locked_by = worker_id; - -- clear the queue - UPDATE - app_jobs.job_queues - SET - locked_at = NULL, - locked_by = NULL - WHERE - locked_by = worker_id; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE; - -CREATE FUNCTION app_jobs.permanently_fail_jobs(job_ids bigint[], error_message text DEFAULT NULL) RETURNS SETOF app_jobs.jobs LANGUAGE sql AS $EOFCODE$ - UPDATE - app_jobs.jobs - SET - last_error = coalesce(error_message, 'Manually marked as failed'), - attempts = max_attempts - WHERE - id = ANY (job_ids) - AND (locked_by IS NULL - OR locked_at < NOW() - interval '4 hours') - RETURNING - *; -$EOFCODE$; - -CREATE FUNCTION app_jobs.get_scheduled_job(worker_id text, task_identifiers text[] DEFAULT NULL) RETURNS app_jobs.scheduled_jobs LANGUAGE plpgsql AS $EOFCODE$ -DECLARE - v_job_id bigint; - v_row app_jobs.scheduled_jobs; -BEGIN - - -- - - IF worker_id IS NULL THEN - RAISE exception 'INVALID_WORKER_ID'; - END IF; - - -- - - SELECT - scheduled_jobs.id INTO v_job_id - FROM - app_jobs.scheduled_jobs - WHERE (scheduled_jobs.locked_at IS NULL) - AND (task_identifiers IS NULL - OR task_identifier = ANY (task_identifiers)) - ORDER BY - priority ASC, - id ASC - LIMIT 1 - FOR UPDATE - SKIP LOCKED; - - -- - - IF v_job_id IS NULL THEN - RETURN NULL; - END IF; - - -- - - UPDATE - app_jobs.scheduled_jobs - SET - locked_by = worker_id, - locked_at = NOW() - WHERE - id = v_job_id - RETURNING - * INTO v_row; - - -- - - RETURN v_row; -END; -$EOFCODE$; - -CREATE FUNCTION app_jobs.get_job(worker_id text, task_identifiers text[] DEFAULT NULL, job_expiry interval DEFAULT '4 hours') RETURNS app_jobs.jobs LANGUAGE plpgsql AS $EOFCODE$ -DECLARE - v_job_id bigint; - v_queue_name text; - v_row app_jobs.jobs; - v_now timestamptz = now(); -BEGIN - - IF worker_id IS NULL THEN - RAISE exception 'INVALID_WORKER_ID'; - END IF; - - -- - - SELECT - jobs.queue_name, - jobs.id INTO v_queue_name, - v_job_id - FROM - app_jobs.jobs - WHERE (jobs.locked_at IS NULL - OR jobs.locked_at < (v_now - job_expiry)) - AND (jobs.queue_name IS NULL - OR EXISTS ( - SELECT - 1 - FROM - app_jobs.job_queues - WHERE - job_queues.queue_name = jobs.queue_name - AND (job_queues.locked_at IS NULL - OR job_queues.locked_at < (v_now - job_expiry)) - FOR UPDATE - SKIP LOCKED)) - AND run_at <= v_now - AND attempts < max_attempts - AND (task_identifiers IS NULL - OR task_identifier = ANY (task_identifiers)) - ORDER BY - priority ASC, - run_at ASC, - id ASC - LIMIT 1 - FOR UPDATE - SKIP LOCKED; - - -- - - IF v_job_id IS NULL THEN - RETURN NULL; - END IF; - - -- - - IF v_queue_name IS NOT NULL THEN - UPDATE - app_jobs.job_queues - SET - locked_by = worker_id, - locked_at = v_now - WHERE - job_queues.queue_name = v_queue_name; - END IF; - - -- - - UPDATE - app_jobs.jobs - SET - attempts = attempts + 1, - locked_by = worker_id, - locked_at = v_now - WHERE - id = v_job_id - RETURNING - * INTO v_row; - - -- - RETURN v_row; -END; -$EOFCODE$; - -CREATE FUNCTION app_jobs.fail_job(worker_id text, job_id bigint, error_message text) RETURNS app_jobs.jobs LANGUAGE plpgsql STRICT AS $EOFCODE$ -DECLARE - v_row app_jobs.jobs; -BEGIN - UPDATE - app_jobs.jobs - SET - last_error = error_message, - run_at = greatest (now(), run_at) + (exp(least (attempts, 10))::text || ' seconds')::interval, - locked_by = NULL, - locked_at = NULL - WHERE - id = job_id - AND locked_by = worker_id - RETURNING - * INTO v_row; - IF v_row.queue_name IS NOT NULL THEN - UPDATE - app_jobs.job_queues - SET - locked_by = NULL, - locked_at = NULL - WHERE - queue_name = v_row.queue_name - AND locked_by = worker_id; - END IF; - RETURN v_row; -END; -$EOFCODE$; - -CREATE FUNCTION app_jobs.complete_jobs(job_ids bigint[]) RETURNS SETOF app_jobs.jobs LANGUAGE sql AS $EOFCODE$ - DELETE FROM app_jobs.jobs - WHERE id = ANY (job_ids) - AND (locked_by IS NULL - OR locked_at < NOW() - interval '4 hours') - RETURNING - *; -$EOFCODE$; - -CREATE FUNCTION app_jobs.complete_job(worker_id text, job_id bigint) RETURNS app_jobs.jobs LANGUAGE plpgsql AS $EOFCODE$ -DECLARE - v_row app_jobs.jobs; -BEGIN - DELETE FROM app_jobs.jobs - WHERE id = job_id - RETURNING - * INTO v_row; - IF v_row.queue_name IS NOT NULL THEN - UPDATE - app_jobs.job_queues - SET - locked_by = NULL, - locked_at = NULL - WHERE - queue_name = v_row.queue_name - AND locked_by = worker_id; - END IF; - RETURN v_row; -END; -$EOFCODE$; - -CREATE FUNCTION app_jobs.add_scheduled_job(db_id uuid, identifier text, payload pg_catalog.json DEFAULT '{}'::json, schedule_info pg_catalog.json DEFAULT '{}'::json, job_key text DEFAULT NULL, queue_name text DEFAULT NULL, max_attempts int DEFAULT 25, priority int DEFAULT 0) RETURNS app_jobs.scheduled_jobs AS $EOFCODE$ -DECLARE - v_job app_jobs.scheduled_jobs; -BEGIN - IF job_key IS NOT NULL THEN - - -- Upsert job - INSERT INTO app_jobs.scheduled_jobs ( - database_id, - task_identifier, - payload, - queue_name, - schedule_info, - max_attempts, - key, - priority - ) VALUES ( - db_id, - identifier, - coalesce(payload, '{}'::json), - queue_name, - schedule_info, - coalesce(max_attempts, 25), - job_key, - coalesce(priority, 0) - ) - ON CONFLICT (key) - DO UPDATE SET - task_identifier = EXCLUDED.task_identifier, - payload = EXCLUDED.payload, - queue_name = EXCLUDED.queue_name, - max_attempts = EXCLUDED.max_attempts, - schedule_info = EXCLUDED.schedule_info, - priority = EXCLUDED.priority - WHERE - scheduled_jobs.locked_at IS NULL - RETURNING - * INTO v_job; - - -- If upsert succeeded (insert or update), return early - - IF NOT (v_job IS NULL) THEN - RETURN v_job; - END IF; - - -- Upsert failed -> there must be an existing scheduled job that is locked. Remove - -- and allow a new one to be inserted - - DELETE FROM - app_jobs.scheduled_jobs - WHERE - KEY = job_key; - END IF; - - INSERT INTO app_jobs.scheduled_jobs ( - database_id, - task_identifier, - payload, - queue_name, - schedule_info, - max_attempts, - priority - ) VALUES ( - db_id, - identifier, - payload, - queue_name, - schedule_info, - max_attempts, - priority - ) RETURNING * INTO v_job; - RETURN v_job; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE SECURITY DEFINER; - -CREATE FUNCTION app_jobs.add_job(db_id uuid, identifier text, payload pg_catalog.json DEFAULT '{}'::json, job_key text DEFAULT NULL, queue_name text DEFAULT NULL, run_at timestamptz DEFAULT now(), max_attempts int DEFAULT 25, priority int DEFAULT 0) RETURNS app_jobs.jobs AS $EOFCODE$ -DECLARE - v_job app_jobs.jobs; -BEGIN - IF job_key IS NOT NULL THEN - -- Upsert job - INSERT INTO app_jobs.jobs ( - database_id, - task_identifier, - payload, - queue_name, - run_at, - max_attempts, - key, - priority - ) VALUES ( - db_id, - identifier, - coalesce(payload, - '{}'::json), - queue_name, - coalesce(run_at, now()), - coalesce(max_attempts, 25), - job_key, - coalesce(priority, 0) - ) - ON CONFLICT (key) - DO UPDATE SET - task_identifier = EXCLUDED.task_identifier, - payload = EXCLUDED.payload, - queue_name = EXCLUDED.queue_name, - max_attempts = EXCLUDED.max_attempts, - run_at = EXCLUDED.run_at, - priority = EXCLUDED.priority, - -- always reset error/retry state - attempts = 0, last_error = NULL - WHERE - jobs.locked_at IS NULL - RETURNING - * INTO v_job; - - -- If upsert succeeded (insert or update), return early - - IF NOT (v_job IS NULL) THEN - RETURN v_job; - END IF; - - -- Upsert failed -> there must be an existing job that is locked. Remove - -- existing key to allow a new one to be inserted, and prevent any - -- subsequent retries by bumping attempts to the max allowed. - - UPDATE - app_jobs.jobs - SET - KEY = NULL, - attempts = jobs.max_attempts - WHERE - KEY = job_key; - END IF; - - INSERT INTO app_jobs.jobs ( - database_id, - task_identifier, - payload, - queue_name, - run_at, - max_attempts, - priority - ) VALUES ( - db_id, - identifier, - payload, - queue_name, - run_at, - max_attempts, - priority - ) - RETURNING * INTO v_job; - - RETURN v_job; -END; -$EOFCODE$ LANGUAGE plpgsql VOLATILE SECURITY DEFINER; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/helpers/json_build_object_apply.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/helpers/json_build_object_apply.sql deleted file mode 100644 index e05072cfb..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/helpers/json_build_object_apply.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/helpers/json_build_object_apply on pg - -BEGIN; - -SELECT verify_function ('app_jobs.json_build_object_apply'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/add_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/add_job.sql deleted file mode 100644 index c841e7d04..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/add_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/add_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.add_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/add_scheduled_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/add_scheduled_job.sql deleted file mode 100644 index a2f7d4815..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/add_scheduled_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/add_scheduled_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.add_scheduled_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/complete_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/complete_job.sql deleted file mode 100644 index 4bd179aee..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/complete_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/complete_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.complete_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/complete_jobs.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/complete_jobs.sql deleted file mode 100644 index aa9a5a457..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/complete_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/complete_jobs on pg - -BEGIN; - -SELECT verify_function ('app_jobs.complete_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/do_notify.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/do_notify.sql deleted file mode 100644 index df64a9f48..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/do_notify.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/do_notify on pg - -BEGIN; - -SELECT verify_function ('app_jobs.do_notify'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/fail_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/fail_job.sql deleted file mode 100644 index b9c65b489..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/fail_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/fail_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.fail_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/get_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/get_job.sql deleted file mode 100644 index 86170be11..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/get_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/get_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.get_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/get_scheduled_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/get_scheduled_job.sql deleted file mode 100644 index bb7e58d7f..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/get_scheduled_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/get_scheduled_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.get_scheduled_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/permanently_fail_jobs.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/permanently_fail_jobs.sql deleted file mode 100644 index dfd8852f0..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/permanently_fail_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/permanently_fail_jobs on pg - -BEGIN; - -SELECT verify_function ('app_jobs.permanently_fail_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/release_jobs.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/release_jobs.sql deleted file mode 100644 index 70004e7e1..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/release_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/release_jobs on pg - -BEGIN; - -SELECT verify_function ('app_jobs.release_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/release_scheduled_jobs.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/release_scheduled_jobs.sql deleted file mode 100644 index 5b9b5929a..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/release_scheduled_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/release_scheduled_jobs on pg - -BEGIN; - -SELECT verify_function ('app_jobs.release_scheduled_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/reschedule_jobs.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/reschedule_jobs.sql deleted file mode 100644 index 80ab587b3..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/reschedule_jobs.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/reschedule_jobs on pg - -BEGIN; - -SELECT verify_function ('app_jobs.reschedule_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/run_scheduled_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/run_scheduled_job.sql deleted file mode 100644 index 02257023b..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/procedures/run_scheduled_job.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/procedures/run_scheduled_job on pg - -BEGIN; - -SELECT verify_function ('app_jobs.run_scheduled_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/schema.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/schema.sql deleted file mode 100644 index 5e0b19d49..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/schema.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/schema on pg - -BEGIN; - -SELECT verify_schema ('app_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index d645d8558..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,10 +0,0 @@ --- Verify schemas/app_jobs/tables/job_queues/grants/grant_select_insert_update_delete_to_administrator on pg - -BEGIN; - - SELECT has_table_privilege('administrator', 'app_jobs.job_queues', 'SELECT'); - SELECT has_table_privilege('administrator', 'app_jobs.job_queues', 'INSERT'); - SELECT has_table_privilege('administrator', 'app_jobs.job_queues', 'UPDATE'); - SELECT has_table_privilege('administrator', 'app_jobs.job_queues', 'DELETE'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql deleted file mode 100644 index bb3786608..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/job_queues/indexes/job_queues_locked_by_idx on pg - -BEGIN; - -SELECT verify_index ('app_jobs.job_queues', 'job_queues_locked_by_idx'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/table.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/table.sql deleted file mode 100644 index 3a5e4b1cd..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/job_queues/table.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/job_queues/table on pg - -BEGIN; - -SELECT verify_table ('app_jobs.job_queues'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index 6255d7164..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,10 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/grants/grant_select_insert_update_delete_to_administrator on pg - -BEGIN; - - SELECT has_table_privilege('administrator', 'app_jobs.jobs', 'SELECT'); - SELECT has_table_privilege('administrator', 'app_jobs.jobs', 'INSERT'); - SELECT has_table_privilege('administrator', 'app_jobs.jobs', 'UPDATE'); - SELECT has_table_privilege('administrator', 'app_jobs.jobs', 'DELETE'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql deleted file mode 100644 index 3635677ae..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/indexes/jobs_locked_by_idx on pg - -BEGIN; - -SELECT verify_index ('app_jobs.jobs', 'jobs_locked_by_idx'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql deleted file mode 100644 index 2fc8b4ccd..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/indexes/priority_run_at_id_idx on pg - -BEGIN; - -SELECT verify_index ('app_jobs.jobs', 'priority_run_at_id_idx'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/table.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/table.sql deleted file mode 100644 index aaa0584da..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/table.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/table on pg - -BEGIN; - -SELECT verify_table ('app_jobs.jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql deleted file mode 100644 index 97b717d08..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count.sql +++ /dev/null @@ -1,10 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/triggers/decrease_job_queue_count on pg -BEGIN; -SELECT - verify_function ('app_jobs.tg_decrease_job_queue_count'); -SELECT - verify_trigger ('app_jobs.decrease_job_queue_count_on_delete'); -SELECT - verify_trigger ('app_jobs.decrease_job_queue_count_on_update'); -ROLLBACK; - diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql deleted file mode 100644 index a6e89dd17..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count.sql +++ /dev/null @@ -1,10 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/triggers/increase_job_queue_count on pg -BEGIN; -SELECT - verify_function ('app_jobs.tg_increase_job_queue_count'); -SELECT - verify_trigger ('app_jobs._500_increase_job_queue_count_on_insert'); -SELECT - verify_trigger ('app_jobs._500_increase_job_queue_count_on_update'); -ROLLBACK; - diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql deleted file mode 100644 index dc0436efa..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/notify_worker.sql +++ /dev/null @@ -1,6 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/triggers/notify_worker on pg -BEGIN; -SELECT - verify_trigger ('app_jobs._900_notify_worker'); -ROLLBACK; - diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/timestamps.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/timestamps.sql deleted file mode 100644 index ed9466a37..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/jobs/triggers/timestamps.sql +++ /dev/null @@ -1,16 +0,0 @@ --- Verify schemas/app_jobs/tables/jobs/triggers/timestamps on pg -BEGIN; -SELECT - created_at -FROM - app_jobs.jobs -LIMIT 1; -SELECT - updated_at -FROM - app_jobs.jobs -LIMIT 1; -SELECT - verify_trigger ('app_jobs._100_update_jobs_modtime_tg'); -ROLLBACK; - diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql deleted file mode 100644 index c4aa4eb6c..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator.sql +++ /dev/null @@ -1,10 +0,0 @@ --- Verify schemas/app_jobs/tables/scheduled_jobs/grants/grant_select_insert_update_delete_to_administrator on pg - -BEGIN; - - SELECT has_table_privilege('administrator', 'app_jobs.scheduled_jobs', 'SELECT'); - SELECT has_table_privilege('administrator', 'app_jobs.scheduled_jobs', 'INSERT'); - SELECT has_table_privilege('administrator', 'app_jobs.scheduled_jobs', 'UPDATE'); - SELECT has_table_privilege('administrator', 'app_jobs.scheduled_jobs', 'DELETE'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql deleted file mode 100644 index 34ee9f117..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_locked_by_idx on pg - -BEGIN; - -SELECT verify_index ('app_jobs.scheduled_jobs', 'scheduled_jobs_locked_by_idx'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql deleted file mode 100644 index d26a68223..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/scheduled_jobs/indexes/scheduled_jobs_priority_id_idx on pg - -BEGIN; - -SELECT verify_index ('app_jobs.scheduled_jobs', 'scheduled_jobs_priority_id_idx'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/table.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/table.sql deleted file mode 100644 index 065f427b1..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/table.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/tables/scheduled_jobs/table on pg - -BEGIN; - -SELECT verify_table ('app_jobs.scheduled_jobs'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql deleted file mode 100644 index 599c63a3a..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job.sql +++ /dev/null @@ -1,8 +0,0 @@ --- Verify schemas/app_jobs/tables/scheduled_jobs/triggers/notify_scheduled_job on pg - -BEGIN; - - -SELECT verify_trigger ('app_jobs._900_notify_scheduled_job'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_fields.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_fields.sql deleted file mode 100644 index 9b36e4f2e..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_fields.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/triggers/tg_add_job_with_fields on pg - -BEGIN; - -SELECT verify_function ('app_jobs.trigger_job_with_fields'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_row.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_row.sql deleted file mode 100644 index bdf8cc7eb..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_row.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/triggers/tg_add_job_with_row on pg - -BEGIN; - -SELECT verify_function ('app_jobs.tg_add_job_with_row'); - -ROLLBACK; diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql deleted file mode 100644 index 72b5a7b90..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_add_job_with_row_id.sql +++ /dev/null @@ -1,6 +0,0 @@ --- Verify schemas/app_jobs/triggers/tg_add_job_with_row_id on pg -BEGIN; -SELECT - verify_function ('app_jobs.tg_add_job_with_row_id'); -ROLLBACK; - diff --git a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_update_timestamps.sql b/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_update_timestamps.sql deleted file mode 100644 index fd53ed3e9..000000000 --- a/packages/database-jobs-v1/verify/schemas/app_jobs/triggers/tg_update_timestamps.sql +++ /dev/null @@ -1,7 +0,0 @@ --- Verify schemas/app_jobs/triggers/tg_update_timestamps on pg - -BEGIN; - -SELECT verify_function ('app_jobs.tg_update_timestamps'); - -ROLLBACK; diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index de16237ad..ca756ad1e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -99,16 +99,6 @@ importers: specifier: ^4.16.6 version: 4.16.6(@dataplan/json@1.0.0(grafast@1.0.0(graphql@16.13.0)))(@dataplan/pg@1.0.0(@dataplan/json@1.0.0(grafast@1.0.0(graphql@16.13.0)))(grafast@1.0.0(graphql@16.13.0))(graphile-config@1.0.0)(graphql@16.13.0)(pg-sql2@5.0.0)(pg@8.20.0))(@types/node@22.19.17)(grafserv@1.0.0(@types/node@22.19.17)(grafast@1.0.0(graphql@16.13.0))(graphile-config@1.0.0)(graphql@16.13.0)(react-dom@19.2.5(react@19.2.5))(react@19.2.5)(use-sync-external-store@1.6.0(react@19.2.5))(ws@8.20.0))(graphile-build@5.0.0(grafast@1.0.0(graphql@16.13.0))(graphile-config@1.0.0)(graphql@16.13.0))(pg-sql2@5.0.0)(react-dom@19.2.5(react@19.2.5))(react@19.2.5)(tamedevil@0.1.0)(use-sync-external-store@1.6.0(react@19.2.5))(ws@8.20.0) - packages/database-jobs-v1: - dependencies: - '@pgpm/verify': - specifier: workspace:* - version: link:../verify - devDependencies: - pgpm: - specifier: ^4.16.6 - version: 4.16.6(@dataplan/json@1.0.0(grafast@1.0.0(graphql@16.13.0)))(@dataplan/pg@1.0.0(@dataplan/json@1.0.0(grafast@1.0.0(graphql@16.13.0)))(grafast@1.0.0(graphql@16.13.0))(graphile-config@1.0.0)(graphql@16.13.0)(pg-sql2@5.0.0)(pg@8.20.0))(@types/node@22.19.17)(grafserv@1.0.0(@types/node@22.19.17)(grafast@1.0.0(graphql@16.13.0))(graphile-config@1.0.0)(graphql@16.13.0)(react-dom@19.2.5(react@19.2.5))(react@19.2.5)(use-sync-external-store@1.6.0(react@19.2.5))(ws@8.20.0))(graphile-build@5.0.0(grafast@1.0.0(graphql@16.13.0))(graphile-config@1.0.0)(graphql@16.13.0))(pg-sql2@5.0.0)(react-dom@19.2.5(react@19.2.5))(react@19.2.5)(tamedevil@0.1.0)(use-sync-external-store@1.6.0(react@19.2.5))(ws@8.20.0) - packages/defaults: dependencies: '@pgpm/verify':