Skip to content

Commit 88c25ca

Browse files
Adam Erbsvc-squareup-copybara
authored andcommitted
More robust error handling in payload parser
GitOrigin-RevId: 6708daf1d3ef13708579f715baedc4fbe5ef0966
1 parent 1915641 commit 88c25ca

File tree

14 files changed

+133
-96
lines changed

14 files changed

+133
-96
lines changed

misk-admin-web-actions/src/index.html

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,11 @@
2626
background-color: #e69a9a;
2727
position: absolute;
2828
}
29+
.error-marker {
30+
background-color: rgba(255, 0, 0, 0.2);
31+
border-bottom: 2px solid red;
32+
position: absolute;
33+
}
2934
</style>
3035
</head>
3136
<body>

misk-admin-web-actions/src/index.tsx

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import {
1212
Input,
1313
IconButton,
1414
Button,
15+
useToast,
1516
} from '@chakra-ui/react';
1617
import { DeleteIcon, AddIcon } from '@chakra-ui/icons';
1718
import HelpPanel from '@web-actions/ui/HelpPanel';
@@ -43,6 +44,7 @@ function App() {
4344
}));
4445
const endPointSelectorRef = useRef<EndpointSelector>(null);
4546
const requestEditorRef = useRef<RequestEditor>(null);
47+
const toast = useToast();
4648

