@westbayberry/dg 1.1.2 → 1.1.4

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.
Files changed (2) hide show
  1. package/dist/index.mjs +587 -817
  2. package/package.json +2 -1
package/dist/index.mjs CHANGED
@@ -1649,7 +1649,7 @@ function initTelemetry(version) {
1649
1649
  });
1650
1650
  }
1651
1651
  function redact(s) {
1652
- return s.replace(/dg_(?:live|test)_[A-Za-z0-9_-]{3,}/gi, "[DG_KEY_REDACTED]").replace(/\/Users\/[^\s:]+/g, "[USER_PATH]").replace(/\/home\/[^\s:]+/g, "[USER_PATH]").replace(/C:\\Users\\[^\s:]+/g, "[USER_PATH]").replace(/Bearer [^\s]+/g, "Bearer [REDACTED]");
1652
+ return s.replace(/(--token(?:=|\s+))\S+/gi, "$1[REDACTED]").replace(/dg_(?:live|test)_[A-Za-z0-9_-]{3,}/gi, "[DG_KEY_REDACTED]").replace(/\/Users\/[^\s:]+/g, "[USER_PATH]").replace(/\/home\/[^\s:]+/g, "[USER_PATH]").replace(/C:\\Users\\[^\s:]+/g, "[USER_PATH]").replace(/Bearer [^\s]+/g, "Bearer [REDACTED]");
1653
1653
  }
