From 1c4ef050651fba57e5ffbd406f5421289f7089cd Mon Sep 17 00:00:00 2001 From: Matt Kantor Date: Wed, 12 Feb 2025 11:48:27 -0500 Subject: [PATCH 1/2] Drop `isUnelaborated`, use `isExpression` instead These represented the same concept. I'll clean up the separate tracking of unelaboratedness in the next commit. --- src/language/semantics.ts | 1 - src/language/semantics/semantic-graph.ts | 10 +++------- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/src/language/semantics.ts b/src/language/semantics.ts index ce67e1e..443134c 100644 --- a/src/language/semantics.ts +++ b/src/language/semantics.ts @@ -67,7 +67,6 @@ export { applyKeyPathToSemanticGraph, containsAnyUnelaboratedNodes, isSemanticGraph, - isUnelaborated, matchSemanticGraph, serialize, stringifySemanticGraphForEndUser, diff --git a/src/language/semantics/semantic-graph.ts b/src/language/semantics/semantic-graph.ts index 078c36d..59fe817 100644 --- a/src/language/semantics/semantic-graph.ts +++ b/src/language/semantics/semantic-graph.ts @@ -8,6 +8,7 @@ import type { import type { Atom, Molecule } from '../parsing.js' import type { Canonicalized } from '../parsing/syntax-tree.js' import { inlinePlz, unparse } from '../unparsing.js' +import { isExpression } from './expression.js' import { serializeFunctionNode, type FunctionNode } from './function-node.js' import { stringifyKeyPathForEndUser, type KeyPath } from './key-path.js' import { @@ -49,15 +50,10 @@ export const applyKeyPathToSemanticGraph = ( } } -export const isUnelaborated = (node: SemanticGraph | Molecule): boolean => - typeof node !== 'string' && - unelaboratedKey in node && - node[unelaboratedKey] === true - export const containsAnyUnelaboratedNodes = ( node: SemanticGraph | Molecule, ): boolean => { - if (isUnelaborated(node)) { + if (isExpression(node)) { return true } else if (typeof node === 'object') { for (const propertyValue of Object.values(node)) { @@ -113,7 +109,7 @@ export const updateValueAtKeyPathInSemanticGraph = ( operation, ), updatedNode => - (isUnelaborated(node) + (isExpression(node) ? makeUnelaboratedObjectNode : makeObjectNode)({ ...node, From e80cf4a2a05d2e81fd5f6d60972da77e79c1d976 Mon Sep 17 00:00:00 2001 From: Matt Kantor Date: Wed, 12 Feb 2025 11:52:26 -0500 Subject: [PATCH 2/2] Clean up now-unused `unelaboratedKey` and `makeUnelaboratedObjectNode` --- src/language/runtime/keywords.ts | 10 ++-------- src/language/semantics.ts | 1 - .../semantics/expression-elaboration.ts | 13 +++---------- .../semantics/expressions/apply-expression.ts | 8 ++++---- .../semantics/expressions/check-expression.ts | 8 ++++---- .../expressions/expression-utilities.ts | 10 +++------- .../expressions/function-expression.ts | 12 ++++-------- .../semantics/expressions/index-expression.ts | 8 ++++---- .../semantics/expressions/lookup-expression.ts | 12 ++++-------- .../expressions/runtime-expression.ts | 9 +++------ src/language/semantics/object-node.ts | 18 +----------------- src/language/semantics/semantic-graph.ts | 11 ++--------- 12 files changed, 34 insertions(+), 86 deletions(-) diff --git a/src/language/runtime/keywords.ts b/src/language/runtime/keywords.ts index 8e44301..4753e04 100644 --- a/src/language/runtime/keywords.ts +++ b/src/language/runtime/keywords.ts @@ -14,10 +14,7 @@ import { type KeywordHandlers, type SemanticGraph, } from '../semantics.js' -import { - lookupPropertyOfObjectNode, - makeUnelaboratedObjectNode, -} from '../semantics/object-node.js' +import { lookupPropertyOfObjectNode } from '../semantics/object-node.js' import { prettyJson } from '../unparsing.js' const unserializableFunction = () => @@ -169,10 +166,7 @@ const lookupWithinExpression = ( expression: Expression, ): Option => { for (const key of keyAliases) { - const result = lookupPropertyOfObjectNode( - key, - makeUnelaboratedObjectNode(expression), - ) + const result = lookupPropertyOfObjectNode(key, makeObjectNode(expression)) if (!option.isNone(result)) { return result } diff --git a/src/language/semantics.ts b/src/language/semantics.ts index 443134c..16232ea 100644 --- a/src/language/semantics.ts +++ b/src/language/semantics.ts @@ -59,7 +59,6 @@ export { isObjectNode, lookupPropertyOfObjectNode, makeObjectNode, - makeUnelaboratedObjectNode, type ObjectNode, } from './semantics/object-node.js' export { prelude } from './semantics/prelude.js' diff --git a/src/language/semantics/expression-elaboration.ts b/src/language/semantics/expression-elaboration.ts index 1a54147..2882e6a 100644 --- a/src/language/semantics/expression-elaboration.ts +++ b/src/language/semantics/expression-elaboration.ts @@ -7,11 +7,7 @@ import type { Atom, Molecule, SyntaxTree } from '../parsing.js' import type { Expression } from './expression.js' import type { KeyPath } from './key-path.js' import { isKeyword, type Keyword } from './keyword.js' -import { - makeObjectNode, - makeUnelaboratedObjectNode, - type ObjectNode, -} from './object-node.js' +import { makeObjectNode, type ObjectNode } from './object-node.js' import { extractStringValueIfPossible, updateValueAtKeyPathInSemanticGraph, @@ -44,10 +40,7 @@ export const elaborate = ( elaborateWithContext(program, { keywordHandlers, location: [], - program: - typeof program === 'string' - ? program - : makeUnelaboratedObjectNode(program), + program: typeof program === 'string' ? program : makeObjectNode(program), }) export const elaborateWithContext = ( @@ -161,7 +154,7 @@ const handleObjectNodeWhichMayBeAExpression = ( const { 0: possibleKeyword, ...possibleArguments } = node return isKeyword(possibleKeyword) ? context.keywordHandlers[possibleKeyword]( - makeUnelaboratedObjectNode({ + makeObjectNode({ ...possibleArguments, 0: possibleKeyword, }), diff --git a/src/language/semantics/expressions/apply-expression.ts b/src/language/semantics/expressions/apply-expression.ts index d74b203..87d91b5 100644 --- a/src/language/semantics/expressions/apply-expression.ts +++ b/src/language/semantics/expressions/apply-expression.ts @@ -2,8 +2,8 @@ import either, { type Either } from '@matt.kantor/either' import type { ElaborationError } from '../../errors.js' import type { Molecule } from '../../parsing.js' import { isSpecificExpression } from '../expression.js' -import { makeUnelaboratedObjectNode, type ObjectNode } from '../object-node.js' -import { type SemanticGraph, type unelaboratedKey } from '../semantic-graph.js' +import { makeObjectNode, type ObjectNode } from '../object-node.js' +import { type SemanticGraph } from '../semantic-graph.js' import { readArgumentsFromExpression } from './expression-utilities.js' export type ApplyExpression = ObjectNode & { @@ -34,8 +34,8 @@ export const makeApplyExpression = ({ }: { readonly function: SemanticGraph | Molecule readonly argument: SemanticGraph | Molecule -}): ApplyExpression & { readonly [unelaboratedKey]: true } => - makeUnelaboratedObjectNode({ +}): ApplyExpression => + makeObjectNode({ 0: '@apply', function: f, argument, diff --git a/src/language/semantics/expressions/check-expression.ts b/src/language/semantics/expressions/check-expression.ts index 69d37f7..39b234a 100644 --- a/src/language/semantics/expressions/check-expression.ts +++ b/src/language/semantics/expressions/check-expression.ts @@ -2,8 +2,8 @@ import either, { type Either } from '@matt.kantor/either' import type { ElaborationError } from '../../errors.js' import type { Molecule } from '../../parsing.js' import { isSpecificExpression } from '../expression.js' -import { makeUnelaboratedObjectNode, type ObjectNode } from '../object-node.js' -import { type SemanticGraph, type unelaboratedKey } from '../semantic-graph.js' +import { makeObjectNode, type ObjectNode } from '../object-node.js' +import { type SemanticGraph } from '../semantic-graph.js' import { readArgumentsFromExpression } from './expression-utilities.js' export type CheckExpression = ObjectNode & { @@ -34,8 +34,8 @@ export const makeCheckExpression = ({ }: { value: SemanticGraph | Molecule type: SemanticGraph | Molecule -}): CheckExpression & { readonly [unelaboratedKey]: true } => - makeUnelaboratedObjectNode({ +}): CheckExpression => + makeObjectNode({ 0: '@check', value, type, diff --git a/src/language/semantics/expressions/expression-utilities.ts b/src/language/semantics/expressions/expression-utilities.ts index 4edaed9..a34b97a 100644 --- a/src/language/semantics/expressions/expression-utilities.ts +++ b/src/language/semantics/expressions/expression-utilities.ts @@ -7,7 +7,7 @@ import type { Expression } from '../expression.js' import { stringifyKeyPathForEndUser } from '../key-path.js' import { lookupPropertyOfObjectNode, - makeUnelaboratedObjectNode, + makeObjectNode, type ObjectNode, } from '../object-node.js' import { @@ -18,8 +18,7 @@ import { export const asSemanticGraph = ( value: SemanticGraph | Molecule, -): SemanticGraph => - isSemanticGraph(value) ? value : makeUnelaboratedObjectNode(value) +): SemanticGraph => (isSemanticGraph(value) ? value : makeObjectNode(value)) export const locateSelf = (context: ExpressionContext) => option.match(applyKeyPathToSemanticGraph(context.program, context.location), { @@ -73,10 +72,7 @@ const lookupWithinExpression = ( expression: Expression, ): Option => { for (const key of keyAliases) { - const result = lookupPropertyOfObjectNode( - key, - makeUnelaboratedObjectNode(expression), - ) + const result = lookupPropertyOfObjectNode(key, makeObjectNode(expression)) if (!option.isNone(result)) { return result } diff --git a/src/language/semantics/expressions/function-expression.ts b/src/language/semantics/expressions/function-expression.ts index b67e469..218d369 100644 --- a/src/language/semantics/expressions/function-expression.ts +++ b/src/language/semantics/expressions/function-expression.ts @@ -2,12 +2,8 @@ import either, { type Either } from '@matt.kantor/either' import type { ElaborationError } from '../../errors.js' import type { Atom, Molecule } from '../../parsing.js' import { isSpecificExpression } from '../expression.js' -import { makeUnelaboratedObjectNode, type ObjectNode } from '../object-node.js' -import { - serialize, - type SemanticGraph, - type unelaboratedKey, -} from '../semantic-graph.js' +import { makeObjectNode, type ObjectNode } from '../object-node.js' +import { serialize, type SemanticGraph } from '../semantic-graph.js' import { asSemanticGraph, readArgumentsFromExpression, @@ -46,8 +42,8 @@ export const readFunctionExpression = ( export const makeFunctionExpression = ( parameter: Atom, body: SemanticGraph | Molecule, -): FunctionExpression & { readonly [unelaboratedKey]: true } => - makeUnelaboratedObjectNode({ +): FunctionExpression => + makeObjectNode({ 0: '@function', parameter, body, diff --git a/src/language/semantics/expressions/index-expression.ts b/src/language/semantics/expressions/index-expression.ts index 3ae9df9..3e2b574 100644 --- a/src/language/semantics/expressions/index-expression.ts +++ b/src/language/semantics/expressions/index-expression.ts @@ -5,10 +5,10 @@ import { isSpecificExpression } from '../expression.js' import { keyPathFromObjectNodeOrMolecule } from '../key-path.js' import { isObjectNode, - makeUnelaboratedObjectNode, + makeObjectNode, type ObjectNode, } from '../object-node.js' -import { type SemanticGraph, type unelaboratedKey } from '../semantic-graph.js' +import { type SemanticGraph } from '../semantic-graph.js' import { asSemanticGraph, readArgumentsFromExpression, @@ -61,8 +61,8 @@ export const makeIndexExpression = ({ }: { readonly query: ObjectNode | Molecule readonly object: ObjectNode | Molecule -}): IndexExpression & { readonly [unelaboratedKey]: true } => - makeUnelaboratedObjectNode({ +}): IndexExpression => + makeObjectNode({ 0: '@index', object, query, diff --git a/src/language/semantics/expressions/lookup-expression.ts b/src/language/semantics/expressions/lookup-expression.ts index cf34e0f..0fde7cb 100644 --- a/src/language/semantics/expressions/lookup-expression.ts +++ b/src/language/semantics/expressions/lookup-expression.ts @@ -7,12 +7,8 @@ import { keyPathFromObjectNodeOrMolecule, keyPathToMolecule, } from '../key-path.js' -import { - makeObjectNode, - makeUnelaboratedObjectNode, - type ObjectNode, -} from '../object-node.js' -import { type SemanticGraph, type unelaboratedKey } from '../semantic-graph.js' +import { makeObjectNode, type ObjectNode } from '../object-node.js' +import { type SemanticGraph } from '../semantic-graph.js' import { asSemanticGraph, readArgumentsFromExpression, @@ -56,8 +52,8 @@ export const readLookupExpression = ( export const makeLookupExpression = ( query: ObjectNode | Molecule, -): LookupExpression & { readonly [unelaboratedKey]: true } => - makeUnelaboratedObjectNode({ +): LookupExpression => + makeObjectNode({ 0: '@lookup', query, }) diff --git a/src/language/semantics/expressions/runtime-expression.ts b/src/language/semantics/expressions/runtime-expression.ts index b8cd1b9..a70af86 100644 --- a/src/language/semantics/expressions/runtime-expression.ts +++ b/src/language/semantics/expressions/runtime-expression.ts @@ -3,11 +3,10 @@ import type { ElaborationError } from '../../errors.js' import type { Molecule } from '../../parsing.js' import { isSpecificExpression } from '../expression.js' import { isFunctionNode } from '../function-node.js' -import { makeUnelaboratedObjectNode, type ObjectNode } from '../object-node.js' +import { makeObjectNode, type ObjectNode } from '../object-node.js' import { containsAnyUnelaboratedNodes, type SemanticGraph, - type unelaboratedKey, } from '../semantic-graph.js' import { asSemanticGraph, @@ -46,10 +45,8 @@ export const readRuntimeExpression = ( message: 'not an expression', }) -export const makeRuntimeExpression = ( - f: SemanticGraph, -): RuntimeExpression & { readonly [unelaboratedKey]: true } => - makeUnelaboratedObjectNode({ +export const makeRuntimeExpression = (f: SemanticGraph): RuntimeExpression => + makeObjectNode({ 0: '@runtime', function: f, }) diff --git a/src/language/semantics/object-node.ts b/src/language/semantics/object-node.ts index 7f554d7..cd26af7 100644 --- a/src/language/semantics/object-node.ts +++ b/src/language/semantics/object-node.ts @@ -3,17 +3,11 @@ import option, { type Option } from '@matt.kantor/option' import type { Writable } from '../../utility-types.js' import type { UnserializableValueError } from '../errors.js' import type { Atom, Molecule } from '../parsing.js' -import { - nodeTag, - serialize, - unelaboratedKey, - type SemanticGraph, -} from './semantic-graph.js' +import { nodeTag, serialize, type SemanticGraph } from './semantic-graph.js' export type ObjectNode = { readonly [nodeTag]: 'object' readonly [key: Atom]: SemanticGraph | Molecule - readonly [unelaboratedKey]?: true } export const isObjectNode = (node: SemanticGraph) => @@ -38,16 +32,6 @@ export const makeObjectNode = < [nodeTag]: 'object', }) -export const makeUnelaboratedObjectNode = < - const Properties extends Readonly>, ->( - properties: Properties, -): ObjectNode & Properties & { readonly [unelaboratedKey]: true } => ({ - ...properties, - [nodeTag]: 'object', - [unelaboratedKey]: true, -}) - export const serializeObjectNode = ( node: ObjectNode, ): Either => { diff --git a/src/language/semantics/semantic-graph.ts b/src/language/semantics/semantic-graph.ts index 59fe817..7dc2db0 100644 --- a/src/language/semantics/semantic-graph.ts +++ b/src/language/semantics/semantic-graph.ts @@ -13,15 +13,12 @@ import { serializeFunctionNode, type FunctionNode } from './function-node.js' import { stringifyKeyPathForEndUser, type KeyPath } from './key-path.js' import { makeObjectNode, - makeUnelaboratedObjectNode, serializeObjectNode, type ObjectNode, } from './object-node.js' export const nodeTag = Symbol('nodeTag') -export const unelaboratedKey = Symbol('unelaborated') - export type SemanticGraph = Atom | FunctionNode | ObjectNode export const applyKeyPathToSemanticGraph = ( @@ -109,9 +106,7 @@ export const updateValueAtKeyPathInSemanticGraph = ( operation, ), updatedNode => - (isExpression(node) - ? makeUnelaboratedObjectNode - : makeObjectNode)({ + (isExpression(node) ? makeObjectNode : makeObjectNode)({ ...node, [firstKey]: updatedNode, }), @@ -189,6 +184,4 @@ export const isSemanticGraph = ( const syntaxTreeToSemanticGraph = ( syntaxTree: Atom | Molecule, ): ObjectNode | Atom => - typeof syntaxTree === 'string' - ? syntaxTree - : makeUnelaboratedObjectNode(syntaxTree) + typeof syntaxTree === 'string' ? syntaxTree : makeObjectNode(syntaxTree)