Skip to content

Commit 052cfe7

Browse files
authored
Merge pull request #44 from mkantor/panic-keyword
Add `@panic` keyword expression
2 parents a348871 + df1e0cb commit 052cfe7

File tree

6 files changed

+70
-1
lines changed

6 files changed

+70
-1
lines changed

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -153,7 +153,7 @@ keyword expressions.
153153
Under the hood, keyword expressions are modeled as objects. For example, `:foo`
154154
desugars to `{@lookup key: foo}`. All such expressions have a key `0` referring
155155
to a value that is an `@`-prefixed atom (the keyword). Keywords include
156-
`@function`, `@lookup`, `@apply`, `@check`, `@index`, and `@runtime`.
156+
`@function`, `@lookup`, `@apply`, `@check`, `@index`, `@panic`, and `@runtime`.
157157

158158
Currently only `@function`, `@lookup`, `@index`, and `@apply` have syntax
159159
sugars.

src/end-to-end.test.ts

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,22 @@ testCases(endToEnd, code => code)('end-to-end tests', [
2727
['{a,1:overwritten,c}', either.makeRight({ 0: 'a', 1: 'c' })],
2828
['{overwritten,0:a,c}', either.makeRight({ 0: 'a', 1: 'c' })],
2929
['{@check type:true value:true}', either.makeRight('true')],
30+
[
31+
'{@panic}',
32+
result => {
33+
assert(either.isLeft(result))
34+
assert('kind' in result.value)
35+
assert.deepEqual(result.value.kind, 'panic')
36+
},
37+
],
38+
[
39+
'{@runtime _ => {@panic}}',
40+
result => {
41+
assert(either.isLeft(result))
42+
assert('kind' in result.value)
43+
assert.deepEqual(result.value.kind, 'panic')
44+
},
45+
],
3046
['{a:A b:{@lookup a}}', either.makeRight({ a: 'A', b: 'A' })],
3147
['{a:A b: :a}', either.makeRight({ a: 'A', b: 'A' })],
3248
['{a:A {@lookup a}}', either.makeRight({ a: 'A', 0: 'A' })],
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import either from '@matt.kantor/either'
2+
import assert from 'node:assert'
3+
import { elaborationSuite } from '../test-utilities.test.js'
4+
5+
elaborationSuite('@panic', [
6+
[
7+
{ 0: '@panic' },
8+
output => {
9+
assert(either.isLeft(output))
10+
assert.deepEqual(output.value.kind, 'panic')
11+
},
12+
],
13+
[
14+
{ 0: '@panic', 1: 'blah' },
15+
output => {
16+
assert(either.isLeft(output))
17+
assert.deepEqual(output.value.kind, 'panic')
18+
},
19+
],
20+
[
21+
{ 0: '@panic', message: { a: { b: 'c' } } },
22+
output => {
23+
assert(either.isLeft(output))
24+
assert.deepEqual(output.value.kind, 'panic')
25+
},
26+
],
27+
])
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
import either, { type Either } from '@matt.kantor/either'
2+
import type { ElaborationError } from '../../../errors.js'
3+
import {
4+
asSemanticGraph,
5+
stringifySemanticGraphForEndUser,
6+
type Expression,
7+
type ExpressionContext,
8+
type KeywordHandler,
9+
type SemanticGraph,
10+
} from '../../../semantics.js'
11+
12+
export const panicKeywordHandler: KeywordHandler = (
13+
expression: Expression,
14+
_context: ExpressionContext,
15+
): Either<ElaborationError, SemanticGraph> =>
16+
either.makeLeft({
17+
kind: 'panic',
18+
message: stringifySemanticGraphForEndUser(asSemanticGraph(expression)),
19+
})

src/language/compiling/semantics/keywords.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import { checkKeywordHandler } from './keyword-handlers/check-handler.js'
44
import { functionKeywordHandler } from './keyword-handlers/function-handler.js'
55
import { indexKeywordHandler } from './keyword-handlers/index-handler.js'
66
import { lookupKeywordHandler } from './keyword-handlers/lookup-handler.js'
7+
import { panicKeywordHandler } from './keyword-handlers/panic-handler.js'
78
import { runtimeKeywordHandler } from './keyword-handlers/runtime-handler.js'
89
import { todoKeywordHandler } from './keyword-handlers/todo-handler.js'
910

@@ -33,6 +34,11 @@ export const keywordHandlers: KeywordHandlers = {
3334
*/
3435
'@lookup': lookupKeywordHandler,
3536

37+
/**
38+
* Immediately terminates the process when evaluated.
39+
*/
40+
'@panic': panicKeywordHandler,
41+
3642
/**
3743
* Defers evaluation until runtime.
3844
*/

src/language/semantics/keyword.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ export const isKeyword = (input: string) =>
44
input === '@function' ||
55
input === '@index' ||
66
input === '@lookup' ||
7+
input === '@panic' ||
78
input === '@runtime' ||
89
input === '@todo'
910

0 commit comments

Comments
 (0)