@suss/packs 0.34.1 → 0.35.0

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/prisma.js CHANGED
@@ -14,20 +14,63 @@ import {
14
14
  declaredBy,
15
15
  sqlStatements
16
16
  } from "@suss/recognize";
17
- import fs from "fs";
18
- import path from "path";
17
+ import fs3 from "fs";
18
+ import path3 from "path";
19
19
  import { getSchema as getSchema2 } from "@mrleebo/prisma-ast";
20
20
  import { ts } from "ts-morph";
21
21
 
22
22
  // ../contract/prisma/dist/index.js
23
+ import fs from "fs";
24
+ import path from "path";
23
25
  import { getSchema } from "@mrleebo/prisma-ast";
24
26
  import { storageBinding } from "@suss/behavioral-ir";
27
+ import { defaultProjectRoot, pathInProject } from "@suss/behavioral-ir/files";
25
28
  var PROVIDER_TO_SYSTEM = {
26
29
  postgresql: "postgresql",
27
30
  postgres: "postgresql",
28
31
  mysql: "mysql",
29
32
  sqlite: "sqlite"
30
33
  };
34
+ function prismaSchemaFiles(schemaPath) {
35
+ const stat = statOf(schemaPath);
36
+ if (stat?.isDirectory() === true) {
37
+ return prismaFilesIn(schemaPath, true);
38
+ }
39
+ if (stat?.isFile() !== true) {
40
+ return [];
41
+ }
42
+ const beside = prismaFilesIn(path.dirname(schemaPath), false).flatMap(
43
+ (file) => {
44
+ const list = schemaListOf(file);
45
+ return list === null ? [] : [{ file, list }];
46
+ }
47
+ );
48
+ const datasources = beside.filter(
49
+ ({ list }) => list.some(isDatasource)
50
+ ).length;
51
+ const given = path.resolve(schemaPath);
52
+ return datasources === 1 && beside.some(({ file }) => path.resolve(file) === given) ? beside.map(({ file }) => file) : [schemaPath];
53
+ }
54
+ function statOf(file) {
55
+ try {
56
+ return fs.statSync(file);
57
+ } catch {
58
+ return null;
59
+ }
60
+ }
61
+ function prismaFilesIn(dir, below) {
62
+ return fs.readdirSync(dir, { recursive: below, encoding: "utf8" }).filter((name) => name.endsWith(".prisma")).map((name) => path.join(dir, name)).filter((file) => statOf(file)?.isFile() === true).sort();
63
+ }
64
+ function schemaListOf(file) {
65
+ try {
66
+ return getSchema(fs.readFileSync(file, "utf8")).list;
67
+ } catch {
68
+ return null;
69
+ }
70
+ }
71
+ function isDatasource(node) {
72
+ return node.type === "datasource";
73
+ }
31
74
  function prismaStorageSystem(source) {
32
75
  try {
33
76
  return storageSystemIn(getSchema(source).list);
@@ -67,9 +110,9 @@ var CONFIG_FILES = [
67
110
  "prisma.config.js",
68
111
  "prisma.config.mjs",
69
112
  "prisma.config.cjs",
70
- path.join(".config", "prisma.ts")
113
+ path3.join(".config", "prisma.ts")
71
114
  ];
72
- var DEFAULT_SCHEMAS = [path.join("prisma", "schema.prisma"), "schema.prisma"];
115
+ var DEFAULT_SCHEMAS = [path3.join("prisma", "schema.prisma"), "schema.prisma"];
73
116
  var readProjects = /* @__PURE__ */ new Map();
74
117
  function generatedClientDirs(fromDir) {
75
118
  return readProjectAt(fromDir)?.dirs ?? [];
@@ -102,26 +145,26 @@ function readProjectAt(fromDir) {
102
145
  }
103
146
  function textOf(file) {
104
147
  try {
105
- return fs.readFileSync(file, "utf8");
148
+ return fs3.readFileSync(file, "utf8");
106
149
  } catch {
107
150
  return "";
108
151
  }
109
152
  }
110
153
  function isInGeneratedClient(filePath) {
111
- return generatedClientDirs(path.dirname(filePath)).some(
112
- (dir) => filePath.startsWith(`${dir}${path.sep}`)
154
+ return generatedClientDirs(path3.dirname(filePath)).some(
155
+ (dir) => filePath.startsWith(`${dir}${path3.sep}`)
113
156
  );
114
157
  }
115
158
  function projectFilesOf(root) {
116
159
  return [
117
- path.join(root, "package.json"),
118
- ...CONFIG_FILES.map((name) => path.join(root, name)),
119
- ...DEFAULT_SCHEMAS.map((name) => path.join(root, name))
160
+ path3.join(root, "package.json"),
161
+ ...CONFIG_FILES.map((name) => path3.join(root, name)),
162
+ ...DEFAULT_SCHEMAS.map((name) => path3.join(root, name))
120
163
  ];
121
164
  }
122
165
  function changedAt(file) {
123
166
  try {
124
- return fs.statSync(file).mtimeMs;
167
+ return fs3.statSync(file).mtimeMs;
125
168
  } catch {
126
169
  return -1;
127
170
  }
@@ -145,12 +188,12 @@ function projectRootOf(fromDir) {
145
188
  return root;
146
189
  }
147
190
  function findProjectRoot(fromDir) {
148
- let dir = path.resolve(fromDir);
191
+ let dir = path3.resolve(fromDir);
149
192
  while (true) {
150
- if (fs.existsSync(path.join(dir, "package.json")) || configFileIn(dir) !== null) {
193
+ if (fs3.existsSync(path3.join(dir, "package.json")) || configFileIn(dir) !== null) {
151
194
  return dir;
152
195
  }
153
- const parent = path.dirname(dir);
196
+ const parent = path3.dirname(dir);
154
197
  if (parent === dir) {
155
198
  return null;
156
199
  }
@@ -159,41 +202,31 @@ function findProjectRoot(fromDir) {
159
202
  }
160
203
  function configFileIn(dir) {
161
204
  for (const name of CONFIG_FILES) {
162
- const candidate = path.join(dir, name);
163
- if (fs.existsSync(candidate)) {
205
+ const candidate = path3.join(dir, name);
206
+ if (fs3.existsSync(candidate)) {
164
207
  return candidate;
165
208
  }
166
209
  }
167
210
  return null;
168
211
  }
169
212
  function schemaFilesOf(root) {
170
- const stated = [configuredSchema(root), packageJsonSchema(root)];
213
+ const manifest = manifestOf(root);
214
+ const stated = [
215
+ configuredSchema(root),
216
+ packageJsonSchema(root, manifest),
217
+ generateScriptSchema(root, manifest)
218
+ ];
171
219
  for (const schema of [
172
220
  ...stated.filter((one) => one !== null),
173
- ...DEFAULT_SCHEMAS.map((name) => path.join(root, name))
221
+ ...DEFAULT_SCHEMAS.map((name) => path3.join(root, name))
174
222
  ]) {
175
- const files = prismaFilesAt(schema);
223
+ const files = prismaSchemaFiles(schema);
176
224
  if (files.length > 0) {
177
225
  return files;
178
226
  }
179
227
  }
180
228
  return [];
181
229
  }
182
- function prismaFilesAt(schemaPath) {
183
- let stat;
184
- try {
185
- stat = fs.statSync(schemaPath);
186
- } catch {
187
- return [];
188
- }
189
- if (stat.isFile()) {
190
- return [schemaPath];
191
- }
192
- if (!stat.isDirectory()) {
193
- return [];
194
- }
195
- return fs.readdirSync(schemaPath, { recursive: true, encoding: "utf8" }).filter((name) => name.endsWith(".prisma")).map((name) => path.join(schemaPath, name)).sort();
196
- }
197
230
  function configuredSchema(root) {
198
231
  const config = configFileIn(root);
199
232
  if (config === null) {
@@ -201,7 +234,7 @@ function configuredSchema(root) {
201
234
  }
202
235
  const source = ts.createSourceFile(
203
236
  config,
204
- fs.readFileSync(config, "utf8"),
237
+ fs3.readFileSync(config, "utf8"),
205
238
  ts.ScriptTarget.Latest
206
239
  );
207
240
  let found = null;
@@ -216,21 +249,31 @@ function configuredSchema(root) {
216
249
  ts.forEachChild(node, visit);
217
250
  };
218
251
  visit(source);
219
- return found === null ? null : path.resolve(root, found);
252
+ return found === null ? null : path3.resolve(root, found);
220
253
  }
221
- function packageJsonSchema(root) {
222
- const file = path.join(root, "package.json");
223
- if (!fs.existsSync(file)) {
224
- return null;
225
- }
254
+ function manifestOf(root) {
226
255
  try {
227
- const manifest = JSON.parse(fs.readFileSync(file, "utf8"));
228
- const schema = manifest.prisma?.schema;
229
- return typeof schema === "string" ? path.resolve(root, schema) : null;
256
+ return JSON.parse(
257
+ fs3.readFileSync(path3.join(root, "package.json"), "utf8")
258
+ );
230
259
  } catch {
231
260
  return null;
232
261
  }
233
262
  }
263
+ function packageJsonSchema(root, manifest) {
264
+ const schema = manifest?.prisma?.schema;
265
+ return typeof schema === "string" ? path3.resolve(root, schema) : null;
266
+ }
267
+ var GENERATE_SCHEMA_FLAG = /\bprisma\s+generate\b[^&|;]*?--schema(?:=|\s+)(["']?)([^\s"'&|;]+)\1/;
268
+ function generateScriptSchema(root, manifest) {
269
+ for (const script of Object.values(manifest?.scripts ?? {})) {
270
+ const match = typeof script === "string" ? GENERATE_SCHEMA_FLAG.exec(script) : null;
271
+ if (match?.[2] !== void 0) {
272
+ return path3.resolve(root, match[2]);
273
+ }
274
+ }
275
+ return null;
276
+ }
234
277
  function outputDirsIn(schema) {
235
278
  const schemaFile = schema.file;
236
279
  let list;
@@ -243,7 +286,7 @@ function outputDirsIn(schema) {
243
286
  for (const block of list) {
244
287
  const output = generatorOutput(block);
245
288
  if (output !== null) {
246
- dirs.push(path.resolve(path.dirname(schemaFile), output));
289
+ dirs.push(path3.resolve(path3.dirname(schemaFile), output));
247
290
  }
248
291
  }
249
292
  return dirs;
@@ -421,7 +464,7 @@ function nestedReads(optionsArg) {
421
464
  collectRelations(optionsArg, [], found);
422
465
  return found;
423
466
  }
424
- function collectRelations(shape, path3, found) {
467
+ function collectRelations(shape, path32, found) {
425
468
  const select = readObjectArg(shape.fields.select);
426
469
  if (select !== null) {
427
470
  for (const [name, value] of Object.entries(select.fields)) {
@@ -429,7 +472,7 @@ function collectRelations(shape, path3, found) {
429
472
  if (nested === null) {
430
473
  continue;
431
474
  }
432
- recordRelation(name, nested, path3, found);
475
+ recordRelation(name, nested, path32, found);
433
476
  }
434
477
  }
435
478
  const include = readObjectArg(shape.fields.include);
@@ -439,14 +482,14 @@ function collectRelations(shape, path3, found) {
439
482
  for (const [name, value] of Object.entries(include.fields)) {
440
483
  const nested = readObjectArg(value);
441
484
  if (nested === null) {
442
- found.push({ relationPath: [...path3, name], fields: ["*"] });
485
+ found.push({ relationPath: [...path32, name], fields: ["*"] });
443
486
  continue;
444
487
  }
445
- recordRelation(name, nested, path3, found);
488
+ recordRelation(name, nested, path32, found);
446
489
  }
447
490
  }
448
- function recordRelation(name, nested, path3, found) {
449
- const relationPath = [...path3, name];
491
+ function recordRelation(name, nested, path32, found) {
492
+ const relationPath = [...path32, name];
450
493
  found.push({ relationPath, fields: extractFields(nested, "read") });
451
494
  collectRelations(nested, relationPath, found);
452
495
  }
@@ -500,13 +543,13 @@ function nestedWrites(optionsArg) {
500
543
  }
501
544
  return found;
502
545
  }
503
- function collectNestedWrites(row, path3, found) {
546
+ function collectNestedWrites(row, path32, found) {
504
547
  for (const [field, value] of Object.entries(row.fields)) {
505
548
  const nested = readObjectArg(value);
506
549
  if (nested === null) {
507
550
  continue;
508
551
  }
509
- const relationPath = [...path3, field];
552
+ const relationPath = [...path32, field];
510
553
  for (const [operation, payload] of Object.entries(nested.fields)) {
511
554
  const does = NESTED_OPERATIONS.get(operation);
512
555
  if (does === void 0) {
package/dist/rails.js CHANGED
@@ -1362,7 +1362,9 @@ var RelationSchema = z14.enum([
1362
1362
  var EffectRelationSchema = RelationSchema.exclude(["provides"]);
1363
1363
  var SuppressionSideSchema = z22.object({
1364
1364
  summary: z22.string().optional(),
1365
- transitionId: z22.string().optional()
1365
+ transitionId: z22.string().optional(),
1366
+ /** The field on that side, for a finding about one field and no transition. */
1367
+ field: z22.string().optional()
1366
1368
  }).optional();
1367
1369
  var SuppressionRuleSchema = z22.object({
1368
1370
  /**
@@ -2455,6 +2457,7 @@ var RACK_STATUS_CODE_NAMES = {
2455
2457
  variant_also_negotiates: 506,
2456
2458
  insufficient_storage: 507,
2457
2459
  loop_detected: 508,
2460
+ bandwidth_limit_exceeded: 509,
2458
2461
  not_extended: 510,
2459
2462
  network_authentication_required: 511
2460
2463
  };
@@ -2650,7 +2653,8 @@ function railsFramework(options = {}) {
2650
2653
  options.configDirectory,
2651
2654
  options.routesFile ?? "config/routes.rb"
2652
2655
  );
2653
- const displayPathOf = (file) => options.configDirectory === void 0 ? file : path5.relative(options.configDirectory, file);
2656
+ const railsRoot = path5.dirname(root);
2657
+ const displayPathOf = (file) => path5.isAbsolute(file) ? path5.relative(railsRoot, file) : file;
2654
2658
  const engineRoots = () => expandPatterns(options.configDirectory, options.engineRoots);
2655
2659
  const extraRoutesFiles = () => expandPatterns(options.configDirectory, options.routesFiles);
2656
2660
  const inflections = options.configDirectory === void 0 ? EMPTY_INFLECTIONS : readInflections(options.configDirectory);
@@ -2658,7 +2662,7 @@ function railsFramework(options = {}) {
2658
2662
  const routesInput = () => ({
2659
2663
  routesFile: {
2660
2664
  file: routesFile,
2661
- displayPath: options.routesFile ?? "config/routes.rb"
2665
+ displayPath: displayPathOf(routesFile)
2662
2666
  },
2663
2667
  engines: readEngines(engineRoots(), acronyms).map((engine) => ({
2664
2668
  ...engine,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@suss/packs",
3
- "version": "0.34.1",
3
+ "version": "0.35.0",
4
4
  "type": "module",
5
5
  "description": "Every pack suss ships in one install, so it can read Express, Hono, NestJS, FastAPI, Rails, Prisma, OpenAPI and the rest.",
6
6
  "keywords": [
@@ -267,15 +267,15 @@
267
267
  },
268
268
  "dependencies": {
269
269
  "@mrleebo/prisma-ast": "^0.15.0",
270
- "@suss/adapter-python": "0.34.1",
271
- "@suss/adapter-ruby": "0.34.1",
272
- "@suss/adapter-typescript": "0.34.1",
273
- "@suss/behavioral-ir": "0.34.1",
274
- "@suss/contract-graphql": "0.34.1",
275
- "@suss/extractor": "0.34.1",
276
- "@suss/manifest-aws": "0.34.1",
277
- "@suss/recognize": "0.34.1",
278
- "@suss/sql": "0.34.1",
270
+ "@suss/adapter-python": "0.35.0",
271
+ "@suss/adapter-ruby": "0.35.0",
272
+ "@suss/adapter-typescript": "0.35.0",
273
+ "@suss/behavioral-ir": "0.35.0",
274
+ "@suss/contract-graphql": "0.35.0",
275
+ "@suss/extractor": "0.35.0",
276
+ "@suss/manifest-aws": "0.35.0",
277
+ "@suss/recognize": "0.35.0",
278
+ "@suss/sql": "0.35.0",
279
279
  "zod": "^4.0.0"
280
280
  },
281
281
  "devDependencies": {