Skip to content

Commit

Permalink
[slimfast-node]: Add Types for Constraints (#68)
Browse files Browse the repository at this point in the history
  • Loading branch information
antonyfaris authored Oct 27, 2023
1 parent b9c7444 commit 90937a1
Show file tree
Hide file tree
Showing 36 changed files with 307 additions and 228 deletions.
5 changes: 5 additions & 0 deletions .changeset/mighty-beans-occur.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@modular-rocks/slimfast-node': patch
---

Added types for constraints
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { combineImports } from '.';
import { extractIdentifiers } from '../../../../visitors/utils/extract-identifiers';
import { parser } from '../../../../visitors/utils/parser';

import type { RandomObject, SlimFastOpts } from '../../../../../types';
import type { SlimFastOpts } from '../../../../../types';
import type { Binding, NodePath } from '@babel/traverse';

const files: [string, string][] = [[`/path`, '']];
Expand Down Expand Up @@ -42,7 +42,10 @@ describe('Combine imports', () => {
});

if (rootPath !== null) {
const data: RandomObject = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
// TODO: Verify 'data.toImport' content and ensure it provides valid 'Binding[]' for 'combineImports'.
const imports = unique(data.toImport) as Binding[];
Expand Down Expand Up @@ -74,7 +77,10 @@ describe('Combine imports', () => {
});

if (rootPath !== null) {
const data: RandomObject = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
// TODO: Verify 'data.toImport' content and ensure it provides valid 'Binding[]' for 'combineImports'.
const imports = unique(data.toImport) as Binding[];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
expect(rootPath.isJSXElement()).toBe(false);
const el = replace('myFunction', rootPath, data, opts);
Expand All @@ -65,7 +68,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
expect(rootPath.isJSXElement()).toBe(false);
const el = replace('myFunction', rootPath, data, opts);
Expand Down Expand Up @@ -94,7 +100,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
expect(rootPath.isJSXElement()).toBe(true);
const el = replace('MyComponent', rootPath, data, opts);
Expand Down Expand Up @@ -124,7 +133,10 @@ describe('Generate JSX', () => {
});

if (rootPath) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
expect(rootPath.isJSXElement()).toBe(true);
const el = replace('MyComponent', rootPath, data, opts);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateJSXElement('MyComponent', data);
expect(file.astToCode(el)).toBe(`<MyComponent />`);
Expand Down Expand Up @@ -73,7 +76,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateJSXElement('MyComponent', data);
expect(file.astToCode(el)).toBe(`<MyComponent name={name} />`);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateFunction('myFunction', data);
expect(file.astToCode(el)).toBe(`myFunction()`);
Expand All @@ -65,7 +68,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateFunction('myFunction', data);
expect(file.astToCode(el)).toBe(`myFunction(name)`);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = wrap(rootPath, data, opts);
expect(file.astToCode(el)).toBe(`export default function() {
Expand All @@ -67,7 +70,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = wrap(rootPath, data, opts);
expect(file.astToCode(el)).toBe(`export default function(name) {
Expand Down Expand Up @@ -97,7 +103,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = wrap(rootPath, data, opts);
expect(file.astToCode(el)).toBe(`export default function(props) {
Expand Down Expand Up @@ -133,7 +142,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = wrap(rootPath, data, opts);
expect(file.astToCode(el)).toBe(`export default function(props) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateExportedJSXComponent(rootPath, data);
expect(file.astToCode(el)).toBe(`export default function(props) {
Expand Down Expand Up @@ -79,7 +82,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateExportedJSXComponent(rootPath, data);
expect(file.astToCode(el)).toBe(`export default function(props) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateExportedFunction(rootPath, data);
expect(file.astToCode(el)).toBe(`export default function() {
Expand Down Expand Up @@ -71,7 +74,10 @@ describe('Generate JSX', () => {
});

if (rootPath !== null) {
const data = {};
const data = {
toImport: [],
toInject: [],
};
extractIdentifiers(rootPath, data);
const el = generateExportedFunction(rootPath, data);
expect(file.astToCode(el)).toBe(`export default function(props) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { shouldIgnore } from '../utils/contraints/should-ignore';
import { tooSmall } from '../utils/contraints/too-small';
import { Visitor } from '../visitor';

import type { RandomObject } from '../../../types';
import type { Constraints, RandomObject } from '../../../types';

/**
* A `Visitor` that traverses AST expression nodes, evaluating them against specific constraints.
Expand All @@ -20,7 +20,7 @@ export class ExpressionVisitor extends Visitor {
*
* @returns An array of constraint functions specific to expressions.
*/
constraints(): Function[] {
constraints(): Constraints {
return [
removesTooMuch(2),
shouldIgnore,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ describe('Contains variables in other scopes', () => {
}`;
const ast = parser(code);
let rootPath: NodePath | null = null;
const data = {};

traverse(ast, {
VariableDeclaration(path) {
Expand All @@ -24,7 +23,7 @@ describe('Contains variables in other scopes', () => {
},
});
if (rootPath !== null) {
const result = containsIdentifiersInOtherScopes(rootPath, data, {}, ast);
const result = containsIdentifiersInOtherScopes(rootPath);
expect(result).toBe(true);
}
});
Expand All @@ -33,7 +32,6 @@ describe('Contains variables in other scopes', () => {
const code = `let yes = 'yes'`;
const ast = parser(code);
let rootPath: NodePath | null = null;
const data = {};

traverse(ast, {
VariableDeclarator(path) {
Expand All @@ -42,7 +40,7 @@ describe('Contains variables in other scopes', () => {
},
});
if (rootPath !== null) {
const result = containsIdentifiersInOtherScopes(rootPath, data, {}, ast);
const result = containsIdentifiersInOtherScopes(rootPath);
expect(result).toBe(false);
}
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import type { RandomObject } from '../../../../../types';
import type { NodePath, Node } from '@babel/traverse';
import type { Constraint, RandomObject } from '../../../../../types';
import type { NodePath } from '@babel/traverse';

function isInsidePath(innerPath: NodePath, outerPath: NodePath): boolean {
let currentPath: NodePath | null = innerPath;
Expand All @@ -21,23 +21,15 @@ function isInsidePath(innerPath: NodePath, outerPath: NodePath): boolean {
* This can be particularly useful for understanding dependencies or potential side-effects associated with variables.
*
* @param path - The AST node path of the variable declaration to be examined.
* @param data - Additional information or context related to the node.
* @param opts - Configuration options influencing the check.
* @param ast - The complete Abstract Syntax Tree.
* @returns `true` if any of the declared variables within the node path are referenced or manipulated outside their declaring scope, otherwise `false`.
*
* @example
* const hasExternalReferences = containsIdentifiersInOtherScopes(nodePath, data, opts, ast);
* const hasExternalReferences = containsIdentifiersInOtherScopes(nodePath);
* if (hasExternalReferences) {
* // Handle or analyze the variables that are used externally.
* }
*/
export const containsIdentifiersInOtherScopes = (
path: NodePath,
data: RandomObject,
opts: RandomObject,
ast: Node
) => {
export const containsIdentifiersInOtherScopes: Constraint = (path) => {
let usedInOtherScopes = false;

// TODO: double check this condition
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ describe('Has assignment expression', () => {
const code = `yes = 'no'`;
const ast = parser(code);
let rootPath: NodePath | null = null;
const data = {};

traverse(ast, {
AssignmentExpression(path) {
Expand All @@ -20,7 +19,7 @@ describe('Has assignment expression', () => {
},
});
if (rootPath !== null) {
const result = hasAssignmentExpression(rootPath, data, {}, ast);
const result = hasAssignmentExpression(rootPath);
expect(result).toBe(true);
}
});
Expand All @@ -29,7 +28,6 @@ describe('Has assignment expression', () => {
const code = `yes`;
const ast = parser(code);
let rootPath: NodePath | null = null;
const data = {};

traverse(ast, {
AssignmentExpression(path) {
Expand All @@ -38,7 +36,7 @@ describe('Has assignment expression', () => {
},
});
if (rootPath !== null) {
const result = hasAssignmentExpression(rootPath, data, {}, ast);
const result = hasAssignmentExpression(rootPath);
expect(result).toBe(false);
}
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import type { RandomObject } from '../../../../../types';
import type { NodePath, Node } from '@babel/traverse';
import type { Constraint, RandomObject } from '../../../../../types';
import type { NodePath } from '@babel/traverse';

function isInsidePath(
innerPath: NodePath,
Expand Down Expand Up @@ -40,23 +40,15 @@ const isUsedInPath = (
* The node path is examined for direct representations of an assignment expression. Additionally, nested nodes are inspected for assignment patterns, to determine if the assigned variables are referenced outside their original context.
*
* @param path - The AST node path to be checked.
* @param data - Information or context related to the node.
* @param opts - Configuration options.
* @param ast - The complete Abstract Syntax Tree.
* @returns `true` if the node path contains an assignment expression and the assigned variables are used in other scopes, otherwise `false`.
*
* @example
* const containsAssignment = hasAssignmentExpression(nodePath, data, opts, ast);
* const containsAssignment = hasAssignmentExpression(nodePath);
* if (containsAssignment) {
* // Handle or flag the assignment for further analysis.
* }
*/
export const hasAssignmentExpression = (
path: NodePath,
data: RandomObject,
opts: RandomObject,
ast: Node
) => {
export const hasAssignmentExpression: Constraint = (path) => {
let usedInOtherScopes = false;

if (path.isAssignmentExpression()) {
Expand Down
Loading

0 comments on commit 90937a1

Please sign in to comment.