@abdssamie/convex-checkpoints 0.1.1 → 0.1.7

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/README.md CHANGED
@@ -29,30 +29,7 @@ export default app;
29
29
 
30
30
  ## Usage
31
31
 
32
- Define your checkpoint registry in app code and expose wrapper functions from
33
- your own app modules. That keeps auth, permission checks, and business rules
34
- close to the rest of your application code.
35
-
36
- Expose checkpoint submissions as Convex mutations by default. Mutations are the
37
- right fit when recording a checkpoint, updating Convex data, reading Convex
38
- data, or scheduling follow-up work from a handler.
39
-
40
- Use an action only when the submit path needs external, non-transactional work,
41
- such as calling a third-party API, sending an email directly, using Node APIs,
42
- or doing longer-running processing. For most integrations, keep the checkpoint
43
- submission in a mutation and schedule an internal action from the checkpoint
44
- handler:
45
-
46
- ```ts
47
- checkpoints.on("user.signup", async (ctx, payload) => {
48
- await ctx.scheduler.runAfter(0, internal.emails.sendWelcome, {
49
- userId: payload.userId,
50
- });
51
- });
52
- ```
53
-
54
- Actions are not database transactions, so design retries and idempotency
55
- explicitly when external systems are involved.
32
+ There are two steps: define your checkpoint registry with handlers, then expose submit mutations for your app to call.
56
33
 
57
34
  ```ts
58
35
  // convex/checkpoints.ts
@@ -62,10 +39,11 @@ import { v } from "convex/values";
62
39
  import { ConvexCheckpoints } from "@abdssamie/convex-checkpoints";
63
40
 
64
41
  export const checkpoints = new ConvexCheckpoints<{
65
- "user.signup": { userId: string };
42
+ "user.signup": { userId: string; email: string };
66
43
  "post.created": { userId: string; postId: string; title: string };
67
44
  }>(components.convexCheckpoints);
68
45
 
46
+ // Handlers run when a checkpoint is first recorded (deduplicated by idempotencyKey)
69
47
  checkpoints.on("user.signup", async (ctx, payload) => {
70
48
  await ctx.scheduler.runAfter(30 * 60 * 1000, internal.emails.welcome, {
71
49
  userId: payload.userId,
@@ -85,6 +63,7 @@ checkpoints.on("post.created", async (ctx, payload) => {
85
63
  }
86
64
  });
87
65
 
66
+ // Submit mutations — called from your app code
88
67
  export const submitPostCreated = mutation({
89
68
  args: {
90
69
  userId: v.string(),
@@ -144,34 +123,48 @@ checkpoint ID and skip handler re-execution.
144
123
 
145
124
  ## HTTP
146
125
 
147
- Expose an HTTP route from your app when you need checkpoint ingestion over HTTP:
126
+ Prefer mutation wrappers for app-driven checkpoints. They run inside your app's
127
+ Convex functions, so you can authenticate the user, validate the input, write
128
+ app data, and submit the checkpoint in one place.
129
+
130
+ HTTP ingestion is for server-to-server entry points such as webhooks or trusted
131
+ backend jobs. Treat it as a public endpoint: anyone who can reach the URL can
132
+ try to submit a checkpoint unless you verify the request.
148
133
 
149
134
  ```ts
150
135
  // convex/http.ts
151
136
  import { checkpoints } from "./checkpoints.js";
152
137
 
153
- export default checkpoints.http("/checkpoints");
138
+ export default checkpoints.http("/checkpoints", {
139
+ token: process.env.CHECKPOINTS_SECRET,
140
+ });
154
141
  ```
155
142
 
143
+ Requests must include `Authorization: Bearer <token>`. Keep
144
+ `CHECKPOINTS_SECRET` in server-side environment variables only. If the token
145
+ option is configured but the environment variable is missing or empty, HTTP
146
+ checkpoint submissions are rejected.
147
+
156
148
  This registers both `POST /checkpoints` and checkpoint-specific routes such as
157
149
  `POST /checkpoints/post.created`.
158
150
 
159
- For checkpoint-specific routes, the request body is used as the checkpoint
160
- payload:
151
+ For checkpoint-specific routes, the route selects the checkpoint name and the
152
+ request body becomes the payload:
161
153
 
162
154
  ```sh
