@suss/adapter-typescript 0.5.8 → 0.5.9

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/index.cjs CHANGED
@@ -4954,7 +4954,7 @@ function indexFunctions(sf) {
4954
4954
  var import_node_crypto2 = require("crypto");
4955
4955
  var import_promises2 = __toESM(require("fs/promises"), 1);
4956
4956
  var import_node_path2 = __toESM(require("path"), 1);
4957
- var SCHEMA_VERSION = "4";
4957
+ var SCHEMA_VERSION = "5";
4958
4958
  var MAX_ENTRIES = 2;
4959
4959
  var ENTRY_PREFIX = "key-";
4960
4960
  var ENTRY_DIR_NAME = new RegExp(`^${ENTRY_PREFIX}[0-9a-f]{16}$`);
@@ -5248,15 +5248,19 @@ function unwrapContractInit(init) {
5248
5248
  if (init === void 0) {
5249
5249
  return null;
5250
5250
  }
5251
- if (import_ts_morph25.Node.isCallExpression(init)) {
5252
- const args = init.getArguments();
5251
+ let node = init;
5252
+ while (import_ts_morph25.Node.isAsExpression(node)) {
5253
+ node = node.getExpression();
5254
+ }
5255
+ if (import_ts_morph25.Node.isCallExpression(node)) {
5256
+ const args = node.getArguments();
5253
5257
  if (args.length > 0 && import_ts_morph25.Node.isObjectLiteralExpression(args[0])) {
5254
5258
  return args[0];
5255
5259
  }
5256
5260
  return null;
5257
5261
  }
5258
- if (import_ts_morph25.Node.isObjectLiteralExpression(init)) {
5259
- return init;
5262
+ if (import_ts_morph25.Node.isObjectLiteralExpression(node)) {
5263
+ return node;
5260
5264
  }
5261
5265
  return null;
5262
5266
  }
@@ -5317,6 +5321,16 @@ function extractEndpointContract(endpointNode, pattern, framework) {
5317
5321
  };
5318
5322
  }
5319
5323
  function readContract(unit, pattern, framework) {
5324
+ if (pattern.endpoint?.from === "registrationArgument") {
5325
+ const endpointNode = endpointFromRegistrationArgument(
5326
+ unit,
5327
+ pattern.endpoint.position
5328
+ );
5329
+ if (endpointNode === null) {
5330
+ return null;
5331
+ }
5332
+ return extractEndpointContract(endpointNode, pattern, framework);
5333
+ }
5320
5334
  const routerInfo = findRouterCall(unit);
5321
5335
  if (routerInfo === null) {
5322
5336
  return null;
@@ -5340,6 +5354,35 @@ function readContract(unit, pattern, framework) {
5340
5354
  }
5341
5355
  return null;
5342
5356
  }
5357
+ function endpointFromRegistrationArgument(unit, position) {
5358
+ const func = unit.func;
5359
+ if (func === null) {
5360
+ return null;
5361
+ }
5362
+ const call = func.getParent();
5363
+ if (call === void 0 || !import_ts_morph25.Node.isCallExpression(call)) {
5364
+ return null;
5365
+ }
5366
+ const args = call.getArguments();
5367
+ if (!args.includes(func)) {
5368
+ return null;
5369
+ }
5370
+ const arg = args[position];
5371
+ if (arg === void 0 || arg === func) {
5372
+ return null;
5373
+ }
5374
+ let node = arg;
5375
+ while (import_ts_morph25.Node.isAsExpression(node)) {
5376
+ node = node.getExpression();
5377
+ }
5378
+ if (import_ts_morph25.Node.isObjectLiteralExpression(node)) {
5379
+ return node;
5380
+ }
5381
+ if (import_ts_morph25.Node.isCallExpression(node)) {
5382
+ return unwrapContractInit(node);
5383
+ }
5384
+ return resolveContractObject(node);
5385
+ }
5343
5386
  function readContractForClientCall(callExpression, methodName, pattern, framework) {
5344
5387
  const callee = import_ts_morph25.Node.isCallExpression(callExpression) ? callExpression.getExpression() : null;
5345
5388
  if (callee === null || !import_ts_morph25.Node.isPropertyAccessExpression(callee)) {
@@ -27288,6 +27331,12 @@ function extractFromSourceFile(sourceFile, frameworks, claimedUnits, options, ta
27288
27331
  }
27289
27332
  }
27290
27333
  }
27334
+ if (raw.declaredContract === null && pack.contractReading?.endpoint?.from === "registrationArgument") {
27335
+ const contract = readContract(unit, pack.contractReading, pack.name);
27336
+ if (contract !== null) {
27337
+ raw.declaredContract = contract.declaredContract;
27338
+ }
27339
+ }
27291
27340
  if (raw.boundaryBinding === null) {
27292
27341
  if (unit.packageExportInfo !== void 0) {
27293
27342
  raw.boundaryBinding = (0, import_behavioral_ir5.packageExportBinding)({
@@ -27332,6 +27381,92 @@ function extractFromSourceFile(sourceFile, frameworks, claimedUnits, options, ta
27332
27381
  }
27333
27382
  return summaries;
27334
27383
  }
27384
+ function stampModuleImports(summaries, project) {
27385
+ const byFile2 = /* @__PURE__ */ new Map();
27386
+ for (const summary of summaries) {
27387
+ const file2 = summary.location.file;
27388
+ let imports = byFile2.get(file2);
27389
+ if (imports === void 0) {
27390
+ imports = internalImportsOf(project, file2);
27391
+ byFile2.set(file2, imports);
27392
+ }
27393
+ if (imports.length === 0) {
27394
+ continue;
27395
+ }
27396
+ summary.metadata = {
27397
+ ...summary.metadata ?? {},
27398
+ moduleImports: imports
27399
+ };
27400
+ }
27401
+ }
27402
+ function emitLibraryEnvReadMarkers(summaries, project, frameworks) {
27403
+ for (const pack of frameworks) {
27404
+ for (const declared of pack.libraryEnvVars ?? []) {
27405
+ const importer = fileImporting(project, declared.module);
27406
+ if (importer === void 0) {
27407
+ continue;
27408
+ }
27409
+ summaries.push(libraryEnvReadMarker(pack, declared, importer));
27410
+ }
27411
+ }
27412
+ }
27413
+ function fileImporting(project, modulePrefix) {
27414
+ for (const sourceFile of project.getSourceFiles()) {
27415
+ if (sourceFile.isInNodeModules() || sourceFile.isDeclarationFile()) {
27416
+ continue;
27417
+ }
27418
+ for (const imp of sourceFile.getImportDeclarations()) {
27419
+ if (imp.getModuleSpecifierValue().startsWith(modulePrefix)) {
27420
+ return sourceFile.getFilePath();
27421
+ }
27422
+ }
27423
+ }
27424
+ return void 0;
27425
+ }
27426
+ function libraryEnvReadMarker(pack, declared, importer) {
27427
+ return {
27428
+ kind: "library",
27429
+ location: { file: importer, range: { start: 0, end: 0 }, exportName: null },
27430
+ identity: {
27431
+ name: `${declared.module} env reads`,
27432
+ exportPath: null,
27433
+ boundaryBinding: (0, import_behavioral_ir5.functionCallBinding)({
27434
+ transport: "in-process",
27435
+ recognition: pack.name
27436
+ })
27437
+ },
27438
+ inputs: [],
27439
+ transitions: [],
27440
+ gaps: [],
27441
+ confidence: { source: "declared", level: "high" },
27442
+ metadata: {
27443
+ libraryEnvReads: {
27444
+ module: declared.module,
27445
+ ...declared.prefixes !== void 0 ? { prefixes: declared.prefixes } : {},
27446
+ ...declared.names !== void 0 ? { names: declared.names } : {}
27447
+ }
27448
+ }
27449
+ };
27450
+ }
27451
+ function internalImportsOf(project, file2) {
27452
+ const sourceFile = project.getSourceFile(file2);
27453
+ if (sourceFile === void 0) {
27454
+ return [];
27455
+ }
27456
+ const targets = /* @__PURE__ */ new Set();
27457
+ const record2 = (target) => {
27458
+ if (target !== void 0 && !target.isInNodeModules() && !target.isDeclarationFile()) {
27459
+ targets.add(target.getFilePath());
27460
+ }
27461
+ };
27462
+ for (const imp of sourceFile.getImportDeclarations()) {
27463
+ record2(imp.getModuleSpecifierSourceFile());
27464
+ }
27465
+ for (const exp of sourceFile.getExportDeclarations()) {
27466
+ record2(exp.getModuleSpecifierSourceFile());
27467
+ }
27468
+ return [...targets].sort();
27469
+ }
27335
27470
  function expandWrapperCallers(summaries, project, options) {
27336
27471
  const wrappers = [];
27337
27472
  let lookup = null;
@@ -27742,6 +27877,14 @@ function createTypeScriptAdapter(config2) {
27742
27877
  () => deriveBoundaryEffects(enriched, closureFacts)
27743
27878
  );
27744
27879
  }
27880
+ timer.time(
27881
+ "stampModuleImports",
27882
+ () => stampModuleImports(enriched, project)
27883
+ );
27884
+ timer.time(
27885
+ "emitLibraryEnvReadMarkers",
27886
+ () => emitLibraryEnvReadMarkers(enriched, project, config2.frameworks)
27887
+ );
27745
27888
  await timer.timeAsync("cache.write", async () => {
27746
27889
  if (enriched.length === 0) {
27747
27890
  return;
package/dist/index.js CHANGED
@@ -4931,7 +4931,7 @@ function indexFunctions(sf) {
4931
4931
  import { createHash as createHash2 } from "crypto";
4932
4932
  import fs2 from "fs/promises";
4933
4933
  import path2 from "path";
4934
- var SCHEMA_VERSION = "4";
4934
+ var SCHEMA_VERSION = "5";
4935
4935
  var MAX_ENTRIES = 2;
4936
4936
  var ENTRY_PREFIX = "key-";
4937
4937
  var ENTRY_DIR_NAME = new RegExp(`^${ENTRY_PREFIX}[0-9a-f]{16}$`);
@@ -5225,15 +5225,19 @@ function unwrapContractInit(init) {
5225
5225
  if (init === void 0) {
5226
5226
  return null;
5227
5227
  }
5228
- if (Node24.isCallExpression(init)) {
5229
- const args = init.getArguments();
5228
+ let node = init;
5229
+ while (Node24.isAsExpression(node)) {
5230
+ node = node.getExpression();
5231
+ }
5232
+ if (Node24.isCallExpression(node)) {
5233
+ const args = node.getArguments();
5230
5234
  if (args.length > 0 && Node24.isObjectLiteralExpression(args[0])) {
5231
5235
  return args[0];
5232
5236
  }
5233
5237
  return null;
5234
5238
  }
5235
- if (Node24.isObjectLiteralExpression(init)) {
5236
- return init;
5239
+ if (Node24.isObjectLiteralExpression(node)) {
5240
+ return node;
5237
5241
  }
5238
5242
  return null;
5239
5243
  }
@@ -5294,6 +5298,16 @@ function extractEndpointContract(endpointNode, pattern, framework) {
5294
5298
  };
5295
5299
  }
5296
5300
  function readContract(unit, pattern, framework) {
5301
+ if (pattern.endpoint?.from === "registrationArgument") {
5302
+ const endpointNode = endpointFromRegistrationArgument(
5303
+ unit,
5304
+ pattern.endpoint.position
5305
+ );
5306
+ if (endpointNode === null) {
5307
+ return null;
5308
+ }
5309
+ return extractEndpointContract(endpointNode, pattern, framework);
5310
+ }
5297
5311
  const routerInfo = findRouterCall(unit);
5298
5312
  if (routerInfo === null) {
5299
5313
  return null;
@@ -5317,6 +5331,35 @@ function readContract(unit, pattern, framework) {
5317
5331
  }
5318
5332
  return null;
5319
5333
  }
5334
+ function endpointFromRegistrationArgument(unit, position) {
5335
+ const func = unit.func;
5336
+ if (func === null) {
5337
+ return null;
5338
+ }
5339
+ const call = func.getParent();
5340
+ if (call === void 0 || !Node24.isCallExpression(call)) {
5341
+ return null;
5342
+ }
5343
+ const args = call.getArguments();
5344
+ if (!args.includes(func)) {
5345
+ return null;
5346
+ }
5347
+ const arg = args[position];
5348
+ if (arg === void 0 || arg === func) {
5349
+ return null;
5350
+ }
5351
+ let node = arg;
5352
+ while (Node24.isAsExpression(node)) {
5353
+ node = node.getExpression();
5354
+ }
5355
+ if (Node24.isObjectLiteralExpression(node)) {
5356
+ return node;
5357
+ }
5358
+ if (Node24.isCallExpression(node)) {
5359
+ return unwrapContractInit(node);
5360
+ }
5361
+ return resolveContractObject(node);
5362
+ }
5320
5363
  function readContractForClientCall(callExpression, methodName, pattern, framework) {
5321
5364
  const callee = Node24.isCallExpression(callExpression) ? callExpression.getExpression() : null;
5322
5365
  if (callee === null || !Node24.isPropertyAccessExpression(callee)) {
@@ -27294,6 +27337,12 @@ function extractFromSourceFile(sourceFile, frameworks, claimedUnits, options, ta
27294
27337
  }
27295
27338
  }
27296
27339
  }
27340
+ if (raw.declaredContract === null && pack.contractReading?.endpoint?.from === "registrationArgument") {
27341
+ const contract = readContract(unit, pack.contractReading, pack.name);
27342
+ if (contract !== null) {
27343
+ raw.declaredContract = contract.declaredContract;
27344
+ }
27345
+ }
27297
27346
  if (raw.boundaryBinding === null) {
27298
27347
  if (unit.packageExportInfo !== void 0) {
27299
27348
  raw.boundaryBinding = packageExportBinding({
@@ -27338,6 +27387,92 @@ function extractFromSourceFile(sourceFile, frameworks, claimedUnits, options, ta
27338
27387
  }
27339
27388
  return summaries;
27340
27389
  }
27390
+ function stampModuleImports(summaries, project) {
27391
+ const byFile2 = /* @__PURE__ */ new Map();
27392
+ for (const summary of summaries) {
27393
+ const file2 = summary.location.file;
27394
+ let imports = byFile2.get(file2);
27395
+ if (imports === void 0) {
27396
+ imports = internalImportsOf(project, file2);
27397
+ byFile2.set(file2, imports);
27398
+ }
27399
+ if (imports.length === 0) {
27400
+ continue;
27401
+ }
27402
+ summary.metadata = {
27403
+ ...summary.metadata ?? {},
27404
+ moduleImports: imports
27405
+ };
27406
+ }
27407
+ }
27408
+ function emitLibraryEnvReadMarkers(summaries, project, frameworks) {
27409
+ for (const pack of frameworks) {
27410
+ for (const declared of pack.libraryEnvVars ?? []) {
27411
+ const importer = fileImporting(project, declared.module);
27412
+ if (importer === void 0) {
27413
+ continue;
27414
+ }
27415
+ summaries.push(libraryEnvReadMarker(pack, declared, importer));
27416
+ }
27417
+ }
27418
+ }
27419
+ function fileImporting(project, modulePrefix) {
27420
+ for (const sourceFile of project.getSourceFiles()) {
27421
+ if (sourceFile.isInNodeModules() || sourceFile.isDeclarationFile()) {
27422
+ continue;
27423
+ }
27424
+ for (const imp of sourceFile.getImportDeclarations()) {
27425
+ if (imp.getModuleSpecifierValue().startsWith(modulePrefix)) {
27426
+ return sourceFile.getFilePath();
27427
+ }
27428
+ }
27429
+ }
27430
+ return void 0;
27431
+ }
27432
+ function libraryEnvReadMarker(pack, declared, importer) {
27433
+ return {
27434
+ kind: "library",
27435
+ location: { file: importer, range: { start: 0, end: 0 }, exportName: null },
27436
+ identity: {
27437
+ name: `${declared.module} env reads`,
27438
+ exportPath: null,
27439
+ boundaryBinding: functionCallBinding2({
27440
+ transport: "in-process",
27441
+ recognition: pack.name
27442
+ })
27443
+ },
27444
+ inputs: [],
27445
+ transitions: [],
27446
+ gaps: [],
27447
+ confidence: { source: "declared", level: "high" },
27448
+ metadata: {
27449
+ libraryEnvReads: {
27450
+ module: declared.module,
27451
+ ...declared.prefixes !== void 0 ? { prefixes: declared.prefixes } : {},
27452
+ ...declared.names !== void 0 ? { names: declared.names } : {}
27453
+ }
27454
+ }
27455
+ };
27456
+ }
27457
+ function internalImportsOf(project, file2) {
27458
+ const sourceFile = project.getSourceFile(file2);
27459
+ if (sourceFile === void 0) {
27460
+ return [];
27461
+ }
27462
+ const targets = /* @__PURE__ */ new Set();
27463
+ const record2 = (target) => {
27464
+ if (target !== void 0 && !target.isInNodeModules() && !target.isDeclarationFile()) {
27465
+ targets.add(target.getFilePath());
27466
+ }
27467
+ };
27468
+ for (const imp of sourceFile.getImportDeclarations()) {
27469
+ record2(imp.getModuleSpecifierSourceFile());
27470
+ }
27471
+ for (const exp of sourceFile.getExportDeclarations()) {
27472
+ record2(exp.getModuleSpecifierSourceFile());
27473
+ }
27474
+ return [...targets].sort();
27475
+ }
27341
27476
  function expandWrapperCallers(summaries, project, options) {
27342
27477
  const wrappers = [];
27343
27478
  let lookup = null;
@@ -27748,6 +27883,14 @@ function createTypeScriptAdapter(config2) {
27748
27883
  () => deriveBoundaryEffects(enriched, closureFacts)
27749
27884
  );
27750
27885
  }
27886
+ timer.time(
27887
+ "stampModuleImports",
27888
+ () => stampModuleImports(enriched, project)
27889
+ );
27890
+ timer.time(
27891
+ "emitLibraryEnvReadMarkers",
27892
+ () => emitLibraryEnvReadMarkers(enriched, project, config2.frameworks)
27893
+ );
27751
27894
  await timer.timeAsync("cache.write", async () => {
27752
27895
  if (enriched.length === 0) {
27753
27896
  return;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@suss/adapter-typescript",
3
- "version": "0.5.8",
3
+ "version": "0.5.9",
4
4
  "type": "module",
5
5
  "description": "TypeScript adapter for suss — walks source files with ts-morph and emits raw extractions for the suss pipeline.",
6
6
  "keywords": [
@@ -46,10 +46,10 @@
46
46
  "typecheck": "tsc --noEmit"
47
47
  },
48
48
  "dependencies": {
49
- "@suss/behavioral-ir": "0.5.8",
50
- "@suss/datalog": "0.5.8",
51
- "@suss/extractor": "0.5.8",
52
- "@suss/resolution": "0.5.8",
49
+ "@suss/behavioral-ir": "0.5.9",
50
+ "@suss/datalog": "0.5.9",
51
+ "@suss/extractor": "0.5.9",
52
+ "@suss/resolution": "0.5.9",
53
53
  "graphql": "^16.8.0",
54
54
  "picomatch": "^4.0.4",
55
55
  "ts-morph": "^23.0.0"