// SPDX-License-Identifier: AGPL-3.0-only 'use strict'; const test = require('node:test'); const assert = require('node:assert/strict'); const fs = require('node:fs'); const path = require('node:path'); const textmate = require('vscode-textmate'); const oniguruma = require('vscode-oniguruma'); test('mixed HTML and every Hime-san delimiter has stable scopes', async () => { const root = path.join(__dirname, '..', '..'); const wasm = fs.readFileSync(require.resolve('vscode-oniguruma/release/onig.wasm')); await oniguruma.loadWASM(wasm.buffer.slice(wasm.byteOffset, wasm.byteOffset + wasm.byteLength)); const registry = new textmate.Registry({ onigLib: Promise.resolve({createOnigScanner: (sources) => new oniguruma.OnigScanner(sources), createOnigString: (value) => new oniguruma.OnigString(value)}), loadGrammar: async (scopeName) => { if (scopeName === 'text.html.sando') return textmate.parseRawGrammar(fs.readFileSync(path.join(root, 'syntaxes', 'sando.tmLanguage.json'), 'utf8'), 'sando.tmLanguage.json'); if (scopeName === 'source.go') return {scopeName: 'source.go', patterns: [{match: '\\b(?:package|func|if)\\b', name: 'keyword.control.go'}]}; if (scopeName === 'text.html.basic') return {scopeName: 'text.html.basic', patterns: [{match: ']*>', name: 'meta.tag.html'}]}; return null; }, }); const grammar = await registry.loadGrammar('text.html.sando'); const lines = fs.readFileSync(path.join(__dirname, 'fixtures', 'mixed.sando'), 'utf8').trimEnd().split('\n'); const seen = new Set(); let stack = textmate.INITIAL; for (const line of lines) { const result = grammar.tokenizeLine(line, stack); stack = result.ruleStack; for (const token of result.tokens) for (const scope of token.scopes) seen.add(scope); } const snapshot = [...seen].filter((scope) => scope.includes('sando')).sort(); assert.deepEqual(snapshot, [ 'comment.block.sando', 'component.composition.sando', 'expression.output.sando', 'meta.embedded.block.sando.component', 'meta.embedded.block.sando.expression', 'meta.embedded.block.sando.header', 'meta.embedded.block.sando.statement', 'punctuation.definition.comment.begin.sando', 'punctuation.definition.comment.end.sando', 'punctuation.section.embedded.begin.sando', 'punctuation.section.embedded.end.sando', 'support.constant.language.sando', 'text.html.sando', ]); assert.ok(seen.has('meta.tag.html'), 'visible HTML was not delegated to the HTML grammar'); });