deepspace 0.6.0 → 0.6.1
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/CHANGELOG.md +6 -0
- package/dist/cli.js +169 -55
- package/dist/cli.js.map +1 -1
- package/dist/index.d.ts +26 -3
- package/dist/index.js +124 -13
- package/dist/index.js.map +1 -1
- package/features/cron/src/CronLogPage.tsx +3 -3
- package/package.json +2 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
1
|
# deepspace
|
|
2
2
|
|
|
3
|
+
## 0.6.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- Make silent failures visible. `RecordProvider` now accepts an `onWriteError` prop (`(error: WriteError) => void`, where `WriteError` is `{ kind: 'permission' | 'validation', title, detail }`) — previously the friendly-error pipeline (server rejection → `parseServerError` → callback) was unreachable from the public API, so a denied or invalid optimistic write looked like a success with no signal anywhere. Unhandled rejections fall back to a loud `console.error` explaining how to wire real UI (note: this fires in production too — existing apps that never wired a handler will start logging rejected writes to the console; each unique error logs once, repeats are suppressed), and the starter template routes `onWriteError` to its toast system out of the box (permission → warning toast, validation → error toast). On localhost, a signed-out `RecordProvider` without `allowAnonymous` renders a visible diagnostic instead of a blank page (production still renders nothing), and passing `schemas` alongside `roomId` (where it's ignored) warns once; both diagnostics can be forced on or off via `globalThis.DEEPSPACE_DEV = true | false` (LAN/tunnel previews, consumer test suites). `deepspace dev` and `deepspace deploy` now run schema lint up front and print findings (e.g. a `visibilityField` no role enforces) in the terminal, capped at 5 with an overflow count — previously these only appeared in the worker console after a client connected.
|
|
8
|
+
|
|
3
9
|
## 0.6.0
|
|
4
10
|
|
|
5
11
|
### Minor Changes
|
package/dist/cli.js
CHANGED
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
// src/cli/cli.ts
|
|
4
4
|
import { defineCommand as defineCommand22, runMain } from "citty";
|
|
5
5
|
import { spawnSync as spawnSync6 } from "child_process";
|
|
6
|
-
import { readFileSync as readFileSync17, existsSync as
|
|
7
|
-
import { dirname as dirname5, join as
|
|
6
|
+
import { readFileSync as readFileSync17, existsSync as existsSync15 } from "fs";
|
|
7
|
+
import { dirname as dirname5, join as join16 } from "path";
|
|
8
8
|
import { fileURLToPath as fileURLToPath3 } from "url";
|
|
9
9
|
|
|
10
10
|
// src/cli/lib/cli-errors.ts
|
|
@@ -1342,7 +1342,7 @@ var logout_default = defineCommand2({
|
|
|
1342
1342
|
|
|
1343
1343
|
// src/cli/commands/dev.ts
|
|
1344
1344
|
import { defineCommand as defineCommand3 } from "citty";
|
|
1345
|
-
import { resolve as resolve4, basename as basename2, join as
|
|
1345
|
+
import { resolve as resolve4, basename as basename2, join as join10 } from "path";
|
|
1346
1346
|
import spawn from "cross-spawn";
|
|
1347
1347
|
|
|
1348
1348
|
// src/cli/auth.ts
|
|
@@ -1788,6 +1788,112 @@ function removeMacosJunk(dir) {
|
|
|
1788
1788
|
return removed;
|
|
1789
1789
|
}
|
|
1790
1790
|
|
|
1791
|
+
// src/cli/lib/schema-lint.ts
|
|
1792
|
+
import { existsSync as existsSync9 } from "fs";
|
|
1793
|
+
import { join as join9 } from "path";
|
|
1794
|
+
import { pathToFileURL } from "url";
|
|
1795
|
+
|
|
1796
|
+
// src/server/schemas/registry.ts
|
|
1797
|
+
var USERS_COLUMNS = [
|
|
1798
|
+
{ name: "email", storage: "text", interpretation: "plain" },
|
|
1799
|
+
{ name: "name", storage: "text", interpretation: "plain" },
|
|
1800
|
+
{ name: "imageUrl", storage: "text", interpretation: "plain" },
|
|
1801
|
+
{ name: "role", storage: "text", interpretation: "plain" },
|
|
1802
|
+
{ name: "createdAt", storage: "text", interpretation: { kind: "datetime" } },
|
|
1803
|
+
{ name: "lastSeenAt", storage: "text", interpretation: { kind: "datetime" } }
|
|
1804
|
+
];
|
|
1805
|
+
var BASE_USERS_SCHEMA = {
|
|
1806
|
+
name: "users",
|
|
1807
|
+
columns: [...USERS_COLUMNS],
|
|
1808
|
+
permissions: {
|
|
1809
|
+
"*": { read: "own", create: false, update: false, delete: false },
|
|
1810
|
+
admin: { read: true, create: false, update: true, delete: true }
|
|
1811
|
+
}
|
|
1812
|
+
};
|
|
1813
|
+
function lintSchema(schema) {
|
|
1814
|
+
const warnings = [];
|
|
1815
|
+
const VISIBILITY_AWARE = ["published", "shared"];
|
|
1816
|
+
if (schema.visibilityField) {
|
|
1817
|
+
const offendingRoles = Object.entries(schema.permissions).filter(([, perms]) => perms.read === true).map(([role]) => role);
|
|
1818
|
+
if (offendingRoles.length > 0) {
|
|
1819
|
+
const usesAware = Object.values(schema.permissions).some(
|
|
1820
|
+
(p10) => typeof p10.read === "string" && VISIBILITY_AWARE.includes(p10.read)
|
|
1821
|
+
);
|
|
1822
|
+
if (!usesAware) {
|
|
1823
|
+
warnings.push(
|
|
1824
|
+
`[${schema.name}] visibilityField is declared but no role uses read: 'published' or 'shared'. Roles with read: true (${offendingRoles.join(", ")}) will see every row regardless of visibility. Change those to read: 'published' (owner OR public) or 'shared' (owner OR collaborator OR public) to actually enforce the filter, or remove visibilityField if you don't intend to gate reads by it.`
|
|
1825
|
+
);
|
|
1826
|
+
}
|
|
1827
|
+
}
|
|
1828
|
+
}
|
|
1829
|
+
if (schema.ownerField) {
|
|
1830
|
+
const col = schema.columns.find((c) => c.name === schema.ownerField);
|
|
1831
|
+
if (col && !col.userBound) {
|
|
1832
|
+
warnings.push(
|
|
1833
|
+
`[${schema.name}] ownerField is '${schema.ownerField}' but that column is not marked userBound: true. A client can create a row with someone else's id in this field, bypassing 'own' permission checks. Add userBound: true (and ideally immutable: true) to the column.`
|
|
1834
|
+
);
|
|
1835
|
+
}
|
|
1836
|
+
}
|
|
1837
|
+
for (const col of schema.columns) {
|
|
1838
|
+
if (col.userBound && col.storage !== "text") {
|
|
1839
|
+
warnings.push(
|
|
1840
|
+
`[${schema.name}] column '${col.name}' is userBound but storage is '${col.storage}'. userBound stamps the user id (a string); use storage: 'text'.`
|
|
1841
|
+
);
|
|
1842
|
+
}
|
|
1843
|
+
}
|
|
1844
|
+
return warnings;
|
|
1845
|
+
}
|
|
1846
|
+
|
|
1847
|
+
// src/cli/lib/schema-lint.ts
|
|
1848
|
+
async function lintProjectSchemas(appDir) {
|
|
1849
|
+
const schemasPath = join9(appDir, "src", "schemas.ts");
|
|
1850
|
+
if (!existsSync9(schemasPath)) return null;
|
|
1851
|
+
let schemas;
|
|
1852
|
+
try {
|
|
1853
|
+
const esbuild = await import("esbuild");
|
|
1854
|
+
const outFile = join9(appDir, ".wrangler", "deploy", "schemas.lint.bundle.mjs");
|
|
1855
|
+
await esbuild.build({
|
|
1856
|
+
entryPoints: [schemasPath],
|
|
1857
|
+
bundle: true,
|
|
1858
|
+
format: "esm",
|
|
1859
|
+
platform: "node",
|
|
1860
|
+
target: "node18",
|
|
1861
|
+
outfile: outFile,
|
|
1862
|
+
logLevel: "silent",
|
|
1863
|
+
write: true
|
|
1864
|
+
});
|
|
1865
|
+
const mod = await import(`${pathToFileURL(outFile).href}?t=${Date.now()}`);
|
|
1866
|
+
schemas = mod.schemas;
|
|
1867
|
+
} catch {
|
|
1868
|
+
console.warn(
|
|
1869
|
+
"Schema lint skipped: could not bundle src/schemas.ts (the worker still lints at runtime)."
|
|
1870
|
+
);
|
|
1871
|
+
return null;
|
|
1872
|
+
}
|
|
1873
|
+
if (!Array.isArray(schemas)) return null;
|
|
1874
|
+
const findings = [];
|
|
1875
|
+
for (const schema of schemas) {
|
|
1876
|
+
if (!schema || typeof schema !== "object") continue;
|
|
1877
|
+
try {
|
|
1878
|
+
findings.push(...lintSchema(schema));
|
|
1879
|
+
} catch {
|
|
1880
|
+
}
|
|
1881
|
+
}
|
|
1882
|
+
return findings;
|
|
1883
|
+
}
|
|
1884
|
+
var MAX_PRINTED_FINDINGS = 5;
|
|
1885
|
+
function formatSchemaLintFindings(findings) {
|
|
1886
|
+
if (findings.length === 0) return [];
|
|
1887
|
+
const n = findings.length;
|
|
1888
|
+
const shown = findings.slice(0, MAX_PRINTED_FINDINGS);
|
|
1889
|
+
const hidden = n - shown.length;
|
|
1890
|
+
return [
|
|
1891
|
+
`Schema lint: ${n} warning${n === 1 ? "" : "s"} in src/schemas.ts \u2014 ${n === 1 ? "this ships" : "these ship"} as permission/privacy bugs:`,
|
|
1892
|
+
...shown.map((f) => ` \u2022 ${f}`),
|
|
1893
|
+
...hidden > 0 ? [` \u2026and ${hidden} more \u2014 fix the above and re-run to see the rest.`] : []
|
|
1894
|
+
];
|
|
1895
|
+
}
|
|
1896
|
+
|
|
1791
1897
|
// src/cli/lib/port.ts
|
|
1792
1898
|
import { createServer } from "net";
|
|
1793
1899
|
var DEFAULT_PORT = 5173;
|
|
@@ -1874,7 +1980,7 @@ var dev_default = defineCommand3({
|
|
|
1874
1980
|
);
|
|
1875
1981
|
} else {
|
|
1876
1982
|
console.warn(
|
|
1877
|
-
`Warning: could not update ${
|
|
1983
|
+
`Warning: could not update ${join10(worktree.mainRepoRoot, ".claude", "launch.json")} (malformed or unwritable) \u2014 the Claude preview tool may serve the main repo's code instead of this worktree.`
|
|
1878
1984
|
);
|
|
1879
1985
|
}
|
|
1880
1986
|
if (!explicitPort && process.env.DEEPSPACE_PORT) {
|
|
@@ -1887,6 +1993,10 @@ var dev_default = defineCommand3({
|
|
|
1887
1993
|
updatePort: explicitPort
|
|
1888
1994
|
});
|
|
1889
1995
|
ensureInstallReady(appDir);
|
|
1996
|
+
const lintFindings = await lintProjectSchemas(appDir);
|
|
1997
|
+
if (lintFindings && lintFindings.length > 0) {
|
|
1998
|
+
for (const line of formatSchemaLintFindings(lintFindings)) console.warn(line);
|
|
1999
|
+
}
|
|
1890
2000
|
let token;
|
|
1891
2001
|
try {
|
|
1892
2002
|
token = await ensureToken();
|
|
@@ -2474,15 +2584,15 @@ var screenshot_default = defineCommand6({
|
|
|
2474
2584
|
// src/cli/commands/test-accounts.ts
|
|
2475
2585
|
import { defineCommand as defineCommand7 } from "citty";
|
|
2476
2586
|
import * as p3 from "@clack/prompts";
|
|
2477
|
-
import { readFileSync as readFileSync10, writeFileSync as writeFileSync8, existsSync as
|
|
2478
|
-
import { join as
|
|
2587
|
+
import { readFileSync as readFileSync10, writeFileSync as writeFileSync8, existsSync as existsSync10, mkdirSync as mkdirSync4 } from "fs";
|
|
2588
|
+
import { join as join11 } from "path";
|
|
2479
2589
|
import { homedir as homedir4 } from "os";
|
|
2480
2590
|
var SESSION_COOKIE2 = "__Secure-better-auth.session_token";
|
|
2481
2591
|
var AUTH_URL4 = process.env.DEEPSPACE_AUTH_URL ?? PLATFORM_URLS.auth;
|
|
2482
|
-
var DIR3 =
|
|
2483
|
-
var ACCOUNTS_PATH =
|
|
2592
|
+
var DIR3 = join11(homedir4(), ".deepspace");
|
|
2593
|
+
var ACCOUNTS_PATH = join11(DIR3, "test-accounts.json");
|
|
2484
2594
|
function loadAccounts() {
|
|
2485
|
-
if (!
|
|
2595
|
+
if (!existsSync10(ACCOUNTS_PATH)) return [];
|
|
2486
2596
|
try {
|
|
2487
2597
|
return JSON.parse(readFileSync10(ACCOUNTS_PATH, "utf-8"));
|
|
2488
2598
|
} catch {
|
|
@@ -2764,9 +2874,9 @@ var test_accounts_default = defineCommand7({
|
|
|
2764
2874
|
import { defineCommand as defineCommand8 } from "citty";
|
|
2765
2875
|
import { execSync as execSync2 } from "child_process";
|
|
2766
2876
|
import { randomUUID } from "crypto";
|
|
2767
|
-
import { readFileSync as readFileSync11, readdirSync as readdirSync4, existsSync as
|
|
2768
|
-
import { join as
|
|
2769
|
-
import { pathToFileURL } from "url";
|
|
2877
|
+
import { readFileSync as readFileSync11, readdirSync as readdirSync4, existsSync as existsSync11 } from "fs";
|
|
2878
|
+
import { join as join12, resolve as resolve7, dirname as dirname2 } from "path";
|
|
2879
|
+
import { pathToFileURL as pathToFileURL2 } from "url";
|
|
2770
2880
|
import * as p4 from "@clack/prompts";
|
|
2771
2881
|
var DEPLOY_URL3 = process.env.DEEPSPACE_DEPLOY_URL ?? PLATFORM_URLS.deploy;
|
|
2772
2882
|
var API_URL2 = process.env.DEEPSPACE_API_URL ?? PLATFORM_URLS.api;
|
|
@@ -2978,7 +3088,7 @@ var deploy_default = defineCommand8({
|
|
|
2978
3088
|
}
|
|
2979
3089
|
p4.log.info(`Id: ${appId}`);
|
|
2980
3090
|
const readCustomDevVarsAt = (path) => {
|
|
2981
|
-
if (!
|
|
3091
|
+
if (!existsSync11(path)) return {};
|
|
2982
3092
|
const section = extractCustomDevVars(stripGeneratedSecretsCache(readFileSync11(path, "utf-8")));
|
|
2983
3093
|
if (!section) return {};
|
|
2984
3094
|
try {
|
|
@@ -3017,6 +3127,10 @@ var deploy_default = defineCommand8({
|
|
|
3017
3127
|
}
|
|
3018
3128
|
const junk = removeMacosJunk(appDir);
|
|
3019
3129
|
if (junk > 0) p4.log.info(`Removed ${junk} macOS metadata file(s) (._*, .DS_Store)`);
|
|
3130
|
+
const lintFindings = await lintProjectSchemas(appDir);
|
|
3131
|
+
if (lintFindings && lintFindings.length > 0) {
|
|
3132
|
+
p4.log.warn(formatSchemaLintFindings(lintFindings).join("\n"));
|
|
3133
|
+
}
|
|
3020
3134
|
const s = createSpinner();
|
|
3021
3135
|
s.start("Building...");
|
|
3022
3136
|
let preparedWranglerConfig;
|
|
@@ -3039,14 +3153,14 @@ var deploy_default = defineCommand8({
|
|
|
3039
3153
|
preparedWranglerConfig?.cleanup();
|
|
3040
3154
|
}
|
|
3041
3155
|
s.stop("Built");
|
|
3042
|
-
const deployConfigPath =
|
|
3043
|
-
if (!
|
|
3156
|
+
const deployConfigPath = join12(appDir, ".wrangler", "deploy", "config.json");
|
|
3157
|
+
if (!existsSync11(deployConfigPath)) {
|
|
3044
3158
|
p4.cancel("Build output config not found at .wrangler/deploy/config.json");
|
|
3045
3159
|
process.exit(1);
|
|
3046
3160
|
}
|
|
3047
3161
|
const deployConfig = JSON.parse(readFileSync11(deployConfigPath, "utf-8"));
|
|
3048
3162
|
const outputWranglerPath = resolve7(dirname2(deployConfigPath), deployConfig.configPath);
|
|
3049
|
-
if (!
|
|
3163
|
+
if (!existsSync11(outputWranglerPath)) {
|
|
3050
3164
|
p4.cancel(`Output wrangler.json not found at ${outputWranglerPath}`);
|
|
3051
3165
|
process.exit(1);
|
|
3052
3166
|
}
|
|
@@ -3059,13 +3173,13 @@ var deploy_default = defineCommand8({
|
|
|
3059
3173
|
process.exit(1);
|
|
3060
3174
|
}
|
|
3061
3175
|
const workerDir = dirname2(outputWranglerPath);
|
|
3062
|
-
const workerBundlePath =
|
|
3176
|
+
const workerBundlePath = join12(workerDir, outputConfig.main);
|
|
3063
3177
|
const clientDir = outputConfig.assets?.directory ? resolve7(workerDir, outputConfig.assets.directory) : null;
|
|
3064
|
-
if (!
|
|
3178
|
+
if (!existsSync11(workerBundlePath)) {
|
|
3065
3179
|
p4.cancel(`Worker bundle not found at ${workerBundlePath}`);
|
|
3066
3180
|
process.exit(1);
|
|
3067
3181
|
}
|
|
3068
|
-
if (!clientDir || !
|
|
3182
|
+
if (!clientDir || !existsSync11(clientDir)) {
|
|
3069
3183
|
p4.cancel(`Client assets not found at ${clientDir}`);
|
|
3070
3184
|
process.exit(1);
|
|
3071
3185
|
}
|
|
@@ -3300,13 +3414,13 @@ then redeploy. (Pass --allow-missing-secrets to deploy without them.)`
|
|
|
3300
3414
|
}
|
|
3301
3415
|
});
|
|
3302
3416
|
async function syncSubscriptionPlans(appDir, appName, token) {
|
|
3303
|
-
const subsPath =
|
|
3304
|
-
if (!
|
|
3417
|
+
const subsPath = join12(appDir, "src", "subscriptions.ts");
|
|
3418
|
+
if (!existsSync11(subsPath)) return;
|
|
3305
3419
|
let plans;
|
|
3306
3420
|
try {
|
|
3307
3421
|
const esbuild = await import("esbuild");
|
|
3308
|
-
const outDir =
|
|
3309
|
-
const outFile =
|
|
3422
|
+
const outDir = join12(appDir, ".wrangler", "deploy");
|
|
3423
|
+
const outFile = join12(outDir, "subscriptions.bundle.mjs");
|
|
3310
3424
|
await esbuild.build({
|
|
3311
3425
|
entryPoints: [subsPath],
|
|
3312
3426
|
bundle: true,
|
|
@@ -3317,7 +3431,7 @@ async function syncSubscriptionPlans(appDir, appName, token) {
|
|
|
3317
3431
|
logLevel: "silent",
|
|
3318
3432
|
write: true
|
|
3319
3433
|
});
|
|
3320
|
-
const mod = await import(`${
|
|
3434
|
+
const mod = await import(`${pathToFileURL2(outFile).href}?t=${Date.now()}`);
|
|
3321
3435
|
plans = mod.subscriptionPlans;
|
|
3322
3436
|
} catch (err) {
|
|
3323
3437
|
p4.log.warn(`Could not load src/subscriptions.ts: ${errMessage(err)}`);
|
|
@@ -3448,13 +3562,13 @@ current billing period? (Skip to leave them grandfathered.)`
|
|
|
3448
3562
|
}
|
|
3449
3563
|
}
|
|
3450
3564
|
async function syncOneTimeProducts(appDir, appName, token) {
|
|
3451
|
-
const productsPath =
|
|
3452
|
-
if (!
|
|
3565
|
+
const productsPath = join12(appDir, "src", "products.ts");
|
|
3566
|
+
if (!existsSync11(productsPath)) return;
|
|
3453
3567
|
let products;
|
|
3454
3568
|
try {
|
|
3455
3569
|
const esbuild = await import("esbuild");
|
|
3456
|
-
const outDir =
|
|
3457
|
-
const outFile =
|
|
3570
|
+
const outDir = join12(appDir, ".wrangler", "deploy");
|
|
3571
|
+
const outFile = join12(outDir, "products.bundle.mjs");
|
|
3458
3572
|
await esbuild.build({
|
|
3459
3573
|
entryPoints: [productsPath],
|
|
3460
3574
|
bundle: true,
|
|
@@ -3465,7 +3579,7 @@ async function syncOneTimeProducts(appDir, appName, token) {
|
|
|
3465
3579
|
logLevel: "silent",
|
|
3466
3580
|
write: true
|
|
3467
3581
|
});
|
|
3468
|
-
const mod = await import(`${
|
|
3582
|
+
const mod = await import(`${pathToFileURL2(outFile).href}?t=${Date.now()}`);
|
|
3469
3583
|
products = mod.oneTimeProducts;
|
|
3470
3584
|
} catch (err) {
|
|
3471
3585
|
p4.log.warn(`Could not load src/products.ts: ${errMessage(err)}`);
|
|
@@ -3529,7 +3643,7 @@ function collectAssets(dir) {
|
|
|
3529
3643
|
function walk(d, prefix) {
|
|
3530
3644
|
for (const entry of readdirSync4(d, { withFileTypes: true })) {
|
|
3531
3645
|
if (entry.name === ".assetsignore") continue;
|
|
3532
|
-
const full =
|
|
3646
|
+
const full = join12(d, entry.name);
|
|
3533
3647
|
const rel = prefix ? `${prefix}/${entry.name}` : entry.name;
|
|
3534
3648
|
if (entry.isDirectory()) {
|
|
3535
3649
|
walk(full, rel);
|
|
@@ -3710,26 +3824,26 @@ var apps_default = defineCommand11({
|
|
|
3710
3824
|
|
|
3711
3825
|
// src/cli/commands/add.ts
|
|
3712
3826
|
import { defineCommand as defineCommand12 } from "citty";
|
|
3713
|
-
import { existsSync as
|
|
3714
|
-
import { resolve as resolve8, join as
|
|
3827
|
+
import { existsSync as existsSync12, readFileSync as readFileSync12 } from "fs";
|
|
3828
|
+
import { resolve as resolve8, join as join13, dirname as dirname3 } from "path";
|
|
3715
3829
|
import { fileURLToPath } from "url";
|
|
3716
3830
|
import { spawnSync as spawnSync5 } from "child_process";
|
|
3717
3831
|
function findScript(from) {
|
|
3718
|
-
const inNodeModules =
|
|
3719
|
-
if (
|
|
3720
|
-
const inDotDeepspace =
|
|
3721
|
-
if (
|
|
3832
|
+
const inNodeModules = join13(from, "node_modules", "deepspace", "scripts", "add-feature.cjs");
|
|
3833
|
+
if (existsSync12(inNodeModules)) return inNodeModules;
|
|
3834
|
+
const inDotDeepspace = join13(from, ".deepspace", "scripts", "add-feature.cjs");
|
|
3835
|
+
if (existsSync12(inDotDeepspace)) return inDotDeepspace;
|
|
3722
3836
|
return null;
|
|
3723
3837
|
}
|
|
3724
3838
|
function runningScript() {
|
|
3725
3839
|
const here = dirname3(fileURLToPath(import.meta.url));
|
|
3726
|
-
const script =
|
|
3727
|
-
return
|
|
3840
|
+
const script = join13(here, "..", "scripts", "add-feature.cjs");
|
|
3841
|
+
return existsSync12(script) ? script : null;
|
|
3728
3842
|
}
|
|
3729
3843
|
function isDeepSpaceApp(dir) {
|
|
3730
|
-
if (
|
|
3731
|
-
const pkgPath =
|
|
3732
|
-
if (!
|
|
3844
|
+
if (existsSync12(join13(dir, "wrangler.toml"))) return true;
|
|
3845
|
+
const pkgPath = join13(dir, "package.json");
|
|
3846
|
+
if (!existsSync12(pkgPath)) return false;
|
|
3733
3847
|
try {
|
|
3734
3848
|
const pkg2 = JSON.parse(readFileSync12(pkgPath, "utf-8"));
|
|
3735
3849
|
return Boolean(pkg2.dependencies?.deepspace || pkg2.devDependencies?.deepspace);
|
|
@@ -3790,7 +3904,7 @@ var add_default = defineCommand12({
|
|
|
3790
3904
|
const passArgs2 = args.list ? ["--list"] : args.info ? ["--info", String(args.info)] : ["--help"];
|
|
3791
3905
|
runInstaller(script2, passArgs2, process.cwd());
|
|
3792
3906
|
}
|
|
3793
|
-
if (!
|
|
3907
|
+
if (!existsSync12(appDir)) {
|
|
3794
3908
|
console.error(`Target directory not found: ${appDir}`);
|
|
3795
3909
|
console.error("Create a new app first: deepspace create <name>");
|
|
3796
3910
|
process.exit(1);
|
|
@@ -3806,8 +3920,8 @@ var add_default = defineCommand12({
|
|
|
3806
3920
|
if (!script) {
|
|
3807
3921
|
console.error("Could not find the deepspace feature installer.");
|
|
3808
3922
|
console.error("Looked in:");
|
|
3809
|
-
console.error(` ${
|
|
3810
|
-
console.error(` ${
|
|
3923
|
+
console.error(` ${join13(appDir, "node_modules", "deepspace", "scripts", "add-feature.cjs")}`);
|
|
3924
|
+
console.error(` ${join13(appDir, ".deepspace", "scripts", "add-feature.cjs")}`);
|
|
3811
3925
|
console.error("Are you in a DeepSpace app directory? Try `npm install` first.");
|
|
3812
3926
|
process.exit(1);
|
|
3813
3927
|
}
|
|
@@ -4833,8 +4947,8 @@ var invoke_default = defineCommand17({
|
|
|
4833
4947
|
|
|
4834
4948
|
// src/cli/commands/library.ts
|
|
4835
4949
|
import { defineCommand as defineCommand18 } from "citty";
|
|
4836
|
-
import { existsSync as
|
|
4837
|
-
import { join as
|
|
4950
|
+
import { existsSync as existsSync13, readFileSync as readFileSync14 } from "fs";
|
|
4951
|
+
import { join as join14, resolve as resolve9 } from "path";
|
|
4838
4952
|
import { parse as parseToml4 } from "smol-toml";
|
|
4839
4953
|
import * as p8 from "@clack/prompts";
|
|
4840
4954
|
var DEFAULT_LIBRARY_APP = "deepdotspace-site";
|
|
@@ -4912,8 +5026,8 @@ var publish = defineCommand18({
|
|
|
4912
5026
|
let appName = typeof args.app === "string" && args.app.trim() ? args.app.trim() : void 0;
|
|
4913
5027
|
if (!appName) {
|
|
4914
5028
|
const appDir = resolve9(typeof args.dir === "string" && args.dir ? args.dir : ".");
|
|
4915
|
-
const wranglerPath =
|
|
4916
|
-
if (!
|
|
5029
|
+
const wranglerPath = join14(appDir, "wrangler.toml");
|
|
5030
|
+
if (!existsSync13(wranglerPath)) {
|
|
4917
5031
|
return die("No --app provided and no wrangler.toml found. Either pass --app <name> or run from your app's directory.");
|
|
4918
5032
|
}
|
|
4919
5033
|
const cfg = parseToml4(readFileSync14(wranglerPath, "utf-8"));
|
|
@@ -5050,8 +5164,8 @@ var library_default = defineCommand18({
|
|
|
5050
5164
|
// src/cli/commands/feedback.ts
|
|
5051
5165
|
import { defineCommand as defineCommand19 } from "citty";
|
|
5052
5166
|
import * as p9 from "@clack/prompts";
|
|
5053
|
-
import { existsSync as
|
|
5054
|
-
import { dirname as dirname4, join as
|
|
5167
|
+
import { existsSync as existsSync14, readFileSync as readFileSync15 } from "fs";
|
|
5168
|
+
import { dirname as dirname4, join as join15 } from "path";
|
|
5055
5169
|
import { fileURLToPath as fileURLToPath2 } from "url";
|
|
5056
5170
|
import { release } from "os";
|
|
5057
5171
|
var API_URL7 = process.env.DEEPSPACE_API_URL ?? PLATFORM_URLS.api;
|
|
@@ -5074,11 +5188,11 @@ function readCliVersion() {
|
|
|
5074
5188
|
try {
|
|
5075
5189
|
const here = dirname4(fileURLToPath2(import.meta.url));
|
|
5076
5190
|
const candidates = [
|
|
5077
|
-
|
|
5078
|
-
|
|
5191
|
+
join15(here, "..", "package.json"),
|
|
5192
|
+
join15(here, "..", "..", "..", "package.json")
|
|
5079
5193
|
];
|
|
5080
5194
|
for (const path of candidates) {
|
|
5081
|
-
if (!
|
|
5195
|
+
if (!existsSync14(path)) continue;
|
|
5082
5196
|
const pkg2 = JSON.parse(readFileSync15(path, "utf-8"));
|
|
5083
5197
|
if (pkg2.name === "deepspace" && pkg2.version) return pkg2.version;
|
|
5084
5198
|
}
|
|
@@ -5696,8 +5810,8 @@ var init_default = defineCommand21({
|
|
|
5696
5810
|
|
|
5697
5811
|
// src/cli/cli.ts
|
|
5698
5812
|
var __dirname = dirname5(fileURLToPath3(import.meta.url));
|
|
5699
|
-
var pkg = JSON.parse(readFileSync17(
|
|
5700
|
-
if (process.platform === "linux" && !process.env.SSL_CERT_FILE &&
|
|
5813
|
+
var pkg = JSON.parse(readFileSync17(join16(__dirname, "..", "package.json"), "utf-8"));
|
|
5814
|
+
if (process.platform === "linux" && !process.env.SSL_CERT_FILE && existsSync15("/etc/ssl/certs/ca-certificates.crt")) {
|
|
5701
5815
|
process.env.SSL_CERT_FILE = "/etc/ssl/certs/ca-certificates.crt";
|
|
5702
5816
|
}
|
|
5703
5817
|
var create2 = defineCommand22({
|