@suss/adapter-ruby 0.26.0 → 0.28.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/index.d.cts CHANGED
@@ -31,6 +31,13 @@ interface Range {
31
31
  }
32
32
  declare function field(node: Node, name: string): Node | null;
33
33
  declare function bodyStatements(body: Node): Node[];
34
+ /**
35
+ * Every statement written directly inside a branching statement's
36
+ * branches, across its `elsif`, `else`, `when`, `rescue` and `ensure`
37
+ * clauses. A statement inside a nested branching statement is not
38
+ * included; the caller descends into that one itself.
39
+ */
40
+ declare function nestedStatements(stmt: Node): Node[];
34
41
  /** A call whose block is the thing being configured rather than a place statements run. */
35
42
  type BlockConfigures = (call: Node) => boolean;
36
43
  /**
@@ -68,8 +75,14 @@ declare function readCallArgs(argumentList: Node | null): CallArgs;
68
75
  */
69
76
  /** A pack picks a convention by name, and the code for each one lives here. */
70
77
  type ConstantPathConvention = "railsUnderscore";
71
- /** Ported from ActiveSupport's own `String#underscore`, which is what Rails autoloading runs a constant path through. */
72
- declare function underscoreConstantPath(qualifiedName: string): string;
78
+ /**
79
+ * Ported from ActiveSupport's own `String#underscore`, which is what
80
+ * Rails autoloading runs a constant path through. An acronym the
81
+ * project registers with the inflector is one word to it, so with
82
+ * `ActivityPub` registered the path is `activitypub`, not
83
+ * `activity_pub`.
84
+ */
85
+ declare function underscoreConstantPath(qualifiedName: string, acronyms?: readonly string[]): string;
73
86
  /**
74
87
  * Null when there is no file at that path. Rails autoloads from every
75
88
  * directory directly under `app`, so `ApplicationController` is
@@ -77,14 +90,14 @@ declare function underscoreConstantPath(qualifiedName: string): string;
77
90
  * `app/application_controller.rb`; those directories are tried after
78
91
  * the root itself, in name order, and no other spelling is tried.
79
92
  */
80
- declare function resolveConstantFile(root: string, qualifiedName: string, convention: ConstantPathConvention): string | null;
93
+ declare function resolveConstantFile(root: string, qualifiedName: string, convention: ConstantPathConvention, acronyms?: readonly string[]): string | null;
81
94
 
82
95
  /**
83
96
  * Resolves Ruby constant paths against lexical nesting.
84
97
  *
85
- * A compound path written out, like `Data::Record`, means the same thing
86
- * wherever it appears, so its text is the qualified name. A bare name is
87
- * relative to the nesting it is written inside. `require` is never resolved,
98
+ * A compound path referenced, like `Data::Record`, is read as absolute. A
99
+ * bare name is relative to the nesting it is written inside, and so is a
100
+ * compound name `class` or `module` opens. `require` is never resolved,
88
101
  * because Rails autoloads by naming convention rather than through a load graph
89
102
  * a static reader could follow, so a constant that nesting alone cannot qualify
90
103
  * keeps whatever name the source wrote and callers treat it as unresolved.
@@ -141,7 +154,13 @@ interface ReachedBody {
141
154
  /** Absolute path of the file the block is written in. */
142
155
  file: string;
143
156
  }
