diff --git a/.github/dependabot.yml b/.github/dependabot.yml
index 2204679a6..8915c39dd 100644
--- a/.github/dependabot.yml
+++ b/.github/dependabot.yml
@@ -66,10 +66,6 @@ updates:
- dependency-name: "@babel/preset-react"
versions:
- 7.13.13
- - dependency-name: codemirror
- versions:
- - 5.59.3
- - 5.60.0
- dependency-name: classnames
versions:
- 2.3.0
diff --git a/client/components/codeEditor/autocompleteEmoji.js b/client/components/codeEditor/autocompleteEmoji.js
index fc64e7bbd..309668884 100644
--- a/client/components/codeEditor/autocompleteEmoji.js
+++ b/client/components/codeEditor/autocompleteEmoji.js
@@ -1,3 +1,5 @@
+import { autocompletion } from '@codemirror/autocomplete';
+
import diceFont from '@themes/fonts/iconFonts/diceFont.js';
import elderberryInn from '@themes/fonts/iconFonts/elderberryInn.js';
import fontAwesome from '@themes/fonts/iconFonts/fontAwesome.js';
@@ -10,75 +12,65 @@ const emojis = {
...gameIcons
};
-const showAutocompleteEmoji = function(CodeMirror, editor) {
- CodeMirror.commands.autocomplete = function(editor) {
- editor.showHint({
- completeSingle : false,
- hint : function(editor) {
- const cursor = editor.getCursor();
- const line = cursor.line;
- const lineContent = editor.getLine(line);
- const start = lineContent.lastIndexOf(':', cursor.ch - 1) + 1;
- const end = cursor.ch;
- const currentWord = lineContent.slice(start, end);
+const emojiCompletionList = (context)=>{
+ const word = context.matchBefore(/:[^\s:]+/);
+ if(!word) return null;
+ const line = context.state.doc.lineAt(context.pos);
+ const textToCursor = line.text.slice(0, context.pos - line.from);
- const list = Object.keys(emojis).filter(function(emoji) {
- return emoji.toLowerCase().indexOf(currentWord.toLowerCase()) >= 0;
- }).sort((a, b)=>{
- const lowerA = a.replace(/\d+/g, function(match) { // Temporarily convert any numbers in emoji string
- return match.padStart(4, '0'); // to 4-digits, left-padded with 0's, to aid in
- }).toLowerCase(); // sorting numbers, i.e., "d6, d10, d20", not "d10, d20, d6"
- const lowerB = b.replace(/\d+/g, function(match) { // Also make lowercase for case-insensitive alpha sorting
- return match.padStart(4, '0');
- }).toLowerCase();
+ if(textToCursor.includes('{')) {
+ const curlyToCursor = textToCursor.slice(textToCursor.indexOf('{'));
+ const curlySpanRegex = /{(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\1$/g;
+ if(curlySpanRegex.test(curlyToCursor)) return null;
+ }
- if(lowerA < lowerB)
- return -1;
- return 1;
- }).map(function(emoji) {
- return {
- text : `${emoji}:`, // Text to output to editor when option is selected
- render : function(element, self, data) { // How to display the option in the dropdown
- const div = document.createElement('div');
- div.innerHTML = ` ${emoji}`;
- element.appendChild(div);
- }
- };
- });
+ const currentWord = word.text.slice(1); // remove ':'
- return {
- list : list.length ? list : [],
- from : CodeMirror.Pos(line, start),
- to : CodeMirror.Pos(line, end)
- };
- }
- });
+ const options = Object.keys(emojis)
+ .filter((e)=>e.toLowerCase().includes(currentWord.toLowerCase()))
+ .sort((a, b)=>{
+ const normalize = (str)=>str.replace(/\d+/g, (m)=>m.padStart(4, '0')).toLowerCase();
+ return normalize(a) < normalize(b) ? -1 : 1;
+ })
+ .map((e)=>({
+ label : e,
+ apply : `${e}:`,
+ type : 'text',
+ info : ()=>{
+ const div = document.createElement('div');
+ div.innerHTML = ` ${e}`;
+ return div;
+ }
+ }));
+ //Label is the text in the list, comes with an icon that just
+ //renders example text "abc", hid that with css because i didn't see other choice
+ //Apply is the text that is set when the choice is selected
+ //Info is the tooltip
+
+ return {
+ from : word.from + 1,
+ options,
+ filter : false,
};
-
- editor.on('inputRead', function(instance, change) {
- const cursor = editor.getCursor();
- const line = editor.getLine(cursor.line);
-
- // Get the text from the start of the line to the cursor
- const textToCursor = line.slice(0, cursor.ch);
-
- // Do not autosuggest emojis in curly span/div/injector properties
- if(line.includes('{')) {
- const curlyToCursor = textToCursor.slice(textToCursor.indexOf(`{`));
- const curlySpanRegex = /{(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\1$/g;
-
- if(curlySpanRegex.test(curlyToCursor))
- return;
- }
-
- // Check if the text ends with ':xyz'
- if(/:[^\s:]+$/.test(textToCursor)) {
- CodeMirror.commands.autocomplete(editor);
- }
- });
};
-export default {
- showAutocompleteEmoji
-};
\ No newline at end of file
+export const autocompleteEmoji = autocompletion({
+ override : [emojiCompletionList],
+ activateOnTyping : true,
+ addToOptions : [
+ {
+ render(completion) {
+ const e = completion.label;
+
+ const icon = document.createElement('i');
+ icon.className = `emojiPreview ${emojis[e]}`;
+
+ const fragment = document.createDocumentFragment();
+ fragment.appendChild(icon);
+
+ return fragment;
+ }
+ }
+ ]
+});
\ No newline at end of file
diff --git a/client/components/codeEditor/close-tag.js b/client/components/codeEditor/close-tag.js
deleted file mode 100644
index 84cf62169..000000000
--- a/client/components/codeEditor/close-tag.js
+++ /dev/null
@@ -1,48 +0,0 @@
-const autoCloseCurlyBraces = function(CodeMirror, cm, typingClosingBrace) {
- const ranges = cm.listSelections(), replacements = [];
- for (let i = 0; i < ranges.length; i++) {
- if(!ranges[i].empty()) return CodeMirror.Pass;
- const pos = ranges[i].head, line = cm.getLine(pos.line), tok = cm.getTokenAt(pos);
- if(!typingClosingBrace && (tok.type == 'string' || tok.string.charAt(0) != '{' || tok.start != pos.ch - 1))
- return CodeMirror.Pass;
- else if(typingClosingBrace) {
- let hasUnclosedBraces = false, index = -1;
- do {
- index = line.indexOf('{{', index + 1);
- if(index !== -1 && line.indexOf('}}', index + 1) === -1) {
- hasUnclosedBraces = true;
- break;
- }
- } while (index !== -1);
- if(!hasUnclosedBraces) return CodeMirror.Pass;
- }
-
- replacements[i] = typingClosingBrace ? {
- text : '}}',
- newPos : CodeMirror.Pos(pos.line, pos.ch + 2)
- } : {
- text : '{}}',
- newPos : CodeMirror.Pos(pos.line, pos.ch + 1)
- };
- }
-
- for (let i = ranges.length - 1; i >= 0; i--) {
- const info = replacements[i];
- cm.replaceRange(info.text, ranges[i].head, ranges[i].anchor, '+insert');
- const sel = cm.listSelections().slice(0);
- sel[i] = {
- head : info.newPos,
- anchor : info.newPos
- };
- cm.setSelections(sel);
- }
-};
-
-export default {
- autoCloseCurlyBraces : function(CodeMirror, codeMirror) {
- const map = { name: 'autoCloseCurlyBraces' };
- map[`'{'`] = function(cm) { return autoCloseCurlyBraces(CodeMirror, cm); };
- map[`'}'`] = function(cm) { return autoCloseCurlyBraces(CodeMirror, cm, true); };
- codeMirror?.addKeyMap(map);
- }
-};
\ No newline at end of file
diff --git a/client/components/codeEditor/codeEditor.jsx b/client/components/codeEditor/codeEditor.jsx
index 5e82de156..708a65cb3 100644
--- a/client/components/codeEditor/codeEditor.jsx
+++ b/client/components/codeEditor/codeEditor.jsx
@@ -1,494 +1,410 @@
-/* eslint-disable max-lines */
+/* eslint max-lines: ["error", { "max": 400 }] */
import './codeEditor.less';
-import React from 'react';
-import createReactClass from 'create-react-class';
-import _ from 'lodash';
-import closeTag from './close-tag';
-import autoCompleteEmoji from './autocompleteEmoji';
-let CodeMirror;
+import React, { useEffect, useRef, forwardRef, useImperativeHandle } from 'react';
-const CodeEditor = createReactClass({
- displayName : 'CodeEditor',
- getDefaultProps : function() {
- return {
- language : '',
- tab : 'brewText',
- value : '',
- wrap : true,
- onChange : ()=>{},
- onReady : ()=>{},
- enableFolding : true,
- editorTheme : 'default'
- };
- },
+import {
+ EditorView,
+ keymap,
+ lineNumbers,
+ highlightActiveLineGutter,
+ highlightActiveLine,
+ scrollPastEnd,
+ Decoration,
+ ViewPlugin,
+ drawSelection,
+ dropCursor,
+} from '@codemirror/view';
+import { EditorState, Compartment, StateEffect, StateField } from '@codemirror/state';
+import { foldAll as foldAllCmd, unfoldAll as unfoldAllCmd, foldGutter, foldKeymap, syntaxHighlighting } from '@codemirror/language';
+import { defaultKeymap, history, undo, redo, undoDepth, redoDepth } from '@codemirror/commands';
+import { languages } from '@codemirror/language-data';
+import { css } from '@codemirror/lang-css';
+import { markdown, markdownLanguage } from '@codemirror/lang-markdown';
+import { html } from '@codemirror/lang-html';
+import { autocompleteEmoji } from './autocompleteEmoji.js';
+import { searchKeymap, search } from '@codemirror/search';
+import { closeBrackets } from '@codemirror/autocomplete';
- getInitialState : function() {
- return {
- docs : {}
- };
- },
+const autoCloseBrackets = closeBrackets({ brackets: ['()', '[]', '{{}}'] });
- editor : React.createRef(null),
+import * as themesImport from '@uiw/codemirror-themes-all';
+import defaultCM5Theme from '@themes/codeMirror/default.js';
+import darkbrewery from '@themes/codeMirror/darkbrewery.js';
- async componentDidMount() {
- CodeMirror = (await import('codemirror')).default;
- this.CodeMirror = CodeMirror;
+const themes = { default: defaultCM5Theme, darkbrewery, ...themesImport };
+const themeCompartment = new Compartment();
+const highlightCompartment = new Compartment();
- await import('codemirror/mode/gfm/gfm.js');
- await import('codemirror/mode/css/css.js');
- await import('codemirror/mode/javascript/javascript.js');
+import { generalKeymap, markdownKeymap } from './customKeyMaps.js';
+import foldOnPages from './customFolding.js';
+import { customHighlightStyle, tokenizeCustomMarkdown, tokenizeCustomCSS } from './customHighlight.js';
+import { legacyCustomHighlightStyle, legacyTokenizeCustomMarkdown } from './legacyCustomHighlight.js';
- // addons
- await import('codemirror/addon/fold/foldcode.js');
- await import('codemirror/addon/fold/foldgutter.js');
- await import('codemirror/addon/fold/xml-fold.js');
- await import('codemirror/addon/search/search.js');
- await import('codemirror/addon/search/searchcursor.js');
- await import('codemirror/addon/search/jump-to-line.js');
- await import('codemirror/addon/search/match-highlighter.js');
- await import('codemirror/addon/search/matchesonscrollbar.js');
- await import('codemirror/addon/dialog/dialog.js');
- await import('codemirror/addon/scroll/scrollpastend.js');
- await import('codemirror/addon/edit/closetag.js');
- await import('codemirror/addon/hint/show-hint.js');
- // import 'codemirror/addon/selection/active-line.js';
- // import 'codemirror/addon/edit/trailingspace.js';
+const PAGEBREAK_REGEX_V3 = /^(?=\\page(?:break)?(?: *{[^\n{}]*})?$)/m;
+const createHighlightPlugin = (renderer, tab)=>{
+ //this function takes the custom tokens created in the tokenize function in customhighlight files
+ //takes the tokens defined by that function and assigns classes to them
+ //it also creates page number and snippet number widgets
- // register helpers dynamically as well
- const foldPagesCode = (await import('./fold-pages')).default;
- const foldCSSCode = (await import('./fold-css')).default;
- foldPagesCode.registerHomebreweryHelper(CodeMirror);
- foldCSSCode.registerHomebreweryHelper(CodeMirror);
+ let tokenize;
- this.buildEditor();
- const newDoc = CodeMirror?.Doc(this.props.value, this.props.language);
- this.codeMirror?.swapDoc(newDoc);
- },
-
-
- componentDidUpdate : function(prevProps) {
- if(prevProps.view !== this.props.view){ //view changed; swap documents
- let newDoc;
-
- if(!this.state.docs[this.props.view]) {
- newDoc = CodeMirror?.Doc(this.props.value, this.props.language);
- } else {
- newDoc = this.state.docs[this.props.view];
- }
-
- const oldDoc = { [prevProps.view]: this.codeMirror?.swapDoc(newDoc) };
-
- this.setState((prevState)=>({
- docs : _.merge({}, prevState.docs, oldDoc)
- }));
-
- this.props.rerenderParent();
- } else if(this.codeMirror?.getValue() != this.props.value) { //update editor contents if brew.text is changed from outside
- this.codeMirror?.setValue(this.props.value);
- }
-
- if(this.props.enableFolding) {
- this.codeMirror?.setOption('foldOptions', this.foldOptions(this.codeMirror));
- } else {
- this.codeMirror?.setOption('foldOptions', false);
- }
-
- if(prevProps.editorTheme !== this.props.editorTheme){
- this.codeMirror?.setOption('theme', this.props.editorTheme);
- }
- },
-
- buildEditor : function() {
- this.codeMirror = CodeMirror(this.editor.current, {
- lineNumbers : true,
- lineWrapping : this.props.wrap,
- indentWithTabs : false,
- tabSize : 2,
- smartIndent : false,
- historyEventDelay : 250,
- scrollPastEnd : true,
- extraKeys : {
- 'Tab' : this.indent,
- 'Shift-Tab' : this.dedent,
- 'Ctrl-B' : this.makeBold,
- 'Cmd-B' : this.makeBold,
- 'Shift-Ctrl-=' : this.makeSuper,
- 'Shift-Cmd-=' : this.makeSuper,
- 'Ctrl-=' : this.makeSub,
- 'Cmd-=' : this.makeSub,
- 'Ctrl-I' : this.makeItalic,
- 'Cmd-I' : this.makeItalic,
- 'Ctrl-U' : this.makeUnderline,
- 'Cmd-U' : this.makeUnderline,
- 'Ctrl-.' : this.makeNbsp,
- 'Cmd-.' : this.makeNbsp,
- 'Shift-Ctrl-.' : this.makeSpace,
- 'Shift-Cmd-.' : this.makeSpace,
- 'Shift-Ctrl-,' : this.removeSpace,
- 'Shift-Cmd-,' : this.removeSpace,
- 'Ctrl-M' : this.makeSpan,
- 'Cmd-M' : this.makeSpan,
- 'Shift-Ctrl-M' : this.makeDiv,
- 'Shift-Cmd-M' : this.makeDiv,
- 'Ctrl-/' : this.makeComment,
- 'Cmd-/' : this.makeComment,
- 'Ctrl-K' : this.makeLink,
- 'Cmd-K' : this.makeLink,
- 'Ctrl-L' : ()=>this.makeList('UL'),
- 'Cmd-L' : ()=>this.makeList('UL'),
- 'Shift-Ctrl-L' : ()=>this.makeList('OL'),
- 'Shift-Cmd-L' : ()=>this.makeList('OL'),
- 'Shift-Ctrl-1' : ()=>this.makeHeader(1),
- 'Shift-Ctrl-2' : ()=>this.makeHeader(2),
- 'Shift-Ctrl-3' : ()=>this.makeHeader(3),
- 'Shift-Ctrl-4' : ()=>this.makeHeader(4),
- 'Shift-Ctrl-5' : ()=>this.makeHeader(5),
- 'Shift-Ctrl-6' : ()=>this.makeHeader(6),
- 'Shift-Cmd-1' : ()=>this.makeHeader(1),
- 'Shift-Cmd-2' : ()=>this.makeHeader(2),
- 'Shift-Cmd-3' : ()=>this.makeHeader(3),
- 'Shift-Cmd-4' : ()=>this.makeHeader(4),
- 'Shift-Cmd-5' : ()=>this.makeHeader(5),
- 'Shift-Cmd-6' : ()=>this.makeHeader(6),
- 'Shift-Ctrl-Enter' : this.newColumn,
- 'Shift-Cmd-Enter' : this.newColumn,
- 'Ctrl-Enter' : this.newPage,
- 'Cmd-Enter' : this.newPage,
- 'Ctrl-F' : 'findPersistent',
- 'Cmd-F' : 'findPersistent',
- 'Shift-Enter' : 'findPersistentPrevious',
- 'Ctrl-[' : this.foldAllCode,
- 'Cmd-[' : this.foldAllCode,
- 'Ctrl-]' : this.unfoldAllCode,
- 'Cmd-]' : this.unfoldAllCode
- },
- foldGutter : true,
- foldOptions : this.foldOptions(this.codeMirror),
- gutters : ['CodeMirror-linenumbers', 'CodeMirror-foldgutter'],
- autoCloseTags : true,
- styleActiveLine : true,
- showTrailingSpace : false,
- theme : this.props.editorTheme
- // specialChars : / /,
- // specialCharPlaceholder : function(char) {
- // const el = document.createElement('span');
- // el.className = 'cm-space';
- // el.innerHTML = ' ';
- // return el;
- // }
- });
- this.props.onReady?.(this.codeMirror);
- // Add custom behaviors (auto-close curlies and auto-complete emojis)
- closeTag.autoCloseCurlyBraces(CodeMirror, this.codeMirror);
- autoCompleteEmoji.showAutocompleteEmoji(CodeMirror, this.codeMirror);
-
- // Note: codeMirror passes a copy of itself in this callback. cm === this.codeMirror?. Either one works.
- this.codeMirror?.on('change', (cm)=>{this.props.onChange(cm.getValue());});
- this.updateSize();
- },
-
- // Use for GFM tabs that use common hot-keys
- isGFM : function() {
- console.log(this.props.tab);
- if( this.props.tab === 'brewText' || this.props.tab === 'brewSnippets') return true;
- return false;
- },
-
- isBrewText : function() {
- if(this.isGFM()) return true;
- return false;
- },
-
- isBrewSnippets : function() {
- if(this.props.tab === 'brewSnippets') return true;
- return false;
- },
-
- indent : function () {
- const cm = this.codeMirror;
- if(cm.somethingSelected()) {
- cm.execCommand('indentMore');
- } else {
- cm.execCommand('insertSoftTab');
- }
- },
-
- dedent : function () {
- this.codeMirror?.execCommand('indentLess');
- },
-
- makeHeader : function (number) {
- if(!this.isGFM()) return;
- const selection = this.codeMirror?.getSelection();
- const header = Array(number).fill('#').join('');
- this.codeMirror?.replaceSelection(`${header} ${selection}`, 'around');
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch + selection.length + number + 1 });
- },
-
- makeBold : function() {
- console.log('hello');
- if(!this.isGFM()) return;
- console.log(this.isGFM());
- const selection = this.codeMirror?.getSelection(), t = selection.slice(0, 2) === '**' && selection.slice(-2) === '**';
- this.codeMirror?.replaceSelection(t ? selection.slice(2, -2) : `**${selection}**`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - 2 });
- }
- },
-
- makeItalic : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror.getSelection(), t = selection.slice(0, 1) === '*' && selection.slice(-1) === '*';
- this.codeMirror?.replaceSelection(t ? selection.slice(1, -1) : `*${selection}*`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - 1 });
- }
- },
-
- makeSuper : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror.getSelection(), t = selection.slice(0, 1) === '^' && selection.slice(-1) === '^';
- this.codeMirror?.replaceSelection(t ? selection.slice(1, -1) : `^${selection}^`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - 1 });
- }
- },
-
- makeSub : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror.getSelection(), t = selection.slice(0, 2) === '^^' && selection.slice(-2) === '^^';
- this.codeMirror?.replaceSelection(t ? selection.slice(2, -2) : `^^${selection}^^`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - 2 });
- }
- },
-
-
- makeNbsp : function() {
- if(!this.isGFM()) return;
- this.codeMirror?.replaceSelection(' ', 'end');
- },
-
- makeSpace : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror?.getSelection();
- const t = selection.slice(0, 8) === '{{width:' && selection.slice(0 -4) === '% }}';
- if(t){
- const percent = parseInt(selection.slice(8, -4)) + 10;
- this.codeMirror?.replaceSelection(percent < 90 ? `{{width:${percent}% }}` : '{{width:100% }}', 'around');
- } else {
- this.codeMirror?.replaceSelection(`{{width:10% }}`, 'around');
- }
- },
-
- removeSpace : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror?.getSelection();
- const t = selection.slice(0, 8) === '{{width:' && selection.slice(0 -4) === '% }}';
- if(t){
- const percent = parseInt(selection.slice(8, -4)) - 10;
- this.codeMirror?.replaceSelection(percent > 10 ? `{{width:${percent}% }}` : '', 'around');
- }
- },
-
- newColumn : function() {
- if(!this.isGFM()) return;
- this.codeMirror?.replaceSelection('\n\\column\n\n', 'end');
- },
-
- newPage : function() {
- if(!this.isGFM()) return;
- this.codeMirror?.replaceSelection('\n\\page\n\n', 'end');
- },
-
- injectText : function(injectText, overwrite=true) {
- const cm = this.codeMirror;
- if(!overwrite) {
- cm.setCursor(cm.getCursor('from'));
- }
- cm.replaceSelection(injectText, 'end');
- cm.focus();
- },
-
- makeUnderline : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror.getSelection(), t = selection.slice(0, 3) === '' && selection.slice(-4) === '';
- this.codeMirror?.replaceSelection(t ? selection.slice(3, -4) : `${selection}`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - 4 });
- }
- },
-
- makeSpan : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror.getSelection(), t = selection.slice(0, 2) === '{{' && selection.slice(-2) === '}}';
- this.codeMirror?.replaceSelection(t ? selection.slice(2, -2) : `{{ ${selection}}}`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - 2 });
- }
- },
-
- makeDiv : function() {
- if(!this.isGFM()) return;
- const selection = this.codeMirror.getSelection(), t = selection.slice(0, 2) === '{{' && selection.slice(-2) === '}}';
- this.codeMirror?.replaceSelection(t ? selection.slice(2, -2) : `{{\n${selection}\n}}`, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line - 1, ch: cursor.ch }); // set to -2? if wanting to enter classes etc. if so, get rid of first \n when replacing selection
- }
- },
-
- makeComment : function() {
- let regex;
- let cursorPos;
- let newComment;
- const selection = this.codeMirror?.getSelection();
- if(this.isGFM()){
- regex = /^\s*()\s*$/gs;
- cursorPos = 4;
- newComment = ``;
- } else {
- regex = /^\s*(\/\*\s?)(.*?)(\s?\*\/)\s*$/gs;
- cursorPos = 3;
- newComment = `/* ${selection} */`;
- }
- this.codeMirror?.replaceSelection(regex.test(selection) == true ? selection.replace(regex, '$2') : newComment, 'around');
- if(selection.length === 0){
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setCursor({ line: cursor.line, ch: cursor.ch - cursorPos });
- };
- },
-
- makeLink : function() {
- if(!this.isGFM()) return;
- const isLink = /^\[(.*)\]\((.*)\)$/;
- const selection = this.codeMirror?.getSelection().trim();
- let match;
- if(match = isLink.exec(selection)){
- const altText = match[1];
- const url = match[2];
- this.codeMirror?.replaceSelection(`${altText} ${url}`);
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setSelection({ line: cursor.line, ch: cursor.ch - url.length }, { line: cursor.line, ch: cursor.ch });
- } else {
- this.codeMirror?.replaceSelection(`[${selection || 'alt text'}](url)`);
- const cursor = this.codeMirror?.getCursor();
- this.codeMirror?.setSelection({ line: cursor.line, ch: cursor.ch - 4 }, { line: cursor.line, ch: cursor.ch - 1 });
- }
- },
-
- makeList : function(listType) {
- if(!this.isGFM()) return;
- const selectionStart = this.codeMirror.getCursor('from'), selectionEnd = this.codeMirror.getCursor('to');
- this.codeMirror?.setSelection(
- { line: selectionStart.line, ch: 0 },
- { line: selectionEnd.line, ch: this.codeMirror?.getLine(selectionEnd.line).length }
- );
- const newSelection = this.codeMirror?.getSelection();
-
- const regex = /^\d+\.\s|^-\s/gm;
- if(newSelection.match(regex) != null){ // if selection IS A LIST
- this.codeMirror?.replaceSelection(newSelection.replace(regex, ''), 'around');
- } else { // if selection IS NOT A LIST
- listType == 'UL' ? this.codeMirror?.replaceSelection(newSelection.replace(/^/gm, `- `), 'around') :
- this.codeMirror?.replaceSelection(newSelection.replace(/^/gm, (()=>{
- let n = 1;
- return ()=>{
- return `${n++}. `;
- };
- })()), 'around');
- }
- },
-
- foldAllCode : function() {
- this.codeMirror?.execCommand('foldAll');
- },
-
- unfoldAllCode : function() {
- this.codeMirror?.execCommand('unfoldAll');
- },
-
- //=-- Externally used -==//
- setCursorPosition : function(line, char){
- setTimeout(()=>{
- this.codeMirror?.focus();
- this.codeMirror?.doc.setCursor(line, char);
- }, 10);
- },
- getCursorPosition : function(){
- return this.codeMirror?.getCursor();
- },
- getTopVisibleLine : function(){
- const rect = this.codeMirror?.getWrapperElement().getBoundingClientRect();
- const topVisibleLine = this.codeMirror?.lineAtHeight(rect.top, 'window');
- return topVisibleLine;
- },
- updateSize : function(){
- this.codeMirror?.refresh();
- },
- redo : function(){
- return this.codeMirror?.redo();
- },
- undo : function(){
- return this.codeMirror?.undo();
- },
- historySize : function(){
- return this.codeMirror?.doc.historySize();
- },
-
- foldOptions : function(cm){
- return {
- scanUp : true,
- rangeFinder : this.props.language === 'css' ? CodeMirror.fold.homebrewerycss : CodeMirror.fold.homebrewery,
- widget : (from, to)=>{
- let text = '';
- let currentLine = from.line;
- let maxLength = 50;
-
- let foldPreviewText = '';
- while (currentLine <= to.line && text.length <= maxLength) {
- const currentText = this.codeMirror?.getLine(currentLine);
- currentLine++;
- if(currentText[0] == '#'){
- foldPreviewText = currentText;
- break;
- }
- if(!foldPreviewText && currentText != '\n') {
- foldPreviewText = currentText;
- }
- }
- text = foldPreviewText || `Lines ${from.line+1}-${to.line+1}`;
- text = text.replace('{', '').trim();
-
- // Truncate data URLs at `data:`
- const startOfData = text.indexOf('data:');
- if(startOfData > 0)
- maxLength = Math.min(startOfData + 5, maxLength);
-
- if(text.length > maxLength)
- text = `${text.slice(0, maxLength)}...`;
-
- return `\u21A4 ${text} \u21A6`;
- }
- };
- },
- //----------------------//
-
- render : function(){
- return <>
-
-
- >;
+ if(tab === 'brewStyles') {
+ tokenize = tokenizeCustomCSS;
+ } else {
+ tokenize = renderer === 'V3' ? tokenizeCustomMarkdown : legacyTokenizeCustomMarkdown;
}
+
+ return ViewPlugin.fromClass(
+ class {
+ constructor(view) {
+ this.decorations = this.buildDecorations(view);
+ }
+ update(update) {
+ if(update.docChanged) {
+ this.decorations = this.buildDecorations(update.view);
+ }
+ }
+ buildDecorations(view) {
+ const decos = [];
+ const tokens = tokenize(view.state.doc.toString());
+ let pageCount = 1;
+ let snippetCount = 0;
+
+ tokens.forEach((tok)=>{
+ const line = view.state.doc.line(tok.line + 1);
+
+ if(tok.from != null && tok.to != null && tok.from < tok.to) {
+ decos.push(Decoration.mark({ class: `cm-${tok.type}` }).range(line.from + tok.from, line.from + tok.to));
+ } else {
+ decos.push(Decoration.line({ class: `cm-${tok.type}` }).range(line.from));
+ if(tok.type === 'pageLine' && tab === 'brewText') {
+ pageCount++;
+ line.from === 0 && pageCount--;
+ decos.push(Decoration.line({ attributes: { 'data-page-number': pageCount } }).range(line.from));
+ }
+ if(tok.type === 'snippetLine' && tab === 'brewSnippets') {
+ snippetCount++;
+ decos.push(Decoration.line({ attributes: { 'data-page-number': snippetCount } }).range(line.from));
+ }
+ }
+ });
+
+ decos.sort((a, b)=>a.from - b.from || a.to - b.to);
+ return Decoration.set(decos);
+ }
+ },
+ { decorations: (v)=>v.decorations }
+ );
+};
+
+const setProgrammaticCursorLine = StateEffect.define();
+
+const programmaticCursorLineField = StateField.define({
+ create() {
+ return Decoration.none;
+ },
+ update(decorations, transitionState) {
+ //deco is the decoratiions object
+ //tr is the transition state object, tr.effects is an array of stateEffects
+ //seems to be the easiest way of setting a class programatically only when called
+ for (const effects of transitionState.effects) {
+ if(effects.is(setProgrammaticCursorLine)) {
+ const pos = effects.value;
+ if(pos == null) return Decoration.none;
+ const line = transitionState.state.doc.lineAt(pos);
+
+ return Decoration.set([
+ Decoration.line({
+ class : 'sourceMoveFlash'
+ }).range(line.from)
+ ]);
+ }
+ }
+ return decorations;
+ },
+ provide : (decorationSet)=>EditorView.decorations.from(decorationSet)
});
-export default CodeEditor;
+const CodeEditor = forwardRef(
+ (
+ {
+ language = '',
+ tab = 'brewText',
+ view,
+ value = '',
+ onChange = ()=>{},
+ onCursorChange = ()=>{},
+ onViewChange = ()=>{},
+ editorTheme = 'default',
+ style,
+ renderer,
+ ...props
+ },
+ ref,
+ )=>{
+ const editorRef = useRef(null);
+ const viewRef = useRef(null);
+ const docsRef = useRef({});
+ const prevTabRef = useRef(tab);
+ const pageMap = useRef([]);
+
+ const recomputePages = (doc)=>{
+ const pages = [0];
+ const text = doc.toString();
+ let offset = 0;
+
+ for (const line of text.split('\n')) {
+ if(PAGEBREAK_REGEX_V3.test(line)) {
+ pages.push(offset);
+ }
+ offset += line.length + 1;
+ }
+
+ pageMap.current = pages;
+ };
+
+ const findPageFromPos = (pos)=>{
+ const pages = pageMap.current;
+ let page = 1;
+
+ for (let i = 1; i < pages.length; i++) {
+ if(pos >= pages[i]) page = i + 1;
+ }
+
+ return page;
+ };
+
+ const createExtensions = ({ onChange, language, editorTheme })=>{
+ const setEventListeners = EditorView.updateListener.of((update)=>{
+ if(update.docChanged) {
+ recomputePages(update.state.doc);
+ onChange(update.state.doc.toString());
+ }
+ if(update.selectionSet) {
+ const pos = update.state.selection.main.head;
+ const page = findPageFromPos(pos);
+ onCursorChange(page);
+ }
+ });
+
+ const highlightExtension = renderer === 'V3'
+ ? syntaxHighlighting(customHighlightStyle)
+ : syntaxHighlighting(legacyCustomHighlightStyle);
+
+ const customHighlightPlugin = createHighlightPlugin(renderer, tab);
+
+ const languageExtension = language === 'css' ? css() : [markdown({ base: markdownLanguage, codeLanguages: languages }), html({ autoCloseTags: true })];
+ const themeExtension = Array.isArray(themes[editorTheme]) ? themes[editorTheme] : themes[editorTheme] || themes['default'];
+
+ return [
+ EditorView.lineWrapping,
+ setEventListeners,
+ languageExtension,
+ autoCloseBrackets,
+ lineNumbers(),
+ scrollPastEnd(),
+ search(),
+ history(), //allows for undo and redo
+ ...(tab !== 'brewStyles' ? [autocompleteEmoji] : []),
+
+ //folding
+ foldOnPages,
+ foldGutter({
+ openText : '▾',
+ closedText : '▸'
+ }),
+
+ //highlights
+ highlightCompartment.of([customHighlightPlugin, highlightExtension]),
+ themeCompartment.of(themeExtension),
+ highlightActiveLine(),
+ highlightActiveLineGutter(),
+
+ //keyboard shortcut
+ keymap.of([...defaultKeymap, foldKeymap, ...searchKeymap]),
+ generalKeymap,
+ ...(tab !== 'brewStyles' ? [markdownKeymap] : []),
+
+ //multiple cursors and selections
+ drawSelection(),
+ EditorState.allowMultipleSelections.of(true),
+ dropCursor(),
+ programmaticCursorLineField,
+ ];
+ };
+
+ useEffect(()=>{
+ if(!editorRef.current) return;
+
+ const state = EditorState.create({
+ doc : value,
+ extensions : createExtensions({ onChange, language, editorTheme }),
+ });
+
+ recomputePages(state.doc);
+
+ viewRef.current = new EditorView({
+ state,
+ parent : editorRef.current,
+ });
+
+ const view = viewRef.current;
+
+ let ticking = false;
+
+ const handleScroll = ()=>{
+ if(ticking) return;
+
+ ticking = true;
+ requestAnimationFrame(()=>{
+ const top = view.scrollDOM.scrollTop;
+ const block = view.lineBlockAtHeight(top);
+
+ const page = findPageFromPos(block.from); // CHANGED
+ onViewChange(page);
+
+ ticking = false;
+ });
+ };
+
+ view.scrollDOM.addEventListener('scroll', handleScroll);
+
+ docsRef.current[tab] = state;
+
+ return ()=>{
+ view.scrollDOM.removeEventListener('scroll', handleScroll);
+ viewRef.current?.destroy();
+ };
+ }, []);
+
+ useEffect(()=>{
+ const view = viewRef.current;
+ if(!view) return;
+
+ const prevTab = prevTabRef.current;
+
+ if(prevTab !== tab) {
+ docsRef.current[prevTab] = view.state;
+
+ let nextState = docsRef.current[tab];
+
+ if(!nextState) {
+ nextState = EditorState.create({
+ doc : value,
+ extensions : createExtensions({ onChange, language, editorTheme }),
+ });
+ }
+
+ view.setState(nextState);
+ prevTabRef.current = tab;
+ }
+ view.focus();
+ }, [tab]);
+
+ useEffect(()=>{
+ const view = viewRef.current;
+ if(!view) return;
+
+ const current = view.state.doc.toString();
+ if(value !== current) {
+ view.dispatch({
+ changes : { from: 0, to: current.length, insert: value },
+ });
+ }
+ }, [value]);
+
+ useEffect(()=>{
+ //rebuild theme extension on theme change
+ const view = viewRef.current;
+ if(!view) return;
+
+ const themeExtension = Array.isArray(themes[editorTheme])? themes[editorTheme]: themes[editorTheme] || themes['default'];
+
+ view.dispatch({
+ effects : themeCompartment.reconfigure(themeExtension),
+ });
+ }, [editorTheme]);
+
+ useEffect(()=>{
+ //rebuild syntax highlight when changing tab or renderer
+ const view = viewRef.current;
+ if(!view) return;
+
+ const highlightExtension =renderer === 'V3'
+ ? syntaxHighlighting(customHighlightStyle)
+ : syntaxHighlighting(legacyCustomHighlightStyle);
+
+ const customHighlightPlugin = createHighlightPlugin(renderer, tab);
+
+ view.dispatch({
+ effects : highlightCompartment.reconfigure([customHighlightPlugin, highlightExtension]),
+ });
+ }, [renderer, tab]);
+
+ useImperativeHandle(ref, ()=>({
+
+ injectText : (text)=>{
+ const view = viewRef.current;
+
+
+ view.dispatch(
+ view.state.replaceSelection(text)
+ );
+ view.focus();
+ },
+ getCursorPosition : ()=>viewRef.current.state.selection.main.head,
+
+ scrollToPage : (pageNumber, smooth = true)=>{
+ const view = viewRef.current;
+ if(!view) return;
+
+ const pos = pageMap.current[pageNumber - 1] ?? 0;
+
+ view.dispatch({
+ selection : { anchor: pos },
+ effects : [setProgrammaticCursorLine.of(pos), EditorView.scrollIntoView(pos, { y: 'start' })],
+ });
+
+ view.focus();
+
+ setTimeout(()=>{
+ view.dispatch({
+ effects : setProgrammaticCursorLine.of(null)
+ });
+ }, 400);
+ },
+
+ undo : ()=>undo(viewRef.current),
+ redo : ()=>redo(viewRef.current),
+
+ historySize : ()=>{
+ const view = viewRef.current;
+ if(!view) return { done: 0, undone: 0 };
+
+ return {
+ done : undoDepth(view.state),
+ undone : redoDepth(view.state),
+ };
+ },
+
+ foldAll : ()=>{
+ const view = viewRef.current;
+ if(!view) return;
+ view.dispatch(foldAllCmd(view));
+ },
+ unfoldAll : ()=>{
+ const view = viewRef.current;
+ if(!view) return;
+ view.dispatch(unfoldAllCmd(view));
+ },
+
+ focus : ()=>viewRef.current.focus(),
+ }));
+
+ return
;
+ },
+);
+
+export default CodeEditor;
diff --git a/client/components/codeEditor/codeEditor.less b/client/components/codeEditor/codeEditor.less
index 89d0c9497..3f3869756 100644
--- a/client/components/codeEditor/codeEditor.less
+++ b/client/components/codeEditor/codeEditor.less
@@ -1,60 +1,72 @@
-@import (less) 'codemirror/lib/codemirror.css';
-@import (less) 'codemirror/addon/fold/foldgutter.css';
-@import (less) 'codemirror/addon/search/matchesonscrollbar.css';
-@import (less) 'codemirror/addon/dialog/dialog.css';
-@import (less) 'codemirror/addon/hint/show-hint.css';
-
-//Icon fonts included so they can appear in emoji autosuggest dropdown
-@import (less) '@themes/fonts/iconFonts/diceFont.less';
-@import (less) '@themes/fonts/iconFonts/elderberryInn.less';
-@import (less) '@themes/fonts/iconFonts/gameIcons.less';
-@import (less) '@themes/fonts/iconFonts/fontAwesome.less';
+// Icon fonts for emoji/autocomplete
+@import (less) "@themes/fonts/iconFonts/diceFont.less";
+@import (less) "@themes/fonts/iconFonts/elderberryInn.less";
+@import (less) "@themes/fonts/iconFonts/gameIcons.less";
+@import (less) "@themes/fonts/iconFonts/fontAwesome.less";
@keyframes sourceMoveAnimation {
- 50% { color : white;background-color : red;}
- 100% { color : unset;background-color : unset;}
+ 50% {
+ color: white;
+ background-color: red;
+ }
+ 100% {
+ color: unset;
+ background-color: unset;
+ }
}
-.codeEditor {
- @media screen and (pointer : coarse) {
- font-size : 16px;
+:where(.codeEditor) {
+ font-family: monospace;
+ height: 100%;
+ width:100%;
+
+ .cm-content {
+ tab-size:2 !important;
}
- .CodeMirror-foldmarker {
+
+ @media screen and (pointer: coarse) {
+ font-size: 16px;
+ }
+
+ .cm-gutterElement span {
font-family : inherit;
font-weight : 600;
color : grey;
text-shadow : none;
}
- .CodeMirror-foldgutter {
+ .cm-foldGutter {
cursor : pointer;
border-left : 1px solid #EEEEEE;
transition : background 0.1s;
&:hover { background : #DDDDDD; }
}
- .sourceMoveFlash .CodeMirror-line {
- animation-name : sourceMoveAnimation;
- animation-duration : 0.4s;
+ /* Flash animation for source moves */
+ .cm-line.sourceMoveFlash {
+ animation-name: sourceMoveAnimation;
+ animation-duration: 0.4s;
}
- .CodeMirror-search-field {
- width:25em !important;
- outline:1px inset #00000055 !important;
+ /* Search input */
+ .cm-searchField {
+ width: 25em !important;
+ outline: 1px inset #00000055 !important;
}
+ /* Tab character visualization (optional) */
//.cm-tab {
- // background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAMCAQAAACOs/baAAAARUlEQVR4nGJgIAG8JkXxUAcCtDWemcGR1lY4MvgzCEKY7jSBjgxBDAG09UEQzAe0AMwMHrSOAwEGRtpaMIwAAAAA//8DAG4ID9EKs6YqAAAAAElFTkSuQmCC) no-repeat right;
+ // background: url(...) no-repeat right;
//}
- //.cm-trailingspace {
- // .cm-space {
- // background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAQAgMAAABW5NbuAAAACVBMVEVHcEwAAAAAAAAWawmTAAAAA3RSTlMAPBJ6PMxpAAAACXBIWXMAAC4jAAAuIwF4pT92AAAAFUlEQVQI12NgwACcCQysASAEZGAAACMuAX06aCQUAAAAAElFTkSuQmCC) no-repeat right;
- // }
+ /* Trailing space visualization (optional) */
+ //.cm-trailingSpace .cm-space {
+ // background: url(...) no-repeat right;
//}
}
+/* Emoji preview styling */
.emojiPreview {
- font-size : 1.5em;
- line-height : 1.2em;
-}
\ No newline at end of file
+ font-size: 1.5em;
+ line-height: 1.2em;
+}
diff --git a/client/components/codeEditor/customFolding.js b/client/components/codeEditor/customFolding.js
new file mode 100644
index 000000000..49cb449e7
--- /dev/null
+++ b/client/components/codeEditor/customFolding.js
@@ -0,0 +1,46 @@
+import { foldService, codeFolding } from '@codemirror/language';
+
+const foldOnPages = [
+ foldService.of((state, lineStart)=>{ //tells where to fold
+ const doc = state.doc;
+ const matcher = /^(?=\\page(?:break)?(?: *{[^\n{}]*})?$)/m;
+
+ const startLine = doc.lineAt(lineStart);
+ const prevLineText = startLine.number > 1 ? doc.line(startLine.number - 1).text : '';
+
+ if(!matcher.test(prevLineText)) return null;
+
+ let endLine = startLine.number;
+ while (endLine < doc.lines && !matcher.test(doc.line(endLine + 1).text)) {
+ endLine++;
+ }
+
+ if(endLine === startLine.number) return null;
+
+ return { from: startLine.from, to: doc.line(endLine).to };
+ }),
+ codeFolding({
+ preparePlaceholder : (state, range)=>{
+ const doc = state.doc;
+ const start = doc.lineAt(range.from).number;
+ const end = doc.lineAt(range.to).number;
+
+ if(doc.line(start).text.trim()) return ` ↤ Lines ${start}-${end} ↦`;
+
+ const preview = Array.from({ length: end - start }, (_, i)=>doc.line(start + 1 + i).text.trim()
+ ).find(Boolean) || `Lines ${start}-${end}`;
+
+ return ` ↤ ${preview.replace('{', '').slice(0, 50).trim()}${preview.length > 50 ? '...' : ''} ↦`;
+ },
+ placeholderDOM(view, onclick, prepared) {
+ const span = document.createElement('span');
+ span.className = 'cm-fold-placeholder';
+ span.textContent = prepared;
+ span.onclick = onclick;
+ span.style.color = '#989898';
+ return span;
+ },
+ }),
+];
+
+export default foldOnPages;
\ No newline at end of file
diff --git a/client/components/codeEditor/customHighlight.js b/client/components/codeEditor/customHighlight.js
new file mode 100644
index 000000000..3fa164757
--- /dev/null
+++ b/client/components/codeEditor/customHighlight.js
@@ -0,0 +1,295 @@
+import { HighlightStyle } from '@codemirror/language';
+import { tags } from '@lezer/highlight';
+
+// Making the tokens
+const customTags = {
+ pageLine : 'pageLine', // .cm-pageLine
+ snippetLine : 'snippetLine', // .cm-snippetLine
+ columnSplit : 'columnSplit', // .cm-columnSplit
+ block : 'block', // .cm-block
+ inlineBlock : 'inline-block', // .cm-inline-block
+ injection : 'injection', // .cm-injection
+ emoji : 'emoji', // .cm-emoji
+ superscript : 'superscript', // .cm-superscript
+ subscript : 'subscript', // .cm-subscript
+ definitionList : 'definitionList', // .cm-definitionList
+ definitionTerm : 'definitionTerm', // .cm-definitionTerm
+ definitionDesc : 'definitionDesc', // .cm-definitionDesc
+ definitionColon : 'definitionColon', // .cm-definitionColon
+
+ //CSS
+
+ variable : 'variable',
+};
+
+export function tokenizeCustomMarkdown(text) {
+ const tokens = [];
+ const lines = text.split('\n');
+
+ //tokens without a `from` or `to` are interpreted by the custom plugin as line tokens
+
+ lines.forEach((lineText, lineNumber)=>{
+ // --- Page / snippet lines ---
+ if(/^(?=\\page(?:break)?(?: *{[^\n{}]*})?$)/m.test(lineText)) tokens.push({ line: lineNumber, type: customTags.pageLine });
+ if(/^\\snippet\ .*$/.test(lineText)) tokens.push({ line: lineNumber, type: customTags.snippetLine });
+ if(/^\\column(?:break)?$/.test(lineText)) tokens.push({ line: lineNumber, type: customTags.columnSplit });
+
+ // --- Emoji ---
+ if(/:.\w+?:/.test(lineText)) {
+ const emojiRegex = /(:\w+?:)/g;
+ let match;
+ while ((match = emojiRegex.exec(lineText)) !== null) {
+ tokens.push({
+ line : lineNumber,
+ type : customTags.emoji,
+ from : match.index,
+ to : match.index + match[0].length,
+ });
+ }
+ }
+
+ // --- Superscript / Subscript ---
+ if(/\^/.test(lineText)) {
+ let startIndex = lineText.indexOf('^');
+ const superRegex = /\^(?!\s)(?=([^\n\^]*[^\s\^]))\1\^/gy;
+ const subRegex = /\^\^(?!\s)(?=([^\n\^]*[^\s\^]))\1\^\^/gy;
+
+ while (startIndex >= 0) {
+ superRegex.lastIndex = subRegex.lastIndex = startIndex;
+
+ let match = subRegex.exec(lineText);
+ let type = customTags.subscript;
+
+ if(!match) {
+ match = superRegex.exec(lineText);
+ type = customTags.superscript;
+ }
+
+ if(match) {
+ tokens.push({
+ line : lineNumber,
+ type,
+ from : match.index,
+ to : match.index + match[0].length,
+ });
+ }
+
+ startIndex = lineText.indexOf(
+ '^',
+ Math.max(startIndex + 1, superRegex.lastIndex || 0, subRegex.lastIndex || 0),
+ );
+ }
+ }
+
+ // --- single line def list ---
+ const singleLineRegex = /^(?=.*[^:])(.+?)(\s*)(::)([^\n]*)$/dmy;
+ const match = singleLineRegex.exec(lineText);
+
+ if(match) {
+ const [full, term, spaces, colons, desc] = match;
+
+ let offset = 0;
+
+ tokens.push({
+ line : lineNumber,
+ type : customTags.definitionList,
+ });
+
+ // Term
+ tokens.push({
+ line : lineNumber,
+ type : customTags.definitionTerm,
+ from : offset,
+ to : offset + term.length,
+ });
+ offset += term.length;
+
+ // Spaces before ::
+ if(spaces) {
+ offset += spaces.length;
+ }
+
+ // :: colons
+ tokens.push({
+ line : lineNumber,
+ type : customTags.definitionColon,
+ from : offset,
+ to : offset + colons.length,
+ });
+ offset += colons.length;
+
+ // Definition
+ tokens.push({
+ line : lineNumber,
+ type : customTags.definitionDesc,
+ from : offset,
+ to : offset + desc.length,
+ });
+
+ return;
+ }
+
+ // --- multiline def list ---
+ if(!/^::/.test(lines[lineNumber]) && lineNumber + 1 < lines.length && /^::/.test(lines[lineNumber + 1])) {
+ const startLine = lineNumber;
+ const defs = [];
+ let endLine = startLine;
+
+ // collect all following :: definitions
+ for (let i = lineNumber + 1; i < lines.length; i++) {
+ const nextLine = lines[i];
+ const onlyColonsMatch = /^:*$/.test(nextLine);
+ const defMatch = /^(::)(.*\S.*)?\s*$/.exec(nextLine);
+ if(!onlyColonsMatch && defMatch) {
+ defs.push({ colons: defMatch[1], desc: defMatch[2], line: i });
+ endLine = i;
+ } else break;
+ }
+
+ if(defs.length > 0) {
+ tokens.push({
+ line : startLine,
+ type : customTags.definitionList,
+ });
+
+ // term
+ tokens.push({
+ line : startLine,
+ type : customTags.definitionTerm,
+ from : 0,
+ to : lineText.length,
+ });
+
+ // definitions
+ defs.forEach((d)=>{
+ tokens.push({
+ line : d.line,
+ type : customTags.definitionList,
+ });
+
+ tokens.push({
+ line : d.line,
+ type : customTags.definitionColon,
+ from : 0,
+ to : d.colons.length,
+ });
+ tokens.push({
+ line : d.line,
+ type : customTags.definitionDesc,
+ from : d.colons.length,
+ to : d.colons.length + d.desc.length,
+ });
+ });
+ }
+ }
+
+ if(lineText.includes('{') && lineText.includes('}')) {
+ const injectionRegex = /(?:^|[^{\n])({(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\2})/gm;
+ let match;
+ while ((match = injectionRegex.exec(lineText)) !== null) {
+ tokens.push({
+ line : lineNumber,
+ from : match.index,
+ to : match.index + match[1].length,
+ type : customTags.injection,
+ });
+ }
+ }
+ if(lineText.includes('{{') && lineText.includes('}}')) {
+ // Inline blocks: single-line {{…}}
+ const spanRegex = /{{(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\1 *|}}/g;
+ let match;
+ let blockCount = 0;
+ while ((match = spanRegex.exec(lineText)) !== null) {
+ if(match[0].startsWith('{{')) {
+ blockCount += 1;
+ } else {
+ blockCount -= 1;
+ }
+ if(blockCount < 0) {
+ blockCount = 0;
+ continue;
+ }
+ tokens.push({
+ line : lineNumber,
+ from : match.index,
+ to : match.index + match[0].length,
+ type : customTags.inlineBlock,
+ });
+ }
+ } else if(lineText.trimLeft().startsWith('{{') || lineText.trimLeft().startsWith('}}')) {
+ // Highlight block divs {{\n Content \n}}
+ let endCh = lineText.length + 1;
+
+ const match = lineText.match(
+ /^ *{{(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\1 *$|^ *}}$/,
+ );
+ if(match) endCh = match.index + match[0].length;
+ tokens.push({ line: lineNumber, type: customTags.block });
+ }
+ });
+
+ return tokens;
+}
+
+export function tokenizeCustomCSS(text) {
+ const tokens = [];
+ const lines = text.split('\n');
+
+ lines.forEach((lineText, lineNumber)=>{
+
+ if(/--[a-zA-Z0-9-_]+/gm.test(lineText)) {
+ const varRegex =/--[a-zA-Z0-9-_]+/gm;
+ let match;
+ while ((match = varRegex.exec(lineText)) !== null) {
+ tokens.push({
+ line : lineNumber,
+ from : match.index +1,
+ to : match.index + match.length[1] +1,
+ type : customTags.varProperty,
+ });
+ }
+ }
+ });
+
+ return tokens;
+}
+
+//assign classes to tags provided by lezer, not unlike the function above
+export const customHighlightStyle = HighlightStyle.define([
+ { tag: tags.heading, class: 'cm-header' },
+ { tag: tags.heading1, class: 'cm-header cm-header-1' },
+ { tag: tags.heading2, class: 'cm-header cm-header-2' },
+ { tag: tags.heading3, class: 'cm-header cm-header-3' },
+ { tag: tags.heading4, class: 'cm-header cm-header-4' },
+ { tag: tags.heading5, class: 'cm-header cm-header-5' },
+ { tag: tags.heading6, class: 'cm-header cm-header-6' },
+ { tag: tags.link, class: 'cm-link' },
+ { tag: tags.string, class: 'cm-string' },
+ { tag: tags.url, class: 'cm-string cm-url' },
+ { tag: tags.list, class: 'cm-list' },
+ { tag: tags.strong, class: 'cm-strong' },
+ { tag: tags.emphasis, class: 'cm-em' },
+ { tag: tags.quote, class: 'cm-quote' },
+ { tag: tags.comment, class: 'cm-comment' },
+ { tag: tags.monospace, class: 'cm-comment' },
+
+ //css tags
+
+ { tag: tags.tagName, class: 'cm-tag' },
+ { tag: tags.className, class: 'cm-class' },
+ { tag: tags.propertyName, class: 'cm-property' },
+ { tag: tags.attributeValue, class: 'cm-value' },
+ { tag: tags.keyword, class: 'cm-keyword' },
+ { tag: tags.atom, class: 'cm-atom' },
+ { tag: tags.integer, class: 'cm-integer' },
+ { tag: tags.unit, class: 'cm-unit' },
+ { tag: tags.color, class: 'cm-color' },
+ { tag: tags.paren, class: 'cm-paren' },
+ { tag: tags.variableName, class: 'cm-variable' },
+ { tag: tags.invalid, class: 'cm-error' },
+
+]);
+
+
+
diff --git a/client/components/codeEditor/customKeyMaps.js b/client/components/codeEditor/customKeyMaps.js
new file mode 100644
index 000000000..4bf1142ae
--- /dev/null
+++ b/client/components/codeEditor/customKeyMaps.js
@@ -0,0 +1,222 @@
+/* eslint max-lines: ["error", { "max": 300 }] */
+import { keymap } from '@codemirror/view';
+import { undo, redo, indentMore } from '@codemirror/commands';
+
+const indentLess = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const lines = [];
+ for (let l = view.state.doc.lineAt(from).number; l <= view.state.doc.lineAt(to).number; l++) {
+ const line = view.state.doc.line(l);
+ const match = line.text.match(/^ {1,2}/); // match up to 2 spaces
+ if(match) {
+ lines.push({ from: line.from, to: line.from + match[0].length, insert: '' });
+ }
+ }
+ if(lines.length > 0) view.dispatch({ changes: lines });
+ return true;
+};
+
+const makeBold = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('**') && selected.endsWith('**')
+ ? selected.slice(2, -2)
+ : `**${selected}**`;
+ view.dispatch({
+ changes : { from, to, insert: text },
+ selection : { anchor: from + text.length },
+ });
+ return true;
+};
+
+const makeItalic = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('*') && selected.endsWith('*')
+ ? selected.slice(1, -1)
+ : `*${selected}*`;
+ view.dispatch({
+ changes : { from, to, insert: text },
+ selection : { anchor: from + text.length },
+ });
+ return true;
+};
+
+const makeUnderline = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('
') && selected.endsWith('')
+ ? selected.slice(3, -4)
+ : `
${selected}`;
+ view.dispatch({
+ changes : { from, to, insert: text },
+ selection : { anchor: from + text.length },
+ });
+ return true;
+};
+
+const makeSuper = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('^') && selected.endsWith('^')
+ ? selected.slice(1, -1)
+ : `^${selected}^`;
+ view.dispatch({
+ changes : { from, to, insert: text },
+ selection : { anchor: from + text.length },
+ });
+ return true;
+};
+
+const makeSub = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('^^') && selected.endsWith('^^')
+ ? selected.slice(2, -2)
+ : `^^${selected}^^`;
+ view.dispatch({
+ changes : { from, to, insert: text },
+ selection : { anchor: from + text.length },
+ });
+ return true;
+};
+
+const makeNbsp = (view)=>{
+ const { from, to } = view.state.selection.main;
+ view.dispatch({ changes: { from, to, insert: ' ' } });
+ return true;
+};
+
+const makeSpace = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const match = selected.match(/^{{width:(\d+)% }}$/);
+ let newText = '{{width:10% }}';
+ if(match) {
+ const percent = Math.min(parseInt(match[1], 10) + 10, 100);
+ newText = `{{width:${percent}% }}`;
+ }
+ view.dispatch({ changes: { from, to, insert: newText } });
+ return true;
+};
+
+const removeSpace = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const match = selected.match(/^{{width:(\d+)% }}$/);
+ if(match) {
+ const percent = parseInt(match[1], 10) - 10;
+ const newText = percent > 0 ? `{{width:${percent}% }}` : '';
+ view.dispatch({ changes: { from, to, insert: newText } });
+ }
+ return true;
+};
+
+const makeSpan = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('{{') && selected.endsWith('}}')
+ ? selected.slice(2, -2)
+ : `{{${selected}}}`;
+ view.dispatch({ changes: { from, to, insert: text } });
+ return true;
+};
+
+const makeDiv = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = selected.startsWith('{{') && selected.endsWith('}}')
+ ? selected.slice(2, -2)
+ : `{{\n${selected}\n}}`;
+ view.dispatch({ changes: { from, to, insert: text } });
+ return true;
+};
+
+const makeComment = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const isHtmlComment = selected.startsWith('');
+ const text = isHtmlComment
+ ? selected.slice(4, -3)
+ : ``;
+ view.dispatch({ changes: { from, to, insert: text } });
+ return true;
+};
+
+const makeLink = (view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to).trim();
+ const isLink = /^\[(.*)\]\((.*)\)$/.exec(selected);
+ const text = isLink ? `${isLink[1]} ${isLink[2]}` : `[${selected || 'alt text'}](url)`;
+ view.dispatch({ changes: { from, to, insert: text } });
+ return true;
+};
+
+const makeList = (type)=>(view)=>{
+ const { from, to } = view.state.selection.main;
+ const lines = [];
+ for (let l = from; l <= to; l++) {
+ const lineText = view.state.doc.line(l + 1).text;
+ lines.push(lineText);
+ }
+ const joined = lines.join('\n');
+ let newText;
+ if(type === 'UL') newText = joined.replace(/^/gm, '- ');
+ else newText = joined.replace(/^/gm, (m, i)=>`${i + 1}. `);
+ view.dispatch({ changes: { from, to, insert: newText } });
+ return true;
+};
+
+const makeHeader = (level)=>(view)=>{
+ const { from, to } = view.state.selection.main;
+ const selected = view.state.doc.sliceString(from, to);
+ const text = `${'#'.repeat(level)} ${selected}`;
+ view.dispatch({ changes: { from, to, insert: text } });
+ return true;
+};
+
+const newColumn = (view)=>{
+ const { from, to } = view.state.selection.main;
+ view.dispatch({ changes: { from, to, insert: '\n\\column\n\n' } });
+ return true;
+};
+
+const newPage = (view)=>{
+ const { from, to } = view.state.selection.main;
+ view.dispatch({ changes: { from, to, insert: '\n\\page\n\n' } });
+ return true;
+};
+
+export const generalKeymap = keymap.of([
+ { key: 'Tab', run: indentMore },
+ { key: 'Mod-z', run: undo }, //i think it may be unnecessary
+ { key: 'Mod-Shift-z', run: redo },
+]);
+
+export const markdownKeymap = keymap.of([
+ //{ key: 'Shift-Tab', run: indentMore },
+ { key: 'Shift-Tab', run: indentLess },
+ { key: 'Mod-b', run: makeBold },
+ { key: 'Mod-i', run: makeItalic },
+ { key: 'Mod-u', run: makeUnderline },
+ { key: 'Shift-Mod-=', run: makeSuper },
+ { key: 'Mod-=', run: makeSub },
+ { key: 'Mod-.', run: makeNbsp },
+ { key: 'Shift-Mod-.', run: makeSpace },
+ { key: 'Shift-Mod-,', run: removeSpace },
+ { key: 'Mod-m', run: makeSpan },
+ { key: 'Shift-Mod-m', run: makeDiv },
+ { key: 'Mod-/', run: makeComment },
+ { key: 'Mod-k', run: makeLink },
+ { key: 'Mod-l', run: makeList('UL') },
+ { key: 'Shift-Mod-l', run: makeList('OL') },
+ { key: 'Shift-Mod-1', run: makeHeader(1) },
+ { key: 'Shift-Mod-2', run: makeHeader(2) },
+ { key: 'Shift-Mod-3', run: makeHeader(3) },
+ { key: 'Shift-Mod-4', run: makeHeader(4) },
+ { key: 'Shift-Mod-5', run: makeHeader(5) },
+ { key: 'Shift-Mod-6', run: makeHeader(6) },
+ { key: 'Shift-Mod-Enter', run: newColumn },
+ { key: 'Mod-Enter', run: newPage },
+
+]);
diff --git a/client/components/codeEditor/fold-css.js b/client/components/codeEditor/fold-css.js
deleted file mode 100644
index 06bfd96a4..000000000
--- a/client/components/codeEditor/fold-css.js
+++ /dev/null
@@ -1,44 +0,0 @@
-export default {
- registerHomebreweryHelper : function(CodeMirror) {
- CodeMirror.registerHelper('fold', 'homebrewerycss', function(cm, start) {
-
- // BRACE FOLDING
- const startMatcher = /\{[ \t]*$/;
- const endMatcher = /\}[ \t]*$/;
- const activeLine = cm.getLine(start.line);
-
-
- if(activeLine.match(startMatcher)) {
- const lastLineNo = cm.lastLine();
- let end = start.line + 1;
- let braceCount = 1;
-
- while (end < lastLineNo) {
- const curLine = cm.getLine(end);
- if(curLine.match(startMatcher)) braceCount++;
- if(curLine.match(endMatcher)) braceCount--;
- if(braceCount == 0) break;
- ++end;
- }
-
- return {
- from : CodeMirror.Pos(start.line, 0),
- to : CodeMirror.Pos(end, cm.getLine(end).length)
- };
- }
-
- // @import and data-url folding
- const importMatcher = /^@import.*?;/;
- const dataURLMatcher = /url\(.*?data\:.*\)/;
-
- if(activeLine.match(importMatcher) || activeLine.match(dataURLMatcher)) {
- return {
- from : CodeMirror.Pos(start.line, 0),
- to : CodeMirror.Pos(start.line, activeLine.length)
- };
- }
-
- return null;
- });
- }
-};
diff --git a/client/components/codeEditor/fold-pages.js b/client/components/codeEditor/fold-pages.js
deleted file mode 100644
index 1d8d19f6b..000000000
--- a/client/components/codeEditor/fold-pages.js
+++ /dev/null
@@ -1,26 +0,0 @@
-export default {
- registerHomebreweryHelper : function(CodeMirror) {
- CodeMirror.registerHelper('fold', 'homebrewery', function(cm, start) {
- const matcher = /^\\page.*/;
- const prevLine = cm.getLine(start.line - 1);
-
- if(start.line === cm.firstLine() || prevLine.match(matcher)) {
- const lastLineNo = cm.lastLine();
- let end = start.line;
-
- while (end < lastLineNo) {
- if(cm.getLine(end + 1).match(matcher))
- break;
- ++end;
- }
-
- return {
- from : CodeMirror.Pos(start.line, 0),
- to : CodeMirror.Pos(end, cm.getLine(end).length)
- };
- }
-
- return null;
- });
- }
-};
diff --git a/client/components/codeEditor/legacyCustomHighlight.js b/client/components/codeEditor/legacyCustomHighlight.js
new file mode 100644
index 000000000..cccb6647b
--- /dev/null
+++ b/client/components/codeEditor/legacyCustomHighlight.js
@@ -0,0 +1,54 @@
+import { HighlightStyle } from '@codemirror/language';
+import { tags } from '@lezer/highlight';
+
+const customTags = {
+ pageLine : 'pageLine', // .cm-pageLine
+ snippetLine : 'snippetLine', // .cm-snippetLine
+};
+
+export function legacyTokenizeCustomMarkdown(text) {
+ const tokens = [];
+ const lines = text.split('\n');
+
+ lines.forEach((lineText, lineNumber)=>{
+ // --- Page / snippet lines ---
+ if(/^(?=\\page(?:break)?(?: *{[^\n{}]*})?$)/m.test(lineText)) tokens.push({ line: lineNumber, type: customTags.pageLine });
+ if(/^\\snippet\ .*$/.test(lineText)) tokens.push({ line: lineNumber, type: customTags.snippetLine });
+ });
+
+ return tokens;
+}
+
+export const legacyCustomHighlightStyle = HighlightStyle.define([
+ { tag: tags.heading, class: 'cm-header' },
+ { tag: tags.heading1, class: 'cm-header cm-header-1' },
+ { tag: tags.heading2, class: 'cm-header cm-header-2' },
+ { tag: tags.heading3, class: 'cm-header cm-header-3' },
+ { tag: tags.heading4, class: 'cm-header cm-header-4' },
+ { tag: tags.heading5, class: 'cm-header cm-header-5' },
+ { tag: tags.heading6, class: 'cm-header cm-header-6' },
+ { tag: tags.link, class: 'cm-link' },
+ { tag: tags.string, class: 'cm-string' },
+ { tag: tags.url, class: 'cm-string cm-url' },
+ { tag: tags.list, class: 'cm-list' },
+ { tag: tags.strong, class: 'cm-strong' },
+ { tag: tags.emphasis, class: 'cm-em' },
+ { tag: tags.quote, class: 'cm-quote' },
+
+ //css tags
+
+ { tag: tags.tagName, class: 'cm-tag' },
+ { tag: tags.className, class: 'cm-class' },
+ { tag: tags.propertyName, class: 'cm-property' },
+ { tag: tags.attributeValue, class: 'cm-value' },
+ { tag: tags.keyword, class: 'cm-keyword' },
+ { tag: tags.atom, class: 'cm-atom' },
+ { tag: tags.integer, class: 'cm-integer' },
+ { tag: tags.unit, class: 'cm-unit' },
+ { tag: tags.color, class: 'cm-color' },
+ { tag: tags.paren, class: 'cm-paren' },
+ { tag: tags.variableName, class: 'cm-variable' },
+ { tag: tags.invalid, class: 'cm-error' },
+ { tag: tags.comment, class: 'cm-comment' },
+]);
+
diff --git a/client/homebrew/brewRenderer/brewRenderer.jsx b/client/homebrew/brewRenderer/brewRenderer.jsx
index e5f5eb1ef..202c1a375 100644
--- a/client/homebrew/brewRenderer/brewRenderer.jsx
+++ b/client/homebrew/brewRenderer/brewRenderer.jsx
@@ -273,13 +273,7 @@ const BrewRenderer = (props)=>{
const frameDidMount = ()=>{ //This triggers when iFrame finishes internal "componentDidMount"
scrollToHash(window.location.hash);
- window.addEventListener('hashchange', ()=>{
- scrollToHash(window.location.hash);
- });
-
- window.onbeforeunload(()=>{
- window.removeEventListener('hashchange');
- });
+ window.addEventListener('hashchange', ()=>scrollToHash(window.location.hash));
setTimeout(()=>{ //We still see a flicker where the style isn't applied yet, so wait 100ms before showing iFrame
renderPages(); //Make sure page is renderable before showing
diff --git a/client/homebrew/editor/editor.jsx b/client/homebrew/editor/editor.jsx
index ced40f48f..0da396697 100644
--- a/client/homebrew/editor/editor.jsx
+++ b/client/homebrew/editor/editor.jsx
@@ -4,7 +4,6 @@ import React from 'react';
import createReactClass from 'create-react-class';
import _ from 'lodash';
import dedent from 'dedent';
-import Markdown from '@shared/markdown.js';
import CodeEditor from '../../components/codeEditor/codeEditor.jsx';
import SnippetBar from './snippetbar/snippetbar.jsx';
@@ -12,8 +11,22 @@ import MetadataEditor from './metadataEditor/metadataEditor.jsx';
const EDITOR_THEME_KEY = 'HB_editor_theme';
-const PAGEBREAK_REGEX_V3 = /^(?=\\page(?:break)?(?: *{[^\n{}]*})?$)/m;
-const SNIPPETBREAK_REGEX_V3 = /^\\snippet\ .*$/;
+import * as themesImport from '@uiw/codemirror-themes-all';
+import defaultCM5Theme from '@themes/codeMirror/default.js';
+import darkbrewery from '@themes/codeMirror/darkbrewery.js';
+
+const themes = { default: defaultCM5Theme, darkbrewery, ...themesImport };
+
+const EditorThemes = Object.entries(themes)
+ .filter(([name, value])=>Array.isArray(value) &&
+ !name.endsWith('Init') &&
+ !name.endsWith('Style')
+ )
+ .map(([name])=>name);
+
+
+//const PAGEBREAK_REGEX_V3 = /^(?=\\page(?:break)?(?: *{[^\n{}]*})?$)/m;
+//const SNIPPETBREAK_REGEX_V3 = /^\\snippet\ .*$/;
const DEFAULT_STYLE_TEXT = dedent`
/*=======--- Example CSS styling ---=======*/
/* Any CSS here will apply to your document! */
@@ -30,6 +43,7 @@ const DEFAULT_SNIPPET_TEXT = dedent`
This snippet is accessible in the brew tab, and will be inherited if the brew is used as a theme.
`;
let isJumping = false;
+let jumpSource = null;
const Editor = createReactClass({
displayName : 'Editor',
@@ -72,15 +86,15 @@ const Editor = createReactClass({
componentDidMount : function() {
- this.highlightCustomMarkdown();
- document.getElementById('BrewRenderer').addEventListener('keydown', this.handleControlKeys);
+ const brewRenderer = document.getElementById('BrewRenderer');
+ brewRenderer.onload = ()=>brewRenderer.contentDocument?.addEventListener('keydown', this.handleControlKeys);
document.addEventListener('keydown', this.handleControlKeys);
const editorTheme = window.localStorage.getItem(EDITOR_THEME_KEY);
- if(editorTheme) {
- this.setState({
- editorTheme : editorTheme
- });
+ if(editorTheme && EditorThemes.includes(editorTheme)) {
+ this.setState({ editorTheme });
+ } else {
+ this.setState({ editorTheme: 'default' });
}
const snippetBar = document.querySelector('.editor > .snippetBar');
if(!snippetBar) return;
@@ -95,7 +109,6 @@ const Editor = createReactClass({
componentDidUpdate : function(prevProps, prevState, snapshot) {
- this.highlightCustomMarkdown();
if(prevProps.moveBrew !== this.props.moveBrew)
this.brewJump();
@@ -129,22 +142,16 @@ const Editor = createReactClass({
}
},
- updateCurrentCursorPage : function(cursor) {
- const lines = this.props.brew.text.split('\n').slice(1, cursor.line + 1);
- const pageRegex = this.props.brew.renderer == 'V3' ? PAGEBREAK_REGEX_V3 : /\\page/;
- const currentPage = lines.reduce((count, line)=>count + (pageRegex.test(line) ? 1 : 0), 1);
- this.props.onCursorPageChange(currentPage);
+ updateCurrentCursorPage : function(pageNumber) {
+ this.props.onCursorPageChange(pageNumber);
},
- updateCurrentViewPage : function(topScrollLine) {
- const lines = this.props.brew.text.split('\n').slice(1, topScrollLine + 1);
- const pageRegex = this.props.brew.renderer == 'V3' ? PAGEBREAK_REGEX_V3 : /\\page/;
- const currentPage = lines.reduce((count, line)=>count + (pageRegex.test(line) ? 1 : 0), 1);
- this.props.onViewPageChange(currentPage);
+ updateCurrentViewPage : function(pageNumber) {
+ this.props.onViewPageChange(pageNumber);
},
handleInject : function(injectText){
- this.codeEditor.current?.injectText(injectText, false);
+ this.codeEditor.current?.injectText(injectText);
},
handleViewChange : function(newView){
@@ -153,181 +160,12 @@ const Editor = createReactClass({
this.setState({
view : newView
}, ()=>{
- this.codeEditor.current?.codeMirror?.focus();
+ this.codeEditor.current?.focus();
});
},
- highlightCustomMarkdown : function(){
- if(!this.codeEditor.current?.codeMirror) return;
- if((this.state.view === 'text') ||(this.state.view === 'snippet')) {
- const codeMirror = this.codeEditor.current.codeMirror;
-
- codeMirror?.operation(()=>{ // Batch CodeMirror styling
-
- const foldLines = [];
-
- //reset custom text styles
- const customHighlights = codeMirror?.getAllMarks().filter((mark)=>{
- // Record details of folded sections
- if(mark.__isFold) {
- const fold = mark.find();
- foldLines.push({ from: fold.from?.line, to: fold.to?.line });
- }
- return !mark.__isFold;
- }); //Don't undo code folding
-
- for (let i=customHighlights.length - 1;i>=0;i--) customHighlights[i].clear();
-
- let userSnippetCount = 1; // start snippet count from snippet 1
- let editorPageCount = 1; // start page count from page 1
-
- const whichSource = this.state.view === 'text' ? this.props.brew.text : this.props.brew.snippets;
- _.forEach(whichSource?.split('\n'), (line, lineNumber)=>{
-
- const tabHighlight = this.state.view === 'text' ? 'pageLine' : 'snippetLine';
- const textOrSnip = this.state.view === 'text';
-
- //reset custom line styles
- codeMirror?.removeLineClass(lineNumber, 'background', 'pageLine');
- codeMirror?.removeLineClass(lineNumber, 'background', 'snippetLine');
- codeMirror?.removeLineClass(lineNumber, 'text');
- codeMirror?.removeLineClass(lineNumber, 'wrap', 'sourceMoveFlash');
-
- // Don't process lines inside folded text
- // If the current lineNumber is inside any folded marks, skip line styling
- if(foldLines.some((fold)=>lineNumber >= fold.from && lineNumber <= fold.to))
- return;
-
- // Styling for \page breaks
- if((this.props.renderer == 'legacy' && line.includes('\\page')) ||
- (this.props.renderer == 'V3' && line.match(textOrSnip ? PAGEBREAK_REGEX_V3 : SNIPPETBREAK_REGEX_V3))) {
-
- if((lineNumber > 0) && (textOrSnip)) // Since \page is optional on first line of document,
- editorPageCount += 1; // don't use it to increment page count; stay at 1
- else if(this.state.view !== 'text') userSnippetCount += 1;
-
- // add back the original class 'background' but also add the new class '.pageline'
- codeMirror?.addLineClass(lineNumber, 'background', tabHighlight);
- const pageCountElement = Object.assign(document.createElement('span'), {
- className : 'editor-page-count',
- textContent : textOrSnip ? editorPageCount : userSnippetCount
- });
- codeMirror?.setBookmark({ line: lineNumber, ch: line.length }, pageCountElement);
- };
-
-
- // New CodeMirror styling for V3 renderer
- if(this.props.renderer === 'V3') {
- if(line.match(/^\\column(?:break)?$/)){
- codeMirror?.addLineClass(lineNumber, 'text', 'columnSplit');
- }
-
- // definition lists
- if(line.includes('::')){
- if(/^:*$/.test(line) == true){ return; };
- const regex = /^([^\n]*?:?\s?)(::[^\n]*)(?:\n|$)/ymd; // the `d` flag, for match indices, throws an ESLint error.
- let match;
- while ((match = regex.exec(line)) != null){
- codeMirror?.markText({ line: lineNumber, ch: match.indices[0][0] }, { line: lineNumber, ch: match.indices[0][1] }, { className: 'dl-highlight' });
- codeMirror?.markText({ line: lineNumber, ch: match.indices[1][0] }, { line: lineNumber, ch: match.indices[1][1] }, { className: 'dt-highlight' });
- codeMirror?.markText({ line: lineNumber, ch: match.indices[2][0] }, { line: lineNumber, ch: match.indices[2][1] }, { className: 'dd-highlight' });
- const ddIndex = match.indices[2][0];
- const colons = /::/g;
- const colonMatches = colons.exec(match[2]);
- if(colonMatches !== null){
- codeMirror?.markText({ line: lineNumber, ch: colonMatches.index + ddIndex }, { line: lineNumber, ch: colonMatches.index + colonMatches[0].length + ddIndex }, { className: 'dl-colon-highlight' });
- }
- }
- }
-
- // Subscript & Superscript
- if(line.includes('^')) {
- let startIndex = line.indexOf('^');
- const superRegex = /\^(?!\s)(?=([^\n\^]*[^\s\^]))\1\^/gy;
- const subRegex = /\^\^(?!\s)(?=([^\n\^]*[^\s\^]))\1\^\^/gy;
-
- while (startIndex >= 0) {
- superRegex.lastIndex = subRegex.lastIndex = startIndex;
- let isSuper = false;
- const match = subRegex.exec(line) || superRegex.exec(line);
- if(match) {
- isSuper = !subRegex.lastIndex;
- codeMirror?.markText({ line: lineNumber, ch: match.index }, { line: lineNumber, ch: match.index + match[0].length }, { className: isSuper ? 'superscript' : 'subscript' });
- }
- startIndex = line.indexOf('^', Math.max(startIndex + 1, subRegex.lastIndex, superRegex.lastIndex));
- }
- }
-
- // Highlight injectors {style}
- if(line.includes('{') && line.includes('}')){
- const regex = /(?:^|[^{\n])({(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\2})/gm;
- let match;
- while ((match = regex.exec(line)) != null) {
- codeMirror?.markText({ line: lineNumber, ch: line.indexOf(match[1]) }, { line: lineNumber, ch: line.indexOf(match[1]) + match[1].length }, { className: 'injection' });
- }
- }
- // Highlight inline spans {{content}}
- if(line.includes('{{') && line.includes('}}')){
- const regex = /{{(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\1 *|}}/g;
- let match;
- let blockCount = 0;
- while ((match = regex.exec(line)) != null) {
- if(match[0].startsWith('{')) {
- blockCount += 1;
- } else {
- blockCount -= 1;
- }
- if(blockCount < 0) {
- blockCount = 0;
- continue;
- }
- codeMirror?.markText({ line: lineNumber, ch: match.index }, { line: lineNumber, ch: match.index + match[0].length }, { className: 'inline-block' });
- }
- } else if(line.trimLeft().startsWith('{{') || line.trimLeft().startsWith('}}')){
- // Highlight block divs {{\n Content \n}}
- let endCh = line.length+1;
-
- const match = line.match(/^ *{{(?=((?:[:=](?:"[\w,\-()#%. ]*"|[\w\-()#%.]*)|[^"':={}\s]*)*))\1 *$|^ *}}$/);
- if(match)
- endCh = match.index+match[0].length;
- codeMirror?.markText({ line: lineNumber, ch: 0 }, { line: lineNumber, ch: endCh }, { className: 'block' });
- }
-
- // Emojis
- if(line.match(/:[^\s:]+:/g)) {
- let startIndex = line.indexOf(':');
- const emojiRegex = /:[^\s:]+:/gy;
-
- while (startIndex >= 0) {
- emojiRegex.lastIndex = startIndex;
- const match = emojiRegex.exec(line);
- if(match) {
- let tokens = Markdown.marked.lexer(match[0]);
- tokens = tokens[0].tokens.filter((t)=>t.type == 'emoji');
- if(!tokens.length)
- return;
-
- const startPos = { line: lineNumber, ch: match.index };
- const endPos = { line: lineNumber, ch: match.index + match[0].length };
-
- // Iterate over conflicting marks and clear them
- const marks = codeMirror?.findMarks(startPos, endPos);
- marks.forEach(function(marker) {
- if(!marker.__isFold) marker.clear();
- });
- codeMirror?.markText(startPos, endPos, { className: 'emoji' });
- }
- startIndex = line.indexOf(':', Math.max(startIndex + 1, emojiRegex.lastIndex));
- }
- }
- }
- });
- });
- }
- },
-
brewJump : function(targetPage=this.props.currentEditorCursorPageNum, smooth=true){
- if(!window || !this.isText() || isJumping)
+ if(!window || !this.isText() || isJumping || jumpSource === 'source')
return;
// Get current brewRenderer scroll position and calculate target position
@@ -340,11 +178,13 @@ const Editor = createReactClass({
clearTimeout(scrollingTimeout); // Reset the timer every time a scroll event occurs
scrollingTimeout = setTimeout(()=>{
isJumping = false;
+ jumpSource = null;
brewRenderer.removeEventListener('scroll', checkIfScrollComplete);
}, 150); // If 150 ms pass without a brewRenderer scroll event, assume scrolling is done
};
isJumping = true;
+ jumpSource = 'brew';
checkIfScrollComplete();
brewRenderer.addEventListener('scroll', checkIfScrollComplete);
@@ -368,54 +208,17 @@ const Editor = createReactClass({
},
sourceJump : function(targetPage=this.props.currentBrewRendererPageNum, smooth=true){
- if(!this.isText() || isJumping)
+ if(!this.isText() || isJumping || jumpSource === 'brew')
return;
- const textSplit = this.props.renderer == 'V3' ? PAGEBREAK_REGEX_V3 : /\\page/;
- const textString = this.props.brew.text.split(textSplit).slice(0, targetPage-1).join(textSplit);
- const targetLine = textString.match('\n') ? textString.split('\n').length - 1 : -1;
+ const editor = this.codeEditor.current;
+ if(!editor) return;
+ jumpSource = 'source';
- let currentY = this.codeEditor.current.codeMirror?.getScrollInfo().top;
- let targetY = this.codeEditor.current.codeMirror?.heightAtLine(targetLine, 'local', true);
-
- let scrollingTimeout;
- const checkIfScrollComplete = ()=>{ // Prevent interrupting a scroll in progress if user clicks multiple times
- clearTimeout(scrollingTimeout); // Reset the timer every time a scroll event occurs
- scrollingTimeout = setTimeout(()=>{
- isJumping = false;
- this.codeEditor.current.codeMirror?.off('scroll', checkIfScrollComplete);
- }, 150); // If 150 ms pass without a scroll event, assume scrolling is done
- };
-
- isJumping = true;
- checkIfScrollComplete();
- if(this.codeEditor.current?.codeMirror) {
- this.codeEditor.current.codeMirror?.on('scroll', checkIfScrollComplete);
- }
-
- if(smooth) {
- //Scroll 1/10 of the way every 10ms until 1px off.
- const incrementalScroll = setInterval(()=>{
- currentY += (targetY - currentY) / 10;
- this.codeEditor.current.codeMirror?.scrollTo(null, currentY);
-
- // Update target: target height is not accurate until within +-10 lines of the visible window
- if(Math.abs(targetY - currentY > 100))
- targetY = this.codeEditor.current.codeMirror?.heightAtLine(targetLine, 'local', true);
-
- // End when close enough
- if(Math.abs(targetY - currentY) < 1) {
- this.codeEditor.current.codeMirror?.scrollTo(null, targetY); // Scroll any remaining difference
- this.codeEditor.current.setCursorPosition({ line: targetLine + 1, ch: 0 });
- this.codeEditor.current.codeMirror?.addLineClass(targetLine + 1, 'wrap', 'sourceMoveFlash');
- clearInterval(incrementalScroll);
- }
- }, 10);
- } else {
- this.codeEditor.current.codeMirror?.scrollTo(null, targetY); // Scroll any remaining difference
- this.codeEditor.current.setCursorPosition({ line: targetLine + 1, ch: 0 });
- this.codeEditor.current.codeMirror?.addLineClass(targetLine + 1, 'wrap', 'sourceMoveFlash');
- }
+ editor.scrollToPage(targetPage);
+ setTimeout(()=>{
+ jumpSource = null;
+ }, 200);
},
//Called when there are changes to the editor's dimensions
@@ -433,29 +236,6 @@ const Editor = createReactClass({
this.forceUpdate();
},
- //temporary fix until cm6 comes next update
- attachCodeMirrorListeners : function(cm) {
- if(!cm) return;
- // detach previous (important on remount / view switch)
- if(this._cm) {
- this._cm.off('cursorActivity', this._onCursor);
- this._cm.off('scroll', this._onScroll);
- }
-
- this._cm = cm;
-
- this._onCursor = ()=>{
- this.updateCurrentCursorPage(cm.getCursor());
- };
-
- this._onScroll = _.throttle(()=>{
- const topLine = cm.lineAtHeight(cm.getScrollInfo().top, 'local');
- this.updateCurrentViewPage(topLine);
- }, 200);
-
- cm.on('cursorActivity', this._onCursor);
- cm.on('scroll', this._onScroll);
- },
renderEditor : function(){
if(this.isText()){
return <>
@@ -466,10 +246,11 @@ const Editor = createReactClass({
view={this.state.view}
value={this.props.brew.text}
onChange={this.props.onBrewChange('text')}
+ onCursorChange={(page)=>this.updateCurrentCursorPage(page)}
+ onViewChange={(page)=>this.updateCurrentViewPage(page)}
editorTheme={this.state.editorTheme}
- rerenderParent={this.rerenderParent}
- style={{ height: `calc(100% - ${this.state.snippetBarHeight}px)` }}
- onReady={this.attachCodeMirrorListeners}/>
+ renderer={this.props.brew.renderer}
+ style={{ height: `calc(100% - ${this.state.snippetBarHeight}px)` }}/>
>;
}
if(this.isStyle()){
@@ -481,19 +262,16 @@ const Editor = createReactClass({
view={this.state.view}
value={this.props.brew.style ?? DEFAULT_STYLE_TEXT}
onChange={this.props.onBrewChange('style')}
- enableFolding={true}
editorTheme={this.state.editorTheme}
- rerenderParent={this.rerenderParent}
- style={{ height: `calc(100% - ${this.state.snippetBarHeight}px)` }}
- onReady={this.attachCodeMirrorListeners}/>
+ renderer={this.props.brew.renderer}
+ style={{ height: `calc(100% - ${this.state.snippetBarHeight}px)` }}/>
>;
}
if(this.isMeta()){
return <>
+ style={{ display: 'none' }}/>
+ style={{ height: `calc(100% - 25px)` }}/>
>;
}
},
@@ -533,14 +311,13 @@ const Editor = createReactClass({
return this.codeEditor.current?.undo();
},
- foldCode : function(){
- return this.codeEditor.current?.foldAllCode();
+ foldCode : function() {
+ return this.codeEditor.current?.foldAll();
},
- unfoldCode : function(){
- return this.codeEditor.current?.unfoldAllCode();
+ unfoldCode : function() {
+ return this.codeEditor.current?.unfoldAll();
},
-
render : function(){
return (
@@ -570,4 +347,4 @@ const Editor = createReactClass({
}
});
-export default Editor;
+export default Editor;
\ No newline at end of file
diff --git a/client/homebrew/editor/editor.less b/client/homebrew/editor/editor.less
index 3851b50c5..7503749fc 100644
--- a/client/homebrew/editor/editor.less
+++ b/client/homebrew/editor/editor.less
@@ -1,89 +1,120 @@
@import '@sharedStyles/core.less';
-@import '@themes/codeMirror/customEditorStyles.less';
-.editor {
- position : relative;
- width : 100%;
- height : 100%;
- container : editor / inline-size;
- background:white;
- .codeEditor {
+:where(.editor) {
+ position : relative;
+ width : 100%;
+ height : 100%;
+ container : editor / inline-size;
+ background : white;
+ :where(.codeEditor) {
height : calc(100% - 25px);
- .CodeMirror { height : 100%; }
- .pageLine, .snippetLine {
+ .cm-editor { height : 100%;
+ outline:none !important;
+ }
+ &.brewSnippets .cm-snippetLine {
background : #33333328;
border-top : #333399 solid 1px;
}
- .editor-page-count {
- float : right;
- color : grey;
+
+ :where(&.brewText) .cm-pageLine {
+ background : #33333328;
+ border-top : #333399 solid 1px;
}
- .editor-snippet-count {
- float : right;
- color : grey;
- }
- .columnSplit {
- font-style : italic;
- color : grey;
- background-color : fade(#229999, 15%);
- border-bottom : #229999 solid 1px;
- }
- .define {
- &:not(.term):not(.definition) {
- font-weight : bold;
- color : #949494;
- background : #E5E5E5;
- border-radius : 3px;
+
+ &.brewSnippets {
+ .cm-pageLine {
+ background : #3e4e3e1b;
+ border-top : #3399423b solid 1px;
+ color:#777;
}
- &.term { color : rgb(96, 117, 143); }
- &.definition { color : rgb(97, 57, 178); }
}
- .block:not(.cm-comment) {
- font-weight : bold;
- color : purple;
- //font-style: italic;
- }
- .inline-block:not(.cm-comment) {
- font-weight : bold;
- color : red;
- //font-style: italic;
- }
- .injection:not(.cm-comment) {
- font-weight : bold;
- color : green;
- }
- .emoji:not(.cm-comment) {
- padding-bottom : 1px;
- margin-left : 2px;
- font-weight : bold;
- color : #360034;
- outline : solid 2px #FF96FC;
- outline-offset : -2px;
- background : #FFC8FF;
- border-radius : 6px;
- }
- .superscript:not(.cm-comment) {
- font-size : 0.9em;
- font-weight : bold;
- vertical-align : super;
- color : goldenrod;
- }
- .subscript:not(.cm-comment) {
- font-size : 0.9em;
- font-weight : bold;
- vertical-align : sub;
- color : rgb(123, 123, 15);
- }
- .dl-highlight {
- &.dl-colon-highlight {
- font-weight : bold;
- color : #949494;
- background : #E5E5E5;
- border-radius : 3px;
+
+ &:where(.brewText), &.brewSnippets {
+
+
+ .cm-tooltip-autocomplete {
+
+ li {
+ display : flex;
+ gap : 10px;
+ align-items : center;
+ justify-content : flex-start;
+
+ .cm-completionIcon { display : none; }
+ .cm-tooltip-autocomplete .cm-completionLabel { translate : 0 -2px; }
+ }
}
- &.dt-highlight { color : rgb(96, 117, 143); }
- &.dd-highlight { color : rgb(97, 57, 178); }
- }
+
+ .cm-pageLine[data-page-number]::after {
+ content:attr(data-page-number);
+ float:right;
+ color : grey;
+ }
+ .cm-columnSplit {
+ font-style : italic;
+ color : grey;
+ background-color : fade(#229999, 15%);
+ border-bottom : #229999 solid 1px;
+ }
+ .cm-define {
+ &:not(.term):not(.definition) {
+ font-weight : bold;
+ color : #949494;
+ background : #E5E5E5;
+ border-radius : 3px;
+ }
+ &.term { color : rgb(96, 117, 143); }
+ &.definition { color : rgb(97, 57, 178); }
+ }
+ .cm-block:not(.cm-comment) {
+ font-weight : bold;
+ color : purple;
+ }
+ .cm-inline-block:not(.cm-comment) {
+ font-weight : bold;
+ color : red ;
+ span { color : inherit }
+ }
+ .cm-injection:not(.cm-comment) {
+ font-weight : bold;
+ color : green;
+ span { color : inherit }
+ }
+ .cm-emoji:not(.cm-comment) {
+ padding-bottom : 1px;
+ margin-left : 2px;
+ font-weight : bold;
+ color : #360034;
+ outline : solid 2px #FF96FC;
+ outline-offset : -2px;
+ background : #FFC8FF;
+ border-radius : 6px;
+ }
+ .cm-superscript:not(.cm-comment) {
+ font-size : 0.9em;
+ font-weight : bold;
+ vertical-align : super;
+ color : goldenrod;
+ }
+ .cm-subscript:not(.cm-comment) {
+ font-size : 0.9em;
+ font-weight : bold;
+ vertical-align : sub;
+ color : rgb(123, 123, 15);
+ }
+ .cm-definitionList {
+ .cm-definitionTerm { color : rgb(96, 117, 143); }
+ .cm-definitionColon {
+ font-weight : bold;
+ color : #949494;
+ background : #E5E5E5;
+ border-radius : 3px;
+ }
+ .cm-definitionDesc { color : rgb(97, 57, 178); }
+ }
+
+ }
+
}
.brewJump {
diff --git a/client/homebrew/editor/snippetbar/snippetbar.jsx b/client/homebrew/editor/snippetbar/snippetbar.jsx
index 304664ff5..112e3b701 100644
--- a/client/homebrew/editor/snippetbar/snippetbar.jsx
+++ b/client/homebrew/editor/snippetbar/snippetbar.jsx
@@ -23,7 +23,19 @@ const ThemeSnippets = {
V3_Blank : V3_Blank,
};
-import EditorThemes from '../../../../build/homebrew/codeMirror/editorThemes.json';
+import * as themesImport from '@uiw/codemirror-themes-all';
+import defaultCM5Theme from '@themes/codeMirror/default.js';
+import darkbrewery from '@themes/codeMirror/darkbrewery.js';
+
+const themes = { default: defaultCM5Theme, darkbrewery, ...themesImport };
+
+const EditorThemes = Object.entries(themes)
+ .filter(([name, value]) =>
+ Array.isArray(value) &&
+ !name.endsWith('Init') &&
+ !name.endsWith('Style')
+ )
+ .map(([name]) => name);
const execute = function(val, props){
if(_.isFunction(val)) return val(props);
@@ -232,11 +244,11 @@ const Snippetbar = createReactClass({
{ this.state.showHistory && this.renderHistoryItems() }
-
-
diff --git a/package-lock.json b/package-lock.json
index b67bcb18f..59f0a8206 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -15,13 +15,25 @@
"@babel/preset-env": "^7.29.2",
"@babel/preset-react": "^7.28.5",
"@babel/runtime": "^7.29.2",
+ "@codemirror/autocomplete": "^6.20.1",
+ "@codemirror/commands": "^6.10.3",
+ "@codemirror/highlight": "^0.19.8",
+ "@codemirror/lang-css": "^6.3.1",
+ "@codemirror/lang-javascript": "^6.2.5",
+ "@codemirror/lang-markdown": "^6.5.0",
+ "@codemirror/language": "^6.12.2",
+ "@codemirror/language-data": "^6.5.2",
+ "@codemirror/search": "^6.6.0",
+ "@codemirror/state": "^6.6.0",
+ "@codemirror/view": "^6.40.0",
"@dmsnell/diff-match-patch": "^1.1.0",
"@googleapis/drive": "^20.1.0",
+ "@lezer/highlight": "^1.2.3",
"@sanity/diff-match-patch": "^3.2.0",
+ "@uiw/codemirror-themes-all": "^4.25.8",
"@vitejs/plugin-react": "^5.1.2",
"body-parser": "^2.2.0",
"classnames": "^2.5.1",
- "codemirror": "^5.65.6",
"cookie-parser": "^1.4.7",
"core-js": "^3.49.0",
"cors": "^2.8.5",
@@ -93,32 +105,22 @@
"license": "MIT"
},
"node_modules/@asamuzakjp/css-color": {
- "version": "5.1.5",
- "resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-5.1.5.tgz",
- "integrity": "sha512-8cMAA1bE66Mb/tfmkhcfJLjEPgyT7SSy6lW6id5XL113ai1ky76d/1L27sGnXCMsLfq66DInAU3OzuahB4lu9Q==",
+ "version": "5.1.11",
+ "resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-5.1.11.tgz",
+ "integrity": "sha512-KVw6qIiCTUQhByfTd78h2yD1/00waTmm9uy/R7Ck/ctUyAPj+AEDLkQIdJW0T8+qGgj3j5bpNKK7Q3G+LedJWg==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@csstools/css-calc": "^3.1.1",
- "@csstools/css-color-parser": "^4.0.2",
+ "@asamuzakjp/generational-cache": "^1.0.1",
+ "@csstools/css-calc": "^3.2.0",
+ "@csstools/css-color-parser": "^4.1.0",
"@csstools/css-parser-algorithms": "^4.0.0",
- "@csstools/css-tokenizer": "^4.0.0",
- "lru-cache": "^11.2.7"
+ "@csstools/css-tokenizer": "^4.0.0"
},
"engines": {
"node": "^20.19.0 || ^22.12.0 || >=24.0.0"
}
},
- "node_modules/@asamuzakjp/css-color/node_modules/lru-cache": {
- "version": "11.2.7",
- "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.7.tgz",
- "integrity": "sha512-aY/R+aEsRelme17KGQa/1ZSIpLpNYYrhcrepKTZgE+W3WM16YMCaPwOHLHsmopZHELU0Ojin1lPVxKR0MihncA==",
- "dev": true,
- "license": "BlueOak-1.0.0",
- "engines": {
- "node": "20 || >=22"
- }
- },
"node_modules/@asamuzakjp/dom-selector": {
"version": "6.8.1",
"resolved": "https://registry.npmjs.org/@asamuzakjp/dom-selector/-/dom-selector-6.8.1.tgz",
@@ -134,15 +136,25 @@
}
},
"node_modules/@asamuzakjp/dom-selector/node_modules/lru-cache": {
- "version": "11.2.7",
- "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.7.tgz",
- "integrity": "sha512-aY/R+aEsRelme17KGQa/1ZSIpLpNYYrhcrepKTZgE+W3WM16YMCaPwOHLHsmopZHELU0Ojin1lPVxKR0MihncA==",
+ "version": "11.3.5",
+ "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.3.5.tgz",
+ "integrity": "sha512-NxVFwLAnrd9i7KUBxC4DrUhmgjzOs+1Qm50D3oF1/oL+r1NpZ4gA7xvG0/zJ8evR7zIKn4vLf7qTNduWFtCrRw==",
"dev": true,
"license": "BlueOak-1.0.0",
"engines": {
"node": "20 || >=22"
}
},
+ "node_modules/@asamuzakjp/generational-cache": {
+ "version": "1.0.1",
+ "resolved": "https://registry.npmjs.org/@asamuzakjp/generational-cache/-/generational-cache-1.0.1.tgz",
+ "integrity": "sha512-wajfB8KqzMCN2KGNFdLkReeHncd0AslUSrvHVvvYWuU8ghncRJoA50kT3zP9MVL0+9g4/67H+cdvBskj9THPzg==",
+ "dev": true,
+ "license": "MIT",
+ "engines": {
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
+ }
+ },
"node_modules/@asamuzakjp/nwsapi": {
"version": "2.3.9",
"resolved": "https://registry.npmjs.org/@asamuzakjp/nwsapi/-/nwsapi-2.3.9.tgz",
@@ -2037,6 +2049,498 @@
"@keyv/serialize": "^1.1.1"
}
},
+ "node_modules/@codemirror/autocomplete": {
+ "version": "6.20.1",
+ "resolved": "https://registry.npmjs.org/@codemirror/autocomplete/-/autocomplete-6.20.1.tgz",
+ "integrity": "sha512-1cvg3Vz1dSSToCNlJfRA2WSI4ht3K+WplO0UMOgmUYPivCyy2oueZY6Lx7M9wThm7SDUBViRmuT+OG/i8+ON9A==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.17.0",
+ "@lezer/common": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/commands": {
+ "version": "6.10.3",
+ "resolved": "https://registry.npmjs.org/@codemirror/commands/-/commands-6.10.3.tgz",
+ "integrity": "sha512-JFRiqhKu+bvSkDLI+rUhJwSxQxYb759W5GBezE8Uc8mHLqC9aV/9aTC7yJSqCtB3F00pylrLCwnyS91Ap5ej4Q==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.6.0",
+ "@codemirror/view": "^6.27.0",
+ "@lezer/common": "^1.1.0"
+ }
+ },
+ "node_modules/@codemirror/highlight": {
+ "version": "0.19.8",
+ "resolved": "https://registry.npmjs.org/@codemirror/highlight/-/highlight-0.19.8.tgz",
+ "integrity": "sha512-v/lzuHjrYR8MN2mEJcUD6fHSTXXli9C1XGYpr+ElV6fLBIUhMTNKR3qThp611xuWfXfwDxeL7ppcbkM/MzPV3A==",
+ "deprecated": "As of 0.20.0, this package has been split between @lezer/highlight and @codemirror/language",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^0.19.0",
+ "@codemirror/rangeset": "^0.19.0",
+ "@codemirror/state": "^0.19.3",
+ "@codemirror/view": "^0.19.39",
+ "@lezer/common": "^0.15.0",
+ "style-mod": "^4.0.0"
+ }
+ },
+ "node_modules/@codemirror/highlight/node_modules/@codemirror/language": {
+ "version": "0.19.10",
+ "resolved": "https://registry.npmjs.org/@codemirror/language/-/language-0.19.10.tgz",
+ "integrity": "sha512-yA0DZ3RYn2CqAAGW62VrU8c4YxscMQn45y/I9sjBlqB1e2OTQLg4CCkMBuMSLXk4xaqjlsgazeOQWaJQOKfV8Q==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/state": "^0.19.0",
+ "@codemirror/text": "^0.19.0",
+ "@codemirror/view": "^0.19.0",
+ "@lezer/common": "^0.15.5",
+ "@lezer/lr": "^0.15.0"
+ }
+ },
+ "node_modules/@codemirror/highlight/node_modules/@codemirror/state": {
+ "version": "0.19.9",
+ "resolved": "https://registry.npmjs.org/@codemirror/state/-/state-0.19.9.tgz",
+ "integrity": "sha512-psOzDolKTZkx4CgUqhBQ8T8gBc0xN5z4gzed109aF6x7D7umpDRoimacI/O6d9UGuyl4eYuDCZmDFr2Rq7aGOw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/text": "^0.19.0"
+ }
+ },
+ "node_modules/@codemirror/highlight/node_modules/@codemirror/view": {
+ "version": "0.19.48",
+ "resolved": "https://registry.npmjs.org/@codemirror/view/-/view-0.19.48.tgz",
+ "integrity": "sha512-0eg7D2Nz4S8/caetCTz61rK0tkHI17V/d15Jy0kLOT8dTLGGNJUponDnW28h2B6bERmPlVHKh8MJIr5OCp1nGw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/rangeset": "^0.19.5",
+ "@codemirror/state": "^0.19.3",
+ "@codemirror/text": "^0.19.0",
+ "style-mod": "^4.0.0",
+ "w3c-keyname": "^2.2.4"
+ }
+ },
+ "node_modules/@codemirror/highlight/node_modules/@lezer/common": {
+ "version": "0.15.12",
+ "resolved": "https://registry.npmjs.org/@lezer/common/-/common-0.15.12.tgz",
+ "integrity": "sha512-edfwCxNLnzq5pBA/yaIhwJ3U3Kz8VAUOTRg0hhxaizaI1N+qxV7EXDv/kLCkLeq2RzSFvxexlaj5Mzfn2kY0Ig==",
+ "license": "MIT"
+ },
+ "node_modules/@codemirror/highlight/node_modules/@lezer/lr": {
+ "version": "0.15.8",
+ "resolved": "https://registry.npmjs.org/@lezer/lr/-/lr-0.15.8.tgz",
+ "integrity": "sha512-bM6oE6VQZ6hIFxDNKk8bKPa14hqFrV07J/vHGOeiAbJReIaQXmkVb6xQu4MR+JBTLa5arGRyAAjJe1qaQt3Uvg==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^0.15.0"
+ }
+ },
+ "node_modules/@codemirror/lang-angular": {
+ "version": "0.1.4",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-angular/-/lang-angular-0.1.4.tgz",
+ "integrity": "sha512-oap+gsltb/fzdlTQWD6BFF4bSLKcDnlxDsLdePiJpCVNKWXSTAbiiQeYI3UmES+BLAdkmIC1WjyztC1pi/bX4g==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/lang-javascript": "^6.1.2",
+ "@codemirror/language": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.3.3"
+ }
+ },
+ "node_modules/@codemirror/lang-cpp": {
+ "version": "6.0.3",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-cpp/-/lang-cpp-6.0.3.tgz",
+ "integrity": "sha512-URM26M3vunFFn9/sm6rzqrBzDgfWuDixp85uTY49wKudToc2jTHUrKIGGKs+QWND+YLofNNZpxcNGRynFJfvgA==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@lezer/cpp": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-css": {
+ "version": "6.3.1",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-css/-/lang-css-6.3.1.tgz",
+ "integrity": "sha512-kr5fwBGiGtmz6l0LSJIbno9QrifNMUusivHbnA1H6Dmqy4HZFte3UAICix1VuKo0lMPKQr2rqB+0BkKi/S3Ejg==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.0.2",
+ "@lezer/css": "^1.1.7"
+ }
+ },
+ "node_modules/@codemirror/lang-go": {
+ "version": "6.0.1",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-go/-/lang-go-6.0.1.tgz",
+ "integrity": "sha512-7fNvbyNylvqCphW9HD6WFnRpcDjr+KXX/FgqXy5H5ZS0eC5edDljukm/yNgYkwTsgp2busdod50AOTIy6Jikfg==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/language": "^6.6.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.0.0",
+ "@lezer/go": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-html": {
+ "version": "6.4.11",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-html/-/lang-html-6.4.11.tgz",
+ "integrity": "sha512-9NsXp7Nwp891pQchI7gPdTwBuSuT3K65NGTHWHNJ55HjYcHLllr0rbIZNdOzas9ztc1EUVBlHou85FFZS4BNnw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/lang-css": "^6.0.0",
+ "@codemirror/lang-javascript": "^6.0.0",
+ "@codemirror/language": "^6.4.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.17.0",
+ "@lezer/common": "^1.0.0",
+ "@lezer/css": "^1.1.0",
+ "@lezer/html": "^1.3.12"
+ }
+ },
+ "node_modules/@codemirror/lang-java": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-java/-/lang-java-6.0.2.tgz",
+ "integrity": "sha512-m5Nt1mQ/cznJY7tMfQTJchmrjdjQ71IDs+55d1GAa8DGaB8JXWsVCkVT284C3RTASaY43YknrK2X3hPO/J3MOQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@lezer/java": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-javascript": {
+ "version": "6.2.5",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-javascript/-/lang-javascript-6.2.5.tgz",
+ "integrity": "sha512-zD4e5mS+50htS7F+TYjBPsiIFGanfVqg4HyUz6WNFikgOPf2BgKlx+TQedI1w6n/IqRBVBbBWmGFdLB/7uxO4A==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/language": "^6.6.0",
+ "@codemirror/lint": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.17.0",
+ "@lezer/common": "^1.0.0",
+ "@lezer/javascript": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-jinja": {
+ "version": "6.0.1",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-jinja/-/lang-jinja-6.0.1.tgz",
+ "integrity": "sha512-P5kyHLObzjtbGj16h+hyvZTxJhSjBEeSx4wMjbnAf3b0uwTy2+F0zGjMZL4PQOm/mh2eGZ5xUDVZXgwP783Nsw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.2.0",
+ "@lezer/lr": "^1.4.0"
+ }
+ },
+ "node_modules/@codemirror/lang-json": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-json/-/lang-json-6.0.2.tgz",
+ "integrity": "sha512-x2OtO+AvwEHrEwR0FyyPtfDUiloG3rnVTSZV1W8UteaLL8/MajQd8DpvUb2YVzC+/T18aSDv0H9mu+xw0EStoQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@lezer/json": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-less": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-less/-/lang-less-6.0.2.tgz",
+ "integrity": "sha512-EYdQTG22V+KUUk8Qq582g7FMnCZeEHsyuOJisHRft/mQ+ZSZ2w51NupvDUHiqtsOy7It5cHLPGfHQLpMh9bqpQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/lang-css": "^6.2.0",
+ "@codemirror/language": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-liquid": {
+ "version": "6.3.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-liquid/-/lang-liquid-6.3.2.tgz",
+ "integrity": "sha512-6PDVU3ZnfeYyz1at1E/ttorErZvZFXXt1OPhtfe1EZJ2V2iDFa0CwPqPgG5F7NXN0yONGoBogKmFAafKTqlwIw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.0.0",
+ "@lezer/common": "^1.0.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.3.1"
+ }
+ },
+ "node_modules/@codemirror/lang-markdown": {
+ "version": "6.5.0",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-markdown/-/lang-markdown-6.5.0.tgz",
+ "integrity": "sha512-0K40bZ35jpHya6FriukbgaleaqzBLZfOh7HuzqbMxBXkbYMJDxfF39c23xOgxFezR+3G+tR2/Mup+Xk865OMvw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.7.1",
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/language": "^6.3.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.0.0",
+ "@lezer/common": "^1.2.1",
+ "@lezer/markdown": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-php": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-php/-/lang-php-6.0.2.tgz",
+ "integrity": "sha512-ZKy2v1n8Fc8oEXj0Th0PUMXzQJ0AIR6TaZU+PbDHExFwdu+guzOA4jmCHS1Nz4vbFezwD7LyBdDnddSJeScMCA==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.0.0",
+ "@lezer/php": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-python": {
+ "version": "6.2.1",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-python/-/lang-python-6.2.1.tgz",
+ "integrity": "sha512-IRjC8RUBhn9mGR9ywecNhB51yePWCGgvHfY1lWN/Mrp3cKuHr0isDKia+9HnvhiWNnMpbGhWrkhuWOc09exRyw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.3.2",
+ "@codemirror/language": "^6.8.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.2.1",
+ "@lezer/python": "^1.1.4"
+ }
+ },
+ "node_modules/@codemirror/lang-rust": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-rust/-/lang-rust-6.0.2.tgz",
+ "integrity": "sha512-EZaGjCUegtiU7kSMvOfEZpaCReowEf3yNidYu7+vfuGTm9ow4mthAparY5hisJqOHmJowVH3Upu+eJlUji6qqA==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@lezer/rust": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-sass": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-sass/-/lang-sass-6.0.2.tgz",
+ "integrity": "sha512-l/bdzIABvnTo1nzdY6U+kPAC51czYQcOErfzQ9zSm9D8GmNPD0WTW8st/CJwBTPLO8jlrbyvlSEcN20dc4iL0Q==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/lang-css": "^6.2.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.0.2",
+ "@lezer/sass": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-sql": {
+ "version": "6.10.0",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-sql/-/lang-sql-6.10.0.tgz",
+ "integrity": "sha512-6ayPkEd/yRw0XKBx5uAiToSgGECo/GY2NoJIHXIIQh1EVwLuKoU8BP/qK0qH5NLXAbtJRLuT73hx7P9X34iO4w==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-vue": {
+ "version": "0.1.3",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-vue/-/lang-vue-0.1.3.tgz",
+ "integrity": "sha512-QSKdtYTDRhEHCfo5zOShzxCmqKJvgGrZwDQSdbvCRJ5pRLWBS7pD/8e/tH44aVQT6FKm0t6RVNoSUWHOI5vNug==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/lang-javascript": "^6.1.2",
+ "@codemirror/language": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.3.1"
+ }
+ },
+ "node_modules/@codemirror/lang-wast": {
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-wast/-/lang-wast-6.0.2.tgz",
+ "integrity": "sha512-Imi2KTpVGm7TKuUkqyJ5NRmeFWF7aMpNiwHnLQe0x9kmrxElndyH0K6H/gXtWwY6UshMRAhpENsgfpSwsgmC6Q==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-xml": {
+ "version": "6.1.0",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-xml/-/lang-xml-6.1.0.tgz",
+ "integrity": "sha512-3z0blhicHLfwi2UgkZYRPioSgVTo9PV5GP5ducFH6FaHy0IAJRg+ixj5gTR1gnT/glAIC8xv4w2VL1LoZfs+Jg==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/language": "^6.4.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.0.0",
+ "@lezer/common": "^1.0.0",
+ "@lezer/xml": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/lang-yaml": {
+ "version": "6.1.3",
+ "resolved": "https://registry.npmjs.org/@codemirror/lang-yaml/-/lang-yaml-6.1.3.tgz",
+ "integrity": "sha512-AZ8DJBuXGVHybpBQhmZtgew5//4hv3tdkXnr3vDmOUMJRuB6vn/uuwtmTOTlqEaQFg3hQSVeA90NmvIQyUV6FQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/autocomplete": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.2.0",
+ "@lezer/lr": "^1.0.0",
+ "@lezer/yaml": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/language": {
+ "version": "6.12.3",
+ "resolved": "https://registry.npmjs.org/@codemirror/language/-/language-6.12.3.tgz",
+ "integrity": "sha512-QwCZW6Tt1siP37Jet9Tb02Zs81TQt6qQrZR2H+eGMcFsL1zMrk2/b9CLC7/9ieP1fjIUMgviLWMmgiHoJrj+ZA==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.23.0",
+ "@lezer/common": "^1.5.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0",
+ "style-mod": "^4.0.0"
+ }
+ },
+ "node_modules/@codemirror/language-data": {
+ "version": "6.5.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/language-data/-/language-data-6.5.2.tgz",
+ "integrity": "sha512-CPkWBKrNS8stYbEU5kwBwTf3JB1kghlbh4FSAwzGW2TEscdeHHH4FGysREW86Mqnj3Qn09s0/6Ea/TutmoTobg==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/lang-angular": "^0.1.0",
+ "@codemirror/lang-cpp": "^6.0.0",
+ "@codemirror/lang-css": "^6.0.0",
+ "@codemirror/lang-go": "^6.0.0",
+ "@codemirror/lang-html": "^6.0.0",
+ "@codemirror/lang-java": "^6.0.0",
+ "@codemirror/lang-javascript": "^6.0.0",
+ "@codemirror/lang-jinja": "^6.0.0",
+ "@codemirror/lang-json": "^6.0.0",
+ "@codemirror/lang-less": "^6.0.0",
+ "@codemirror/lang-liquid": "^6.0.0",
+ "@codemirror/lang-markdown": "^6.0.0",
+ "@codemirror/lang-php": "^6.0.0",
+ "@codemirror/lang-python": "^6.0.0",
+ "@codemirror/lang-rust": "^6.0.0",
+ "@codemirror/lang-sass": "^6.0.0",
+ "@codemirror/lang-sql": "^6.0.0",
+ "@codemirror/lang-vue": "^0.1.1",
+ "@codemirror/lang-wast": "^6.0.0",
+ "@codemirror/lang-xml": "^6.0.0",
+ "@codemirror/lang-yaml": "^6.0.0",
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/legacy-modes": "^6.4.0"
+ }
+ },
+ "node_modules/@codemirror/legacy-modes": {
+ "version": "6.5.2",
+ "resolved": "https://registry.npmjs.org/@codemirror/legacy-modes/-/legacy-modes-6.5.2.tgz",
+ "integrity": "sha512-/jJbwSTazlQEDOQw2FJ8LEEKVS72pU0lx6oM54kGpL8t/NJ2Jda3CZ4pcltiKTdqYSRk3ug1B3pil1gsjA6+8Q==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0"
+ }
+ },
+ "node_modules/@codemirror/lint": {
+ "version": "6.9.5",
+ "resolved": "https://registry.npmjs.org/@codemirror/lint/-/lint-6.9.5.tgz",
+ "integrity": "sha512-GElsbU9G7QT9xXhpUg1zWGmftA/7jamh+7+ydKRuT0ORpWS3wOSP0yT1FOlIZa7mIJjpVPipErsyvVqB9cfTFA==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.35.0",
+ "crelt": "^1.0.5"
+ }
+ },
+ "node_modules/@codemirror/rangeset": {
+ "version": "0.19.9",
+ "resolved": "https://registry.npmjs.org/@codemirror/rangeset/-/rangeset-0.19.9.tgz",
+ "integrity": "sha512-V8YUuOvK+ew87Xem+71nKcqu1SXd5QROMRLMS/ljT5/3MCxtgrRie1Cvild0G/Z2f1fpWxzX78V0U4jjXBorBQ==",
+ "deprecated": "As of 0.20.0, this package has been merged into @codemirror/state",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/state": "^0.19.0"
+ }
+ },
+ "node_modules/@codemirror/rangeset/node_modules/@codemirror/state": {
+ "version": "0.19.9",
+ "resolved": "https://registry.npmjs.org/@codemirror/state/-/state-0.19.9.tgz",
+ "integrity": "sha512-psOzDolKTZkx4CgUqhBQ8T8gBc0xN5z4gzed109aF6x7D7umpDRoimacI/O6d9UGuyl4eYuDCZmDFr2Rq7aGOw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/text": "^0.19.0"
+ }
+ },
+ "node_modules/@codemirror/search": {
+ "version": "6.6.0",
+ "resolved": "https://registry.npmjs.org/@codemirror/search/-/search-6.6.0.tgz",
+ "integrity": "sha512-koFuNXcDvyyotWcgOnZGmY7LZqEOXZaaxD/j6n18TCLx2/9HieZJ5H6hs1g8FiRxBD0DNfs0nXn17g872RmYdw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.37.0",
+ "crelt": "^1.0.5"
+ }
+ },
+ "node_modules/@codemirror/state": {
+ "version": "6.6.0",
+ "resolved": "https://registry.npmjs.org/@codemirror/state/-/state-6.6.0.tgz",
+ "integrity": "sha512-4nbvra5R5EtiCzr9BTHiTLc+MLXK2QGiAVYMyi8PkQd3SR+6ixar/Q/01Fa21TBIDOZXgeWV4WppsQolSreAPQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@marijn/find-cluster-break": "^1.0.0"
+ }
+ },
+ "node_modules/@codemirror/text": {
+ "version": "0.19.6",
+ "resolved": "https://registry.npmjs.org/@codemirror/text/-/text-0.19.6.tgz",
+ "integrity": "sha512-T9jnREMIygx+TPC1bOuepz18maGq/92q2a+n4qTqObKwvNMg+8cMTslb8yxeEDEq7S3kpgGWxgO1UWbQRij0dA==",
+ "deprecated": "As of 0.20.0, this package has been merged into @codemirror/state",
+ "license": "MIT"
+ },
+ "node_modules/@codemirror/view": {
+ "version": "6.41.1",
+ "resolved": "https://registry.npmjs.org/@codemirror/view/-/view-6.41.1.tgz",
+ "integrity": "sha512-ToDnWKbBnke+ZLrP6vgTTDScGi5H37YYuZGniQaBzxMVdtCxMrslsmtnOvbPZk4RX9bvkQqnWR/WS/35tJA0qg==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/state": "^6.6.0",
+ "crelt": "^1.0.6",
+ "style-mod": "^4.1.0",
+ "w3c-keyname": "^2.2.4"
+ }
+ },
"node_modules/@csstools/color-helpers": {
"version": "6.0.2",
"resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-6.0.2.tgz",
@@ -2058,9 +2562,9 @@
}
},
"node_modules/@csstools/css-calc": {
- "version": "3.1.1",
- "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-3.1.1.tgz",
- "integrity": "sha512-HJ26Z/vmsZQqs/o3a6bgKslXGFAungXGbinULZO3eMsOyNJHeBBZfup5FiZInOghgoM4Hwnmw+OgbJCNg1wwUQ==",
+ "version": "3.2.0",
+ "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-3.2.0.tgz",
+ "integrity": "sha512-bR9e6o2BDB12jzN/gIbjHa5wLJ4UjD1CB9pM7ehlc0ddk6EBz+yYS1EV2MF55/HUxrHcB/hehAyt5vhsA3hx7w==",
"dev": true,
"funding": [
{
@@ -2082,9 +2586,9 @@
}
},
"node_modules/@csstools/css-color-parser": {
- "version": "4.0.2",
- "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-4.0.2.tgz",
- "integrity": "sha512-0GEfbBLmTFf0dJlpsNU7zwxRIH0/BGEMuXLTCvFYxuL1tNhqzTbtnFICyJLTNK4a+RechKP75e7w42ClXSnJQw==",
+ "version": "4.1.0",
+ "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-4.1.0.tgz",
+ "integrity": "sha512-U0KhLYmy2GVj6q4T3WaAe6NPuFYCPQoE3b0dRGxejWDgcPp8TP7S5rVdM5ZrFaqu4N67X8YaPBw14dQSYx3IyQ==",
"dev": true,
"funding": [
{
@@ -2099,7 +2603,7 @@
"license": "MIT",
"dependencies": {
"@csstools/color-helpers": "^6.0.2",
- "@csstools/css-calc": "^3.1.1"
+ "@csstools/css-calc": "^3.2.0"
},
"engines": {
"node": ">=20.19.0"
@@ -2134,9 +2638,9 @@
}
},
"node_modules/@csstools/css-syntax-patches-for-csstree": {
- "version": "1.1.2",
- "resolved": "https://registry.npmjs.org/@csstools/css-syntax-patches-for-csstree/-/css-syntax-patches-for-csstree-1.1.2.tgz",
- "integrity": "sha512-5GkLzz4prTIpoyeUiIu3iV6CSG3Plo7xRVOFPKI7FVEJ3mZ0A8SwK0XU3Gl7xAkiQ+mDyam+NNp875/C5y+jSA==",
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/@csstools/css-syntax-patches-for-csstree/-/css-syntax-patches-for-csstree-1.1.3.tgz",
+ "integrity": "sha512-SH60bMfrRCJF3morcdk57WklujF4Jr/EsQUzqkarfHXEFcAR1gg7fS/chAE922Sehgzc1/+Tz5H3Ypa1HiEKrg==",
"dev": true,
"funding": [
{
@@ -2256,9 +2760,9 @@
"license": "Apache-2.0"
},
"node_modules/@emnapi/core": {
- "version": "1.9.2",
- "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.9.2.tgz",
- "integrity": "sha512-UC+ZhH3XtczQYfOlu3lNEkdW/p4dsJ1r/bP7H8+rhao3TTTMO1ATq/4DdIi23XuGoFY+Cz0JmCbdVl0hz9jZcA==",
+ "version": "1.10.0",
+ "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.10.0.tgz",
+ "integrity": "sha512-yq6OkJ4p82CAfPl0u9mQebQHKPJkY7WrIuk205cTYnYe+k2Z8YBh11FrbRG/H6ihirqcacOgl2BIO8oyMQLeXw==",
"dev": true,
"license": "MIT",
"optional": true,
@@ -2268,9 +2772,9 @@
}
},
"node_modules/@emnapi/runtime": {
- "version": "1.9.2",
- "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.9.2.tgz",
- "integrity": "sha512-3U4+MIWHImeyu1wnmVygh5WlgfYDtyf0k8AbLhMFxOipihf6nrWC4syIm/SwEeec0mNSafiiNnMJwbza/Is6Lw==",
+ "version": "1.10.0",
+ "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.10.0.tgz",
+ "integrity": "sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==",
"dev": true,
"license": "MIT",
"optional": true,
@@ -2966,9 +3470,9 @@
}
},
"node_modules/@istanbuljs/schema": {
- "version": "0.1.3",
- "resolved": "https://registry.npmjs.org/@istanbuljs/schema/-/schema-0.1.3.tgz",
- "integrity": "sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==",
+ "version": "0.1.6",
+ "resolved": "https://registry.npmjs.org/@istanbuljs/schema/-/schema-0.1.6.tgz",
+ "integrity": "sha512-+Sg6GCR/wy1oSmQDFq4LQDAhm3ETKnorxN+y5nbLULOR3P0c14f2Wurzj3/xqPXtasLFfHd5iRFQ7AJt4KH2cw==",
"dev": true,
"license": "MIT",
"engines": {
@@ -3367,10 +3871,193 @@
"dev": true,
"license": "MIT"
},
+ "node_modules/@lezer/common": {
+ "version": "1.5.2",
+ "resolved": "https://registry.npmjs.org/@lezer/common/-/common-1.5.2.tgz",
+ "integrity": "sha512-sxQE460fPZyU3sdc8lafxiPwJHBzZRy/udNFynGQky1SePYBdhkBl1kOagA9uT3pxR8K09bOrmTUqA9wb/PjSQ==",
+ "license": "MIT"
+ },
+ "node_modules/@lezer/cpp": {
+ "version": "1.1.5",
+ "resolved": "https://registry.npmjs.org/@lezer/cpp/-/cpp-1.1.5.tgz",
+ "integrity": "sha512-DIhSXmYtJKLehrjzDFN+2cPt547ySQ41nA8yqcDf/GxMc+YM736xqltFkvADL2M0VebU5I+3+4ks2Vv+Kyq3Aw==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/css": {
+ "version": "1.3.3",
+ "resolved": "https://registry.npmjs.org/@lezer/css/-/css-1.3.3.tgz",
+ "integrity": "sha512-RzBo8r+/6QJeow7aPHIpGVIH59xTcJXp399820gZoMo9noQDRVpJLheIBUicYwKcsbOYoBRoLZlf2720dG/4Tg==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.3.0"
+ }
+ },
+ "node_modules/@lezer/go": {
+ "version": "1.0.1",
+ "resolved": "https://registry.npmjs.org/@lezer/go/-/go-1.0.1.tgz",
+ "integrity": "sha512-xToRsYxwsgJNHTgNdStpcvmbVuKxTapV0dM0wey1geMMRc9aggoVyKgzYp41D2/vVOx+Ii4hmE206kvxIXBVXQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.3.0"
+ }
+ },
+ "node_modules/@lezer/highlight": {
+ "version": "1.2.3",
+ "resolved": "https://registry.npmjs.org/@lezer/highlight/-/highlight-1.2.3.tgz",
+ "integrity": "sha512-qXdH7UqTvGfdVBINrgKhDsVTJTxactNNxLk7+UMwZhU13lMHaOBlJe9Vqp907ya56Y3+ed2tlqzys7jDkTmW0g==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.3.0"
+ }
+ },
+ "node_modules/@lezer/html": {
+ "version": "1.3.13",
+ "resolved": "https://registry.npmjs.org/@lezer/html/-/html-1.3.13.tgz",
+ "integrity": "sha512-oI7n6NJml729m7pjm9lvLvmXbdoMoi2f+1pwSDJkl9d68zGr7a9Btz8NdHTGQZtW2DA25ybeuv/SyDb9D5tseg==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/java": {
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/@lezer/java/-/java-1.1.3.tgz",
+ "integrity": "sha512-yHquUfujwg6Yu4Fd1GNHCvidIvJwi/1Xu2DaKl/pfWIA2c1oXkVvawH3NyXhCaFx4OdlYBVX5wvz2f7Aoa/4Xw==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/javascript": {
+ "version": "1.5.4",
+ "resolved": "https://registry.npmjs.org/@lezer/javascript/-/javascript-1.5.4.tgz",
+ "integrity": "sha512-vvYx3MhWqeZtGPwDStM2dwgljd5smolYD2lR2UyFcHfxbBQebqx8yjmFmxtJ/E6nN6u1D9srOiVWm3Rb4tmcUA==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.1.3",
+ "@lezer/lr": "^1.3.0"
+ }
+ },
+ "node_modules/@lezer/json": {
+ "version": "1.0.3",
+ "resolved": "https://registry.npmjs.org/@lezer/json/-/json-1.0.3.tgz",
+ "integrity": "sha512-BP9KzdF9Y35PDpv04r0VeSTKDeox5vVr3efE7eBbx3r4s3oNLfunchejZhjArmeieBH+nVOpgIiBJpEAv8ilqQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/lr": {
+ "version": "1.4.10",
+ "resolved": "https://registry.npmjs.org/@lezer/lr/-/lr-1.4.10.tgz",
+ "integrity": "sha512-rnCpTIBafOx4mRp43xOxDJbFipJm/c0cia/V5TiGlhmMa+wsSdoGmUN3w5Bqrks/09Q/D4tNAmWaT8p6NRi77A==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/markdown": {
+ "version": "1.6.3",
+ "resolved": "https://registry.npmjs.org/@lezer/markdown/-/markdown-1.6.3.tgz",
+ "integrity": "sha512-jpGm5Ps+XErS+xA4urw7ogEGkeZOahVQF21Z6oECF0sj+2liwZopd2+I8uH5I/vZsRuuze3OxBREIANLf6KKUw==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.5.0",
+ "@lezer/highlight": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/php": {
+ "version": "1.0.5",
+ "resolved": "https://registry.npmjs.org/@lezer/php/-/php-1.0.5.tgz",
+ "integrity": "sha512-W7asp9DhM6q0W6DYNwIkLSKOvxlXRrif+UXBMxzsJUuqmhE7oVU+gS3THO4S/Puh7Xzgm858UNaFi6dxTP8dJA==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.1.0"
+ }
+ },
+ "node_modules/@lezer/python": {
+ "version": "1.1.18",
+ "resolved": "https://registry.npmjs.org/@lezer/python/-/python-1.1.18.tgz",
+ "integrity": "sha512-31FiUrU7z9+d/ElGQLJFXl+dKOdx0jALlP3KEOsGTex8mvj+SoE1FgItcHWK/axkxCHGUSpqIHt6JAWfWu9Rhg==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/rust": {
+ "version": "1.0.2",
+ "resolved": "https://registry.npmjs.org/@lezer/rust/-/rust-1.0.2.tgz",
+ "integrity": "sha512-Lz5sIPBdF2FUXcWeCu1//ojFAZqzTQNRga0aYv6dYXqJqPfMdCAI0NzajWUd4Xijj1IKJLtjoXRPMvTKWBcqKg==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/sass": {
+ "version": "1.1.0",
+ "resolved": "https://registry.npmjs.org/@lezer/sass/-/sass-1.1.0.tgz",
+ "integrity": "sha512-3mMGdCTUZ/84ArHOuXWQr37pnf7f+Nw9ycPUeKX+wu19b7pSMcZGLbaXwvD2APMBDOGxPmpK/O6S1v1EvLoqgQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/xml": {
+ "version": "1.0.6",
+ "resolved": "https://registry.npmjs.org/@lezer/xml/-/xml-1.0.6.tgz",
+ "integrity": "sha512-CdDwirL0OEaStFue/66ZmFSeppuL6Dwjlk8qk153mSQwiSH/Dlri4GNymrNWnUmPl2Um7QfV1FO9KFUyX3Twww==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.0.0"
+ }
+ },
+ "node_modules/@lezer/yaml": {
+ "version": "1.0.4",
+ "resolved": "https://registry.npmjs.org/@lezer/yaml/-/yaml-1.0.4.tgz",
+ "integrity": "sha512-2lrrHqxalACEbxIbsjhqGpSW8kWpUKuY6RHgnSAFZa6qK62wvnPxA8hGOwOoDbwHcOFs5M4o27mjGu+P7TvBmw==",
+ "license": "MIT",
+ "dependencies": {
+ "@lezer/common": "^1.2.0",
+ "@lezer/highlight": "^1.0.0",
+ "@lezer/lr": "^1.4.0"
+ }
+ },
+ "node_modules/@marijn/find-cluster-break": {
+ "version": "1.0.2",
+ "resolved": "https://registry.npmjs.org/@marijn/find-cluster-break/-/find-cluster-break-1.0.2.tgz",
+ "integrity": "sha512-l0h88YhZFyKdXIFNfSWpyjStDjGHwZ/U7iobcK1cQQD8sejsONdQtTVU+1wVN1PBw40PiiHB1vA5S7VTfQiP9g==",
+ "license": "MIT"
+ },
"node_modules/@mongodb-js/saslprep": {
- "version": "1.4.6",
- "resolved": "https://registry.npmjs.org/@mongodb-js/saslprep/-/saslprep-1.4.6.tgz",
- "integrity": "sha512-y+x3H1xBZd38n10NZF/rEBlvDOOMQ6LKUTHqr8R9VkJ+mmQOYtJFxIlkkK8fZrtOiL6VixbOBWMbZGBdal3Z1g==",
+ "version": "1.4.8",
+ "resolved": "https://registry.npmjs.org/@mongodb-js/saslprep/-/saslprep-1.4.8.tgz",
+ "integrity": "sha512-kpjr2jy2w71w0oqAMI8oibBmiF9lXxWkEQs5gMkW4hVE48bsqINGLxnCSYW62ck/NHXJQpQEfA9WlJ1sY0eqBg==",
"license": "MIT",
"dependencies": {
"sparse-bitfield": "^3.0.3"
@@ -3480,9 +4167,9 @@
"license": "MIT"
},
"node_modules/@rollup/rollup-android-arm-eabi": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.60.1.tgz",
- "integrity": "sha512-d6FinEBLdIiK+1uACUttJKfgZREXrF0Qc2SmLII7W2AD8FfiZ9Wjd+rD/iRuf5s5dWrr1GgwXCvPqOuDquOowA==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.60.2.tgz",
+ "integrity": "sha512-dnlp69efPPg6Uaw2dVqzWRfAWRnYVb1XJ8CyyhIbZeaq4CA5/mLeZ1IEt9QqQxmbdvagjLIm2ZL8BxXv5lH4Yw==",
"cpu": [
"arm"
],
@@ -3493,9 +4180,9 @@
]
},
"node_modules/@rollup/rollup-android-arm64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.60.1.tgz",
- "integrity": "sha512-YjG/EwIDvvYI1YvYbHvDz/BYHtkY4ygUIXHnTdLhG+hKIQFBiosfWiACWortsKPKU/+dUwQQCKQM3qrDe8c9BA==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.60.2.tgz",
+ "integrity": "sha512-OqZTwDRDchGRHHm/hwLOL7uVPB9aUvI0am/eQuWMNyFHf5PSEQmyEeYYheA0EPPKUO/l0uigCp+iaTjoLjVoHg==",
"cpu": [
"arm64"
],
@@ -3506,9 +4193,9 @@
]
},
"node_modules/@rollup/rollup-darwin-arm64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.60.1.tgz",
- "integrity": "sha512-mjCpF7GmkRtSJwon+Rq1N8+pI+8l7w5g9Z3vWj4T7abguC4Czwi3Yu/pFaLvA3TTeMVjnu3ctigusqWUfjZzvw==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.60.2.tgz",
+ "integrity": "sha512-UwRE7CGpvSVEQS8gUMBe1uADWjNnVgP3Iusyda1nSRwNDCsRjnGc7w6El6WLQsXmZTbLZx9cecegumcitNfpmA==",
"cpu": [
"arm64"
],
@@ -3519,9 +4206,9 @@
]
},
"node_modules/@rollup/rollup-darwin-x64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.60.1.tgz",
- "integrity": "sha512-haZ7hJ1JT4e9hqkoT9R/19XW2QKqjfJVv+i5AGg57S+nLk9lQnJ1F/eZloRO3o9Scy9CM3wQ9l+dkXtcBgN5Ew==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.60.2.tgz",
+ "integrity": "sha512-gjEtURKLCC5VXm1I+2i1u9OhxFsKAQJKTVB8WvDAHF+oZlq0GTVFOlTlO1q3AlCTE/DF32c16ESvfgqR7343/g==",
"cpu": [
"x64"
],
@@ -3532,9 +4219,9 @@
]
},
"node_modules/@rollup/rollup-freebsd-arm64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.60.1.tgz",
- "integrity": "sha512-czw90wpQq3ZsAVBlinZjAYTKduOjTywlG7fEeWKUA7oCmpA8xdTkxZZlwNJKWqILlq0wehoZcJYfBvOyhPTQ6w==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.60.2.tgz",
+ "integrity": "sha512-Bcl6CYDeAgE70cqZaMojOi/eK63h5Me97ZqAQoh77VPjMysA/4ORQBRGo3rRy45x4MzVlU9uZxs8Uwy7ZaKnBw==",
"cpu": [
"arm64"
],
@@ -3545,9 +4232,9 @@
]
},
"node_modules/@rollup/rollup-freebsd-x64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.60.1.tgz",
- "integrity": "sha512-KVB2rqsxTHuBtfOeySEyzEOB7ltlB/ux38iu2rBQzkjbwRVlkhAGIEDiiYnO2kFOkJp+Z7pUXKyrRRFuFUKt+g==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.60.2.tgz",
+ "integrity": "sha512-LU+TPda3mAE2QB0/Hp5VyeKJivpC6+tlOXd1VMoXV/YFMvk/MNk5iXeBfB4MQGRWyOYVJ01625vjkr0Az98OJQ==",
"cpu": [
"x64"
],
@@ -3558,9 +4245,9 @@
]
},
"node_modules/@rollup/rollup-linux-arm-gnueabihf": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.60.1.tgz",
- "integrity": "sha512-L+34Qqil+v5uC0zEubW7uByo78WOCIrBvci69E7sFASRl0X7b/MB6Cqd1lky/CtcSVTydWa2WZwFuWexjS5o6g==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.60.2.tgz",
+ "integrity": "sha512-2QxQrM+KQ7DAW4o22j+XZ6RKdxjLD7BOWTP0Bv0tmjdyhXSsr2Ul1oJDQqh9Zf5qOwTuTc7Ek83mOFaKnodPjg==",
"cpu": [
"arm"
],
@@ -3571,9 +4258,9 @@
]
},
"node_modules/@rollup/rollup-linux-arm-musleabihf": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.60.1.tgz",
- "integrity": "sha512-n83O8rt4v34hgFzlkb1ycniJh7IR5RCIqt6mz1VRJD6pmhRi0CXdmfnLu9dIUS6buzh60IvACM842Ffb3xd6Gg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.60.2.tgz",
+ "integrity": "sha512-TbziEu2DVsTEOPif2mKWkMeDMLoYjx95oESa9fkQQK7r/Orta0gnkcDpzwufEcAO2BLBsD7mZkXGFqEdMRRwfw==",
"cpu": [
"arm"
],
@@ -3584,9 +4271,9 @@
]
},
"node_modules/@rollup/rollup-linux-arm64-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.60.1.tgz",
- "integrity": "sha512-Nql7sTeAzhTAja3QXeAI48+/+GjBJ+QmAH13snn0AJSNL50JsDqotyudHyMbO2RbJkskbMbFJfIJKWA6R1LCJQ==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.60.2.tgz",
+ "integrity": "sha512-bO/rVDiDUuM2YfuCUwZ1t1cP+/yqjqz+Xf2VtkdppefuOFS2OSeAfgafaHNkFn0t02hEyXngZkxtGqXcXwO8Rg==",
"cpu": [
"arm64"
],
@@ -3597,9 +4284,9 @@
]
},
"node_modules/@rollup/rollup-linux-arm64-musl": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.60.1.tgz",
- "integrity": "sha512-+pUymDhd0ys9GcKZPPWlFiZ67sTWV5UU6zOJat02M1+PiuSGDziyRuI/pPue3hoUwm2uGfxdL+trT6Z9rxnlMA==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.60.2.tgz",
+ "integrity": "sha512-hr26p7e93Rl0Za+JwW7EAnwAvKkehh12BU1Llm9Ykiibg4uIr2rbpxG9WCf56GuvidlTG9KiiQT/TXT1yAWxTA==",
"cpu": [
"arm64"
],
@@ -3610,9 +4297,9 @@
]
},
"node_modules/@rollup/rollup-linux-loong64-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.60.1.tgz",
- "integrity": "sha512-VSvgvQeIcsEvY4bKDHEDWcpW4Yw7BtlKG1GUT4FzBUlEKQK0rWHYBqQt6Fm2taXS+1bXvJT6kICu5ZwqKCnvlQ==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.60.2.tgz",
+ "integrity": "sha512-pOjB/uSIyDt+ow3k/RcLvUAOGpysT2phDn7TTUB3n75SlIgZzM6NKAqlErPhoFU+npgY3/n+2HYIQVbF70P9/A==",
"cpu": [
"loong64"
],
@@ -3623,9 +4310,9 @@
]
},
"node_modules/@rollup/rollup-linux-loong64-musl": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.60.1.tgz",
- "integrity": "sha512-4LqhUomJqwe641gsPp6xLfhqWMbQV04KtPp7/dIp0nzPxAkNY1AbwL5W0MQpcalLYk07vaW9Kp1PBhdpZYYcEw==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.60.2.tgz",
+ "integrity": "sha512-2/w+q8jszv9Ww1c+6uJT3OwqhdmGP2/4T17cu8WuwyUuuaCDDJ2ojdyYwZzCxx0GcsZBhzi3HmH+J5pZNXnd+Q==",
"cpu": [
"loong64"
],
@@ -3636,9 +4323,9 @@
]
},
"node_modules/@rollup/rollup-linux-ppc64-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.60.1.tgz",
- "integrity": "sha512-tLQQ9aPvkBxOc/EUT6j3pyeMD6Hb8QF2BTBnCQWP/uu1lhc9AIrIjKnLYMEroIz/JvtGYgI9dF3AxHZNaEH0rw==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.60.2.tgz",
+ "integrity": "sha512-11+aL5vKheYgczxtPVVRhdptAM2H7fcDR5Gw4/bTcteuZBlH4oP9f5s9zYO9aGZvoGeBpqXI/9TZZihZ609wKw==",
"cpu": [
"ppc64"
],
@@ -3649,9 +4336,9 @@
]
},
"node_modules/@rollup/rollup-linux-ppc64-musl": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.60.1.tgz",
- "integrity": "sha512-RMxFhJwc9fSXP6PqmAz4cbv3kAyvD1etJFjTx4ONqFP9DkTkXsAMU4v3Vyc5BgzC+anz7nS/9tp4obsKfqkDHg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.60.2.tgz",
+ "integrity": "sha512-i16fokAGK46IVZuV8LIIwMdtqhin9hfYkCh8pf8iC3QU3LpwL+1FSFGej+O7l3E/AoknL6Dclh2oTdnRMpTzFQ==",
"cpu": [
"ppc64"
],
@@ -3662,9 +4349,9 @@
]
},
"node_modules/@rollup/rollup-linux-riscv64-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.60.1.tgz",
- "integrity": "sha512-QKgFl+Yc1eEk6MmOBfRHYF6lTxiiiV3/z/BRrbSiW2I7AFTXoBFvdMEyglohPj//2mZS4hDOqeB0H1ACh3sBbg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.60.2.tgz",
+ "integrity": "sha512-49FkKS6RGQoriDSK/6E2GkAsAuU5kETFCh7pG4yD/ylj9rKhTmO3elsnmBvRD4PgJPds5W2PkhC82aVwmUcJ7A==",
"cpu": [
"riscv64"
],
@@ -3675,9 +4362,9 @@
]
},
"node_modules/@rollup/rollup-linux-riscv64-musl": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.60.1.tgz",
- "integrity": "sha512-RAjXjP/8c6ZtzatZcA1RaQr6O1TRhzC+adn8YZDnChliZHviqIjmvFwHcxi4JKPSDAt6Uhf/7vqcBzQJy0PDJg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.60.2.tgz",
+ "integrity": "sha512-mjYNkHPfGpUR00DuM1ZZIgs64Hpf4bWcz9Z41+4Q+pgDx73UwWdAYyf6EG/lRFldmdHHzgrYyge5akFUW0D3mQ==",
"cpu": [
"riscv64"
],
@@ -3688,9 +4375,9 @@
]
},
"node_modules/@rollup/rollup-linux-s390x-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.60.1.tgz",
- "integrity": "sha512-wcuocpaOlaL1COBYiA89O6yfjlp3RwKDeTIA0hM7OpmhR1Bjo9j31G1uQVpDlTvwxGn2nQs65fBFL5UFd76FcQ==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.60.2.tgz",
+ "integrity": "sha512-ALyvJz965BQk8E9Al/JDKKDLH2kfKFLTGMlgkAbbYtZuJt9LU8DW3ZoDMCtQpXAltZxwBHevXz5u+gf0yA0YoA==",
"cpu": [
"s390x"
],
@@ -3701,9 +4388,9 @@
]
},
"node_modules/@rollup/rollup-linux-x64-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.60.1.tgz",
- "integrity": "sha512-77PpsFQUCOiZR9+LQEFg9GClyfkNXj1MP6wRnzYs0EeWbPcHs02AXu4xuUbM1zhwn3wqaizle3AEYg5aeoohhg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.60.2.tgz",
+ "integrity": "sha512-UQjrkIdWrKI626Du8lCQ6MJp/6V1LAo2bOK9OTu4mSn8GGXIkPXk/Vsp4bLHCd9Z9Iz2OTEaokUE90VweJgIYQ==",
"cpu": [
"x64"
],
@@ -3714,9 +4401,9 @@
]
},
"node_modules/@rollup/rollup-linux-x64-musl": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.60.1.tgz",
- "integrity": "sha512-5cIATbk5vynAjqqmyBjlciMJl1+R/CwX9oLk/EyiFXDWd95KpHdrOJT//rnUl4cUcskrd0jCCw3wpZnhIHdD9w==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.60.2.tgz",
+ "integrity": "sha512-bTsRGj6VlSdn/XD4CGyzMnzaBs9bsRxy79eTqTCBsA8TMIEky7qg48aPkvJvFe1HyzQ5oMZdg7AnVlWQSKLTnw==",
"cpu": [
"x64"
],
@@ -3727,9 +4414,9 @@
]
},
"node_modules/@rollup/rollup-openbsd-x64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.60.1.tgz",
- "integrity": "sha512-cl0w09WsCi17mcmWqqglez9Gk8isgeWvoUZ3WiJFYSR3zjBQc2J5/ihSjpl+VLjPqjQ/1hJRcqBfLjssREQILw==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.60.2.tgz",
+ "integrity": "sha512-6d4Z3534xitaA1FcMWP7mQPq5zGwBmGbhphh2DwaA1aNIXUu3KTOfwrWpbwI4/Gr0uANo7NTtaykFyO2hPuFLg==",
"cpu": [
"x64"
],
@@ -3740,9 +4427,9 @@
]
},
"node_modules/@rollup/rollup-openharmony-arm64": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.60.1.tgz",
- "integrity": "sha512-4Cv23ZrONRbNtbZa37mLSueXUCtN7MXccChtKpUnQNgF010rjrjfHx3QxkS2PI7LqGT5xXyYs1a7LbzAwT0iCA==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.60.2.tgz",
+ "integrity": "sha512-NetAg5iO2uN7eB8zE5qrZ3CSil+7IJt4WDFLcC75Ymywq1VZVD6qJ6EvNLjZ3rEm6gB7XW5JdT60c6MN35Z85Q==",
"cpu": [
"arm64"
],
@@ -3753,9 +4440,9 @@
]
},
"node_modules/@rollup/rollup-win32-arm64-msvc": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.60.1.tgz",
- "integrity": "sha512-i1okWYkA4FJICtr7KpYzFpRTHgy5jdDbZiWfvny21iIKky5YExiDXP+zbXzm3dUcFpkEeYNHgQ5fuG236JPq0g==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.60.2.tgz",
+ "integrity": "sha512-NCYhOotpgWZ5kdxCZsv6Iudx0wX8980Q/oW4pNFNihpBKsDbEA1zpkfxJGC0yugsUuyDZ7gL37dbzwhR0VI7pQ==",
"cpu": [
"arm64"
],
@@ -3766,9 +4453,9 @@
]
},
"node_modules/@rollup/rollup-win32-ia32-msvc": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.60.1.tgz",
- "integrity": "sha512-u09m3CuwLzShA0EYKMNiFgcjjzwqtUMLmuCJLeZWjjOYA3IT2Di09KaxGBTP9xVztWyIWjVdsB2E9goMjZvTQg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.60.2.tgz",
+ "integrity": "sha512-RXsaOqXxfoUBQoOgvmmijVxJnW2IGB0eoMO7F8FAjaj0UTywUO/luSqimWBJn04WNgUkeNhh7fs7pESXajWmkg==",
"cpu": [
"ia32"
],
@@ -3779,9 +4466,9 @@
]
},
"node_modules/@rollup/rollup-win32-x64-gnu": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.60.1.tgz",
- "integrity": "sha512-k+600V9Zl1CM7eZxJgMyTUzmrmhB/0XZnF4pRypKAlAgxmedUA+1v9R+XOFv56W4SlHEzfeMtzujLJD22Uz5zg==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.60.2.tgz",
+ "integrity": "sha512-qdAzEULD+/hzObedtmV6iBpdL5TIbKVztGiK7O3/KYSf+HIzU257+MX1EXJcyIiDbMAqmbwaufcYPvyRryeZtA==",
"cpu": [
"x64"
],
@@ -3792,9 +4479,9 @@
]
},
"node_modules/@rollup/rollup-win32-x64-msvc": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.60.1.tgz",
- "integrity": "sha512-lWMnixq/QzxyhTV6NjQJ4SFo1J6PvOX8vUx5Wb4bBPsEb+8xZ89Bz6kOXpfXj9ak9AHTQVQzlgzBEc1SyM27xQ==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.60.2.tgz",
+ "integrity": "sha512-Nd/SgG27WoA9e+/TdK74KnHz852TLa94ovOYySo/yMPuTmpckK/jIF2jSwS3g7ELSKXK13/cVdmg1Z/DaCWKxA==",
"cpu": [
"x64"
],
@@ -3844,9 +4531,9 @@
}
},
"node_modules/@sinonjs/fake-timers": {
- "version": "15.3.0",
- "resolved": "https://registry.npmjs.org/@sinonjs/fake-timers/-/fake-timers-15.3.0.tgz",
- "integrity": "sha512-m2xozxSfCIxjDdvbhIWazlP2i2aha/iUmbl94alpsIbd3iLTfeXgfBVbwyWogB6l++istyGZqamgA/EcqYf+Bg==",
+ "version": "15.3.2",
+ "resolved": "https://registry.npmjs.org/@sinonjs/fake-timers/-/fake-timers-15.3.2.tgz",
+ "integrity": "sha512-mrn35Jl2pCpns+mE3HaZa1yPN5EYCRgiMI+135COjr2hr8Cls9DXqIZ57vZe2cz7y2XVSq92tcs6kGQcT1J8Rw==",
"dev": true,
"license": "BSD-3-Clause",
"dependencies": {
@@ -3961,13 +4648,13 @@
}
},
"node_modules/@types/node": {
- "version": "25.5.2",
- "resolved": "https://registry.npmjs.org/@types/node/-/node-25.5.2.tgz",
- "integrity": "sha512-tO4ZIRKNC+MDWV4qKVZe3Ql/woTnmHDr5JD8UI5hn2pwBrHEwOEMZK7WlNb5RKB6EoJ02gwmQS9OrjuFnZYdpg==",
+ "version": "25.6.0",
+ "resolved": "https://registry.npmjs.org/@types/node/-/node-25.6.0.tgz",
+ "integrity": "sha512-+qIYRKdNYJwY3vRCZMdJbPLJAtGjQBudzZzdzwQYkEPQd+PJGixUL5QfvCLDaULoLv+RhT3LDkwEfKaAkgSmNQ==",
"devOptional": true,
"license": "MIT",
"dependencies": {
- "undici-types": "~7.18.0"
+ "undici-types": "~7.19.0"
}
},
"node_modules/@types/stack-utils": {
@@ -4010,14 +4697,14 @@
"license": "MIT"
},
"node_modules/@typescript-eslint/project-service": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.58.0.tgz",
- "integrity": "sha512-8Q/wBPWLQP1j16NxoPNIKpDZFMaxl7yWIoqXWYeWO+Bbd2mjgvoF0dxP2jKZg5+x49rgKdf7Ck473M8PC3V9lg==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.58.2.tgz",
+ "integrity": "sha512-Cq6UfpZZk15+r87BkIh5rDpi38W4b+Sjnb8wQCPPDDweS/LRCFjCyViEbzHk5Ck3f2QDfgmlxqSa7S7clDtlfg==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@typescript-eslint/tsconfig-utils": "^8.58.0",
- "@typescript-eslint/types": "^8.58.0",
+ "@typescript-eslint/tsconfig-utils": "^8.58.2",
+ "@typescript-eslint/types": "^8.58.2",
"debug": "^4.4.3"
},
"engines": {
@@ -4032,14 +4719,14 @@
}
},
"node_modules/@typescript-eslint/scope-manager": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.58.0.tgz",
- "integrity": "sha512-W1Lur1oF50FxSnNdGp3Vs6P+yBRSmZiw4IIjEeYxd8UQJwhUF0gDgDD/W/Tgmh73mxgEU3qX0Bzdl/NGuSPEpQ==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.58.2.tgz",
+ "integrity": "sha512-SgmyvDPexWETQek+qzZnrG6844IaO02UVyOLhI4wpo82dpZJY9+6YZCKAMFzXb7qhx37mFK1QcPQ18tud+vo6Q==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@typescript-eslint/types": "8.58.0",
- "@typescript-eslint/visitor-keys": "8.58.0"
+ "@typescript-eslint/types": "8.58.2",
+ "@typescript-eslint/visitor-keys": "8.58.2"
},
"engines": {
"node": "^18.18.0 || ^20.9.0 || >=21.1.0"
@@ -4050,9 +4737,9 @@
}
},
"node_modules/@typescript-eslint/tsconfig-utils": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.58.0.tgz",
- "integrity": "sha512-doNSZEVJsWEu4htiVC+PR6NpM+pa+a4ClH9INRWOWCUzMst/VA9c4gXq92F8GUD1rwhNvRLkgjfYtFXegXQF7A==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.58.2.tgz",
+ "integrity": "sha512-3SR+RukipDvkkKp/d0jP0dyzuls3DbGmwDpVEc5wqk5f38KFThakqAAO0XMirWAE+kT00oTauTbzMFGPoAzB0A==",
"dev": true,
"license": "MIT",
"engines": {
@@ -4067,9 +4754,9 @@
}
},
"node_modules/@typescript-eslint/types": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.58.0.tgz",
- "integrity": "sha512-O9CjxypDT89fbHxRfETNoAnHj/i6IpRK0CvbVN3qibxlLdo5p5hcLmUuCCrHMpxiWSwKyI8mCP7qRNYuOJ0Uww==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.58.2.tgz",
+ "integrity": "sha512-9TukXyATBQf/Jq9AMQXfvurk+G5R2MwfqQGDR2GzGz28HvY/lXNKGhkY+6IOubwcquikWk5cjlgPvD2uAA7htQ==",
"dev": true,
"license": "MIT",
"engines": {
@@ -4081,16 +4768,16 @@
}
},
"node_modules/@typescript-eslint/typescript-estree": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.58.0.tgz",
- "integrity": "sha512-7vv5UWbHqew/dvs+D3e1RvLv1v2eeZ9txRHPnEEBUgSNLx5ghdzjHa0sgLWYVKssH+lYmV0JaWdoubo0ncGYLA==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.58.2.tgz",
+ "integrity": "sha512-ELGuoofuhhoCvNbQjFFiobFcGgcDCEm0ThWdmO4Z0UzLqPXS3KFvnEZ+SHewwOYHjM09tkzOWXNTv9u6Gqtyuw==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@typescript-eslint/project-service": "8.58.0",
- "@typescript-eslint/tsconfig-utils": "8.58.0",
- "@typescript-eslint/types": "8.58.0",
- "@typescript-eslint/visitor-keys": "8.58.0",
+ "@typescript-eslint/project-service": "8.58.2",
+ "@typescript-eslint/tsconfig-utils": "8.58.2",
+ "@typescript-eslint/types": "8.58.2",
+ "@typescript-eslint/visitor-keys": "8.58.2",
"debug": "^4.4.3",
"minimatch": "^10.2.2",
"semver": "^7.7.3",
@@ -4161,16 +4848,16 @@
}
},
"node_modules/@typescript-eslint/utils": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.58.0.tgz",
- "integrity": "sha512-RfeSqcFeHMHlAWzt4TBjWOAtoW9lnsAGiP3GbaX9uVgTYYrMbVnGONEfUCiSss+xMHFl+eHZiipmA8WkQ7FuNA==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.58.2.tgz",
+ "integrity": "sha512-QZfjHNEzPY8+l0+fIXMvuQ2sJlplB4zgDZvA+NmvZsZv3EQwOcc1DuIU1VJUTWZ/RKouBMhDyNaBMx4sWvrzRA==",
"dev": true,
"license": "MIT",
"dependencies": {
"@eslint-community/eslint-utils": "^4.9.1",
- "@typescript-eslint/scope-manager": "8.58.0",
- "@typescript-eslint/types": "8.58.0",
- "@typescript-eslint/typescript-estree": "8.58.0"
+ "@typescript-eslint/scope-manager": "8.58.2",
+ "@typescript-eslint/types": "8.58.2",
+ "@typescript-eslint/typescript-estree": "8.58.2"
},
"engines": {
"node": "^18.18.0 || ^20.9.0 || >=21.1.0"
@@ -4185,13 +4872,13 @@
}
},
"node_modules/@typescript-eslint/visitor-keys": {
- "version": "8.58.0",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.58.0.tgz",
- "integrity": "sha512-XJ9UD9+bbDo4a4epraTwG3TsNPeiB9aShrUneAVXy8q4LuwowN+qu89/6ByLMINqvIMeI9H9hOHQtg/ijrYXzQ==",
+ "version": "8.58.2",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.58.2.tgz",
+ "integrity": "sha512-f1WO2Lx8a9t8DARmcWAUPJbu0G20bJlj8L4z72K00TMeJAoyLr/tHhI/pzYBLrR4dXWkcxO1cWYZEOX8DKHTqA==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@typescript-eslint/types": "8.58.0",
+ "@typescript-eslint/types": "8.58.2",
"eslint-visitor-keys": "^5.0.0"
},
"engines": {
@@ -4215,6 +4902,489 @@
"url": "https://opencollective.com/eslint"
}
},
+ "node_modules/@uiw/codemirror-theme-abcdef": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-abcdef/-/codemirror-theme-abcdef-4.25.9.tgz",
+ "integrity": "sha512-F6bZcm20N3r4ZeCMdyjjII/fYHqE17sbRk6pFWfU+NPxe522A/uaRKpEaBK/iDwYqpKZgI3XUz7j3KcYzA99Mg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-abyss": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-abyss/-/codemirror-theme-abyss-4.25.9.tgz",
+ "integrity": "sha512-zcMHX3abHsaV+IRhnHeWA5aYTP/9HTk/MR5Zh3pfwASv8YMsQlcjBva8vEZULV9pJDferW/9GXbKbbPdmceJeg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-androidstudio": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-androidstudio/-/codemirror-theme-androidstudio-4.25.9.tgz",
+ "integrity": "sha512-HPIWpEC9ElhpJ2NZUKB6z+eStQzFDrkIGW9pTJxYHSCv2Los7FgD/R6eGqjTS4LVlBf9FR+KU/5E6dLT8DQHlw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-andromeda": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-andromeda/-/codemirror-theme-andromeda-4.25.9.tgz",
+ "integrity": "sha512-JSqK8/sVFbFfTyv/okaT4c8suulf9zasqd4YBuTSkPZo+Sd/50blxMSVe5IWwDSiW5hkiupb7FC2IP1siHhncw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-atomone": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-atomone/-/codemirror-theme-atomone-4.25.9.tgz",
+ "integrity": "sha512-EXG/+p+Y9j/StU2yAtz/+JZj/8WaSGqwjsad79CSBgpHrSU0ERzv4urYWXgEmLTKKkFimwTigy7qOJlLAwkN2A==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-aura": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-aura/-/codemirror-theme-aura-4.25.9.tgz",
+ "integrity": "sha512-cJyInS81wh0lWYs1XDiyFSxCCXrJ+4qifBsDHSYELdLgbnr441T3Kr6a9lyUobtL4DZVaIaCKE9rajrFdJIeAw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-basic": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-basic/-/codemirror-theme-basic-4.25.9.tgz",
+ "integrity": "sha512-40x+anangMmPziZSeEcg6P5YDLn7fF1ioS5VxEPXMGUTbikv0au4PXVNsf7CtP0VwO4MmGt87zZI6rQIexEP3w==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-bbedit": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-bbedit/-/codemirror-theme-bbedit-4.25.9.tgz",
+ "integrity": "sha512-SGXQ0tLsqcRvxXCrdeU/MiQ3liNKvr8DCxaSt4N5LP7EPGO94ebuvba0F+H/3LpeJJrn5Xq0FuhaPlMYJ10RXg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-bespin": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-bespin/-/codemirror-theme-bespin-4.25.9.tgz",
+ "integrity": "sha512-Zr35B1FpM+VMIoHot397GP/dQBWkFz6SlFqf3JSX6wlwgy2d4ot3YF9fBglGkM3C3ITmkBBQRnlvELwke+dXBg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-console": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-console/-/codemirror-theme-console-4.25.9.tgz",
+ "integrity": "sha512-vhN9QKStneKyiNzu+DuA5JOss9WfzecuDjvmEYApQL9zvRmNUAP6La0C2vpZCji1Y23OAFZUJvTU+eKbept3cw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-copilot": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-copilot/-/codemirror-theme-copilot-4.25.9.tgz",
+ "integrity": "sha512-MLBXBEp+jDQC+BbFUQxxwsOKvhbCsIpIjwBgNfR4KKKQxD6tF6u+CE7ERcrRWJ6cCV2lDrs1IZRZGPQCSpHMIA==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-darcula": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-darcula/-/codemirror-theme-darcula-4.25.9.tgz",
+ "integrity": "sha512-lrex1DXg/mx2BX1UtnyFlat7w6c3RyE5GMvyR8uPfXNAXMUEKjYxNRdUuQ9WGlOMzQZ3x+UbKnUZd/r6AmXwsw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-dracula": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-dracula/-/codemirror-theme-dracula-4.25.9.tgz",
+ "integrity": "sha512-0VTnpPCHPc+7LqYsQOX6nvW32XiiT+O6kJjReUbV7Eio3vPHsb+b9P4DKhz4AAvIIYMxmHkMuautHKuWktFXSg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-duotone": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-duotone/-/codemirror-theme-duotone-4.25.9.tgz",
+ "integrity": "sha512-6IPZncdrtcgnU1EtQ1/IzaULZ+Jw5uAeVeQCae+rFBnW/m6Q8nWB8+iVnk8kCevgjT5ScZmRd9h4yqtSeJbUwQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-eclipse": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-eclipse/-/codemirror-theme-eclipse-4.25.9.tgz",
+ "integrity": "sha512-0pT0vRyLAotj5UjIZbHSmsZ8oz7l8IU5bhx5p7MDrTOdi73ZjyTsG4YsDzSXndERnfgkBbZJrlZiExBkXnhtUA==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-github": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-github/-/codemirror-theme-github-4.25.9.tgz",
+ "integrity": "sha512-AGpTamNiySKNzq3Jc7QjpwgQRVaHUaBtmOKiUDghYSfEGjsc5uW4NUW70sSU3BnkGv+lCTUnF3175KM24BWZbw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-gruvbox-dark": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-gruvbox-dark/-/codemirror-theme-gruvbox-dark-4.25.9.tgz",
+ "integrity": "sha512-9qIa1z4zwubN2kHAs+lJvdrmMMMf69JeyVPAwSoNaImL8wUQ/J3291qcfuoZjv8RsqSzrKTgxqLHtkAhB7xcwg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-kimbie": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-kimbie/-/codemirror-theme-kimbie-4.25.9.tgz",
+ "integrity": "sha512-zLjT7MkotuT07rx4ZPZOM1/H+sa+kCmJr5BDu2ASNpF7Sj4w0cTNcAyxKHj+N6LcgIM8PICxqB97CJhlurNTBA==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-material": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-material/-/codemirror-theme-material-4.25.9.tgz",
+ "integrity": "sha512-6f2x+gmj2hHagqy6VkpnPbK7SWyP6kKruGgqpyIy09/f9pAUCqkW8mRY5ZEr28tA+YEGQaSY0Z2IBCHl8OKJog==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-monokai": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-monokai/-/codemirror-theme-monokai-4.25.9.tgz",
+ "integrity": "sha512-qKWRZOGpBCasZJdYU+SsXd92TjncF3QYHpraCPe29bxN22jeIxi2UC4MCuJHwa8hHljHOCSdx1XG/GuUMn7XiQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-monokai-dimmed": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-monokai-dimmed/-/codemirror-theme-monokai-dimmed-4.25.9.tgz",
+ "integrity": "sha512-6/Z9tF4UFngaXifAKC4DI2l61G3rtcWOxvCwgs5zzNVMTciUI+Bl/K7eCvjf2y0LfLmK8Ovob8ODDBcVgwzp5g==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-noctis-lilac": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-noctis-lilac/-/codemirror-theme-noctis-lilac-4.25.9.tgz",
+ "integrity": "sha512-HXjQutWsVYfiBM6ze4SomXmSJNzYYJ/fUYJ3TJLhnp5cjIPNBsMsgOAaWp3L64xUqqorb0+1y6kdmUKxTEp6rQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-nord": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-nord/-/codemirror-theme-nord-4.25.9.tgz",
+ "integrity": "sha512-5c568xmMidwICADxACB1zIhKoEgqbdVrdeOUZ2p5pE6NNKGR4ATzk9OSqhvr1ZhZPNOktxqSLLRzihFaZG0bDQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-okaidia": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-okaidia/-/codemirror-theme-okaidia-4.25.9.tgz",
+ "integrity": "sha512-lIJFUs/ws0prQz+dVo5ZIp0o6vxW7p6nf8iRFETN5S3KA3nJUR2cTF6u8mYLFwHMrFs2eReRsFyH94wjmuPWvg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-quietlight": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-quietlight/-/codemirror-theme-quietlight-4.25.9.tgz",
+ "integrity": "sha512-BWFcFb3WHTCVROkjExh/TMMTJ5SNcDafaVEIwneKypiHoTJoIY6RlSRBj6GA3O5IgKdrGmhje87s0Gx2OLIndg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-red": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-red/-/codemirror-theme-red-4.25.9.tgz",
+ "integrity": "sha512-pSOs2ByCVGJXbABhfTEU4TlRh/Wa9BJlDUa219iq1jO3AUDUM/LIPNLhmQvMtOituMX8WKJprspBrDcveXsisg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-solarized": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-solarized/-/codemirror-theme-solarized-4.25.9.tgz",
+ "integrity": "sha512-axUgU9+3JKXW83F+te454qcyTmQAm0+2Fxv0yoegiH6bdl7DjFq/lNVGGZtLwN47AQCj2Qwrheeet2t3GbY9VQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-sublime": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-sublime/-/codemirror-theme-sublime-4.25.9.tgz",
+ "integrity": "sha512-/Ha1K3P0sqFWrsYtCu6Uih/t8C73dVY6m5rObjCnnokr//kOusKwlwt1fJiEFdIcSKlH2WBIvW5tb75tcYitnw==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-tokyo-night": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-tokyo-night/-/codemirror-theme-tokyo-night-4.25.9.tgz",
+ "integrity": "sha512-NkSqguMpzRjsRBbTIfOrGS35tQkE3K8AAetZHlbRZC7fnI52RreZ11X41cOYrc/Dapt8xqUPlhlvclymGFgy8g==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-tokyo-night-day": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-tokyo-night-day/-/codemirror-theme-tokyo-night-day-4.25.9.tgz",
+ "integrity": "sha512-1ziFletBO6tfRtX4FVWij1wYIf95uYi54dgnMz5CXe4A4u710rJ3uS3C4ijlnclRbwHjNTqtrMWNuicKDBMsPg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-tokyo-night-storm": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-tokyo-night-storm/-/codemirror-theme-tokyo-night-storm-4.25.9.tgz",
+ "integrity": "sha512-qz8Vg+ze12TuLk+fqwx3oga3H6rDE+81PpKMGLfbI1BwPDgg7GZGTGrWZoN1Bpf6EV0dA4WO8K6lbzFhlS6S1Q==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-tomorrow-night-blue": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-tomorrow-night-blue/-/codemirror-theme-tomorrow-night-blue-4.25.9.tgz",
+ "integrity": "sha512-iG2wCXO/rkJIrvW7rJY7Ehh4yushw8X4vQnstjArxofR6uNrE9ay3Ut7M0cxrwY7z8YIU5f7NQFODE/h3HNmVA==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-vscode": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-vscode/-/codemirror-theme-vscode-4.25.9.tgz",
+ "integrity": "sha512-9KTnScHTSk97yGnyNYvDm6QZuBCdbO1OzMQ5bHtoBSPSVtH0LjY3bS6CXsBagb22v8OLPx/XwrBYOjKFp409CQ==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-white": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-white/-/codemirror-theme-white-4.25.9.tgz",
+ "integrity": "sha512-75PHfVejBvgF1EbponpEOgND/T6MJYZ673aODPuR7mKPZNfn8649qOSrp7wvMN/NEZ+W5CxV3U7tb9MQWPcM4A==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-theme-xcode": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-theme-xcode/-/codemirror-theme-xcode-4.25.9.tgz",
+ "integrity": "sha512-sMiDpOiW0iiNsLyqL1Vx6wZKOSoVUNfmWbBDtaYzlkRcKzkyJQp68cPIq5VG8Mhl2z+PX5cPbOA0nZEegNLicA==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
+ "node_modules/@uiw/codemirror-themes": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-themes/-/codemirror-themes-4.25.9.tgz",
+ "integrity": "sha512-DAHKb/L9ELwjY4nCf/MP/mIllHOn4GQe7RR4x8AMJuNeh9nGRRoo1uPxrxMmUL/bKqe6kDmDbIZ2AlhlqyIJuw==",
+ "license": "MIT",
+ "dependencies": {
+ "@codemirror/language": "^6.0.0",
+ "@codemirror/state": "^6.0.0",
+ "@codemirror/view": "^6.0.0"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ },
+ "peerDependencies": {
+ "@codemirror/language": ">=6.0.0",
+ "@codemirror/state": ">=6.0.0",
+ "@codemirror/view": ">=6.0.0"
+ }
+ },
+ "node_modules/@uiw/codemirror-themes-all": {
+ "version": "4.25.9",
+ "resolved": "https://registry.npmjs.org/@uiw/codemirror-themes-all/-/codemirror-themes-all-4.25.9.tgz",
+ "integrity": "sha512-OVcGb6dkgJ8NgcHFvSQkRLHHIRswZhBKK0XZZzRVMxDnCIXfmnDfeChNoKjuzwBr+C0jS7UAAqrWbcqrLj3mhg==",
+ "license": "MIT",
+ "dependencies": {
+ "@uiw/codemirror-theme-abcdef": "4.25.9",
+ "@uiw/codemirror-theme-abyss": "4.25.9",
+ "@uiw/codemirror-theme-androidstudio": "4.25.9",
+ "@uiw/codemirror-theme-andromeda": "4.25.9",
+ "@uiw/codemirror-theme-atomone": "4.25.9",
+ "@uiw/codemirror-theme-aura": "4.25.9",
+ "@uiw/codemirror-theme-basic": "4.25.9",
+ "@uiw/codemirror-theme-bbedit": "4.25.9",
+ "@uiw/codemirror-theme-bespin": "4.25.9",
+ "@uiw/codemirror-theme-console": "4.25.9",
+ "@uiw/codemirror-theme-copilot": "4.25.9",
+ "@uiw/codemirror-theme-darcula": "4.25.9",
+ "@uiw/codemirror-theme-dracula": "4.25.9",
+ "@uiw/codemirror-theme-duotone": "4.25.9",
+ "@uiw/codemirror-theme-eclipse": "4.25.9",
+ "@uiw/codemirror-theme-github": "4.25.9",
+ "@uiw/codemirror-theme-gruvbox-dark": "4.25.9",
+ "@uiw/codemirror-theme-kimbie": "4.25.9",
+ "@uiw/codemirror-theme-material": "4.25.9",
+ "@uiw/codemirror-theme-monokai": "4.25.9",
+ "@uiw/codemirror-theme-monokai-dimmed": "4.25.9",
+ "@uiw/codemirror-theme-noctis-lilac": "4.25.9",
+ "@uiw/codemirror-theme-nord": "4.25.9",
+ "@uiw/codemirror-theme-okaidia": "4.25.9",
+ "@uiw/codemirror-theme-quietlight": "4.25.9",
+ "@uiw/codemirror-theme-red": "4.25.9",
+ "@uiw/codemirror-theme-solarized": "4.25.9",
+ "@uiw/codemirror-theme-sublime": "4.25.9",
+ "@uiw/codemirror-theme-tokyo-night": "4.25.9",
+ "@uiw/codemirror-theme-tokyo-night-day": "4.25.9",
+ "@uiw/codemirror-theme-tokyo-night-storm": "4.25.9",
+ "@uiw/codemirror-theme-tomorrow-night-blue": "4.25.9",
+ "@uiw/codemirror-theme-vscode": "4.25.9",
+ "@uiw/codemirror-theme-white": "4.25.9",
+ "@uiw/codemirror-theme-xcode": "4.25.9",
+ "@uiw/codemirror-themes": "4.25.9"
+ },
+ "funding": {
+ "url": "https://jaywcjlove.github.io/#/sponsor"
+ }
+ },
"node_modules/@ungap/structured-clone": {
"version": "1.3.0",
"resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.3.0.tgz",
@@ -5019,9 +6189,9 @@
"license": "MIT"
},
"node_modules/baseline-browser-mapping": {
- "version": "2.10.14",
- "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.14.tgz",
- "integrity": "sha512-fOVLPAsFTsQfuCkvahZkzq6nf8KvGWanlYoTh0SVA0A/PIUxQGU2AOZAoD95n2gFLVDW/jP6sbGLny95nmEuHA==",
+ "version": "2.10.20",
+ "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.20.tgz",
+ "integrity": "sha512-1AaXxEPfXT+GvTBJFuy4yXVHWJBXa4OdbIebGN/wX5DlsIkU0+wzGnd2lOzokSk51d5LUmqjgBLRLlypLUqInQ==",
"license": "Apache-2.0",
"bin": {
"baseline-browser-mapping": "dist/cli.cjs"
@@ -5074,9 +6244,9 @@
}
},
"node_modules/brace-expansion": {
- "version": "1.1.13",
- "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.13.tgz",
- "integrity": "sha512-9ZLprWS6EENmhEOpjCYW2c8VkmOvckIJZfkr7rBW6dObmfgJ/L1GpSYW5Hpo9lDz4D1+n0Ckz8rU7FwHDQiG/w==",
+ "version": "1.1.14",
+ "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.14.tgz",
+ "integrity": "sha512-MWPGfDxnyzKU7rNOW9SP/c50vi3xrmrua/+6hfPbCS2ABNWfx24vPidzvC7krjU/RTo235sV776ymlsMtGKj8g==",
"dev": true,
"license": "MIT",
"dependencies": {
@@ -5197,15 +6367,15 @@
}
},
"node_modules/call-bind": {
- "version": "1.0.8",
- "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.8.tgz",
- "integrity": "sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==",
+ "version": "1.0.9",
+ "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.9.tgz",
+ "integrity": "sha512-a/hy+pNsFUTR+Iz8TCJvXudKVLAnz/DyeSUo10I5yvFDQJBFU2s9uqQpoSrJlroHUKoKqzg+epxyP9lqFdzfBQ==",
"dev": true,
"license": "MIT",
"dependencies": {
- "call-bind-apply-helpers": "^1.0.0",
- "es-define-property": "^1.0.0",
- "get-intrinsic": "^1.2.4",
+ "call-bind-apply-helpers": "^1.0.2",
+ "es-define-property": "^1.0.1",
+ "get-intrinsic": "^1.3.0",
"set-function-length": "^1.2.2"
},
"engines": {
@@ -5265,9 +6435,9 @@
}
},
"node_modules/caniuse-lite": {
- "version": "1.0.30001785",
- "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001785.tgz",
- "integrity": "sha512-blhOL/WNR+Km1RI/LCVAvA73xplXA7ZbjzI4YkMK9pa6T/P3F2GxjNpEkyw5repTw9IvkyrjyHpwjnhZ5FOvYQ==",
+ "version": "1.0.30001788",
+ "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001788.tgz",
+ "integrity": "sha512-6q8HFp+lOQtcf7wBK+uEenxymVWkGKkjFpCvw5W25cmMwEDU45p1xQFBQv8JDlMMry7eNxyBaR+qxgmTUZkIRQ==",
"funding": [
{
"type": "opencollective",
@@ -5406,12 +6576,6 @@
"node": ">= 0.12.0"
}
},
- "node_modules/codemirror": {
- "version": "5.65.21",
- "resolved": "https://registry.npmjs.org/codemirror/-/codemirror-5.65.21.tgz",
- "integrity": "sha512-6teYk0bA0nR3QP0ihGMoxuKzpl5W80FpnHpBJpgy66NK3cZv5b/d/HY8PnRvfSsCG1MTfr92u2WUl+wT0E40mQ==",
- "license": "MIT"
- },
"node_modules/collect-v8-coverage": {
"version": "1.0.3",
"resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.3.tgz",
@@ -5473,9 +6637,9 @@
"license": "MIT"
},
"node_modules/content-disposition": {
- "version": "1.0.1",
- "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.0.1.tgz",
- "integrity": "sha512-oIXISMynqSqm241k6kcQ5UwttDILMK4BiurCfGEREw6+X9jkkpEe5T9FZaApyLGGOnFuyMWZpdolTXMtvEJ08Q==",
+ "version": "1.1.0",
+ "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.1.0.tgz",
+ "integrity": "sha512-5jRCH9Z/+DRP7rkvY83B+yGIGX96OYdJmzngqnw2SBSxqCFPd0w2km3s5iawpGX8krnwSGmF0FW5Nhr0Hfai3g==",
"license": "MIT",
"engines": {
"node": ">=18"
@@ -5627,6 +6791,12 @@
"object-assign": "^4.1.1"
}
},
+ "node_modules/crelt": {
+ "version": "1.0.6",
+ "resolved": "https://registry.npmjs.org/crelt/-/crelt-1.0.6.tgz",
+ "integrity": "sha512-VQ2MBenTq1fWZUH9DJNGti7kKv6EeAuYr3cLwxUWhIu1baTaXh4Ib5W2CqHVqib4/MqbYGJqiL3Zb8GJZr3l4g==",
+ "license": "MIT"
+ },
"node_modules/cross-spawn": {
"version": "7.0.6",
"resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz",
@@ -5696,9 +6866,9 @@
}
},
"node_modules/cssstyle/node_modules/lru-cache": {
- "version": "11.2.7",
- "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.7.tgz",
- "integrity": "sha512-aY/R+aEsRelme17KGQa/1ZSIpLpNYYrhcrepKTZgE+W3WM16YMCaPwOHLHsmopZHELU0Ojin1lPVxKR0MihncA==",
+ "version": "11.3.5",
+ "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.3.5.tgz",
+ "integrity": "sha512-NxVFwLAnrd9i7KUBxC4DrUhmgjzOs+1Qm50D3oF1/oL+r1NpZ4gA7xvG0/zJ8evR7zIKn4vLf7qTNduWFtCrRw==",
"dev": true,
"license": "BlueOak-1.0.0",
"engines": {
@@ -5961,9 +7131,9 @@
"license": "MIT"
},
"node_modules/electron-to-chromium": {
- "version": "1.5.331",
- "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.331.tgz",
- "integrity": "sha512-IbxXrsTlD3hRodkLnbxAPP4OuJYdWCeM3IOdT+CpcMoIwIoDfCmRpEtSPfwBXxVkg9xmBeY7Lz2Eo2TDn/HC3Q==",
+ "version": "1.5.340",
+ "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.340.tgz",
+ "integrity": "sha512-908qahOGocRMinT2nM3ajCEM99H4iPdv84eagPP3FfZy/1ZGeOy2CZYzjhms81ckOPCXPlW7LkY4XpxD8r1DrA==",
"license": "ISC"
},
"node_modules/emittery": {
@@ -6042,9 +7212,9 @@
}
},
"node_modules/es-abstract": {
- "version": "1.24.1",
- "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.1.tgz",
- "integrity": "sha512-zHXBLhP+QehSSbsS9Pt23Gg964240DPd6QCf8WpkqEXxQ7fhdZzYsocOr5u7apWonsS5EjZDmTF+/slGMyasvw==",
+ "version": "1.24.2",
+ "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.2.tgz",
+ "integrity": "sha512-2FpH9Q5i2RRwyEP1AylXe6nYLR5OhaJTZwmlcP0dL/+JCbgg7yyEo/sEK6HeGZRf3dFpWwThaRHVApXSkW3xeg==",
"dev": true,
"license": "MIT",
"dependencies": {
@@ -6129,16 +7299,16 @@
}
},
"node_modules/es-iterator-helpers": {
- "version": "1.3.1",
- "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.3.1.tgz",
- "integrity": "sha512-zWwRvqWiuBPr0muUG/78cW3aHROFCNIQ3zpmYDpwdbnt2m+xlNyRWpHBpa2lJjSBit7BQ+RXA1iwbSmu5yJ/EQ==",
+ "version": "1.3.2",
+ "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.3.2.tgz",
+ "integrity": "sha512-HVLACW1TppGYjJ8H6/jqH/pqOtKRw6wMlrB23xfExmFWxFquAIWCmwoLsOyN96K4a5KbmOf5At9ZUO3GZbetAw==",
"dev": true,
"license": "MIT",
"dependencies": {
- "call-bind": "^1.0.8",
+ "call-bind": "^1.0.9",
"call-bound": "^1.0.4",
"define-properties": "^1.2.1",
- "es-abstract": "^1.24.1",
+ "es-abstract": "^1.24.2",
"es-errors": "^1.3.0",
"es-set-tostringtag": "^2.1.0",
"function-bind": "^1.1.2",
@@ -6150,8 +7320,7 @@
"has-symbols": "^1.1.0",
"internal-slot": "^1.1.0",
"iterator.prototype": "^1.1.5",
- "math-intrinsics": "^1.1.0",
- "safe-array-concat": "^1.1.3"
+ "math-intrinsics": "^1.1.0"
},
"engines": {
"node": ">= 0.4"
@@ -6338,9 +7507,9 @@
}
},
"node_modules/eslint-plugin-jest": {
- "version": "29.15.1",
- "resolved": "https://registry.npmjs.org/eslint-plugin-jest/-/eslint-plugin-jest-29.15.1.tgz",
- "integrity": "sha512-6BjyErCQauz3zfJvzLw/kAez2lf4LEpbHLvWBfEcG4EI0ZiRSwjoH2uZulMouU8kRkBH+S0rhqn11IhTvxKgKw==",
+ "version": "29.15.2",
+ "resolved": "https://registry.npmjs.org/eslint-plugin-jest/-/eslint-plugin-jest-29.15.2.tgz",
+ "integrity": "sha512-kEN4r9RZl1xcsb4arGq89LrcVdOUFII/JSCwtTPJyv16mDwmPrcuEQwpxqZHeINvcsd7oK5O/rhdGlxFRaZwvQ==",
"dev": true,
"license": "MIT",
"dependencies": {
@@ -7342,9 +8511,9 @@
}
},
"node_modules/glob/node_modules/brace-expansion": {
- "version": "2.0.3",
- "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.3.tgz",
- "integrity": "sha512-MCV/fYJEbqx68aE58kv2cA/kiky1G8vux3OR6/jbS+jIMe/6fJWa0DTzJU7dqijOWYwHi1t29FlfYI9uytqlpA==",
+ "version": "2.1.0",
+ "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.1.0.tgz",
+ "integrity": "sha512-TN1kCZAgdgweJhWWpgKYrQaMNHcDULHkWwQIspdtjV4Y5aurRdZpjAqn6yX3FPqTA9ngHCc4hJxMAMgGfve85w==",
"dev": true,
"license": "MIT",
"dependencies": {
@@ -7668,9 +8837,9 @@
}
},
"node_modules/hasown": {
- "version": "2.0.2",
- "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz",
- "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==",
+ "version": "2.0.3",
+ "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.3.tgz",
+ "integrity": "sha512-ej4AhfhfL2Q2zpMmLo7U1Uv9+PyhIZpgQLGT1F9miIGmiCJIoCgSmczFdrc97mWT4kVY72KA+WnnhJ5pghSvSg==",
"license": "MIT",
"dependencies": {
"function-bind": "^1.1.2"
@@ -9576,12 +10745,12 @@
}
},
"node_modules/marked-emoji": {
- "version": "2.0.2",
- "resolved": "https://registry.npmjs.org/marked-emoji/-/marked-emoji-2.0.2.tgz",
- "integrity": "sha512-EFnLQn4wTyf+6pXfptkm83Z2mt3VbdEYedHBAsDpwUas5n5satsj42RGqAijBpmetgGerI1EzUuzf7NIccINUQ==",
+ "version": "2.0.3",
+ "resolved": "https://registry.npmjs.org/marked-emoji/-/marked-emoji-2.0.3.tgz",
+ "integrity": "sha512-fChW/AfUqCHgoEC1nFDgiw3OR/qsi71/QXH/HTo05yd6B5+T+VHh1SqCpn/HpeGLDxkA+MK4+hr4eULB2/A8Jw==",
"license": "MIT",
"peerDependencies": {
- "marked": ">=4 <18"
+ "marked": ">=4 <19"
}
},
"node_modules/marked-extended-tables": {
@@ -9594,15 +10763,15 @@
}
},
"node_modules/marked-gfm-heading-id": {
- "version": "4.1.3",
- "resolved": "https://registry.npmjs.org/marked-gfm-heading-id/-/marked-gfm-heading-id-4.1.3.tgz",
- "integrity": "sha512-aR0i63LmFbuxU/gAgrgz1Ir+8HK6zAIFXMlckeKHpV+qKbYaOP95L4Ux5Gi+sKmCZU5qnN2rdKpvpb7PnUBIWg==",
+ "version": "4.1.4",
+ "resolved": "https://registry.npmjs.org/marked-gfm-heading-id/-/marked-gfm-heading-id-4.1.4.tgz",
+ "integrity": "sha512-CspnvVfHSkb/znqdPS4jUR8HtCjq3M/DnrsJCrfLBLvdrgbemmoINKpeWKQYkBiXAoBGejw0cV7xzqrPdup3WA==",
"license": "MIT",
"dependencies": {
"github-slugger": "^2.0.0"
},
"peerDependencies": {
- "marked": ">=13 <18"
+ "marked": ">=13 <19"
}
},
"node_modules/marked-nonbreaking-spaces": {
@@ -10734,9 +11903,9 @@
}
},
"node_modules/postcss": {
- "version": "8.5.8",
- "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.8.tgz",
- "integrity": "sha512-OW/rX8O/jXnm82Ey1k44pObPtdblfiuWnrd8X7GJ7emImCOstunGbXUpp7HdBrFQX6rJzn3sPT397Wp5aCwCHg==",
+ "version": "8.5.10",
+ "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.10.tgz",
+ "integrity": "sha512-pMMHxBOZKFU6HgAZ4eyGnwXF/EvPGGqUr0MnZ5+99485wwW41kW91A4LOGxSHhgugZmSChL5AlElNdwlNgcnLQ==",
"funding": [
{
"type": "opencollective",
@@ -10975,9 +12144,9 @@
"license": "MIT"
},
"node_modules/qs": {
- "version": "6.15.0",
- "resolved": "https://registry.npmjs.org/qs/-/qs-6.15.0.tgz",
- "integrity": "sha512-mAZTtNCeetKMH+pSjrb76NAM8V9a05I9aBZOHztWy/UqcJdQYNsf59vrRKWnojAT9Y+GbIvoTBC++CPHqpDBhQ==",
+ "version": "6.15.1",
+ "resolved": "https://registry.npmjs.org/qs/-/qs-6.15.1.tgz",
+ "integrity": "sha512-6YHEFRL9mfgcAvql/XhwTvf5jKcOiiupt2FiJxHkiX1z4j7WL8J/jRHYLluORvc1XxB5rV20KoeK00gVJamspg==",
"license": "BSD-3-Clause",
"dependencies": {
"side-channel": "^1.1.0"
@@ -11035,9 +12204,9 @@
}
},
"node_modules/react": {
- "version": "19.2.4",
- "resolved": "https://registry.npmjs.org/react/-/react-19.2.4.tgz",
- "integrity": "sha512-9nfp2hYpCwOjAN+8TZFGhtWEwgvWHXqESH8qT89AT/lWklpLON22Lc8pEtnpsZz7VmawabSU0gCjnj8aC0euHQ==",
+ "version": "19.2.5",
+ "resolved": "https://registry.npmjs.org/react/-/react-19.2.5.tgz",
+ "integrity": "sha512-llUJLzz1zTUBrskt2pwZgLq59AemifIftw4aB7JxOqf1HY2FDaGDxgwpAPVzHU1kdWabH7FauP4i1oEeer2WCA==",
"license": "MIT",
"peer": true,
"engines": {
@@ -11045,16 +12214,16 @@
}
},
"node_modules/react-dom": {
- "version": "19.2.4",
- "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.4.tgz",
- "integrity": "sha512-AXJdLo8kgMbimY95O2aKQqsz2iWi9jMgKJhRBAxECE4IFxfcazB2LmzloIoibJI3C12IlY20+KFaLv+71bUJeQ==",
+ "version": "19.2.5",
+ "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.5.tgz",
+ "integrity": "sha512-J5bAZz+DXMMwW/wV3xzKke59Af6CHY7G4uYLN1OvBcKEsWOs4pQExj86BBKamxl/Ik5bx9whOrvBlSDfWzgSag==",
"license": "MIT",
"peer": true,
"dependencies": {
"scheduler": "^0.27.0"
},
"peerDependencies": {
- "react": "^19.2.4"
+ "react": "^19.2.5"
}
},
"node_modules/react-frame-component": {
@@ -11085,9 +12254,9 @@
}
},
"node_modules/react-router": {
- "version": "7.14.0",
- "resolved": "https://registry.npmjs.org/react-router/-/react-router-7.14.0.tgz",
- "integrity": "sha512-m/xR9N4LQLmAS0ZhkY2nkPA1N7gQ5TUVa5n8TgANuDTARbn1gt+zLPXEm7W0XDTbrQ2AJSJKhoa6yx1D8BcpxQ==",
+ "version": "7.14.1",
+ "resolved": "https://registry.npmjs.org/react-router/-/react-router-7.14.1.tgz",
+ "integrity": "sha512-5BCvFskyAAVumqhEKh/iPhLOIkfxcEUz8WqFIARCkMg8hZZzDYX9CtwxXA0e+qT8zAxmMC0x3Ckb9iMONwc5jg==",
"license": "MIT",
"dependencies": {
"cookie": "^1.0.1",
@@ -11236,11 +12405,12 @@
}
},
"node_modules/resolve": {
- "version": "1.22.11",
- "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.11.tgz",
- "integrity": "sha512-RfqAvLnMl313r7c9oclB1HhUEAezcpLjz95wFH4LVuhk9JF/r22qmVP9AMmOU4vMX7Q8pN8jwNg/CSpdFnMjTQ==",
+ "version": "1.22.12",
+ "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.12.tgz",
+ "integrity": "sha512-TyeJ1zif53BPfHootBGwPRYT1RUt6oGWsaQr8UyZW/eAm9bKoijtvruSDEmZHm92CwS9nj7/fWttqPCgzep8CA==",
"license": "MIT",
"dependencies": {
+ "es-errors": "^1.3.0",
"is-core-module": "^2.16.1",
"path-parse": "^1.0.7",
"supports-preserve-symlinks-flag": "^1.0.0"
@@ -11290,9 +12460,9 @@
}
},
"node_modules/rollup": {
- "version": "4.60.1",
- "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.60.1.tgz",
- "integrity": "sha512-VmtB2rFU/GroZ4oL8+ZqXgSA38O6GR8KSIvWmEFv63pQ0G6KaBH9s07PO8XTXP4vI+3UJUEypOfjkGfmSBBR0w==",
+ "version": "4.60.2",
+ "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.60.2.tgz",
+ "integrity": "sha512-J9qZyW++QK/09NyN/zeO0dG/1GdGfyp9lV8ajHnRVLfo/uFsbji5mHnDgn/qYdUHyCkM2N+8VyspgZclfAh0eQ==",
"license": "MIT",
"dependencies": {
"@types/estree": "1.0.8"
@@ -11305,31 +12475,31 @@
"npm": ">=8.0.0"
},
"optionalDependencies": {
- "@rollup/rollup-android-arm-eabi": "4.60.1",
- "@rollup/rollup-android-arm64": "4.60.1",
- "@rollup/rollup-darwin-arm64": "4.60.1",
- "@rollup/rollup-darwin-x64": "4.60.1",
- "@rollup/rollup-freebsd-arm64": "4.60.1",
- "@rollup/rollup-freebsd-x64": "4.60.1",
- "@rollup/rollup-linux-arm-gnueabihf": "4.60.1",
- "@rollup/rollup-linux-arm-musleabihf": "4.60.1",
- "@rollup/rollup-linux-arm64-gnu": "4.60.1",
- "@rollup/rollup-linux-arm64-musl": "4.60.1",
- "@rollup/rollup-linux-loong64-gnu": "4.60.1",
- "@rollup/rollup-linux-loong64-musl": "4.60.1",
- "@rollup/rollup-linux-ppc64-gnu": "4.60.1",
- "@rollup/rollup-linux-ppc64-musl": "4.60.1",
- "@rollup/rollup-linux-riscv64-gnu": "4.60.1",
- "@rollup/rollup-linux-riscv64-musl": "4.60.1",
- "@rollup/rollup-linux-s390x-gnu": "4.60.1",
- "@rollup/rollup-linux-x64-gnu": "4.60.1",
- "@rollup/rollup-linux-x64-musl": "4.60.1",
- "@rollup/rollup-openbsd-x64": "4.60.1",
- "@rollup/rollup-openharmony-arm64": "4.60.1",
- "@rollup/rollup-win32-arm64-msvc": "4.60.1",
- "@rollup/rollup-win32-ia32-msvc": "4.60.1",
- "@rollup/rollup-win32-x64-gnu": "4.60.1",
- "@rollup/rollup-win32-x64-msvc": "4.60.1",
+ "@rollup/rollup-android-arm-eabi": "4.60.2",
+ "@rollup/rollup-android-arm64": "4.60.2",
+ "@rollup/rollup-darwin-arm64": "4.60.2",
+ "@rollup/rollup-darwin-x64": "4.60.2",
+ "@rollup/rollup-freebsd-arm64": "4.60.2",
+ "@rollup/rollup-freebsd-x64": "4.60.2",
+ "@rollup/rollup-linux-arm-gnueabihf": "4.60.2",
+ "@rollup/rollup-linux-arm-musleabihf": "4.60.2",
+ "@rollup/rollup-linux-arm64-gnu": "4.60.2",
+ "@rollup/rollup-linux-arm64-musl": "4.60.2",
+ "@rollup/rollup-linux-loong64-gnu": "4.60.2",
+ "@rollup/rollup-linux-loong64-musl": "4.60.2",
+ "@rollup/rollup-linux-ppc64-gnu": "4.60.2",
+ "@rollup/rollup-linux-ppc64-musl": "4.60.2",
+ "@rollup/rollup-linux-riscv64-gnu": "4.60.2",
+ "@rollup/rollup-linux-riscv64-musl": "4.60.2",
+ "@rollup/rollup-linux-s390x-gnu": "4.60.2",
+ "@rollup/rollup-linux-x64-gnu": "4.60.2",
+ "@rollup/rollup-linux-x64-musl": "4.60.2",
+ "@rollup/rollup-openbsd-x64": "4.60.2",
+ "@rollup/rollup-openharmony-arm64": "4.60.2",
+ "@rollup/rollup-win32-arm64-msvc": "4.60.2",
+ "@rollup/rollup-win32-ia32-msvc": "4.60.2",
+ "@rollup/rollup-win32-x64-gnu": "4.60.2",
+ "@rollup/rollup-win32-x64-msvc": "4.60.2",
"fsevents": "~2.3.2"
}
},
@@ -11662,13 +12832,13 @@
}
},
"node_modules/side-channel-list": {
- "version": "1.0.0",
- "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.0.tgz",
- "integrity": "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==",
+ "version": "1.0.1",
+ "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.1.tgz",
+ "integrity": "sha512-mjn/0bi/oUURjc5Xl7IaWi/OJJJumuoJFQJfDDyO46+hBWsfaVM65TBHq2eoZBhzl9EchxOijpkbRC8SVBQU0w==",
"license": "MIT",
"dependencies": {
"es-errors": "^1.3.0",
- "object-inspect": "^1.13.3"
+ "object-inspect": "^1.13.4"
},
"engines": {
"node": ">= 0.4"
@@ -12094,6 +13264,12 @@
"url": "https://github.com/sponsors/sindresorhus"
}
},
+ "node_modules/style-mod": {
+ "version": "4.1.3",
+ "resolved": "https://registry.npmjs.org/style-mod/-/style-mod-4.1.3.tgz",
+ "integrity": "sha512-i/n8VsZydrugj3Iuzll8+x/00GH2vnYsk1eomD8QiRrSAeW6ItbCQDtfXCeJHd0iwiNagqjQkvpvREEPtW3IoQ==",
+ "license": "MIT"
+ },
"node_modules/style-search": {
"version": "0.1.0",
"resolved": "https://registry.npmjs.org/style-search/-/style-search-0.1.0.tgz",
@@ -12102,9 +13278,9 @@
"license": "ISC"
},
"node_modules/stylelint": {
- "version": "17.6.0",
- "resolved": "https://registry.npmjs.org/stylelint/-/stylelint-17.6.0.tgz",
- "integrity": "sha512-tokrsMIVAR9vAQ/q3UVEr7S0dGXCi7zkCezPRnS2kqPUulvUh5Vgfwngrk4EoAoW7wnrThqTdnTFN5Ra7CaxIg==",
+ "version": "17.8.0",
+ "resolved": "https://registry.npmjs.org/stylelint/-/stylelint-17.8.0.tgz",
+ "integrity": "sha512-oHkld9T60LDSaUQ4CSVc+tlt9eUoDlxhaGWShsUCKyIL14boZfmK5bSphZqx64aiC5tCqX+BsQMTMoSz8D1zIg==",
"dev": true,
"funding": [
{
@@ -12121,7 +13297,7 @@
"dependencies": {
"@csstools/css-calc": "^3.1.1",
"@csstools/css-parser-algorithms": "^4.0.0",
- "@csstools/css-syntax-patches-for-csstree": "^1.1.1",
+ "@csstools/css-syntax-patches-for-csstree": "^1.1.2",
"@csstools/css-tokenizer": "^4.0.0",
"@csstools/media-query-list-parser": "^5.0.0",
"@csstools/selector-resolve-nested": "^4.0.0",
@@ -12135,7 +13311,7 @@
"fastest-levenshtein": "^1.0.16",
"file-entry-cache": "^11.1.2",
"global-modules": "^2.0.0",
- "globby": "^16.1.1",
+ "globby": "^16.2.0",
"globjoin": "^0.1.4",
"html-tags": "^5.1.0",
"ignore": "^7.0.5",
@@ -12146,7 +13322,7 @@
"micromatch": "^4.0.8",
"normalize-path": "^3.0.0",
"picocolors": "^1.1.1",
- "postcss": "^8.5.8",
+ "postcss": "^8.5.9",
"postcss-safe-parser": "^7.0.1",
"postcss-selector-parser": "^7.1.1",
"postcss-value-parser": "^4.2.0",
@@ -12568,13 +13744,13 @@
"license": "MIT"
},
"node_modules/tinyglobby": {
- "version": "0.2.15",
- "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.15.tgz",
- "integrity": "sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==",
+ "version": "0.2.16",
+ "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.16.tgz",
+ "integrity": "sha512-pn99VhoACYR8nFHhxqix+uvsbXineAasWm5ojXoN8xEwK5Kd3/TrhNn1wByuD52UxWRLy8pu+kRMniEi6Eq9Zg==",
"license": "MIT",
"dependencies": {
"fdir": "^6.5.0",
- "picomatch": "^4.0.3"
+ "picomatch": "^4.0.4"
},
"engines": {
"node": ">=12.0.0"
@@ -12816,9 +13992,9 @@
}
},
"node_modules/typescript": {
- "version": "6.0.2",
- "resolved": "https://registry.npmjs.org/typescript/-/typescript-6.0.2.tgz",
- "integrity": "sha512-bGdAIrZ0wiGDo5l8c++HWtbaNCWTS4UTv7RaTH/ThVIgjkveJt83m74bBHMJkuCbslY8ixgLBVZJIOiQlQTjfQ==",
+ "version": "6.0.3",
+ "resolved": "https://registry.npmjs.org/typescript/-/typescript-6.0.3.tgz",
+ "integrity": "sha512-y2TvuxSZPDyQakkFRPZHKFm+KKVqIisdg9/CZwm9ftvKXLP8NRWj38/ODjNbr43SsoXqNuAisEf1GdCxqWcdBw==",
"dev": true,
"license": "Apache-2.0",
"peer": true,
@@ -12850,9 +14026,9 @@
}
},
"node_modules/undici": {
- "version": "7.24.7",
- "resolved": "https://registry.npmjs.org/undici/-/undici-7.24.7.tgz",
- "integrity": "sha512-H/nlJ/h0ggGC+uRL3ovD+G0i4bqhvsDOpbDv7At5eFLlj2b41L8QliGbnl2H7SnDiYhENphh1tQFJZf+MyfLsQ==",
+ "version": "7.25.0",
+ "resolved": "https://registry.npmjs.org/undici/-/undici-7.25.0.tgz",
+ "integrity": "sha512-xXnp4kTyor2Zq+J1FfPI6Eq3ew5h6Vl0F/8d9XU5zZQf1tX9s2Su1/3PiMmUANFULpmksxkClamIZcaUqryHsQ==",
"dev": true,
"license": "MIT",
"engines": {
@@ -12860,9 +14036,9 @@
}
},
"node_modules/undici-types": {
- "version": "7.18.2",
- "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.18.2.tgz",
- "integrity": "sha512-AsuCzffGHJybSaRrmr5eHr81mwJU3kjw6M+uprWvCXiNeN9SOGwQ3Jn8jb8m3Z6izVgknn1R0FTCEAP2QrLY/w==",
+ "version": "7.19.2",
+ "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.19.2.tgz",
+ "integrity": "sha512-qYVnV5OEm2AW8cJMCpdV20CDyaN3g0AjDlOGf1OW4iaDEx8MwdtChUp4zu4H0VP3nDRF/8RKWH+IPp9uW0YGZg==",
"devOptional": true,
"license": "MIT"
},
@@ -13056,9 +14232,9 @@
}
},
"node_modules/vite": {
- "version": "7.3.1",
- "resolved": "https://registry.npmjs.org/vite/-/vite-7.3.1.tgz",
- "integrity": "sha512-w+N7Hifpc3gRjZ63vYBXA56dvvRlNWRczTdmCBBa+CotUzAPf5b7YMdMR/8CQoeYE5LX3W4wj6RYTgonm1b9DA==",
+ "version": "7.3.2",
+ "resolved": "https://registry.npmjs.org/vite/-/vite-7.3.2.tgz",
+ "integrity": "sha512-Bby3NOsna2jsjfLVOHKes8sGwgl4TT0E6vvpYgnAYDIF/tie7MRaFthmKuHx1NSXjiTueXH3do80FMQgvEktRg==",
"license": "MIT",
"peer": true,
"dependencies": {
@@ -13130,6 +14306,12 @@
}
}
},
+ "node_modules/w3c-keyname": {
+ "version": "2.2.8",
+ "resolved": "https://registry.npmjs.org/w3c-keyname/-/w3c-keyname-2.2.8.tgz",
+ "integrity": "sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ==",
+ "license": "MIT"
+ },
"node_modules/w3c-xmlserializer": {
"version": "5.0.0",
"resolved": "https://registry.npmjs.org/w3c-xmlserializer/-/w3c-xmlserializer-5.0.0.tgz",
diff --git a/package.json b/package.json
index 2ac02e4a1..a786d22c8 100644
--- a/package.json
+++ b/package.json
@@ -91,13 +91,25 @@
"@babel/preset-env": "^7.29.2",
"@babel/preset-react": "^7.28.5",
"@babel/runtime": "^7.29.2",
+ "@codemirror/autocomplete": "^6.20.1",
+ "@codemirror/commands": "^6.10.3",
+ "@codemirror/highlight": "^0.19.8",
+ "@codemirror/lang-css": "^6.3.1",
+ "@codemirror/lang-javascript": "^6.2.5",
+ "@codemirror/lang-markdown": "^6.5.0",
+ "@codemirror/language": "^6.12.2",
+ "@codemirror/language-data": "^6.5.2",
+ "@codemirror/search": "^6.6.0",
+ "@codemirror/state": "^6.6.0",
+ "@codemirror/view": "^6.40.0",
"@dmsnell/diff-match-patch": "^1.1.0",
"@googleapis/drive": "^20.1.0",
+ "@lezer/highlight": "^1.2.3",
"@sanity/diff-match-patch": "^3.2.0",
+ "@uiw/codemirror-themes-all": "^4.25.8",
"@vitejs/plugin-react": "^5.1.2",
"body-parser": "^2.2.0",
"classnames": "^2.5.1",
- "codemirror": "^5.65.6",
"cookie-parser": "^1.4.7",
"core-js": "^3.49.0",
"cors": "^2.8.5",
diff --git a/server/homebrew.api.js b/server/homebrew.api.js
index 04c6507e8..c47e3640e 100644
--- a/server/homebrew.api.js
+++ b/server/homebrew.api.js
@@ -392,7 +392,7 @@ const api = {
if(brewFromServer?.hash !== brewFromClient?.hash) {
console.log(`Hash mismatch on brew ${brewFromClient.editId}`);
- //debugTextMismatch(brewFromClient.text, brewFromServer.text, `edit/${brewFromClient.editId}`);
+ debugTextMismatch(brewFromClient.text, brewFromServer.text, `edit/${brewFromClient.editId}`);
res.setHeader('Content-Type', 'application/json');
return res.status(409).send(JSON.stringify({ message: `The server copy is out of sync with the saved brew. Please save your changes elsewhere, refresh, and try again.` }));
}
@@ -405,7 +405,7 @@ const api = {
throw ('Patches did not apply cleanly, text mismatch detected');
// brew.text = applyPatches(patches, brewFromServer.text)[0];
} catch (err) {
- //debugTextMismatch(brewFromClient.text, brewFromServer.text, `edit/${brewFromClient.editId}`);
+ debugTextMismatch(brewFromClient.text, brewFromServer.text, `edit/${brewFromClient.editId}`);
console.error('Failed to apply patches:', {
//patches : brewFromClient.patches,
brewId : brewFromClient.editId || 'unknown',
diff --git a/themes/codeMirror/customEditorStyles.less b/themes/codeMirror/customEditorStyles.less
deleted file mode 100644
index 8c48c1b43..000000000
--- a/themes/codeMirror/customEditorStyles.less
+++ /dev/null
@@ -1,83 +0,0 @@
-.editor .codeEditor .CodeMirror {
- // Themes with dark backgrounds
- &.cm-s-3024-night,
- &.cm-s-abbott,
- &.cm-s-abcdef,
- &.cm-s-ambiance,
- &.cm-s-ayu-dark,
- &.cm-s-ayu-mirage,
- &.cm-s-base16-dark,
- &.cm-s-bespin,
- &.cm-s-blackboard,
- &.cm-s-cobalt,
- &.cm-s-colorforth,
- &.cm-s-darcula,
- &.cm-s-dracula,
- &.cm-s-duotone-dark,
- &.cm-s-erlang-dark,
- &.cm-s-gruvbox-dark,
- &.cm-s-hopscotch,
- &.cm-s-icecoder,
- &.cm-s-isotope,
- &.cm-s-lesser-dark,
- &.cm-s-liquibyte,
- &.cm-s-lucario,
- &.cm-s-material,
- &.cm-s-material-darker,
- &.cm-s-material-ocean,
- &.cm-s-material-palenight,
- &.cm-s-mbo,
- &.cm-s-midnight,
- &.cm-s-monokai,
- &.cm-s-moxer,
- &.cm-s-night,
- &.cm-s-nord,
- &.cm-s-oceanic-next,
- &.cm-s-panda-syntax,
- &.cm-s-paraiso-dark,
- &.cm-s-pastel-on-dark,
- &.cm-s-railscasts,
- &.cm-s-rubyblue,
- &.cm-s-seti,
- &.cm-s-shadowfox,
- &.cm-s-the-matrix,
- &.cm-s-tomorrow-night-bright,
- &.cm-s-tomorrow-night-eighties,
- &.cm-s-twilight,
- &.cm-s-vibrant-ink,
- &.cm-s-xq-dark,
- &.cm-s-yonce,
- &.cm-s-zenburn {
- .CodeMirror-code {
- .block:not(.cm-comment) { color : magenta; }
- .columnSplit {
- color : black;
- background-color : rgba(35,153,153,0.5);
- }
- .pageLine {
- background-color : rgba(255,255,255,0.5);
- & ~ pre.CodeMirror-line { color : black; }
- }
- }
- }
- // Themes with light backgrounds
- &.cm-s-default,
- &.cm-s-3024-day,
- &.cm-s-ambiance-mobile,
- &.cm-s-base16-light,
- &.cm-s-duotone-light,
- &.cm-s-eclipse,
- &.cm-s-elegant,
- &.cm-s-juejin,
- &.cm-s-neat,
- &.cm-s-neo,
- &.cm-s-paraiso-lightm
- &.cm-s-solarized,
- &.cm-s-ssms,
- &.cm-s-ttcn,
- &.cm-s-xq-light,
- &.cm-s-yeti {
- // Future styling for themes with light backgrounds
- --dummyVar : 'currently unused';
- }
-}
diff --git a/themes/codeMirror/customThemes/darkbrewery.css b/themes/codeMirror/customThemes/darkbrewery.css
deleted file mode 100644
index 6fba4001c..000000000
--- a/themes/codeMirror/customThemes/darkbrewery.css
+++ /dev/null
@@ -1,134 +0,0 @@
-/*stylelint-disable*/
-.editor .snippetBar {
- color: white;
- background-color: #2F393C;
- .dropdown {
- background-color: #2F393C;
- }
- .editors {
- border-color: #ccc;
- }
-}
-/* Main BG color and normal text color */
-.CodeMirror {
- --bg: #293134;
- --highlight: #bcbcbc;
- color: #91A6AA;
- background: var(--bg);
- .CodeMirror-scroll {
- .CodeMirror-gutters {
- border-right: 1px solid #555;
- background: var(--bg);
- .CodeMirror-gutter {
- background-color: var(--bg);
- &.CodeMirror-foldgutter {
- cursor: pointer;
- border-left: 1px solid #555;
- transition: background 0.1s;
- &:hover {
- background: #555;
- }
- }
- }
- }
- .CodeMirror-lines {
- /* Line numbers*/
- .CodeMirror-linenumber.CodeMirror-gutter-elt {
- background-color: var(--bg);
- color: #81969A;
- }
- /* Blinking cursor */
- .CodeMirror-cursor {
- border-left: 1px solid #E0E2E4;
- }
- .pageLine {
- color: #000000;
- background: #000000;
- border-bottom: 1px solid #FFFFFF;
- }
- .CodeMirror-code .CodeMirror-line {
- &.columnSplit {
- font-style: italic;
- color: inherit;
- background-color: #1F5763;
- border-bottom: #229999 solid 1px;
- }
- /*syntax*/
- .cm-header {
- font-weight: bold;
- color: #C51B1B;
- -webkit-text-stroke-width: 0.1px;
- -webkit-text-stroke-color: #000000;
- }
- .cm-strong {
- color: #309DD2;
- }
- .cm-em {
- /*italics*/
- }
- .cm-link {
- color: #DD6300;
- }
- .cm-string {
- color: #AA8261;
- }
- /* @import */
- .cm-def {
- color: #2986CC;
- }
- /* Bullets and such */
- .cm-variable-2 {
- color: #3CBF30;
- }
- .block:not(.cm-comment) {
- color: #E3E3E3;
- }
- .inline-block {
- color: #E3E3E3;
- }
- .cm-tag {
- color: #E3FF00;
- }
- .cm-attribute {
- color: #E3FF00;
- }
- .cm-atom {
- color: #c1939a;
- }
- .cm-number {
- color: #2986CC;
- }
- .cm-property:not(.cm-error) ~ .cm-variable {
- color:#9e1f9e;
- }
- .cm-qualifier {
- color: #EE1919;
- }
- .cm-comment {
- color: #BBC700;
- }
- .cm-keyword {
- color: white;
- }
- .cm-error {
- color: #C50202;
- }
- .CodeMirror-foldmarker {
- color: #F0FF00;
- }
- .cm-builtin {
- color: #FFFFFF;
- }
- .dt-highlight {
- background: #ffffff14;
- }
- .dl-colon-highlight {
- background: #ccc;
- }
- .dl-highlight.dd-highlight {
- color: #b5858d;
- }
- }
- }
- }
-}
\ No newline at end of file
diff --git a/themes/codeMirror/darkbrewery.js b/themes/codeMirror/darkbrewery.js
new file mode 100644
index 000000000..4dca1e466
--- /dev/null
+++ b/themes/codeMirror/darkbrewery.js
@@ -0,0 +1,114 @@
+import { EditorView } from '@codemirror/view';
+
+
+export default EditorView.theme({
+ '&' : {
+ backgroundColor : '#293134',
+ color : '#91a6aa',
+ },
+ '.cm-content' : {
+ padding : '4px 0',
+ fontFamily : 'monospace',
+ fontSize : '13px',
+ lineHeight : '1',
+ },
+ '.cm-line' : {
+ padding : '0 4px',
+ },
+ '.cm-gutters' : {
+ borderRight : '1px solid #555',
+ backgroundColor : '#293134',
+ whiteSpace : 'nowrap',
+ },
+ '.cm-foldGutter' : {
+ borderLeft : '1px solid #555',
+ backgroundColor : '#293134',
+ },
+ '.cm-foldGutter:hover' : {
+ backgroundColor : '#555',
+ },
+ '.cm-gutterElement' : {
+ color : '#81969a',
+ },
+ '.cm-linenumber' : {
+ padding : '0 3px 0 5px',
+ minWidth : '20px',
+ textAlign : 'right',
+ color : '#999',
+ whiteSpace : 'nowrap',
+ },
+ '.cm-cursor' : {
+ borderLeft : '1px solid #E0E2E4',
+ },
+ '.cm-fat-cursor' : {
+ width : 'auto',
+ backgroundColor : '#7e7',
+ caretColor : 'transparent',
+ },
+ '.cm-activeLine' : {
+ backgroundColor : '#868c9323',
+ },
+ '.cm-gutterElement.cm-activeLineGutter' : {
+ backgroundColor : '#868c9323',
+ },
+ '.cm-activeLine' : {
+ backgroundColor : '#868c9323',
+ },
+ '.cm-selected' : {
+ backgroundColor : '#d7d4f0',
+ },
+ '.cm-pageLine' : {
+ backgroundColor : '#7ca97c',
+ color : '#000',
+ fontWeight : 'bold',
+ letterSpacing : '.5px',
+ borderTop : '1px solid #ff0',
+ },
+ '.cm-columnSplit' : {
+ backgroundColor : '#7ca97c',
+ color : 'black',
+ fontWeight : 'bold',
+ letterSpacing : '1px',
+ borderBottom : '1px solid #ff0',
+ },
+ '.cm-line.cm-block, .cm-line .cm-inline-block' : {
+ color : '#E3E3E3',
+ },
+ '.cm-definitionList .cm-definitionTerm' : {
+ color : '#E3E3E3',
+ },
+ '.cm-definitionList .cm-definitionColon' : {
+ backgroundColor : '#0000',
+ color : '#e3FF00',
+ },
+ '.cm-definitionList .cm-definitionDesc' : {
+ color : '#b5858d',
+ },
+
+ // Semantic classes
+ '.cm-header' : { color: '#C51B1B', fontWeight: 'bold' },
+ '.cm-strong' : { color: '#309dd2', fontWeight: 'bold' },
+ '.cm-em' : { fontStyle: 'italic' },
+ '.cm-keyword' : { color: '#fff' },
+ '.cm-atom, cm-value, cm-color' : { color: '#c1939a' },
+ '.cm-number' : { color: '#2986cc' },
+ '.cm-def' : { color: '#2986cc' },
+ '.cm-list' : { color: '#3cbf30' },
+ '.cm-variable, .cm-type' : { color: '#085' },
+ '.cm-comment' : { color: '#bbc700' },
+ '.cm-link' : { color: '#DD6300', textDecoration: 'underline' },
+ '.cm-string' : { color: '#AA8261', textDecoration: 'none' },
+ '.cm-string-2' : { color: '#f50', textDecoration: 'none' },
+ '.cm-meta, .cm-qualifier, .cm-class' : { color: '#19ee2b' },
+ '.cm-builtin' : { color: '#fff' },
+ '.cm-bracket' : { color: '#997' },
+ '.cm-tag, .cm-attribute' : { color: '#e3ff00' },
+ '.cm-hr' : { color: '#999' },
+ '.cm-negative' : { color: '#d44' },
+ '.cm-positive' : { color: '#292' },
+ '.cm-error, .cm-invalidchar' : { color: '#c50202' },
+ '.cm-matchingbracket' : { color: '#0b0' },
+ '.cm-nonmatchingbracket' : { color: '#a22' },
+ '.cm-matchingtag' : { backgroundColor: 'rgba(255, 150, 0, 0.3)' },
+ '.cm-quote' : { color: '#090' },
+}, { dark: true });
\ No newline at end of file
diff --git a/themes/codeMirror/customThemes/darkvision.css b/themes/codeMirror/darkvision.css
similarity index 89%
rename from themes/codeMirror/customThemes/darkvision.css
rename to themes/codeMirror/darkvision.css
index 4c74d105e..c88455c91 100644
--- a/themes/codeMirror/customThemes/darkvision.css
+++ b/themes/codeMirror/darkvision.css
@@ -1,3 +1,8 @@
+/*This document is old, from back when Codemirror was version 5,
+if someone wants to update it, feel free, it needs to be like default.js or darkbrewery.js
+Then imported in snippetbar.jsx and codeEditor.jsx.
+*/
+
.CodeMirror {
background: #0C0C0C;
color: #B9BDB6;
@@ -18,13 +23,13 @@
}
/* Line number stuff */
- .CodeMirror-gutter-elt {
+ .cm-gutter-elt {
color: #81969A;
}
.CodeMirror-linenumber {
background-color: #0C0C0C;
}
- .CodeMirror-gutter {
+ .cm-gutter {
background-color: #0C0C0C;
}
diff --git a/themes/codeMirror/default.js b/themes/codeMirror/default.js
new file mode 100644
index 000000000..0625ded76
--- /dev/null
+++ b/themes/codeMirror/default.js
@@ -0,0 +1,81 @@
+import { EditorView } from '@codemirror/view';
+
+//This theme is made of the base css for the codemirror 5 editor
+
+export default EditorView.theme({
+ '&' : {
+ backgroundColor : 'white',
+ color : 'black',
+ },
+ '.cm-content' : {
+ padding : '4px 0',
+ fontFamily : 'monospace',
+ fontSize : '13px',
+ lineHeight : '1',
+ },
+ '.cm-line' : {
+ padding : '0 4px',
+ },
+ '.cm-gutters' : {
+ borderRight : '1px solid #ddd',
+ backgroundColor : '#f7f7f7',
+ whiteSpace : 'nowrap',
+ },
+ '.cm-linenumber' : {
+ padding : '0 3px 0 5px',
+ minWidth : '20px',
+ textAlign : 'right',
+ color : '#999',
+ whiteSpace : 'nowrap',
+ },
+ '.cm-cursor' : {
+ borderLeft : '1px solid black',
+ },
+ '.cm-fat-cursor' : {
+ width : 'auto',
+ backgroundColor : '#7e7',
+ caretColor : 'transparent',
+ },
+ '.cm-activeLine' : {
+ backgroundColor : '#becee374',
+ },
+ '.cm-gutterElement.cm-activeLineGutter' : {
+ backgroundColor : '#becee374',
+ },
+ '.cm-selected' : {
+ backgroundColor : '#d7d4f0',
+ },
+ '.cm-foldmarker' : {
+ color : 'blue',
+ fontFamily : 'arial',
+ lineHeight : '0.3',
+ cursor : 'pointer',
+ },
+
+ '.cm-header' : { color: 'blue', fontWeight: 'bold' },
+ '.cm-strong' : { fontWeight: 'bold' },
+ '.cm-em' : { fontStyle: 'italic' },
+ '.cm-keyword' : { color: '#708' },
+ '.cm-atom, cm-value, cm-color' : { color: '#219' },
+ '.cm-number' : { color: '#164' },
+ '.cm-def' : { color: '#00f' },
+ '.cm-list' : { color: '#05a' },
+ '.cm-variable, .cm-type' : { color: '#085' },
+ '.cm-comment' : { color: '#a50' },
+ '.cm-link' : { color: '#00c', textDecoration: 'underline' },
+ '.cm-string' : { color: '#a11', textDecoration: 'none' },
+ '.cm-string-2' : { color: '#f50', textDecoration: 'none' },
+ '.cm-meta, .cm-qualifier, .cm-class' : { color: '#555' },
+ '.cm-builtin' : { color: '#30a' },
+ '.cm-bracket' : { color: '#997' },
+ '.cm-tag' : { color: '#170' },
+ '.cm-attribute' : { color: '#00c' },
+ '.cm-hr' : { color: '#999' },
+ '.cm-negative' : { color: '#d44' },
+ '.cm-positive' : { color: '#292' },
+ '.cm-error, .cm-invalidchar' : { color: '#f00' },
+ '.cm-matchingbracket' : { color: '#0b0' },
+ '.cm-nonmatchingbracket' : { color: '#a22' },
+ '.cm-matchingtag' : { backgroundColor: '#ff96004d' },
+ '.cm-quote' : { color: '#090' },
+}, { dark: false });
\ No newline at end of file
diff --git a/vitePlugins/generateAssetsPlugin.js b/vitePlugins/generateAssetsPlugin.js
index caea2c1e8..749cc5636 100644
--- a/vitePlugins/generateAssetsPlugin.js
+++ b/vitePlugins/generateAssetsPlugin.js
@@ -61,19 +61,6 @@ export function generateAssetsPlugin(isDev = false) {
await fs.copy('./themes/fonts', `${buildDir}/fonts`);
await fs.copy('./themes/assets', `${buildDir}/assets`);
await fs.copy('./client/icons', `${buildDir}/icons`);
-
- // Compile CodeMirror editor themes
- const editorThemesBuildDir = `${buildDir}/homebrew/cm-themes`;
- await fs.copy('./node_modules/codemirror/theme', editorThemesBuildDir);
- await fs.copy('./themes/codeMirror/customThemes', editorThemesBuildDir);
-
- const editorThemeFiles = fs.readdirSync(editorThemesBuildDir);
- await fs.outputFile(`${buildDir}/homebrew/codeMirror/editorThemes.json`,
- JSON.stringify(['default', ...editorThemeFiles.map((f)=>f.slice(0, -4))], null, 2),
- );
-
- // Copy remaining CodeMirror assets
- await fs.copy('./themes/codeMirror', `${buildDir}/homebrew/codeMirror`);
},
};
}