@saptools/cf-inspector 0.9.0 → 0.9.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.js CHANGED
@@ -1298,6 +1298,20 @@ function registerSelfUpdateCommand(program, options) {
1298
1298
  });
1299
1299
  }
1300
1300
 
1301
+ // ../core/src/cloud-logging/instance-discovery.ts
1302
+ var INSTANCE_LISTING_FIELDS = `&${encodeURIComponent("fields[service_plan]")}=guid,name,relationships.service_offering&${encodeURIComponent("fields[service_plan.service_offering]")}=guid,name`;
1303
+
1304
+ // ../core/src/cloud-logging/credential-cache.ts
1305
+ import { readdir, rm } from "fs/promises";
1306
+ import { dirname as dirname5, join as join7 } from "path";
1307
+
1308
+ // ../core/src/cloud-logging/result-store.ts
1309
+ import { randomBytes } from "crypto";
1310
+ import { mkdir, readdir as readdir2, readFile, rename, rm as rm2, stat, unlink, writeFile } from "fs/promises";
1311
+ import { join as join8 } from "path";
1312
+ var DEFAULT_MAX_BYTES = 256 * 1024 * 1024;
1313
+ var STRANDED_AGE_MS = 24 * 60 * 60 * 1e3;
1314
+
1301
1315
  // src/cli/program.ts
1302
1316
  import { Command } from "commander";
1303
1317
 
@@ -2931,9 +2945,9 @@ init_types();
2931
2945
  import { execFileSync } from "child_process";
2932
2946
  import { createHash, randomUUID } from "crypto";
2933
2947
  import { constants as constants3 } from "fs";
2934
- import { mkdir, open, readFile, readdir, stat, unlink, writeFile } from "fs/promises";
2948
+ import { mkdir as mkdir2, open, readFile as readFile2, readdir as readdir3, stat as stat2, unlink as unlink2, writeFile as writeFile2 } from "fs/promises";
2935
2949
  import { homedir as homedir3 } from "os";
2936
- import { join as join7 } from "path";
2950
+ import { join as join9 } from "path";
2937
2951
  var ELECTION_WINDOW_MS = 25;
2938
2952
  var LOCK_FILE_SUFFIX = ".lock";