1654
1654
  function suppressNudge() {
1655
1655
  return !telemetryEnabled();
@@ -1669,7 +1669,7 @@ function trimStack(raw, debug) {
1669
1669
  }
1670
1670
  function buildIssueUrl(error, ctx) {
1671
1671
  const msg = redact(error.message || error.name || "Unknown error").slice(0, 120);
1672
- const cmd = process.argv.slice(2).join(" ") || "(none)";
1672
+ const cmd = redact(process.argv.slice(2).join(" ")) || "(none)";
1673
1673
  const stack = trimStack(error.stack, false).join("\n");
1674
1674
  const body = [
1675
1675
  "**dg crashed**",
@@ -1730,7 +1730,7 @@ function captureError(error, context) {
1730
1730
  process.exitCode = 1;
1731
1731
  return;
1732
1732
  }
1733
- const cmd = process.argv.slice(2).join(" ") || "(none)";
1733
+ const cmd = redact(process.argv.slice(2).join(" ")) || "(none)";
1734
1734
  process.stderr.write("\n" + chalk18.dim(SEPARATOR) + "\n\n");
1735
1735
  process.stderr.write(
1736
1736
  " " + chalk18.red.bold("\u2718 dg crashed: ") + chalk18.red(redact(err.message || err.name)) + "\n\n"
@@ -1801,70 +1801,50 @@ __export(paths_exports, {
1801
1801
  dgCachePath: () => dgCachePath,
1802
1802
  dgConfigDir: () => dgConfigDir,
1803
1803
  dgConfigPath: () => dgConfigPath,
1804
- dgMigrationBreadcrumb: () => dgMigrationBreadcrumb,
1805
- dgMigrationLock: () => dgMigrationLock,
1806
1804
  dgPaths: () => dgPaths,
1807
1805
  dgReadme: () => dgReadme,
1808
1806
  dgRoot: () => dgRoot,
1809
1807
  dgStateDir: () => dgStateDir,
1810
- dgStatePath: () => dgStatePath,
1811
- legacyPaths: () => legacyPaths
1808
+ dgStatePath: () => dgStatePath
1812
1809
  });
1813
1810
  import { homedir } from "node:os";
1814
- import { join as join2, isAbsolute } from "node:path";
1811
+ import { join, isAbsolute } from "node:path";
1815
1812
  function safeAbsolute(p, fallback) {
1816
1813
  if (!p || typeof p !== "string") return fallback;
1817
1814
  if (!isAbsolute(p)) return fallback;
1818
1815
  return p;
1819
1816
  }
1820
1817
  function dgRoot() {
1821
- return join2(homedir(), `.${ROOT_DIR_NAME}`);
1818
+ return join(homedir(), `.${ROOT_DIR_NAME}`);
1822
1819
  }
1823
1820
  function dgConfigDir() {
1824
1821
  const xdg = safeAbsolute(process.env.XDG_CONFIG_HOME, "");
1825
- if (xdg) return join2(xdg, ROOT_DIR_NAME);
1822
+ if (xdg) return join(xdg, ROOT_DIR_NAME);
1826
1823
  return dgRoot();
1827
1824
  }
1828
1825
  function dgCacheDir() {
1829
1826
  const explicit = safeAbsolute(process.env.DG_CACHE_DIR, "");
1830
1827
  if (explicit) return explicit;
1831
1828
  const xdg = safeAbsolute(process.env.XDG_CACHE_HOME, "");
1832
- if (xdg) return join2(xdg, ROOT_DIR_NAME);
1833
- return join2(dgRoot(), "cache");
1829
+ if (xdg) return join(xdg, ROOT_DIR_NAME);
1830
+ return join(dgRoot(), "cache");
1834
1831
  }
1835
1832
  function dgStateDir() {
1836
1833
  const xdg = safeAbsolute(process.env.XDG_STATE_HOME, "");
1837
- if (xdg) return join2(xdg, ROOT_DIR_NAME);
1838
- return join2(dgRoot(), "state");
1834
+ if (xdg) return join(xdg, ROOT_DIR_NAME);
1835
+ return join(dgRoot(), "state");
1839
1836
  }
1840
1837
  function dgConfigPath() {
1841
- return join2(dgConfigDir(), "config.json");
1838
+ return join(dgConfigDir(), "config.json");
1842
1839
  }
1843
1840
  function dgCachePath(name) {
1844
- return join2(dgCacheDir(), name);
1841
+ return join(dgCacheDir(), name);
1845
1842
  }
1846
1843
  function dgStatePath(name) {
1847
- return join2(dgStateDir(), name);
1848
- }
1849
- function dgMigrationBreadcrumb() {
1850
- return join2(dgRoot(), ".migrated-from-v1");
1851
- }
1852
- function dgMigrationLock() {
1853
- return join2(dgRoot(), ".migration.lock");
1844
+ return join(dgStateDir(), name);
1854
1845
  }
1855
1846
  function dgReadme() {
1856
- return join2(dgRoot(), "README.txt");
1857
- }
1858
- function legacyPaths() {
1859
- const home = homedir();
1860
- const depGuardianDir = join2(home, ".dependency-guardian");
1861
- return {
1862
- dgrc: join2(home, ".dgrc.json"),
1863
- cacheDir: depGuardianDir,
1864
- updateCheck: join2(home, ".dg-update-check.json"),
1865
- aliasesShOld: join2(depGuardianDir, "aliases.sh"),
1866
- depGuardianDir
1867
- };
1847
+ return join(dgRoot(), "README.txt");
1868
1848
  }
1869
1849
  function dgPaths() {
1870
1850
  return {
@@ -1876,9 +1856,7 @@ function dgPaths() {
1876
1856
  updateCheck: dgCachePath("update-check.json"),
1877
1857
  aliasesSh: dgStatePath("aliases.sh"),
1878
1858
  hooksRegistry: dgStatePath("hooks-installed.json"),
1879
- readme: dgReadme(),
1880
- migrationBreadcrumb: dgMigrationBreadcrumb(),
1881
- migrationLock: dgMigrationLock()
1859
+ readme: dgReadme()
1882
1860
  };
1883
1861
  }
1884
1862
  var ROOT_DIR_NAME;
@@ -1958,49 +1936,64 @@ function authBase() {
1958
1936
  }
1959
1937
  }
1960
1938
  async function createAuthSession() {
1961
- let res;
1939
+ const ctrl = new AbortController();
1940
+ const timer = setTimeout(() => ctrl.abort(), 1e4);
1962
1941
  try {
1963
- res = await globalThis.fetch(`${authBase()}/cli/auth/sessions`, {
1964
- method: "POST",
1965
- headers: { "Content-Type": "application/json" }
1966
- });
1967
- } catch {
1968
- throw new Error("Could not connect to westbayberry.com");
1969
- }
1970
- if (!res.ok) {
1971
- const body = await res.text().catch(() => "");
1972
- throw new Error(
1973
- `Failed to create auth session (HTTP ${res.status})${body ? `: ${body}` : ""}`
1974
- );
1942
+ let res;
1943
+ try {
1944
+ res = await globalThis.fetch(`${authBase()}/cli/auth/sessions`, {
1945
+ method: "POST",
1946
+ headers: { "Content-Type": "application/json" },
1947
+ signal: ctrl.signal
1948
+ });
1949
+ } catch {
1950
+ throw new Error("Could not connect to westbayberry.com");
1951
+ }
1952
+ if (!res.ok) {
1953
+ const body = await res.text().catch(() => "");
1954
+ throw new Error(
1955
+ `Failed to create auth session (HTTP ${res.status})${body ? `: ${body}` : ""}`
1956
+ );
1957
+ }
1958
+ const json = await res.json();
1959
+ return {
1960
+ sessionId: json.session_id,
1961
+ verifyUrl: json.verify_url,
1962
+ expiresIn: json.expires_in
1963
+ };
1964
+ } finally {
1965
+ clearTimeout(timer);
1975
1966
  }
1976
- const json = await res.json();
1977
- return {
1978
- sessionId: json.session_id,
1979
- verifyUrl: json.verify_url,
1980
- expiresIn: json.expires_in
1981
- };
1982
1967
  }
1983
1968
  async function pollAuthSession(sessionId) {
1984
- let res;
1969
+ const ctrl = new AbortController();
1970
+ const timer = setTimeout(() => ctrl.abort(), 8e3);
1985
1971
  try {
1986
- res = await globalThis.fetch(
1987
- `${authBase()}/cli/auth/sessions/${sessionId}/token`
1988
- );
1989
- } catch {
1990
- return { status: "expired" };
1991
- }
1992
- if (res.status === 404) {
1993
- return { status: "expired" };
1994
- }
1995
- if (!res.ok) {
1996
- return { status: "expired" };
1972
+ let res;
1973
+ try {
1974
+ res = await globalThis.fetch(
1975
+ `${authBase()}/cli/auth/sessions/${sessionId}/token`,
1976
+ { signal: ctrl.signal }
1977
+ );
1978
+ } catch (e) {
1979
+ if (e instanceof Error && e.name === "AbortError") return { status: "pending" };
1980
+ return { status: "expired" };
1981
+ }
1982
+ if (res.status === 404) {
1983
+ return { status: "expired" };
1984
+ }
1985
+ if (!res.ok) {
1986
+ return { status: "expired" };
1987
+ }
1988
+ const json = await res.json();
1989
+ return {
1990
+ status: json.status,
1991
+ apiKey: json.api_key,
1992
+ email: json.email
1993
+ };
1994
+ } finally {
1995
+ clearTimeout(timer);
1997
1996
  }
1998
- const json = await res.json();
1999
- return {
2000
- status: json.status,
2001
- apiKey: json.api_key,
2002
- email: json.email
2003
- };
2004
1997
  }
2005
1998
  function configPath() {
2006
1999
  return dgConfigPath();
@@ -2297,7 +2290,7 @@ async function preflightAuthCheck(apiUrl) {
2297
2290
  const cached = readCachedAuthStatus();
2298
2291
  if (cached) {
2299
2292
  if (cached.freeTierCapReached) {
2300
- throw new PreflightFreeCapReachedError(cached.scansUsed, cached.scansLimit ?? cached.scansUsed);
2293
+ throw new PreflightFreeCapReachedError(cached.scansUsed, cached.scansLimit ?? cached.scansUsed, cached.capReason ?? "monthly_limit");
2301
2294
  }
2302
2295
  return cached;
2303
2296
  }
@@ -2331,15 +2324,17 @@ async function preflightAuthCheck(apiUrl) {
2331
2324
  } catch {
2332
2325
  }
2333
2326
  if (body.freeTierCapReached) {
2327
+ const capReason = body.capReason === "prefix_cap" ? "prefix_cap" : "monthly_limit";
2334
2328
  const status2 = {
2335
2329
  authenticated: !!apiKey,
2336
2330
  freeTierCapReached: true,
2337
2331
  scansUsed: body.scansUsed ?? 0,
2338
2332
  scansLimit: body.maxScans ?? 0,
2333
+ capReason,
2339
2334
  fetchedAt: Date.now()
2340
2335
  };
2341
2336
  writeCachedAuthStatus(status2);
2342
- throw new PreflightFreeCapReachedError(status2.scansUsed, status2.scansLimit ?? 0);
2337
+ throw new PreflightFreeCapReachedError(status2.scansUsed, status2.scansLimit ?? 0, capReason);
2343
2338
  }
2344
2339
  }
2345
2340
  if (!resp.ok) {
@@ -2476,10 +2471,13 @@ var init_auth = __esm({
2476
2471
  init_paths();
2477
2472
  DEFAULT_WEB_BASE = "https://westbayberry.com";
2478
2473
  PreflightFreeCapReachedError = class extends Error {
2479
- constructor(scansUsed, maxScans) {
2480
- super("Free tier monthly cap reached. Run `dg upgrade` for Pro.");
2474
+ constructor(scansUsed, maxScans, reason = "monthly_limit") {
2475
+ super(
2476
+ reason === "prefix_cap" ? "Too many anonymous devices from your network this month. Sign in with `dg login` to keep scanning." : "Free tier monthly package limit reached. Run `dg upgrade` for Pro."
2477
+ );
2481
2478
  this.scansUsed = scansUsed;
2482
2479
  this.maxScans = maxScans;
2480
+ this.reason = reason;
2483
2481
  this.name = "PreflightFreeCapReachedError";
2484
2482
  }
2485
2483
  };
@@ -2499,7 +2497,7 @@ __export(config_exports, {
2499
2497
  });
2500
2498
  import { parseArgs } from "node:util";
2501
2499
  import { readFileSync as readFileSync2, existsSync as existsSync2 } from "node:fs";
2502
- import { join as join3, dirname as dirname2 } from "node:path";
2500
+ import { join as join2, dirname as dirname2 } from "node:path";
2503
2501
  import { fileURLToPath } from "node:url";
2504
2502
  function levenshtein(a, b) {
2505
2503
  if (a === b) return 0;
@@ -2540,28 +2538,24 @@ function warnUnknownDgrcKeys(parsed, source) {
2540
2538
  }
2541
2539
  }
2542
2540
  function loadDgrc() {
2543
- const cwdPath = join3(process.cwd(), ".dgrc.json");
2541
+ const cwdPath = join2(process.cwd(), ".dgrc.json");
2544
2542
  const homePath = dgConfigPath();
2545
- const legacyHomePath = legacyPaths().dgrc;
2546
2543
  let config = {};
2547
- const sources = [homePath, legacyHomePath].filter((p, i, arr) => arr.indexOf(p) === i);
2548
- for (const src of sources) {
2549
- if (!existsSync2(src)) continue;
2544
+ if (existsSync2(homePath)) {
2550
2545
  try {
2551
- const data = JSON.parse(readFileSync2(src, "utf-8"));
2552
- warnUnknownDgrcKeys(data, src);
2546
+ const data = JSON.parse(readFileSync2(homePath, "utf-8"));
2547
+ warnUnknownDgrcKeys(data, homePath);
2553
2548
  const filtered = {};
2554
2549
  for (const k of KNOWN_DGRC_KEYS) {
2555
2550
  if (k in data) filtered[k] = data[k];
2556
2551
  }
2557
2552
  config = filtered;
2558
- break;
2559
2553
  } catch {
2560
- process.stderr.write(`Warning: Failed to parse ${src}, ignoring.
2554
+ process.stderr.write(`Warning: Failed to parse ${homePath}, ignoring.
2561
2555
  `);
2562
2556
  }
2563
2557
  }
2564
- if (cwdPath !== homePath && cwdPath !== legacyHomePath && existsSync2(cwdPath) && process.env.DG_QUIET !== "1") {
2558
+ if (cwdPath !== homePath && existsSync2(cwdPath) && process.env.DG_QUIET !== "1") {
2565
2559
  process.stderr.write(
2566
2560
  `dg: note: ./.dgrc.json is ignored (repo-controlled config is no longer honored). Use ~/.dg/.dgrc.json, env vars (DG_MODE, DG_API_URL), or CLI flags.
2567
2561
  `
@@ -2599,7 +2593,7 @@ function getVersion() {
2599
2593
  try {
2600
2594
  const thisDir = dirname2(fileURLToPath(import.meta.url));
2601
2595
  const pkg = JSON.parse(
2602
- readFileSync2(join3(thisDir, "..", "package.json"), "utf-8")
2596
+ readFileSync2(join2(thisDir, "..", "package.json"), "utf-8")
2603
2597
  );
2604
2598
  return pkg.version ?? "1.0.0";
2605
2599
  } catch {
@@ -3047,8 +3041,8 @@ var init_terminal_state = __esm({
3047
3041
  });
3048
3042
 
3049
3043
  // src/shims/safe-fs.ts
3050
- import { existsSync as existsSync5, lstatSync as lstatSync3, mkdirSync as mkdirSync4, renameSync, statSync as statSync2, unlinkSync as unlinkSync4, writeFileSync as writeFileSync4 } from "node:fs";
3051
- import { dirname as dirname5, sep } from "node:path";
3044
+ import { existsSync as existsSync4, lstatSync as lstatSync3, mkdirSync as mkdirSync3, renameSync, statSync, unlinkSync as unlinkSync3, writeFileSync as writeFileSync3 } from "node:fs";
3045
+ import { dirname as dirname4, sep } from "node:path";
3052
3046
  import { homedir as homedir2 } from "node:os";
3053
3047
  function ensureUnderHome(target) {
3054
3048
  const home = homedir2();
@@ -3077,28 +3071,28 @@ function safeMkdirRecursive(target, mode = 493) {
3077
3071
  for (const segment of rel) {
3078
3072
  cur = cur + sep + segment;
3079
3073
  lstatNoSymlink(cur);
3080
- if (!existsSync5(cur)) {
3081
- mkdirSync4(cur, { mode });
3074
+ if (!existsSync4(cur)) {
3075
+ mkdirSync3(cur, { mode });
3082
3076
  }
3083
3077
  }
3084
3078
  }
3085
3079
  function safeWriteFile(target, content, mode = 420) {
3086
3080
  ensureUnderHome(target);
3087
- lstatNoSymlink(dirname5(target));
3081
+ lstatNoSymlink(dirname4(target));
3088
3082
  lstatNoSymlink(target);
3089
- writeFileSync4(target, content, { mode });
3083
+ writeFileSync3(target, content, { mode });
3090
3084
  }
3091
3085
  function atomicWriteFile(target, content, mode = 420) {
3092
3086
  ensureUnderHome(target);
3093
- lstatNoSymlink(dirname5(target));
3087
+ lstatNoSymlink(dirname4(target));
3094
3088
  lstatNoSymlink(target);
3095
3089
  const tmp = `${target}.tmp.${process.pid}.${Date.now()}`;
3096
- writeFileSync4(tmp, content, { mode });
3090
+ writeFileSync3(tmp, content, { mode });
3097
3091
  renameSync(tmp, target);
3098
3092
  }
3099
3093
  function isExecutable(path2) {
3100
3094
  try {
3101
- const st = statSync2(path2);
3095
+ const st = statSync(path2);
3102
3096
  return st.isFile() && (st.mode & 73) !== 0;
3103
3097
  } catch {
3104
3098
  return false;
@@ -3112,7 +3106,7 @@ function safeUnlink(target) {
3112
3106
  if (e instanceof UnsafePathError) throw e;
3113
3107
  }
3114
3108
  try {
3115
- unlinkSync4(target);
3109
+ unlinkSync3(target);
3116
3110
  } catch (e) {
3117
3111
  const code = e.code;
3118
3112
  if (code !== "ENOENT") throw e;
@@ -3241,10 +3235,10 @@ exit /b 127
3241
3235
 
3242
3236
  // src/shims/rc-syntax.ts
3243
3237
  import { homedir as homedir3 } from "node:os";
3244
- import { join as join4 } from "node:path";
3245
- import { existsSync as existsSync6, readFileSync as readFileSync5, lstatSync as lstatSync4, appendFileSync, writeFileSync as writeFileSync5 } from "node:fs";
3238
+ import { join as join3 } from "node:path";
3239
+ import { existsSync as existsSync5, readFileSync as readFileSync4, lstatSync as lstatSync4, appendFileSync, writeFileSync as writeFileSync4 } from "node:fs";
3246
3240
  function expandHome(path2) {
3247
- if (path2.startsWith("~/")) return join4(homedir3(), path2.slice(2));
3241
+ if (path2.startsWith("~/")) return join3(homedir3(), path2.slice(2));
3248
3242
  return path2;
3249
3243
  }
3250
3244
  function detectShellKind(envShell) {
@@ -3258,13 +3252,13 @@ function rcCandidates(kind) {
3258
3252
  const home = homedir3();
3259
3253
  switch (kind) {
3260
3254
  case "zsh":
3261
- return [join4(home, ".zshrc")];
3255
+ return [join3(home, ".zshrc")];
3262
3256
  case "bash":
3263
- return [join4(home, ".bashrc"), join4(home, ".bash_profile")];
3257
+ return [join3(home, ".bashrc"), join3(home, ".bash_profile")];
3264
3258
  case "fish":
3265
- return [join4(home, ".config", "fish", "config.fish")];
3259
+ return [join3(home, ".config", "fish", "config.fish")];
3266
3260
  case "sh":
3267
- return [join4(home, ".profile")];
3261
+ return [join3(home, ".profile")];
3268
3262
  }
3269
3263
  }
3270
3264
  function pathSnippet(kind) {
@@ -3287,12 +3281,12 @@ function appendSentinelBlock(rcPath, snippet) {
3287
3281
  return { status: "failed", path: resolved, reason: e.message };
3288
3282
  }
3289
3283
  }
3290
- if (existsSync6(resolved)) {
3284
+ if (existsSync5(resolved)) {
3291
3285
  const st = lstatSync4(resolved);
3292
3286
  if (!st.isFile()) {
3293
3287
  return { status: "failed", path: resolved, reason: "rc path is not a regular file" };
3294
3288
  }
3295
- const existing = readFileSync5(resolved, "utf-8");
3289
+ const existing = readFileSync4(resolved, "utf-8");
3296
3290
  if (existing.includes(RC_SENTINEL_OPEN)) {
3297
3291
  return { status: "already-present", path: resolved };
3298
3292
  }
@@ -3303,10 +3297,10 @@ ${snippet}
3303
3297
  ${RC_SENTINEL_CLOSE}
3304
3298
  `;
3305
3299
  try {
3306
- if (existsSync6(resolved)) {
3300
+ if (existsSync5(resolved)) {
3307
3301
  appendFileSync(resolved, block, { encoding: "utf-8" });
3308
3302
  } else {
3309
- writeFileSync5(resolved, block, { encoding: "utf-8", mode: 420 });
3303
+ writeFileSync4(resolved, block, { encoding: "utf-8", mode: 420 });
3310
3304
  }
3311
3305
  return { status: "appended", path: resolved };
3312
3306
  } catch (e) {
@@ -3320,7 +3314,7 @@ function stripSentinelBlock(rcPath) {
3320
3314
  } catch (e) {
3321
3315
  return { status: "failed", path: resolved, reason: e.message };
3322
3316
  }
3323
- if (!existsSync6(resolved)) {
3317
+ if (!existsSync5(resolved)) {
3324
3318
  return { status: "already-present", path: resolved };
3325
3319
  }
3326
3320
  try {
@@ -3330,7 +3324,7 @@ function stripSentinelBlock(rcPath) {
3330
3324
  return { status: "failed", path: resolved, reason: e.message };
3331
3325
  }
3332
3326
  }
3333
- const original = readFileSync5(resolved, "utf-8");
3327
+ const original = readFileSync4(resolved, "utf-8");
3334
3328
  if (!original.includes(RC_SENTINEL_OPEN)) {
3335
3329
  return { status: "already-present", path: resolved };
3336
3330
  }
@@ -3357,7 +3351,7 @@ function stripSentinelBlock(rcPath) {
3357
3351
  if (original.endsWith("\n") && !result.endsWith("\n")) result += "\n";
3358
3352
  if (!original.endsWith("\n") && result.endsWith("\n")) result = result.slice(0, -1);
3359
3353
  try {
3360
- writeFileSync5(resolved, result, { encoding: "utf-8" });
3354
+ writeFileSync4(resolved, result, { encoding: "utf-8" });
3361
3355
  return { status: "appended", path: resolved };
3362
3356
  } catch (e) {
3363
3357
  return { status: "failed", path: resolved, reason: e.message };
@@ -3381,11 +3375,11 @@ __export(resolve_exports, {
3381
3375
  resolveRealBinary: () => resolveRealBinary,
3382
3376
  walkPathExcludingShimDir: () => walkPathExcludingShimDir
3383
3377
  });
3384
- import { existsSync as existsSync7, readFileSync as readFileSync6 } from "node:fs";
3385
- import { join as join5, delimiter, sep as sep2 } from "node:path";
3378
+ import { existsSync as existsSync6, readFileSync as readFileSync5 } from "node:fs";
3379
+ import { join as join4, delimiter, sep as sep2 } from "node:path";
3386
3380
  import { homedir as homedir4 } from "node:os";
3387
3381
  function shimDir() {
3388
- return join5(homedir4(), ".dg", "shims");
3382
+ return join4(homedir4(), ".dg", "shims");
3389
3383
  }
3390
3384
  function walkPathExcludingShimDir(name, extraExtensions = []) {
3391
3385
  const raw = process.env.PATH ?? "/usr/bin:/bin";
@@ -3395,7 +3389,7 @@ function walkPathExcludingShimDir(name, extraExtensions = []) {
3395
3389
  for (const dir of parts) {
3396
3390
  if (dir === shims || dir.startsWith(shims + sep2)) continue;
3397
3391
  for (const ext of ["", ...exts]) {
3398
- const candidate = join5(dir, name + ext);
3392
+ const candidate = join4(dir, name + ext);
3399
3393
  if (isExecutable(candidate)) return candidate;
3400
3394
  }
3401
3395
  }
@@ -3410,7 +3404,7 @@ function platformExtensions() {
3410
3404
  }
3411
3405
  function readCache2() {
3412
3406
  try {
3413
- const raw = readFileSync6(CACHE_PATH(), "utf-8");
3407
+ const raw = readFileSync5(CACHE_PATH(), "utf-8");
3414
3408
  const parsed = JSON.parse(raw);
3415
3409
  if (typeof parsed === "object" && parsed !== null) {
3416
3410
  return parsed;
@@ -3432,7 +3426,7 @@ function resolveRealBinary(ecosystem) {
3432
3426
  }
3433
3427
  const cache3 = readCache2();
3434
3428
  const cached = cache3[ecosystem];
3435
- if (cached && existsSync7(cached) && isExecutable(cached)) {
3429
+ if (cached && existsSync6(cached) && isExecutable(cached)) {
3436
3430
  return cached;
3437
3431
  }
3438
3432
  const resolved = walkPath(ecosystem, exts);
@@ -3479,13 +3473,13 @@ __export(install_exports, {
3479
3473
  uninstallShims: () => uninstallShims
3480
3474
  });
3481
3475
  import { homedir as homedir5 } from "node:os";
3482
- import { join as join6, dirname as dirname6 } from "node:path";
3476
+ import { join as join5, dirname as dirname5 } from "node:path";
3483
3477
  import { fileURLToPath as fileURLToPath2 } from "node:url";
3484
- import { chmodSync as chmodSync4, chownSync, existsSync as existsSync8, readdirSync, readFileSync as readFileSync7, statSync as statSync3, appendFileSync as appendFileSync2, writeFileSync as writeFileSync6 } from "node:fs";
3478
+ import { chmodSync as chmodSync3, chownSync, existsSync as existsSync7, readdirSync, readFileSync as readFileSync6, statSync as statSync2, appendFileSync as appendFileSync2, writeFileSync as writeFileSync5 } from "node:fs";
3485
3479
  import { spawnSync } from "node:child_process";
3486
3480
  import { randomBytes } from "node:crypto";
3487
3481
  function dgShimDir() {
3488
- return join6(homedir5(), ".dg", "shims");
3482
+ return join5(homedir5(), ".dg", "shims");
3489
3483
  }
3490
3484
  function noncePath() {
3491
3485
  return dgStatePath("shim-nonce");
@@ -3497,12 +3491,12 @@ function bypassLogPath() {
3497
3491
  return dgStatePath("bypass.log");
3498
3492
  }
3499
3493
  function dgEntryStatePath(targetHome) {
3500
- return join6(targetHome, ".dg", "state", "dg-entry");
3494
+ return join5(targetHome, ".dg", "state", "dg-entry");
3501
3495
  }
3502
3496
  function currentDgEntry() {
3503
3497
  try {
3504
- const entry = join6(dirname6(fileURLToPath2(import.meta.url)), "index.mjs");
3505
- if (existsSync8(entry)) return entry;
3498
+ const entry = join5(dirname5(fileURLToPath2(import.meta.url)), "index.mjs");
3499
+ if (existsSync7(entry)) return entry;
3506
3500
  } catch {
3507
3501
  }
3508
3502
  try {
@@ -3518,18 +3512,18 @@ function ensureDgEntryRecorded(targetHome = homedir5()) {
3518
3512
  const path2 = dgEntryStatePath(targetHome);
3519
3513
  let existing = null;
3520
3514
  try {
3521
- existing = readFileSync7(path2, "utf-8").trim();
3515
+ existing = readFileSync6(path2, "utf-8").trim();
3522
3516
  } catch {
3523
3517
  }
3524
3518
  if (existing === entry) return;
3525
- safeMkdirRecursive(dirname6(path2), 493);
3519
+ safeMkdirRecursive(dirname5(path2), 493);
3526
3520
  safeWriteFile(path2, entry + "\n", 420);
3527
3521
  } catch {
3528
3522
  }
3529
3523
  }
3530
3524
  function readNonce() {
3531
3525
  try {
3532
- const raw = readFileSync7(noncePath(), "utf-8").trim();
3526
+ const raw = readFileSync6(noncePath(), "utf-8").trim();
3533
3527
  return raw.length > 0 ? raw : null;
3534
3528
  } catch {
3535
3529
  return null;
@@ -3571,13 +3565,13 @@ function persistWindowsPath(shimsDir, outcomes) {
3571
3565
  }
3572
3566
  function updatePowerShellProfile(targetHome, shimsDir, outcomes) {
3573
3567
  if (process.platform !== "win32") return;
3574
- const profilePath = join6(targetHome, "Documents", "PowerShell", "Microsoft.PowerShell_profile.ps1");
3575
- if (!existsSync8(profilePath)) {
3568
+ const profilePath = join5(targetHome, "Documents", "PowerShell", "Microsoft.PowerShell_profile.ps1");
3569
+ if (!existsSync7(profilePath)) {
3576
3570
  outcomes.push({ status: "already-present", path: profilePath });
3577
3571
  return;
3578
3572
  }
3579
3573
  try {
3580
- const existing = readFileSync7(profilePath, "utf-8");
3574
+ const existing = readFileSync6(profilePath, "utf-8");
3581
3575
  if (existing.includes(">>> dg-managed >>>")) {
3582
3576
  outcomes.push({ status: "already-present", path: profilePath });
3583
3577
  return;
@@ -3596,12 +3590,12 @@ $env:Path = "${shimsDir};$env:Path"
3596
3590
  function chownTreeIfNeeded(root, uid, gid) {
3597
3591
  if (uid === void 0 || gid === void 0) return;
3598
3592
  if (process.platform === "win32") return;
3599
- if (!existsSync8(root)) return;
3593
+ if (!existsSync7(root)) return;
3600
3594
  chownIfNeeded(root, uid, gid);
3601
3595
  try {
3602
3596
  for (const entry of readdirSync(root)) {
3603
- const child = join6(root, entry);
3604
- const st = statSync3(child);
3597
+ const child = join5(root, entry);
3598
+ const st = statSync2(child);
3605
3599
  if (st.isDirectory()) {
3606
3600
  chownTreeIfNeeded(child, uid, gid);
3607
3601
  } else {
@@ -3614,18 +3608,18 @@ function chownTreeIfNeeded(root, uid, gid) {
3614
3608
  function installShims(opts = {}) {
3615
3609
  const targetHome = opts.targetHome ?? homedir5();
3616
3610
  const platform3 = opts.platform ?? (process.platform === "win32" ? "windows" : "unix");
3617
- const dgRoot2 = join6(targetHome, ".dg");
3618
- const shimsDir = join6(targetHome, ".dg", "shims");
3619
- const stateDir = join6(targetHome, ".dg", "state");
3611
+ const dgRoot2 = join5(targetHome, ".dg");
3612
+ const shimsDir = join5(targetHome, ".dg", "shims");
3613
+ const stateDir = join5(targetHome, ".dg", "state");
3620
3614
  safeMkdirRecursive(dgRoot2, 493);
3621
3615
  safeMkdirRecursive(stateDir, 493);
3622
3616
  safeMkdirRecursive(shimsDir, 493);
3623
3617
  const nonce = randomBytes(16).toString("hex");
3624
- const noncePathResolved = join6(stateDir, "shim-nonce");
3618
+ const noncePathResolved = join5(stateDir, "shim-nonce");
3625
3619
  safeWriteFile(noncePathResolved, nonce, 384);
3626
3620
  chownIfNeeded(noncePathResolved, opts.targetUid, opts.targetGid);
3627
3621
  const dgEntry = currentDgEntry();
3628
- const dgEntryPathResolved = join6(stateDir, "dg-entry");
3622
+ const dgEntryPathResolved = join5(stateDir, "dg-entry");
3629
3623
  if (dgEntry) {
3630
3624
  safeWriteFile(dgEntryPathResolved, dgEntry + "\n", 420);
3631
3625
  chownIfNeeded(dgEntryPathResolved, opts.targetUid, opts.targetGid);
@@ -3633,10 +3627,10 @@ function installShims(opts = {}) {
3633
3627
  const shimsCreated = [];
3634
3628
  for (const eco of ECOSYSTEMS) {
3635
3629
  const filename = shimFilename(eco, platform3);
3636
- const fullPath = join6(shimsDir, filename);
3630
+ const fullPath = join5(shimsDir, filename);
3637
3631
  const body = renderShim({ ecosystem: eco, platform: platform3 });
3638
3632
  safeWriteFile(fullPath, body, platform3 === "windows" ? 420 : 493);
3639
- if (platform3 !== "windows") chmodSync4(fullPath, 493);
3633
+ if (platform3 !== "windows") chmodSync3(fullPath, 493);
3640
3634
  chownIfNeeded(fullPath, opts.targetUid, opts.targetGid);
3641
3635
  shimsCreated.push(filename);
3642
3636
  }
@@ -3648,7 +3642,7 @@ function installShims(opts = {}) {
3648
3642
  resolvedRealBinaries[eco] = resolveRealBinary(eco);
3649
3643
  }
3650
3644
  const cachePathResolved = realBinaryCachePath();
3651
- if (existsSync8(cachePathResolved)) {
3645
+ if (existsSync7(cachePathResolved)) {
3652
3646
  chownIfNeeded(cachePathResolved, opts.targetUid, opts.targetGid);
3653
3647
  }
3654
3648
  const rcOutcomes = [];
@@ -3683,7 +3677,7 @@ function installShims(opts = {}) {
3683
3677
  nodeVersion: process.version,
3684
3678
  dgVersion: process.env.DG_CLI_VERSION ?? "unknown"
3685
3679
  };
3686
- const receiptResolved = join6(stateDir, "install-receipt.json");
3680
+ const receiptResolved = join5(stateDir, "install-receipt.json");
3687
3681
  safeWriteFile(receiptResolved, JSON.stringify(receipt, null, 2), 420);
3688
3682
  chownIfNeeded(receiptResolved, opts.targetUid, opts.targetGid);
3689
3683
  chownTreeIfNeeded(dgRoot2, opts.targetUid, opts.targetGid);
@@ -3699,31 +3693,31 @@ function installShims(opts = {}) {
3699
3693
  function uninstallShims(opts = {}) {
3700
3694
  const targetHome = opts.targetHome ?? homedir5();
3701
3695
  const platform3 = opts.platform ?? (process.platform === "win32" ? "windows" : "unix");
3702
- const shimsDir = join6(targetHome, ".dg", "shims");
3703
- const stateDir = join6(targetHome, ".dg", "state");
3696
+ const shimsDir = join5(targetHome, ".dg", "shims");
3697
+ const stateDir = join5(targetHome, ".dg", "state");
3704
3698
  const shimsRemoved = [];
3705
- if (existsSync8(shimsDir)) {
3699
+ if (existsSync7(shimsDir)) {
3706
3700
  for (const eco of ECOSYSTEMS) {
3707
3701
  const filename = shimFilename(eco, platform3);
3708
- const fullPath = join6(shimsDir, filename);
3709
- if (existsSync8(fullPath)) {
3702
+ const fullPath = join5(shimsDir, filename);
3703
+ if (existsSync7(fullPath)) {
3710
3704
  safeUnlink(fullPath);
3711
3705
  shimsRemoved.push(filename);
3712
3706
  }
3713
3707
  }
3714
3708
  }
3715
3709
  const stateFiles = [
3716
- join6(stateDir, "shim-nonce"),
3717
- join6(stateDir, "dg-entry"),
3718
- join6(stateDir, "install-receipt.json"),
3719
- join6(stateDir, "real-binaries.json"),
3720
- join6(stateDir, "bypass.log"),
3721
- join6(stateDir, "wiring-hint-shown"),
3722
- join6(stateDir, "first-run-shown")
3710
+ join5(stateDir, "shim-nonce"),
3711
+ join5(stateDir, "dg-entry"),
3712
+ join5(stateDir, "install-receipt.json"),
3713
+ join5(stateDir, "real-binaries.json"),
3714
+ join5(stateDir, "bypass.log"),
3715
+ join5(stateDir, "wiring-hint-shown"),
3716
+ join5(stateDir, "first-run-shown")
3723
3717
  ];
3724
3718
  const stateFilesRemoved = [];
3725
3719
  for (const f of stateFiles) {
3726
- if (existsSync8(f)) {
3720
+ if (existsSync7(f)) {
3727
3721
  safeUnlink(f);
3728
3722
  stateFilesRemoved.push(f);
3729
3723
  }
@@ -3743,7 +3737,7 @@ function uninstallShims(opts = {}) {
3743
3737
  }
3744
3738
  function revertWindowsPath(targetHome, outcomes) {
3745
3739
  if (process.platform !== "win32") return;
3746
- const shimsDir = join6(targetHome, ".dg", "shims");
3740
+ const shimsDir = join5(targetHome, ".dg", "shims");
3747
3741
  const currentPath = process.env.PATH ?? "";
3748
3742
  if (!currentPath.toLowerCase().includes(shimsDir.toLowerCase())) {
3749
3743
  outcomes.push({ status: "already-present", path: "user PATH (HKCU\\Environment)" });
@@ -3767,19 +3761,19 @@ function revertWindowsPath(targetHome, outcomes) {
3767
3761
  }
3768
3762
  function revertPowerShellProfile(targetHome, outcomes) {
3769
3763
  if (process.platform !== "win32") return;
3770
- const profilePath = join6(targetHome, "Documents", "PowerShell", "Microsoft.PowerShell_profile.ps1");
3771
- if (!existsSync8(profilePath)) {
3764
+ const profilePath = join5(targetHome, "Documents", "PowerShell", "Microsoft.PowerShell_profile.ps1");
3765
+ if (!existsSync7(profilePath)) {
3772
3766
  outcomes.push({ status: "already-present", path: profilePath });
3773
3767
  return;
3774
3768
  }
3775
3769
  try {
3776
- const existing = readFileSync7(profilePath, "utf-8");
3770
+ const existing = readFileSync6(profilePath, "utf-8");
3777
3771
  if (!existing.includes(">>> dg-managed >>>")) {
3778
3772
  outcomes.push({ status: "already-present", path: profilePath });
3779
3773
  return;
3780
3774
  }
3781
3775
  const stripped = existing.replace(/\n?# >>> dg-managed >>>[\s\S]*?# <<< dg-managed <<<\n?/g, "");
3782
- writeFileSync6(profilePath, stripped, "utf-8");
3776
+ writeFileSync5(profilePath, stripped, "utf-8");
3783
3777
  outcomes.push({ status: "appended", path: profilePath });
3784
3778
  } catch (e) {
3785
3779
  outcomes.push({ status: "failed", path: profilePath, reason: e.message });
@@ -3945,7 +3939,7 @@ unset it manually if you want fully anonymous behavior.
3945
3939
  UPGRADE = `
3946
3940
  dg upgrade \u2014 start Stripe checkout for Pro
3947
3941
 
3948
- Free tier is 1000 scans/mo per device. Pro is 5000/mo + watchlists +
3942
+ Free tier is 50,000 packages/mo per device. Pro is 250,000/mo + watchlists +
3949
3943
  saved reports + Dashboard analytics.
3950
3944
 
3951
3945
  Usage:
@@ -4000,8 +3994,8 @@ var first_run_exports = {};
4000
3994
  __export(first_run_exports, {
4001
3995
  maybeShowWelcomePanel: () => maybeShowWelcomePanel
4002
3996
  });
4003
- import { existsSync as existsSync9, writeFileSync as writeFileSync7, mkdirSync as mkdirSync5 } from "node:fs";
4004
- import { dirname as dirname7 } from "node:path";
3997
+ import { existsSync as existsSync8, writeFileSync as writeFileSync6, mkdirSync as mkdirSync4 } from "node:fs";
3998
+ import { dirname as dirname6 } from "node:path";
4005
3999
  function welcomeShownPath() {
4006
4000
  return dgStatePath("first-run-shown");
4007
4001
  }
@@ -4011,10 +4005,10 @@ function installReceiptPath2() {
4011
4005
  async function maybeShowWelcomePanel(opts) {
4012
4006
  if (SKIP_LIST.has(opts.rawCommand)) return;
4013
4007
  if (!opts.isInteractive) return;
4014
- if (existsSync9(welcomeShownPath())) return;
4015
- if (!existsSync9(installReceiptPath2())) return;
4008
+ if (existsSync8(welcomeShownPath())) return;
4009
+ if (!existsSync8(installReceiptPath2())) return;
4016
4010
  try {
4017
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
4011
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
4018
4012
  const lines = [
4019
4013
  "",
4020
4014
  chalk18.bold(" \u2713 Dependency Guardian is active.") + "",
@@ -4029,8 +4023,8 @@ async function maybeShowWelcomePanel(opts) {
4029
4023
  ];
4030
4024
  process.stderr.write(lines.join("\n"));
4031
4025
  try {
4032
- mkdirSync5(dirname7(welcomeShownPath()), { recursive: true });
4033
- writeFileSync7(welcomeShownPath(), (/* @__PURE__ */ new Date()).toISOString(), { encoding: "utf-8", mode: 420 });
4026
+ mkdirSync4(dirname6(welcomeShownPath()), { recursive: true });
4027
+ writeFileSync6(welcomeShownPath(), (/* @__PURE__ */ new Date()).toISOString(), { encoding: "utf-8", mode: 420 });
4034
4028
  } catch {
4035
4029
  }
4036
4030
  } catch {
@@ -4065,7 +4059,7 @@ __export(upgrade_exports, {
4065
4059
  handleUpgradeCommand: () => handleUpgradeCommand
4066
4060
  });
4067
4061
  async function handleUpgradeCommand(opts) {
4068
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
4062
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
4069
4063
  const webUrl = opts?.webUrl ?? process.env.DG_WEB_URL ?? "https://westbayberry.com";
4070
4064
  const deviceId = getOrCreateDeviceId();
4071
4065
  const url = `${webUrl}/upgrade?device=${encodeURIComponent(deviceId)}`;
@@ -39038,9 +39032,9 @@ var import_react22, import_jsx_runtime, CHAR_POOL, COLOR_POOL, GRAVITY, DRAG, FR
39038
39032
  var init_Confetti = __esm({
39039
39033
  async "src/ui/components/Confetti.tsx"() {
39040
39034
  "use strict";
39041
- import_react22 = __toESM(require_react());
39035
+ import_react22 = __toESM(require_react(), 1);
39042
39036
  await init_build2();
39043
- import_jsx_runtime = __toESM(require_jsx_runtime());
39037
+ import_jsx_runtime = __toESM(require_jsx_runtime(), 1);
39044
39038
  CHAR_POOL = [
39045
39039
  "*",
39046
39040
  "*",
@@ -39155,7 +39149,7 @@ var import_react23;
39155
39149
  var init_useTerminalSize = __esm({
39156
39150
  async "src/ui/hooks/useTerminalSize.ts"() {
39157
39151
  "use strict";
39158
- import_react23 = __toESM(require_react());
39152
+ import_react23 = __toESM(require_react(), 1);
39159
39153
  await init_build2();
39160
39154
  }
39161
39155
  });
@@ -39169,11 +39163,11 @@ var import_react24, import_jsx_runtime2, LoginCelebrateApp;
39169
39163
  var init_LoginCelebrateApp = __esm({
39170
39164
  async "src/ui/apps/LoginCelebrateApp.tsx"() {
39171
39165
  "use strict";
39172
- import_react24 = __toESM(require_react());
39166
+ import_react24 = __toESM(require_react(), 1);
39173
39167
  await init_build2();
39174
39168
  await init_Confetti();
39175
39169
  await init_useTerminalSize();
39176
- import_jsx_runtime2 = __toESM(require_jsx_runtime());
39170
+ import_jsx_runtime2 = __toESM(require_jsx_runtime(), 1);
39177
39171
  LoginCelebrateApp = ({ email, durationMs = 2500 }) => {
39178
39172
  const { exit } = use_app_default();
39179
39173
  const { cols, rows } = useTerminalSize();
@@ -39207,13 +39201,13 @@ var celebrate_exports = {};
39207
39201
  __export(celebrate_exports, {
39208
39202
  celebrateFirstLoginIfNew: () => celebrateFirstLoginIfNew
39209
39203
  });
39210
- import { existsSync as existsSync11, writeFileSync as writeFileSync8, mkdirSync as mkdirSync6 } from "node:fs";
39211
- import { dirname as dirname8 } from "node:path";
39204
+ import { existsSync as existsSync10, writeFileSync as writeFileSync7, mkdirSync as mkdirSync5 } from "node:fs";
39205
+ import { dirname as dirname7 } from "node:path";
39212
39206
  function celebratedMarker() {
39213
39207
  return dgStatePath("login-celebrated");
39214
39208
  }
39215
39209
  function shouldCelebrate() {
39216
- if (existsSync11(celebratedMarker())) return false;
39210
+ if (existsSync10(celebratedMarker())) return false;
39217
39211
  if (process.env.CI === "1" || process.env.CI === "true") return false;
39218
39212
  if (process.env.DG_NO_CELEBRATE === "1") return false;
39219
39213
  if (!process.stderr.isTTY) return false;
@@ -39221,8 +39215,8 @@ function shouldCelebrate() {
39221
39215
  }
39222
39216
  function writeCelebratedMarker() {
39223
39217
  try {
39224
- mkdirSync6(dirname8(celebratedMarker()), { recursive: true });
39225
- writeFileSync8(celebratedMarker(), (/* @__PURE__ */ new Date()).toISOString(), { encoding: "utf-8", mode: 420 });
39218
+ mkdirSync5(dirname7(celebratedMarker()), { recursive: true });
39219
+ writeFileSync7(celebratedMarker(), (/* @__PURE__ */ new Date()).toISOString(), { encoding: "utf-8", mode: 420 });
39226
39220
  } catch {
39227
39221
  }
39228
39222
  }
@@ -39230,7 +39224,7 @@ async function celebrateFirstLoginIfNew(email) {
39230
39224
  if (!shouldCelebrate()) return;
39231
39225
  try {
39232
39226
  const { render: render2 } = await init_build2().then(() => build_exports);
39233
- const React22 = await Promise.resolve().then(() => __toESM(require_react()));
39227
+ const React22 = await Promise.resolve().then(() => __toESM(require_react(), 1));
39234
39228
  const { LoginCelebrateApp: LoginCelebrateApp2 } = await init_LoginCelebrateApp().then(() => LoginCelebrateApp_exports);
39235
39229
  const { enterTui: enterTui2, leaveTui: leaveTui2 } = await Promise.resolve().then(() => (init_terminal_state(), terminal_state_exports));
39236
39230
  enterTui2();
@@ -39284,7 +39278,7 @@ function parseLoginArgs(args) {
39284
39278
  return { kind: "token", value: token, force };
39285
39279
  }
39286
39280
  async function handleLoginWithToken(raw, opts) {
39287
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
39281
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
39288
39282
  const existing = getStoredApiKey();
39289
39283
  if (existing && !opts.force) {
39290
39284
  process.stderr.write(
@@ -39439,7 +39433,7 @@ var import_react25, POLL_INTERVAL_MS, MAX_POLL_ATTEMPTS;
39439
39433
  var init_useLogin = __esm({
39440
39434
  "src/ui/hooks/useLogin.ts"() {
39441
39435
  "use strict";
39442
- import_react25 = __toESM(require_react());
39436
+ import_react25 = __toESM(require_react(), 1);
39443
39437
  init_auth();
39444
39438
  POLL_INTERVAL_MS = 2e3;
39445
39439
  MAX_POLL_ATTEMPTS = 150;
@@ -41125,7 +41119,7 @@ var init_Spinner = __esm({
41125
41119
  "use strict";
41126
41120
  await init_build2();
41127
41121
  await init_build3();
41128
- import_jsx_runtime3 = __toESM(require_jsx_runtime());
41122
+ import_jsx_runtime3 = __toESM(require_jsx_runtime(), 1);
41129
41123
  Spinner2 = ({ label }) => /* @__PURE__ */ (0, import_jsx_runtime3.jsxs)(Box_default, { children: [
41130
41124
  /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(Text, { color: "cyan", children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(build_default, { type: "dots" }) }),
41131
41125
  /* @__PURE__ */ (0, import_jsx_runtime3.jsxs)(Text, { children: [
@@ -41145,11 +41139,11 @@ var import_react27, import_jsx_runtime4, LoginApp;
41145
41139
  var init_LoginApp = __esm({
41146
41140
  async "src/ui/apps/LoginApp.tsx"() {
41147
41141
  "use strict";
41148
- import_react27 = __toESM(require_react());
41142
+ import_react27 = __toESM(require_react(), 1);
41149
41143
  await init_build2();
41150
41144
  init_useLogin();
41151
41145
  await init_Spinner();
41152
- import_jsx_runtime4 = __toESM(require_jsx_runtime());
41146
+ import_jsx_runtime4 = __toESM(require_jsx_runtime(), 1);
41153
41147
  LoginApp = () => {
41154
41148
  const { state, openAndPoll } = useLogin();
41155
41149
  const { exit } = use_app_default();
@@ -41289,7 +41283,8 @@ __export(client_exports, {
41289
41283
  callAnalyzeAPI: () => callAnalyzeAPI,
41290
41284
  callPyPIAnalyzeAPI: () => callPyPIAnalyzeAPI,
41291
41285
  fetchLicenses: () => fetchLicenses,
41292
- fetchPyPILicenses: () => fetchPyPILicenses
41286
+ fetchPyPILicenses: () => fetchPyPILicenses,
41287
+ mergeResponses: () => mergeResponses
41293
41288
  });
41294
41289
  import { randomUUID as randomUUID2 } from "node:crypto";
41295
41290
  function batchConcurrency() {
@@ -41328,7 +41323,11 @@ async function handleFreeCapReached(response) {
41328
41323
  const body = await response.json().catch(() => ({}));
41329
41324
  if (body && body.freeTierCapReached) {
41330
41325
  const b = body;
41331
- throw new FreeCapReachedError(b.scansUsed, b.maxScans);
41326
+ throw new FreeCapReachedError(
41327
+ b.scansUsed,
41328
+ b.maxScans,
41329
+ b.capReason === "prefix_cap" ? "prefix_cap" : "monthly_limit"
41330
+ );
41332
41331
  }
41333
41332
  throw new APIError("Forbidden", 403, JSON.stringify(body));
41334
41333
  }
@@ -41462,17 +41461,24 @@ function mergeResponses(results) {
41462
41461
  const anyBlock = results.some((r) => r.action === "block");
41463
41462
  const anyWarn = results.some((r) => r.action === "warn");
41464
41463
  const anyIncomplete = results.some((r) => r.action === "analysis_incomplete") || allPackages.some((p) => Array.isArray(p.findings) && p.findings.some((f) => f.id === "analysis_incomplete"));
41465
- const action = maxScore >= 70 || anyBlock ? "block" : maxScore >= 60 || anyWarn ? "warn" : anyIncomplete ? "analysis_incomplete" : "pass";
41464
+ const action = anyBlock ? "block" : anyWarn ? "warn" : anyIncomplete ? "analysis_incomplete" : "pass";
41466
41465
  const safeVersions = {};
41467
41466
  for (const r of results) {
41468
41467
  Object.assign(safeVersions, r.safeVersions);
41469
41468
  }
41469
+ const remaining = results.map((r) => r.freeScansRemaining).filter((v) => typeof v === "number");
41470
+ const usage = results.map((r) => r.usage).filter((u) => !!u).reduce(
41471
+ (best, u) => best === void 0 || u.used > best.used ? u : best,
41472
+ void 0
41473
+ );
41470
41474
  return {
41471
41475
  score: maxScore,
41472
41476
  action,
41473
41477
  packages: allPackages,
41474
41478
  safeVersions,
41475
- durationMs: results.reduce((s, r) => s + (r.durationMs || 0), 0)
41479
+ durationMs: results.reduce((s, r) => s + (r.durationMs || 0), 0),
41480
+ ...remaining.length > 0 ? { freeScansRemaining: Math.min(...remaining) } : {},
41481
+ ...usage ? { usage } : {}
41476
41482
  };
41477
41483
  }
41478
41484
  function formatApiErrorMessage(status, rawBody, config) {
@@ -41858,10 +41864,13 @@ var init_client = __esm({
41858
41864
  }
41859
41865
  };
41860
41866
  FreeCapReachedError = class extends Error {
41861
- constructor(scansUsed, maxScans) {
41862
- super("Free trial scans used up. Run `dg login` to create a free account and continue scanning.");
41867
+ constructor(scansUsed, maxScans, reason = "monthly_limit") {
41868
+ super(
41869
+ reason === "prefix_cap" ? "Too many anonymous devices from your network this month. Sign in with `dg login` to keep scanning." : "Free tier monthly package limit reached. Run `dg upgrade` for Pro."
41870
+ );
41863
41871
  this.scansUsed = scansUsed;
41864
41872
  this.maxScans = maxScans;
41873
+ this.reason = reason;
41865
41874
  this.name = "FreeCapReachedError";
41866
41875
  }
41867
41876
  };
@@ -42255,27 +42264,31 @@ var init_parse_package_json = __esm({
42255
42264
  });
42256
42265
 
42257
42266
  // src/lockfile/index.ts
42258
- import { readFileSync as readFileSync9, existsSync as existsSync12, statSync as statSync4 } from "node:fs";
42259
- import { join as join7 } from "node:path";
42267
+ import { readFileSync as readFileSync8, existsSync as existsSync11, statSync as statSync3 } from "node:fs";
42268
+ import { join as join6 } from "node:path";
42260
42269
  function readFileSafe(path2) {
42261
- const size = statSync4(path2).size;
42270
+ const size = statSync3(path2).size;
42262
42271
  if (size > MAX_LOCKFILE_BYTES) {
42263
42272
  throw new Error(`Lockfile too large (${(size / 1024 / 1024).toFixed(0)} MB, max 50 MB): ${path2}`);
42264
42273
  }
42265
- return readFileSync9(path2, "utf-8");
42274
+ return readFileSync8(path2, "utf-8");
42266
42275
  }
42267
42276
  function discoverChanges(cwd2, config) {
42268
42277
  if (config.workspace) {
42269
- cwd2 = join7(cwd2, config.workspace);
42278
+ cwd2 = join6(cwd2, config.workspace);
42270
42279
  }
42271
42280
  const lockfileInfo = findLockfile(cwd2);
42272
- const pythonDepFiles = ["requirements.txt", "Pipfile.lock", "poetry.lock"];
42281
+ const pythonDepFiles = ["requirements.txt", "Pipfile.lock", "poetry.lock", "uv.lock"];
42273
42282
  let pythonPackages = [];
42283
+ const pythonSkipped = [];
42274
42284
  for (const pyFile of pythonDepFiles) {
42275
- if (existsSync12(join7(cwd2, pyFile))) {
42285
+ if (existsSync11(join6(cwd2, pyFile))) {
42276
42286
  const pyPkgs = parsePythonDepFile(cwd2, pyFile);
42277
42287
  for (const p of pyPkgs) {
42278
- if (p.version === "latest") continue;
42288
+ if (p.version === "latest") {
42289
+ pythonSkipped.push(`${p.name} (unpinned \u2014 pin with == to scan)`);
42290
+ continue;
42291
+ }
42279
42292
  pythonPackages.push({
42280
42293
  name: sanitize(p.name),
42281
42294
  version: sanitize(p.version),
@@ -42287,8 +42300,8 @@ function discoverChanges(cwd2, config) {
42287
42300
  }
42288
42301
  }
42289
42302
  if (!lockfileInfo) {
42290
- if (pythonPackages.length > 0) {
42291
- const skipped2 = [];
42303
+ if (pythonPackages.length > 0 || pythonSkipped.length > 0) {
42304
+ const skipped2 = [...pythonSkipped];
42292
42305
  if (pythonPackages.length > config.maxPackages) {
42293
42306
  skipped2.push(...pythonPackages.slice(config.maxPackages).map((p) => `${p.name}@${p.version}`));
42294
42307
  pythonPackages = pythonPackages.slice(0, config.maxPackages);
@@ -42296,14 +42309,14 @@ function discoverChanges(cwd2, config) {
42296
42309
  return { packages: [], pythonPackages, method: "scan-all", skipped: skipped2 };
42297
42310
  }
42298
42311
  throw new Error(
42299
- "No lockfile found (package-lock.json, yarn.lock, pnpm-lock.yaml, requirements.txt, Pipfile.lock, or poetry.lock). Run from your project root or use --base-lockfile."
42312
+ "No lockfile found (package-lock.json, yarn.lock, pnpm-lock.yaml, requirements.txt, Pipfile.lock, poetry.lock, or uv.lock). Run from your project root or use --base-lockfile."
42300
42313
  );
42301
42314
  }
42302
42315
  const headContent = readFileSafe(lockfileInfo.path);
42303
42316
  const headParsed = parseLockfileByType(headContent, lockfileInfo.type);
42304
42317
  const directDeps = getDirectDeps(cwd2);
42305
42318
  if (config.baseLockfile) {
42306
- if (!existsSync12(config.baseLockfile)) {
42319
+ if (!existsSync11(config.baseLockfile)) {
42307
42320
  throw new Error(`Base lockfile not found: ${config.baseLockfile}`);
42308
42321
  }
42309
42322
  const baseContent = readFileSafe(config.baseLockfile);
@@ -42313,7 +42326,7 @@ function discoverChanges(cwd2, config) {
42313
42326
  packages: diff2.changes.map(toPackageInput).filter((p) => p.name !== SELF_PACKAGE),
42314
42327
  pythonPackages,
42315
42328
  method: "base-lockfile",
42316
- skipped: diff2.skipped
42329
+ skipped: [...diff2.skipped, ...pythonSkipped]
42317
42330
  };
42318
42331
  }
42319
42332
  if (!config.scanAll) {
@@ -42325,11 +42338,11 @@ function discoverChanges(cwd2, config) {
42325
42338
  packages: diff2.changes.map(toPackageInput).filter((p) => p.name !== SELF_PACKAGE),
42326
42339
  pythonPackages,
42327
42340
  method: "git-diff",
42328
- skipped: diff2.skipped
42341
+ skipped: [...diff2.skipped, ...pythonSkipped]
42329
42342
  };
42330
42343
  }
42331
- const pkgJsonPath = join7(cwd2, "package.json");
42332
- if (existsSync12(pkgJsonPath)) {
42344
+ const pkgJsonPath = join6(cwd2, "package.json");
42345
+ if (existsSync11(pkgJsonPath)) {
42333
42346
  const headPkgJson = readFileSafe(pkgJsonPath);
42334
42347
  const basePkgJson = getGitBaseFile(cwd2, "package.json");
42335
42348
  if (basePkgJson !== null) {
@@ -42346,7 +42359,7 @@ function discoverChanges(cwd2, config) {
42346
42359
  packages: resolved.map(toPackageInput).filter((p) => p.name !== SELF_PACKAGE),
42347
42360
  pythonPackages,
42348
42361
  method: "fallback",
42349
- skipped: []
42362
+ skipped: [...pythonSkipped]
42350
42363
  };
42351
42364
  }
42352
42365
  }
@@ -42369,7 +42382,7 @@ function discoverChanges(cwd2, config) {
42369
42382
  });
42370
42383
  }
42371
42384
  }
42372
- return { packages, pythonPackages, method: "scan-all", skipped };
42385
+ return { packages, pythonPackages, method: "scan-all", skipped: [...skipped, ...pythonSkipped] };
42373
42386
  }
42374
42387
  function findLockfile(cwd2) {
42375
42388
  const candidates = [
@@ -42379,8 +42392,8 @@ function findLockfile(cwd2) {
42379
42392
  ["pnpm-lock.yaml", "pnpm"]
42380
42393
  ];
42381
42394
  for (const [name, type] of candidates) {
42382
- const p = join7(cwd2, name);
42383
- if (existsSync12(p)) return { path: p, type };
42395
+ const p = join6(cwd2, name);
42396
+ if (existsSync11(p)) return { path: p, type };
42384
42397
  }
42385
42398
  return null;
42386
42399
  }
@@ -42396,7 +42409,7 @@ function parseLockfileByType(content, type) {
42396
42409
  }
42397
42410
  function getDirectDeps(cwd2) {
42398
42411
  try {
42399
- const content = readFileSafe(join7(cwd2, "package.json"));
42412
+ const content = readFileSafe(join6(cwd2, "package.json"));
42400
42413
  const pkg = JSON.parse(content);
42401
42414
  return /* @__PURE__ */ new Set([
42402
42415
  ...Object.keys(pkg.dependencies ?? {}),
@@ -42457,7 +42470,7 @@ function toPackageInput(change) {
42457
42470
  };
42458
42471
  }
42459
42472
  function parsePythonDepFile(projectDir, depFile) {
42460
- const content = readFileSafe(join7(projectDir, depFile));
42473
+ const content = readFileSafe(join6(projectDir, depFile));
42461
42474
  if (depFile === "Pipfile.lock") {
42462
42475
  try {
42463
42476
  const parsed = JSON.parse(content);
@@ -42476,10 +42489,11 @@ function parsePythonDepFile(projectDir, depFile) {
42476
42489
  return [];
42477
42490
  }
42478
42491
  }
42479
- if (depFile === "poetry.lock") {
42492
+ if (depFile === "poetry.lock" || depFile === "uv.lock") {
42480
42493
  const packages2 = [];
42481
42494
  const blocks = content.split(/^\[\[package\]\]/gm);
42482
42495
  for (const block of blocks) {
42496
+ if (/source\s*=\s*\{[^}]*\b(editable|virtual|directory)\b/.test(block)) continue;
42483
42497
  const nameMatch = block.match(/^name\s*=\s*"([^"]+)"/m);
42484
42498
  const versionMatch = block.match(/^version\s*=\s*"([^"]+)"/m);
42485
42499
  if (nameMatch && versionMatch) {
@@ -42594,8 +42608,8 @@ var init_wrapper_shared = __esm({
42594
42608
 
42595
42609
  // src/commands/npm-wrapper.ts
42596
42610
  import { spawn as spawn2 } from "node:child_process";
42597
- import { readFileSync as readFileSync10, existsSync as existsSync13, mkdtempSync, writeFileSync as writeFileSync9, rmSync as rmSync2 } from "node:fs";
42598
- import { join as join8 } from "node:path";
42611
+ import { readFileSync as readFileSync9, existsSync as existsSync12, mkdtempSync, writeFileSync as writeFileSync8, rmSync } from "node:fs";
42612
+ import { join as join7 } from "node:path";
42599
42613
  import { tmpdir } from "node:os";
42600
42614
  function realNpmBinary() {
42601
42615
  const real = resolveRealBinary("npm");
@@ -42781,9 +42795,9 @@ async function resolveTreeNpm(specs) {
42781
42795
  if (safe.length === 0) {
42782
42796
  return { packages: [], ok: false, errorMessage: "all specs were flag-shaped (refused)" };
42783
42797
  }
42784
- const dir = mkdtempSync(join8(tmpdir(), "dg-resolve-"));
42798
+ const dir = mkdtempSync(join7(tmpdir(), "dg-resolve-"));
42785
42799
  try {
42786
- writeFileSync9(join8(dir, "package.json"), '{"name":"_dg_resolve","version":"1.0.0","private":true}');
42800
+ writeFileSync8(join7(dir, "package.json"), '{"name":"_dg_resolve","version":"1.0.0","private":true}');
42787
42801
  const stdout = await new Promise((resolve3) => {
42788
42802
  const child = spawn2(
42789
42803
  realNpmBinary(),
@@ -42842,7 +42856,7 @@ async function resolveTreeNpm(specs) {
42842
42856
  return { packages: [], ok: false, errorMessage: e.message };
42843
42857
  } finally {
42844
42858
  try {
42845
- rmSync2(dir, { recursive: true, force: true });
42859
+ rmSync(dir, { recursive: true, force: true });
42846
42860
  } catch {
42847
42861
  }
42848
42862
  }
@@ -42863,10 +42877,10 @@ function pinTopLevelArgs(rawArgs, userSpecs, tree) {
42863
42877
  });
42864
42878
  }
42865
42879
  function readLockfilePins(cwd2) {
42866
- const lockPath = join8(cwd2, "package-lock.json");
42867
- if (!existsSync13(lockPath)) return null;
42880
+ const lockPath = join7(cwd2, "package-lock.json");
42881
+ if (!existsSync12(lockPath)) return null;
42868
42882
  try {
42869
- const lock = JSON.parse(readFileSync10(lockPath, "utf-8"));
42883
+ const lock = JSON.parse(readFileSync9(lockPath, "utf-8"));
42870
42884
  const pins = /* @__PURE__ */ new Map();
42871
42885
  const root = lock.packages?.[""] ?? {};
42872
42886
  const directDeps = /* @__PURE__ */ new Set([
@@ -42893,10 +42907,10 @@ function readBareInstallPackages(cwd2) {
42893
42907
  return readBareInstallPackagesTyped(cwd2).map((s) => s.spec);
42894
42908
  }
42895
42909
  function readBareInstallPackagesTyped(cwd2) {
42896
- const pkgPath = join8(cwd2, "package.json");
42897
- if (!existsSync13(pkgPath)) return [];
42910
+ const pkgPath = join7(cwd2, "package.json");
42911
+ if (!existsSync12(pkgPath)) return [];
42898
42912
  try {
42899
- const pkg = JSON.parse(readFileSync10(pkgPath, "utf-8"));
42913
+ const pkg = JSON.parse(readFileSync9(pkgPath, "utf-8"));
42900
42914
  const lockPins = readLockfilePins(cwd2) ?? /* @__PURE__ */ new Map();
42901
42915
  const out = [];
42902
42916
  const addOne = (name, range) => {
@@ -42946,7 +42960,7 @@ var init_npm_wrapper = __esm({
42946
42960
 
42947
42961
  // src/commands/pip-wrapper.ts
42948
42962
  import { spawn as spawn3 } from "node:child_process";
42949
- import { existsSync as existsSync14 } from "node:fs";
42963
+ import { existsSync as existsSync13 } from "node:fs";
42950
42964
  function parsePipArgs(args) {
42951
42965
  const { filtered, dgForce, dgForceReason, dgNoScripts } = stripDgFlags(args);
42952
42966
  const command = filtered[0] ?? "";
@@ -43006,7 +43020,7 @@ function parseRequirementsFile(filePath) {
43006
43020
  return parseRequirementsFileInternal(filePath, /* @__PURE__ */ new Set());
43007
43021
  }
43008
43022
  function parseRequirementsFileInternal(filePath, visited) {
43009
- if (!existsSync14(filePath)) return [];
43023
+ if (!existsSync13(filePath)) return [];
43010
43024
  let absPath;
43011
43025
  try {
43012
43026
  absPath = __require("node:path").resolve(filePath);
@@ -43460,6 +43474,24 @@ var init_artifact_integrity = __esm({
43460
43474
  });
43461
43475
 
43462
43476
  // src/ui/format-helpers.ts
43477
+ var format_helpers_exports = {};
43478
+ __export(format_helpers_exports, {
43479
+ USAGE_NEAR_LIMIT_RATIO: () => USAGE_NEAR_LIMIT_RATIO,
43480
+ formatUsage: () => formatUsage,
43481
+ groupPackages: () => groupPackages,
43482
+ pad: () => pad,
43483
+ truncate: () => truncate
43484
+ });
43485
+ function formatUsage(usage) {
43486
+ const used = usage.used.toLocaleString();
43487
+ if (usage.limit === null) {
43488
+ return { text: `${used} packages this month`, nearLimit: false };
43489
+ }
43490
+ return {
43491
+ text: `${used} / ${usage.limit.toLocaleString()} packages this month`,
43492
+ nearLimit: usage.used / usage.limit >= USAGE_NEAR_LIMIT_RATIO
43493
+ };
43494
+ }
43463
43495
  function pad(s, len) {
43464
43496
  return s + " ".repeat(Math.max(0, len - s.length));
43465
43497
  }
@@ -43479,9 +43511,11 @@ function groupPackages(packages, keyBy = "name") {
43479
43511
  key: keyBy === "fingerprint" ? fingerprint : pkgs[0].name
43480
43512
  })).sort((a, b) => b.packages[0].score - a.packages[0].score);
43481
43513
  }
43514
+ var USAGE_NEAR_LIMIT_RATIO;
43482
43515
  var init_format_helpers = __esm({
43483
43516
  "src/ui/format-helpers.ts"() {
43484
43517
  "use strict";
43518
+ USAGE_NEAR_LIMIT_RATIO = 0.8;
43485
43519
  }
43486
43520
  });
43487
43521
 
@@ -43490,8 +43524,8 @@ var FileSavePrompt_exports = {};
43490
43524
  __export(FileSavePrompt_exports, {
43491
43525
  FileSavePrompt: () => FileSavePrompt
43492
43526
  });
43493
- import { existsSync as existsSync15, readdirSync as readdirSync2, writeFileSync as writeFileSync10 } from "node:fs";
43494
- import { dirname as dirname9, join as join9 } from "node:path";
43527
+ import { existsSync as existsSync14, readdirSync as readdirSync2, writeFileSync as writeFileSync9 } from "node:fs";
43528
+ import { dirname as dirname8, join as join8 } from "node:path";
43495
43529
  function listDirectory(dir) {
43496
43530
  try {
43497
43531
  const raw = readdirSync2(dir, { withFileTypes: true });
@@ -43499,7 +43533,7 @@ function listDirectory(dir) {
43499
43533
  if (a.isDirectory !== b.isDirectory) return a.isDirectory ? -1 : 1;
43500
43534
  return a.name.localeCompare(b.name);
43501
43535
  });
43502
- if (dirname9(dir) !== dir) {
43536
+ if (dirname8(dir) !== dir) {
43503
43537
  entries.unshift({ name: "..", isDirectory: true });
43504
43538
  }
43505
43539
  return entries;
@@ -43545,11 +43579,11 @@ var import_react28, import_chalk4, import_jsx_runtime5, VISIBLE_ROWS, FileSavePr
43545
43579
  var init_FileSavePrompt = __esm({
43546
43580
  async "src/ui/components/FileSavePrompt.tsx"() {
43547
43581
  "use strict";
43548
- import_react28 = __toESM(require_react());
43582
+ import_react28 = __toESM(require_react(), 1);
43549
43583
  await init_build2();
43550
- import_chalk4 = __toESM(require_source());
43584
+ import_chalk4 = __toESM(require_source(), 1);
43551
43585
  await init_useTerminalSize();
43552
- import_jsx_runtime5 = __toESM(require_jsx_runtime());
43586
+ import_jsx_runtime5 = __toESM(require_jsx_runtime(), 1);
43553
43587
  VISIBLE_ROWS = 15;
43554
43588
  FileSavePrompt = ({
43555
43589
  defaultName,
@@ -43594,13 +43628,13 @@ var init_FileSavePrompt = __esm({
43594
43628
  if (state.focus === "filename") {
43595
43629
  if (key.return) {
43596
43630
  const fullName = ensureJsonExtension(state.filename);
43597
- const fullPath = join9(state.directory, fullName);
43598
- if (!state.confirmOverwrite && existsSync15(fullPath)) {
43631
+ const fullPath = join8(state.directory, fullName);
43632
+ if (!state.confirmOverwrite && existsSync14(fullPath)) {
43599
43633
  dispatch({ type: "CONFIRM_OVERWRITE" });
43600
43634
  return;
43601
43635
  }
43602
43636
  try {
43603
- writeFileSync10(fullPath, json + "\n");
43637
+ writeFileSync9(fullPath, json + "\n");
43604
43638
  } catch (err) {
43605
43639
  const msg = err instanceof Error ? err.message : String(err);
43606
43640
  dispatch({ type: "SET_ERROR", error: `Write failed: ${msg}` });
@@ -43824,7 +43858,7 @@ async function countPythonPackages(depPath, depFile) {
43824
43858
  const parsed = JSON.parse(content);
43825
43859
  return Object.keys(parsed.default || {}).length + Object.keys(parsed.develop || {}).length;
43826
43860
  }
43827
- if (depFile === "poetry.lock") {
43861
+ if (depFile === "poetry.lock" || depFile === "uv.lock") {
43828
43862
  return (content.match(/^\[\[package\]\]/gm) || []).length;
43829
43863
  }
43830
43864
  return content.split("\n").filter(
@@ -43843,7 +43877,7 @@ var init_count_packages = __esm({
43843
43877
  "src/discover/count-packages.ts"() {
43844
43878
  "use strict";
43845
43879
  NPM_LOCKFILES = ["package-lock.json", "yarn.lock", "pnpm-lock.yaml", "npm-shrinkwrap.json"];
43846
- PYTHON_DEPFILES = ["requirements.txt", "Pipfile.lock", "poetry.lock"];
43880
+ PYTHON_DEPFILES = ["requirements.txt", "Pipfile.lock", "poetry.lock", "uv.lock"];
43847
43881
  }
43848
43882
  });
43849
43883
 
@@ -43854,7 +43888,7 @@ __export(walker_exports, {
43854
43888
  discoverProjectsAsync: () => discoverProjectsAsync
43855
43889
  });
43856
43890
  import { readdir, lstat } from "node:fs/promises";
43857
- import { join as join10, relative } from "node:path";
43891
+ import { join as join9, relative } from "node:path";
43858
43892
  async function discoverProjectsAsync(root, opts = {}) {
43859
43893
  const queue = [{ dir: root, depth: 0 }];
43860
43894
  const projects = [];
@@ -43907,7 +43941,7 @@ async function scanDir(dir, depth, _root) {
43907
43941
  for (const lockfile of NPM_LOCKFILES) {
43908
43942
  const e = byName.get(lockfile);
43909
43943
  if (e && e.isFile() && !e.isSymbolicLink()) {
43910
- const lockPath = join10(dir, lockfile);
43944
+ const lockPath = join9(dir, lockfile);
43911
43945
  if (await isSafeRegularFile(lockPath)) {
43912
43946
  lockfileHits.push({ dir, lockPath, depFile: lockfile, isNpm: true });
43913
43947
  }
@@ -43917,7 +43951,7 @@ async function scanDir(dir, depth, _root) {
43917
43951
  for (const depFile of PYTHON_DEPFILES) {
43918
43952
  const e = byName.get(depFile);
43919
43953
  if (e && e.isFile() && !e.isSymbolicLink()) {
43920
- const lockPath = join10(dir, depFile);
43954
+ const lockPath = join9(dir, depFile);
43921
43955
  if (await isSafeRegularFile(lockPath)) {
43922
43956
  lockfileHits.push({ dir, lockPath, depFile, isNpm: false });
43923
43957
  }
@@ -43928,7 +43962,7 @@ async function scanDir(dir, depth, _root) {
43928
43962
  for (const e of entries) {
43929
43963
  if (!e.isDirectory() || e.isSymbolicLink()) continue;
43930
43964
  if (SKIP_DIRS.has(e.name) || e.name.startsWith(".")) continue;
43931
- subdirs.push({ dir: join10(dir, e.name), depth: depth + 1 });
43965
+ subdirs.push({ dir: join9(dir, e.name), depth: depth + 1 });
43932
43966
  }
43933
43967
  }
43934
43968
  return { subdirs, lockfileHits };
@@ -44020,8 +44054,10 @@ async function scanProjectAtPath(cwd2, config, onProgress) {
44020
44054
  };
44021
44055
  }
44022
44056
  const maxScore = allPackages.length > 0 ? Math.max(0, ...allPackages.map((p) => p.score)) : 0;
44057
+ const anyBlock = responses.some((r) => r.action === "block") || allPackages.some((p) => p.action === "block");
44058
+ const anyWarn = responses.some((r) => r.action === "warn") || allPackages.some((p) => p.action === "warn");
44023
44059
  const anyIncomplete = responses.some((r) => r.action === "analysis_incomplete") || allPackages.some((p) => Array.isArray(p.findings) && p.findings.some((f) => f?.id === "analysis_incomplete"));
44024
- const action = maxScore >= 70 ? "block" : maxScore >= 60 ? "warn" : anyIncomplete ? "analysis_incomplete" : "pass";
44060
+ const action = anyBlock ? "block" : anyWarn ? "warn" : anyIncomplete ? "analysis_incomplete" : "pass";
44025
44061
  const safeVersions = {};
44026
44062
  for (const r of responses) Object.assign(safeVersions, r.safeVersions);
44027
44063
  const totalDuration = elapsedMs();
@@ -44147,8 +44183,10 @@ async function scanConsolidated(projectPaths, config, onProgress) {
44147
44183
  };
44148
44184
  }
44149
44185
  const maxScore = allPackages.length > 0 ? Math.max(0, ...allPackages.map((p) => p.score)) : 0;
44186
+ const anyBlock = responses.some((r) => r.action === "block") || allPackages.some((p) => p.action === "block");
44187
+ const anyWarn = responses.some((r) => r.action === "warn") || allPackages.some((p) => p.action === "warn");
44150
44188
  const anyIncomplete = responses.some((r) => r.action === "analysis_incomplete") || allPackages.some((p) => Array.isArray(p.findings) && p.findings.some((f) => f?.id === "analysis_incomplete"));
44151
- const action = maxScore >= 70 ? "block" : maxScore >= 60 ? "warn" : anyIncomplete ? "analysis_incomplete" : "pass";
44189
+ const action = anyBlock ? "block" : anyWarn ? "warn" : anyIncomplete ? "analysis_incomplete" : "pass";
44152
44190
  const safeVersions = {};
44153
44191
  for (const r of responses) Object.assign(safeVersions, r.safeVersions);
44154
44192
  const totalDuration = elapsedMs();
@@ -44215,8 +44253,8 @@ __export(allowlist_exports, {
44215
44253
  loadAllowlist: () => loadAllowlist,
44216
44254
  validateAllowlist: () => validateAllowlist
44217
44255
  });
44218
- import { existsSync as existsSync16, readFileSync as readFileSync11 } from "node:fs";
44219
- import { join as join11, dirname as dirname10 } from "node:path";
44256
+ import { existsSync as existsSync15, readFileSync as readFileSync10 } from "node:fs";
44257
+ import { join as join10, dirname as dirname9 } from "node:path";
44220
44258
  function isExpired(expires) {
44221
44259
  if (!expires) return false;
44222
44260
  const date = new Date(expires);
@@ -44226,9 +44264,9 @@ function isExpired(expires) {
44226
44264
  function findAllowlistFile(startDir) {
44227
44265
  let dir = startDir;
44228
44266
  for (let i = 0; i < 32; i++) {
44229
- const candidate = join11(dir, ALLOWLIST_FILENAME);
44230
- if (existsSync16(candidate)) return candidate;
44231
- const parent = dirname10(dir);
44267
+ const candidate = join10(dir, ALLOWLIST_FILENAME);
44268
+ if (existsSync15(candidate)) return candidate;
44269
+ const parent = dirname9(dir);
44232
44270
  if (parent === dir) return null;
44233
44271
  dir = parent;
44234
44272
  }
@@ -44337,7 +44375,7 @@ function loadAllowlist(cwd2) {
44337
44375
  if (!path2) return null;
44338
44376
  let raw;
44339
44377
  try {
44340
- raw = JSON.parse(readFileSync11(path2, "utf-8"));
44378
+ raw = JSON.parse(readFileSync10(path2, "utf-8"));
44341
44379
  } catch (e) {
44342
44380
  process.stderr.write(
44343
44381
  `dg: .dg-allowlist.json at ${path2} is not valid JSON (${e.message}). Ignoring.
@@ -44368,30 +44406,23 @@ function packageMatches(entry, pkg, apiKind) {
44368
44406
  if (entry.version && entry.version !== pkg.version) return false;
44369
44407
  return true;
44370
44408
  }
44371
- function derivePackageActionFromFindings(pkg) {
44372
- const findings = pkg.findings ?? [];
44373
- if (findings.length === 0) return "pass";
44374
- const maxSev = findings.reduce((m, f) => Math.max(m, f.severity ?? 0), 0);
44375
- if (maxSev >= 4) return "block";
44376
- if (maxSev >= 2) return "warn";
44377
- return "pass";
44378
- }
44379
44409
  function derivePackageAction(pkg) {
44380
- if (pkg.action === "block" || pkg.action === "warn" || pkg.action === "pass") return pkg.action;
44381
- if (pkg.score >= 70) return "block";
44382
- if (pkg.score >= 60) return "warn";
44410
+ if (pkg.action === "block" || pkg.action === "warn") return pkg.action;
44383
44411
  return "pass";
44384
44412
  }
44385
44413
  function overallAction(packages) {
44386
44414
  let hasBlock = false;
44387
44415
  let hasWarn = false;
44416
+ let hasIncomplete = false;
44388
44417
  for (const p of packages) {
44389
- const a = derivePackageActionFromFindings(p);
44418
+ const a = derivePackageAction(p);
44390
44419
  if (a === "block") hasBlock = true;
44391
44420
  else if (a === "warn") hasWarn = true;
44421
+ if (p.action === "analysis_incomplete") hasIncomplete = true;
44392
44422
  }
44393
44423
  if (hasBlock) return "block";
44394
44424
  if (hasWarn) return "warn";
44425
+ if (hasIncomplete) return "analysis_incomplete";
44395
44426
  return "pass";
44396
44427
  }
44397
44428
  function applyAllowlist(allowlist, result, apiKind) {
@@ -44423,6 +44454,7 @@ function applyAllowlist(allowlist, result, apiKind) {
44423
44454
  let suppressedCount = 0;
44424
44455
  const filteredPackages = result.packages.map((pkg) => {
44425
44456
  const matchingEntry = activePackages.find((e) => packageMatches(e, pkg, apiKind));
44457
+ const originalCount = (pkg.findings ?? []).length;
44426
44458
  let findings = pkg.findings ?? [];
44427
44459
  if (matchingEntry) {
44428
44460
  if (!matchingEntry.rules) {
@@ -44437,8 +44469,9 @@ function applyAllowlist(allowlist, result, apiKind) {
44437
44469
  const globallySupressed = findings.filter((f) => activeGlobalRules[findingRuleId(f)] !== void 0);
44438
44470
  suppressedCount += globallySupressed.length;
44439
44471
  findings = findings.filter((f) => activeGlobalRules[findingRuleId(f)] === void 0);
44440
- const newPkg = { ...pkg, findings };
44441
- return newPkg;
44472
+ const fullyAllowlisted = originalCount > 0 && findings.length === 0;
44473
+ const action = fullyAllowlisted ? "pass" : pkg.action ?? "pass";
44474
+ return { ...pkg, findings, action };
44442
44475
  });
44443
44476
  const newAction = overallAction(filteredPackages);
44444
44477
  return {
@@ -44622,8 +44655,8 @@ __export(audit_dispatcher_exports, {
44622
44655
  recordBypassLocally: () => recordBypassLocally,
44623
44656
  shouldFireAudit: () => shouldFireAudit
44624
44657
  });
44625
- import { appendFileSync as appendFileSync3, mkdirSync as mkdirSync7, existsSync as existsSync17 } from "node:fs";
44626
- import { dirname as dirname11 } from "node:path";
44658
+ import { appendFileSync as appendFileSync3, mkdirSync as mkdirSync6, existsSync as existsSync16 } from "node:fs";
44659
+ import { dirname as dirname10 } from "node:path";
44627
44660
  function _setPolicyFetcherForTests(fn) {
44628
44661
  _policyOverride = fn;
44629
44662
  }
@@ -44672,8 +44705,8 @@ function bypassLogPath2() {
44672
44705
  function recordBypassLocally(record) {
44673
44706
  try {
44674
44707
  const path2 = bypassLogPath2();
44675
- const dir = dirname11(path2);
44676
- if (!existsSync17(dir)) mkdirSync7(dir, { recursive: true, mode: 448 });
44708
+ const dir = dirname10(path2);
44709
+ if (!existsSync16(dir)) mkdirSync6(dir, { recursive: true, mode: 448 });
44677
44710
  const full = {
44678
44711
  ts: (/* @__PURE__ */ new Date()).toISOString(),
44679
44712
  cwd: record.cwd ?? process.cwd(),
@@ -44733,10 +44766,11 @@ __export(static_output_exports, {
44733
44766
  runStatic: () => runStatic,
44734
44767
  runStaticLogin: () => runStaticLogin,
44735
44768
  runStaticNpm: () => runStaticNpm,
44736
- runStaticPip: () => runStaticPip
44769
+ runStaticPip: () => runStaticPip,
44770
+ scanExitCode: () => scanExitCode
44737
44771
  });
44738
- import { writeFileSync as writeFileSync11, readFileSync as readFileSync12, existsSync as existsSync18, mkdirSync as mkdirSync8, lstatSync as lstatSync5 } from "node:fs";
44739
- import { resolve as resolvePath, dirname as dirname12 } from "node:path";
44772
+ import { writeFileSync as writeFileSync10, readFileSync as readFileSync11, existsSync as existsSync17, mkdirSync as mkdirSync7, lstatSync as lstatSync5 } from "node:fs";
44773
+ import { resolve as resolvePath, dirname as dirname11 } from "node:path";
44740
44774
  function note(config, text) {
44741
44775
  if (config.quiet) return;
44742
44776
  process.stderr.write(text);
@@ -44756,12 +44790,12 @@ function wrapperPackagesFromResult(result, topLevelNames) {
44756
44790
  }
44757
44791
  function loadPackageLockJson(cwd2 = process.cwd()) {
44758
44792
  const path2 = resolvePath(cwd2, "package-lock.json");
44759
- if (!existsSync18(path2)) return null;
44793
+ if (!existsSync17(path2)) return null;
44760
44794
  try {
44761
44795
  const st = lstatSync5(path2);
44762
44796
  if (!st.isFile()) return null;
44763
44797
  if (st.size > MAX_PACKAGE_LOCK_BYTES) return null;
44764
- return JSON.parse(readFileSync12(path2, "utf8"));
44798
+ return JSON.parse(readFileSync11(path2, "utf8"));
44765
44799
  } catch {
44766
44800
  return null;
44767
44801
  }
@@ -44769,7 +44803,7 @@ function loadPackageLockJson(cwd2 = process.cwd()) {
44769
44803
  function writeJsonFile(filepath, json) {
44770
44804
  const resolved = resolvePath(filepath);
44771
44805
  try {
44772
- writeFileSync11(resolved, json + "\n");
44806
+ writeFileSync10(resolved, json + "\n");
44773
44807
  process.stderr.write(import_chalk5.default.green(` \u2713 Saved to ${resolved}
44774
44808
 
44775
44809
  `));
@@ -44806,7 +44840,7 @@ async function handleJsonOutput(result, config) {
44806
44840
  const localDate = (/* @__PURE__ */ new Date()).toLocaleDateString("sv-SE");
44807
44841
  const defaultName = `dg-scan-${localDate}`;
44808
44842
  const { render: render2 } = await init_build2().then(() => build_exports);
44809
- const React22 = await Promise.resolve().then(() => __toESM(require_react()));
44843
+ const React22 = await Promise.resolve().then(() => __toESM(require_react(), 1));
44810
44844
  const { FileSavePrompt: FileSavePrompt2 } = await init_FileSavePrompt().then(() => FileSavePrompt_exports);
44811
44845
  await new Promise((resolve3) => {
44812
44846
  const inkInstance = render2(
@@ -44854,11 +44888,11 @@ function printTrialBanner(result, config) {
44854
44888
  if (process.env.CI === "1" || process.env.CI === "true") return;
44855
44889
  try {
44856
44890
  const stampPath = dgStatePath("trial-banner");
44857
- const lastMs = existsSync18(stampPath) ? Number(readFileSync12(stampPath, "utf-8").trim()) || 0 : 0;
44891
+ const lastMs = existsSync17(stampPath) ? Number(readFileSync11(stampPath, "utf-8").trim()) || 0 : 0;
44858
44892
  const now = Date.now();
44859
44893
  if (now - lastMs < NUDGE_INTERVAL_MS) return;
44860
- mkdirSync8(dirname12(stampPath), { recursive: true, mode: 448 });
44861
- writeFileSync11(stampPath, String(now) + "\n", { mode: 384 });
44894
+ mkdirSync7(dirname11(stampPath), { recursive: true, mode: 448 });
44895
+ writeFileSync10(stampPath, String(now) + "\n", { mode: 384 });
44862
44896
  } catch {
44863
44897
  return;
44864
44898
  }
@@ -44874,7 +44908,7 @@ function handleFreeCapReached2(error, jsonMode = false) {
44874
44908
  hasKey = !!getStoredApiKey();
44875
44909
  } catch {
44876
44910
  }
44877
- const message = hasKey ? "Your API key may be invalid or expired. Run `dg logout` then `dg login` to re-authenticate." : `Free tier monthly cap reached (${error.scansUsed}/${error.maxScans}). Run \`dg upgrade\` for Pro (5000/mo) or wait until next month.`;
44911
+ const message = hasKey ? "Your API key may be invalid or expired. Run `dg logout` then `dg login` to re-authenticate." : `Free tier monthly package limit reached (${error.scansUsed.toLocaleString()}/${error.maxScans.toLocaleString()}). Run \`dg upgrade\` for Pro or wait until next month.`;
44878
44912
  if (jsonMode) {
44879
44913
  process.stdout.write(JSON.stringify({
44880
44914
  error: true,
@@ -44892,8 +44926,8 @@ function handleFreeCapReached2(error, jsonMode = false) {
44892
44926
  } else {
44893
44927
  process.stderr.write(
44894
44928
  import_chalk5.default.yellow(`
44895
- Free tier monthly cap reached (${error.scansUsed}/${error.maxScans}).
44896
- `) + import_chalk5.default.white(` Run \`dg upgrade\` for Pro (5000/mo) or wait until next month.
44929
+ Free tier monthly package limit reached (${error.scansUsed.toLocaleString()}/${error.maxScans.toLocaleString()}).
44930
+ `) + import_chalk5.default.white(` Run \`dg upgrade\` for Pro or wait until next month.
44897
44931
 
44898
44932
  `)
44899
44933
  );
@@ -44915,15 +44949,13 @@ function actionBadge(pkg) {
44915
44949
  if (a === "warn") return { label: "Warn", color: import_chalk5.default.yellow };
44916
44950
  if (a === "pass") return { label: "Pass", color: import_chalk5.default.green };
44917
44951
  if (a === "analysis_incomplete") return { label: "Unknown", color: import_chalk5.default.cyan };
44918
- if (pkg.score >= 70) return { label: "Block", color: import_chalk5.default.red };
44919
- if (pkg.score >= 60) return { label: "Warn", color: import_chalk5.default.yellow };
44920
44952
  return { label: "Pass", color: import_chalk5.default.green };
44921
44953
  }
44922
44954
  function isBlocked(p) {
44923
- return p.action === "block" || p.action === void 0 && p.score >= 70;
44955
+ return p.action === "block";
44924
44956
  }
44925
44957
  function isWarned(p) {
44926
- return p.action === "warn" || p.action === void 0 && p.score >= 60 && p.score < 70;
44958
+ return p.action === "warn";
44927
44959
  }
44928
44960
  function renderResultClean(result, _config) {
44929
44961
  const lines = [];
@@ -45045,6 +45077,12 @@ function renderResultDetails(result, _config) {
45045
45077
  function renderResultStatic(result, config) {
45046
45078
  return config.details ? renderResultDetails(result, config) : renderResultClean(result, config);
45047
45079
  }
45080
+ function scanExitCode(action, mode) {
45081
+ if (action === "block" && mode === "block") return 2;
45082
+ if (action === "block" || action === "warn") return 1;
45083
+ if (action === "analysis_incomplete") return 4;
45084
+ return 0;
45085
+ }
45048
45086
  async function runStatic(config) {
45049
45087
  const dbg = (msg) => {
45050
45088
  if (config.debug)
@@ -45107,7 +45145,7 @@ async function runStatic(config) {
45107
45145
  `
45108
45146
  )
45109
45147
  );
45110
- if (discovery.skipped.length > 0 && config.maxPackages < 1e4) {
45148
+ if (discovery.skipped.length > 0) {
45111
45149
  note(
45112
45150
  config,
45113
45151
  import_chalk5.default.dim(
@@ -45183,34 +45221,31 @@ async function runStatic(config) {
45183
45221
  const sarif = emitSarif2(result, {});
45184
45222
  const outputPath = config.outputFile;
45185
45223
  if (outputPath) {
45186
- const { writeFileSync: writeFileSync16 } = await import("node:fs");
45187
- writeFileSync16(outputPath, sarif);
45224
+ const { writeFileSync: writeFileSync15 } = await import("node:fs");
45225
+ writeFileSync15(outputPath, sarif);
45188
45226
  process.stderr.write(import_chalk5.default.green(` \u2713 Wrote SARIF to ${outputPath}
45189
45227
  `));
45190
45228
  } else {
45191
45229
  process.stdout.write(sarif + "\n");
45192
45230
  }
45193
45231
  printTrialBanner(result, config);
45194
- if (result.action === "block" && config.mode === "block") process.exit(2);
45195
- else if (result.action === "block" || result.action === "warn") process.exit(1);
45196
- process.exit(0);
45232
+ process.exit(scanExitCode(result.action, config.mode));
45197
45233
  }
45198
45234
  const jsonHandled = await handleJsonOutput(result, config);
45199
45235
  if (jsonHandled) {
45200
45236
  printTrialBanner(result, config);
45201
- if (result.action === "block" && config.mode === "block") process.exit(2);
45202
- else if (result.action === "block" || result.action === "warn") process.exit(1);
45203
- process.exit(0);
45237
+ process.exit(scanExitCode(result.action, config.mode));
45204
45238
  }
45205
45239
  const output = renderResultStatic(result, config);
45206
45240
  process.stdout.write(output + "\n");
45207
- printTrialBanner(result, config);
45208
- if (result.action === "block" && config.mode === "block") {
45209
- process.exit(2);
45210
- } else if (result.action === "block" || result.action === "warn") {
45211
- process.exit(1);
45241
+ if (result.usage) {
45242
+ const u = formatUsage(result.usage);
45243
+ process.stdout.write(
45244
+ (u.nearLimit ? import_chalk5.default.yellow(` ${u.text} \u2191 dg upgrade for Pro`) : import_chalk5.default.dim(` ${u.text}`)) + "\n"
45245
+ );
45212
45246
  }
45213
- process.exit(0);
45247
+ printTrialBanner(result, config);
45248
+ process.exit(scanExitCode(result.action, config.mode));
45214
45249
  }
45215
45250
  function mergeProjectConfig(config, _argv) {
45216
45251
  return config;
@@ -45927,7 +45962,7 @@ var import_chalk5, MAX_PACKAGE_LOCK_BYTES, NUDGE_INTERVAL_MS;
45927
45962
  var init_static_output = __esm({
45928
45963
  "src/formatters/static-output.ts"() {
45929
45964
  "use strict";
45930
- import_chalk5 = __toESM(require_source());
45965
+ import_chalk5 = __toESM(require_source(), 1);
45931
45966
  init_paths();
45932
45967
  init_client();
45933
45968
  init_auth();
@@ -45948,13 +45983,13 @@ __export(status_exports, {
45948
45983
  collectStatusSnapshot: () => collectStatusSnapshot,
45949
45984
  handleStatusCommand: () => handleStatusCommand
45950
45985
  });
45951
- import { existsSync as existsSync19, readFileSync as readFileSync13 } from "node:fs";
45952
- import { join as join12 } from "node:path";
45986
+ import { existsSync as existsSync18, readFileSync as readFileSync12 } from "node:fs";
45987
+ import { join as join11 } from "node:path";
45953
45988
  import { homedir as homedir6 } from "node:os";
45954
45989
  function readPythonReceipt() {
45955
45990
  try {
45956
- const { readFileSync: readFileSync18 } = __require("node:fs");
45957
- const receipt = JSON.parse(readFileSync18(dgStatePath("python-hook-receipt.json"), "utf-8"));
45991
+ const { readFileSync: readFileSync17 } = __require("node:fs");
45992
+ const receipt = JSON.parse(readFileSync17(dgStatePath("python-hook-receipt.json"), "utf-8"));
45958
45993
  const rows = receipt?.results ?? [];
45959
45994
  return rows.map((r) => ({ pythonVersion: r.pythonVersion, status: r.status, reason: r.reason }));
45960
45995
  } catch {
@@ -45997,12 +46032,12 @@ async function collectStatusSnapshot(cliVersion2) {
45997
46032
  authPart.reachable = false;
45998
46033
  }
45999
46034
  }
46000
- const shimDir2 = join12(homedir6(), ".dg", "shims");
46035
+ const shimDir2 = join11(homedir6(), ".dg", "shims");
46001
46036
  const shimRows = ECOSYSTEMS.map((eco) => {
46002
46037
  const filename = process.platform === "win32" ? `${eco}.cmd` : eco;
46003
46038
  return {
46004
46039
  ecosystem: eco,
46005
- shimPresent: existsSync19(join12(shimDir2, filename))
46040
+ shimPresent: existsSync18(join11(shimDir2, filename))
46006
46041
  };
46007
46042
  });
46008
46043
  const engineResolvable = isEngineResolvable();
@@ -46010,11 +46045,11 @@ async function collectStatusSnapshot(cliVersion2) {
46010
46045
  const cwd2 = process.cwd();
46011
46046
  const hookPart = { installed: false };
46012
46047
  try {
46013
- const { existsSync: ex, readFileSync: readFileSync18 } = await import("node:fs");
46014
- const candidates = [join12(cwd2, ".husky", "pre-commit"), join12(cwd2, ".git", "hooks", "pre-commit")];
46048
+ const { existsSync: ex, readFileSync: readFileSync17 } = await import("node:fs");
46049
+ const candidates = [join11(cwd2, ".husky", "pre-commit"), join11(cwd2, ".git", "hooks", "pre-commit")];
46015
46050
  for (const p of candidates) {
46016
46051
  if (ex(p)) {
46017
- const content = readFileSync18(p, "utf-8");
46052
+ const content = readFileSync17(p, "utf-8");
46018
46053
  if (content.includes("dependency-guardian")) {
46019
46054
  hookPart.installed = true;
46020
46055
  break;
@@ -46045,8 +46080,8 @@ async function collectStatusSnapshot(cliVersion2) {
46045
46080
  }
46046
46081
  function isEngineResolvable() {
46047
46082
  try {
46048
- const recorded = readFileSync13(join12(homedir6(), ".dg", "state", "dg-entry"), "utf-8").trim();
46049
- if (recorded && existsSync19(recorded)) return true;
46083
+ const recorded = readFileSync12(join11(homedir6(), ".dg", "state", "dg-entry"), "utf-8").trim();
46084
+ if (recorded && existsSync18(recorded)) return true;
46050
46085
  } catch {
46051
46086
  }
46052
46087
  try {
@@ -46056,7 +46091,7 @@ function isEngineResolvable() {
46056
46091
  }
46057
46092
  }
46058
46093
  async function renderStatusHuman(s) {
46059
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
46094
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
46060
46095
  const out = [];
46061
46096
  out.push("\n");
46062
46097
  out.push(` ${chalk18.bold("Dependency Guardian")} ${chalk18.dim(s.update.current)}
@@ -46074,7 +46109,7 @@ async function renderStatusHuman(s) {
46074
46109
  authGlyph = chalk18.green("\u2713");
46075
46110
  authLine = "signed in";
46076
46111
  } else {
46077
- const usage = s.auth.scansLimit === null ? "unlimited scans" : `${s.auth.scansUsed ?? 0}/${s.auth.scansLimit} scans this month`;
46112
+ const usage = s.auth.scansLimit === null ? "unlimited packages" : `${(s.auth.scansUsed ?? 0).toLocaleString()}/${s.auth.scansLimit.toLocaleString()} packages this month`;
46078
46113
  authGlyph = chalk18.green("\u2713");
46079
46114
  authLine = `${s.auth.tier ?? "free"} tier \xB7 ${usage}`;
46080
46115
  }
@@ -46198,7 +46233,7 @@ var import_chalk6, USAGE2;
46198
46233
  var init_config2 = __esm({
46199
46234
  "src/commands/config.ts"() {
46200
46235
  "use strict";
46201
- import_chalk6 = __toESM(require_source());
46236
+ import_chalk6 = __toESM(require_source(), 1);
46202
46237
  init_auth();
46203
46238
  USAGE2 = `
46204
46239
  dg config \u2014 view or set persisted CLI preferences
@@ -46304,7 +46339,7 @@ var import_chalk7, SINK_RANKS, CSV_FORMULA_PREFIXES;
46304
46339
  var init_license_export = __esm({
46305
46340
  "src/formatters/license-export.ts"() {
46306
46341
  "use strict";
46307
- import_chalk7 = __toESM(require_source());
46342
+ import_chalk7 = __toESM(require_source(), 1);
46308
46343
  SINK_RANKS = { "no-license": 2, unknown: 1 };
46309
46344
  CSV_FORMULA_PREFIXES = /* @__PURE__ */ new Set(["=", "+", "-", "@", " ", "\r"]);
46310
46345
  }
@@ -46367,9 +46402,9 @@ var init_ScoreHeader = __esm({
46367
46402
  async "src/ui/components/ScoreHeader.tsx"() {
46368
46403
  "use strict";
46369
46404
  await init_build2();
46370
- import_chalk8 = __toESM(require_source());
46405
+ import_chalk8 = __toESM(require_source(), 1);
46371
46406
  await init_useTerminalSize();
46372
- import_jsx_runtime6 = __toESM(require_jsx_runtime());
46407
+ import_jsx_runtime6 = __toESM(require_jsx_runtime(), 1);
46373
46408
  LOGO_DATA = (() => {
46374
46409
  const W = 22, H = 28;
46375
46410
  const grid = Array.from({ length: H }, () => Array(W).fill(0));
@@ -46417,7 +46452,8 @@ var init_ScoreHeader = __esm({
46417
46452
  flagged,
46418
46453
  clean,
46419
46454
  userStatus,
46420
- scanUsage
46455
+ scanUsage,
46456
+ usageNearLimit
46421
46457
  }) => {
46422
46458
  const logo = renderLogo(action);
46423
46459
  const { cols } = useTerminalSize();
@@ -46457,7 +46493,10 @@ var init_ScoreHeader = __esm({
46457
46493
  import_chalk8.default.green("all clean")
46458
46494
  ] })
46459
46495
  ] }),
46460
- scanUsage && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(Text, { dimColor: true, children: scanUsage })
46496
+ scanUsage && (usageNearLimit ? /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(Text, { color: "yellow", children: [
46497
+ scanUsage,
46498
+ " \u2191 dg upgrade for Pro"
46499
+ ] }) : /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(Text, { dimColor: true, children: scanUsage }))
46461
46500
  ] })
46462
46501
  ] }),
46463
46502
  showLogo && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(Box_default, { flexDirection: "column", marginLeft: 2, children: logo.map((line, i) => /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(Text, { children: line }, i)) })
@@ -46510,7 +46549,7 @@ var import_react29;
46510
46549
  var init_useExpandAnimation = __esm({
46511
46550
  "src/ui/hooks/useExpandAnimation.ts"() {
46512
46551
  "use strict";
46513
- import_react29 = __toESM(require_react());
46552
+ import_react29 = __toESM(require_react(), 1);
46514
46553
  }
46515
46554
  });
46516
46555
 
@@ -46519,16 +46558,15 @@ var InteractiveResultsView_exports = {};
46519
46558
  __export(InteractiveResultsView_exports, {
46520
46559
  InteractiveResultsView: () => InteractiveResultsView
46521
46560
  });
46522
- import { writeFileSync as writeFileSync12 } from "node:fs";
46561
+ import { writeFileSync as writeFileSync11 } from "node:fs";
46523
46562
  import { resolve as resolvePath2 } from "node:path";
46524
46563
  function groupPackages2(packages) {
46525
46564
  return groupPackages(packages, "fingerprint");
46526
46565
  }
46527
- function actionBadge2(score) {
46528
- if (score >= 70)
46529
- return { label: "Block", color: import_chalk9.default.red };
46530
- if (score >= 60)
46531
- return { label: "Warn", color: import_chalk9.default.yellow };
46566
+ function actionBadge2(action) {
46567
+ if (action === "block") return { label: "Block", color: import_chalk9.default.red };
46568
+ if (action === "warn") return { label: "Warn", color: import_chalk9.default.yellow };
46569
+ if (action === "analysis_incomplete") return { label: "Unknown", color: import_chalk9.default.cyan };
46532
46570
  return { label: "Pass", color: import_chalk9.default.green };
46533
46571
  }
46534
46572
  function findingsSummaryHeight(group) {
@@ -46683,16 +46721,16 @@ var import_react30, import_chalk9, import_jsx_runtime7, SEVERITY_LABELS, SEVERIT
46683
46721
  var init_InteractiveResultsView = __esm({
46684
46722
  async "src/ui/components/InteractiveResultsView.tsx"() {
46685
46723
  "use strict";
46686
- import_react30 = __toESM(require_react());
46724
+ import_react30 = __toESM(require_react(), 1);
46687
46725
  await init_build2();
46688
- import_chalk9 = __toESM(require_source());
46726
+ import_chalk9 = __toESM(require_source(), 1);
46689
46727
  init_auth();
46690
46728
  await init_ScoreHeader();
46691
46729
  init_useExpandAnimation();
46692
46730
  await init_useTerminalSize();
46693
46731
  init_terminal_state();
46694
46732
  init_format_helpers();
46695
- import_jsx_runtime7 = __toESM(require_jsx_runtime());
46733
+ import_jsx_runtime7 = __toESM(require_jsx_runtime(), 1);
46696
46734
  SEVERITY_LABELS = {
46697
46735
  5: "CRIT",
46698
46736
  4: "HIGH",
@@ -46721,7 +46759,9 @@ var init_InteractiveResultsView = __esm({
46721
46759
  scanUsage: scanUsageProp,
46722
46760
  initialView
46723
46761
  }) => {
46724
- const scanUsage = result.freeScansRemaining !== void 0 ? `${result.freeScansRemaining} scans left` : scanUsageProp;
46762
+ const usageDisplay = result.usage ? formatUsage(result.usage) : null;
46763
+ const scanUsage = usageDisplay ? usageDisplay.text : result.freeScansRemaining !== void 0 ? `${result.freeScansRemaining.toLocaleString()} packages left` : scanUsageProp;
46764
+ const usageNearLimit = usageDisplay?.nearLimit ?? false;
46725
46765
  const flagged = (0, import_react30.useMemo)(
46726
46766
  () => result.packages.filter((p) => p.score > 0),
46727
46767
  [result.packages]
@@ -46785,8 +46825,8 @@ var init_InteractiveResultsView = __esm({
46785
46825
  setExportMenu({ scope: defaultScope, format: "json", activeRow: "scope" });
46786
46826
  };
46787
46827
  const buildExportPayload = (scope, currentLicenseIdx) => {
46788
- const blocked = result.packages.filter((p) => p.score >= 70);
46789
- const warned = result.packages.filter((p) => p.score >= 60 && p.score < 70);
46828
+ const blocked = result.packages.filter((p) => p.action === "block");
46829
+ const warned = result.packages.filter((p) => p.action === "warn");
46790
46830
  const cleanPkgs = result.packages.filter((p) => p.score === 0);
46791
46831
  const passWithScore = result.packages.filter((p) => p.score > 0 && p.score < 60);
46792
46832
  const summary = {
@@ -46833,7 +46873,7 @@ var init_InteractiveResultsView = __esm({
46833
46873
  name: p.name,
46834
46874
  version: p.version,
46835
46875
  score: p.score,
46836
- action: p.score >= 70 ? "block" : "warn",
46876
+ action: p.action,
46837
46877
  findings: p.findings.map((f) => ({
46838
46878
  severity: f.severity,
46839
46879
  category: f.category ?? null,
@@ -47024,7 +47064,7 @@ var init_InteractiveResultsView = __esm({
47024
47064
  const scopeTag = scope === "current-license" && currentLicenseIdx !== null ? `${(licenseGroups[currentLicenseIdx]?.spdx ?? "license").replace(/[^A-Za-z0-9._-]/g, "_").slice(0, 32)}` : scope;
47025
47065
  const filename = `dg-scan-${ts}-${scopeTag}.${ext}`;
47026
47066
  const path2 = resolvePath2(process.cwd(), filename);
47027
- writeFileSync12(path2, body, "utf-8");
47067
+ writeFileSync11(path2, body, "utf-8");
47028
47068
  showExportMsg(`\u2713 Exported to ${filename}`);
47029
47069
  } catch (e) {
47030
47070
  showExportMsg(`Export failed: ${e.message}`);
@@ -47422,7 +47462,8 @@ var init_InteractiveResultsView = __esm({
47422
47462
  flagged: flagged.length,
47423
47463
  clean: clean.length,
47424
47464
  userStatus,
47425
- scanUsage
47465
+ scanUsage,
47466
+ usageNearLimit
47426
47467
  }
47427
47468
  ),
47428
47469
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(Box_default, { flexDirection: "column", borderStyle: "round", borderColor: "cyan", paddingLeft: 2, paddingRight: 2, children: [
@@ -47466,7 +47507,8 @@ var init_InteractiveResultsView = __esm({
47466
47507
  flagged: flagged.length,
47467
47508
  clean: clean.length,
47468
47509
  userStatus,
47469
- scanUsage
47510
+ scanUsage,
47511
+ usageNearLimit
47470
47512
  }
47471
47513
  ),
47472
47514
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(
@@ -47613,7 +47655,8 @@ var init_InteractiveResultsView = __esm({
47613
47655
  flagged: flagged.length,
47614
47656
  clean: clean.length,
47615
47657
  userStatus,
47616
- scanUsage
47658
+ scanUsage,
47659
+ usageNearLimit
47617
47660
  }
47618
47661
  ),
47619
47662
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(Box_default, { flexDirection: "column", borderStyle: "round", borderColor: "cyan", paddingLeft: 2, paddingRight: 2, width: "100%", children: [
@@ -47714,7 +47757,8 @@ var init_InteractiveResultsView = __esm({
47714
47757
  flagged: flagged.length,
47715
47758
  clean: clean.length,
47716
47759
  userStatus,
47717
- scanUsage
47760
+ scanUsage,
47761
+ usageNearLimit
47718
47762
  }
47719
47763
  ),
47720
47764
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(Text, { dimColor: true, children: import_chalk9.default.dim("\u2500".repeat(Math.max(20, termCols - 4))) }),
@@ -47805,7 +47849,7 @@ var init_InteractiveResultsView = __esm({
47805
47849
  setDetailPane(null);
47806
47850
  } else {
47807
47851
  const dpRep = dpGroup.packages[0];
47808
- const { color: dpColor } = actionBadge2(dpRep.score);
47852
+ const { color: dpColor } = actionBadge2(dpRep.action);
47809
47853
  const dpScroll = detailPane.scroll;
47810
47854
  const dpAbove = dpScroll;
47811
47855
  const dpBelow = Math.max(0, detailLines.length - dpScroll - detailContentRows);
@@ -47820,7 +47864,8 @@ var init_InteractiveResultsView = __esm({
47820
47864
  flagged: flagged.length,
47821
47865
  clean: clean.length,
47822
47866
  userStatus,
47823
- scanUsage
47867
+ scanUsage,
47868
+ usageNearLimit
47824
47869
  }
47825
47870
  ),
47826
47871
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(Text, { dimColor: true, children: import_chalk9.default.dim("\u2500".repeat(Math.max(20, termCols - 4))) }),
@@ -47908,7 +47953,8 @@ var init_InteractiveResultsView = __esm({
47908
47953
  flagged: flagged.length,
47909
47954
  clean: clean.length,
47910
47955
  userStatus,
47911
- scanUsage
47956
+ scanUsage,
47957
+ usageNearLimit
47912
47958
  }
47913
47959
  ),
47914
47960
  groups.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(import_jsx_runtime7.Fragment, { children: [
@@ -47936,7 +47982,7 @@ var init_InteractiveResultsView = __esm({
47936
47982
  const isCursor = globalIdx === clampedCursor;
47937
47983
  const level = getLevel(globalIdx);
47938
47984
  const rep = group.packages[0];
47939
- const { label, color } = actionBadge2(rep.score);
47985
+ const { label, color } = actionBadge2(rep.action);
47940
47986
  const names = groupNames(group);
47941
47987
  const scoreStr = String(rep.score);
47942
47988
  const lcInfo = rep.license;
@@ -48260,7 +48306,7 @@ function toAPIResponse(results) {
48260
48306
  };
48261
48307
  }
48262
48308
  async function renderTui(results) {
48263
- const React22 = (await Promise.resolve().then(() => __toESM(require_react()))).default;
48309
+ const React22 = (await Promise.resolve().then(() => __toESM(require_react(), 1))).default;
48264
48310
  const { render: render2, Box: Box2 } = await init_build2().then(() => build_exports);
48265
48311
  const { InteractiveResultsView: InteractiveResultsView2 } = await init_InteractiveResultsView().then(() => InteractiveResultsView_exports);
48266
48312
  const { enterTui: enterTui2, leaveTui: leaveTui2 } = await Promise.resolve().then(() => (init_terminal_state(), terminal_state_exports));
@@ -48302,7 +48348,7 @@ async function handleLicensesCommand() {
48302
48348
  return;
48303
48349
  }
48304
48350
  const config = parseConfig(process.argv, false);
48305
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
48351
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
48306
48352
  let discovery;
48307
48353
  try {
48308
48354
  discovery = await discoverLicenseTargets(process.cwd(), config);
@@ -48422,8 +48468,8 @@ __export(publish_check_exports, {
48422
48468
  summarize: () => summarize
48423
48469
  });
48424
48470
  import { spawn as spawn4 } from "node:child_process";
48425
- import { readFileSync as readFileSync14, existsSync as existsSync20, readdirSync as readdirSync3 } from "node:fs";
48426
- import { join as join13, basename as basename2 } from "node:path";
48471
+ import { readFileSync as readFileSync13, existsSync as existsSync19, readdirSync as readdirSync3 } from "node:fs";
48472
+ import { join as join12, basename as basename2 } from "node:path";
48427
48473
  import { createGunzip } from "node:zlib";
48428
48474
  import { createReadStream } from "node:fs";
48429
48475
  function sanitizeSnippet(s, max = 40) {
@@ -48470,7 +48516,7 @@ async function npmPackDryRun(cwd2 = process.cwd()) {
48470
48516
  }));
48471
48517
  let packageJson;
48472
48518
  try {
48473
- const raw = readFileSync14(join13(cwd2, "package.json"), "utf-8");
48519
+ const raw = readFileSync13(join12(cwd2, "package.json"), "utf-8");
48474
48520
  packageJson = JSON.parse(raw);
48475
48521
  } catch {
48476
48522
  }
@@ -48482,9 +48528,9 @@ async function npmPackDryRun(cwd2 = process.cwd()) {
48482
48528
  });
48483
48529
  }
48484
48530
  function findPypiArtifacts(cwd2 = process.cwd()) {
48485
- const dist = join13(cwd2, "dist");
48486
- if (!existsSync20(dist)) return [];
48487
- return readdirSync3(dist).filter((f) => f.endsWith(".tar.gz") || f.endsWith(".whl")).map((f) => join13(dist, f));
48531
+ const dist = join12(cwd2, "dist");
48532
+ if (!existsSync19(dist)) return [];
48533
+ return readdirSync3(dist).filter((f) => f.endsWith(".tar.gz") || f.endsWith(".whl")).map((f) => join12(dist, f));
48488
48534
  }
48489
48535
  function scanPayload(files) {
48490
48536
  const findings = [];
@@ -48558,7 +48604,7 @@ async function runNpmPublishCheck(cwd2 = process.cwd()) {
48558
48604
  const payload = pack.files.map((f) => ({
48559
48605
  path: f.path,
48560
48606
  size: f.size,
48561
- read: () => readFileSync14(join13(cwd2, f.path))
48607
+ read: () => readFileSync13(join12(cwd2, f.path))
48562
48608
  }));
48563
48609
  const findings = scanPayload(payload);
48564
48610
  const scripts = pack.packageJson?.scripts ?? {};
@@ -48806,8 +48852,8 @@ var init_publish_check = __esm({
48806
48852
  });
48807
48853
 
48808
48854
  // src/state/hooks_registry.ts
48809
- import { existsSync as existsSync21, mkdirSync as mkdirSync9, readFileSync as readFileSync15, writeFileSync as writeFileSync13, chmodSync as chmodSync5 } from "node:fs";
48810
- import { dirname as dirname13, isAbsolute as isAbsolute2, normalize as normalize2 } from "node:path";
48855
+ import { existsSync as existsSync20, mkdirSync as mkdirSync8, readFileSync as readFileSync14, writeFileSync as writeFileSync12, chmodSync as chmodSync4 } from "node:fs";
48856
+ import { dirname as dirname12, isAbsolute as isAbsolute2, normalize as normalize2 } from "node:path";
48811
48857
  import { homedir as homedir7 } from "node:os";
48812
48858
  function registryPath() {
48813
48859
  return dgStatePath("hooks-installed.json");
@@ -48849,10 +48895,10 @@ function validateEntry(raw) {
48849
48895
  }
48850
48896
  function readRegistry() {
48851
48897
  const path2 = registryPath();
48852
- if (!existsSync21(path2)) return [];
48898
+ if (!existsSync20(path2)) return [];
48853
48899
  let raw;
48854
48900
  try {
48855
- raw = readFileSync15(path2, "utf-8");
48901
+ raw = readFileSync14(path2, "utf-8");
48856
48902
  } catch {
48857
48903
  return [];
48858
48904
  }
@@ -48874,12 +48920,12 @@ function readRegistry() {
48874
48920
  }
48875
48921
  function writeRegistry(entries) {
48876
48922
  const path2 = registryPath();
48877
- const parent = dirname13(path2);
48878
- if (!existsSync21(parent)) mkdirSync9(parent, { recursive: true, mode: 448 });
48923
+ const parent = dirname12(path2);
48924
+ if (!existsSync20(parent)) mkdirSync8(parent, { recursive: true, mode: 448 });
48879
48925
  const payload = { version: 1, entries };
48880
- writeFileSync13(path2, JSON.stringify(payload, null, 2) + "\n", { encoding: "utf-8", mode: 384 });
48926
+ writeFileSync12(path2, JSON.stringify(payload, null, 2) + "\n", { encoding: "utf-8", mode: 384 });
48881
48927
  try {
48882
- chmodSync5(path2, 384);
48928
+ chmodSync4(path2, 384);
48883
48929
  } catch {
48884
48930
  }
48885
48931
  }
@@ -48925,20 +48971,20 @@ __export(hook_exports, {
48925
48971
  });
48926
48972
  import { createHash } from "node:crypto";
48927
48973
  import {
48928
- existsSync as existsSync22,
48974
+ existsSync as existsSync21,
48929
48975
  lstatSync as lstatSync6,
48930
- readFileSync as readFileSync16,
48931
- writeFileSync as writeFileSync14,
48932
- mkdirSync as mkdirSync10,
48933
- chmodSync as chmodSync6,
48934
- unlinkSync as unlinkSync5
48976
+ readFileSync as readFileSync15,
48977
+ writeFileSync as writeFileSync13,
48978
+ mkdirSync as mkdirSync9,
48979
+ chmodSync as chmodSync5,
48980
+ unlinkSync as unlinkSync4
48935
48981
  } from "node:fs";
48936
- import { join as join14, dirname as dirname14, resolve as resolvePath3, isAbsolute as isAbsolute3 } from "node:path";
48982
+ import { join as join13, dirname as dirname13, resolve as resolvePath3, isAbsolute as isAbsolute3 } from "node:path";
48937
48983
  function hashRepoPath(repoPath) {
48938
48984
  return createHash("sha256").update(repoPath).digest("hex");
48939
48985
  }
48940
48986
  function assertSafeWriteTarget(target) {
48941
- const parent = dirname14(target);
48987
+ const parent = dirname13(target);
48942
48988
  try {
48943
48989
  const parentStat = lstatSync6(parent);
48944
48990
  if (parentStat.isSymbolicLink()) {
@@ -48966,7 +49012,7 @@ function assertSafeWriteTarget(target) {
48966
49012
  }
48967
49013
  function safeWriteFileSync(target, content) {
48968
49014
  assertSafeWriteTarget(target);
48969
- writeFileSync14(target, content);
49015
+ writeFileSync13(target, content);
48970
49016
  }
48971
49017
  function findHooksDir() {
48972
49018
  try {
@@ -48984,13 +49030,13 @@ function findRepoRoot() {
48984
49030
  }
48985
49031
  function detectHookFramework(repoRoot) {
48986
49032
  const root = repoRoot ?? findRepoRoot();
48987
- const huskyHook = join14(root, ".husky", "pre-commit");
48988
- const lefthookConfig = join14(root, "lefthook.yml");
48989
- const lefthookConfigYaml = join14(root, "lefthook.yaml");
49033
+ const huskyHook = join13(root, ".husky", "pre-commit");
49034
+ const lefthookConfig = join13(root, "lefthook.yml");
49035
+ const lefthookConfigYaml = join13(root, "lefthook.yaml");
48990
49036
  const hooksDir = findHooksDir();
48991
- const bareHook = join14(hooksDir, "pre-commit");
48992
- if (existsSync22(huskyHook)) {
48993
- const content = readFileSync16(huskyHook, "utf-8");
49037
+ const bareHook = join13(hooksDir, "pre-commit");
49038
+ if (existsSync21(huskyHook)) {
49039
+ const content = readFileSync15(huskyHook, "utf-8");
48994
49040
  return {
48995
49041
  framework: "husky",
48996
49042
  targetFile: huskyHook,
@@ -48998,8 +49044,8 @@ function detectHookFramework(repoRoot) {
48998
49044
  };
48999
49045
  }
49000
49046
  for (const cfg of [lefthookConfig, lefthookConfigYaml]) {
49001
- if (existsSync22(cfg)) {
49002
- const content = readFileSync16(cfg, "utf-8");
49047
+ if (existsSync21(cfg)) {
49048
+ const content = readFileSync15(cfg, "utf-8");
49003
49049
  const installed2 = /^\s+dependency-guardian\s*:/m.test(content);
49004
49050
  return {
49005
49051
  framework: "lefthook",
@@ -49009,8 +49055,8 @@ function detectHookFramework(repoRoot) {
49009
49055
  }
49010
49056
  }
49011
49057
  let installed = false;
49012
- if (existsSync22(bareHook)) {
49013
- installed = readFileSync16(bareHook, "utf-8").includes(HOOK_MARKER);
49058
+ if (existsSync21(bareHook)) {
49059
+ installed = readFileSync15(bareHook, "utf-8").includes(HOOK_MARKER);
49014
49060
  }
49015
49061
  return {
49016
49062
  framework: "bare",
@@ -49019,12 +49065,12 @@ function detectHookFramework(repoRoot) {
49019
49065
  };
49020
49066
  }
49021
49067
  function verifyHookInstalled(info) {
49022
- if (!existsSync22(info.targetFile)) {
49068
+ if (!existsSync21(info.targetFile)) {
49023
49069
  return { ok: false, reason: `hook file missing: ${info.targetFile}` };
49024
49070
  }
49025
49071
  let content;
49026
49072
  try {
49027
- content = readFileSync16(info.targetFile, "utf-8");
49073
+ content = readFileSync15(info.targetFile, "utf-8");
49028
49074
  } catch (e) {
49029
49075
  return { ok: false, reason: `cannot read ${info.targetFile}: ${e.message}` };
49030
49076
  }
@@ -49062,7 +49108,7 @@ ${HUSKY_SNIPPET}`;
49062
49108
 
49063
49109
  ${LEFTHOOK_ENTRY}`;
49064
49110
  case "bare":
49065
- if (existsSync22(info.targetFile)) {
49111
+ if (existsSync21(info.targetFile)) {
49066
49112
  return `Will append to existing hook at ${info.targetFile}:
49067
49113
  ${HOOK_SECTION}`;
49068
49114
  }
@@ -49071,21 +49117,21 @@ ${HOOK_SCRIPT}`;
49071
49117
  }
49072
49118
  }
49073
49119
  function installHuskyHook(targetFile) {
49074
- const existing = readFileSync16(targetFile, "utf-8");
49120
+ const existing = readFileSync15(targetFile, "utf-8");
49075
49121
  if (existing.includes(HOOK_MARKER)) {
49076
49122
  process.stderr.write(" Hook already installed in Husky.\n");
49077
49123
  return;
49078
49124
  }
49079
49125
  safeWriteFileSync(targetFile, existing.trimEnd() + "\n" + HUSKY_SNIPPET);
49080
49126
  try {
49081
- chmodSync6(targetFile, 493);
49127
+ chmodSync5(targetFile, 493);
49082
49128
  } catch {
49083
49129
  }
49084
49130
  process.stderr.write(` Appended Dependency Guardian to ${targetFile}
49085
49131
  `);
49086
49132
  }
49087
49133
  function installLefthookHook(targetFile) {
49088
- const existing = readFileSync16(targetFile, "utf-8");
49134
+ const existing = readFileSync15(targetFile, "utf-8");
49089
49135
  if (/^\s+dependency-guardian\s*:/m.test(existing)) {
49090
49136
  process.stderr.write(" Hook already installed in lefthook.\n");
49091
49137
  return;
@@ -49117,16 +49163,16 @@ function installLefthookHook(targetFile) {
49117
49163
  `);
49118
49164
  }
49119
49165
  function installBareHook(targetFile) {
49120
- const hooksDir = dirname14(targetFile);
49121
- mkdirSync10(hooksDir, { recursive: true });
49122
- if (existsSync22(targetFile)) {
49123
- const existing = readFileSync16(targetFile, "utf-8");
49166
+ const hooksDir = dirname13(targetFile);
49167
+ mkdirSync9(hooksDir, { recursive: true });
49168
+ if (existsSync21(targetFile)) {
49169
+ const existing = readFileSync15(targetFile, "utf-8");
49124
49170
  if (existing.includes(HOOK_MARKER)) {
49125
49171
  process.stderr.write(" Hook already installed.\n");
49126
49172
  return;
49127
49173
  }
49128
49174
  safeWriteFileSync(targetFile, existing.trimEnd() + "\n" + HOOK_SECTION);
49129
- chmodSync6(targetFile, 493);
49175
+ chmodSync5(targetFile, 493);
49130
49176
  process.stderr.write(
49131
49177
  ` Appended Dependency Guardian hook to existing ${targetFile}
49132
49178
  `
@@ -49134,7 +49180,7 @@ function installBareHook(targetFile) {
49134
49180
  return;
49135
49181
  }
49136
49182
  safeWriteFileSync(targetFile, HOOK_SCRIPT);
49137
- chmodSync6(targetFile, 493);
49183
+ chmodSync5(targetFile, 493);
49138
49184
  process.stderr.write(` Installed git pre-commit hook at ${targetFile}
49139
49185
  `);
49140
49186
  }
@@ -49177,10 +49223,10 @@ async function installHook() {
49177
49223
  }
49178
49224
  }
49179
49225
  function stripDgFromHookFile(hookPath, framework, repoPath) {
49180
- if (!existsSync22(hookPath)) {
49226
+ if (!existsSync21(hookPath)) {
49181
49227
  return { status: "not-found", hookPath, repoPath };
49182
49228
  }
49183
- const content = readFileSync16(hookPath, "utf-8");
49229
+ const content = readFileSync15(hookPath, "utf-8");
49184
49230
  if (framework === "lefthook") {
49185
49231
  if (!/^\s+dependency-guardian\s*:/m.test(content)) {
49186
49232
  return { status: "not-found", hookPath, repoPath };
@@ -49197,7 +49243,7 @@ function stripDgFromHookFile(hookPath, framework, repoPath) {
49197
49243
  return { status: "not-found", hookPath, repoPath };
49198
49244
  }
49199
49245
  if (framework === "bare" && content.trimStart().startsWith("#!/bin/sh\n" + HOOK_MARKER)) {
49200
- unlinkSync5(hookPath);
49246
+ unlinkSync4(hookPath);
49201
49247
  removeEntry(repoPath, hookPath);
49202
49248
  return { status: "removed", hookPath, repoPath };
49203
49249
  }
@@ -49210,7 +49256,7 @@ function stripDgFromHookFile(hookPath, framework, repoPath) {
49210
49256
  const after = content.slice(endIdx + MARKER_END.length).trimStart();
49211
49257
  const remaining = (before + (after ? "\n" + after : "")).trimEnd() + "\n";
49212
49258
  if (remaining.trim() === "" || remaining.trim() === "#!/bin/sh") {
49213
- unlinkSync5(hookPath);
49259
+ unlinkSync4(hookPath);
49214
49260
  } else {
49215
49261
  safeWriteFileSync(hookPath, remaining);
49216
49262
  }
@@ -49220,10 +49266,10 @@ function stripDgFromHookFile(hookPath, framework, repoPath) {
49220
49266
  function uninstallHookFromRepo(repoRootOverride) {
49221
49267
  const root = repoRootOverride ?? findRepoRoot();
49222
49268
  const hooksDir = findHooksDir();
49223
- const hookPath = join14(hooksDir, "pre-commit");
49224
- const huskyPath = join14(root, ".husky", "pre-commit");
49225
- if (existsSync22(huskyPath)) {
49226
- const content2 = readFileSync16(huskyPath, "utf-8");
49269
+ const hookPath = join13(hooksDir, "pre-commit");
49270
+ const huskyPath = join13(root, ".husky", "pre-commit");
49271
+ if (existsSync21(huskyPath)) {
49272
+ const content2 = readFileSync15(huskyPath, "utf-8");
49227
49273
  if (content2.includes(HOOK_MARKER)) {
49228
49274
  const startIdx2 = content2.indexOf(MARKER_START);
49229
49275
  const endIdx2 = content2.indexOf(MARKER_END);
@@ -49237,9 +49283,9 @@ function uninstallHookFromRepo(repoRootOverride) {
49237
49283
  }
49238
49284
  }
49239
49285
  }
49240
- for (const cfg of [join14(root, "lefthook.yml"), join14(root, "lefthook.yaml")]) {
49241
- if (!existsSync22(cfg)) continue;
49242
- const content2 = readFileSync16(cfg, "utf-8");
49286
+ for (const cfg of [join13(root, "lefthook.yml"), join13(root, "lefthook.yaml")]) {
49287
+ if (!existsSync21(cfg)) continue;
49288
+ const content2 = readFileSync15(cfg, "utf-8");
49243
49289
  if (/^\s+dependency-guardian\s*:/m.test(content2)) {
49244
49290
  const stripped = content2.replace(
49245
49291
  /^\s+dependency-guardian\s*:\s*\n(?:\s{6,}.*\n)+/gm,
@@ -49250,15 +49296,15 @@ function uninstallHookFromRepo(repoRootOverride) {
49250
49296
  return { status: "removed", hookPath: cfg, repoPath: root };
49251
49297
  }
49252
49298
  }
49253
- if (!existsSync22(hookPath)) {
49299
+ if (!existsSync21(hookPath)) {
49254
49300
  return { status: "not-found", hookPath, repoPath: root };
49255
49301
  }
49256
- const content = readFileSync16(hookPath, "utf-8");
49302
+ const content = readFileSync15(hookPath, "utf-8");
49257
49303
  if (!content.includes(HOOK_MARKER)) {
49258
49304
  return { status: "not-found", hookPath, repoPath: root };
49259
49305
  }
49260
49306
  if (content.trimStart().startsWith("#!/bin/sh\n" + HOOK_MARKER)) {
49261
- unlinkSync5(hookPath);
49307
+ unlinkSync4(hookPath);
49262
49308
  removeEntry(root, hookPath);
49263
49309
  return { status: "removed", hookPath, repoPath: root };
49264
49310
  }
@@ -49272,7 +49318,7 @@ function uninstallHookFromRepo(repoRootOverride) {
49272
49318
  removeEntry(root, hookPath);
49273
49319
  return { status: "removed", hookPath, repoPath: root };
49274
49320
  }
49275
- unlinkSync5(hookPath);
49321
+ unlinkSync4(hookPath);
49276
49322
  removeEntry(root, hookPath);
49277
49323
  return { status: "removed", hookPath, repoPath: root };
49278
49324
  }
@@ -49426,7 +49472,7 @@ __export(update_exports, {
49426
49472
  runUpdate: () => runUpdate
49427
49473
  });
49428
49474
  import { spawnSync as spawnSync2 } from "node:child_process";
49429
- import { accessSync, constants as constants2, realpathSync, unlinkSync as unlinkSync6 } from "node:fs";
49475
+ import { accessSync, constants as constants2, realpathSync, unlinkSync as unlinkSync5 } from "node:fs";
49430
49476
  import { sep as sep3 } from "node:path";
49431
49477
  function parseUpdateArgs(args) {
49432
49478
  return {
@@ -49537,7 +49583,7 @@ function printUpgradeCommand(latest, kind) {
49537
49583
  }
49538
49584
  function invalidateUpdateCache() {
49539
49585
  try {
49540
- unlinkSync6(dgCachePath("update-check.json"));
49586
+ unlinkSync5(dgCachePath("update-check.json"));
49541
49587
  } catch {
49542
49588
  }
49543
49589
  }
@@ -49661,7 +49707,7 @@ var import_chalk10, PKG_NAME2, FETCH_TIMEOUT_MS, USAGE4;
49661
49707
  var init_update = __esm({
49662
49708
  "src/commands/update.ts"() {
49663
49709
  "use strict";
49664
- import_chalk10 = __toESM(require_source());
49710
+ import_chalk10 = __toESM(require_source(), 1);
49665
49711
  init_paths();
49666
49712
  init_update_check();
49667
49713
  PKG_NAME2 = "@westbayberry/dg";
@@ -49687,8 +49733,8 @@ var init_update = __esm({
49687
49733
  });
49688
49734
 
49689
49735
  // src/python-hook/install.ts
49690
- import { existsSync as existsSync23, readFileSync as readFileSync17, unlinkSync as unlinkSync7, readdirSync as readdirSync4, statSync as statSync5 } from "node:fs";
49691
- import { dirname as dirname15, join as join15, resolve } from "node:path";
49736
+ import { existsSync as existsSync22, readFileSync as readFileSync16, unlinkSync as unlinkSync6, readdirSync as readdirSync4, statSync as statSync4 } from "node:fs";
49737
+ import { dirname as dirname14, join as join14, resolve } from "node:path";
49692
49738
  import { spawnSync as spawnSync3 } from "node:child_process";
49693
49739
  import { homedir as homedir8 } from "node:os";
49694
49740
  function probeUserSite(pythonName) {
@@ -49712,8 +49758,8 @@ function uninstallPythonHooks(_opts = {}) {
49712
49758
  const removed = [];
49713
49759
  let receipt = null;
49714
49760
  try {
49715
- if (existsSync23(receiptPath)) {
49716
- receipt = JSON.parse(readFileSync17(receiptPath, "utf-8"));
49761
+ if (existsSync22(receiptPath)) {
49762
+ receipt = JSON.parse(readFileSync16(receiptPath, "utf-8"));
49717
49763
  }
49718
49764
  } catch {
49719
49765
  receipt = null;
@@ -49731,9 +49777,9 @@ function uninstallPythonHooks(_opts = {}) {
49731
49777
  }
49732
49778
  for (const site of sites) {
49733
49779
  for (const filename of ["dg_pip_hook.py", "dg_pip_hook.pth"]) {
49734
- const full = join15(site, filename);
49780
+ const full = join14(site, filename);
49735
49781
  try {
49736
- if (existsSync23(full)) {
49782
+ if (existsSync22(full)) {
49737
49783
  safeUnlink(full);
49738
49784
  removed.push(full);
49739
49785
  }
@@ -49741,13 +49787,13 @@ function uninstallPythonHooks(_opts = {}) {
49741
49787
  }
49742
49788
  }
49743
49789
  try {
49744
- const pyCache = join15(site, "__pycache__");
49745
- if (existsSync23(pyCache) && statSync5(pyCache).isDirectory()) {
49790
+ const pyCache = join14(site, "__pycache__");
49791
+ if (existsSync22(pyCache) && statSync4(pyCache).isDirectory()) {
49746
49792
  for (const f of readdirSync4(pyCache)) {
49747
49793
  if (f.startsWith("dg_pip_hook.")) {
49748
49794
  try {
49749
- safeUnlink(join15(pyCache, f));
49750
- removed.push(join15(pyCache, f));
49795
+ safeUnlink(join14(pyCache, f));
49796
+ removed.push(join14(pyCache, f));
49751
49797
  } catch {
49752
49798
  }
49753
49799
  }
@@ -49757,8 +49803,8 @@ function uninstallPythonHooks(_opts = {}) {
49757
49803
  }
49758
49804
  }
49759
49805
  try {
49760
- if (existsSync23(receiptPath)) {
49761
- unlinkSync7(receiptPath);
49806
+ if (existsSync22(receiptPath)) {
49807
+ unlinkSync6(receiptPath);
49762
49808
  }
49763
49809
  } catch {
49764
49810
  }
@@ -49789,7 +49835,7 @@ __export(uninstall_exports, {
49789
49835
  parseUninstallArgs: () => parseUninstallArgs,
49790
49836
  runUninstall: () => runUninstall
49791
49837
  });
49792
- import { existsSync as existsSync24, rmSync as rmSync3, unlinkSync as unlinkSync8, statSync as statSync6 } from "node:fs";
49838
+ import { existsSync as existsSync23, rmSync as rmSync2, unlinkSync as unlinkSync7 } from "node:fs";
49793
49839
  function parseUninstallArgs(args) {
49794
49840
  return {
49795
49841
  assumeYes: args.includes("--yes") || args.includes("-y"),
@@ -49800,21 +49846,18 @@ function parseUninstallArgs(args) {
49800
49846
  }
49801
49847
  function safeExists(p) {
49802
49848
  try {
49803
- return existsSync24(p);
49849
+ return existsSync23(p);
49804
49850
  } catch {
49805
49851
  return false;
49806
49852
  }
49807
49853
  }
49808
49854
  function buildPlan(opts) {
49809
49855
  const p = dgPaths();
49810
- const legacy = legacyPaths();
49811
49856
  const plan = {
49812
49857
  configFiles: [],
49813
49858
  cacheDir: null,
49814
49859
  stateDir: null,
49815
49860
  rootDir: null,
49816
- legacyFiles: [],
49817
- legacyDirs: [],
49818
49861
  hooks: [],
49819
49862
  rcCleanup: false
49820
49863
  };
@@ -49823,10 +49866,6 @@ function buildPlan(opts) {
49823
49866
  if (safeExists(p.cacheDir)) plan.cacheDir = p.cacheDir;
49824
49867
  if (safeExists(p.stateDir)) plan.stateDir = p.stateDir;
49825
49868
  if (safeExists(p.root)) plan.rootDir = p.root;
49826
- for (const f of [legacy.dgrc, legacy.updateCheck]) {
49827
- if (safeExists(f)) plan.legacyFiles.push(f);
49828
- }
49829
- if (safeExists(legacy.cacheDir)) plan.legacyDirs.push(legacy.cacheDir);
49830
49869
  if (!opts.keepHooks) {
49831
49870
  plan.hooks = listEntries();
49832
49871
  }
@@ -49850,10 +49889,6 @@ function printPlan(plan, opts) {
49850
49889
  process.stderr.write(` ${plan.rootDir}/ (entire tree)
49851
49890
  `);
49852
49891
  }
49853
- for (const f of plan.legacyFiles) process.stderr.write(` ${f} (legacy)
49854
- `);
49855
- for (const d of plan.legacyDirs) process.stderr.write(` ${d}/ (legacy)
49856
- `);
49857
49892
  if (plan.hooks.length > 0) {
49858
49893
  process.stderr.write(` pre-commit hooks in ${plan.hooks.length} repo(s):
49859
49894
  `);
@@ -49916,7 +49951,7 @@ async function revokeApiKey(apiKey) {
49916
49951
  }
49917
49952
  function rmFile(path2) {
49918
49953
  try {
49919
- unlinkSync8(path2);
49954
+ unlinkSync7(path2);
49920
49955
  return { ok: true };
49921
49956
  } catch (e) {
49922
49957
  const code = e.code;
@@ -49926,20 +49961,12 @@ function rmFile(path2) {
49926
49961
  }
49927
49962
  function rmTree(path2) {
49928
49963
  try {
49929
- rmSync3(path2, { recursive: true, force: true });
49964
+ rmSync2(path2, { recursive: true, force: true });
49930
49965
  return { ok: true };
49931
49966
  } catch (e) {
49932
49967
  return { ok: false, reason: e.message };
49933
49968
  }
49934
49969
  }
49935
- function isWritableTarget(path2) {
49936
- try {
49937
- const st = statSync6(path2);
49938
- return st.isDirectory() || st.isFile();
49939
- } catch {
49940
- return false;
49941
- }
49942
- }
49943
49970
  async function runUninstall(args) {
49944
49971
  if (args.includes("--help") || args.includes("-h")) {
49945
49972
  process.stdout.write(USAGE5);
@@ -49985,7 +50012,7 @@ async function runUninstall(args) {
49985
50012
  }
49986
50013
  if (!opts.keepHooks && !opts.soft) {
49987
50014
  for (const h of plan.hooks) {
49988
- if (!existsSync24(h.repoPath)) {
50015
+ if (!existsSync23(h.repoPath)) {
49989
50016
  process.stderr.write(import_chalk11.default.dim(` \xB7 ${h.repoPath} no longer exists \u2014 skipping registered hook
49990
50017
  `));
49991
50018
  continue;
@@ -50051,22 +50078,6 @@ async function runUninstall(args) {
50051
50078
  `);
50052
50079
  }
50053
50080
  } else {
50054
- for (const f of plan.legacyFiles) {
50055
- if (!isWritableTarget(f)) continue;
50056
- const r = rmFile(f);
50057
- if (r.ok) process.stderr.write(import_chalk11.default.green(" \u2713 ") + `Removed ${f}
50058
- `);
50059
- else process.stderr.write(import_chalk11.default.red(" \u2718 ") + `${f}: ${r.reason}
50060
- `);
50061
- }
50062
- for (const d of plan.legacyDirs) {
50063
- if (!isWritableTarget(d)) continue;
50064
- const r = rmTree(d);
50065
- if (r.ok) process.stderr.write(import_chalk11.default.green(" \u2713 ") + `Removed ${d}
50066
- `);
50067
- else process.stderr.write(import_chalk11.default.red(" \u2718 ") + `${d}: ${r.reason}
50068
- `);
50069
- }
50070
50081
  if (plan.rootDir) {
50071
50082
  const r = rmTree(plan.rootDir);
50072
50083
  if (r.ok) process.stderr.write(import_chalk11.default.green(" \u2713 ") + `Removed ${plan.rootDir}
@@ -50092,7 +50103,7 @@ var import_chalk11, REVOKE_TIMEOUT_MS, USAGE5;
50092
50103
  var init_uninstall = __esm({
50093
50104
  "src/commands/uninstall.ts"() {
50094
50105
  "use strict";
50095
- import_chalk11 = __toESM(require_source());
50106
+ import_chalk11 = __toESM(require_source(), 1);
50096
50107
  init_paths();
50097
50108
  init_hooks_registry();
50098
50109
  init_hook();
@@ -50116,9 +50127,6 @@ var init_uninstall = __esm({
50116
50127
 
50117
50128
  Removes:
50118
50129
  ~/.dg/ (config + cache + state + hooks registry)
50119
- ~/.dgrc.json (legacy, if still present)
50120
- ~/.dg/ (legacy, if still present)
50121
- ~/.dg-update-check.json (legacy, if still present)
50122
50130
  every per-repo pre-commit hook installed via 'dg hook install'
50123
50131
  the dg sentinel block in your shell rc files
50124
50132
 
@@ -50135,7 +50143,7 @@ var verify_exports = {};
50135
50143
  __export(verify_exports, {
50136
50144
  handleVerifyCommand: () => handleVerifyCommand
50137
50145
  });
50138
- import { writeFileSync as writeFileSync15 } from "node:fs";
50146
+ import { writeFileSync as writeFileSync14 } from "node:fs";
50139
50147
  function detectEcosystem(spec) {
50140
50148
  if (/[<>=!~]=?|~=/.test(spec)) return "pypi";
50141
50149
  if (spec.startsWith("@")) return "npm";
@@ -50250,7 +50258,7 @@ async function callApi(packages, ecosystem, config) {
50250
50258
  }
50251
50259
  function writeOutput(content, outputPath) {
50252
50260
  if (outputPath) {
50253
- writeFileSync15(outputPath, content);
50261
+ writeFileSync14(outputPath, content);
50254
50262
  process.stderr.write(import_chalk12.default.green(` \u2713 Wrote ${content.length} bytes to ${outputPath}
50255
50263
  `));
50256
50264
  } else {
@@ -50375,7 +50383,7 @@ var import_chalk12, USAGE6;
50375
50383
  var init_verify = __esm({
50376
50384
  "src/commands/verify.ts"() {
50377
50385
  "use strict";
50378
- import_chalk12 = __toESM(require_source());
50386
+ import_chalk12 = __toESM(require_source(), 1);
50379
50387
  init_config();
50380
50388
  init_client();
50381
50389
  init_npm_wrapper();
@@ -50434,11 +50442,11 @@ var import_react31, import_jsx_runtime8, ConfettiDemoApp;
50434
50442
  var init_ConfettiDemoApp = __esm({
50435
50443
  async "src/ui/apps/ConfettiDemoApp.tsx"() {
50436
50444
  "use strict";
50437
- import_react31 = __toESM(require_react());
50445
+ import_react31 = __toESM(require_react(), 1);
50438
50446
  await init_build2();
50439
50447
  await init_Confetti();
50440
50448
  await init_useTerminalSize();
50441
- import_jsx_runtime8 = __toESM(require_jsx_runtime());
50449
+ import_jsx_runtime8 = __toESM(require_jsx_runtime(), 1);
50442
50450
  ConfettiDemoApp = () => {
50443
50451
  const { exit } = use_app_default();
50444
50452
  const { cols, rows } = useTerminalSize();
@@ -50490,7 +50498,7 @@ var import_react32, USAGE7;
50490
50498
  var init_confetti = __esm({
50491
50499
  "src/commands/confetti.ts"() {
50492
50500
  "use strict";
50493
- import_react32 = __toESM(require_react());
50501
+ import_react32 = __toESM(require_react(), 1);
50494
50502
  USAGE7 = `
50495
50503
  dg confetti \u2014 preview the terminal confetti effect (dev)
50496
50504
 
@@ -50559,7 +50567,7 @@ function reducer3(_state, action) {
50559
50567
  case "ERROR":
50560
50568
  return { phase: "error", error: action.error };
50561
50569
  case "FREE_CAP_REACHED":
50562
- return { phase: "free_cap_reached", scansUsed: action.scansUsed, maxScans: action.maxScans };
50570
+ return { phase: "free_cap_reached", scansUsed: action.scansUsed, maxScans: action.maxScans, capReason: action.capReason };
50563
50571
  }
50564
50572
  }
50565
50573
  function useScan(config) {
@@ -50620,7 +50628,7 @@ async function runNpmScan(packages, skippedCount, config, dispatch) {
50620
50628
  dispatch({ type: "SCAN_COMPLETE", result, durationMs: Date.now() - startMs, skippedCount });
50621
50629
  } catch (error) {
50622
50630
  if (error instanceof FreeCapReachedError) {
50623
- dispatch({ type: "FREE_CAP_REACHED", scansUsed: error.scansUsed, maxScans: error.maxScans });
50631
+ dispatch({ type: "FREE_CAP_REACHED", scansUsed: error.scansUsed, maxScans: error.maxScans, capReason: error.reason });
50624
50632
  return;
50625
50633
  }
50626
50634
  const err = error instanceof Error ? error : new Error(String(error));
@@ -50669,7 +50677,6 @@ async function scanProjects(projects, config, dispatch) {
50669
50677
  dispatch({ type: "DISCOVERY_EMPTY", message: "No packages to scan." });
50670
50678
  return;
50671
50679
  }
50672
- const startMs = Date.now();
50673
50680
  const results = [];
50674
50681
  let completed = 0;
50675
50682
  if (npmPackages.length > 0) {
@@ -50696,22 +50703,11 @@ async function scanProjects(projects, config, dispatch) {
50696
50703
  });
50697
50704
  results.push(pypiResult);
50698
50705
  }
50699
- const allPackages = results.flatMap((r) => r.packages);
50700
- const maxScore = Math.max(0, ...allPackages.map((p) => p.score));
50701
- const action = maxScore >= 70 ? "block" : maxScore >= 60 ? "warn" : "pass";
50702
- const safeVersions = {};
50703
- for (const r of results) Object.assign(safeVersions, r.safeVersions);
50704
- const merged = {
50705
- score: maxScore,
50706
- action,
50707
- packages: allPackages,
50708
- safeVersions,
50709
- durationMs: Date.now() - startMs
50710
- };
50706
+ const merged = mergeResponses(results);
50711
50707
  dispatch({ type: "SCAN_COMPLETE", result: merged, durationMs: merged.durationMs, skippedCount: 0, discoveredTotal });
50712
50708
  } catch (error) {
50713
50709
  if (error instanceof FreeCapReachedError) {
50714
- dispatch({ type: "FREE_CAP_REACHED", scansUsed: error.scansUsed, maxScans: error.maxScans });
50710
+ dispatch({ type: "FREE_CAP_REACHED", scansUsed: error.scansUsed, maxScans: error.maxScans, capReason: error.reason });
50715
50711
  return;
50716
50712
  }
50717
50713
  const err = error instanceof Error ? error : new Error(String(error));
@@ -50723,7 +50719,7 @@ var import_react33;
50723
50719
  var init_useScan = __esm({
50724
50720
  "src/ui/hooks/useScan.ts"() {
50725
50721
  "use strict";
50726
- import_react33 = __toESM(require_react());
50722
+ import_react33 = __toESM(require_react(), 1);
50727
50723
  init_lockfile();
50728
50724
  init_client();
50729
50725
  init_walker();
@@ -50761,12 +50757,12 @@ var import_react34, import_chalk13, import_jsx_runtime9, ProgressBar;
50761
50757
  var init_ProgressBar = __esm({
50762
50758
  async "src/ui/components/ProgressBar.tsx"() {
50763
50759
  "use strict";
50764
- import_react34 = __toESM(require_react());
50760
+ import_react34 = __toESM(require_react(), 1);
50765
50761
  await init_build2();
50766
50762
  await init_build3();
50767
- import_chalk13 = __toESM(require_source());
50763
+ import_chalk13 = __toESM(require_source(), 1);
50768
50764
  await init_useTerminalSize();
50769
- import_jsx_runtime9 = __toESM(require_jsx_runtime());
50765
+ import_jsx_runtime9 = __toESM(require_jsx_runtime(), 1);
50770
50766
  ProgressBar = ({
50771
50767
  value,
50772
50768
  total,
@@ -50863,9 +50859,9 @@ var init_ErrorView = __esm({
50863
50859
  async "src/ui/components/ErrorView.tsx"() {
50864
50860
  "use strict";
50865
50861
  await init_build2();
50866
- import_chalk14 = __toESM(require_source());
50862
+ import_chalk14 = __toESM(require_source(), 1);
50867
50863
  init_sanitize();
50868
- import_jsx_runtime10 = __toESM(require_jsx_runtime());
50864
+ import_jsx_runtime10 = __toESM(require_jsx_runtime(), 1);
50869
50865
  ErrorView = ({ error }) => {
50870
50866
  const hint = getHint(error);
50871
50867
  return /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)(
@@ -50896,12 +50892,12 @@ var import_react35, import_chalk15, import_jsx_runtime11, ProjectSelector;
50896
50892
  var init_ProjectSelector = __esm({
50897
50893
  async "src/ui/components/ProjectSelector.tsx"() {
50898
50894
  "use strict";
50899
- import_react35 = __toESM(require_react());
50895
+ import_react35 = __toESM(require_react(), 1);
50900
50896
  await init_build2();
50901
- import_chalk15 = __toESM(require_source());
50897
+ import_chalk15 = __toESM(require_source(), 1);
50902
50898
  init_sanitize();
50903
50899
  await init_useTerminalSize();
50904
- import_jsx_runtime11 = __toESM(require_jsx_runtime());
50900
+ import_jsx_runtime11 = __toESM(require_jsx_runtime(), 1);
50905
50901
  ProjectSelector = ({ projects, onConfirm, onCancel, userStatus }) => {
50906
50902
  const [cursor, setCursor] = (0, import_react35.useState)(0);
50907
50903
  const [selected, setSelected] = (0, import_react35.useState)(() => new Set(projects.map((_, i) => i)));
@@ -50996,7 +50992,7 @@ var init_SetupBanner = __esm({
50996
50992
  async "src/ui/components/SetupBanner.tsx"() {
50997
50993
  "use strict";
50998
50994
  await init_build2();
50999
- import_jsx_runtime12 = __toESM(require_jsx_runtime());
50995
+ import_jsx_runtime12 = __toESM(require_jsx_runtime(), 1);
51000
50996
  SetupBanner = ({ issues }) => {
51001
50997
  if (issues.length === 0) return null;
51002
50998
  return /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)(
@@ -51039,7 +51035,7 @@ var import_react36, import_jsx_runtime13, App2;
51039
51035
  var init_App2 = __esm({
51040
51036
  async "src/ui/App.tsx"() {
51041
51037
  "use strict";
51042
- import_react36 = __toESM(require_react());
51038
+ import_react36 = __toESM(require_react(), 1);
51043
51039
  await init_build2();
51044
51040
  init_auth();
51045
51041
  init_useScan();
@@ -51051,7 +51047,7 @@ var init_App2 = __esm({
51051
51047
  await init_SetupBanner();
51052
51048
  await init_useTerminalSize();
51053
51049
  init_terminal_state();
51054
- import_jsx_runtime13 = __toESM(require_jsx_runtime());
51050
+ import_jsx_runtime13 = __toESM(require_jsx_runtime(), 1);
51055
51051
  App2 = ({ config, userStatus, scanUsage, setupIssues = [] }) => {
51056
51052
  const { state, scanSelectedProjects, restartSelection } = useScan(config);
51057
51053
  const { exit } = use_app_default();
@@ -51135,7 +51131,7 @@ var init_App2 = __esm({
51135
51131
  exit();
51136
51132
  }
51137
51133
  }
51138
- if (state.phase === "trial_exhausted") {
51134
+ if (state.phase === "free_cap_reached") {
51139
51135
  if (input === "q" || key.escape || key.return) {
51140
51136
  process.exitCode = 1;
51141
51137
  leaveAltScreen();
@@ -51188,7 +51184,7 @@ var init_App2 = __esm({
51188
51184
  return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { dimColor: true, children: state.message });
51189
51185
  case "error":
51190
51186
  return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(ErrorView, { error: state.error });
51191
- case "trial_exhausted": {
51187
+ case "free_cap_reached": {
51192
51188
  let hasKey = false;
51193
51189
  try {
51194
51190
  hasKey = !!getStoredApiKey();
@@ -51205,12 +51201,25 @@ var init_App2 = __esm({
51205
51201
  /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { color: "cyan", bold: true, children: "dg login" }),
51206
51202
  " to re-authenticate."
51207
51203
  ] })
51208
- ] }) : /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(import_jsx_runtime13.Fragment, { children: [
51209
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { color: "yellow", bold: true, children: "You've used your 5 free anonymous scans." }),
51204
+ ] }) : state.capReason === "prefix_cap" ? /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(import_jsx_runtime13.Fragment, { children: [
51205
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { color: "yellow", bold: true, children: "Too many anonymous devices from your network this month." }),
51210
51206
  /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(Text, { children: [
51211
- "Run ",
51207
+ "Sign in with ",
51212
51208
  /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { color: "cyan", bold: true, children: "dg login" }),
51213
- " to access Dependency Guardian for free."
51209
+ " to keep scanning."
51210
+ ] })
51211
+ ] }) : /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(import_jsx_runtime13.Fragment, { children: [
51212
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(Text, { color: "yellow", bold: true, children: [
51213
+ "Free monthly limit reached (",
51214
+ state.scansUsed.toLocaleString(),
51215
+ "/",
51216
+ state.maxScans.toLocaleString(),
51217
+ " packages)."
51218
+ ] }),
51219
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(Text, { children: [
51220
+ "Upgrade to Pro with ",
51221
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { color: "cyan", bold: true, children: "dg upgrade" }),
51222
+ " for 250k packages/month."
51214
51223
  ] })
51215
51224
  ] }),
51216
51225
  /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(Text, { children: " " }),
@@ -51240,8 +51249,8 @@ __export(ink_controls_exports, {
51240
51249
  setInkClear: () => setInkClear,
51241
51250
  setInkInstance: () => setInkInstance
51242
51251
  });
51243
- import { resolve as resolve2, dirname as dirname16 } from "node:path";
51244
- import { existsSync as existsSync25 } from "node:fs";
51252
+ import { resolve as resolve2, dirname as dirname15 } from "node:path";
51253
+ import { existsSync as existsSync24 } from "node:fs";
51245
51254
  function locateInkInstancesPath() {
51246
51255
  let cur;
51247
51256
  try {
@@ -51251,13 +51260,13 @@ function locateInkInstancesPath() {
51251
51260
  }
51252
51261
  while (cur && cur !== "/" && cur !== ".") {
51253
51262
  const candidate = resolve2(cur, "node_modules", "ink", "build", "instances.js");
51254
- if (existsSync25(candidate)) return candidate;
51255
- const parent = dirname16(cur);
51263
+ if (existsSync24(candidate)) return candidate;
51264
+ const parent = dirname15(cur);
51256
51265
  if (parent === cur) break;
51257
51266
  cur = parent;
51258
51267
  }
51259
51268
  const cwdCandidate = resolve2(process.cwd(), "node_modules", "ink", "build", "instances.js");
51260
- if (existsSync25(cwdCandidate)) return cwdCandidate;
51269
+ if (existsSync24(cwdCandidate)) return cwdCandidate;
51261
51270
  return null;
51262
51271
  }
51263
51272
  async function initInkInstances() {
@@ -51581,7 +51590,7 @@ function useInstallWrapper(rawArgs, config, opts, exit) {
51581
51590
  const result = await opts.callAnalyze(resolved, config);
51582
51591
  if (result.action === "pass") {
51583
51592
  if (exit) exit();
51584
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
51593
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
51585
51594
  const line = formatPassLine(result, chalk18);
51586
51595
  process.stderr.write(" " + line + "\n\n");
51587
51596
  const code = await opts.runInstall(parsed.rawArgs);
@@ -51700,7 +51709,7 @@ var import_react37, NPM_OPTIONS, PIP_OPTIONS;
51700
51709
  var init_useWrapperBase = __esm({
51701
51710
  "src/ui/hooks/useWrapperBase.ts"() {
51702
51711
  "use strict";
51703
- import_react37 = __toESM(require_react());
51712
+ import_react37 = __toESM(require_react(), 1);
51704
51713
  init_client();
51705
51714
  init_npm_wrapper();
51706
51715
  init_pip_wrapper();
@@ -51732,7 +51741,7 @@ var init_DurationLine = __esm({
51732
51741
  async "src/ui/components/DurationLine.tsx"() {
51733
51742
  "use strict";
51734
51743
  await init_build2();
51735
- import_jsx_runtime14 = __toESM(require_jsx_runtime());
51744
+ import_jsx_runtime14 = __toESM(require_jsx_runtime(), 1);
51736
51745
  DurationLine = ({ ms }) => /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(Text, { dimColor: true, children: [
51737
51746
  "Completed in ",
51738
51747
  (ms / 1e3).toFixed(1),
@@ -51749,9 +51758,10 @@ function severityColor(sev) {
51749
51758
  if (sev >= 2) return import_chalk16.default.dim;
51750
51759
  return import_chalk16.default.dim;
51751
51760
  }
51752
- function actionBadge3(score) {
51753
- if (score >= 70) return { label: "BLOCK", color: import_chalk16.default.red };
51754
- if (score >= 60) return { label: "WARN", color: import_chalk16.default.yellow };
51761
+ function actionBadge3(action) {
51762
+ if (action === "block") return { label: "BLOCK", color: import_chalk16.default.red };
51763
+ if (action === "warn") return { label: "WARN", color: import_chalk16.default.yellow };
51764
+ if (action === "analysis_incomplete") return { label: "UNKNOWN", color: import_chalk16.default.cyan };
51755
51765
  return { label: "PASS", color: import_chalk16.default.green };
51756
51766
  }
51757
51767
  var import_chalk16, import_jsx_runtime15, SEVERITY_LABELS2, EVIDENCE_LIMIT2, ResultsView;
@@ -51759,11 +51769,11 @@ var init_ResultsView = __esm({
51759
51769
  async "src/ui/components/ResultsView.tsx"() {
51760
51770
  "use strict";
51761
51771
  await init_build2();
51762
- import_chalk16 = __toESM(require_source());
51772
+ import_chalk16 = __toESM(require_source(), 1);
51763
51773
  await init_ScoreHeader();
51764
51774
  await init_DurationLine();
51765
51775
  init_format_helpers();
51766
- import_jsx_runtime15 = __toESM(require_jsx_runtime());
51776
+ import_jsx_runtime15 = __toESM(require_jsx_runtime(), 1);
51767
51777
  SEVERITY_LABELS2 = {
51768
51778
  5: "CRITICAL",
51769
51779
  4: "HIGH",
@@ -51803,7 +51813,7 @@ var init_ResultsView = __esm({
51803
51813
  /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(Text, { dimColor: true, children: "\u2500".repeat(60) }),
51804
51814
  groups.map((group) => {
51805
51815
  const rep = group.packages[0];
51806
- const { label, color } = actionBadge3(rep.score);
51816
+ const { label, color } = actionBadge3(rep.action);
51807
51817
  const names = group.packages.length === 1 ? rep.name : group.packages.length <= 3 ? group.packages.map((p) => p.name).join(", ") : `${group.packages[0].name} + ${group.packages.length - 1} similar`;
51808
51818
  return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(Text, { children: [
51809
51819
  " ",
@@ -51883,8 +51893,8 @@ var init_ConfirmPrompt = __esm({
51883
51893
  "use strict";
51884
51894
  await init_build2();
51885
51895
  await init_build2();
51886
- import_chalk17 = __toESM(require_source());
51887
- import_jsx_runtime16 = __toESM(require_jsx_runtime());
51896
+ import_chalk17 = __toESM(require_source(), 1);
51897
+ import_jsx_runtime16 = __toESM(require_jsx_runtime(), 1);
51888
51898
  ConfirmPrompt = ({
51889
51899
  message,
51890
51900
  onConfirm,
@@ -51935,8 +51945,8 @@ function countSummary(result) {
51935
51945
  let warn = 0;
51936
51946
  let clean = 0;
51937
51947
  for (const p of result.packages) {
51938
- if (p.score >= 70) block++;
51939
- else if (p.score >= 60) warn++;
51948
+ if (p.action === "block") block++;
51949
+ else if (p.action === "warn") warn++;
51940
51950
  else clean++;
51941
51951
  }
51942
51952
  return { block, warn, clean };
@@ -51946,7 +51956,7 @@ var init_WrapperVerdictLine = __esm({
51946
51956
  async "src/ui/components/WrapperVerdictLine.tsx"() {
51947
51957
  "use strict";
51948
51958
  await init_build2();
51949
- import_jsx_runtime17 = __toESM(require_jsx_runtime());
51959
+ import_jsx_runtime17 = __toESM(require_jsx_runtime(), 1);
51950
51960
  WrapperVerdictLine = ({
51951
51961
  result,
51952
51962
  verdict,
@@ -52043,7 +52053,7 @@ var import_react38, import_jsx_runtime18, LABELS, WrapperApp;
52043
52053
  var init_WrapperApp = __esm({
52044
52054
  async "src/ui/apps/WrapperApp.tsx"() {
52045
52055
  "use strict";
52046
- import_react38 = __toESM(require_react());
52056
+ import_react38 = __toESM(require_react(), 1);
52047
52057
  await init_build2();
52048
52058
  init_auth();
52049
52059
  init_useWrapperBase();
@@ -52052,7 +52062,7 @@ var init_WrapperApp = __esm({
52052
52062
  await init_ConfirmPrompt();
52053
52063
  await init_ErrorView();
52054
52064
  await init_WrapperVerdictLine();
52055
- import_jsx_runtime18 = __toESM(require_jsx_runtime());
52065
+ import_jsx_runtime18 = __toESM(require_jsx_runtime(), 1);
52056
52066
  LABELS = {
52057
52067
  npm: {
52058
52068
  resolving: (n, s) => `Resolving ${n} package${s}...`,
@@ -52080,7 +52090,7 @@ var init_WrapperApp = __esm({
52080
52090
  const timer = setTimeout(() => exit(), 0);
52081
52091
  return () => clearTimeout(timer);
52082
52092
  }
52083
- if (state.phase === "trial_exhausted") {
52093
+ if (state.phase === "free_cap_reached") {
52084
52094
  process.exitCode = 1;
52085
52095
  const timer = setTimeout(() => exit(), 0);
52086
52096
  return () => clearTimeout(timer);
@@ -52123,7 +52133,7 @@ var init_WrapperApp = __esm({
52123
52133
  return /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(ErrorView, { error: new Error(state.message) });
52124
52134
  case "passthrough":
52125
52135
  return null;
52126
- case "trial_exhausted": {
52136
+ case "free_cap_reached": {
52127
52137
  let hasKey = false;
52128
52138
  try {
52129
52139
  hasKey = !!getStoredApiKey();
@@ -52215,7 +52225,7 @@ var import_chalk18, INSTALL_COMMANDS3, adapter;
52215
52225
  var init_conda_wrapper = __esm({
52216
52226
  "src/commands/conda-wrapper.ts"() {
52217
52227
  "use strict";
52218
- import_chalk18 = __toESM(require_source());
52228
+ import_chalk18 = __toESM(require_source(), 1);
52219
52229
  init_wrapper_shared();
52220
52230
  init_resolve();
52221
52231
  init_install();
@@ -53028,7 +53038,7 @@ var import_chalk19;
53028
53038
  var init_wrapper_factory = __esm({
53029
53039
  "src/commands/wrapper-factory.ts"() {
53030
53040
  "use strict";
53031
- import_chalk19 = __toESM(require_source());
53041
+ import_chalk19 = __toESM(require_source(), 1);
53032
53042
  init_client();
53033
53043
  init_resolve();
53034
53044
  init_install();
@@ -53065,253 +53075,10 @@ function closestCommand(input, commands) {
53065
53075
  return bestDist <= 3 ? best : null;
53066
53076
  }
53067
53077
 
53068
- // src/migrate.ts
53069
- init_paths();
53070
- import {
53071
- existsSync as existsSync4,
53072
- mkdirSync as mkdirSync3,
53073
- readFileSync as readFileSync4,
53074
- writeFileSync as writeFileSync3,
53075
- copyFileSync,
53076
- unlinkSync as unlinkSync3,
53077
- rmSync,
53078
- chmodSync as chmodSync3,
53079
- statSync,
53080
- openSync as openSync2,
53081
- closeSync as closeSync2,
53082
- constants as fsConstants2
53083
- } from "node:fs";
53084
- import { dirname as dirname4 } from "node:path";
53085
- var README = `dependency-guardian \u2014 local state for the dg CLI.
53086
-
53087
- config.json your account + preferences (mode 0600)
53088
- cache/update-check.json latest-version probe (24h TTL)
53089
- state/aliases.sh optional shell aliases (npm/pip wrappers)
53090
- state/auth-status.json 60s cache of /v1/auth/status
53091
- state/trial-banner throttle stamp for the trial nudge
53092
- state/bypass-log.jsonl append-only log of install-wrapper bypasses
53093
- state/hooks-installed.json registry of git hooks dg installed
53094
-
53095
- To remove everything dg has written to your machine, run:
53096
- dg uninstall
53097
-
53098
- This directory is created and managed by the dg CLI. Safe to delete.
53099
- `;
53100
- function ensureDir(path2, mode) {
53101
- if (!existsSync4(path2)) {
53102
- mkdirSync3(path2, { recursive: true, mode });
53103
- }
53104
- try {
53105
- chmodSync3(path2, mode);
53106
- } catch {
53107
- }
53108
- }
53109
- function moveFile(from, to, mode) {
53110
- const parent = dirname4(to);
53111
- ensureDir(parent, 448);
53112
- copyFileSync(from, to);
53113
- try {
53114
- chmodSync3(to, mode);
53115
- } catch {
53116
- }
53117
- if (statSync(to).size !== statSync(from).size) {
53118
- throw new Error(`size mismatch after copy: ${from} -> ${to}`);
53119
- }
53120
- unlinkSync3(from);
53121
- }
53122
- function isPidAlive(pid) {
53123
- if (!Number.isInteger(pid) || pid <= 0) return false;
53124
- try {
53125
- process.kill(pid, 0);
53126
- return true;
53127
- } catch (e) {
53128
- const code = e.code;
53129
- return code === "EPERM";
53130
- }
53131
- }
53132
- var LOCK_STALE_MS = 6e4;
53133
- function acquireLock(lockPath) {
53134
- ensureDir(dirname4(lockPath), 448);
53135
- if (existsSync4(lockPath)) {
53136
- let stale = false;
53137
- try {
53138
- const raw = readFileSync4(lockPath, "utf-8").trim();
53139
- const data = JSON.parse(raw);
53140
- const age = Date.now() - (data.at ?? 0);
53141
- const dead = !isPidAlive(data.pid ?? 0);
53142
- stale = dead || age > LOCK_STALE_MS;
53143
- } catch {
53144
- stale = true;
53145
- }
53146
- if (!stale) return "held";
53147
- try {
53148
- unlinkSync3(lockPath);
53149
- } catch {
53150
- }
53151
- }
53152
- let fd;
53153
- try {
53154
- fd = openSync2(lockPath, fsConstants2.O_CREAT | fsConstants2.O_EXCL | fsConstants2.O_WRONLY, 384);
53155
- } catch {
53156
- return "stale-held";
53157
- }
53158
- try {
53159
- writeFileSync3(lockPath, JSON.stringify({ pid: process.pid, at: Date.now() }) + "\n");
53160
- } catch {
53161
- }
53162
- return { fd, lockPath };
53163
- }
53164
- function releaseLock(state) {
53165
- if (state.fd !== null) {
53166
- try {
53167
- closeSync2(state.fd);
53168
- } catch {
53169
- }
53170
- }
53171
- try {
53172
- unlinkSync3(state.lockPath);
53173
- } catch {
53174
- }
53175
- }
53176
- function rollback(moves) {
53177
- for (const m of moves) {
53178
- try {
53179
- if (existsSync4(m.to) && !existsSync4(m.from)) {
53180
- copyFileSync(m.to, m.from);
53181
- unlinkSync3(m.to);
53182
- }
53183
- } catch {
53184
- }
53185
- }
53186
- }
53187
- function detectLegacy() {
53188
- const legacy = legacyPaths();
53189
- return existsSync4(legacy.dgrc) || existsSync4(legacy.updateCheck) || existsSync4(legacy.aliasesShOld) || existsSync4(legacy.depGuardianDir);
53190
- }
53191
- function validateLegacyConfig(path2) {
53192
- let raw;
53193
- try {
53194
- const st = statSync(path2);
53195
- if (!st.isFile()) return { ok: false, reason: "not a regular file" };
53196
- if (st.size > 1e6) return { ok: false, reason: `file too large (${st.size} bytes)` };
53197
- raw = readFileSync4(path2, "utf-8");
53198
- } catch (e) {
53199
- return { ok: false, reason: e.message };
53200
- }
53201
- let parsed;
53202
- try {
53203
- const stripped = raw.charCodeAt(0) === 65279 ? raw.slice(1) : raw;
53204
- parsed = JSON.parse(stripped);
53205
- } catch (e) {
53206
- return { ok: false, reason: `invalid JSON: ${e.message}` };
53207
- }
53208
- if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
53209
- return { ok: false, reason: "config root is not an object" };
53210
- }
53211
- return { ok: true, data: parsed };
53212
- }
53213
- function runMigrationIfNeeded() {
53214
- const p = dgPaths();
53215
- if (existsSync4(p.migrationBreadcrumb)) {
53216
- return { status: "no-op" };
53217
- }
53218
- if (!detectLegacy()) {
53219
- return { status: "no-op" };
53220
- }
53221
- ensureDir(p.root, 448);
53222
- const lock = acquireLock(p.migrationLock);
53223
- if (lock === "held" || lock === "stale-held") {
53224
- return { status: "skipped", reason: "another dg process is migrating" };
53225
- }
53226
- const legacy = legacyPaths();
53227
- const moves = [];
53228
- let movedCount = 0;
53229
- try {
53230
- if (existsSync4(legacy.dgrc)) {
53231
- const validation = validateLegacyConfig(legacy.dgrc);
53232
- if (!validation.ok) {
53233
- releaseLock(lock);
53234
- return {
53235
- status: "failed",
53236
- reason: `~/.dgrc.json could not be read (${validation.reason}). Fix or remove the file and re-run dg.`
53237
- };
53238
- }
53239
- ensureDir(p.configDir, 448);
53240
- writeFileSync3(p.config, JSON.stringify(validation.data, null, 2) + "\n", { mode: 384 });
53241
- try {
53242
- chmodSync3(p.config, 384);
53243
- } catch {
53244
- }
53245
- try {
53246
- unlinkSync3(legacy.dgrc);
53247
- } catch {
53248
- }
53249
- moves.push({ from: legacy.dgrc, to: p.config });
53250
- movedCount++;
53251
- }
53252
- ensureDir(p.cacheDir, 448);
53253
- if (existsSync4(legacy.updateCheck)) {
53254
- moveFile(legacy.updateCheck, p.updateCheck, 384);
53255
- moves.push({ from: legacy.updateCheck, to: p.updateCheck });
53256
- movedCount++;
53257
- }
53258
- ensureDir(p.stateDir, 448);
53259
- if (existsSync4(legacy.aliasesShOld)) {
53260
- moveFile(legacy.aliasesShOld, p.aliasesSh, 420);
53261
- moves.push({ from: legacy.aliasesShOld, to: p.aliasesSh });
53262
- movedCount++;
53263
- }
53264
- if (existsSync4(legacy.depGuardianDir) && legacy.depGuardianDir !== p.root) {
53265
- const candidates = [
53266
- { from: join(legacy.depGuardianDir, "config.json"), to: p.config, mode: 384 },
53267
- { from: join(legacy.depGuardianDir, "cache", "update-check.json"), to: p.updateCheck, mode: 384 },
53268
- { from: join(legacy.depGuardianDir, "state", "aliases.sh"), to: p.aliasesSh, mode: 420 },
53269
- { from: join(legacy.depGuardianDir, "state", "hooks-installed.json"), to: p.hooksRegistry, mode: 384 },
53270
- { from: join(legacy.depGuardianDir, "aliases.sh"), to: p.aliasesSh, mode: 420 }
53271
- ];
53272
- for (const c of candidates) {
53273
- if (existsSync4(c.from) && !existsSync4(c.to)) {
53274
- moveFile(c.from, c.to, c.mode);
53275
- moves.push({ from: c.from, to: c.to });
53276
- movedCount++;
53277
- }
53278
- }
53279
- try {
53280
- rmSync(legacy.depGuardianDir, { recursive: true, force: true });
53281
- } catch {
53282
- }
53283
- }
53284
- try {
53285
- if (existsSync4(legacy.cacheDir) && legacy.cacheDir !== p.root) {
53286
- rmSync(legacy.cacheDir, { recursive: true, force: true });
53287
- }
53288
- } catch {
53289
- }
53290
- try {
53291
- writeFileSync3(p.readme, README, { mode: 420 });
53292
- } catch {
53293
- }
53294
- writeFileSync3(p.migrationBreadcrumb, (/* @__PURE__ */ new Date()).toISOString() + "\n", { mode: 384 });
53295
- releaseLock(lock);
53296
- if (process.stderr.isTTY) {
53297
- process.stderr.write(
53298
- `dg: reorganized local state into ${p.root} (one-time, ${movedCount} file${movedCount === 1 ? "" : "s"}; see README inside).
53299
- `
53300
- );
53301
- }
53302
- return { status: "migrated", movedCount };
53303
- } catch (e) {
53304
- rollback(moves);
53305
- releaseLock(lock);
53306
- return { status: "failed", reason: e.message };
53307
- }
53308
- }
53309
-
53310
53078
  // src/bin.ts
53311
53079
  init_terminal_state();
53312
53080
  var CLI_VERSION = getVersion();
53313
53081
  initTelemetry(CLI_VERSION);
53314
- runMigrationIfNeeded();
53315
53082
  function setProcessTitle(title) {
53316
53083
  try {
53317
53084
  process.title = title;
@@ -53343,16 +53110,16 @@ async function maybeShowWiringHint(rawCommand) {
53343
53110
  const SKIP = /* @__PURE__ */ new Set(["uninstall", "__wrap", "version", "--version", "-v", "help", "--help", "-h"]);
53344
53111
  if (SKIP.has(rawCommand)) return;
53345
53112
  try {
53346
- const { existsSync: existsSync26 } = await import("node:fs");
53347
- const { join: join16 } = await import("node:path");
53113
+ const { existsSync: existsSync25 } = await import("node:fs");
53114
+ const { join: join15 } = await import("node:path");
53348
53115
  const { homedir: homedir9 } = await import("node:os");
53349
53116
  const { dgStatePath: dgStatePath2 } = await Promise.resolve().then(() => (init_paths(), paths_exports));
53350
- const receiptPath = join16(homedir9(), ".dg", "state", "install-receipt.json");
53351
- const shimPath = join16(homedir9(), ".dg", "shims", "npm");
53117
+ const receiptPath = join15(homedir9(), ".dg", "state", "install-receipt.json");
53118
+ const shimPath = join15(homedir9(), ".dg", "shims", "npm");
53352
53119
  const hintMarker = dgStatePath2("wiring-hint-shown");
53353
- if (existsSync26(receiptPath) || existsSync26(shimPath)) return;
53354
- if (existsSync26(hintMarker)) return;
53355
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53120
+ if (existsSync25(receiptPath) || existsSync25(shimPath)) return;
53121
+ if (existsSync25(hintMarker)) return;
53122
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53356
53123
  process.stderr.write(
53357
53124
  `
53358
53125
  ${chalk18.yellow("\u2139 Shell wiring not detected.")} Reinstall with ${chalk18.cyan("npm install -g @westbayberry/dg")}
@@ -53361,10 +53128,10 @@ async function maybeShowWiringHint(rawCommand) {
53361
53128
  `
53362
53129
  );
53363
53130
  try {
53364
- const { writeFileSync: writeFileSync16, mkdirSync: mkdirSync11 } = await import("node:fs");
53365
- const { dirname: dirname17 } = await import("node:path");
53366
- mkdirSync11(dirname17(hintMarker), { recursive: true });
53367
- writeFileSync16(hintMarker, (/* @__PURE__ */ new Date()).toISOString());
53131
+ const { writeFileSync: writeFileSync15, mkdirSync: mkdirSync10 } = await import("node:fs");
53132
+ const { dirname: dirname16 } = await import("node:path");
53133
+ mkdirSync10(dirname16(hintMarker), { recursive: true });
53134
+ writeFileSync15(hintMarker, (/* @__PURE__ */ new Date()).toISOString());
53368
53135
  } catch {
53369
53136
  }
53370
53137
  } catch {
@@ -53395,7 +53162,7 @@ async function main() {
53395
53162
  }
53396
53163
  const KNOWN_COMMANDS = ["scan", "licenses", "login", "logout", "upgrade", "status", "hook", "config", "update", "help", "version", "publish-check", "uninstall", "verify", "gallery", "confetti", "__wrap"];
53397
53164
  if (rawCommand && !rawCommand.startsWith("-") && !KNOWN_COMMANDS.includes(rawCommand)) {
53398
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53165
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53399
53166
  const best = closestCommand(rawCommand, KNOWN_COMMANDS);
53400
53167
  const hint = best ? ` Did you mean '${best}'?` : "";
53401
53168
  process.stderr.write(`
@@ -53431,7 +53198,7 @@ async function main() {
53431
53198
  const loginArgs = process.argv.slice(3);
53432
53199
  const parsed = parseLoginArgs2(loginArgs);
53433
53200
  if (parsed.kind === "unknown-flag") {
53434
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53201
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53435
53202
  process.stderr.write(`
53436
53203
  ${chalk18.red("Error:")} Unknown option '${parsed.flag}'.
53437
53204
  `);
@@ -53441,7 +53208,7 @@ async function main() {
53441
53208
  process.exit(1);
53442
53209
  }
53443
53210
  if (parsed.kind === "missing-value") {
53444
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53211
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53445
53212
  process.stderr.write(`
53446
53213
  ${chalk18.red("Error:")} ${parsed.flag} requires a value.
53447
53214
 
@@ -53454,7 +53221,7 @@ async function main() {
53454
53221
  }
53455
53222
  if (isInteractive) {
53456
53223
  const { render: render2 } = await init_build2().then(() => build_exports);
53457
- const React22 = await Promise.resolve().then(() => __toESM(require_react()));
53224
+ const React22 = await Promise.resolve().then(() => __toESM(require_react(), 1));
53458
53225
  const { LoginApp: LoginApp2 } = await init_LoginApp().then(() => LoginApp_exports);
53459
53226
  const { waitUntilExit } = render2(React22.createElement(LoginApp2));
53460
53227
  await waitUntilExit();
@@ -53498,11 +53265,11 @@ async function main() {
53498
53265
  if (v === "npm" || v === "pypi") ecosystem = v;
53499
53266
  }
53500
53267
  const { runNpmPublishCheck: runNpmPublishCheck2, runPypiPublishCheck: runPypiPublishCheck2, renderPublishCheckResult: renderPublishCheckResult2 } = await Promise.resolve().then(() => (init_publish_check(), publish_check_exports));
53501
- const { existsSync: existsSync26 } = await import("node:fs");
53502
- const { join: join16 } = await import("node:path");
53268
+ const { existsSync: existsSync25 } = await import("node:fs");
53269
+ const { join: join15 } = await import("node:path");
53503
53270
  if (ecosystem === "auto") {
53504
- if (existsSync26(join16(process.cwd(), "package.json"))) ecosystem = "npm";
53505
- else if (existsSync26(join16(process.cwd(), "pyproject.toml")) || existsSync26(join16(process.cwd(), "setup.py"))) ecosystem = "pypi";
53271
+ if (existsSync25(join15(process.cwd(), "package.json"))) ecosystem = "npm";
53272
+ else if (existsSync25(join15(process.cwd(), "pyproject.toml")) || existsSync25(join15(process.cwd(), "setup.py"))) ecosystem = "pypi";
53506
53273
  else {
53507
53274
  process.stderr.write("\n publish-check: no package.json, pyproject.toml, or setup.py in current directory.\n Pass --ecosystem npm|pypi explicitly if your project layout differs.\n\n");
53508
53275
  process.exit(3);
@@ -53513,7 +53280,7 @@ async function main() {
53513
53280
  if (wantJson) {
53514
53281
  process.stdout.write(JSON.stringify({ ok: false, error: out.errorMessage }) + "\n");
53515
53282
  } else {
53516
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53283
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53517
53284
  process.stderr.write(`
53518
53285
  ${chalk18.red("publish-check error:")} ${out.errorMessage}
53519
53286
 
@@ -53557,7 +53324,7 @@ async function main() {
53557
53324
  await handleHookCommand2(process.argv.slice(3));
53558
53325
  const updateMsg = await updatePromise2;
53559
53326
  if (updateMsg) {
53560
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53327
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53561
53328
  process.stderr.write(chalk18.dim(updateMsg));
53562
53329
  }
53563
53330
  return;
@@ -53589,7 +53356,7 @@ async function main() {
53589
53356
  }
53590
53357
  if (rawCommand === "logout") {
53591
53358
  const { getStoredApiKey: getStoredApiKey2, clearCredentials: clearCredentials2 } = await Promise.resolve().then(() => (init_auth(), auth_exports));
53592
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53359
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53593
53360
  const apiKey = getStoredApiKey2();
53594
53361
  if (apiKey) {
53595
53362
  const { parseConfig: parseConfig2 } = await Promise.resolve().then(() => (init_config(), config_exports));
@@ -53616,7 +53383,7 @@ async function main() {
53616
53383
  await preflightAuthCheck2(config.apiUrl);
53617
53384
  } catch (err) {
53618
53385
  if (err instanceof PreflightFreeCapReachedError2) {
53619
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53386
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53620
53387
  const { getStoredApiKey: getStoredApiKey2 } = await Promise.resolve().then(() => (init_auth(), auth_exports));
53621
53388
  const hasKey = !!getStoredApiKey2();
53622
53389
  process.stderr.write("\n");
@@ -53624,11 +53391,16 @@ async function main() {
53624
53391
  process.stderr.write(chalk18.yellow(" Your API key may be invalid or expired.\n"));
53625
53392
  process.stderr.write(` Run ${chalk18.cyan("dg logout")} then ${chalk18.cyan("dg login")} to re-authenticate.
53626
53393
 
53394
+ `);
53395
+ } else if (err.reason === "prefix_cap") {
53396
+ process.stderr.write(chalk18.yellow(" Too many anonymous devices from your network this month (anti-abuse limit).\n"));
53397
+ process.stderr.write(` Sign in with ${chalk18.cyan("dg login")} to keep scanning.
53398
+
53627
53399
  `);
53628
53400
  } else {
53629
- process.stderr.write(chalk18.yellow(` Free tier monthly cap reached (${err.scansUsed}/${err.maxScans}).
53401
+ process.stderr.write(chalk18.yellow(` Free tier monthly package limit reached (${err.scansUsed.toLocaleString()}/${err.maxScans.toLocaleString()} packages).
53630
53402
  `));
53631
- process.stderr.write(` Run ${chalk18.cyan("dg upgrade")} for Pro (5000/mo) or wait until next month.
53403
+ process.stderr.write(` Run ${chalk18.cyan("dg upgrade")} for Pro or wait until next month.
53632
53404
 
53633
53405
  `);
53634
53406
  }
@@ -53643,13 +53415,13 @@ async function main() {
53643
53415
  await runStatic2(config);
53644
53416
  } else {
53645
53417
  if (config.mode === "off") {
53646
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53418
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53647
53419
  process.stderr.write(chalk18.dim(" Dependency Guardian: mode is off \u2014 skipping.\n"));
53648
53420
  process.exit(0);
53649
53421
  }
53650
53422
  const { getStoredApiKey: getStoredApiKey2 } = await Promise.resolve().then(() => (init_auth(), auth_exports));
53651
53423
  const apiKey = getStoredApiKey2();
53652
- const chalkMod = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53424
+ const chalkMod = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53653
53425
  const loginChip = chalkMod.cyan.bold("dg login");
53654
53426
  const freeTierStatus = `${chalkMod.dim("free tier \xB7")} ${loginChip} ${chalkMod.dim("for more")}`;
53655
53427
  const sessionExpiredStatus = `${chalkMod.dim("session expired \xB7")} ${loginChip}`;
@@ -53667,14 +53439,12 @@ async function main() {
53667
53439
  const tier = data.tier || "free";
53668
53440
  const tierColor = tier === "free" ? chalkMod.yellow(tier) : chalkMod.green(tier);
53669
53441
  userStatus = `${chalkMod.dim(name)} ${chalkMod.dim("\xB7")} ${tierColor}`;
53670
- if (data.scansLimit === null || data.scansLimit === void 0) {
53671
- scanUsage = "unlimited scans";
53672
- } else {
53673
- const used = data.scansUsed ?? 0;
53674
- const limit = data.scansLimit;
53675
- const remaining = limit - used;
53676
- scanUsage = `${remaining}/${limit} scans left`;
53677
- }
53442
+ const { formatUsage: formatUsage2 } = await Promise.resolve().then(() => (init_format_helpers(), format_helpers_exports));
53443
+ scanUsage = formatUsage2({
53444
+ used: data.scansUsed ?? 0,
53445
+ limit: data.scansLimit ?? null,
53446
+ tier
53447
+ }).text;
53678
53448
  } else if (resp.status === 401) {
53679
53449
  userStatus = sessionExpiredStatus;
53680
53450
  } else {
@@ -53687,7 +53457,7 @@ async function main() {
53687
53457
  const { getSetupIssues: getSetupIssues2 } = await Promise.resolve().then(() => (init_setup_status(), setup_status_exports));
53688
53458
  const setupIssues = getSetupIssues2(process.cwd());
53689
53459
  const { render: render2 } = await init_build2().then(() => build_exports);
53690
- const React22 = await Promise.resolve().then(() => __toESM(require_react()));
53460
+ const React22 = await Promise.resolve().then(() => __toESM(require_react(), 1));
53691
53461
  const { App: App3 } = await init_App2().then(() => App_exports);
53692
53462
  const { setInkInstance: setInkInstance2, resetInkClear: resetInkClear2, initInkInstances: initInkInstances2, patchInkLogForAbsolutePositioning: patchInkLogForAbsolutePositioning2 } = await Promise.resolve().then(() => (init_ink_controls(), ink_controls_exports));
53693
53463
  await initInkInstances2();
@@ -53702,7 +53472,7 @@ async function main() {
53702
53472
  }
53703
53473
  const updateMsg = await updatePromise;
53704
53474
  if (updateMsg) {
53705
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53475
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53706
53476
  process.stderr.write(chalk18.dim(updateMsg));
53707
53477
  }
53708
53478
  try {
@@ -53778,7 +53548,7 @@ async function handleWrapInternal(argv) {
53778
53548
  return 0;
53779
53549
  }
53780
53550
  const { render: render2 } = await init_build2().then(() => build_exports);
53781
- const React22 = await Promise.resolve().then(() => __toESM(require_react()));
53551
+ const React22 = await Promise.resolve().then(() => __toESM(require_react(), 1));
53782
53552
  const { WrapperApp: WrapperApp2 } = await init_WrapperApp().then(() => WrapperApp_exports);
53783
53553
  const { waitUntilExit } = render2(
53784
53554
  React22.createElement(WrapperApp2, { config, args: wrapperArgs, ecosystem: "npm" })
@@ -53793,7 +53563,7 @@ async function handleWrapInternal(argv) {
53793
53563
  return 0;
53794
53564
  }
53795
53565
  const { render: render2 } = await init_build2().then(() => build_exports);
53796
- const React22 = await Promise.resolve().then(() => __toESM(require_react()));
53566
+ const React22 = await Promise.resolve().then(() => __toESM(require_react(), 1));
53797
53567
  const { WrapperApp: WrapperApp2 } = await init_WrapperApp().then(() => WrapperApp_exports);
53798
53568
  const { waitUntilExit } = render2(
53799
53569
  React22.createElement(WrapperApp2, { config, args: wrapperArgs, ecosystem: "pypi" })
@@ -53838,7 +53608,7 @@ main().catch(async (err) => {
53838
53608
  authenticated: isAuthed
53839
53609
  });
53840
53610
  await flush();
53841
- const chalk18 = (await Promise.resolve().then(() => __toESM(require_source()))).default;
53611
+ const chalk18 = (await Promise.resolve().then(() => __toESM(require_source(), 1))).default;
53842
53612
  const color = err.securityRelease ? chalk18.bold.red : chalk18.yellow;
53843
53613
  if (process.argv.includes("--json")) {
53844
53614
  process.stdout.write(JSON.stringify({
@@ -53876,7 +53646,7 @@ main().catch(async (err) => {
53876
53646
  }, null, 2) + "\n");
53877
53647
  } else {
53878
53648
  try {
53879
- const chalkMod = await Promise.resolve().then(() => __toESM(require_source()));
53649
+ const chalkMod = await Promise.resolve().then(() => __toESM(require_source(), 1));
53880
53650
  process.stderr.write(`
53881
53651
  ${chalkMod.default.bold.red("Error:")} ${err.message}
53882
53652