4749
const {
4850
submit: handleSubmitRequest,
@@ -55,7 +57,7 @@ function App() {
5557
() => requestEditorRef.current?.editor?.getValue() ?? '',
5658
);
5759

58-
useAppEvent<ActionGroup>(APP_EVENTS.ENDPOINT_SELECTED, (selectedAction) => {
60+
useAppEvent(APP_EVENTS.ENDPOINT_SELECTED, (selectedAction: ActionGroup) => {
5961
const callables = selectedAction.getCallablesByMethod();
6062
const defaultCallable = callables[0];
6163

@@ -83,6 +85,16 @@ function App() {
8385
endPointSelectorRef.current?.focusSelect();
8486
});
8587

88+
useAppEvent(APP_EVENTS.SHOW_ERROR_TOAST, () => {
89+
toast({
90+
title: 'Error',
91+
description: 'There are syntax or field name errors in the JSON Request',
92+
status: 'error',
93+
duration: 5000,
94+
isClosable: true,
95+
});
96+
});
97+
8698
useEffect(() => {
8799
fetchCached<MiskMetadataResponse>(`/api/web-actions/metadata`).finally(
88100
() => {

misk-admin-web-actions/src/web-actions/events/appEvents.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,15 @@ export type AppEventType =
22
| 'focus-endpoint-selector'
33
| 'toggle-help'
44
| 'submit-request'
5-
| 'endpoint-selected';
5+
| 'endpoint-selected'
6+
| 'show-error-toast';
67

78
export const APP_EVENTS = {
89
FOCUS_ENDPOINT_SELECTOR: 'focus-endpoint-selector' as const,
910
TOGGLE_HELP: 'toggle-help' as const,
1011
SUBMIT_REQUEST: 'submit-request' as const,
1112
ENDPOINT_SELECTED: 'endpoint-selected' as const,
13+
SHOW_ERROR_TOAST: 'show-error-toast' as const,
1214
};
1315

1416
class AppEventBus {

misk-admin-web-actions/src/web-actions/parsing/CommandParser.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ import Unexpected from '@web-actions/parsing/ast/Unexpected';
1313
import NumLiteral from '@web-actions/parsing/ast/NumLiteral';
1414
import BoolLiteral from '@web-actions/parsing/ast/BoolLiteral';
1515

16-
export function parseDocument(text: string, cursorIndex: number): TopLevel {
16+
export function parseDocument(text: string, cursorIndex?: number): TopLevel {
1717
return new CommandParser(text, cursorIndex).parse();
1818
}
1919

@@ -172,13 +172,13 @@ export class CommandParser {
172172
} else {
173173
const u = this.readUnexpected();
174174
if (u) {
175-
unexpected.push(u);
175+
arr.push(u);
176176
} else {
177177
break;
178178
}
179179
}
180180
}
181-
return new Arr(arr, unexpected);
181+
return new Arr(arr);
182182
});
183183
}
184184

misk-admin-web-actions/src/web-actions/parsing/__test__/parser.spec.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { CommandParser } from '@web-actions/parsing/CommandParser';
22
import StrLiteral from '@web-actions/parsing/ast/StrLiteral';
33
import Obj from '@web-actions/parsing/ast/Obj';
44
import Arr from '@web-actions/parsing/ast/Arr';
5+
import Unexpected from 'src/web-actions/parsing/ast/Unexpected';
56

67
function parser(text: string): CommandParser {
78
return new CommandParser(text);
@@ -54,8 +55,7 @@ test('array', () => {
5455
test('array error', () => {
5556
const result = parser(`["a" ! ]`).parseArr();
5657

57-
expect(result?.values.length).toEqual(1);
58+
expect(result?.values.length).toEqual(2);
5859
expect(result?.values[0].as<StrLiteral>()?.value).toEqual('a');
59-
expect(result?.unexpected.length).toEqual(1);
60-
expect(result?.unexpected[0].value).toEqual('!');
60+
expect(result?.values[1].as<Unexpected>()?.value).toEqual('!');
6161
});

misk-admin-web-actions/src/web-actions/parsing/ast/Action.ts

Lines changed: 0 additions & 50 deletions
This file was deleted.

misk-admin-web-actions/src/web-actions/parsing/ast/Arr.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,16 @@
11
import AstNode from '@web-actions/parsing/ast/AstNode';
22

33
import JsonValue from '@web-actions/parsing/ast/JsonValue';
4-
import Unexpected from '@web-actions/parsing/ast/Unexpected';
54
import MiskType from '@web-actions/api/MiskType';
65
import { MiskObjectTypes } from '@web-actions/api/responseTypes';
76

87
export default class Arr extends JsonValue {
98
values: JsonValue[];
109
type?: MiskType;
1110

12-
constructor(values: JsonValue[], unexpected: Unexpected[]) {
11+
constructor(values: JsonValue[]) {
1312
super();
1413
this.values = values;
15-
this.unexpected = unexpected;
1614

1715
for (const value of values) {
1816
value.parent = this;

misk-admin-web-actions/src/web-actions/parsing/ast/AstNode.ts

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,7 @@
1-
import Unexpected from '@web-actions/parsing/ast/Unexpected';
2-
31
export default class AstNode {
42
start?: number;
53
end?: number;
64
hasCursor: boolean = false;
7-
unexpected: Unexpected[] = [];
8-
95
parent?: AstNode;
106

117
childNodes(): AstNode[] {
@@ -36,6 +32,18 @@ export default class AstNode {
3632
return null;
3733
}
3834

35+
findAll(predicate: (a: AstNode) => boolean): AstNode[] {
36+
const arr: AstNode[] = [];
37+
if (predicate(this)) {
38+
arr.push(this);
39+
}
40+
for (const child of this.childNodes()) {
41+
const result = child.findAll(predicate);
42+
arr.push(...result);
43+
}
44+
return arr;
45+
}
46+
3947
render(): string {
4048
throw new Error('Method not implemented');
4149
}

misk-admin-web-actions/src/web-actions/parsing/ast/Field.ts

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ import MiskType from '@web-actions/api/MiskType';
1212

1313
export default class Field extends AstNode {
1414
name: StrLiteral;
15-
value: JsonValue | null;
15+
value: JsonValue | Unexpected | null;
1616

1717
colonIndex: number | null;
1818
cursorInValuePosition: boolean = false;
@@ -27,14 +27,7 @@ export default class Field extends AstNode {
2727
super();
2828
this.colonIndex = colonIndex;
2929
this.name = name;
30-
if (value instanceof JsonValue) {
31-
this.value = value ?? null;
32-
} else if (value instanceof Unexpected) {
33-
this.unexpected = [value];
34-
this.value = null;
35-
} else {
36-
this.value = null;
37-
}
30+
this.value = value ?? null;
3831

3932
if (this.value) {
4033
this.value.parent = this;

misk-admin-web-actions/src/web-actions/parsing/ast/Obj.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import MiskType from '@web-actions/api/MiskType';
1313
export default class Obj extends JsonValue {
1414
fields: Field[];
1515
type?: MiskObjectType;
16+
unexpected: Unexpected[];
1617

1718
constructor(fields: Field[], unexpected: Unexpected[]) {
1819
super();
@@ -24,7 +25,7 @@ export default class Obj extends JsonValue {
2425
}
2526

2627
childNodes(): AstNode[] {
27-
return this.fields;
28+
return [...this.fields, ...this.unexpected];
2829
}
2930

3031
render(): string {

0 commit comments

Comments
 (0)