2939
2953
  async function acquireDebugSessionLock(target, options = {}) {
@@ -2945,8 +2959,8 @@ async function acquireDebugSessionLock(target, options = {}) {
2945
2959
  const targetIdentity = debugTargetIdentity(target);
2946
2960
  const key = createHash("sha256").update(targetIdentity).digest("hex");
2947
2961
  const lockRoot = options.stateRoot ?? defaultStateRoot();
2948
- const lockDirectory = join7(lockRoot, "cf-inspector", "locks");
2949
- const ownPath = join7(lockDirectory, `${key}.${pid.toString()}.${token}${LOCK_FILE_SUFFIX}`);
2962
+ const lockDirectory = join9(lockRoot, "cf-inspector", "locks");
2963
+ const ownPath = join9(lockDirectory, `${key}.${pid.toString()}.${token}${LOCK_FILE_SUFFIX}`);
2950
2964
  const metadata = {
2951
2965
  pid,
2952
2966
  ...ownerProcessStart === void 0 ? {} : { processStart: ownerProcessStart },
@@ -2955,7 +2969,7 @@ async function acquireDebugSessionLock(target, options = {}) {
2955
2969
  token,
2956
2970
  target: targetIdentity
2957
2971
  };
2958
- await mkdir(lockDirectory, { recursive: true, mode: 448 });
2972
+ await mkdir2(lockDirectory, { recursive: true, mode: 448 });
2959
2973
  const handle = await open(ownPath, constants3.O_CREAT | constants3.O_EXCL | constants3.O_WRONLY, 384);
2960
2974
  try {
2961
2975
  await handle.writeFile(`${JSON.stringify(metadata)}
@@ -2980,7 +2994,7 @@ async function acquireDebugSessionLock(target, options = {}) {
2980
2994
  }
2981
2995
  await writeLockMetadata(ownPath, { ...metadata, state: "owned" });
2982
2996
  } catch (error) {
2983
- await unlink(ownPath).catch(() => {
2997
+ await unlink2(ownPath).catch(() => {
2984
2998
  });
2985
2999
  throw error;
2986
3000
  }
@@ -2996,7 +3010,7 @@ async function acquireDebugSessionLock(target, options = {}) {
2996
3010
  if (current?.token !== token || current.pid !== pid) {
2997
3011
  return;
2998
3012
  }
2999
- await unlink(ownPath).catch((error) => {
3013
+ await unlink2(ownPath).catch((error) => {
3000
3014
  if (!isNodeError(error, "ENOENT")) {
3001
3015
  throw error;
3002
3016
  }
@@ -3025,28 +3039,28 @@ function debugTargetIdentity(target) {
3025
3039
  }
3026
3040
  function defaultStateRoot() {
3027
3041
  const configured = process.env["CF_INSPECTOR_STATE_DIR"]?.trim();
3028
- return configured === void 0 || configured.length === 0 ? join7(homedir3(), ".saptools") : configured;
3042
+ return configured === void 0 || configured.length === 0 ? join9(homedir3(), ".saptools") : configured;
3029
3043
  }
3030
3044
  async function findLiveContenders(lockDirectory, key, ownPath, isProcessAlive, getProcessStart) {
3031
3045
  const prefix = `${key}.`;
3032
- const names = await readdir(lockDirectory);
3046
+ const names = await readdir3(lockDirectory);
3033
3047
  const contenders = [];
3034
3048
  for (const name of names) {
3035
3049
  if (!name.startsWith(prefix) || !name.endsWith(LOCK_FILE_SUFFIX)) {
3036
3050
  continue;
3037
3051
  }
3038
- const path = join7(lockDirectory, name);
3052
+ const path = join9(lockDirectory, name);
3039
3053
  if (path === ownPath) {
3040
3054
  continue;
3041
3055
  }
3042
- const info = await stat(path).catch(() => {
3056
+ const info = await stat2(path).catch(() => {
3043
3057
  });
3044
3058
  const metadata = await readLockMetadata(path) ?? (info === void 0 ? void 0 : metadataFromFilename(name, key, info.mtimeMs));
3045
3059
  if (metadata !== void 0) {
3046
3060
  if (ownerIsAlive(metadata, isProcessAlive, getProcessStart)) {
3047
3061
  contenders.push(metadata);
3048
3062
  } else {
3049
- await unlink(path).catch(() => {
3063
+ await unlink2(path).catch(() => {
3050
3064
  });
3051
3065
  }
3052
3066
  continue;
@@ -3065,7 +3079,7 @@ async function findLiveContenders(lockDirectory, key, ownPath, isProcessAlive, g
3065
3079
  }
3066
3080
  async function readLockMetadata(path) {
3067
3081
  try {
3068
- const parsed = JSON.parse(await readFile(path, "utf8"));
3082
+ const parsed = JSON.parse(await readFile2(path, "utf8"));
3069
3083
  if (!isRecord3(parsed)) {
3070
3084
  return void 0;
3071
3085
  }
@@ -3091,7 +3105,7 @@ async function readLockMetadata(path) {
3091
3105
  }
3092
3106
  }
3093
3107
  async function writeLockMetadata(path, metadata) {
3094
- await writeFile(path, `${JSON.stringify(metadata)}
3108
+ await writeFile2(path, `${JSON.stringify(metadata)}
3095
3109
  `, { encoding: "utf8", mode: 384 });
3096
3110
  }
3097
3111
  function metadataFromFilename(name, key, mtimeMs) {
@@ -3408,7 +3422,7 @@ function parsePositiveInt(raw, label) {
3408
3422
  }
3409
3423
  return value;
3410
3424
  }
3411
- function resolveTarget(opts, options = {}) {
3425
+ function resolveTarget2(opts, options = {}) {
3412
3426
  const port = parsePositiveInt(opts.port, "--port");
3413
3427
  const targetIndex = parseTargetIndex(opts.target);
3414
3428
  const workerIndex = parseSelectionIndex(opts.worker, "--worker");
@@ -3453,7 +3467,7 @@ function resolveTarget(opts, options = {}) {
3453
3467
  );
3454
3468
  }
3455
3469
  async function resolveTargetWithCurrentCfTarget(opts, options = {}) {
3456
- return await Promise.resolve(resolveTarget(opts, options));
3470
+ return await Promise.resolve(resolveTarget2(opts, options));
3457
3471
  }
3458
3472
  function parseTunnelTimeout(opts, options) {
3459
3473
  if (options.useTimeoutForTunnel === false) {
@@ -3679,6 +3693,22 @@ init_types();
3679
3693
  var REGEX_PREFIX = "regex:";
3680
3694
  var REGEX_FLAGS_PATTERN = /^[dgimsuvy]*$/;
3681
3695
  var TS_JS_EXT_PATTERN = /\.(?:ts|js|mts|mjs|cts|cjs)$/i;
3696
+ var MAX_REMOTE_ROOT_PATTERN_LENGTH = 200;
3697
+ var NESTED_QUANTIFIER_PATTERN = /\([^()]*[+*][^()]*\)[+*]/;
3698
+ function assertSafeRemoteRootPattern(pattern) {
3699
+ if (pattern.length > MAX_REMOTE_ROOT_PATTERN_LENGTH) {
3700
+ throw new CfInspectorError(
3701
+ "INVALID_REMOTE_ROOT",
3702
+ `--remote-root regex pattern is too long (${pattern.length.toString()} chars, max ${MAX_REMOTE_ROOT_PATTERN_LENGTH.toString()}) \u2014 this bounds worst-case backtracking cost`
3703
+ );
3704
+ }
3705
+ if (NESTED_QUANTIFIER_PATTERN.test(pattern)) {
3706
+ throw new CfInspectorError(
3707
+ "INVALID_REMOTE_ROOT",
3708
+ `--remote-root regex pattern "${pattern}" contains a nested quantifier (e.g. "(x+)+"), which can cause catastrophic backtracking \u2014 simplify the pattern`
3709
+ );
3710
+ }
3711
+ }
3682
3712
  function parseBreakpointSpec(input) {
3683
3713
  const idx = input.lastIndexOf(":");
3684
3714
  if (idx <= 0 || idx === input.length - 1) {
@@ -3719,6 +3749,7 @@ function parseRemoteRoot(value) {
3719
3749
  return { kind: "literal", value: stripTrailingSlash(trimmed) };
3720
3750
  }
3721
3751
  function toRegex(pattern, flags) {
3752
+ assertSafeRemoteRootPattern(pattern);
3722
3753
  return { kind: "regex", pattern, flags };
3723
3754
  }
3724
3755
  function parseSlashDelimited(value) {
@@ -5595,7 +5626,7 @@ import process10 from "process";
5595
5626
  init_types();
5596
5627
 
5597
5628
  // src/logpoint/condition.ts
5598
- import { randomBytes } from "crypto";
5629
+ import { randomBytes as randomBytes2 } from "crypto";
5599
5630
  var SENTINEL_PREFIX = "__CFI_LOG_";
5600
5631
  var SENTINEL_SUFFIX = "__";
5601
5632
  var HITS_GLOBAL2 = "globalThis.__CFI_LOG_HITS";
@@ -5653,7 +5684,7 @@ function buildLogpointCondition(sentinel, expression, options = {}) {
5653
5684
  return `(${guard})?${iife}:false`;
5654
5685
  }
5655
5686
  function generateSentinel() {
5656
- return `${SENTINEL_PREFIX}${randomBytes(8).toString("hex")}${SENTINEL_SUFFIX}`;
5687
+ return `${SENTINEL_PREFIX}${randomBytes2(8).toString("hex")}${SENTINEL_SUFFIX}`;
5657
5688
  }
5658
5689
 
5659
5690
  // src/logpoint/events.ts