Skip to content

Commit 0b00a93

Browse files
authored
Merge pull request #23 from mkantor/unparsing-iifes
Fix unparsing immediately-invoked function expressions
2 parents d610795 + 00b4837 commit 0b00a93

File tree

2 files changed

+66
-16
lines changed

2 files changed

+66
-16
lines changed

src/language/compiling/unparsing.test.ts

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,18 @@ testCases(
4646
},
4747
either.makeRight('{ identity: a => :a, test: :identity("it works!") }'),
4848
],
49+
[
50+
{
51+
0: '@apply',
52+
function: {
53+
0: '@function',
54+
parameter: 'a',
55+
body: { 0: '@lookup', 1: 'a' },
56+
},
57+
argument: 'it works!',
58+
},
59+
either.makeRight('(a => :a)("it works!")'),
60+
],
4961
])
5062

5163
testCases(
@@ -82,6 +94,18 @@ testCases(
8294
'{\n identity: a => :a\n test: :identity("it works!")\n}',
8395
),
8496
],
97+
[
98+
{
99+
0: '@apply',
100+
function: {
101+
0: '@function',
102+
parameter: 'a',
103+
body: { 0: '@lookup', 1: 'a' },
104+
},
105+
argument: 'it works!',
106+
},
107+
either.makeRight('(a => :a)("it works!")'),
108+
],
85109
])
86110

87111
testCases(
@@ -120,4 +144,18 @@ testCases(
120144
'{\n "identity": {\n "0": "@function",\n "parameter": "a",\n "body": {\n "0": "@lookup",\n "1": "a"\n }\n },\n "test": {\n "0": "@apply",\n "function": {\n "0": "@lookup",\n "1": "identity"\n },\n "argument": "it works!"\n }\n}',
121145
),
122146
],
147+
[
148+
{
149+
0: '@apply',
150+
function: {
151+
0: '@function',
152+
parameter: 'a',
153+
body: { 0: '@lookup', 1: 'a' },
154+
},
155+
argument: 'it works!',
156+
},
157+
either.makeRight(
158+
'{\n "0": "@apply",\n "function": {\n "0": "@function",\n "parameter": "a",\n "body": {\n "0": "@lookup",\n "1": "a"\n }\n },\n "argument": "it works!"\n}',
159+
),
160+
],
123161
])

src/language/unparsing/plz-utilities.ts

Lines changed: 28 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -128,25 +128,37 @@ const escapeStringContents = (value: string) =>
128128
const unparseSugaredApply = (
129129
expression: ApplyExpression,
130130
unparseAtomOrMolecule: UnparseAtomOrMolecule,
131-
) =>
132-
either.flatMap(serializeIfNeeded(expression.function), serializedFunction =>
131+
) => {
132+
const functionUnparseResult = either.map(
133133
either.flatMap(
134-
unparseAtomOrMolecule(serializedFunction),
135-
functionToApplyAsString =>
136-
either.flatMap(
137-
serializeIfNeeded(expression.argument),
138-
serializedArgument =>
139-
either.map(
140-
unparseAtomOrMolecule(serializedArgument),
141-
argumentAsString =>
142-
functionToApplyAsString
143-
.concat(openParenthesis)
144-
.concat(argumentAsString)
145-
.concat(closeParenthesis),
146-
),
147-
),
134+
serializeIfNeeded(expression.function),
135+
unparseAtomOrMolecule,
148136
),
137+
unparsedFunction =>
138+
either.isRight(readFunctionExpression(expression.function))
139+
? // Immediately-applied function expressions need parentheses.
140+
openParenthesis.concat(unparsedFunction).concat(closeParenthesis)
141+
: unparsedFunction,
142+
)
143+
if (either.isLeft(functionUnparseResult)) {
144+
return functionUnparseResult
145+
}
146+
147+
const argumentUnparseResult = either.flatMap(
148+
serializeIfNeeded(expression.argument),
149+
unparseAtomOrMolecule,
149150
)
151+
if (either.isLeft(argumentUnparseResult)) {
152+
return argumentUnparseResult
153+
}
154+
155+
return either.makeRight(
156+
functionUnparseResult.value
157+
.concat(openParenthesis)
158+
.concat(argumentUnparseResult.value)
159+
.concat(closeParenthesis),
160+
)
161+
}
150162

151163
const unparseSugaredFunction = (
152164
expression: FunctionExpression,

0 commit comments

Comments
 (0)