lonnymq 0.0.12 → 0.0.14

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -1,16 +1,16 @@
1
- var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=Object.prototype.hasOwnProperty;var I=new WeakMap,Y=(e)=>{var t=I.get(e),s;if(t)return t;if(t=h({},"__esModule",{value:!0}),e&&typeof e==="object"||typeof e==="function")z(e).map((E)=>!W.call(t,E)&&h(t,E,{get:()=>e[E],enumerable:!(s=V(e,E))||s.enumerable}));return I.set(e,t),t};var X=(e,t)=>{for(var s in t)h(e,s,{get:t[s],enumerable:!0,configurable:!0,set:(E)=>t[s]=()=>E})};var ce={};X(ce,{queueEventDecode:()=>f,Queue:()=>L,MessageDequeueCommand:()=>o,MessageDeleteCommand:()=>i,MessageDeferCommand:()=>u,MessageCreateCommand:()=>m,ChannelPolicySetCommand:()=>c,ChannelPolicyClearCommand:()=>l});module.exports=Y(ce);var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),J=(e)=>({nodeType:"RAW",value:e}),K=(e)=>{return`'${e.replace(/'/g,"''")}'`},j=(e)=>{if(e===null)return"NULL";else if(typeof e==="string")return K(e);else if(typeof e==="number")return e.toString();else if(typeof e==="boolean")return e?"TRUE":"FALSE";else if(e instanceof Date)return`'${e.toISOString()}'`;else if(typeof e==="bigint")return e.toString();else throw new Error(`Unsupported value type: ${typeof e}`)},Z=(e)=>{return`"${e.replace(/"/g,'""')}"`},ee=(e)=>{if(e.nodeType==="VALUE")return j(e.value);else if(e.nodeType==="REF")return Z(e.value);else if(e.nodeType==="RAW")return e.value;else throw new Error("Unsupported SQL node type")};var a=(e,...t)=>{let s=[];for(let E=0;E<e.length;E+=1)if(s.push(e[E]),E<t.length)s.push(ee(t[E]));return J(s.join(""))};class l{schema;channelName;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(a`
2
- SELECT 1 FROM ${n(this.schema)}."channel_policy_clear"(
1
+ var{defineProperty:h,getOwnPropertyNames:W,getOwnPropertyDescriptor:Y}=Object,X=Object.prototype.hasOwnProperty;var U=new WeakMap,J=(e)=>{var t=U.get(e),n;if(t)return t;if(t=h({},"__esModule",{value:!0}),e&&typeof e==="object"||typeof e==="function")W(e).map((E)=>!X.call(t,E)&&h(t,E,{get:()=>e[E],enumerable:!(n=Y(e,E))||n.enumerable}));return U.set(e,t),t};var K=(e,t)=>{for(var n in t)h(e,n,{get:t[n],enumerable:!0,configurable:!0,set:(E)=>t[n]=()=>E})};var ie={};K(ie,{queueEventDecode:()=>x,Queue:()=>L,MessageHeartbeatCommand:()=>S,MessageDequeueCommand:()=>i,MessageDeleteCommand:()=>u,MessageDeferCommand:()=>o,MessageCreateCommand:()=>c,ChannelPolicySetCommand:()=>m,ChannelPolicyClearCommand:()=>l});module.exports=J(ie);var r=(e)=>({nodeType:"VALUE",value:e}),s=(e)=>({nodeType:"REF",value:e}),j=(e)=>({nodeType:"RAW",value:e}),Z=(e)=>{return`'${e.replace(/'/g,"''")}'`},ee=(e)=>{if(e===null)return"NULL";else if(typeof e==="string")return Z(e);else if(typeof e==="number")return e.toString();else if(typeof e==="boolean")return e?"TRUE":"FALSE";else if(e instanceof Date)return`'${e.toISOString()}'`;else if(typeof e==="bigint")return e.toString();else throw new Error(`Unsupported value type: ${typeof e}`)},te=(e)=>{return`"${e.replace(/"/g,'""')}"`},se=(e)=>{if(e.nodeType==="VALUE")return ee(e.value);else if(e.nodeType==="REF")return te(e.value);else if(e.nodeType==="RAW")return e.value;else throw new Error("Unsupported SQL node type")};var a=(e,...t)=>{let n=[];for(let E=0;E<e.length;E+=1)if(n.push(e[E]),E<t.length)n.push(se(t[E]));return j(n.join(""))};class l{schema;channelName;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(a`
2
+ SELECT 1 FROM ${s(this.schema)}."channel_policy_clear"(
3
3
  $1
4
4
  )
