aboutsummaryrefslogtreecommitdiffstats
path: root/subprojects/frontend
diff options
context:
space:
mode:
authorLibravatar Kristóf Marussy <kristof@marussy.com>2024-02-02 16:28:19 +0100
committerLibravatar Kristóf Marussy <kristof@marussy.com>2024-02-02 17:36:24 +0100
commit2dfcb286216419976368ad926f8ac7f018aa2bf9 (patch)
treeb9d235ebf2049e42e58126e743c782333d64681a /subprojects/frontend
parentrefactor: serialize solutions as modules (diff)
downloadrefinery-2dfcb286216419976368ad926f8ac7f018aa2bf9.tar.gz
refinery-2dfcb286216419976368ad926f8ac7f018aa2bf9.tar.zst
refinery-2dfcb286216419976368ad926f8ac7f018aa2bf9.zip
refactor(language): name disambiguation
* Use fully qualified names starting with :: (as in C++) to unambiguously refer to an element. * Name shadowing within modules.
Diffstat (limited to 'subprojects/frontend')
-rw-r--r--subprojects/frontend/src/editor/EditorTheme.ts4
-rw-r--r--subprojects/frontend/src/language/problem.grammar11
-rw-r--r--subprojects/frontend/src/language/problemLanguageSupport.ts4
-rw-r--r--subprojects/frontend/src/language/tokens.ts46
-rw-r--r--subprojects/frontend/src/xtext/ContentAssistService.ts8
-rw-r--r--subprojects/frontend/types/grammar.d.ts6
6 files changed, 71 insertions, 8 deletions
diff --git a/subprojects/frontend/src/editor/EditorTheme.ts b/subprojects/frontend/src/editor/EditorTheme.ts
index f499b0d9..4978c7f7 100644
--- a/subprojects/frontend/src/editor/EditorTheme.ts
+++ b/subprojects/frontend/src/editor/EditorTheme.ts
@@ -40,7 +40,9 @@ function createTypeHashStyles(
40export default styled('div', { 40export default styled('div', {
41 name: 'EditorTheme', 41 name: 'EditorTheme',
42 shouldForwardProp: (propName) => 42 shouldForwardProp: (propName) =>
43 propName !== 'showLineNumbers' && propName !== 'showActiveLine', 43 propName !== 'showLineNumbers' &&
44 propName !== 'showActiveLine' &&
45 propName !== 'colorIdentifiers',
44})<{ 46})<{
45 showLineNumbers: boolean; 47 showLineNumbers: boolean;
46 showActiveLine: boolean; 48 showActiveLine: boolean;
diff --git a/subprojects/frontend/src/language/problem.grammar b/subprojects/frontend/src/language/problem.grammar
index ac451e7a..e39ce102 100644
--- a/subprojects/frontend/src/language/problem.grammar
+++ b/subprojects/frontend/src/language/problem.grammar
@@ -1,5 +1,5 @@
1/* 1/*
2 * SPDX-FileCopyrightText: 2021-2023 The Refinery Authors <https://refinery.tools/> 2 * SPDX-FileCopyrightText: 2021-2024 The Refinery Authors <https://refinery.tools/>
3 * 3 *
4 * SPDX-License-Identifier: EPL-2.0 4 * SPDX-License-Identifier: EPL-2.0
5 */ 5 */
@@ -22,6 +22,9 @@
22@top Problem { statement* } 22@top Problem { statement* }
23 23
24statement { 24statement {
25 ImportStatement {
26 kw<"import"> QualifiedName (kw<"as"> identifier)? "."
27 } |
25 Assertion { 28 Assertion {
26 kw<"default">? (NotOp | UnknownOp)? RelationName 29 kw<"default">? (NotOp | UnknownOp)? RelationName
27 ParameterList<AssertionArgument> 30 ParameterList<AssertionArgument>
@@ -170,7 +173,7 @@ VariableName[@dynamicPrecedence=10] { QualifiedName ~name }
170 173
171NodeName { QualifiedName } 174NodeName { QualifiedName }
172 175
173QualifiedName[implicitCompletion=true] { identifier ("::" identifier)* } 176QualifiedName[implicitCompletion=true] { "::"? identifier (QualifiedNameSeparator "::" identifier)* }
174 177
175kw<term> { @specialize[@name={term},implicitCompletion=true]<identifier, term> } 178kw<term> { @specialize[@name={term},implicitCompletion=true]<identifier, term> }
176 179
@@ -184,6 +187,10 @@ sep1<separator, content> { content (separator content)* }
184 187
185@skip { LineComment | BlockComment | whitespace } 188@skip { LineComment | BlockComment | whitespace }
186 189
190@external tokens qualifiedNameSeparator from "./tokens" {
191 QualifiedNameSeparator
192}
193
187@tokens { 194@tokens {
188 whitespace { std.whitespace+ } 195 whitespace { std.whitespace+ }
189 196
diff --git a/subprojects/frontend/src/language/problemLanguageSupport.ts b/subprojects/frontend/src/language/problemLanguageSupport.ts
index 2483c2e3..aebccfa4 100644
--- a/subprojects/frontend/src/language/problemLanguageSupport.ts
+++ b/subprojects/frontend/src/language/problemLanguageSupport.ts
@@ -1,5 +1,5 @@
1/* 1/*
2 * SPDX-FileCopyrightText: 2021-2023 The Refinery Authors <https://refinery.tools/> 2 * SPDX-FileCopyrightText: 2021-2024 The Refinery Authors <https://refinery.tools/>
3 * 3 *
4 * SPDX-License-Identifier: EPL-2.0 4 * SPDX-License-Identifier: EPL-2.0
5 */ 5 */
@@ -28,7 +28,7 @@ const parserWithMetadata = parser.configure({
28 LineComment: t.lineComment, 28 LineComment: t.lineComment,
29 BlockComment: t.blockComment, 29 BlockComment: t.blockComment,
30 'module problem class enum pred fn scope': t.definitionKeyword, 30 'module problem class enum pred fn scope': t.definitionKeyword,
31 'declare atom multi': t.definitionKeyword, 31 'import as declare atom multi': t.definitionKeyword,
32 'abstract extends refers contains container opposite': t.modifier, 32 'abstract extends refers contains container opposite': t.modifier,
33 'default error contained containment': t.modifier, 33 'default error contained containment': t.modifier,
34 'true false unknown error': t.keyword, 34 'true false unknown error': t.keyword,
diff --git a/subprojects/frontend/src/language/tokens.ts b/subprojects/frontend/src/language/tokens.ts
new file mode 100644
index 00000000..b5d022f1
--- /dev/null
+++ b/subprojects/frontend/src/language/tokens.ts
@@ -0,0 +1,46 @@
1/*
2 * Copyright (C) 2018-2024 by Marijn Haverbeke <marijnh@gmail.com> and others
3 * Copyright (C) 2024 The Refinery Authors <https://refinery.tools/>
4 *
5 * SPDX-License-Identifier: MIT AND EPL-2.0
6 *
7 * Based on the CSS tokenizer at
8 * https://github.com/lezer-parser/css/blob/790568c968a660a94bf0fbd97a86c66da1c529e5/src/tokens.js
9 */
10
11import { ExternalTokenizer } from '@lezer/lr';
12
13/* eslint-disable-next-line import/no-unresolved --
14 Synthetic import from `@lezer/generator/rollup` cannot be found by ESLint.
15*/
16import { QualifiedNameSeparator } from './problem.grammar.terms';
17
18const colon = 58;
19const underscore = 95;
20
21function isAlpha(ch: number) {
22 return (ch >= 65 && ch <= 90) || (ch >= 97 && ch <= 122) || ch >= 161;
23}
24
25function isDigit(ch: number) {
26 return ch >= 48 && ch <= 57;
27}
28
29function isIdentifier(ch: number) {
30 return isAlpha(ch) || isDigit(ch) || ch === underscore;
31}
32
33/* eslint-disable-next-line import/prefer-default-export --
34 Lezer requires a named export.
35*/
36export const qualifiedNameSeparator = new ExternalTokenizer((input) => {
37 if (input.peek(0) === colon && input.peek(1) === colon) {
38 const previous = input.peek(-1);
39 if (isIdentifier(previous)) {
40 // Inject an extra 0-length token into the token stream to let Lezer
41 // consume the `::` on its own. Explicitly consuming 2 characters here
42 // leads to inconsistent highlighting of qualified names.
43 input.acceptToken(QualifiedNameSeparator);
44 }
45 }
46});
diff --git a/subprojects/frontend/src/xtext/ContentAssistService.ts b/subprojects/frontend/src/xtext/ContentAssistService.ts
index ac8ab36a..d42dde14 100644
--- a/subprojects/frontend/src/xtext/ContentAssistService.ts
+++ b/subprojects/frontend/src/xtext/ContentAssistService.ts
@@ -1,5 +1,5 @@
1/* 1/*
2 * SPDX-FileCopyrightText: 2021-2023 The Refinery Authors <https://refinery.tools/> 2 * SPDX-FileCopyrightText: 2021-2024 The Refinery Authors <https://refinery.tools/>
3 * 3 *
4 * SPDX-License-Identifier: EPL-2.0 4 * SPDX-License-Identifier: EPL-2.0
5 */ 5 */
@@ -108,7 +108,11 @@ function createCompletion(entry: ContentAssistEntry): Completion {
108 boost = -90; 108 boost = -90;
109 break; 109 break;
110 default: 110 default:
111 { 111 if (entry.proposal.startsWith('::')) {
112 // Move absolute names below relative names,
113 // they should only be preferred if no relative name is available.
114 boost = -60;
115 } else {
112 // Penalize qualified names (vs available unqualified names). 116 // Penalize qualified names (vs available unqualified names).
113 const extraSegments = entry.proposal.match(/::/g)?.length || 0; 117 const extraSegments = entry.proposal.match(/::/g)?.length || 0;
114 boost = Math.max(-5 * extraSegments, -50); 118 boost = Math.max(-5 * extraSegments, -50);
diff --git a/subprojects/frontend/types/grammar.d.ts b/subprojects/frontend/types/grammar.d.ts
index 92f99ec3..c7848e33 100644
--- a/subprojects/frontend/types/grammar.d.ts
+++ b/subprojects/frontend/types/grammar.d.ts
@@ -1,6 +1,6 @@
1/* 1/*
2 * Copyright (C) 2018 by Marijn Haverbeke <marijn@haverbeke.berlin> and others 2 * Copyright (C) 2018 by Marijn Haverbeke <marijn@haverbeke.berlin> and others
3 * Copyright (C) 2021-2023 The Refinery Authors <https://refinery.tools/> 3 * Copyright (C) 2021-2024 The Refinery Authors <https://refinery.tools/>
4 * 4 *
5 * SPDX-License-Identifier: MIT 5 * SPDX-License-Identifier: MIT
6 */ 6 */
@@ -10,3 +10,7 @@ declare module '*.grammar' {
10 10
11 export const parser: LRParser; 11 export const parser: LRParser;
12} 12}
13
14declare module '*.terms' {
15 export const QualifiedNameSeparator: number;
16}