163
155
  curl -X POST "$CONVEX_SITE_URL/checkpoints/post.created" \
164
156
  -H "Content-Type: application/json" \
157
+ -H "Authorization: Bearer $CHECKPOINTS_SECRET" \
165
158
  -d '{"userId":"user1","postId":"post1"}'
166
159
  ```
167
160
 
168
- `POST /checkpoints` still accepts JSON with `name`, optional `userId`, optional
169
- `payload`, optional `idempotencyKey`, and optional `reachedAt`.
161
+ For webhook providers, verify the provider's signature in `authorize`. The
162
+ request is cloned before authorization runs, so signature checks can read the
163
+ body without preventing checkpoint parsing afterward.
170
164
 
171
- TypeScript checks payload types for `checkpoints.on(...)`,
172
- `checkpoints.trigger(...)`, and `checkpoints.submit(ctx, ...)` inside Convex
173
- code. Public Convex mutations and HTTP requests still need app-defined runtime
174
- validators because TypeScript types are not available at runtime.
165
+ Do not put a checkpoint HTTP secret in browser code. If a user action in your
166
+ app should submit a checkpoint, expose a Convex mutation instead and call
167
+ `checkpoints.submit(ctx, ...)` from that mutation.
175
168
 
176
169
  ## Tests
177
170
 
@@ -11,6 +11,10 @@ type SubmitArgs<TCheckpointRegistry extends CheckpointRegistry, TCheckpoint exte
11
11
  name: TCheckpoint;
12
12
  payload: TCheckpointRegistry[TCheckpoint];
13
13
  };
14
+ type HttpOptions = {
15
+ token?: string;
16
+ authorize?: (request: Request) => boolean | Promise<boolean>;
17
+ };
14
18
  export declare class ConvexCheckpoints<TCheckpointRegistry extends CheckpointRegistry> extends CheckpointDispatcher<TCheckpointRegistry> {
15
19
  private component;
16
20
  constructor(component: ComponentApi);
@@ -55,7 +59,7 @@ export declare class ConvexCheckpoints<TCheckpointRegistry extends CheckpointReg
55
59
  userId?: string;
56
60
  }[]>>;
57
61
  };
58
- http(path?: string): import("convex/server").HttpRouter;
62
+ http(path?: string, options?: HttpOptions): import("convex/server").HttpRouter;
59
63
  private submitFromArgs;
60
64
  }
61
65
  export type { CheckpointHandler };
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/client/index.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,sCAAsC,CAAC;AACzE,OAAO,EACL,iBAAiB,IAAI,oBAAoB,EACzC,KAAK,iBAAiB,EACvB,MAAM,sCAAsC,CAAC;AAE9C,KAAK,kBAAkB,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AAClD,KAAK,cAAc,CAAC,mBAAmB,SAAS,kBAAkB,IAAI,OAAO,CAC3E,MAAM,mBAAmB,EACzB,MAAM,CACP,CAAC;AAEF,KAAK,cAAc,GAAG;IACpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAOF,KAAK,UAAU,CACb,mBAAmB,SAAS,kBAAkB,EAC9C,WAAW,SAAS,cAAc,CAAC,mBAAmB,CAAC,IACrD,cAAc,GAAG;IACnB,IAAI,EAAE,WAAW,CAAC;IAClB,OAAO,EAAE,mBAAmB,CAAC,WAAW,CAAC,CAAC;CAC3C,CAAC;AAEF,qBAAa,iBAAiB,CAC5B,mBAAmB,SAAS,kBAAkB,CAC9C,SAAQ,oBAAoB,CAAC,mBAAmB,CAAC;IACrC,OAAO,CAAC,SAAS;gBAAT,SAAS,EAAE,YAAY;IAI9B,MAAM,CAAC,WAAW,SAAS,cAAc,CAAC,mBAAmB,CAAC,EACzE,GAAG,EAAE,UAAU,CAAC,iBAAiB,CAAC,mBAAmB,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,EACrE,IAAI,EAAE,UAAU,CAAC,mBAAmB,EAAE,WAAW,CAAC;IAS7C,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;IAuBH,IAAI,CAAC,IAAI,SAAiB;YAwDnB,cAAc;CAc7B;AAED,YAAY,EAAE,iBAAiB,EAAE,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/client/index.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,sCAAsC,CAAC;AACzE,OAAO,EACL,iBAAiB,IAAI,oBAAoB,EACzC,KAAK,iBAAiB,EACvB,MAAM,sCAAsC,CAAC;AAE9C,KAAK,kBAAkB,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AAClD,KAAK,cAAc,CAAC,mBAAmB,SAAS,kBAAkB,IAAI,OAAO,CAC3E,MAAM,mBAAmB,EACzB,MAAM,CACP,CAAC;AAEF,KAAK,cAAc,GAAG;IACpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAOF,KAAK,UAAU,CACb,mBAAmB,SAAS,kBAAkB,EAC9C,WAAW,SAAS,cAAc,CAAC,mBAAmB,CAAC,IACrD,cAAc,GAAG;IACnB,IAAI,EAAE,WAAW,CAAC;IAClB,OAAO,EAAE,mBAAmB,CAAC,WAAW,CAAC,CAAC;CAC3C,CAAC;AAEF,KAAK,WAAW,GAAG;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;CAC9D,CAAC;AAEF,qBAAa,iBAAiB,CAC5B,mBAAmB,SAAS,kBAAkB,CAC9C,SAAQ,oBAAoB,CAAC,mBAAmB,CAAC;IACrC,OAAO,CAAC,SAAS;gBAAT,SAAS,EAAE,YAAY;IAI9B,MAAM,CAAC,WAAW,SAAS,cAAc,CAAC,mBAAmB,CAAC,EACzE,GAAG,EAAE,UAAU,CAAC,iBAAiB,CAAC,mBAAmB,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,EACrE,IAAI,EAAE,UAAU,CAAC,mBAAmB,EAAE,WAAW,CAAC;IAS7C,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;IAuBH,IAAI,CAAC,IAAI,SAAiB,EAAE,OAAO,GAAE,WAAgB;YAgE9C,cAAc;CAc7B;AAED,YAAY,EAAE,iBAAiB,EAAE,CAAC"}
@@ -36,12 +36,15 @@ export class ConvexCheckpoints extends CheckpointDispatcher {
36
36
  }),
37
37
  };
38
38
  }
39
- http(path = "/checkpoints") {
39
+ http(path = "/checkpoints", options = {}) {
40
40
  const http = httpRouter();
41
41
  http.route({
42
42
  path,
43
43
  method: "POST",
44
44
  handler: httpActionGeneric(async (ctx, request) => {
45
+ if (!(await isAuthorized(request, options))) {
46
+ return json({ error: "unauthorized" }, 401);
47
+ }
45
48
  const args = await readSubmitArgsFromBody(request);
46
49
  if (args === null) {
47
50
  return json({ error: "invalid_checkpoint" }, 400);
@@ -60,6 +63,9 @@ export class ConvexCheckpoints extends CheckpointDispatcher {
60
63
  pathPrefix,
61
64
  method: "POST",
62
65
  handler: httpActionGeneric(async (ctx, request) => {
66
+ if (!(await isAuthorized(request, options))) {
67
+ return json({ error: "unauthorized" }, 401);
68
+ }
63
69
  const checkpointName = readCheckpointNameFromPath(request, pathPrefix);
64
70
  if (checkpointName === null) {
65
71
  return json({ error: "invalid_checkpoint_path" }, 400);
@@ -87,6 +93,21 @@ export class ConvexCheckpoints extends CheckpointDispatcher {
87
93
  return result;
88
94
  }
89
95
  }
96
+ async function isAuthorized(request, options) {
97
+ if ("token" in options) {
98
+ if (typeof options.token !== "string" || options.token.length === 0) {
99
+ return false;
100
+ }
101
+ const authorization = request.headers.get("authorization");
102
+ if (authorization !== `Bearer ${options.token}`) {
103
+ return false;
104
+ }
105
+ }
106
+ if (options.authorize === undefined) {
107
+ return true;
108
+ }
109
+ return await options.authorize(request.clone());
110
+ }
90
111
  async function readSubmitArgsFromBody(request) {
91
112
  const checkpoint = await readJsonObject(request);
92
113
  if (checkpoint === null || typeof checkpoint.name !== "string") {
@@ -171,7 +192,7 @@ function corsHeaders() {
171
192
  return {
172
193
  "Access-Control-Allow-Origin": "*",
173
194
  "Access-Control-Allow-Methods": "POST, OPTIONS",
174
- "Access-Control-Allow-Headers": "Content-Type",
195
+ "Access-Control-Allow-Headers": "Content-Type, Authorization",
175
196
  };
176
197
  }
177
198
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/client/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/client/index.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,12 +1,15 @@
1
1
  {
2
2
  "name": "@abdssamie/convex-checkpoints",
3
3
  "description": "A Convex component for event-driven user checkpoints.",
4
- "repository": "github:abdssamie/convex-checkpoints",
4
+ "repository": {
5
+ "type": "git",
6
+ "url": "git+https://gitlab.com/Abdssamie/convex-checkpoints.git"
7
+ },
5
8
  "homepage": "https://github.com/abdssamie/convex-checkpoints#readme",
6
9
  "bugs": {
7
10
  "url": "https://github.com/abdssamie/convex-checkpoints/issues"
8
11
  },
9
- "version": "0.1.1",
12
+ "version": "0.1.7",
10
13
  "license": "Apache-2.0",
11
14
  "keywords": [
12
15
  "convex",
@@ -15,6 +18,25 @@
15
18
  "checkpoints"
16
19
  ],
17
20
  "type": "module",
21
+ "scripts": {
22
+ "dev": "convex dev --start 'npm run dev:build'",
23
+ "dev:frontend": "cd example && vite",
24
+ "dev:build": "chokidar 'tsconfig*.json' 'src/**/*.ts' -i '**/*.test.ts' -c 'npm run build:codegen' --initial",
25
+ "predev": "convex init && npm run build:codegen",
26
+ "build": "tsc --project ./tsconfig.build.json",
27
+ "build:codegen": "npx convex codegen --component-dir ./src/component && npm run build",
28
+ "build:clean": "rm -rf dist *.tsbuildinfo && npm run build:codegen",
29
+ "typecheck": "tsc --noEmit && tsc -p example && tsc -p example/convex",
30
+ "lint": "eslint .",
31
+ "test": "vitest run --typecheck",
32
+ "test:watch": "vitest --typecheck --clearScreen false",
33
+ "test:debug": "vitest --inspect-brk --no-file-parallelism",
34
+ "test:coverage": "vitest run --coverage --coverage.reporter=text",
35
+ "preversion": "npm ci && npm run build:clean && npm run test && npm run lint && npm run typecheck",
36
+ "alpha": "npm version prerelease --preid alpha && npm publish --tag alpha && git push --follow-tags",
37
+ "release": "npm version patch && npm publish && git push --follow-tags",
38
+ "version": "(npm whoami || npm login) && vim -c 'normal o' -c 'normal o## '$npm_package_version CHANGELOG.md && prettier -w CHANGELOG.md && git add CHANGELOG.md"
39
+ },
18
40
  "files": [
19
41
  "dist",
20
42
  "src"
@@ -72,23 +94,10 @@
72
94
  },
73
95
  "types": "./dist/client/index.d.ts",
74
96
  "module": "./dist/client/index.js",
75
- "scripts": {
76
- "dev": "convex dev --start 'npm run dev:build'",
77
- "dev:frontend": "cd example && vite",
78
- "dev:build": "chokidar 'tsconfig*.json' 'src/**/*.ts' -i '**/*.test.ts' -c 'npm run build:codegen' --initial",
79
- "predev": "convex init && npm run build:codegen",
80
- "build": "tsc --project ./tsconfig.build.json",
81
- "build:codegen": "npx convex codegen --component-dir ./src/component && npm run build",
82
- "build:clean": "rm -rf dist *.tsbuildinfo && npm run build:codegen",
83
- "typecheck": "tsc --noEmit && tsc -p example && tsc -p example/convex",
84
- "lint": "eslint .",
85
- "test": "vitest run --typecheck",
86
- "test:watch": "vitest --typecheck --clearScreen false",
87
- "test:debug": "vitest --inspect-brk --no-file-parallelism",
88
- "test:coverage": "vitest run --coverage --coverage.reporter=text",
89
- "preversion": "npm ci && npm run build:clean && npm run test && npm run lint && npm run typecheck",
90
- "alpha": "npm version prerelease --preid alpha && npm publish --tag alpha && git push --follow-tags",
91
- "release": "npm version patch && npm publish && git push --follow-tags",
92
- "version": "(npm whoami || npm login) && vim -c 'normal o' -c 'normal o## '$npm_package_version CHANGELOG.md && prettier -w CHANGELOG.md && git add CHANGELOG.md"
97
+ "pnpm": {
98
+ "onlyBuiltDependencies": [
99
+ "esbuild",
100
+ "@tailwindcss/oxide"
101
+ ]
93
102
  }
94
- }
103
+ }
@@ -31,6 +31,11 @@ type SubmitArgs<
31
31
  payload: TCheckpointRegistry[TCheckpoint];
32
32
  };
33
33
 
34
+ type HttpOptions = {
35
+ token?: string;
36
+ authorize?: (request: Request) => boolean | Promise<boolean>;
37
+ };
38
+
34
39
  export class ConvexCheckpoints<
35
40
  TCheckpointRegistry extends CheckpointRegistry,
36
41
  > extends CheckpointDispatcher<TCheckpointRegistry> {
@@ -72,12 +77,16 @@ export class ConvexCheckpoints<
72
77
  };
73
78
  }
74
79
 
75
- public http(path = "/checkpoints") {
80
+ public http(path = "/checkpoints", options: HttpOptions = {}) {
76
81
  const http = httpRouter();
77
82
  http.route({
78
83
  path,
79
84
  method: "POST",
80
85
  handler: httpActionGeneric(async (ctx, request) => {
86
+ if (!(await isAuthorized(request, options))) {
87
+ return json({ error: "unauthorized" }, 401);
88
+ }
89
+
81
90
  const args = await readSubmitArgsFromBody(request);
82
91
  if (args === null) {
83
92
  return json({ error: "invalid_checkpoint" }, 400);
@@ -102,6 +111,10 @@ export class ConvexCheckpoints<
102
111
  pathPrefix,
103
112
  method: "POST",
104
113
  handler: httpActionGeneric(async (ctx, request) => {
114
+ if (!(await isAuthorized(request, options))) {
115
+ return json({ error: "unauthorized" }, 401);
116
+ }
117
+
105
118
  const checkpointName = readCheckpointNameFromPath(request, pathPrefix);
106
119
  if (checkpointName === null) {
107
120
  return json({ error: "invalid_checkpoint_path" }, 400);
@@ -146,6 +159,23 @@ export class ConvexCheckpoints<
146
159
 
147
160
  export type { CheckpointHandler };
148
161
 
162
+ async function isAuthorized(request: Request, options: HttpOptions) {
163
+ if ("token" in options) {
164
+ if (typeof options.token !== "string" || options.token.length === 0) {
165
+ return false;
166
+ }
167
+ const authorization = request.headers.get("authorization");
168
+ if (authorization !== `Bearer ${options.token}`) {
169
+ return false;
170
+ }
171
+ }
172
+
173
+ if (options.authorize === undefined) {
174
+ return true;
175
+ }
176
+ return await options.authorize(request.clone());
177
+ }
178
+
149
179
  async function readSubmitArgsFromBody(
150
180
  request: Request,
151
181
  ): Promise<UntypedSubmitArgs | null> {
@@ -259,6 +289,6 @@ function corsHeaders() {
259
289
  return {
260
290
  "Access-Control-Allow-Origin": "*",
261
291
  "Access-Control-Allow-Methods": "POST, OPTIONS",
262
- "Access-Control-Allow-Headers": "Content-Type",
292
+ "Access-Control-Allow-Headers": "Content-Type, Authorization",
263
293
  };
264
294
  }