144
- /** One ancestor: every block reopening its name, or the name alone when nothing reached it. Blocks stay together because Ruby treats a reopened class as one place in the chain. */
157
+ /**
158
+ * One ancestor: every block reopening its name, the name alone when
159
+ * nothing reached it, or the library's own class the walk stopped at.
160
+ * Blocks stay together because Ruby treats a reopened class as one
161
+ * place in the chain. The root is kept by name so a caller can tell a
162
+ * chain that ended at the library from one that ended at nothing.
163
+ */
145
164
  type AncestorEntry = {
146
165
  type: "bodies";
147
166
  name: string;
@@ -149,6 +168,9 @@ type AncestorEntry = {
149
168
  } | {
150
169
  type: "unfollowed";
151
170
  name: string;
171
+ } | {
172
+ type: "root";
173
+ name: string;
152
174
  };
153
175
  /** A class and everything it inherits from, in Ruby's own method-lookup order. */
154
176
  type Ancestry = readonly AncestorEntry[];
@@ -157,6 +179,8 @@ interface AncestorLookup {
157
179
  /** Directory the constant-to-path convention resolves an ancestor's name against. */
158
180
  root: string;
159
181
  pathConvention: ConstantPathConvention;
182
+ /** Acronyms the convention keeps as one word, `ActivityPub` to `activitypub`. */
183
+ acronyms?: readonly string[];
160
184
  /**
161
185
  * The library's own classes a project's chain ends at. Reaching one
162
186
  * ends a walk with nothing left unfollowed.
@@ -324,15 +348,17 @@ interface RbLoaderPattern {
324
348
  shortcuts: string[];
325
349
  }
326
350
  type RubyDiscoveryPattern = GraphqlObjectFields | ControllerActions;
327
- /** A class whose ancestry reaches one of `baseClassNames` is a controller, and every instance method it defines directly is one of its actions, bound by `routeFor` to the method and path a project's own routing gives it, or discovered with no boundary binding when `routeFor` finds none. */
351
+ /** A class whose ancestry reaches one of `baseClassNames` or `ancestryRootClassNames` is a controller, and every instance method it defines directly is one of its actions, bound by `routeFor` to the method and path a project's own routing gives it, or discovered with no boundary binding when `routeFor` finds none. */
328
352
  interface ControllerActions {
329
353
  type: "controllerActions";
330
- /** The library's own base a project's controllers extend, `ActionController::Base` say. */
354
+ /** A base a project's controllers extend, `ApplicationController` say. The base itself is not a controller. */
331
355
  baseClassNames: string[];
332
356
  /** The directory a bare superclass name is looked up under, the project's own layout. */
333
357
  root: string;
334
358
  pathConvention: ConstantPathConvention;
335
- /** The library's own classes a project's controller chain ends at. */
359
+ /** Acronyms the project registers with the inflector, which the path convention keeps as one word: `ActivityPub` is `activitypub`, not `activity_pub`. */
360
+ acronyms?: string[];
361
+ /** The library's own classes a project's controller chain ends at. A class extending one directly is a controller too. */
336
362
  ancestryRootClassNames: string[];
337
363
  /** Status code a wire response gets when the action does not say otherwise. */
338
364
  defaultStatusCode: number;
@@ -412,6 +438,8 @@ interface GraphqlObjectFields {
412
438
  /** The directory a wiring keyword's referenced class is looked up under. That is the project's own layout, not the library's. */
413
439
  root: string;
414
440
  pathConvention: ConstantPathConvention;
441
+ /** Acronyms the project registers with the inflector, which the path convention keeps as one word. */
442
+ acronyms?: string[];
415
443
  /** The DSL call declaring one schema field in an object type's body. */
416
444
  fieldCallName: string;
417
445
  /** The DSL call declaring a referenced class's own return type. */
@@ -516,6 +544,8 @@ declare function discoverUnits(root: Node, options: DiscoveryOptions): Promise<R
516
544
  interface ConstantDefinition {
517
545
  readonly qualifiedName: string;
518
546
  readonly key: string;
547
+ /** `class`/`module` opens a constant every file may open again; `X = ...` sets one. */
548
+ readonly kind: "declaration" | "assignment";
519
549
  }
520
550
  /** A constant read somewhere, with the nesting it was read inside. */
521
551
  interface ConstantReference {
@@ -555,7 +585,7 @@ declare function nodeId(filePath: string, node: Node): string;
555
585
  * expression in hand and wants to ask the rules about it. `enclosing` is
556
586
  * the method the expression is written in, or null outside one.
557
587
  */
558
- declare function readKey(filePath: string, node: Node, enclosing: Node | null): string;
588
+ declare function readKey(filePath: string, written: Node, enclosing: Node | null): string;
559
589
  /**
560
590
  * Walk a file and emit the value facts. A method is walked in its own right,
561
591
  * so a body's returns and calls belong to the method that wrote them.
@@ -754,10 +784,12 @@ interface ProjectNodes {
754
784
  }
755
785
  /** Register the parsed project, so reads through `db` can follow the facts back to nodes. */
756
786
  declare function bindEvaluator(db: Database, nodes: ProjectNodes): void;
787
+ /** Strings to read for the parameters of the block or method `node` is written in, the way a caller would supply them. */
788
+ type ParameterBindings = ReadonlyMap<string, string>;
757
789
  /** The abstract value `node` comes down to, through the facts when `db` was bound. */
758
- declare function evaluatedValue(node: Node, db?: Database): Value;
790
+ declare function evaluatedValue(node: Node, db?: Database, bindings?: ParameterBindings): Value;
759
791
  /** The one string `node` comes down to, or null when it does not settle on one. */
760
- declare function stringValueOf(node: Node, db?: Database): string | null;
792
+ declare function stringValueOf(node: Node, db?: Database, bindings?: ParameterBindings): string | null;
761
793
  /** Every method a file defines, keyed the way the facts key it, for `bindEvaluator`. */
762
794
  declare function methodDefinitionsIn(file: string, root: Node): Map<string, Node>;
763
795
 
@@ -771,4 +803,4 @@ declare function methodDefinitionsIn(file: string, root: Node): Map<string, Node
771
803
  */
772
804
  declare const ADAPTER_VERSION = "0.1.0";
773
805
 
774
- export { ADAPTER_VERSION, type AncestorEntry, type AncestorLookup, type Ancestry, type CallArgs, type ClassInfo, type ConstantPathConvention, type ControllerActions, type DiscoveryOptions, type EvaluatedFile, type ExtractRubyOptions, type ExtractRubyResult, type FileCache, type FileConstants, type GraphqlObjectFields, type GraphqlTypeNameConvention, type MethodLookup, type ProjectNodes, type Range, type RbStatusCall, type RbStoragePattern, type ReachedBody, type RubyDiscoveryPattern, type RubyExtendsSite, type RubyPack, type RubyRequireSite, type RubyStubEvidence, type RubyStubEvidenceOptions, type RubyValueHandle, RubyWhySession, type RubyWhySessionOptions, type TypeReadContext, ancestryOf, bindEvaluator, bodyStatements, booleanLiteralValue, collectFileConstants, createFileCache, discoverUnits, emitConstantBindings, emitEntryFact, emitValueFacts, evaluatedValue, extractRubyProject, field, findRubyFiles, graphqlTypeNameFromQualified, hashKeySymbolName, inheritedStatements, methodDefinitionsIn, methodInAncestry, nodeId, parseRuby, parseRubySync, preloadRubyGrammar, qualifyConstantRef, reachDefinition, readCallArgs, readKey, resolveConstantFile, rubyStubEvidence, runStatements, stringLiteralValue, stringValueOf, symbolValue, typeShapeFromNode, underscoreConstantPath, unitKey, walkClasses, walkDefinitions };
806
+ export { ADAPTER_VERSION, type AncestorEntry, type AncestorLookup, type Ancestry, type CallArgs, type ClassInfo, type ConstantPathConvention, type ControllerActions, type DiscoveryOptions, type EvaluatedFile, type ExtractRubyOptions, type ExtractRubyResult, type FileCache, type FileConstants, type GraphqlObjectFields, type GraphqlTypeNameConvention, type MethodLookup, type ParameterBindings, type ProjectNodes, type Range, type RbStatusCall, type RbStoragePattern, type ReachedBody, type RubyDiscoveryPattern, type RubyExtendsSite, type RubyPack, type RubyRequireSite, type RubyStubEvidence, type RubyStubEvidenceOptions, type RubyValueHandle, RubyWhySession, type RubyWhySessionOptions, type TypeReadContext, ancestryOf, bindEvaluator, bodyStatements, booleanLiteralValue, collectFileConstants, createFileCache, discoverUnits, emitConstantBindings, emitEntryFact, emitValueFacts, evaluatedValue, extractRubyProject, field, findRubyFiles, graphqlTypeNameFromQualified, hashKeySymbolName, inheritedStatements, methodDefinitionsIn, methodInAncestry, nestedStatements, nodeId, parseRuby, parseRubySync, preloadRubyGrammar, qualifyConstantRef, reachDefinition, readCallArgs, readKey, resolveConstantFile, rubyStubEvidence, runStatements, stringLiteralValue, stringValueOf, symbolValue, typeShapeFromNode, underscoreConstantPath, unitKey, walkClasses, walkDefinitions };
package/dist/index.d.ts CHANGED
@@ -31,6 +31,13 @@ interface Range {
31
31
  }
32
32
  declare function field(node: Node, name: string): Node | null;
33
33
  declare function bodyStatements(body: Node): Node[];
34
+ /**
35
+ * Every statement written directly inside a branching statement's
36
+ * branches, across its `elsif`, `else`, `when`, `rescue` and `ensure`
37
+ * clauses. A statement inside a nested branching statement is not
38
+ * included; the caller descends into that one itself.
39
+ */
40
+ declare function nestedStatements(stmt: Node): Node[];
34
41
  /** A call whose block is the thing being configured rather than a place statements run. */
35
42
  type BlockConfigures = (call: Node) => boolean;
36
43
  /**
@@ -68,8 +75,14 @@ declare function readCallArgs(argumentList: Node | null): CallArgs;
68
75
  */
69
76
  /** A pack picks a convention by name, and the code for each one lives here. */
70
77
  type ConstantPathConvention = "railsUnderscore";
71
- /** Ported from ActiveSupport's own `String#underscore`, which is what Rails autoloading runs a constant path through. */
72
- declare function underscoreConstantPath(qualifiedName: string): string;
78
+ /**
79
+ * Ported from ActiveSupport's own `String#underscore`, which is what
80
+ * Rails autoloading runs a constant path through. An acronym the
81
+ * project registers with the inflector is one word to it, so with
82
+ * `ActivityPub` registered the path is `activitypub`, not
83
+ * `activity_pub`.
84
+ */
85
+ declare function underscoreConstantPath(qualifiedName: string, acronyms?: readonly string[]): string;
73
86
  /**
74
87
  * Null when there is no file at that path. Rails autoloads from every
75
88
  * directory directly under `app`, so `ApplicationController` is
@@ -77,14 +90,14 @@ declare function underscoreConstantPath(qualifiedName: string): string;
77
90
  * `app/application_controller.rb`; those directories are tried after
78
91
  * the root itself, in name order, and no other spelling is tried.
79
92
  */
80
- declare function resolveConstantFile(root: string, qualifiedName: string, convention: ConstantPathConvention): string | null;
93
+ declare function resolveConstantFile(root: string, qualifiedName: string, convention: ConstantPathConvention, acronyms?: readonly string[]): string | null;
81
94
 
82
95
  /**
83
96
  * Resolves Ruby constant paths against lexical nesting.
84
97
  *
85
- * A compound path written out, like `Data::Record`, means the same thing
86
- * wherever it appears, so its text is the qualified name. A bare name is
87
- * relative to the nesting it is written inside. `require` is never resolved,
98
+ * A compound path referenced, like `Data::Record`, is read as absolute. A
99
+ * bare name is relative to the nesting it is written inside, and so is a
100
+ * compound name `class` or `module` opens. `require` is never resolved,
88
101
  * because Rails autoloads by naming convention rather than through a load graph
89
102
  * a static reader could follow, so a constant that nesting alone cannot qualify
90
103
  * keeps whatever name the source wrote and callers treat it as unresolved.
@@ -141,7 +154,13 @@ interface ReachedBody {
141
154
  /** Absolute path of the file the block is written in. */
142
155
  file: string;
143
156
  }
144
- /** One ancestor: every block reopening its name, or the name alone when nothing reached it. Blocks stay together because Ruby treats a reopened class as one place in the chain. */
157
+ /**
158
+ * One ancestor: every block reopening its name, the name alone when
159
+ * nothing reached it, or the library's own class the walk stopped at.
160
+ * Blocks stay together because Ruby treats a reopened class as one
161
+ * place in the chain. The root is kept by name so a caller can tell a
162
+ * chain that ended at the library from one that ended at nothing.
163
+ */
145
164
  type AncestorEntry = {
146
165
  type: "bodies";
147
166
  name: string;
@@ -149,6 +168,9 @@ type AncestorEntry = {
149
168
  } | {
150
169
  type: "unfollowed";
151
170
  name: string;
171
+ } | {
172
+ type: "root";
173
+ name: string;
152
174
  };
153
175
  /** A class and everything it inherits from, in Ruby's own method-lookup order. */
154
176
  type Ancestry = readonly AncestorEntry[];
@@ -157,6 +179,8 @@ interface AncestorLookup {
157
179
  /** Directory the constant-to-path convention resolves an ancestor's name against. */
158
180
  root: string;
159
181
  pathConvention: ConstantPathConvention;
182
+ /** Acronyms the convention keeps as one word, `ActivityPub` to `activitypub`. */
183
+ acronyms?: readonly string[];
160
184
  /**
161
185
  * The library's own classes a project's chain ends at. Reaching one
162
186
  * ends a walk with nothing left unfollowed.
@@ -324,15 +348,17 @@ interface RbLoaderPattern {
324
348
  shortcuts: string[];
325
349
  }
326
350
  type RubyDiscoveryPattern = GraphqlObjectFields | ControllerActions;
327
- /** A class whose ancestry reaches one of `baseClassNames` is a controller, and every instance method it defines directly is one of its actions, bound by `routeFor` to the method and path a project's own routing gives it, or discovered with no boundary binding when `routeFor` finds none. */
351
+ /** A class whose ancestry reaches one of `baseClassNames` or `ancestryRootClassNames` is a controller, and every instance method it defines directly is one of its actions, bound by `routeFor` to the method and path a project's own routing gives it, or discovered with no boundary binding when `routeFor` finds none. */
328
352
  interface ControllerActions {
329
353
  type: "controllerActions";
330
- /** The library's own base a project's controllers extend, `ActionController::Base` say. */
354
+ /** A base a project's controllers extend, `ApplicationController` say. The base itself is not a controller. */
331
355
  baseClassNames: string[];
332
356
  /** The directory a bare superclass name is looked up under, the project's own layout. */
333
357
  root: string;
334
358
  pathConvention: ConstantPathConvention;
335
- /** The library's own classes a project's controller chain ends at. */
359
+ /** Acronyms the project registers with the inflector, which the path convention keeps as one word: `ActivityPub` is `activitypub`, not `activity_pub`. */
360
+ acronyms?: string[];
361
+ /** The library's own classes a project's controller chain ends at. A class extending one directly is a controller too. */
336
362
  ancestryRootClassNames: string[];
337
363
  /** Status code a wire response gets when the action does not say otherwise. */
338
364
  defaultStatusCode: number;
@@ -412,6 +438,8 @@ interface GraphqlObjectFields {
412
438
  /** The directory a wiring keyword's referenced class is looked up under. That is the project's own layout, not the library's. */
413
439
  root: string;
414
440
  pathConvention: ConstantPathConvention;
441
+ /** Acronyms the project registers with the inflector, which the path convention keeps as one word. */
442
+ acronyms?: string[];
415
443
  /** The DSL call declaring one schema field in an object type's body. */
416
444
  fieldCallName: string;
417
445
  /** The DSL call declaring a referenced class's own return type. */
@@ -516,6 +544,8 @@ declare function discoverUnits(root: Node, options: DiscoveryOptions): Promise<R
516
544
  interface ConstantDefinition {
517
545
  readonly qualifiedName: string;
518
546
  readonly key: string;
547
+ /** `class`/`module` opens a constant every file may open again; `X = ...` sets one. */
548
+ readonly kind: "declaration" | "assignment";
519
549
  }
520
550
  /** A constant read somewhere, with the nesting it was read inside. */
521
551
  interface ConstantReference {
@@ -555,7 +585,7 @@ declare function nodeId(filePath: string, node: Node): string;
555
585
  * expression in hand and wants to ask the rules about it. `enclosing` is
556
586
  * the method the expression is written in, or null outside one.
557
587
  */
558
- declare function readKey(filePath: string, node: Node, enclosing: Node | null): string;
588
+ declare function readKey(filePath: string, written: Node, enclosing: Node | null): string;
559
589
  /**
560
590
  * Walk a file and emit the value facts. A method is walked in its own right,
561
591
  * so a body's returns and calls belong to the method that wrote them.
@@ -754,10 +784,12 @@ interface ProjectNodes {
754
784
  }
755
785
  /** Register the parsed project, so reads through `db` can follow the facts back to nodes. */
756
786
  declare function bindEvaluator(db: Database, nodes: ProjectNodes): void;
787
+ /** Strings to read for the parameters of the block or method `node` is written in, the way a caller would supply them. */
788
+ type ParameterBindings = ReadonlyMap<string, string>;
757
789
  /** The abstract value `node` comes down to, through the facts when `db` was bound. */
758
- declare function evaluatedValue(node: Node, db?: Database): Value;
790
+ declare function evaluatedValue(node: Node, db?: Database, bindings?: ParameterBindings): Value;
759
791
  /** The one string `node` comes down to, or null when it does not settle on one. */
760
- declare function stringValueOf(node: Node, db?: Database): string | null;
792
+ declare function stringValueOf(node: Node, db?: Database, bindings?: ParameterBindings): string | null;
761
793
  /** Every method a file defines, keyed the way the facts key it, for `bindEvaluator`. */
762
794
  declare function methodDefinitionsIn(file: string, root: Node): Map<string, Node>;
763
795
 
@@ -771,4 +803,4 @@ declare function methodDefinitionsIn(file: string, root: Node): Map<string, Node
771
803
  */
772
804
  declare const ADAPTER_VERSION = "0.1.0";
773
805
 
774
- export { ADAPTER_VERSION, type AncestorEntry, type AncestorLookup, type Ancestry, type CallArgs, type ClassInfo, type ConstantPathConvention, type ControllerActions, type DiscoveryOptions, type EvaluatedFile, type ExtractRubyOptions, type ExtractRubyResult, type FileCache, type FileConstants, type GraphqlObjectFields, type GraphqlTypeNameConvention, type MethodLookup, type ProjectNodes, type Range, type RbStatusCall, type RbStoragePattern, type ReachedBody, type RubyDiscoveryPattern, type RubyExtendsSite, type RubyPack, type RubyRequireSite, type RubyStubEvidence, type RubyStubEvidenceOptions, type RubyValueHandle, RubyWhySession, type RubyWhySessionOptions, type TypeReadContext, ancestryOf, bindEvaluator, bodyStatements, booleanLiteralValue, collectFileConstants, createFileCache, discoverUnits, emitConstantBindings, emitEntryFact, emitValueFacts, evaluatedValue, extractRubyProject, field, findRubyFiles, graphqlTypeNameFromQualified, hashKeySymbolName, inheritedStatements, methodDefinitionsIn, methodInAncestry, nodeId, parseRuby, parseRubySync, preloadRubyGrammar, qualifyConstantRef, reachDefinition, readCallArgs, readKey, resolveConstantFile, rubyStubEvidence, runStatements, stringLiteralValue, stringValueOf, symbolValue, typeShapeFromNode, underscoreConstantPath, unitKey, walkClasses, walkDefinitions };
806
+ export { ADAPTER_VERSION, type AncestorEntry, type AncestorLookup, type Ancestry, type CallArgs, type ClassInfo, type ConstantPathConvention, type ControllerActions, type DiscoveryOptions, type EvaluatedFile, type ExtractRubyOptions, type ExtractRubyResult, type FileCache, type FileConstants, type GraphqlObjectFields, type GraphqlTypeNameConvention, type MethodLookup, type ParameterBindings, type ProjectNodes, type Range, type RbStatusCall, type RbStoragePattern, type ReachedBody, type RubyDiscoveryPattern, type RubyExtendsSite, type RubyPack, type RubyRequireSite, type RubyStubEvidence, type RubyStubEvidenceOptions, type RubyValueHandle, RubyWhySession, type RubyWhySessionOptions, type TypeReadContext, ancestryOf, bindEvaluator, bodyStatements, booleanLiteralValue, collectFileConstants, createFileCache, discoverUnits, emitConstantBindings, emitEntryFact, emitValueFacts, evaluatedValue, extractRubyProject, field, findRubyFiles, graphqlTypeNameFromQualified, hashKeySymbolName, inheritedStatements, methodDefinitionsIn, methodInAncestry, nestedStatements, nodeId, parseRuby, parseRubySync, preloadRubyGrammar, qualifyConstantRef, reachDefinition, readCallArgs, readKey, resolveConstantFile, rubyStubEvidence, runStatements, stringLiteralValue, stringValueOf, symbolValue, typeShapeFromNode, underscoreConstantPath, unitKey, walkClasses, walkDefinitions };