create-feedbax 0.2.1 → 0.2.2
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 +17 -5
- package/dist/cli.js +502 -209
- package/dist/index.js +251 -68
- package/package.json +7 -7
- package/template/.feedbax-template.sha256 +1 -1
- package/template/.gitignore.template +1 -0
- package/template/.npmignore.template +1 -0
- package/template/.nvmrc +1 -0
- package/template/AGENTS.md +1 -1
- package/template/CONNECTED.md +16 -2
- package/template/README.md +52 -13
- package/template/feedbax-vite.ts +79 -0
- package/template/migrations/0005_github.sql +4 -0
- package/template/migrations/0006_integration.sql +3 -0
- package/template/migrations/0007_ownership.sql +2 -0
- package/template/migrations/0008_integration_recovery.sql +5 -0
- package/template/migrations/0009_observed_history.sql +3 -0
- package/template/package.json +34 -33
- package/template/src/changelog-runtime.ts +2 -1
- package/template/src/cloudflare-workers.d.ts +3 -0
- package/template/src/comment-creation.test.tsx +53 -6
- package/template/src/components/connected-identity-provider.tsx +44 -17
- package/template/src/components/follow-post-button.tsx +2 -13
- package/template/src/components/post-history.tsx +101 -0
- package/template/src/components/profile-menu.tsx +7 -0
- package/template/src/configured-feedback.test.ts +82 -0
- package/template/src/configured-feedback.ts +61 -0
- package/template/src/connected-identity.test.ts +7 -3
- package/template/src/connected-identity.ts +6 -1
- package/template/src/connected-runtime.test.ts +5 -2
- package/template/src/feedback-cache-invalidation.ts +2 -0
- package/template/src/feedback-runtime.ts +61 -18
- package/template/src/feedbax/changelog/index.test.ts +35 -0
- package/template/src/feedbax/changelog/index.ts +5 -1
- package/template/src/feedbax/changelog/notion-changelog.test.ts +1 -1
- package/template/src/feedbax/changelog/notion-changelog.ts +1 -1
- package/template/src/feedbax/config/index.test.ts +45 -1
- package/template/src/feedbax/config/index.ts +112 -9
- package/template/src/feedbax/feedback/comment-storage.ts +38 -0
- package/template/src/feedbax/feedback/connected-feedback.ts +41 -12
- package/template/src/feedbax/feedback/connected.ts +15 -5
- package/template/src/feedbax/feedback/feedback-storage.ts +1 -0
- package/template/src/feedbax/feedback/github-comments.ts +390 -0
- package/template/src/feedbax/feedback/github-feedback.test.ts +1138 -0
- package/template/src/feedbax/feedback/github-feedback.ts +581 -0
- package/template/src/feedbax/feedback/github-request.ts +120 -0
- package/template/src/feedbax/feedback/github-service-client.ts +56 -0
- package/template/src/feedbax/feedback/image-feedback.ts +23 -10
- package/template/src/feedbax/feedback/images.ts +26 -0
- package/template/src/feedbax/feedback/index.ts +172 -16
- package/template/src/feedbax/feedback/integration-auth.ts +138 -0
- package/template/src/feedbax/feedback/notion-comments.ts +2 -35
- package/template/src/feedbax/feedback/observed-history.test.ts +150 -0
- package/template/src/feedbax/feedback/observed-history.ts +219 -0
- package/template/src/feedbax/feedback/ownership.ts +170 -0
- package/template/src/history-runtime.test.ts +80 -0
- package/template/src/history-runtime.ts +37 -0
- package/template/src/index.css +6 -0
- package/template/src/integration-runtime.test.ts +365 -0
- package/template/src/integration-runtime.ts +289 -0
- package/template/src/my-feedback-page.test.tsx +152 -0
- package/template/src/my-feedback-page.tsx +398 -0
- package/template/src/my-feedback-runtime.test.ts +93 -0
- package/template/src/my-feedback-runtime.ts +154 -0
- package/template/src/participation-runtime.ts +3 -3
- package/template/src/portal-comments.ts +11 -0
- package/template/src/portal-feedback-form.tsx +11 -3
- package/template/src/portal-feedback-submission.ts +9 -0
- package/template/src/portal-server-entry.ts +9 -0
- package/template/src/public-portal-error.tsx +1 -1
- package/template/src/public-post-detail.tsx +332 -256
- package/template/src/public-release-links.test.ts +120 -0
- package/template/src/public-release-links.ts +130 -0
- package/template/src/routeTree.gen.ts +21 -0
- package/template/src/routes/my-feedback.tsx +16 -0
- package/template/src/server.ts +46 -1
- package/template/src/submission-intent.ts +26 -0
- package/template/vite.config.ts +2 -0
package/dist/index.js
CHANGED
|
@@ -1,9 +1,12 @@
|
|
|
1
1
|
// src/index.ts
|
|
2
|
-
import { createHash as
|
|
3
|
-
import { readFile as
|
|
2
|
+
import { createHash as createHash3, randomBytes as randomBytes2 } from "node:crypto";
|
|
3
|
+
import { readFile as readFile3, readdir as readdir2, writeFile as writeFile3 } from "node:fs/promises";
|
|
4
4
|
|
|
5
5
|
// ../config/src/index.ts
|
|
6
6
|
var rootKeys = [
|
|
7
|
+
"history",
|
|
8
|
+
"provider",
|
|
9
|
+
"github",
|
|
7
10
|
"connected",
|
|
8
11
|
"product",
|
|
9
12
|
"theme",
|
|
@@ -47,6 +50,8 @@ var changelogPropertyKeys = [
|
|
|
47
50
|
function defineFeedbax(config) {
|
|
48
51
|
const value = object(config, "Feedbax configuration");
|
|
49
52
|
rejectUnknown(value, rootKeys, "Feedbax configuration");
|
|
53
|
+
if (value.history !== void 0 && typeof value.history !== "boolean")
|
|
54
|
+
throw new Error("history must be true or false.");
|
|
50
55
|
const product = object(value.product, "product");
|
|
51
56
|
rejectUnknown(
|
|
52
57
|
product,
|
|
@@ -123,11 +128,19 @@ function defineFeedbax(config) {
|
|
|
123
128
|
}
|
|
124
129
|
const theme = object(value.theme, "theme");
|
|
125
130
|
rejectUnknown(theme, ["preset"], "theme");
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
+
if (value.provider !== void 0 && !["notion", "github"].includes(String(value.provider)))
|
|
132
|
+
throw new Error("provider must be notion or github.");
|
|
133
|
+
const githubMode = value.provider === "github";
|
|
134
|
+
if (githubMode && value.notion !== void 0 || !githubMode && value.github !== void 0)
|
|
135
|
+
throw new Error("Select exactly one Content Provider: notion or github.");
|
|
136
|
+
const content = githubMode ? { provider: "github", github: githubConfiguration(value.github) } : {
|
|
137
|
+
...value.provider ? { provider: "notion" } : {},
|
|
138
|
+
notion: storage(
|
|
139
|
+
value.notion,
|
|
140
|
+
feedbackPropertyKeys,
|
|
141
|
+
"notion"
|
|
142
|
+
)
|
|
143
|
+
};
|
|
131
144
|
const features = object(value.features, "features");
|
|
132
145
|
rejectUnknown(features, featureKeys, "features");
|
|
133
146
|
const validatedFeatures = Object.fromEntries(
|
|
@@ -137,6 +150,10 @@ function defineFeedbax(config) {
|
|
|
137
150
|
return [key, features[key]];
|
|
138
151
|
})
|
|
139
152
|
);
|
|
153
|
+
if (githubMode && (validatedFeatures.changelog || value.changelog !== void 0))
|
|
154
|
+
throw new Error(
|
|
155
|
+
"GitHub Installations must disable Changelog (features.changelog: false) and remove Notion Changelog configuration."
|
|
156
|
+
);
|
|
140
157
|
const changelog = value.changelog === void 0 ? void 0 : storage(
|
|
141
158
|
value.changelog,
|
|
142
159
|
changelogPropertyKeys,
|
|
@@ -163,9 +180,10 @@ function defineFeedbax(config) {
|
|
|
163
180
|
throw new Error("Turnstile is enabled but turnstile.siteKey is missing.");
|
|
164
181
|
return {
|
|
165
182
|
product: validatedProduct,
|
|
183
|
+
...value.history !== void 0 ? { history: value.history } : {},
|
|
166
184
|
...connected ? { connected } : {},
|
|
167
185
|
theme: { preset: text(theme.preset, "theme.preset") },
|
|
168
|
-
|
|
186
|
+
...content,
|
|
169
187
|
...changelog ? { changelog } : {},
|
|
170
188
|
features: validatedFeatures,
|
|
171
189
|
submissions: {
|
|
@@ -230,9 +248,44 @@ function publicUrl(value, label, allowRelative) {
|
|
|
230
248
|
`${label} must be ${allowRelative ? "root-relative or " : ""}an HTTPS URL.`
|
|
231
249
|
);
|
|
232
250
|
}
|
|
251
|
+
function githubConfiguration(value) {
|
|
252
|
+
const input = object(value, "github");
|
|
253
|
+
rejectUnknown(
|
|
254
|
+
input,
|
|
255
|
+
["installationId", "serviceUrl", "repository", "botUserId"],
|
|
256
|
+
"github"
|
|
257
|
+
);
|
|
258
|
+
const installationId = text(input.installationId, "github.installationId");
|
|
259
|
+
if (!/^[a-zA-Z0-9_-]{1,128}$/.test(installationId))
|
|
260
|
+
throw new Error(
|
|
261
|
+
"github.installationId must be a stable Installation identifier."
|
|
262
|
+
);
|
|
263
|
+
const serviceUrl = publicUrl(input.serviceUrl, "github.serviceUrl", false);
|
|
264
|
+
const url = new URL(serviceUrl);
|
|
265
|
+
if (url.origin !== serviceUrl || url.username || url.password)
|
|
266
|
+
throw new Error(
|
|
267
|
+
"github.serviceUrl must be an HTTPS origin without a path or credentials."
|
|
268
|
+
);
|
|
269
|
+
const repository = object(input.repository, "github.repository");
|
|
270
|
+
rejectUnknown(repository, ["id", "owner", "name"], "github.repository");
|
|
271
|
+
const owner = text(repository.owner, "github.repository.owner");
|
|
272
|
+
const name = text(repository.name, "github.repository.name");
|
|
273
|
+
if (!/^[A-Za-z0-9-]+$/.test(owner) || !/^[A-Za-z0-9_.-]+$/.test(name))
|
|
274
|
+
throw new Error("Use a valid GitHub repository owner and name.");
|
|
275
|
+
return {
|
|
276
|
+
installationId,
|
|
277
|
+
serviceUrl,
|
|
278
|
+
repository: {
|
|
279
|
+
id: positiveInteger(repository.id, "github.repository.id"),
|
|
280
|
+
owner,
|
|
281
|
+
name
|
|
282
|
+
},
|
|
283
|
+
botUserId: positiveInteger(input.botUserId, "github.botUserId")
|
|
284
|
+
};
|
|
285
|
+
}
|
|
233
286
|
|
|
234
287
|
// src/index.ts
|
|
235
|
-
import { basename, join as
|
|
288
|
+
import { basename, join as join3 } from "node:path";
|
|
236
289
|
|
|
237
290
|
// src/template.ts
|
|
238
291
|
import { createHash } from "node:crypto";
|
|
@@ -307,7 +360,7 @@ async function assembleFlatTemplate(coreRoot, destination) {
|
|
|
307
360
|
'@source "../../../**/*.{ts,tsx}";'
|
|
308
361
|
)
|
|
309
362
|
);
|
|
310
|
-
for (const name of ["vite.config.ts"])
|
|
363
|
+
for (const name of ["vite.config.ts", "feedbax-vite.ts"])
|
|
311
364
|
await copy(join(coreRoot, "apps/portal", name), join(target, name));
|
|
312
365
|
const components = parse(
|
|
313
366
|
await readFile(join(coreRoot, "apps/portal/components.json"), "utf8")
|
|
@@ -329,6 +382,7 @@ async function assembleFlatTemplate(coreRoot, destination) {
|
|
|
329
382
|
JSON.stringify(wrangler, null, 2) + "\n"
|
|
330
383
|
);
|
|
331
384
|
await copy(join(coreRoot, "LICENSE"), join(target, "LICENSE"));
|
|
385
|
+
await copy(join(coreRoot, ".nvmrc"), join(target, ".nvmrc"));
|
|
332
386
|
await copy(
|
|
333
387
|
join(coreRoot, "eslint.config.mjs"),
|
|
334
388
|
join(target, "eslint.config.mjs")
|
|
@@ -426,11 +480,11 @@ export default defineFeedbax(${JSON.stringify(fixture, null, 2)});
|
|
|
426
480
|
);
|
|
427
481
|
await writeFile(
|
|
428
482
|
join(target, ".gitignore.template"),
|
|
429
|
-
".dev.vars\n.env*\ndist/\n.wrangler/\n*.log\nnode_modules/\n"
|
|
483
|
+
".dev.vars\n.env*\n.feedbax/\ndist/\n.wrangler/\n*.log\nnode_modules/\n"
|
|
430
484
|
);
|
|
431
485
|
await writeFile(
|
|
432
486
|
join(target, ".npmignore.template"),
|
|
433
|
-
".dev.vars\n.env*\ndist/\n.wrangler/\n*.log\n"
|
|
487
|
+
".dev.vars\n.env*\n.feedbax/\ndist/\n.wrangler/\n*.log\n"
|
|
434
488
|
);
|
|
435
489
|
await writeFile(
|
|
436
490
|
join(target, ".prettierignore.template"),
|
|
@@ -529,18 +583,18 @@ async function flatManifest(coreRoot) {
|
|
|
529
583
|
...collect("devDependencies"),
|
|
530
584
|
"@eslint/js": "10.0.1",
|
|
531
585
|
"@shadcn/lint": "0.2.1",
|
|
532
|
-
"@types/node": "
|
|
586
|
+
"@types/node": "24.19.2",
|
|
533
587
|
feedbax: JSON.parse(
|
|
534
588
|
await readFile(join(coreRoot, "packages/feedbax/package.json"), "utf8")
|
|
535
589
|
).version,
|
|
536
|
-
eslint: "10.
|
|
537
|
-
globals: "17.
|
|
538
|
-
prettier: "3.9.
|
|
539
|
-
"typescript-eslint": "8.
|
|
540
|
-
vitest: "
|
|
590
|
+
eslint: "10.12.0",
|
|
591
|
+
globals: "17.13.0",
|
|
592
|
+
prettier: "3.9.10",
|
|
593
|
+
"typescript-eslint": "8.71.2",
|
|
594
|
+
vitest: "5.0.4"
|
|
541
595
|
},
|
|
542
596
|
pnpm: { onlyBuiltDependencies: ["esbuild"] },
|
|
543
|
-
engines: { node: ">=
|
|
597
|
+
engines: { node: "^24.15.0 || >=26.0.0" },
|
|
544
598
|
packageManager: "pnpm@10.29.3",
|
|
545
599
|
license: "Apache-2.0"
|
|
546
600
|
};
|
|
@@ -1000,7 +1054,7 @@ function isPropertyMap(value) {
|
|
|
1000
1054
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
1001
1055
|
}
|
|
1002
1056
|
|
|
1003
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1057
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/entity.js
|
|
1004
1058
|
var entityKind = /* @__PURE__ */ Symbol.for("drizzle:entityKind");
|
|
1005
1059
|
function is(value, type) {
|
|
1006
1060
|
if (!value || typeof value !== "object") {
|
|
@@ -1026,7 +1080,7 @@ function is(value, type) {
|
|
|
1026
1080
|
return false;
|
|
1027
1081
|
}
|
|
1028
1082
|
|
|
1029
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1083
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/column.js
|
|
1030
1084
|
var Column = class {
|
|
1031
1085
|
constructor(table, config) {
|
|
1032
1086
|
this.table = table;
|
|
@@ -1077,7 +1131,7 @@ var Column = class {
|
|
|
1077
1131
|
}
|
|
1078
1132
|
};
|
|
1079
1133
|
|
|
1080
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1134
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/column-builder.js
|
|
1081
1135
|
var ColumnBuilder = class {
|
|
1082
1136
|
static [entityKind] = "ColumnBuilder";
|
|
1083
1137
|
config;
|
|
@@ -1180,10 +1234,10 @@ var ColumnBuilder = class {
|
|
|
1180
1234
|
}
|
|
1181
1235
|
};
|
|
1182
1236
|
|
|
1183
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1237
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/table.utils.js
|
|
1184
1238
|
var TableName = /* @__PURE__ */ Symbol.for("drizzle:Name");
|
|
1185
1239
|
|
|
1186
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1240
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/pg-core/foreign-keys.js
|
|
1187
1241
|
var ForeignKeyBuilder = class {
|
|
1188
1242
|
static [entityKind] = "PgForeignKeyBuilder";
|
|
1189
1243
|
/** @internal */
|
|
@@ -1240,12 +1294,12 @@ var ForeignKey = class {
|
|
|
1240
1294
|
}
|
|
1241
1295
|
};
|
|
1242
1296
|
|
|
1243
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1297
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/tracing-utils.js
|
|
1244
1298
|
function iife(fn, ...args) {
|
|
1245
1299
|
return fn(...args);
|
|
1246
1300
|
}
|
|
1247
1301
|
|
|
1248
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1302
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/pg-core/unique-constraint.js
|
|
1249
1303
|
function uniqueKeyName(table, columns) {
|
|
1250
1304
|
return `${table[TableName]}_${columns.join("_")}_unique`;
|
|
1251
1305
|
}
|
|
@@ -1295,7 +1349,7 @@ var UniqueConstraint = class {
|
|
|
1295
1349
|
}
|
|
1296
1350
|
};
|
|
1297
1351
|
|
|
1298
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1352
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/pg-core/utils/array.js
|
|
1299
1353
|
function parsePgArrayValue(arrayString, startFrom, inQuotes) {
|
|
1300
1354
|
for (let i = startFrom; i < arrayString.length; i++) {
|
|
1301
1355
|
const char = arrayString[i];
|
|
@@ -1371,7 +1425,7 @@ function makePgArray(array) {
|
|
|
1371
1425
|
}).join(",")}}`;
|
|
1372
1426
|
}
|
|
1373
1427
|
|
|
1374
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1428
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/pg-core/columns/common.js
|
|
1375
1429
|
var PgColumnBuilder = class extends ColumnBuilder {
|
|
1376
1430
|
foreignKeyConfigs = [];
|
|
1377
1431
|
static [entityKind] = "PgColumnBuilder";
|
|
@@ -1555,7 +1609,7 @@ var PgArray = class _PgArray extends PgColumn {
|
|
|
1555
1609
|
}
|
|
1556
1610
|
};
|
|
1557
1611
|
|
|
1558
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1612
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/pg-core/columns/enum.js
|
|
1559
1613
|
var PgEnumObjectColumnBuilder = class extends PgColumnBuilder {
|
|
1560
1614
|
static [entityKind] = "PgEnumObjectColumnBuilder";
|
|
1561
1615
|
constructor(name, enumInstance) {
|
|
@@ -1613,7 +1667,7 @@ var PgEnumColumn = class extends PgColumn {
|
|
|
1613
1667
|
}
|
|
1614
1668
|
};
|
|
1615
1669
|
|
|
1616
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1670
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/subquery.js
|
|
1617
1671
|
var Subquery = class {
|
|
1618
1672
|
static [entityKind] = "Subquery";
|
|
1619
1673
|
constructor(sql2, fields, alias, isWith = false, usedTables = []) {
|
|
@@ -1634,10 +1688,10 @@ var WithSubquery = class extends Subquery {
|
|
|
1634
1688
|
static [entityKind] = "WithSubquery";
|
|
1635
1689
|
};
|
|
1636
1690
|
|
|
1637
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1638
|
-
var version = "0.45.
|
|
1691
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/version.js
|
|
1692
|
+
var version = "0.45.4";
|
|
1639
1693
|
|
|
1640
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1694
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/tracing.js
|
|
1641
1695
|
var otel;
|
|
1642
1696
|
var rawTracer;
|
|
1643
1697
|
var tracer = {
|
|
@@ -1672,10 +1726,10 @@ var tracer = {
|
|
|
1672
1726
|
}
|
|
1673
1727
|
};
|
|
1674
1728
|
|
|
1675
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1729
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/view-common.js
|
|
1676
1730
|
var ViewBaseConfig = /* @__PURE__ */ Symbol.for("drizzle:ViewBaseConfig");
|
|
1677
1731
|
|
|
1678
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1732
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/table.js
|
|
1679
1733
|
var Schema = /* @__PURE__ */ Symbol.for("drizzle:Schema");
|
|
1680
1734
|
var Columns = /* @__PURE__ */ Symbol.for("drizzle:Columns");
|
|
1681
1735
|
var ExtraConfigColumns = /* @__PURE__ */ Symbol.for("drizzle:ExtraConfigColumns");
|
|
@@ -1731,7 +1785,7 @@ var Table = class {
|
|
|
1731
1785
|
}
|
|
1732
1786
|
};
|
|
1733
1787
|
|
|
1734
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
1788
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sql/sql.js
|
|
1735
1789
|
var FakePrimitiveParam = class {
|
|
1736
1790
|
static [entityKind] = "FakePrimitiveParam";
|
|
1737
1791
|
};
|
|
@@ -2021,7 +2075,7 @@ function sql(strings, ...params) {
|
|
|
2021
2075
|
return new SQL([new StringChunk(str)]);
|
|
2022
2076
|
}
|
|
2023
2077
|
sql2.raw = raw;
|
|
2024
|
-
function
|
|
2078
|
+
function join4(chunks, separator) {
|
|
2025
2079
|
const result = [];
|
|
2026
2080
|
for (const [i, chunk] of chunks.entries()) {
|
|
2027
2081
|
if (i > 0 && separator !== void 0) {
|
|
@@ -2031,7 +2085,7 @@ function sql(strings, ...params) {
|
|
|
2031
2085
|
}
|
|
2032
2086
|
return new SQL(result);
|
|
2033
2087
|
}
|
|
2034
|
-
sql2.join =
|
|
2088
|
+
sql2.join = join4;
|
|
2035
2089
|
function identifier(value) {
|
|
2036
2090
|
return new Name(value);
|
|
2037
2091
|
}
|
|
@@ -2105,7 +2159,7 @@ Subquery.prototype.getSQL = function() {
|
|
|
2105
2159
|
return new SQL([this]);
|
|
2106
2160
|
};
|
|
2107
2161
|
|
|
2108
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2162
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/utils.js
|
|
2109
2163
|
function getColumnNameAndConfig(a, b) {
|
|
2110
2164
|
return {
|
|
2111
2165
|
name: typeof a === "string" && a.length > 0 ? a : "",
|
|
@@ -2114,7 +2168,7 @@ function getColumnNameAndConfig(a, b) {
|
|
|
2114
2168
|
}
|
|
2115
2169
|
var textDecoder = typeof TextDecoder === "undefined" ? null : new TextDecoder();
|
|
2116
2170
|
|
|
2117
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2171
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/foreign-keys.js
|
|
2118
2172
|
var ForeignKeyBuilder2 = class {
|
|
2119
2173
|
static [entityKind] = "SQLiteForeignKeyBuilder";
|
|
2120
2174
|
/** @internal */
|
|
@@ -2171,7 +2225,7 @@ var ForeignKey2 = class {
|
|
|
2171
2225
|
}
|
|
2172
2226
|
};
|
|
2173
2227
|
|
|
2174
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2228
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/unique-constraint.js
|
|
2175
2229
|
function uniqueKeyName2(table, columns) {
|
|
2176
2230
|
return `${table[TableName]}_${columns.join("_")}_unique`;
|
|
2177
2231
|
}
|
|
@@ -2213,7 +2267,7 @@ var UniqueConstraint2 = class {
|
|
|
2213
2267
|
}
|
|
2214
2268
|
};
|
|
2215
2269
|
|
|
2216
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2270
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/common.js
|
|
2217
2271
|
var SQLiteColumnBuilder = class extends ColumnBuilder {
|
|
2218
2272
|
static [entityKind] = "SQLiteColumnBuilder";
|
|
2219
2273
|
foreignKeyConfigs = [];
|
|
@@ -2264,7 +2318,7 @@ var SQLiteColumn = class extends Column {
|
|
|
2264
2318
|
static [entityKind] = "SQLiteColumn";
|
|
2265
2319
|
};
|
|
2266
2320
|
|
|
2267
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2321
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/blob.js
|
|
2268
2322
|
var SQLiteBigIntBuilder = class extends SQLiteColumnBuilder {
|
|
2269
2323
|
static [entityKind] = "SQLiteBigIntBuilder";
|
|
2270
2324
|
constructor(name) {
|
|
@@ -2353,7 +2407,7 @@ function blob(a, b) {
|
|
|
2353
2407
|
return new SQLiteBlobBufferBuilder(name);
|
|
2354
2408
|
}
|
|
2355
2409
|
|
|
2356
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2410
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/custom.js
|
|
2357
2411
|
var SQLiteCustomColumnBuilder = class extends SQLiteColumnBuilder {
|
|
2358
2412
|
static [entityKind] = "SQLiteCustomColumnBuilder";
|
|
2359
2413
|
constructor(name, fieldConfig, customTypeParams) {
|
|
@@ -2401,7 +2455,7 @@ function customType(customTypeParams) {
|
|
|
2401
2455
|
};
|
|
2402
2456
|
}
|
|
2403
2457
|
|
|
2404
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2458
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/integer.js
|
|
2405
2459
|
var SQLiteBaseIntegerBuilder = class extends SQLiteColumnBuilder {
|
|
2406
2460
|
static [entityKind] = "SQLiteBaseIntegerBuilder";
|
|
2407
2461
|
constructor(name, dataType, columnType) {
|
|
@@ -2510,7 +2564,7 @@ function integer(a, b) {
|
|
|
2510
2564
|
return new SQLiteIntegerBuilder(name);
|
|
2511
2565
|
}
|
|
2512
2566
|
|
|
2513
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2567
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/numeric.js
|
|
2514
2568
|
var SQLiteNumericBuilder = class extends SQLiteColumnBuilder {
|
|
2515
2569
|
static [entityKind] = "SQLiteNumericBuilder";
|
|
2516
2570
|
constructor(name) {
|
|
@@ -2585,7 +2639,7 @@ function numeric(a, b) {
|
|
|
2585
2639
|
return mode === "number" ? new SQLiteNumericNumberBuilder(name) : mode === "bigint" ? new SQLiteNumericBigIntBuilder(name) : new SQLiteNumericBuilder(name);
|
|
2586
2640
|
}
|
|
2587
2641
|
|
|
2588
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2642
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/real.js
|
|
2589
2643
|
var SQLiteRealBuilder = class extends SQLiteColumnBuilder {
|
|
2590
2644
|
static [entityKind] = "SQLiteRealBuilder";
|
|
2591
2645
|
constructor(name) {
|
|
@@ -2606,7 +2660,7 @@ function real(name) {
|
|
|
2606
2660
|
return new SQLiteRealBuilder(name ?? "");
|
|
2607
2661
|
}
|
|
2608
2662
|
|
|
2609
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2663
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/text.js
|
|
2610
2664
|
var SQLiteTextBuilder = class extends SQLiteColumnBuilder {
|
|
2611
2665
|
static [entityKind] = "SQLiteTextBuilder";
|
|
2612
2666
|
constructor(name, config) {
|
|
@@ -2666,7 +2720,7 @@ function text2(a, b = {}) {
|
|
|
2666
2720
|
return new SQLiteTextBuilder(name, config);
|
|
2667
2721
|
}
|
|
2668
2722
|
|
|
2669
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2723
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/columns/all.js
|
|
2670
2724
|
function getSQLiteColumnBuilders() {
|
|
2671
2725
|
return {
|
|
2672
2726
|
blob,
|
|
@@ -2678,7 +2732,7 @@ function getSQLiteColumnBuilders() {
|
|
|
2678
2732
|
};
|
|
2679
2733
|
}
|
|
2680
2734
|
|
|
2681
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2735
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/table.js
|
|
2682
2736
|
var InlineForeignKeys = /* @__PURE__ */ Symbol.for("drizzle:SQLiteInlineForeignKeys");
|
|
2683
2737
|
var SQLiteTable = class extends Table {
|
|
2684
2738
|
static [entityKind] = "SQLiteTable";
|
|
@@ -2717,7 +2771,7 @@ var sqliteTable = (name, columns, extraConfig) => {
|
|
|
2717
2771
|
return sqliteTableBase(name, columns, extraConfig);
|
|
2718
2772
|
};
|
|
2719
2773
|
|
|
2720
|
-
// ../../node_modules/.pnpm/drizzle-orm@0.45.
|
|
2774
|
+
// ../../node_modules/.pnpm/drizzle-orm@0.45.4_@cloudflare+workers-types@5.20261015.1_kysely@0.29.6/node_modules/drizzle-orm/sqlite-core/primary-keys.js
|
|
2721
2775
|
function primaryKey(...config) {
|
|
2722
2776
|
if (config[0].columns) {
|
|
2723
2777
|
return new PrimaryKeyBuilder(config[0].columns, config[0].name);
|
|
@@ -2865,7 +2919,7 @@ async function validateNotionChangelogDataSource({
|
|
|
2865
2919
|
const properties = recordAt(dataSource, "properties");
|
|
2866
2920
|
const propertiesById = new Map(
|
|
2867
2921
|
Object.values(properties).flatMap((property) => {
|
|
2868
|
-
if (!
|
|
2922
|
+
if (!isRecord2(property) || typeof property.id !== "string") return [];
|
|
2869
2923
|
return [[property.id, property]];
|
|
2870
2924
|
})
|
|
2871
2925
|
);
|
|
@@ -2920,7 +2974,7 @@ async function readObject(response, subject) {
|
|
|
2920
2974
|
`Notion rejected the ${subject} request (${response.status}).`
|
|
2921
2975
|
);
|
|
2922
2976
|
}
|
|
2923
|
-
if (!
|
|
2977
|
+
if (!isRecord2(body))
|
|
2924
2978
|
throw new Error(`Notion returned an invalid ${subject} response.`);
|
|
2925
2979
|
return body;
|
|
2926
2980
|
}
|
|
@@ -2928,7 +2982,7 @@ function recordAt(value, key) {
|
|
|
2928
2982
|
return record(value[key]);
|
|
2929
2983
|
}
|
|
2930
2984
|
function record(value) {
|
|
2931
|
-
if (!
|
|
2985
|
+
if (!isRecord2(value))
|
|
2932
2986
|
throw new Error("Notion returned an invalid Changelog response.");
|
|
2933
2987
|
return value;
|
|
2934
2988
|
}
|
|
@@ -2937,13 +2991,141 @@ function requiredString(value) {
|
|
|
2937
2991
|
throw new Error("Notion returned an invalid Changelog response.");
|
|
2938
2992
|
return value;
|
|
2939
2993
|
}
|
|
2940
|
-
function
|
|
2994
|
+
function isRecord2(value) {
|
|
2941
2995
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
2942
2996
|
}
|
|
2943
2997
|
|
|
2998
|
+
// src/github.ts
|
|
2999
|
+
import { createHash as createHash2, randomBytes } from "node:crypto";
|
|
3000
|
+
import { readFile as readFile2, writeFile as writeFile2 } from "node:fs/promises";
|
|
3001
|
+
import { join as join2 } from "node:path";
|
|
3002
|
+
async function provisionGitHubInstallation(options) {
|
|
3003
|
+
const { connected, github } = options;
|
|
3004
|
+
if (!/^[a-z0-9][a-z0-9-]{0,62}$/.test(options.workerName) || !/^[0-9a-f-]{36}$/i.test(options.database.id) || !options.database.name.trim())
|
|
3005
|
+
throw new Error(
|
|
3006
|
+
"GitHub setup requires a distinct Worker and an explicitly provisioned FEEDBAX_DB D1 database."
|
|
3007
|
+
);
|
|
3008
|
+
if (connected && (connected.databaseId !== options.database.id || connected.handoffSecret.length < 32 || connected.processing !== "standard" && !connected.queueName))
|
|
3009
|
+
throw new Error(
|
|
3010
|
+
"Connected setup requires the same D1 database, a handoff secret, and an existing processing queue for small processing."
|
|
3011
|
+
);
|
|
3012
|
+
if (connected?.imageBucket && !/^[a-z0-9][a-z0-9-]{1,61}[a-z0-9]$/.test(connected.imageBucket))
|
|
3013
|
+
throw new Error("Use a dedicated private R2 bucket for images.");
|
|
3014
|
+
const config = defineFeedbax({
|
|
3015
|
+
provider: "github",
|
|
3016
|
+
github,
|
|
3017
|
+
product: { ...options.product, logo: "/feedbax-mark.svg" },
|
|
3018
|
+
theme: { preset: "lyra-neutral" },
|
|
3019
|
+
features: options.features,
|
|
3020
|
+
...connected ? {
|
|
3021
|
+
connected: {
|
|
3022
|
+
processing: connected.processing ?? "small",
|
|
3023
|
+
issuer: connected.issuer,
|
|
3024
|
+
loginUrl: connected.loginUrl,
|
|
3025
|
+
...connected.imageBucket ? { images: true } : {},
|
|
3026
|
+
...connected.email ? {
|
|
3027
|
+
email: {
|
|
3028
|
+
provider: connected.email.provider,
|
|
3029
|
+
from: connected.email.from,
|
|
3030
|
+
...connected.email.endpoint ? { endpoint: connected.email.endpoint } : {}
|
|
3031
|
+
}
|
|
3032
|
+
} : {}
|
|
3033
|
+
}
|
|
3034
|
+
} : {},
|
|
3035
|
+
submissions: {
|
|
3036
|
+
moderation: "required",
|
|
3037
|
+
maxTitleLength: 160,
|
|
3038
|
+
maxDescriptionLength: 5e3
|
|
3039
|
+
},
|
|
3040
|
+
turnstile: {
|
|
3041
|
+
enabled: Boolean(options.turnstile?.siteKey),
|
|
3042
|
+
...options.turnstile?.siteKey ? { siteKey: options.turnstile.siteKey } : {}
|
|
3043
|
+
}
|
|
3044
|
+
});
|
|
3045
|
+
if (!await options.preview(
|
|
3046
|
+
"Create GitHub-backed portal source and private pairing secrets. GitHub requires D1 independently of sign-in. If the repository is public, issue titles/bodies are public immediately even while portal Posts await moderation. This does not create issues, pair the App, or deploy."
|
|
3047
|
+
))
|
|
3048
|
+
throw new Error("GitHub setup was not approved.");
|
|
3049
|
+
await copyPackagedTemplate(options.destination);
|
|
3050
|
+
const path = join2(options.destination, "wrangler.jsonc");
|
|
3051
|
+
const base = JSON.parse(await readFile2(path, "utf8"));
|
|
3052
|
+
const wrangler = {
|
|
3053
|
+
...base,
|
|
3054
|
+
name: options.workerName,
|
|
3055
|
+
compatibility_flags: [
|
|
3056
|
+
.../* @__PURE__ */ new Set([
|
|
3057
|
+
...base.compatibility_flags ?? [],
|
|
3058
|
+
"global_fetch_strictly_public"
|
|
3059
|
+
])
|
|
3060
|
+
],
|
|
3061
|
+
d1_databases: [
|
|
3062
|
+
{
|
|
3063
|
+
binding: "FEEDBAX_DB",
|
|
3064
|
+
database_id: options.database.id,
|
|
3065
|
+
database_name: options.database.name,
|
|
3066
|
+
migrations_dir: "migrations"
|
|
3067
|
+
}
|
|
3068
|
+
],
|
|
3069
|
+
triggers: { crons: ["*/5 * * * *"] },
|
|
3070
|
+
...connected?.queueName ? {
|
|
3071
|
+
queues: {
|
|
3072
|
+
producers: [
|
|
3073
|
+
{ binding: "FEEDBAX_UPDATES", queue: connected.queueName }
|
|
3074
|
+
],
|
|
3075
|
+
consumers: [
|
|
3076
|
+
{
|
|
3077
|
+
queue: connected.queueName,
|
|
3078
|
+
max_batch_size: 1,
|
|
3079
|
+
max_concurrency: 1,
|
|
3080
|
+
max_retries: 3,
|
|
3081
|
+
retry_delay: 60
|
|
3082
|
+
}
|
|
3083
|
+
]
|
|
3084
|
+
}
|
|
3085
|
+
} : {},
|
|
3086
|
+
...connected?.imageBucket ? {
|
|
3087
|
+
r2_buckets: [
|
|
3088
|
+
{ binding: "FEEDBAX_IMAGES", bucket_name: connected.imageBucket }
|
|
3089
|
+
]
|
|
3090
|
+
} : {},
|
|
3091
|
+
...connected?.email?.provider === "cloudflare" ? {
|
|
3092
|
+
send_email: [
|
|
3093
|
+
{
|
|
3094
|
+
name: "FEEDBAX_EMAIL",
|
|
3095
|
+
allowed_sender_addresses: [connected.email.from]
|
|
3096
|
+
}
|
|
3097
|
+
]
|
|
3098
|
+
} : {}
|
|
3099
|
+
};
|
|
3100
|
+
const apiKey = randomBytes(32).toString("base64url");
|
|
3101
|
+
const pairingSecret = randomBytes(32).toString("base64url");
|
|
3102
|
+
const secrets = {
|
|
3103
|
+
FEEDBAX_API_KEY_HASH: createHash2("sha256").update(apiKey).digest("base64url"),
|
|
3104
|
+
PARTICIPATION_SIGNING_SECRET: randomBytes(32).toString("base64url"),
|
|
3105
|
+
GITHUB_PAIRING_SECRET: pairingSecret,
|
|
3106
|
+
...connected ? { IDENTITY_HANDOFF_SECRET: connected.handoffSecret } : {},
|
|
3107
|
+
...connected?.email?.secret ? { EMAIL_PROVIDER_SECRET: connected.email.secret } : {},
|
|
3108
|
+
...options.turnstile?.secretKey ? { TURNSTILE_SECRET_KEY: options.turnstile.secretKey } : {}
|
|
3109
|
+
};
|
|
3110
|
+
await writeFile2(path, JSON.stringify(wrangler, null, 2) + "\n");
|
|
3111
|
+
await writeFile2(
|
|
3112
|
+
join2(options.destination, "src/feedbax.ts"),
|
|
3113
|
+
`import { defineFeedbax } from "@feedbax/config";
|
|
3114
|
+
|
|
3115
|
+
export default defineFeedbax(${JSON.stringify(config, null, 2)});
|
|
3116
|
+
`
|
|
3117
|
+
);
|
|
3118
|
+
await writeFile2(
|
|
3119
|
+
join2(options.destination, ".dev.vars"),
|
|
3120
|
+
Object.entries(secrets).map(([key, value]) => `${key}=${JSON.stringify(value)}`).join("\n") + "\n",
|
|
3121
|
+
{ mode: 384 }
|
|
3122
|
+
);
|
|
3123
|
+
return { apiKey, pairingSecret, configuration: config };
|
|
3124
|
+
}
|
|
3125
|
+
|
|
2944
3126
|
// src/index.ts
|
|
2945
3127
|
function defaultProcessingQueueName(workerName) {
|
|
2946
|
-
return workerName.length <= 55 ? `${workerName}-updates` : `${workerName.slice(0, 46)}-${
|
|
3128
|
+
return workerName.length <= 55 ? `${workerName}-updates` : `${workerName.slice(0, 46)}-${createHash3("sha256").update(workerName).digest("hex").slice(0, 8)}-updates`;
|
|
2947
3129
|
}
|
|
2948
3130
|
async function provisionGuidedInstallation({
|
|
2949
3131
|
destination,
|
|
@@ -3051,9 +3233,9 @@ async function provisionGuidedInstallation({
|
|
|
3051
3233
|
preview
|
|
3052
3234
|
});
|
|
3053
3235
|
await copyPackagedTemplate(destination);
|
|
3054
|
-
const wranglerPath =
|
|
3055
|
-
const wrangler = JSON.parse(await
|
|
3056
|
-
await
|
|
3236
|
+
const wranglerPath = join3(destination, "wrangler.jsonc");
|
|
3237
|
+
const wrangler = JSON.parse(await readFile3(wranglerPath, "utf8"));
|
|
3238
|
+
await writeFile3(
|
|
3057
3239
|
wranglerPath,
|
|
3058
3240
|
JSON.stringify(
|
|
3059
3241
|
{
|
|
@@ -3108,14 +3290,14 @@ async function provisionGuidedInstallation({
|
|
|
3108
3290
|
2
|
|
3109
3291
|
) + "\n"
|
|
3110
3292
|
);
|
|
3111
|
-
const apiKey =
|
|
3112
|
-
const signingSecret =
|
|
3293
|
+
const apiKey = randomBytes2(32).toString("base64url");
|
|
3294
|
+
const signingSecret = randomBytes2(32).toString("base64url");
|
|
3113
3295
|
const values = {
|
|
3114
3296
|
NOTION_TOKEN: notionToken,
|
|
3115
3297
|
NOTION_FEEDBACK_DATABASE_ID: feedback.databaseId,
|
|
3116
3298
|
NOTION_FEEDBACK_DATA_SOURCE_ID: feedback.dataSourceId,
|
|
3117
3299
|
...prefixProperties("NOTION_FEEDBACK", feedback.propertyIds),
|
|
3118
|
-
FEEDBAX_API_KEY_HASH:
|
|
3300
|
+
FEEDBAX_API_KEY_HASH: createHash3("sha256").update(apiKey).digest("base64url"),
|
|
3119
3301
|
PARTICIPATION_SIGNING_SECRET: signingSecret,
|
|
3120
3302
|
...connected ? { IDENTITY_HANDOFF_SECRET: connected.handoffSecret } : {},
|
|
3121
3303
|
...connected?.email?.secret ? { EMAIL_PROVIDER_SECRET: connected.email.secret } : {},
|
|
@@ -3130,8 +3312,8 @@ async function provisionGuidedInstallation({
|
|
|
3130
3312
|
...prefixProperties("NOTION_CHANGELOG", changelog.propertyIds)
|
|
3131
3313
|
} : {}
|
|
3132
3314
|
};
|
|
3133
|
-
await
|
|
3134
|
-
|
|
3315
|
+
await writeFile3(
|
|
3316
|
+
join3(destination, ".dev.vars"),
|
|
3135
3317
|
Object.entries(values).map(([key, value]) => `${key}=${JSON.stringify(value)}`).join("\n") + "\n",
|
|
3136
3318
|
{ mode: 384 }
|
|
3137
3319
|
);
|
|
@@ -3176,16 +3358,16 @@ async function provisionGuidedInstallation({
|
|
|
3176
3358
|
...turnstile.siteKey ? { siteKey: turnstile.siteKey } : {}
|
|
3177
3359
|
}
|
|
3178
3360
|
});
|
|
3179
|
-
await
|
|
3180
|
-
|
|
3361
|
+
await writeFile3(
|
|
3362
|
+
join3(destination, "src/feedbax.ts"),
|
|
3181
3363
|
`import { defineFeedbax } from "@feedbax/config";
|
|
3182
3364
|
|
|
3183
3365
|
export default defineFeedbax(${JSON.stringify(configuration, null, 2)});
|
|
3184
3366
|
`
|
|
3185
3367
|
);
|
|
3186
3368
|
const probePage = commentProbePageId ?? (feedbackSelection.kind === "create" ? feedbackSelection.parentPageId : feedback.databaseId);
|
|
3187
|
-
await
|
|
3188
|
-
|
|
3369
|
+
await writeFile3(
|
|
3370
|
+
join3(destination, ".dev.vars"),
|
|
3189
3371
|
`NOTION_COMMENT_CAPABILITY_PROBE_PAGE_ID=${JSON.stringify(probePage)}
|
|
3190
3372
|
`,
|
|
3191
3373
|
{ flag: "a", mode: 384 }
|
|
@@ -3398,6 +3580,7 @@ export {
|
|
|
3398
3580
|
doctorChangelogStorage,
|
|
3399
3581
|
doctorInstallation,
|
|
3400
3582
|
featureChoices,
|
|
3583
|
+
provisionGitHubInstallation,
|
|
3401
3584
|
provisionGuidedInstallation,
|
|
3402
3585
|
renderChangelogConfiguration,
|
|
3403
3586
|
renderFeatureConfiguration,
|