5
- `.value,[this.channelName])}}class c{schema;channelName;maxSize;maxConcurrency;releaseIntervalMs;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName;let t=e.maxConcurrency??null;this.maxConcurrency=t!==null?Math.max(0,t):null;let s=e.maxSize??null;this.maxSize=s!==null?Math.max(0,s):null;let E=e.releaseIntervalMs??null;this.releaseIntervalMs=E!==null?Math.max(0,E):null,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(a`
6
- SELECT 1 FROM ${n(this.schema)}."channel_policy_set"(
5
+ `.value,[this.channelName])}}class m{schema;channelName;maxSize;maxConcurrency;releaseIntervalMs;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName;let t=e.maxConcurrency??null;this.maxConcurrency=t!==null?Math.max(0,t):null;let n=e.maxSize??null;this.maxSize=n!==null?Math.max(0,n):null;let E=e.releaseIntervalMs??null;this.releaseIntervalMs=E!==null?Math.max(0,E):null,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(a`
6
+ SELECT 1 FROM ${s(this.schema)}."channel_policy_set"(
7
7
  $1,
8
8
  $2::INTEGER,
9
9
  $3::INTEGER,
10
10
  $4::INTEGER
11
11
  )
12
- `.value,[this.channelName,this.maxSize,this.maxConcurrency,this.releaseIntervalMs])}}var N=(e)=>{return e*1000},te=(e)=>{return N(e*60)},U=(e)=>{return te(e*60)};var d=N(0),O=U(1);var f=(e)=>{let t=JSON.parse(e);if(t.type===0)return{eventType:"MESSAGE_CREATED",id:t.id,delayMs:t.delay_ms};else if(t.type===1)return{eventType:"MESSAGE_DELETED",id:t.id};else if(t.type===2)return{eventType:"MESSAGE_DEFERRED",id:t.id,delayMs:t.delay_ms};else throw new Error("Unknown event type")};var x=require("node:crypto");class m{schema;channelName;name;content;lockMs;id;delayMs;createdAt;constructor(e){let t=e.name??null,s=e.lockMs===void 0?O:Math.max(0,e.lockMs),E=e.delayMs===void 0?d:e.delayMs;this.id=x.randomUUID(),this.schema=e.schema,this.channelName=e.channelName,this.content=e.content,this.name=t,this.lockMs=s,this.delayMs=E,this.createdAt=new Date}async execute(e){let t=await e.query(a`
13
- SELECT * FROM ${n(this.schema)}."message_create"(
12
+ `.value,[this.channelName,this.maxSize,this.maxConcurrency,this.releaseIntervalMs])}}var N=(e)=>{return e*1000},ne=(e)=>{return N(e*60)},O=(e)=>{return ne(e*60)};var d=N(0),f=O(1);var x=(e)=>{let t=JSON.parse(e);if(t.type===0)return{eventType:"MESSAGE_CREATED",id:t.id,delayMs:t.delay_ms};else if(t.type===1)return{eventType:"MESSAGE_DELETED",id:t.id};else if(t.type===2)return{eventType:"MESSAGE_DEFERRED",id:t.id,delayMs:t.delay_ms};else throw new Error("Unknown event type")};var G=require("node:crypto");class c{schema;channelName;name;content;lockMs;id;delayMs;createdAt;constructor(e){let t=e.name??null,n=e.lockMs===void 0?f:Math.max(0,e.lockMs),E=e.delayMs===void 0?d:e.delayMs;this.id=G.randomUUID(),this.schema=e.schema,this.channelName=e.channelName,this.content=e.content,this.name=t,this.lockMs=n,this.delayMs=E,this.createdAt=new Date}async execute(e){let t=await e.query(a`
13
+ SELECT * FROM ${s(this.schema)}."message_create"(
14
14
  $1,
15
15
  $2,
16
16
  $3,
@@ -18,27 +18,34 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
18
18
  $5::BIGINT,
19
19
  $6::BIGINT
20
20
  )
21
- `.value,[this.id,this.channelName,this.name,this.content,this.lockMs,this.delayMs]).then((s)=>s.rows[0]);if(t.result_code===1)return{resultType:"MESSAGE_DROPPED"};else if(t.result_code===2)return{resultType:"MESSAGE_DEDUPLICATED"};else if(t.result_code===0)return{resultType:"MESSAGE_CREATED"};else throw new Error("Unexpected result")}}class o{schema;constructor(e){this.schema=e.schema}async execute(e){let t=await e.query(a`
21
+ `.value,[this.id,this.channelName,this.name,this.content,this.lockMs,this.delayMs]).then((n)=>n.rows[0]);if(t.result_code===1)return{resultType:"MESSAGE_DROPPED"};else if(t.result_code===2)return{resultType:"MESSAGE_DEDUPLICATED"};else if(t.result_code===0)return{resultType:"MESSAGE_CREATED"};else throw new Error("Unexpected result")}}class i{schema;constructor(e){this.schema=e.schema}async execute(e){let t=await e.query(a`
22
22
  SELECT
23
23
  result_code,
24
24
  metadata,
25
25
  content,
26
26
  state
27
- FROM ${n(this.schema)}."message_dequeue"()
28
- `.value,[]).then((s)=>s.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_AVAILABLE",retryMs:t.metadata.retry_ms};else if(t.result_code===1)return{resultType:"MESSAGE_DEQUEUED",message:{id:t.metadata.id,channelName:t.metadata.channel_name,isUnlocked:t.metadata.is_unlocked,name:t.metadata.name,content:t.content,state:t.state,numAttempts:t.metadata.num_attempts}};else throw new Error("Unexpected dequeue result")}}class i{schema;id;constructor(e){this.schema=e.schema,this.id=e.id}async execute(e){let t=await e.query(a`
29
- SELECT * FROM ${n(this.schema)}."message_delete"(
30
- $1
27
+ FROM ${s(this.schema)}."message_dequeue"()
28
+ `.value,[]).then((n)=>n.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_AVAILABLE",retryMs:t.metadata.retry_ms};else if(t.result_code===1)return{resultType:"MESSAGE_DEQUEUED",message:{id:t.metadata.id,channelName:t.metadata.channel_name,isUnlocked:t.metadata.is_unlocked,name:t.metadata.name,content:t.content,state:t.state,numAttempts:t.metadata.num_attempts}};else throw new Error("Unexpected dequeue result")}}class u{schema;id;numAttempts;constructor(e){this.schema=e.schema,this.id=e.id,this.numAttempts=e.numAttempts}async execute(e){let t=await e.query(a`
29
+ SELECT * FROM ${s(this.schema)}."message_delete"(
30
+ $1,
31
+ $2::BIGINT
31
32
  )
32
- `.value,[this.id]).then((s)=>s.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DELETED"};else throw new Error("Unexpected result")}}class u{schema;id;delayMs;state;constructor(e){let t=e.delayMs===void 0?d:e.delayMs;this.schema=e.schema,this.id=e.id,this.delayMs=t,this.state=e.state??null}async execute(e){let t=await e.query(a`
33
- SELECT * FROM ${n(this.schema)}."message_defer"(
33
+ `.value,[this.id,this.numAttempts]).then((n)=>n.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DELETED"};else throw new Error("Unexpected result")}}class o{schema;id;numAttempts;delayMs;state;constructor(e){let t=e.delayMs===void 0?d:e.delayMs;this.schema=e.schema,this.numAttempts=e.numAttempts,this.id=e.id,this.delayMs=t,this.state=e.state??null}async execute(e){let t=await e.query(a`
34
+ SELECT * FROM ${s(this.schema)}."message_defer"(
34
35
  $1,
35
36
  $2::BIGINT,
36
- $3
37
+ $3::BIGINT,
38
+ $4
39
+ )
40
+ `.value,[this.id,this.numAttempts,this.delayMs,this.state]).then((n)=>n.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DEFERRED"};else throw new Error("Unexpected result")}}class S{schema;id;numAttempts;constructor(e){this.schema=e.schema,this.numAttempts=e.numAttempts,this.id=e.id}async execute(e){let t=await e.query(a`
41
+ SELECT * FROM ${s(this.schema)}."message_heartbeat"(
42
+ $1,
43
+ $2::BIGINT
37
44
  )
38
- `.value,[this.id,this.delayMs,this.state]).then((s)=>s.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DEFERRED"};else throw new Error("Unexpected result")}}var G=(e)=>{let t=e.split(`
39
- `),s=Number.MAX_SAFE_INTEGER;for(let E of t){if(E.trim().length===0)continue;let T=E.search(/\S/);s=Math.min(s,T)}return t.map((E)=>E.slice(s)).join(`
40
- `).trim()};var g=require("path"),__filename="/home/runner/work/lonnymq/lonnymq/src/core/path.ts",Ee=g.dirname(g.dirname(__filename)),_e=new RegExp(`^${Ee}/`),_=(e)=>{return e.replace(_e,"")};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/00-table-channel-policy.ts",F={name:_(__filename),sql:(e)=>{return[a`
41
- CREATE TABLE ${n(e.schema)}."channel_policy" (
45
+ `.value,[this.id,this.numAttempts]).then((n)=>n.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"MESSAGE_STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_HEARTBEATEDED"};else throw new Error("Unexpected result")}}var F=(e)=>{let t=e.split(`
46
+ `),n=Number.MAX_SAFE_INTEGER;for(let E of t){if(E.trim().length===0)continue;let T=E.search(/\S/);n=Math.min(n,T)}return t.map((E)=>E.slice(n)).join(`
47
+ `).trim()};var g=require("path"),__filename="/home/runner/work/lonnymq/lonnymq/src/core/path.ts",me=g.dirname(g.dirname(__filename)),ce=new RegExp(`^${me}/`),_=(e)=>{return e.replace(ce,"")};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/00-table-channel-policy.ts",q={name:_(__filename),sql:(e)=>{return[a`
48
+ CREATE TABLE ${s(e.schema)}."channel_policy" (
42
49
  "id" UUID NOT NULL DEFAULT GEN_RANDOM_UUID(),
43
50
  "name" TEXT NOT NULL,
44
51
  "max_size" INTEGER,
@@ -49,9 +56,9 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
49
56
  );
50
57
  `,a`
51
58
  CREATE UNIQUE INDEX "channel_policy_name_ux"
52
- ON ${n(e.schema)}."channel_policy" ("name");
53
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/01-table-channel-state.ts",q={name:_(__filename),sql:(e)=>{return[a`
54
- CREATE TABLE ${n(e.schema)}."channel_state" (
59
+ ON ${s(e.schema)}."channel_policy" ("name");
60
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/01-table-channel-state.ts",$={name:_(__filename),sql:(e)=>{return[a`
61
+ CREATE TABLE ${s(e.schema)}."channel_state" (
55
62
  "id" UUID NOT NULL DEFAULT GEN_RANDOM_UUID(),
56
63
  "name" TEXT NOT NULL,
57
64
  "max_size" INTEGER,
@@ -69,15 +76,15 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
69
76
  );
70
77
  `,a`
71
78
  CREATE UNIQUE INDEX "channel_state_name_ux"
72
- ON ${n(e.schema)}."channel_state" ("name");
79
+ ON ${s(e.schema)}."channel_state" ("name");
73
80
  `,a`
74
81
  CREATE INDEX "channel_state_dequeue_ix"
75
- ON ${n(e.schema)}."channel_state" (
82
+ ON ${s(e.schema)}."channel_state" (
76
83
  "active_next_at" ASC
77
84
  ) WHERE "message_id" IS NOT NULL
78
85
  AND ("max_concurrency" IS NULL OR "current_concurrency" < "max_concurrency");
79
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/02-table-message.ts",$={name:_(__filename),sql:(e)=>{return[a`
80
- CREATE TABLE ${n(e.schema)}."message" (
86
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/02-table-message.ts",b={name:_(__filename),sql:(e)=>{return[a`
87
+ CREATE TABLE ${s(e.schema)}."message" (
81
88
  "id" UUID NOT NULL,
82
89
  "channel_name" TEXT NOT NULL,
83
90
  "seq_no" BIGSERIAL NOT NULL,
@@ -94,24 +101,24 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
94
101
  );
95
102
  `,a`
96
103
  CREATE UNIQUE INDEX "message_name_ux"
97
- ON ${n(e.schema)}."message" (
104
+ ON ${s(e.schema)}."message" (
98
105
  "channel_name",
99
106
  "name"
100
107
  ) WHERE "num_attempts" = 0
101
108
  `,a`
102
109
  CREATE INDEX "message_dequeue_ix"
103
- ON ${n(e.schema)}."message" (
110
+ ON ${s(e.schema)}."message" (
104
111
  "channel_name",
105
112
  "dequeue_at" ASC,
106
113
  "seq_no" ASC
107
114
  ) WHERE NOT "is_locked";
108
115
  `,a`
109
116
  CREATE INDEX "message_locked_dequeue_ix"
110
- ON ${n(e.schema)}."message" (
117
+ ON ${s(e.schema)}."message" (
111
118
  "unlock_at" ASC
112
119
  ) WHERE "is_locked";
113
120
  `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/03-function-message-create.ts",B={name:_(__filename),sql:(e)=>{return[a`
114
- CREATE FUNCTION ${n(e.schema)}."message_create" (
121
+ CREATE FUNCTION ${s(e.schema)}."message_create" (
115
122
  p_id UUID,
116
123
  p_channel_name TEXT,
117
124
  p_name TEXT,
@@ -134,12 +141,12 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
134
141
  "channel_policy"."max_size",
135
142
  "channel_policy"."max_concurrency",
136
143
  "channel_policy"."release_interval_ms"
137
- FROM ${n(e.schema)}."channel_policy"
144
+ FROM ${s(e.schema)}."channel_policy"
138
145
  WHERE "name" = p_channel_name
139
146
  FOR SHARE
140
147
  INTO v_channel_policy;
141
148
 
142
- INSERT INTO ${n(e.schema)}."channel_state" (
149
+ INSERT INTO ${s(e.schema)}."channel_state" (
143
150
  "name",
144
151
  "current_size",
145
152
  "current_concurrency",
@@ -178,7 +185,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
178
185
  RETURN;
179
186
  END IF;
180
187
 
181
- INSERT INTO ${n(e.schema)}."message" (
188
+ INSERT INTO ${s(e.schema)}."message" (
182
189
  "id",
183
190
  "channel_name",
184
191
  "name",
@@ -220,7 +227,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
220
227
  v_message."dequeue_at" < v_channel_state."message_dequeue_at" OR
221
228
  v_message."dequeue_at" = v_channel_state."message_dequeue_at" AND v_message."seq_no" < v_channel_state."message_seq_no"
222
229
  THEN
223
- UPDATE ${n(e.schema)}."channel_state" SET
230
+ UPDATE ${s(e.schema)}."channel_state" SET
224
231
  "current_size" = v_channel_state."current_size" + 1,
225
232
  "message_id" = v_message."id",
226
233
  "message_dequeue_at" = v_message."dequeue_at",
@@ -231,7 +238,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
231
238
  )
232
239
  WHERE "id" = v_channel_state."id";
233
240
  ELSE
234
- UPDATE ${n(e.schema)}."channel_state" SET
241
+ UPDATE ${s(e.schema)}."channel_state" SET
235
242
  "current_size" = v_channel_state."current_size" + 1
236
243
  WHERE "id" = v_channel_state."id";
237
244
  END IF;
@@ -253,7 +260,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
253
260
  END;
254
261
  $$ LANGUAGE plpgsql;
255
262
  `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/04-function-message-dequeue.ts",P={name:_(__filename),sql:(e)=>{return[a`
256
- CREATE FUNCTION ${n(e.schema)}."message_dequeue" ()
263
+ CREATE FUNCTION ${s(e.schema)}."message_dequeue" ()
257
264
  RETURNS TABLE (
258
265
  result_code INTEGER,
259
266
  content BYTEA,
@@ -278,7 +285,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
278
285
  "message"."lock_ms",
279
286
  "message"."unlock_at",
280
287
  "message"."num_attempts"
281
- FROM ${n(e.schema)}."message"
288
+ FROM ${s(e.schema)}."message"
282
289
  WHERE "is_locked"
283
290
  AND "unlock_at" <= v_now
284
291
  ORDER BY "unlock_at" ASC
@@ -288,7 +295,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
288
295
  INTO v_message_locked;
289
296
 
290
297
  IF v_message_locked."id" IS NOT NULL THEN
291
- UPDATE ${n(e.schema)}."message" SET
298
+ UPDATE ${s(e.schema)}."message" SET
292
299
  "num_attempts" = v_message_locked."num_attempts" + 1,
293
300
  "unlock_at" = v_now + (v_message_locked."lock_ms" * INTERVAL '1 millisecond')
294
301
  WHERE "id" = v_message_locked."id";
@@ -302,7 +309,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
302
309
  'is_unlocked', TRUE,
303
310
  'channel_name', v_message_locked.channel_name,
304
311
  'name', v_message_locked.name,
305
- 'num_attempts', v_message_locked.num_attempts
312
+ 'num_attempts', v_message_locked.num_attempts + 1
306
313
  );
307
314
  RETURN;
308
315
  END IF;
@@ -315,7 +322,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
315
322
  "channel_state"."active_next_at",
316
323
  "channel_state"."active_prev_at",
317
324
  "channel_state"."current_concurrency"
318
- FROM ${n(e.schema)}."channel_state"
325
+ FROM ${s(e.schema)}."channel_state"
319
326
  WHERE "message_id" IS NOT NULL
320
327
  AND ("max_concurrency" IS NULL OR "current_concurrency" < "max_concurrency")
321
328
  ORDER BY "active_next_at" ASC
@@ -352,11 +359,11 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
352
359
  "message"."num_attempts",
353
360
  "message"."state",
354
361
  "message"."lock_ms"
355
- FROM ${n(e.schema)}."message"
362
+ FROM ${s(e.schema)}."message"
356
363
  WHERE "id" = v_channel_state."message_id"
357
364
  INTO v_message_dequeue;
358
365
 
359
- UPDATE ${n(e.schema)}."message" SET
366
+ UPDATE ${s(e.schema)}."message" SET
360
367
  "is_locked" = TRUE,
361
368
  "num_attempts" = v_message_dequeue."num_attempts" + 1,
362
369
  "unlock_at" = v_now + (v_message_dequeue."lock_ms" * INTERVAL '1 millisecond')
@@ -366,7 +373,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
366
373
  "message"."id",
367
374
  "message"."dequeue_at",
368
375
  "message"."seq_no"
369
- FROM ${n(e.schema)}."message"
376
+ FROM ${s(e.schema)}."message"
370
377
  WHERE NOT "is_locked"
371
378
  AND "channel_name" = v_message_dequeue."channel_name"
372
379
  ORDER BY "dequeue_at" ASC, "seq_no" ASC
@@ -374,13 +381,13 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
374
381
  INTO v_message_next;
375
382
 
376
383
  IF v_message_next."id" IS NULL THEN
377
- UPDATE ${n(e.schema)}."channel_state" SET
384
+ UPDATE ${s(e.schema)}."channel_state" SET
378
385
  "current_concurrency" = v_channel_state."current_concurrency" + 1,
379
386
  "active_prev_at" = v_now,
380
387
  "message_id" = NULL
381
388
  WHERE "id" = v_channel_state."id";
382
389
  ELSE
383
- UPDATE ${n(e.schema)}."channel_state" SET
390
+ UPDATE ${s(e.schema)}."channel_state" SET
384
391
  "current_concurrency" = v_channel_state."current_concurrency" + 1,
385
392
  "message_id" = v_message_next."id",
386
393
  "message_dequeue_at" = v_message_next."dequeue_at",
@@ -402,14 +409,15 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
402
409
  'is_unlocked', FALSE,
403
410
  'channel_name', v_message_dequeue.channel_name,
404
411
  'name', v_message_dequeue.name,
405
- 'num_attempts', v_message_dequeue.num_attempts
412
+ 'num_attempts', v_message_dequeue.num_attempts + 1
406
413
  );
407
414
  RETURN;
408
415
  END;
409
416
  $$ LANGUAGE plpgsql;
410
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/05-function-message-delete.ts",b={name:_(__filename),sql:(e)=>{return[a`
411
- CREATE FUNCTION ${n(e.schema)}."message_delete" (
412
- p_id UUID
417
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/05-function-message-delete.ts",Q={name:_(__filename),sql:(e)=>{return[a`
418
+ CREATE FUNCTION ${s(e.schema)}."message_delete" (
419
+ p_id UUID,
420
+ p_num_attempts BIGINT
413
421
  )
414
422
  RETURNS TABLE (
415
423
  result_code INTEGER
@@ -422,8 +430,9 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
422
430
  SELECT
423
431
  "message"."id",
424
432
  "message"."channel_name",
433
+ "message"."num_attempts",
425
434
  "message"."is_locked"
426
- FROM ${n(e.schema)}."message"
435
+ FROM ${s(e.schema)}."message"
427
436
  WHERE "id" = p_id
428
437
  FOR UPDATE
429
438
  INTO v_message;
@@ -432,7 +441,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
432
441
  RETURN QUERY SELECT
433
442
  ${r(0)};
434
443
  RETURN;
435
- ELSIF NOT v_message."is_locked" THEN
444
+ ELSIF NOT v_message."is_locked" OR v_message."num_attempts" <> p_num_attempts THEN
436
445
  RETURN QUERY SELECT
437
446
  ${r(1)};
438
447
  RETURN;
@@ -440,7 +449,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
440
449
 
441
450
  SELECT
442
451
  "channel_policy"."id"
443
- FROM ${n(e.schema)}."channel_policy"
452
+ FROM ${s(e.schema)}."channel_policy"
444
453
  WHERE "name" = v_message."channel_name"
445
454
  FOR SHARE
446
455
  INTO v_channel_policy;
@@ -449,16 +458,16 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
449
458
  "channel_state"."id",
450
459
  "channel_state"."current_size",
451
460
  "channel_state"."current_concurrency"
452
- FROM ${n(e.schema)}."channel_state"
461
+ FROM ${s(e.schema)}."channel_state"
453
462
  WHERE "name" = v_message."channel_name"
454
463
  FOR UPDATE
455
464
  INTO v_channel_state;
456
465
 
457
466
  IF v_channel_policy."id" IS NULL AND v_channel_state."current_size" = 1 THEN
458
- DELETE FROM ${n(e.schema)}."channel_state"
467
+ DELETE FROM ${s(e.schema)}."channel_state"
459
468
  WHERE "id" = v_channel_state."id";
460
469
  ELSE
461
- UPDATE ${n(e.schema)}."channel_state" SET
470
+ UPDATE ${s(e.schema)}."channel_state" SET
462
471
  "current_concurrency" = v_channel_state."current_concurrency" - 1,
463
472
  "current_size" = v_channel_state."current_size" - 1
464
473
  WHERE "id" = v_channel_state."id";
@@ -474,7 +483,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
474
483
  );
475
484
  END IF;
476
485
 
477
- DELETE FROM ${n(e.schema)}."message"
486
+ DELETE FROM ${s(e.schema)}."message"
478
487
  WHERE "id" = p_id;
479
488
 
480
489
  RETURN QUERY SELECT
@@ -482,9 +491,10 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
482
491
  RETURN;
483
492
  END;
484
493
  $$ LANGUAGE plpgsql;
485
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/06-function-message-defer.ts",Q={name:_(__filename),sql:(e)=>{return[a`
486
- CREATE FUNCTION ${n(e.schema)}."message_defer" (
494
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/06-function-message-defer.ts",H={name:_(__filename),sql:(e)=>{return[a`
495
+ CREATE FUNCTION ${s(e.schema)}."message_defer" (
487
496
  p_id UUID,
497
+ p_num_attempts BIGINT,
488
498
  p_delay_ms BIGINT,
489
499
  p_state BYTEA
490
500
  )
@@ -502,9 +512,10 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
502
512
  SELECT
503
513
  "message"."id",
504
514
  "message"."channel_name",
515
+ "message"."num_attempts",
505
516
  "message"."is_locked",
506
517
  "message"."seq_no"
507
- FROM ${n(e.schema)}."message"
518
+ FROM ${s(e.schema)}."message"
508
519
  WHERE "id" = p_id
509
520
  FOR UPDATE
510
521
  INTO v_message;
@@ -513,7 +524,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
513
524
  RETURN QUERY SELECT
514
525
  ${r(0)};
515
526
  RETURN;
516
- ELSIF NOT v_message."is_locked" THEN
527
+ ELSIF NOT v_message."is_locked" OR v_message."num_attempts" <> p_num_attempts THEN
517
528
  RETURN QUERY SELECT
518
529
  ${r(1)};
519
530
  RETURN;
@@ -526,7 +537,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
526
537
  "channel_state"."message_dequeue_at",
527
538
  "channel_state"."active_prev_at",
528
539
  "channel_state"."message_seq_no"
529
- FROM ${n(e.schema)}."channel_state"
540
+ FROM ${s(e.schema)}."channel_state"
530
541
  WHERE "name" = v_message."channel_name"
531
542
  FOR UPDATE
532
543
  INTO v_channel_state;
@@ -538,7 +549,7 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
538
549
  v_dequeue_at < v_channel_state."message_dequeue_at" OR
539
550
  v_dequeue_at = v_channel_state."message_dequeue_at" AND v_message."seq_no" < v_channel_state."message_seq_no"
540
551
  THEN
541
- UPDATE ${n(e.schema)}."channel_state" SET
552
+ UPDATE ${s(e.schema)}."channel_state" SET
542
553
  "current_concurrency" = v_channel_state."current_concurrency" - 1,
543
554
  "message_id" = v_message."id",
544
555
  "message_dequeue_at" = v_dequeue_at,
@@ -549,12 +560,12 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
549
560
  )
550
561
  WHERE "name" = v_message."channel_name";
551
562
  ELSE
552
- UPDATE ${n(e.schema)}."channel_state" SET
563
+ UPDATE ${s(e.schema)}."channel_state" SET
553
564
  "current_concurrency" = v_channel_state."current_concurrency" - 1
554
565
  WHERE "name" = v_message."channel_name";
555
566
  END IF;
556
567
 
557
- UPDATE ${n(e.schema)}."message" SET
568
+ UPDATE ${s(e.schema)}."message" SET
558
569
  "state" = p_state,
559
570
  "is_locked" = FALSE,
560
571
  "dequeue_at" = v_dequeue_at
@@ -576,65 +587,72 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
576
587
  RETURN;
577
588
  END;
578
589
  $$ LANGUAGE plpgsql;
579
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/07-function-channel-policy-set.ts",w={name:_(__filename),sql:(e)=>{return[a`
580
- CREATE FUNCTION ${n(e.schema)}."channel_policy_set" (
581
- p_name TEXT,
582
- p_max_size INTEGER,
583
- p_max_concurrency INTEGER,
584
- p_release_interval_ms INTEGER
585
- ) RETURNS VOID AS $$
590
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/07-function-message-heartbeat.ts",w={name:_(__filename),sql:(e)=>{return[a`
591
+ CREATE FUNCTION ${s(e.schema)}."message_heartbeat" (
592
+ p_id UUID,
593
+ p_num_attempts BIGINT
594
+ )
595
+ RETURNS TABLE (
596
+ result_code INTEGER
597
+ ) AS $$
586
598
  DECLARE
587
599
  v_now TIMESTAMP;
600
+ v_message RECORD;
588
601
  BEGIN
589
602
  v_now := NOW();
590
603
 
591
- INSERT INTO ${n(e.schema)}."channel_policy" (
592
- "name",
593
- "max_size",
594
- "max_concurrency",
595
- "release_interval_ms",
596
- "created_at"
597
- ) VALUES (
598
- p_name,
599
- p_max_size,
600
- p_max_concurrency,
601
- p_release_interval_ms,
602
- v_now
603
- ) ON CONFLICT ("name") DO UPDATE SET
604
- "max_size" = EXCLUDED."max_size",
605
- "max_concurrency" = EXCLUDED."max_concurrency",
606
- "release_interval_ms" = EXCLUDED."release_interval_ms";
604
+ SELECT
605
+ "message"."id",
606
+ "message"."is_locked",
607
+ "message"."num_attempts",
608
+ "message"."lock_ms"
609
+ FROM ${s(e.schema)}."message"
610
+ WHERE "id" = p_id
611
+ FOR UPDATE
612
+ INTO v_message;
607
613
 
608
- UPDATE ${n(e.schema)}."channel_state" SET
609
- "max_size" = p_max_size,
610
- "max_concurrency" = p_max_concurrency,
611
- "release_interval_ms" = p_release_interval_ms
612
- WHERE "name" = p_name;
614
+ IF v_message."id" IS NULL THEN
615
+ RETURN QUERY SELECT
616
+ ${r(0)};
617
+ RETURN;
618
+ ELSIF NOT v_message."is_locked" OR v_message."num_attempts" <> p_num_attempts THEN
619
+ RETURN QUERY SELECT
620
+ ${r(1)};
621
+ RETURN;
622
+ END IF;
623
+
624
+ UPDATE ${s(e.schema)}."message" SET
625
+ "unlock_at" = v_now + INTERVAL '1 MILLISECOND' * v_message."lock_ms"
626
+ WHERE "id" = p_id;
627
+
628
+ RETURN QUERY SELECT
629
+ ${r(2)};
630
+ RETURN;
613
631
  END;
614
632
  $$ LANGUAGE plpgsql;
615
633
  `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/08-function-channel-policy-clear.ts",k={name:_(__filename),sql:(e)=>{return[a`
616
- CREATE FUNCTION ${n(e.schema)}."channel_policy_clear" (
634
+ CREATE FUNCTION ${s(e.schema)}."channel_policy_clear" (
617
635
  p_name TEXT
618
636
  ) RETURNS VOID AS $$
619
637
  DECLARE
620
638
  v_channel_state RECORD;
621
639
  BEGIN
622
- DELETE FROM ${n(e.schema)}."channel_policy"
640
+ DELETE FROM ${s(e.schema)}."channel_policy"
623
641
  WHERE "name" = p_name;
624
642
 
625
643
  SELECT
626
644
  "channel_state"."id",
627
645
  "channel_state"."current_size"
628
- FROM ${n(e.schema)}."channel_state"
646
+ FROM ${s(e.schema)}."channel_state"
629
647
  WHERE "name" = p_name
630
648
  FOR UPDATE
631
649
  INTO v_channel_state;
632
650
 
633
651
  IF v_channel_state."current_size" = 0 THEN
634
- DELETE FROM ${n(e.schema)}."channel_state"
652
+ DELETE FROM ${s(e.schema)}."channel_state"
635
653
  WHERE "id" = v_channel_state."id";
636
654
  ELSE
637
- UPDATE ${n(e.schema)}."channel_state" SET
655
+ UPDATE ${s(e.schema)}."channel_state" SET
638
656
  "max_size" = NULL,
639
657
  "max_concurrency" = NULL,
640
658
  "release_interval_ms" = NULL
@@ -642,4 +660,40 @@ var{defineProperty:h,getOwnPropertyNames:z,getOwnPropertyDescriptor:V}=Object,W=
642
660
  END IF;
643
661
  END;
644
662
  $$ LANGUAGE plpgsql;
645
- `]}};class S{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}create(e){let t=new m({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}),s=new Promise((E)=>{this.registerFn({sortKey:JSON.stringify([t.channelName,t.name,t.createdAt.toISOString()]),execute:(T)=>t.execute(T).then((H)=>E(H))})});return{messageId:t.id,promise:s}}}class D{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}set(e){let t=new c({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs});this.registerFn({sortKey:JSON.stringify([t.channelName,null,t.createdAt.toISOString()]),execute:async(s)=>{await t.execute(s)}})}clear(){let e=new l({schema:this.schema,channelName:this.channelName});this.registerFn({sortKey:JSON.stringify([e.channelName,null,e.createdAt.toISOString()]),execute:async(t)=>{await e.execute(t)}})}}class A{policy;message;constructor(e){this.message=new S(e),this.policy=new D(e)}}var le=(e,t)=>{return e.sortKey.localeCompare(t.sortKey)};class y{commands;schema;constructor(e){this.commands=[],this.schema=e.schema}channel(e){return new A({schema:this.schema,channelName:e,registerFn:(t)=>{this.commands.push(t)}})}async execute(e){for(let t of this.commands.sort(le))await t.execute(e.databaseClient)}}class M{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}async create(e){return new m({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}).execute(e.databaseClient)}}class p{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}set(e){return new c({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs}).execute(e.databaseClient)}clear(e){return new l({schema:this.schema,channelName:this.channelName}).execute(e.databaseClient)}}class C{policy;message;constructor(e){this.message=new M({schema:e.schema,channelName:e.channelName}),this.policy=new p({schema:e.schema,channelName:e.channelName})}}class v{schema;id;channelName;name;content;state;numAttempts;constructor(e){this.schema=e.schema,this.id=e.id,this.channelName=e.channelName,this.name=e.name,this.content=e.content,this.state=e.state,this.numAttempts=e.numAttempts}async defer(e){return new u({schema:this.schema,id:this.id,delayMs:e.delayMs,state:e.state}).execute(e.databaseClient)}async delete(e){return new i({schema:this.schema,id:this.id}).execute(e.databaseClient)}}class L{schema;constructor(e){this.schema=e.schema}async dequeue(e){let s=await new o({schema:this.schema}).execute(e.databaseClient);if(s.resultType==="MESSAGE_DEQUEUED")return{resultType:"MESSAGE_DEQUEUED",message:new v({schema:this.schema,id:s.message.id,channelName:s.message.channelName,name:s.message.name,content:s.message.content,state:s.message.state,numAttempts:s.message.numAttempts})};else return s}channel(e){return new C({schema:this.schema,channelName:e})}batch(){return new y({schema:this.schema})}migrations(e={}){return[F,q,$,B,P,b,Q,w,k].sort((t,s)=>t.name.localeCompare(s.name)).flatMap((t)=>t.sql({schema:this.schema,eventChannel:e.eventChannel??null})).map((t)=>G(t.value))}}
663
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/09-function-channel-policy-set.ts",V={name:_(__filename),sql:(e)=>{return[a`
664
+ CREATE FUNCTION ${s(e.schema)}."channel_policy_set" (
665
+ p_name TEXT,
666
+ p_max_size INTEGER,
667
+ p_max_concurrency INTEGER,
668
+ p_release_interval_ms INTEGER
669
+ ) RETURNS VOID AS $$
670
+ DECLARE
671
+ v_now TIMESTAMP;
672
+ BEGIN
673
+ v_now := NOW();
674
+
675
+ INSERT INTO ${s(e.schema)}."channel_policy" (
676
+ "name",
677
+ "max_size",
678
+ "max_concurrency",
679
+ "release_interval_ms",
680
+ "created_at"
681
+ ) VALUES (
682
+ p_name,
683
+ p_max_size,
684
+ p_max_concurrency,
685
+ p_release_interval_ms,
686
+ v_now
687
+ ) ON CONFLICT ("name") DO UPDATE SET
688
+ "max_size" = EXCLUDED."max_size",
689
+ "max_concurrency" = EXCLUDED."max_concurrency",
690
+ "release_interval_ms" = EXCLUDED."release_interval_ms";
691
+
692
+ UPDATE ${s(e.schema)}."channel_state" SET
693
+ "max_size" = p_max_size,
694
+ "max_concurrency" = p_max_concurrency,
695
+ "release_interval_ms" = p_release_interval_ms
696
+ WHERE "name" = p_name;
697
+ END;
698
+ $$ LANGUAGE plpgsql;
699
+ `]}};class A{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}create(e){let t=new c({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}),n=new Promise((E)=>{this.registerFn({sortKey:JSON.stringify([t.channelName,t.name,t.createdAt.toISOString()]),execute:(T)=>t.execute(T).then((z)=>E(z))})});return{messageId:t.id,promise:n}}}class D{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}set(e){let t=new m({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs});this.registerFn({sortKey:JSON.stringify([t.channelName,null,t.createdAt.toISOString()]),execute:async(n)=>{await t.execute(n)}})}clear(){let e=new l({schema:this.schema,channelName:this.channelName});this.registerFn({sortKey:JSON.stringify([e.channelName,null,e.createdAt.toISOString()]),execute:async(t)=>{await e.execute(t)}})}}class p{policy;message;constructor(e){this.message=new A(e),this.policy=new D(e)}}var oe=(e,t)=>{return e.sortKey.localeCompare(t.sortKey)};class M{commands;schema;constructor(e){this.commands=[],this.schema=e.schema}channel(e){return new p({schema:this.schema,channelName:e,registerFn:(t)=>{this.commands.push(t)}})}async execute(e){for(let t of this.commands.sort(oe))await t.execute(e.databaseClient)}}class y{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}async create(e){return new c({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}).execute(e.databaseClient)}}class C{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}set(e){return new m({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs}).execute(e.databaseClient)}clear(e){return new l({schema:this.schema,channelName:this.channelName}).execute(e.databaseClient)}}class I{policy;message;constructor(e){this.message=new y({schema:e.schema,channelName:e.channelName}),this.policy=new C({schema:e.schema,channelName:e.channelName})}}class v{schema;id;isUnlocked;channelName;name;content;state;numAttempts;constructor(e){this.schema=e.schema,this.id=e.id,this.channelName=e.channelName,this.isUnlocked=e.isUnlocked,this.name=e.name,this.content=e.content,this.state=e.state,this.numAttempts=e.numAttempts}async defer(e){return new o({schema:this.schema,id:this.id,numAttempts:this.numAttempts,delayMs:e.delayMs,state:e.state}).execute(e.databaseClient)}async delete(e){return new u({schema:this.schema,numAttempts:this.numAttempts,id:this.id}).execute(e.databaseClient)}async heartbeat(e){return new o({schema:this.schema,id:this.id,numAttempts:this.numAttempts,delayMs:e.delayMs}).execute(e.databaseClient)}}class L{schema;constructor(e){this.schema=e.schema}async dequeue(e){let n=await new i({schema:this.schema}).execute(e.databaseClient);if(n.resultType==="MESSAGE_DEQUEUED")return{resultType:"MESSAGE_DEQUEUED",message:new v({schema:this.schema,id:n.message.id,channelName:n.message.channelName,name:n.message.name,isUnlocked:n.message.isUnlocked,content:n.message.content,state:n.message.state,numAttempts:n.message.numAttempts})};else return n}channel(e){return new I({schema:this.schema,channelName:e})}batch(){return new M({schema:this.schema})}migrations(e={}){return[q,$,b,B,P,Q,H,w,V,k].sort((t,n)=>t.name.localeCompare(n.name)).flatMap((t)=>t.sql({schema:this.schema,eventChannel:e.eventChannel??null})).map((t)=>F(t.value))}}
package/dist/index.d.ts CHANGED
@@ -121,8 +121,10 @@ export type MessageDeleteCommandResult = MessageDeleteCommandResultMessageNotFou
121
121
  export declare class MessageDeleteCommand {
122
122
  readonly schema: string;
123
123
  readonly id: string;
124
+ readonly numAttempts: number;
124
125
  constructor(params: {
125
126
  schema: string;
127
+ numAttempts: number;
126
128
  id: string;
127
129
  });
128
130
  execute(databaseClient: DatabaseClient): Promise<MessageDeleteCommandResult>;
@@ -140,16 +142,39 @@ export type MessageDeferCommandResult = MessageDeferCommandResultMessageNotFound
140
142
  export declare class MessageDeferCommand {
141
143
  readonly schema: string;
142
144
  readonly id: string;
145
+ readonly numAttempts: number;
143
146
  readonly delayMs: number;
144
147
  readonly state: Buffer | null;
145
148
  constructor(params: {
146
149
  schema: string;
147
150
  id: string;
151
+ numAttempts: number;
148
152
  delayMs?: number;
149
153
  state?: Buffer | null;
150
154
  });
151
155
  execute(databaseClient: DatabaseClient): Promise<MessageDeferCommandResult>;
152
156
  }
157
+ export type MessageHeartbeatCommandResultMessageNotFound = {
158
+ resultType: "MESSAGE_NOT_FOUND";
159
+ };
160
+ export type MessageHeartbeatCommandResultStateInvalid = {
161
+ resultType: "MESSAGE_STATE_INVALID";
162
+ };
163
+ export type MessageHeartbeatCommandResultMessageHeartbeated = {
164
+ resultType: "MESSAGE_HEARTBEATEDED";
165
+ };
166
+ export type MessageHeartbeatCommandResult = MessageHeartbeatCommandResultMessageNotFound | MessageHeartbeatCommandResultStateInvalid | MessageHeartbeatCommandResultMessageHeartbeated;
167
+ export declare class MessageHeartbeatCommand {
168
+ readonly schema: string;
169
+ readonly id: string;
170
+ readonly numAttempts: number;
171
+ constructor(params: {
172
+ schema: string;
173
+ id: string;
174
+ numAttempts: number;
175
+ });
176
+ execute(databaseClient: DatabaseClient): Promise<MessageHeartbeatCommandResult>;
177
+ }
153
178
  export type QueueBatchChannelMessageCreateResult = {
154
179
  messageId: string;
155
180
  promise: Promise<MessageCreateCommandResult>;
@@ -254,6 +279,7 @@ export declare class QueueChannel {
254
279
  export declare class QueueMessage {
255
280
  private readonly schema;
256
281
  readonly id: string;
282
+ readonly isUnlocked: boolean;
257
283
  readonly channelName: string;
258
284
  readonly name: string | null;
259
285
  readonly content: Buffer;
@@ -263,6 +289,7 @@ export declare class QueueMessage {
263
289
  schema: string;
264
290
  id: string;
265
291
  channelName: string;
292
+ isUnlocked: boolean;
266
293
  name: string | null;
267
294
  content: Buffer;
268
295
  state: Buffer | null;
@@ -276,6 +303,10 @@ export declare class QueueMessage {
276
303
  delete(params: {
277
304
  databaseClient: DatabaseClient;
278
305
  }): Promise<MessageDeleteCommandResult>;
306
+ heartbeat(params: {
307
+ databaseClient: DatabaseClient;
308
+ delayMs?: number;
309
+ }): Promise<MessageDeferCommandResult>;
279
310
  }
280
311
  export type MessageDequeueResult = {
281
312
  resultType: "MESSAGE_NOT_AVAILABLE";
package/dist/index.js CHANGED
@@ -1,16 +1,16 @@
1
- var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=>({nodeType:"RAW",value:e}),w=(e)=>{return`'${e.replace(/'/g,"''")}'`},k=(e)=>{if(e===null)return"NULL";else if(typeof e==="string")return w(e);else if(typeof e==="number")return e.toString();else if(typeof e==="boolean")return e?"TRUE":"FALSE";else if(e instanceof Date)return`'${e.toISOString()}'`;else if(typeof e==="bigint")return e.toString();else throw new Error(`Unsupported value type: ${typeof e}`)},H=(e)=>{return`"${e.replace(/"/g,'""')}"`},z=(e)=>{if(e.nodeType==="VALUE")return k(e.value);else if(e.nodeType==="REF")return H(e.value);else if(e.nodeType==="RAW")return e.value;else throw new Error("Unsupported SQL node type")};var s=(e,...t)=>{let a=[];for(let _=0;_<e.length;_+=1)if(a.push(e[_]),_<t.length)a.push(z(t[_]));return Q(a.join(""))};class l{schema;channelName;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(s`
2
- SELECT 1 FROM ${n(this.schema)}."channel_policy_clear"(
1
+ var r=(e)=>({nodeType:"VALUE",value:e}),s=(e)=>({nodeType:"REF",value:e}),w=(e)=>({nodeType:"RAW",value:e}),k=(e)=>{return`'${e.replace(/'/g,"''")}'`},V=(e)=>{if(e===null)return"NULL";else if(typeof e==="string")return k(e);else if(typeof e==="number")return e.toString();else if(typeof e==="boolean")return e?"TRUE":"FALSE";else if(e instanceof Date)return`'${e.toISOString()}'`;else if(typeof e==="bigint")return e.toString();else throw new Error(`Unsupported value type: ${typeof e}`)},z=(e)=>{return`"${e.replace(/"/g,'""')}"`},W=(e)=>{if(e.nodeType==="VALUE")return V(e.value);else if(e.nodeType==="REF")return z(e.value);else if(e.nodeType==="RAW")return e.value;else throw new Error("Unsupported SQL node type")};var n=(e,...t)=>{let a=[];for(let _=0;_<e.length;_+=1)if(a.push(e[_]),_<t.length)a.push(W(t[_]));return w(a.join(""))};class l{schema;channelName;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(n`
2
+ SELECT 1 FROM ${s(this.schema)}."channel_policy_clear"(
3
3
  $1
4
4
  )
5
- `.value,[this.channelName])}}class c{schema;channelName;maxSize;maxConcurrency;releaseIntervalMs;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName;let t=e.maxConcurrency??null;this.maxConcurrency=t!==null?Math.max(0,t):null;let a=e.maxSize??null;this.maxSize=a!==null?Math.max(0,a):null;let _=e.releaseIntervalMs??null;this.releaseIntervalMs=_!==null?Math.max(0,_):null,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(s`
6
- SELECT 1 FROM ${n(this.schema)}."channel_policy_set"(
5
+ `.value,[this.channelName])}}class m{schema;channelName;maxSize;maxConcurrency;releaseIntervalMs;createdAt;constructor(e){this.schema=e.schema,this.channelName=e.channelName;let t=e.maxConcurrency??null;this.maxConcurrency=t!==null?Math.max(0,t):null;let a=e.maxSize??null;this.maxSize=a!==null?Math.max(0,a):null;let _=e.releaseIntervalMs??null;this.releaseIntervalMs=_!==null?Math.max(0,_):null,this.createdAt=new Date}sortKeyGet(){return JSON.stringify([this.channelName,null,this.createdAt.toISOString()])}async execute(e){await e.query(n`
6
+ SELECT 1 FROM ${s(this.schema)}."channel_policy_set"(
7
7
  $1,
8
8
  $2::INTEGER,
9
9
  $3::INTEGER,
10
10
  $4::INTEGER
11
11
  )
12
- `.value,[this.channelName,this.maxSize,this.maxConcurrency,this.releaseIntervalMs])}}var h=(e)=>{return e*1000},V=(e)=>{return h(e*60)},C=(e)=>{return V(e*60)};var o=h(0),v=C(1);var W=(e)=>{let t=JSON.parse(e);if(t.type===0)return{eventType:"MESSAGE_CREATED",id:t.id,delayMs:t.delay_ms};else if(t.type===1)return{eventType:"MESSAGE_DELETED",id:t.id};else if(t.type===2)return{eventType:"MESSAGE_DEFERRED",id:t.id,delayMs:t.delay_ms};else throw new Error("Unknown event type")};import{randomUUID as X}from"node:crypto";class m{schema;channelName;name;content;lockMs;id;delayMs;createdAt;constructor(e){let t=e.name??null,a=e.lockMs===void 0?v:Math.max(0,e.lockMs),_=e.delayMs===void 0?o:e.delayMs;this.id=X(),this.schema=e.schema,this.channelName=e.channelName,this.content=e.content,this.name=t,this.lockMs=a,this.delayMs=_,this.createdAt=new Date}async execute(e){let t=await e.query(s`
13
- SELECT * FROM ${n(this.schema)}."message_create"(
12
+ `.value,[this.channelName,this.maxSize,this.maxConcurrency,this.releaseIntervalMs])}}var h=(e)=>{return e*1000},Y=(e)=>{return h(e*60)},C=(e)=>{return Y(e*60)};var i=h(0),I=C(1);var X=(e)=>{let t=JSON.parse(e);if(t.type===0)return{eventType:"MESSAGE_CREATED",id:t.id,delayMs:t.delay_ms};else if(t.type===1)return{eventType:"MESSAGE_DELETED",id:t.id};else if(t.type===2)return{eventType:"MESSAGE_DEFERRED",id:t.id,delayMs:t.delay_ms};else throw new Error("Unknown event type")};import{randomUUID as K}from"node:crypto";class c{schema;channelName;name;content;lockMs;id;delayMs;createdAt;constructor(e){let t=e.name??null,a=e.lockMs===void 0?I:Math.max(0,e.lockMs),_=e.delayMs===void 0?i:e.delayMs;this.id=K(),this.schema=e.schema,this.channelName=e.channelName,this.content=e.content,this.name=t,this.lockMs=a,this.delayMs=_,this.createdAt=new Date}async execute(e){let t=await e.query(n`
13
+ SELECT * FROM ${s(this.schema)}."message_create"(
14
14
  $1,
15
15
  $2,
16
16
  $3,
@@ -18,27 +18,34 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
18
18
  $5::BIGINT,
19
19
  $6::BIGINT
20
20
  )
21
- `.value,[this.id,this.channelName,this.name,this.content,this.lockMs,this.delayMs]).then((a)=>a.rows[0]);if(t.result_code===1)return{resultType:"MESSAGE_DROPPED"};else if(t.result_code===2)return{resultType:"MESSAGE_DEDUPLICATED"};else if(t.result_code===0)return{resultType:"MESSAGE_CREATED"};else throw new Error("Unexpected result")}}class i{schema;constructor(e){this.schema=e.schema}async execute(e){let t=await e.query(s`
21
+ `.value,[this.id,this.channelName,this.name,this.content,this.lockMs,this.delayMs]).then((a)=>a.rows[0]);if(t.result_code===1)return{resultType:"MESSAGE_DROPPED"};else if(t.result_code===2)return{resultType:"MESSAGE_DEDUPLICATED"};else if(t.result_code===0)return{resultType:"MESSAGE_CREATED"};else throw new Error("Unexpected result")}}class u{schema;constructor(e){this.schema=e.schema}async execute(e){let t=await e.query(n`
22
22
  SELECT
23
23
  result_code,
24
24
  metadata,
25
25
  content,
26
26
  state
27
- FROM ${n(this.schema)}."message_dequeue"()
28
- `.value,[]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_AVAILABLE",retryMs:t.metadata.retry_ms};else if(t.result_code===1)return{resultType:"MESSAGE_DEQUEUED",message:{id:t.metadata.id,channelName:t.metadata.channel_name,isUnlocked:t.metadata.is_unlocked,name:t.metadata.name,content:t.content,state:t.state,numAttempts:t.metadata.num_attempts}};else throw new Error("Unexpected dequeue result")}}class u{schema;id;constructor(e){this.schema=e.schema,this.id=e.id}async execute(e){let t=await e.query(s`
29
- SELECT * FROM ${n(this.schema)}."message_delete"(
30
- $1
27
+ FROM ${s(this.schema)}."message_dequeue"()
28
+ `.value,[]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_AVAILABLE",retryMs:t.metadata.retry_ms};else if(t.result_code===1)return{resultType:"MESSAGE_DEQUEUED",message:{id:t.metadata.id,channelName:t.metadata.channel_name,isUnlocked:t.metadata.is_unlocked,name:t.metadata.name,content:t.content,state:t.state,numAttempts:t.metadata.num_attempts}};else throw new Error("Unexpected dequeue result")}}class d{schema;id;numAttempts;constructor(e){this.schema=e.schema,this.id=e.id,this.numAttempts=e.numAttempts}async execute(e){let t=await e.query(n`
29
+ SELECT * FROM ${s(this.schema)}."message_delete"(
30
+ $1,
31
+ $2::BIGINT
31
32
  )
32
- `.value,[this.id]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DELETED"};else throw new Error("Unexpected result")}}class d{schema;id;delayMs;state;constructor(e){let t=e.delayMs===void 0?o:e.delayMs;this.schema=e.schema,this.id=e.id,this.delayMs=t,this.state=e.state??null}async execute(e){let t=await e.query(s`
33
- SELECT * FROM ${n(this.schema)}."message_defer"(
33
+ `.value,[this.id,this.numAttempts]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DELETED"};else throw new Error("Unexpected result")}}class o{schema;id;numAttempts;delayMs;state;constructor(e){let t=e.delayMs===void 0?i:e.delayMs;this.schema=e.schema,this.numAttempts=e.numAttempts,this.id=e.id,this.delayMs=t,this.state=e.state??null}async execute(e){let t=await e.query(n`
34
+ SELECT * FROM ${s(this.schema)}."message_defer"(
34
35
  $1,
35
36
  $2::BIGINT,
36
- $3
37
+ $3::BIGINT,
38
+ $4
39
+ )
40
+ `.value,[this.id,this.numAttempts,this.delayMs,this.state]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DEFERRED"};else throw new Error("Unexpected result")}}class v{schema;id;numAttempts;constructor(e){this.schema=e.schema,this.numAttempts=e.numAttempts,this.id=e.id}async execute(e){let t=await e.query(n`
41
+ SELECT * FROM ${s(this.schema)}."message_heartbeat"(
42
+ $1,
43
+ $2::BIGINT
37
44
  )
38
- `.value,[this.id,this.delayMs,this.state]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_DEFERRED"};else throw new Error("Unexpected result")}}var L=(e)=>{let t=e.split(`
45
+ `.value,[this.id,this.numAttempts]).then((a)=>a.rows[0]);if(t.result_code===0)return{resultType:"MESSAGE_NOT_FOUND"};else if(t.result_code===1)return{resultType:"MESSAGE_STATE_INVALID"};else if(t.result_code===2)return{resultType:"MESSAGE_HEARTBEATEDED"};else throw new Error("Unexpected result")}}var L=(e)=>{let t=e.split(`
39
46
  `),a=Number.MAX_SAFE_INTEGER;for(let _ of t){if(_.trim().length===0)continue;let T=_.search(/\S/);a=Math.min(a,T)}return t.map((_)=>_.slice(a)).join(`
40
- `).trim()};import{dirname as I}from"path";var __filename="/home/runner/work/lonnymq/lonnymq/src/core/path.ts",Z=I(I(__filename)),ee=new RegExp(`^${Z}/`),E=(e)=>{return e.replace(ee,"")};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/00-table-channel-policy.ts",U={name:E(__filename),sql:(e)=>{return[s`
41
- CREATE TABLE ${n(e.schema)}."channel_policy" (
47
+ `).trim()};import{dirname as U}from"path";var __filename="/home/runner/work/lonnymq/lonnymq/src/core/path.ts",se=U(U(__filename)),ne=new RegExp(`^${se}/`),E=(e)=>{return e.replace(ne,"")};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/00-table-channel-policy.ts",O={name:E(__filename),sql:(e)=>{return[n`
48
+ CREATE TABLE ${s(e.schema)}."channel_policy" (
42
49
  "id" UUID NOT NULL DEFAULT GEN_RANDOM_UUID(),
43
50
  "name" TEXT NOT NULL,
44
51
  "max_size" INTEGER,
@@ -47,11 +54,11 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
47
54
  "created_at" TIMESTAMP NOT NULL,
48
55
  PRIMARY KEY ("id")
49
56
  );
50
- `,s`
57
+ `,n`
51
58
  CREATE UNIQUE INDEX "channel_policy_name_ux"
52
- ON ${n(e.schema)}."channel_policy" ("name");
53
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/01-table-channel-state.ts",O={name:E(__filename),sql:(e)=>{return[s`
54
- CREATE TABLE ${n(e.schema)}."channel_state" (
59
+ ON ${s(e.schema)}."channel_policy" ("name");
60
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/01-table-channel-state.ts",f={name:E(__filename),sql:(e)=>{return[n`
61
+ CREATE TABLE ${s(e.schema)}."channel_state" (
55
62
  "id" UUID NOT NULL DEFAULT GEN_RANDOM_UUID(),
56
63
  "name" TEXT NOT NULL,
57
64
  "max_size" INTEGER,
@@ -67,17 +74,17 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
67
74
  "created_at" TIMESTAMP NOT NULL,
68
75
  PRIMARY KEY ("id")
69
76
  );
70
- `,s`
77
+ `,n`
71
78
  CREATE UNIQUE INDEX "channel_state_name_ux"
72
- ON ${n(e.schema)}."channel_state" ("name");
73
- `,s`
79
+ ON ${s(e.schema)}."channel_state" ("name");
80
+ `,n`
74
81
  CREATE INDEX "channel_state_dequeue_ix"
75
- ON ${n(e.schema)}."channel_state" (
82
+ ON ${s(e.schema)}."channel_state" (
76
83
  "active_next_at" ASC
77
84
  ) WHERE "message_id" IS NOT NULL
78
85
  AND ("max_concurrency" IS NULL OR "current_concurrency" < "max_concurrency");
79
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/02-table-message.ts",f={name:E(__filename),sql:(e)=>{return[s`
80
- CREATE TABLE ${n(e.schema)}."message" (
86
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/02-table-message.ts",x={name:E(__filename),sql:(e)=>{return[n`
87
+ CREATE TABLE ${s(e.schema)}."message" (
81
88
  "id" UUID NOT NULL,
82
89
  "channel_name" TEXT NOT NULL,
83
90
  "seq_no" BIGSERIAL NOT NULL,
@@ -92,26 +99,26 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
92
99
  "created_at" TIMESTAMP NOT NULL,
93
100
  PRIMARY KEY ("id")
94
101
  );
95
- `,s`
102
+ `,n`
96
103
  CREATE UNIQUE INDEX "message_name_ux"
97
- ON ${n(e.schema)}."message" (
104
+ ON ${s(e.schema)}."message" (
98
105
  "channel_name",
99
106
  "name"
100
107
  ) WHERE "num_attempts" = 0
101
- `,s`
108
+ `,n`
102
109
  CREATE INDEX "message_dequeue_ix"
103
- ON ${n(e.schema)}."message" (
110
+ ON ${s(e.schema)}."message" (
104
111
  "channel_name",
105
112
  "dequeue_at" ASC,
106
113
  "seq_no" ASC
107
114
  ) WHERE NOT "is_locked";
108
- `,s`
115
+ `,n`
109
116
  CREATE INDEX "message_locked_dequeue_ix"
110
- ON ${n(e.schema)}."message" (
117
+ ON ${s(e.schema)}."message" (
111
118
  "unlock_at" ASC
112
119
  ) WHERE "is_locked";
113
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/03-function-message-create.ts",x={name:E(__filename),sql:(e)=>{return[s`
114
- CREATE FUNCTION ${n(e.schema)}."message_create" (
120
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/03-function-message-create.ts",G={name:E(__filename),sql:(e)=>{return[n`
121
+ CREATE FUNCTION ${s(e.schema)}."message_create" (
115
122
  p_id UUID,
116
123
  p_channel_name TEXT,
117
124
  p_name TEXT,
@@ -134,12 +141,12 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
134
141
  "channel_policy"."max_size",
135
142
  "channel_policy"."max_concurrency",
136
143
  "channel_policy"."release_interval_ms"
137
- FROM ${n(e.schema)}."channel_policy"
144
+ FROM ${s(e.schema)}."channel_policy"
138
145
  WHERE "name" = p_channel_name
139
146
  FOR SHARE
140
147
  INTO v_channel_policy;
141
148
 
142
- INSERT INTO ${n(e.schema)}."channel_state" (
149
+ INSERT INTO ${s(e.schema)}."channel_state" (
143
150
  "name",
144
151
  "current_size",
145
152
  "current_concurrency",
@@ -178,7 +185,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
178
185
  RETURN;
179
186
  END IF;
180
187
 
181
- INSERT INTO ${n(e.schema)}."message" (
188
+ INSERT INTO ${s(e.schema)}."message" (
182
189
  "id",
183
190
  "channel_name",
184
191
  "name",
@@ -220,7 +227,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
220
227
  v_message."dequeue_at" < v_channel_state."message_dequeue_at" OR
221
228
  v_message."dequeue_at" = v_channel_state."message_dequeue_at" AND v_message."seq_no" < v_channel_state."message_seq_no"
222
229
  THEN
223
- UPDATE ${n(e.schema)}."channel_state" SET
230
+ UPDATE ${s(e.schema)}."channel_state" SET
224
231
  "current_size" = v_channel_state."current_size" + 1,
225
232
  "message_id" = v_message."id",
226
233
  "message_dequeue_at" = v_message."dequeue_at",
@@ -231,7 +238,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
231
238
  )
232
239
  WHERE "id" = v_channel_state."id";
233
240
  ELSE
234
- UPDATE ${n(e.schema)}."channel_state" SET
241
+ UPDATE ${s(e.schema)}."channel_state" SET
235
242
  "current_size" = v_channel_state."current_size" + 1
236
243
  WHERE "id" = v_channel_state."id";
237
244
  END IF;
@@ -252,8 +259,8 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
252
259
  RETURN;
253
260
  END;
254
261
  $$ LANGUAGE plpgsql;
255
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/04-function-message-dequeue.ts",G={name:E(__filename),sql:(e)=>{return[s`
256
- CREATE FUNCTION ${n(e.schema)}."message_dequeue" ()
262
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/04-function-message-dequeue.ts",F={name:E(__filename),sql:(e)=>{return[n`
263
+ CREATE FUNCTION ${s(e.schema)}."message_dequeue" ()
257
264
  RETURNS TABLE (
258
265
  result_code INTEGER,
259
266
  content BYTEA,
@@ -278,7 +285,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
278
285
  "message"."lock_ms",
279
286
  "message"."unlock_at",
280
287
  "message"."num_attempts"
281
- FROM ${n(e.schema)}."message"
288
+ FROM ${s(e.schema)}."message"
282
289
  WHERE "is_locked"
283
290
  AND "unlock_at" <= v_now
284
291
  ORDER BY "unlock_at" ASC
@@ -288,7 +295,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
288
295
  INTO v_message_locked;
289
296
 
290
297
  IF v_message_locked."id" IS NOT NULL THEN
291
- UPDATE ${n(e.schema)}."message" SET
298
+ UPDATE ${s(e.schema)}."message" SET
292
299
  "num_attempts" = v_message_locked."num_attempts" + 1,
293
300
  "unlock_at" = v_now + (v_message_locked."lock_ms" * INTERVAL '1 millisecond')
294
301
  WHERE "id" = v_message_locked."id";
@@ -302,7 +309,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
302
309
  'is_unlocked', TRUE,
303
310
  'channel_name', v_message_locked.channel_name,
304
311
  'name', v_message_locked.name,
305
- 'num_attempts', v_message_locked.num_attempts
312
+ 'num_attempts', v_message_locked.num_attempts + 1
306
313
  );
307
314
  RETURN;
308
315
  END IF;
@@ -315,7 +322,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
315
322
  "channel_state"."active_next_at",
316
323
  "channel_state"."active_prev_at",
317
324
  "channel_state"."current_concurrency"
318
- FROM ${n(e.schema)}."channel_state"
325
+ FROM ${s(e.schema)}."channel_state"
319
326
  WHERE "message_id" IS NOT NULL
320
327
  AND ("max_concurrency" IS NULL OR "current_concurrency" < "max_concurrency")
321
328
  ORDER BY "active_next_at" ASC
@@ -352,11 +359,11 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
352
359
  "message"."num_attempts",
353
360
  "message"."state",
354
361
  "message"."lock_ms"
355
- FROM ${n(e.schema)}."message"
362
+ FROM ${s(e.schema)}."message"
356
363
  WHERE "id" = v_channel_state."message_id"
357
364
  INTO v_message_dequeue;
358
365
 
359
- UPDATE ${n(e.schema)}."message" SET
366
+ UPDATE ${s(e.schema)}."message" SET
360
367
  "is_locked" = TRUE,
361
368
  "num_attempts" = v_message_dequeue."num_attempts" + 1,
362
369
  "unlock_at" = v_now + (v_message_dequeue."lock_ms" * INTERVAL '1 millisecond')
@@ -366,7 +373,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
366
373
  "message"."id",
367
374
  "message"."dequeue_at",
368
375
  "message"."seq_no"
369
- FROM ${n(e.schema)}."message"
376
+ FROM ${s(e.schema)}."message"
370
377
  WHERE NOT "is_locked"
371
378
  AND "channel_name" = v_message_dequeue."channel_name"
372
379
  ORDER BY "dequeue_at" ASC, "seq_no" ASC
@@ -374,13 +381,13 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
374
381
  INTO v_message_next;
375
382
 
376
383
  IF v_message_next."id" IS NULL THEN
377
- UPDATE ${n(e.schema)}."channel_state" SET
384
+ UPDATE ${s(e.schema)}."channel_state" SET
378
385
  "current_concurrency" = v_channel_state."current_concurrency" + 1,
379
386
  "active_prev_at" = v_now,
380
387
  "message_id" = NULL
381
388
  WHERE "id" = v_channel_state."id";
382
389
  ELSE
383
- UPDATE ${n(e.schema)}."channel_state" SET
390
+ UPDATE ${s(e.schema)}."channel_state" SET
384
391
  "current_concurrency" = v_channel_state."current_concurrency" + 1,
385
392
  "message_id" = v_message_next."id",
386
393
  "message_dequeue_at" = v_message_next."dequeue_at",
@@ -402,14 +409,15 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
402
409
  'is_unlocked', FALSE,
403
410
  'channel_name', v_message_dequeue.channel_name,
404
411
  'name', v_message_dequeue.name,
405
- 'num_attempts', v_message_dequeue.num_attempts
412
+ 'num_attempts', v_message_dequeue.num_attempts + 1
406
413
  );
407
414
  RETURN;
408
415
  END;
409
416
  $$ LANGUAGE plpgsql;
410
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/05-function-message-delete.ts",F={name:E(__filename),sql:(e)=>{return[s`
411
- CREATE FUNCTION ${n(e.schema)}."message_delete" (
412
- p_id UUID
417
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/05-function-message-delete.ts",q={name:E(__filename),sql:(e)=>{return[n`
418
+ CREATE FUNCTION ${s(e.schema)}."message_delete" (
419
+ p_id UUID,
420
+ p_num_attempts BIGINT
413
421
  )
414
422
  RETURNS TABLE (
415
423
  result_code INTEGER
@@ -422,8 +430,9 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
422
430
  SELECT
423
431
  "message"."id",
424
432
  "message"."channel_name",
433
+ "message"."num_attempts",
425
434
  "message"."is_locked"
426
- FROM ${n(e.schema)}."message"
435
+ FROM ${s(e.schema)}."message"
427
436
  WHERE "id" = p_id
428
437
  FOR UPDATE
429
438
  INTO v_message;
@@ -432,7 +441,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
432
441
  RETURN QUERY SELECT
433
442
  ${r(0)};
434
443
  RETURN;
435
- ELSIF NOT v_message."is_locked" THEN
444
+ ELSIF NOT v_message."is_locked" OR v_message."num_attempts" <> p_num_attempts THEN
436
445
  RETURN QUERY SELECT
437
446
  ${r(1)};
438
447
  RETURN;
@@ -440,7 +449,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
440
449
 
441
450
  SELECT
442
451
  "channel_policy"."id"
443
- FROM ${n(e.schema)}."channel_policy"
452
+ FROM ${s(e.schema)}."channel_policy"
444
453
  WHERE "name" = v_message."channel_name"
445
454
  FOR SHARE
446
455
  INTO v_channel_policy;
@@ -449,16 +458,16 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
449
458
  "channel_state"."id",
450
459
  "channel_state"."current_size",
451
460
  "channel_state"."current_concurrency"
452
- FROM ${n(e.schema)}."channel_state"
461
+ FROM ${s(e.schema)}."channel_state"
453
462
  WHERE "name" = v_message."channel_name"
454
463
  FOR UPDATE
455
464
  INTO v_channel_state;
456
465
 
457
466
  IF v_channel_policy."id" IS NULL AND v_channel_state."current_size" = 1 THEN
458
- DELETE FROM ${n(e.schema)}."channel_state"
467
+ DELETE FROM ${s(e.schema)}."channel_state"
459
468
  WHERE "id" = v_channel_state."id";
460
469
  ELSE
461
- UPDATE ${n(e.schema)}."channel_state" SET
470
+ UPDATE ${s(e.schema)}."channel_state" SET
462
471
  "current_concurrency" = v_channel_state."current_concurrency" - 1,
463
472
  "current_size" = v_channel_state."current_size" - 1
464
473
  WHERE "id" = v_channel_state."id";
@@ -474,7 +483,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
474
483
  );
475
484
  END IF;
476
485
 
477
- DELETE FROM ${n(e.schema)}."message"
486
+ DELETE FROM ${s(e.schema)}."message"
478
487
  WHERE "id" = p_id;
479
488
 
480
489
  RETURN QUERY SELECT
@@ -482,9 +491,10 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
482
491
  RETURN;
483
492
  END;
484
493
  $$ LANGUAGE plpgsql;
485
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/06-function-message-defer.ts",q={name:E(__filename),sql:(e)=>{return[s`
486
- CREATE FUNCTION ${n(e.schema)}."message_defer" (
494
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/06-function-message-defer.ts",$={name:E(__filename),sql:(e)=>{return[n`
495
+ CREATE FUNCTION ${s(e.schema)}."message_defer" (
487
496
  p_id UUID,
497
+ p_num_attempts BIGINT,
488
498
  p_delay_ms BIGINT,
489
499
  p_state BYTEA
490
500
  )
@@ -502,9 +512,10 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
502
512
  SELECT
503
513
  "message"."id",
504
514
  "message"."channel_name",
515
+ "message"."num_attempts",
505
516
  "message"."is_locked",
506
517
  "message"."seq_no"
507
- FROM ${n(e.schema)}."message"
518
+ FROM ${s(e.schema)}."message"
508
519
  WHERE "id" = p_id
509
520
  FOR UPDATE
510
521
  INTO v_message;
@@ -513,7 +524,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
513
524
  RETURN QUERY SELECT
514
525
  ${r(0)};
515
526
  RETURN;
516
- ELSIF NOT v_message."is_locked" THEN
527
+ ELSIF NOT v_message."is_locked" OR v_message."num_attempts" <> p_num_attempts THEN
517
528
  RETURN QUERY SELECT
518
529
  ${r(1)};
519
530
  RETURN;
@@ -526,7 +537,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
526
537
  "channel_state"."message_dequeue_at",
527
538
  "channel_state"."active_prev_at",
528
539
  "channel_state"."message_seq_no"
529
- FROM ${n(e.schema)}."channel_state"
540
+ FROM ${s(e.schema)}."channel_state"
530
541
  WHERE "name" = v_message."channel_name"
531
542
  FOR UPDATE
532
543
  INTO v_channel_state;
@@ -538,7 +549,7 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
538
549
  v_dequeue_at < v_channel_state."message_dequeue_at" OR
539
550
  v_dequeue_at = v_channel_state."message_dequeue_at" AND v_message."seq_no" < v_channel_state."message_seq_no"
540
551
  THEN
541
- UPDATE ${n(e.schema)}."channel_state" SET
552
+ UPDATE ${s(e.schema)}."channel_state" SET
542
553
  "current_concurrency" = v_channel_state."current_concurrency" - 1,
543
554
  "message_id" = v_message."id",
544
555
  "message_dequeue_at" = v_dequeue_at,
@@ -549,12 +560,12 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
549
560
  )
550
561
  WHERE "name" = v_message."channel_name";
551
562
  ELSE
552
- UPDATE ${n(e.schema)}."channel_state" SET
563
+ UPDATE ${s(e.schema)}."channel_state" SET
553
564
  "current_concurrency" = v_channel_state."current_concurrency" - 1
554
565
  WHERE "name" = v_message."channel_name";
555
566
  END IF;
556
567
 
557
- UPDATE ${n(e.schema)}."message" SET
568
+ UPDATE ${s(e.schema)}."message" SET
558
569
  "state" = p_state,
559
570
  "is_locked" = FALSE,
560
571
  "dequeue_at" = v_dequeue_at
@@ -576,65 +587,72 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
576
587
  RETURN;
577
588
  END;
578
589
  $$ LANGUAGE plpgsql;
579
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/07-function-channel-policy-set.ts",$={name:E(__filename),sql:(e)=>{return[s`
580
- CREATE FUNCTION ${n(e.schema)}."channel_policy_set" (
581
- p_name TEXT,
582
- p_max_size INTEGER,
583
- p_max_concurrency INTEGER,
584
- p_release_interval_ms INTEGER
585
- ) RETURNS VOID AS $$
590
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/07-function-message-heartbeat.ts",b={name:E(__filename),sql:(e)=>{return[n`
591
+ CREATE FUNCTION ${s(e.schema)}."message_heartbeat" (
592
+ p_id UUID,
593
+ p_num_attempts BIGINT
594
+ )
595
+ RETURNS TABLE (
596
+ result_code INTEGER
597
+ ) AS $$
586
598
  DECLARE
587
599
  v_now TIMESTAMP;
600
+ v_message RECORD;
588
601
  BEGIN
589
602
  v_now := NOW();
590
603
 
591
- INSERT INTO ${n(e.schema)}."channel_policy" (
592
- "name",
593
- "max_size",
594
- "max_concurrency",
595
- "release_interval_ms",
596
- "created_at"
597
- ) VALUES (
598
- p_name,
599
- p_max_size,
600
- p_max_concurrency,
601
- p_release_interval_ms,
602
- v_now
603
- ) ON CONFLICT ("name") DO UPDATE SET
604
- "max_size" = EXCLUDED."max_size",
605
- "max_concurrency" = EXCLUDED."max_concurrency",
606
- "release_interval_ms" = EXCLUDED."release_interval_ms";
604
+ SELECT
605
+ "message"."id",
606
+ "message"."is_locked",
607
+ "message"."num_attempts",
608
+ "message"."lock_ms"
609
+ FROM ${s(e.schema)}."message"
610
+ WHERE "id" = p_id
611
+ FOR UPDATE
612
+ INTO v_message;
607
613
 
608
- UPDATE ${n(e.schema)}."channel_state" SET
609
- "max_size" = p_max_size,
610
- "max_concurrency" = p_max_concurrency,
611
- "release_interval_ms" = p_release_interval_ms
612
- WHERE "name" = p_name;
614
+ IF v_message."id" IS NULL THEN
615
+ RETURN QUERY SELECT
616
+ ${r(0)};
617
+ RETURN;
618
+ ELSIF NOT v_message."is_locked" OR v_message."num_attempts" <> p_num_attempts THEN
619
+ RETURN QUERY SELECT
620
+ ${r(1)};
621
+ RETURN;
622
+ END IF;
623
+
624
+ UPDATE ${s(e.schema)}."message" SET
625
+ "unlock_at" = v_now + INTERVAL '1 MILLISECOND' * v_message."lock_ms"
626
+ WHERE "id" = p_id;
627
+
628
+ RETURN QUERY SELECT
629
+ ${r(2)};
630
+ RETURN;
613
631
  END;
614
632
  $$ LANGUAGE plpgsql;
615
- `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/08-function-channel-policy-clear.ts",B={name:E(__filename),sql:(e)=>{return[s`
616
- CREATE FUNCTION ${n(e.schema)}."channel_policy_clear" (
633
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/08-function-channel-policy-clear.ts",B={name:E(__filename),sql:(e)=>{return[n`
634
+ CREATE FUNCTION ${s(e.schema)}."channel_policy_clear" (
617
635
  p_name TEXT
618
636
  ) RETURNS VOID AS $$
619
637
  DECLARE
620
638
  v_channel_state RECORD;
621
639
  BEGIN
622
- DELETE FROM ${n(e.schema)}."channel_policy"
640
+ DELETE FROM ${s(e.schema)}."channel_policy"
623
641
  WHERE "name" = p_name;
624
642
 
625
643
  SELECT
626
644
  "channel_state"."id",
627
645
  "channel_state"."current_size"
628
- FROM ${n(e.schema)}."channel_state"
646
+ FROM ${s(e.schema)}."channel_state"
629
647
  WHERE "name" = p_name
630
648
  FOR UPDATE
631
649
  INTO v_channel_state;
632
650
 
633
651
  IF v_channel_state."current_size" = 0 THEN
634
- DELETE FROM ${n(e.schema)}."channel_state"
652
+ DELETE FROM ${s(e.schema)}."channel_state"
635
653
  WHERE "id" = v_channel_state."id";
636
654
  ELSE
637
- UPDATE ${n(e.schema)}."channel_state" SET
655
+ UPDATE ${s(e.schema)}."channel_state" SET
638
656
  "max_size" = NULL,
639
657
  "max_concurrency" = NULL,
640
658
  "release_interval_ms" = NULL
@@ -642,4 +660,40 @@ var r=(e)=>({nodeType:"VALUE",value:e}),n=(e)=>({nodeType:"REF",value:e}),Q=(e)=
642
660
  END IF;
643
661
  END;
644
662
  $$ LANGUAGE plpgsql;
645
- `]}};class R{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}create(e){let t=new m({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}),a=new Promise((_)=>{this.registerFn({sortKey:JSON.stringify([t.channelName,t.name,t.createdAt.toISOString()]),execute:(T)=>t.execute(T).then((b)=>_(b))})});return{messageId:t.id,promise:a}}}class g{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}set(e){let t=new c({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs});this.registerFn({sortKey:JSON.stringify([t.channelName,null,t.createdAt.toISOString()]),execute:async(a)=>{await t.execute(a)}})}clear(){let e=new l({schema:this.schema,channelName:this.channelName});this.registerFn({sortKey:JSON.stringify([e.channelName,null,e.createdAt.toISOString()]),execute:async(t)=>{await e.execute(t)}})}}class S{policy;message;constructor(e){this.message=new R(e),this.policy=new g(e)}}var te=(e,t)=>{return e.sortKey.localeCompare(t.sortKey)};class D{commands;schema;constructor(e){this.commands=[],this.schema=e.schema}channel(e){return new S({schema:this.schema,channelName:e,registerFn:(t)=>{this.commands.push(t)}})}async execute(e){for(let t of this.commands.sort(te))await t.execute(e.databaseClient)}}class A{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}async create(e){return new m({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}).execute(e.databaseClient)}}class y{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}set(e){return new c({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs}).execute(e.databaseClient)}clear(e){return new l({schema:this.schema,channelName:this.channelName}).execute(e.databaseClient)}}class M{policy;message;constructor(e){this.message=new A({schema:e.schema,channelName:e.channelName}),this.policy=new y({schema:e.schema,channelName:e.channelName})}}class p{schema;id;channelName;name;content;state;numAttempts;constructor(e){this.schema=e.schema,this.id=e.id,this.channelName=e.channelName,this.name=e.name,this.content=e.content,this.state=e.state,this.numAttempts=e.numAttempts}async defer(e){return new d({schema:this.schema,id:this.id,delayMs:e.delayMs,state:e.state}).execute(e.databaseClient)}async delete(e){return new u({schema:this.schema,id:this.id}).execute(e.databaseClient)}}class P{schema;constructor(e){this.schema=e.schema}async dequeue(e){let a=await new i({schema:this.schema}).execute(e.databaseClient);if(a.resultType==="MESSAGE_DEQUEUED")return{resultType:"MESSAGE_DEQUEUED",message:new p({schema:this.schema,id:a.message.id,channelName:a.message.channelName,name:a.message.name,content:a.message.content,state:a.message.state,numAttempts:a.message.numAttempts})};else return a}channel(e){return new M({schema:this.schema,channelName:e})}batch(){return new D({schema:this.schema})}migrations(e={}){return[U,O,f,x,G,F,q,$,B].sort((t,a)=>t.name.localeCompare(a.name)).flatMap((t)=>t.sql({schema:this.schema,eventChannel:e.eventChannel??null})).map((t)=>L(t.value))}}export{W as queueEventDecode,P as Queue,i as MessageDequeueCommand,u as MessageDeleteCommand,d as MessageDeferCommand,m as MessageCreateCommand,c as ChannelPolicySetCommand,l as ChannelPolicyClearCommand};
663
+ `]}};var __filename="/home/runner/work/lonnymq/lonnymq/src/migration/09-function-channel-policy-set.ts",P={name:E(__filename),sql:(e)=>{return[n`
664
+ CREATE FUNCTION ${s(e.schema)}."channel_policy_set" (
665
+ p_name TEXT,
666
+ p_max_size INTEGER,
667
+ p_max_concurrency INTEGER,
668
+ p_release_interval_ms INTEGER
669
+ ) RETURNS VOID AS $$
670
+ DECLARE
671
+ v_now TIMESTAMP;
672
+ BEGIN
673
+ v_now := NOW();
674
+
675
+ INSERT INTO ${s(e.schema)}."channel_policy" (
676
+ "name",
677
+ "max_size",
678
+ "max_concurrency",
679
+ "release_interval_ms",
680
+ "created_at"
681
+ ) VALUES (
682
+ p_name,
683
+ p_max_size,
684
+ p_max_concurrency,
685
+ p_release_interval_ms,
686
+ v_now
687
+ ) ON CONFLICT ("name") DO UPDATE SET
688
+ "max_size" = EXCLUDED."max_size",
689
+ "max_concurrency" = EXCLUDED."max_concurrency",
690
+ "release_interval_ms" = EXCLUDED."release_interval_ms";
691
+
692
+ UPDATE ${s(e.schema)}."channel_state" SET
693
+ "max_size" = p_max_size,
694
+ "max_concurrency" = p_max_concurrency,
695
+ "release_interval_ms" = p_release_interval_ms
696
+ WHERE "name" = p_name;
697
+ END;
698
+ $$ LANGUAGE plpgsql;
699
+ `]}};class R{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}create(e){let t=new c({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}),a=new Promise((_)=>{this.registerFn({sortKey:JSON.stringify([t.channelName,t.name,t.createdAt.toISOString()]),execute:(T)=>t.execute(T).then((H)=>_(H))})});return{messageId:t.id,promise:a}}}class S{schema;channelName;registerFn;constructor(e){this.schema=e.schema,this.channelName=e.channelName,this.registerFn=e.registerFn}set(e){let t=new m({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs});this.registerFn({sortKey:JSON.stringify([t.channelName,null,t.createdAt.toISOString()]),execute:async(a)=>{await t.execute(a)}})}clear(){let e=new l({schema:this.schema,channelName:this.channelName});this.registerFn({sortKey:JSON.stringify([e.channelName,null,e.createdAt.toISOString()]),execute:async(t)=>{await e.execute(t)}})}}class g{policy;message;constructor(e){this.message=new R(e),this.policy=new S(e)}}var ae=(e,t)=>{return e.sortKey.localeCompare(t.sortKey)};class A{commands;schema;constructor(e){this.commands=[],this.schema=e.schema}channel(e){return new g({schema:this.schema,channelName:e,registerFn:(t)=>{this.commands.push(t)}})}async execute(e){for(let t of this.commands.sort(ae))await t.execute(e.databaseClient)}}class D{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}async create(e){return new c({schema:this.schema,channelName:this.channelName,name:e.name,content:e.content,lockMs:e.lockMs,delayMs:e.delayMs}).execute(e.databaseClient)}}class p{schema;channelName;constructor(e){this.schema=e.schema,this.channelName=e.channelName}set(e){return new m({schema:this.schema,channelName:this.channelName,maxConcurrency:e.maxConcurrency,maxSize:e.maxSize,releaseIntervalMs:e.releaseIntervalMs}).execute(e.databaseClient)}clear(e){return new l({schema:this.schema,channelName:this.channelName}).execute(e.databaseClient)}}class M{policy;message;constructor(e){this.message=new D({schema:e.schema,channelName:e.channelName}),this.policy=new p({schema:e.schema,channelName:e.channelName})}}class y{schema;id;isUnlocked;channelName;name;content;state;numAttempts;constructor(e){this.schema=e.schema,this.id=e.id,this.channelName=e.channelName,this.isUnlocked=e.isUnlocked,this.name=e.name,this.content=e.content,this.state=e.state,this.numAttempts=e.numAttempts}async defer(e){return new o({schema:this.schema,id:this.id,numAttempts:this.numAttempts,delayMs:e.delayMs,state:e.state}).execute(e.databaseClient)}async delete(e){return new d({schema:this.schema,numAttempts:this.numAttempts,id:this.id}).execute(e.databaseClient)}async heartbeat(e){return new o({schema:this.schema,id:this.id,numAttempts:this.numAttempts,delayMs:e.delayMs}).execute(e.databaseClient)}}class Q{schema;constructor(e){this.schema=e.schema}async dequeue(e){let a=await new u({schema:this.schema}).execute(e.databaseClient);if(a.resultType==="MESSAGE_DEQUEUED")return{resultType:"MESSAGE_DEQUEUED",message:new y({schema:this.schema,id:a.message.id,channelName:a.message.channelName,name:a.message.name,isUnlocked:a.message.isUnlocked,content:a.message.content,state:a.message.state,numAttempts:a.message.numAttempts})};else return a}channel(e){return new M({schema:this.schema,channelName:e})}batch(){return new A({schema:this.schema})}migrations(e={}){return[O,f,x,G,F,q,$,b,P,B].sort((t,a)=>t.name.localeCompare(a.name)).flatMap((t)=>t.sql({schema:this.schema,eventChannel:e.eventChannel??null})).map((t)=>L(t.value))}}export{X as queueEventDecode,Q as Queue,v as MessageHeartbeatCommand,u as MessageDequeueCommand,d as MessageDeleteCommand,o as MessageDeferCommand,c as MessageCreateCommand,m as ChannelPolicySetCommand,l as ChannelPolicyClearCommand};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "lonnymq",
3
- "version": "0.0.12",
3
+ "version": "0.0.14",
4
4
  "type": "module",
5
5
  "exports": {
6
6
  ".": {