From fabbc68fd789357fa374826c35193ebe077e411d Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 12 Feb 2021 13:27:47 +0000 Subject: [PATCH 01/56] v0.9.3 --- client/src/extension.ts | 2 +- package.json | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/client/src/extension.ts b/client/src/extension.ts index 9060829..f0b235c 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -9,7 +9,7 @@ import { PersistentState } from './persistent_state' import * as path from 'path' const platforms: { [key: string]: string } = { - 'x64 win32': 'x86_64-pc-windows-msvc', + 'x64 win32': 'x86_64-windows-msvc', 'x64 linux': 'x86_64-unknown-linux-gnu', 'x64 darwin': 'x86_64-apple-darwin', } diff --git a/package.json b/package.json index 05f740c..3d65a27 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "vscode-mc-shader", "displayName": "Minecraft GLSL Shaders", "description": "A Visual Studio Code extension for linting/etc Minecraft GLSL Shaders", - "version": "0.9.2", + "version": "0.9.3", "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", From 72ea905413d13d5d3391f90bb6c7ee8472f03f82 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 13 Feb 2021 18:27:42 +0000 Subject: [PATCH 02/56] fixes merger for mixed CRLF/LF projects --- server/src/commands.rs | 1 + server/src/main.rs | 2 ++ server/src/merge_views.rs | 29 +++++++++-------------------- 3 files changed, 12 insertions(+), 20 deletions(-) diff --git a/server/src/commands.rs b/server/src/commands.rs index b194ad5..3090f4e 100644 --- a/server/src/commands.rs +++ b/server/src/commands.rs @@ -113,6 +113,7 @@ impl VirtualMergedDocument { Ok(s) => s, Err(e) => return Err(format_err!("error reading {:?}: {}", path, e)) }; + let source = crate::RE_CRLF.replace_all(&source, "\n").to_string(); sources.insert(path.clone(), source); } diff --git a/server/src/main.rs b/server/src/main.rs index 8dce1c5..0da5ddf 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -45,6 +45,7 @@ lazy_static! { static ref RE_VERSION: Regex = Regex::new(r#"#version [\d]{3}"#).unwrap(); static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); static ref RE_INCLUDE_EXTENSION: Regex = Regex::new(r#"#extension GL_GOOGLE_include_directive ?: ?require"#).unwrap(); + pub static ref RE_CRLF: Regex = Regex::new(r#"\r\n"#).unwrap(); } fn main() { @@ -456,6 +457,7 @@ impl MinecraftShaderLanguageServer { Ok(s) => s, Err(e) => return Err(anyhow!("error reading {:?}: {}", path, e)) }; + let source = RE_CRLF.replace_all(&source, "\n").to_string(); sources.insert(path.clone(), source); } diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index 1aad5a8..a120e0a 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -29,16 +29,10 @@ pub fn generate_merge_list<'a>( last_offset_set.insert(first_path.clone(), 0); - let line_ending_offset = if is_crlf(sources.get(&first_path).unwrap()) { - 2 - } else { - 1 - }; - // stack to keep track of the depth first traversal let mut stack = VecDeque::::new(); - create_merge_views(&mut nodes_iter, &mut merge_list, &mut last_offset_set, graph, sources, &mut line_directives, &mut stack, line_ending_offset); + create_merge_views(&mut nodes_iter, &mut merge_list, &mut last_offset_set, graph, sources, &mut line_directives, &mut stack); // now we add a view of the remainder of the root file let offset = *last_offset_set.get(&first_path).unwrap(); @@ -58,10 +52,6 @@ pub fn generate_merge_list<'a>( merged } -fn is_crlf(source: &String) -> bool { - source.contains("\r\n") -} - fn create_merge_views<'a>( nodes: &mut Peekable)>>, merge_list: &mut LinkedList<&'a str>, @@ -70,7 +60,6 @@ fn create_merge_views<'a>( sources: &'a HashMap, line_directives: &mut Vec, stack: &mut VecDeque, - line_ending_offset: usize, ) { loop { @@ -86,7 +75,7 @@ fn create_merge_views<'a>( let child_path = graph.get_node(child).clone(); let parent_source = sources.get(&parent_path).unwrap(); - let (char_for_line, char_following_line) = char_offset_for_line(edge.line, parent_source, line_ending_offset); + let (char_for_line, char_following_line) = char_offset_for_line(edge.line, parent_source); let offset = *last_offset_set.insert(parent_path.clone(), char_following_line).get_or_insert(0); merge_list.push_back(&parent_source[offset..char_for_line]); @@ -101,7 +90,7 @@ fn create_merge_views<'a>( // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad let offset = { match child_source.ends_with("\n") { - true => child_source.len()-line_ending_offset, + true => child_source.len()-1, false => child_source.len(), } }; @@ -117,7 +106,7 @@ fn create_merge_views<'a>( } stack.push_back(parent); - create_merge_views(nodes, merge_list, last_offset_set, graph, sources, line_directives, stack, line_ending_offset); + create_merge_views(nodes, merge_list, last_offset_set, graph, sources, line_directives, stack); stack.pop_back(); let offset = *last_offset_set.get(&child_path).unwrap(); @@ -125,7 +114,7 @@ fn create_merge_views<'a>( // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 let end_offset = { match child_source.ends_with("\n") { - true => line_ending_offset/* child_source.len()-1 */, + true => 1/* child_source.len()-1 */, false => 0/* child_source.len() */, } }; @@ -148,7 +137,7 @@ fn create_merge_views<'a>( // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad let offset = { match child_source.ends_with("\n") { - true => child_source.len()-line_ending_offset, + true => child_source.len()-1, false => child_source.len(), } }; @@ -163,15 +152,15 @@ fn create_merge_views<'a>( // returns the character offset + 1 of the end of line number `line` and the character // offset + 1 for the end of the line after the previous one -fn char_offset_for_line(line_num: usize, source: &str, line_ending_offset: usize) -> (usize, usize) { +fn char_offset_for_line(line_num: usize, source: &str) -> (usize, usize) { let mut char_for_line: usize = 0; let mut char_following_line: usize = 0; for (n, line) in source.lines().enumerate() { if n == line_num { - char_following_line += line.len()+line_ending_offset; + char_following_line += line.len()+1; break; } - char_for_line += line.len()+line_ending_offset; + char_for_line += line.len()+1; char_following_line = char_for_line; } (char_for_line, char_following_line) From 3bfa7a2cc49902851012c71b2a6d997cc1dc760a Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 13 Feb 2021 18:28:09 +0000 Subject: [PATCH 03/56] stops bootstraping of server when in debug mode --- client/src/extension.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/extension.ts b/client/src/extension.ts index f0b235c..80a2c33 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -38,7 +38,7 @@ export class Extension { this.extensionContext = context this.state = new PersistentState(context.globalState) - await this.bootstrap() + if(!process.env['MCSHADER_DEBUG']) await this.bootstrap() this.registerCommand('graphDot', commands.generateGraphDot) this.registerCommand('restart', commands.restartExtension) From 22deb53ecd5f26c862a3cab460457af612bbf9de Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 13 Feb 2021 18:28:36 +0000 Subject: [PATCH 04/56] dont add to graph or lint files out-of-tree --- server/src/main.rs | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/server/src/main.rs b/server/src/main.rs index 0da5ddf..f334e73 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -574,6 +574,9 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn did_open_text_document(&mut self, params: DidOpenTextDocumentParams) { //eprintln!("opened doc {}", params.text_document.uri); let path = PathBuf::from_url(params.text_document.uri); + if !path.starts_with(&self.root) { + return + } if self.graph.borrow_mut().find_node(&path) == None { self.add_file_and_includes_to_graph(&path); } @@ -588,9 +591,12 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn did_close_text_document(&mut self, _: DidCloseTextDocumentParams) {} fn did_save_text_document(&mut self, params: DidSaveTextDocumentParams) { - eprintln!("saved doc {}", params.text_document.uri); + //eprintln!("saved doc {}", params.text_document.uri); let path = PathBuf::from_url(params.text_document.uri); + if !path.starts_with(&self.root) { + return + } self.update_includes(&path); match self.lint(&path) { From 9a770f69a4c49b4d93bdc907d4b78b1554318405 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 13 Feb 2021 18:37:27 +0000 Subject: [PATCH 05/56] v0.9.4 --- CHANGELOG.md | 53 ++++++++++++++++++++++++++++++++++++++++++++++- package.json | 2 +- server/Cargo.lock | 2 +- server/Cargo.toml | 2 +- 4 files changed, 55 insertions(+), 4 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6bc78cd..c6bb95b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,57 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +## [0.9.4] + +### Fixed + +- `#include` merging when project consists of files with both CRLF and LF files +- Out-of-tree shader files are not linted or added to the dependency graph +- Client no longer attempts to bootstrap server when `MCSHADER_DEBUG=true` + +## [0.9.3] + +### Fixed + +- Language server download for windows + +## [0.9.2] + +### Changed + +- VSCode extension activation predicate to only when `shaders` folder exists at top level + +### Added + +- Additional client-side logging + +## [0.9.1] + +### Fixed + +- Windows support in client not adding `.exe` to language server path +- Binary release CI + +## [0.9.0] + +### Changed + +- Replaced in-process Typescript language server with Rust based language server + +### Fixed + +- Due to the above, `#include` directive handling is vastly improved + +### Added + +- Command to view read-only document representing a top-level file with all includes merged +- Command to generate a DOT graph file of the entire project +- Command to restart language server + +### Removed + +- `glslangValidatorPath` and `shaderpacksPath` config settings + ## [0.8.5] ### Fixed @@ -33,4 +84,4 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) - Support for #include directives - Basic linting with highlighting with error propogation to all known parents of an include. - Support for .fsh, .vsh, .glsl and .gsh files. -- Incomplete completion items \ No newline at end of file +- Incomplete completion items diff --git a/package.json b/package.json index 3d65a27..49f9373 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "vscode-mc-shader", "displayName": "Minecraft GLSL Shaders", "description": "A Visual Studio Code extension for linting/etc Minecraft GLSL Shaders", - "version": "0.9.3", + "version": "0.9.4", "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", diff --git a/server/Cargo.lock b/server/Cargo.lock index bc5b733..d8c8f0a 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -701,7 +701,7 @@ checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" [[package]] name = "mcshader-lsp" -version = "0.9.2" +version = "0.9.4" dependencies = [ "anyhow", "bit-set", diff --git a/server/Cargo.toml b/server/Cargo.toml index 02d6163..3179c42 100644 --- a/server/Cargo.toml +++ b/server/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mcshader-lsp" -version = "0.9.2" +version = "0.9.4" authors = ["Noah Santschi-Cooney "] edition = "2018" From 551380a6ed00709287460b7d8c88e7803956052c Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 19 Feb 2021 01:02:09 +0000 Subject: [PATCH 06/56] fixes merger for when file is merged twice This happens in projects where an #include is normally guarded by #ifdef. File A conditionally includes either B or C based on an #ifdef. Both B and C include D, so D gets merged twice. Previously, the offset to which a file view has been created is stored globally. This means that the offset would be reused on a fresh include in the above situation. Solved by storing offsets keyed by the NodeIndex of the parent file that is including and the NodeIndex of the file being included. --- server/src/merge_views.rs | 34 ++++++++++++++++++++++++---------- 1 file changed, 24 insertions(+), 10 deletions(-) diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index a120e0a..9666de6 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -8,6 +8,18 @@ use petgraph::stable_graph::NodeIndex; use crate::graph::CachedStableGraph; +/// FilialTuple represents a tuple with a parent at index 0 +/// and a child at index 1. Parent can be nullable in the case of +/// the child being a top level node in the tree. +#[derive(PartialEq, Eq, Hash)] +struct FilialTuple(Option, NodeIndex); + +impl From<(Option<&NodeIndex>, NodeIndex)> for FilialTuple { + fn from(tuple: (Option<&NodeIndex>, NodeIndex)) -> Self { + FilialTuple(tuple.0.and_then(|n| Some(*n)), tuple.1) + } +} + pub fn generate_merge_list<'a>( nodes: &'a [(NodeIndex, Option)], sources: &'a HashMap, @@ -20,14 +32,15 @@ pub fn generate_merge_list<'a>( line_directives.reserve(nodes.len() * 2); - let mut last_offset_set: HashMap = HashMap::new(); + let mut last_offset_set: HashMap = HashMap::new(); let mut nodes_iter = nodes.iter().peekable(); + // invariant: nodes_iter always has _at least_ one element. Can't save a not-file :B let first = nodes_iter.next().unwrap().0; - let first_path = graph.get_node(first).clone(); + let first_path = graph.get_node(first); - last_offset_set.insert(first_path.clone(), 0); + last_offset_set.insert(FilialTuple(None, first), 0); // stack to keep track of the depth first traversal let mut stack = VecDeque::::new(); @@ -35,7 +48,7 @@ pub fn generate_merge_list<'a>( create_merge_views(&mut nodes_iter, &mut merge_list, &mut last_offset_set, graph, sources, &mut line_directives, &mut stack); // now we add a view of the remainder of the root file - let offset = *last_offset_set.get(&first_path).unwrap(); + let offset = *last_offset_set.get(&FilialTuple(None, first)).unwrap(); let len = sources.get(&first_path).unwrap().len(); merge_list.push_back(&sources.get(&first_path).unwrap()[min(offset, len) ..]); @@ -55,7 +68,7 @@ pub fn generate_merge_list<'a>( fn create_merge_views<'a>( nodes: &mut Peekable)>>, merge_list: &mut LinkedList<&'a str>, - last_offset_set: &mut HashMap, + last_offset_set: &mut HashMap, graph: &'a CachedStableGraph, sources: &'a HashMap, line_directives: &mut Vec, @@ -68,6 +81,7 @@ fn create_merge_views<'a>( None => return, }; + // invariant: never None as only the first element in `nodes` should have a None, which is popped off in the calling function let parent = n.1.unwrap(); let child = n.0; let edge = graph.get_edge_meta(parent, child); @@ -77,7 +91,7 @@ fn create_merge_views<'a>( let parent_source = sources.get(&parent_path).unwrap(); let (char_for_line, char_following_line) = char_offset_for_line(edge.line, parent_source); - let offset = *last_offset_set.insert(parent_path.clone(), char_following_line).get_or_insert(0); + let offset = *last_offset_set.insert((stack.back(), parent).into(), char_following_line).get_or_insert(0); merge_list.push_back(&parent_source[offset..char_for_line]); add_opening_line_directive(&child_path, merge_list, line_directives); @@ -95,7 +109,7 @@ fn create_merge_views<'a>( } }; merge_list.push_back(&child_source[..offset]); - last_offset_set.insert(child_path.clone(), 0); + last_offset_set.insert(FilialTuple(Some(parent), child), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line add_closing_line_directive(edge.line+2, &parent_path, merge_list, line_directives); // if the next pair's parent is not the current pair's parent, we need to bubble up @@ -109,7 +123,7 @@ fn create_merge_views<'a>( create_merge_views(nodes, merge_list, last_offset_set, graph, sources, line_directives, stack); stack.pop_back(); - let offset = *last_offset_set.get(&child_path).unwrap(); + let offset = *last_offset_set.get(&FilialTuple(Some(parent), child)).unwrap(); let child_source = sources.get(&child_path).unwrap(); // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 let end_offset = { @@ -121,7 +135,7 @@ fn create_merge_views<'a>( if offset < child_source.len()-end_offset { // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad merge_list.push_back(&child_source[offset../* std::cmp::max( */child_source.len()-end_offset/* , offset) */]); - last_offset_set.insert(child_path.clone(), 0); + last_offset_set.insert(FilialTuple(Some(parent), child), 0); } // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line @@ -142,7 +156,7 @@ fn create_merge_views<'a>( } }; merge_list.push_back(&child_source[..offset]); - last_offset_set.insert(child_path.clone(), 0); + last_offset_set.insert(FilialTuple(Some(parent), child), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line add_closing_line_directive(edge.line+2, &parent_path, merge_list, line_directives); } From c854093a967b5667412e68d07c24ac90e9c2cd12 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 19 Feb 2021 01:07:57 +0000 Subject: [PATCH 07/56] changelog --- CHANGELOG.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index c6bb95b..7bdc49d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,12 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +## Unreleased + +### Fixed + +- Fixed `#include` merging for when file is merged twice that would normally be `#ifdef` guarded. Please see commit message of [551380a](https://github.com/Strum355/mcshader-lsp/commit/551380a6ed00709287460b7d8c88e7803956052c) for detailed explanation. + ## [0.9.4] ### Fixed From 248afcd98896a4bd8ba48b6696c0b7a6bddf8206 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 19 Feb 2021 01:11:36 +0000 Subject: [PATCH 08/56] adds custom file association support to filesystem event watcher --- CHANGELOG.md | 6 +++++- client/src/extension.ts | 32 +++++++++++++++++++++++++++++--- client/src/lspClient.ts | 15 +++++++-------- 3 files changed, 41 insertions(+), 12 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7bdc49d..d732760 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,9 +6,13 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) ## Unreleased +### Added + +- Filesystem watcher reads custom defined file associations + ### Fixed -- Fixed `#include` merging for when file is merged twice that would normally be `#ifdef` guarded. Please see commit message of [551380a](https://github.com/Strum355/mcshader-lsp/commit/551380a6ed00709287460b7d8c88e7803956052c) for detailed explanation. +- Fixed `#include` merging for when file is merged twice that would normally be `#ifdef` guarded. Please see commit message of [551380a](https://github.com/Strum355/mcshader-lsp/commit/551380a6ed00709287460b7d8c88e7803956052c) for detailed explanation ## [0.9.4] diff --git a/client/src/extension.ts b/client/src/extension.ts index 80a2c33..961c6e8 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -45,12 +45,38 @@ export class Extension { this.registerCommand('virtualMerge', commands.virtualMergedDocument) log.info('starting language server...') + + const lspBinary = process.env['MCSHADER_DEBUG'] ? + this.context.asAbsolutePath(path.join('server', 'target', 'debug', 'mcshader-lsp')) + + (process.platform === 'win32' ? '.exe' : '') : + path.join(this.context.globalStoragePath, 'mcshader-lsp') + + const filewatcherGlob = this.fileAssociationsToGlob(this.getGLSLFileAssociations()) - this.client = await new LanguageClient(this).startServer() + this.client = await new LanguageClient(this, lspBinary, filewatcherGlob).startServer() log.info('language server started!') } + fileAssociationsToGlob = (associations: string[]): string => { + return '**/*.{'.concat( + associations.map(s => s.substring(s.indexOf('.'))).join(',') + ) + '}' + } + + getGLSLFileAssociations = (): string[] => { + const exts = ['.fsh', '.vsh', '.gsh', '.glsl'] + const associations = vscode.workspace.getConfiguration('files').get('associations') as {[key: string]: string} + + Object.keys(associations).forEach((key) => { + if(associations[key] === 'glsl') { + exts.push(key.substring(key.indexOf('*')+1)) + } + }) + + return exts + } + registerCommand = (name: string, f: (e: Extension) => commands.Command) => { const cmd = f(this) this.context.subscriptions.push(vscode.commands.registerCommand('mcglsl.'+name, cmd)) @@ -83,7 +109,7 @@ export class Extension { if (!exists) await this.state.updateServerVersion(undefined) const release = await getReleaseInfo(this.package.version) - log.info(`got release info from Github:\n\t`, JSON.stringify(release)) + log.info('got release info from Github:\n\t', JSON.stringify(release)) const platform = platforms[`${process.arch} ${process.platform}`] if (platform === undefined) { @@ -93,7 +119,7 @@ export class Extension { } if (release.tag_name === this.state.serverVersion) { - log.info(`server version is same as extension:\n\t`, this.state.serverVersion) + log.info('server version is same as extension:\n\t', this.state.serverVersion) return } diff --git a/client/src/lspClient.ts b/client/src/lspClient.ts index 8f20423..57cc6aa 100644 --- a/client/src/lspClient.ts +++ b/client/src/lspClient.ts @@ -1,28 +1,27 @@ -import * as path from 'path' import { ConfigurationTarget, workspace } from 'vscode' import * as lsp from 'vscode-languageclient' import { Extension } from './extension' -import { lspOutputChannel } from './log' +import { log, lspOutputChannel } from './log' import { ConfigUpdateParams, statusMethod, StatusParams, updateConfigMethod } from './lspExt' export class LanguageClient extends lsp.LanguageClient { private extension: Extension - constructor(ext: Extension) { + constructor(ext: Extension, lspBinary: string, filewatcherGlob: string) { super('vscode-mc-shader', 'VSCode MC Shader', { - command: process.env['MCSHADER_DEBUG'] ? - ext.context.asAbsolutePath(path.join('server', 'target', 'debug', 'mcshader-lsp')) + - (process.platform === 'win32' ? '.exe' : '') : - path.join(ext.context.globalStoragePath, 'mcshader-lsp') + command: lspBinary }, { documentSelector: [{scheme: 'file', language: 'glsl'}], outputChannel: lspOutputChannel, synchronize: { configurationSection: 'mcglsl', - fileEvents: workspace.createFileSystemWatcher('**/*.{fsh,gsh,vsh,glsl,inc}') + fileEvents: workspace.createFileSystemWatcher(filewatcherGlob) }, }) this.extension = ext + + log.info('server receiving events for file glob:\n\t', filewatcherGlob) + log.info('running with binary at path:\n\t', lspBinary) } public startServer = async (): Promise => { From b649aeb1f644a54f1d10b80cb9028c68d8bbc009 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 19 Feb 2021 01:23:17 +0000 Subject: [PATCH 09/56] v0.9.5 --- CHANGELOG.md | 2 +- logo-mini.png | Bin 0 -> 27427 bytes package.json | 4 ++-- server/Cargo.lock | 4 +++- server/Cargo.toml | 2 +- 5 files changed, 7 insertions(+), 5 deletions(-) create mode 100644 logo-mini.png diff --git a/CHANGELOG.md b/CHANGELOG.md index d732760..dbe0f9e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,7 +4,7 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) -## Unreleased +## [0.9.5] ### Added diff --git a/logo-mini.png b/logo-mini.png new file mode 100644 index 0000000000000000000000000000000000000000..af16bb8fa2d2c06ae5e9ad4d2fa4720f64a1c1e6 GIT binary patch literal 27427 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 __kud9E)^F9E$Iq20|RZI$v}Vi;~e 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 Y6P5xta$qZ|rvLx|07*qoM6N<$g7hL_S^xk5 literal 0 HcmV?d00001 diff --git a/package.json b/package.json index 49f9373..438f0c9 100644 --- a/package.json +++ b/package.json @@ -2,11 +2,11 @@ "name": "vscode-mc-shader", "displayName": "Minecraft GLSL Shaders", "description": "A Visual Studio Code extension for linting/etc Minecraft GLSL Shaders", - "version": "0.9.4", + "version": "0.9.5", "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", - "icon": "logo.png", + "icon": "logo-mini.png", "repository": { "url": "https://github.com/Strum355/vscode-mc-shader" }, diff --git a/server/Cargo.lock b/server/Cargo.lock index d8c8f0a..5e8225a 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -1,5 +1,7 @@ # This file is automatically @generated by Cargo. # It is not intended for manual editing. +version = 3 + [[package]] name = "ab_glyph_rasterizer" version = "0.1.4" @@ -701,7 +703,7 @@ checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" [[package]] name = "mcshader-lsp" -version = "0.9.4" +version = "0.9.5" dependencies = [ "anyhow", "bit-set", diff --git a/server/Cargo.toml b/server/Cargo.toml index 3179c42..cf34f9e 100644 --- a/server/Cargo.toml +++ b/server/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mcshader-lsp" -version = "0.9.4" +version = "0.9.5" authors = ["Noah Santschi-Cooney "] edition = "2018" From db5e5afb26d14379f5d5a6aca3e2487277f84c1e Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 5 Mar 2021 17:26:51 +0000 Subject: [PATCH 10/56] compute shader support apparently? not tested pls no bulli --- server/src/main.rs | 35 +++++++++++++++++++++++++---------- server/src/opengl.rs | 5 +++++ 2 files changed, 30 insertions(+), 10 deletions(-) diff --git a/server/src/main.rs b/server/src/main.rs index f334e73..01a00c9 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -111,7 +111,7 @@ impl Display for IncludePosition { } pub enum TreeType { - Fragment, Vertex, Geometry + Fragment, Vertex, Geometry, Compute } impl MinecraftShaderLanguageServer { @@ -290,15 +290,24 @@ impl MinecraftShaderLanguageServer { merge_views::generate_merge_list(&tree, &all_sources, &graph) }; - let root_path = self.graph.borrow().get_node(root).clone(); - let tree_type = if root_path.extension().unwrap() == "fsh" { + let root_path = self.graph.borrow().get_node(root); + let ext = match root_path.extension() { + Some(ext) => ext, + None => { + back_fill(&all_sources, &mut diagnostics); + return Ok(diagnostics) + }, + }; + let tree_type = if ext == "fsh" { TreeType::Fragment - } else if root_path.extension().unwrap() == "vsh" { + } else if ext == "vsh" { TreeType::Vertex - } else if root_path.extension().unwrap() == "gsh" { + } else if ext == "gsh" { TreeType::Geometry + } else if ext == "csh" { + TreeType::Compute } else { - eprintln!("got a non fsh|vsh ({:?}) as a file root ancestor: {:?}", root_path.extension().unwrap(), root_path); + eprintln!("got a non fsh|vsh|gsh|csh ({:?}) as a file root ancestor: {:?}", ext, root_path); back_fill(&all_sources, &mut diagnostics); return Ok(diagnostics) }; @@ -325,14 +334,20 @@ impl MinecraftShaderLanguageServer { }; let root_path = self.graph.borrow().get_node(*root).clone(); - let tree_type = if root_path.extension().unwrap() == "fsh" { + let ext = match root_path.extension() { + Some(ext) => ext, + None => continue + }; + let tree_type = if ext == "fsh" { TreeType::Fragment - } else if root_path.extension().unwrap() == "vsh" { + } else if ext == "vsh" { TreeType::Vertex - } else if root_path.extension().unwrap() == "gsh" { + } else if ext == "gsh" { TreeType::Geometry + } else if ext == "csh" { + TreeType::Compute } else { - eprintln!("got a non fsh|vsh ({:?}) as a file root ancestor: {:?}", root_path.extension().unwrap(), root_path); + eprintln!("got a non fsh|vsh|gsh|csh ({:?}) as a file root ancestor: {:?}", ext, root_path); continue; }; diff --git a/server/src/opengl.rs b/server/src/opengl.rs index a78936f..09468dc 100644 --- a/server/src/opengl.rs +++ b/server/src/opengl.rs @@ -78,6 +78,11 @@ impl ShaderValidator for OpenGLContext { let geometry_shader = gl::CreateShader(gl::GEOMETRY_SHADER); self.compile_and_get_shader_log(geometry_shader, source) } + crate::TreeType::Compute => { + // Compute shader + let compute_shader= gl::CreateShader(gl::COMPUTE_SHADER); + self.compile_and_get_shader_log(compute_shader, source) + } } } } From c7d8b02ee319f24657adfa0646156554be6fad01 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 5 Mar 2021 17:48:55 +0000 Subject: [PATCH 11/56] fixed all lint warnings --- server/src/commands.rs | 16 ++++++------ server/src/dfs.rs | 18 +++++++------- server/src/graph.rs | 15 ++++++------ server/src/main.rs | 51 ++++++++++++++++++--------------------- server/src/merge_views.rs | 16 ++++++------ server/src/opengl.rs | 11 +++++---- server/src/test.rs | 2 +- server/src/url_norm.rs | 4 +-- 8 files changed, 66 insertions(+), 67 deletions(-) diff --git a/server/src/commands.rs b/server/src/commands.rs index 3090f4e..890e4cb 100644 --- a/server/src/commands.rs +++ b/server/src/commands.rs @@ -1,4 +1,4 @@ -use std::{collections::HashMap, path::PathBuf}; +use std::{collections::HashMap, path::{Path, PathBuf}}; use std::rc::Rc; use std::cell::RefCell; use std::fs::OpenOptions; @@ -12,7 +12,7 @@ use anyhow::{Result, format_err}; use std::fs; -use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJSON}; +use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJson}; use crate::dfs; pub struct CustomCommandProvider { @@ -28,7 +28,7 @@ impl CustomCommandProvider { } } - pub fn execute(&self, command: &str, args: Vec, root_path: &PathBuf) -> Result { + pub fn execute(&self, command: &str, args: Vec, root_path: &Path) -> Result { if self.commands.contains_key(command) { return self.commands.get(command).unwrap().run_command(root_path, args); } @@ -37,7 +37,7 @@ impl CustomCommandProvider { } pub trait Invokeable { - fn run_command(&self, root: &PathBuf, arguments: Vec) -> Result; + fn run_command(&self, root: &Path, arguments: Vec) -> Result; } pub struct GraphDotCommand { @@ -45,7 +45,7 @@ pub struct GraphDotCommand { } impl Invokeable for GraphDotCommand { - fn run_command(&self, root: &PathBuf, _: Vec) -> Result { + fn run_command(&self, root: &Path, _: Vec) -> Result { let filepath = root.join("graph.dot"); eprintln!("generating dot file at {:?}", filepath); let mut file = OpenOptions::new() @@ -78,7 +78,7 @@ pub struct VirtualMergedDocument { impl VirtualMergedDocument { // TODO: DUPLICATE CODE - fn get_file_toplevel_ancestors(&self, uri: &PathBuf) -> Result>> { + fn get_file_toplevel_ancestors(&self, uri: &Path) -> Result>> { let curr_node = match self.graph.borrow_mut().find_node(uri) { Some(n) => n, None => return Err(format_err!("node not found {:?}", uri)), @@ -113,7 +113,7 @@ impl VirtualMergedDocument { Ok(s) => s, Err(e) => return Err(format_err!("error reading {:?}: {}", path, e)) }; - let source = crate::RE_CRLF.replace_all(&source, "\n").to_string(); + let source = source.replace("\r\n", "\n"); sources.insert(path.clone(), source); } @@ -122,7 +122,7 @@ impl VirtualMergedDocument { } impl Invokeable for VirtualMergedDocument { - fn run_command(&self, root: &PathBuf, arguments: Vec) -> Result { + fn run_command(&self, root: &Path, arguments: Vec) -> Result { let path = PathBuf::from_json(arguments.get(0).unwrap())?; let file_ancestors = match self.get_file_toplevel_ancestors(&path) { diff --git a/server/src/dfs.rs b/server/src/dfs.rs index dc62798..b296bd8 100644 --- a/server/src/dfs.rs +++ b/server/src/dfs.rs @@ -114,8 +114,8 @@ pub mod error { impl CycleError { pub fn new(nodes: &[NodeIndex], current_node: NodeIndex, graph: &CachedStableGraph) -> Self { - let mut resolved_nodes: Vec = nodes.iter().map(|i| graph.get_node(*i).clone()).collect(); - resolved_nodes.push(graph.get_node(current_node).clone()); + let mut resolved_nodes: Vec = nodes.iter().map(|i| graph.get_node(*i)).collect(); + resolved_nodes.push(graph.get_node(current_node)); CycleError(resolved_nodes) } } @@ -132,13 +132,13 @@ pub mod error { } } - impl Into for CycleError { - fn into(self) -> Diagnostic { + impl From for Diagnostic { + fn from(e: CycleError) -> Diagnostic { Diagnostic{ severity: Some(DiagnosticSeverity::Error), range: Range::new(Position::new(0, 0), Position::new(0, 500)), source: Some(consts::SOURCE.into()), - message: self.into(), + message: e.into(), code: None, tags: None, related_information: None, @@ -147,10 +147,10 @@ pub mod error { } } } - - impl Into for CycleError { - fn into(self) -> String { - format!("{}", self) + + impl From for String { + fn from(e: CycleError) -> String { + format!("{}", e) } } } \ No newline at end of file diff --git a/server/src/graph.rs b/server/src/graph.rs index b5a79bf..dd6fa26 100644 --- a/server/src/graph.rs +++ b/server/src/graph.rs @@ -3,7 +3,7 @@ use petgraph::stable_graph::NodeIndex; use petgraph::Direction; use petgraph::stable_graph::EdgeIndex; -use std::{collections::{HashMap, HashSet}, path::PathBuf, str::FromStr}; +use std::{collections::{HashMap, HashSet}, path::{Path, PathBuf}, str::FromStr}; use super::IncludePosition; @@ -21,6 +21,7 @@ pub struct CachedStableGraph { } impl CachedStableGraph { + #[allow(clippy::new_without_default)] pub fn new() -> CachedStableGraph { CachedStableGraph{ graph: StableDiGraph::new(), @@ -33,13 +34,13 @@ impl CachedStableGraph { /// and caches the result in the `HashMap`. Complexity is **O(1)** if the value /// is cached (which should always be the case), else **O(n)** where **n** is /// the number of node indices, as an exhaustive search must be done. - pub fn find_node(&mut self, name: &PathBuf) -> Option { + pub fn find_node(&mut self, name: &Path) -> Option { match self.cache.get(name) { Some(n) => Some(*n), None => { // If the string is not in cache, O(n) search the graph (i know...) and then cache the NodeIndex // for later - let n = self.graph.node_indices().find(|n| self.graph[*n] == name.to_str().unwrap().to_string()); + let n = self.graph.node_indices().find(|n| self.graph[*n] == name.to_str().unwrap()); if let Some(n) = n { self.cache.insert(name.into(), n); } @@ -57,20 +58,20 @@ impl CachedStableGraph { } #[allow(dead_code)] - pub fn remove_node(&mut self, name: &PathBuf) { + pub fn remove_node(&mut self, name: &Path) { let idx = self.cache.remove(name); if let Some(idx) = idx { self.graph.remove_node(idx); } } - pub fn add_node(&mut self, name: &PathBuf) -> NodeIndex { + pub fn add_node(&mut self, name: &Path) -> NodeIndex { if let Some(idx) = self.cache.get(name) { return *idx; } let idx = self.graph.add_node(name.to_str().unwrap().to_string()); - self.cache.insert(name.clone(), idx); - self.reverse_index.insert(idx, name.clone()); + self.cache.insert(name.to_owned(), idx); + self.reverse_index.insert(idx, name.to_owned()); idx } diff --git a/server/src/main.rs b/server/src/main.rs index 01a00c9..e7d91f4 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -8,7 +8,7 @@ use serde_json::Value; use url_norm::FromUrl; use walkdir::WalkDir; -use std::{cell::RefCell, path::PathBuf, str::FromStr}; +use std::{cell::RefCell, path::{Path, PathBuf}, str::FromStr}; use std::collections::{HashMap, HashSet}; use std::collections::hash_map::RandomState; use std::convert::TryFrom; @@ -45,7 +45,6 @@ lazy_static! { static ref RE_VERSION: Regex = Regex::new(r#"#version [\d]{3}"#).unwrap(); static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); static ref RE_INCLUDE_EXTENSION: Regex = Regex::new(r#"#extension GL_GOOGLE_include_directive ?: ?require"#).unwrap(); - pub static ref RE_CRLF: Regex = Regex::new(r#"\r\n"#).unwrap(); } fn main() { @@ -61,7 +60,7 @@ fn main() { wait: WaitGroup::new(), root: "".into(), command_provider: None, - opengl_context: Rc::new(opengl::OpenGLContext::new()) + opengl_context: Rc::new(opengl::OpenGlContext::new()) }; langserver.command_provider = Some(commands::CustomCommandProvider::new(vec![ @@ -158,7 +157,7 @@ impl MinecraftShaderLanguageServer { eprintln!("finished building project include graph"); } - fn add_file_and_includes_to_graph(&self, path: &PathBuf) { + fn add_file_and_includes_to_graph(&self, path: &Path) { let includes = self.find_includes(path); let idx = self.graph.borrow_mut().add_node(&path); @@ -174,7 +173,7 @@ impl MinecraftShaderLanguageServer { self.graph.borrow_mut().add_edge(node, child, include.1); } - pub fn find_includes(&self, file: &PathBuf) -> Vec<(PathBuf, IncludePosition)> { + pub fn find_includes(&self, file: &Path) -> Vec<(PathBuf, IncludePosition)> { let mut includes = Vec::default(); let buf = BufReader::new(std::fs::File::open(file).unwrap()); @@ -217,7 +216,7 @@ impl MinecraftShaderLanguageServer { includes } - fn update_includes(&self, file: &PathBuf) { + fn update_includes(&self, file: &Path) { let includes = self.find_includes(file); eprintln!("updating {:?} with {:?}", file, includes); @@ -230,7 +229,7 @@ impl MinecraftShaderLanguageServer { }; let prev_children: HashSet<_, RandomState> = HashSet::from_iter(self.graph.borrow().child_node_meta(idx)); - let new_children: HashSet<_, RandomState> = HashSet::from_iter(includes.iter().map(|e| e.clone())); + let new_children: HashSet<_, RandomState> = includes.iter().cloned().collect(); let to_be_added = new_children.difference(&prev_children); let to_be_removed = prev_children.difference(&new_children); @@ -247,7 +246,7 @@ impl MinecraftShaderLanguageServer { } } - pub fn lint(&self, uri: &PathBuf) -> Result>> { + pub fn lint(&self, uri: &Path) -> Result>> { // get all top level ancestors of this file let file_ancestors = match self.get_file_toplevel_ancestors(uri) { Ok(opt) => match opt { @@ -259,14 +258,14 @@ impl MinecraftShaderLanguageServer { eprintln!("ancestors for {:?}:\n\t{:?}", uri, file_ancestors.iter().map(|e| PathBuf::from_str(&self.graph.borrow().graph.node_weight(*e).unwrap().clone()).unwrap()).collect::>()); - // the set of all filepath->content. TODO: change to Url? + // the set of all filepath->content. let mut all_sources: HashMap = HashMap::new(); // the set of filepath->list of diagnostics to report let mut diagnostics: HashMap> = HashMap::new(); // we want to backfill the diagnostics map with all linked sources - let back_fill = |all_sources, diagnostics: &mut HashMap>| { - for (path, _) in all_sources { + let back_fill = |all_sources: &HashMap, diagnostics: &mut HashMap>| { + for path in all_sources.keys() { diagnostics.entry(Url::from_file_path(path).unwrap()).or_default(); } }; @@ -374,7 +373,7 @@ impl MinecraftShaderLanguageServer { Ok(diagnostics) } - fn parse_validator_stdout(&self, uri: &PathBuf, stdout: String, _source: &str) -> HashMap> { + fn parse_validator_stdout(&self, uri: &Path, stdout: String, _source: &str) -> HashMap> { let stdout_lines = stdout.split('\n'); let mut diagnostics: HashMap> = HashMap::with_capacity(stdout_lines.count()); let stdout_lines = stdout.split('\n'); @@ -390,10 +389,7 @@ impl MinecraftShaderLanguageServer { let msg = diagnostic_capture.name("output").unwrap().as_str(); let line = match diagnostic_capture.name("linenum") { - Some(c) => match c.as_str().parse::() { - Ok(i) => i, - Err(_) => 0, - }, + Some(c) => c.as_str().parse::().unwrap_or(0), None => 0, } - 2; @@ -412,7 +408,7 @@ impl MinecraftShaderLanguageServer { let origin = match diagnostic_capture.name("filepath") { Some(o) => { - if o.as_str().to_string() == "0" { + if o.as_str() == "0" { uri.to_str().unwrap().to_string() } else { o.as_str().to_string() @@ -472,14 +468,14 @@ impl MinecraftShaderLanguageServer { Ok(s) => s, Err(e) => return Err(anyhow!("error reading {:?}: {}", path, e)) }; - let source = RE_CRLF.replace_all(&source, "\n").to_string(); + let source = source.replace("\r\n", "\n"); sources.insert(path.clone(), source); } Ok(sources) } - fn get_file_toplevel_ancestors(&self, uri: &PathBuf) -> Result>> { + fn get_file_toplevel_ancestors(&self, uri: &Path) -> Result>> { let curr_node = match self.graph.borrow_mut().find_node(uri) { Some(n) => n, None => return Err(anyhow!("node not found {:?}", uri)), @@ -515,21 +511,20 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn initialize(&mut self, params: InitializeParams, completable: MethodCompletable) { self.wait.add(1); - let mut capabilities = ServerCapabilities::default(); - capabilities.hover_provider = None; - capabilities.document_link_provider = Some(DocumentLinkOptions { + let capabilities = ServerCapabilities{ + document_link_provider: Some(DocumentLinkOptions { resolve_provider: None, work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None, }, - }); - capabilities.execute_command_provider = Some(ExecuteCommandOptions { + }), + execute_command_provider: Some(ExecuteCommandOptions { commands: vec!["graphDot".into()], work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None, }, - }); - capabilities.text_document_sync = Some(TextDocumentSyncCapability::Options( + }), + text_document_sync: Some(TextDocumentSyncCapability::Options( TextDocumentSyncOptions { open_close: Some(true), will_save: None, @@ -539,7 +534,9 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { include_text: Some(true), })) }, - )); + )), + .. ServerCapabilities::default() + }; let root = match params.root_uri { Some(uri) => PathBuf::from_url(uri), diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index 9666de6..a6c70e2 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -1,4 +1,4 @@ -use std::{collections::{HashMap, LinkedList, VecDeque}, path::PathBuf}; +use std::{collections::{HashMap, LinkedList, VecDeque}, path::{Path, PathBuf}}; use std::iter::Peekable; use std::cmp::min; @@ -16,7 +16,7 @@ struct FilialTuple(Option, NodeIndex); impl From<(Option<&NodeIndex>, NodeIndex)> for FilialTuple { fn from(tuple: (Option<&NodeIndex>, NodeIndex)) -> Self { - FilialTuple(tuple.0.and_then(|n| Some(*n)), tuple.1) + FilialTuple(tuple.0.copied(), tuple.1) } } @@ -103,7 +103,7 @@ fn create_merge_views<'a>( let child_source = sources.get(&child_path).unwrap(); // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad let offset = { - match child_source.ends_with("\n") { + match child_source.ends_with('\n') { true => child_source.len()-1, false => child_source.len(), } @@ -127,7 +127,7 @@ fn create_merge_views<'a>( let child_source = sources.get(&child_path).unwrap(); // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 let end_offset = { - match child_source.ends_with("\n") { + match child_source.ends_with('\n') { true => 1/* child_source.len()-1 */, false => 0/* child_source.len() */, } @@ -150,7 +150,7 @@ fn create_merge_views<'a>( let child_source = sources.get(&child_path).unwrap(); // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad let offset = { - match child_source.ends_with("\n") { + match child_source.ends_with('\n') { true => child_source.len()-1, false => child_source.len(), } @@ -180,13 +180,13 @@ fn char_offset_for_line(line_num: usize, source: &str) -> (usize, usize) { (char_for_line, char_following_line) } -fn add_opening_line_directive(path: &PathBuf, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { +fn add_opening_line_directive(path: &Path, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { let line_directive = format!("#line 1 \"{}\"\n", path.to_str().unwrap().replace("\\", "\\\\")); line_directives.push(line_directive); unsafe_get_and_insert(merge_list, line_directives); } -fn add_closing_line_directive(line: usize, path: &PathBuf, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { +fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { // Optifine doesn't seem to add a leading newline if the previous line was a #line directive let line_directive = if let Some(l) = merge_list.back() { if l.trim().starts_with("#line") { @@ -202,7 +202,7 @@ fn add_closing_line_directive(line: usize, path: &PathBuf, merge_list: &mut Link unsafe_get_and_insert(merge_list, line_directives); } -fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, line_directives: &Vec) { +fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, line_directives: &[String]) { // :^) unsafe { let vec_ptr_offset = line_directives.as_ptr().add(line_directives.len()-1); diff --git a/server/src/opengl.rs b/server/src/opengl.rs index 09468dc..13cca4a 100644 --- a/server/src/opengl.rs +++ b/server/src/opengl.rs @@ -3,17 +3,18 @@ use std::ffi::{CString, CStr}; #[cfg(test)] use mockall::automock; + #[cfg_attr(test, automock)] pub trait ShaderValidator { fn validate(&self, tree_type: super::TreeType, source: String) -> Option; } -pub struct OpenGLContext { +pub struct OpenGlContext { _ctx: glutin::Context } -impl OpenGLContext { - pub fn new() -> OpenGLContext { +impl OpenGlContext { + pub fn new() -> OpenGlContext { let events_loop = glutin::event_loop::EventLoop::new(); let gl_window = glutin::ContextBuilder::new().build_headless(&*events_loop, glutin::dpi::PhysicalSize::new(1, 1)).unwrap(); @@ -31,7 +32,7 @@ impl OpenGLContext { String::from_utf8(CStr::from_ptr(gl::GetString(gl::RENDERER) as *const _).to_bytes().to_vec()).unwrap() ); } - OpenGLContext{ + OpenGlContext{ _ctx: gl_window, } } @@ -59,7 +60,7 @@ impl OpenGLContext { } } -impl ShaderValidator for OpenGLContext { +impl ShaderValidator for OpenGlContext { fn validate(&self, tree_type: super::TreeType, source: String) -> Option { unsafe { match tree_type { diff --git a/server/src/test.rs b/server/src/test.rs index c07cb2e..9105cd7 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -89,7 +89,7 @@ fn test_empty_initialize() { let initialize_params = InitializeParams { process_id: None, root_path: None, - root_uri: Some(Url::from_directory_path(tmp_path.clone()).unwrap()), + root_uri: Some(Url::from_directory_path(tmp_path).unwrap()), client_info: None, initialization_options: None, capabilities: ClientCapabilities { diff --git a/server/src/url_norm.rs b/server/src/url_norm.rs index 276c8a3..adc0993 100644 --- a/server/src/url_norm.rs +++ b/server/src/url_norm.rs @@ -8,7 +8,7 @@ pub trait FromUrl { fn from_url(u: Url) -> Self; } -pub trait FromJSON { +pub trait FromJson { fn from_json(v: &serde_json::value::Value) -> Result where Self: Sized; } @@ -26,7 +26,7 @@ impl FromUrl for PathBuf { } } -impl FromJSON for PathBuf { +impl FromJson for PathBuf { #[cfg(target_family = "windows")] fn from_json(v: &serde_json::value::Value) -> Result where Self: Sized { From 734f0b014bc965e98aa83a4603e237cb939dd9f6 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 2 Jan 2022 21:57:07 +0000 Subject: [PATCH 12/56] attempt #1 for M1 Mac build --- .github/workflows/release.yml | 7 +++++-- .github/workflows/server.yml | 28 ++++++++++++++++++++++++---- 2 files changed, 29 insertions(+), 6 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index a15ea1d..c19d649 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -38,9 +38,12 @@ jobs: - os: windows-latest target: x86_64-windows-msvc.exe dir: server/mcshader-lsp.exe - - os: macos-10.15 + - os: macos-11 target: x86_64-apple-darwin dir: server/mcshader-lsp + - os: macos-11 + target: aarch64-apple-darwin + dir: server/mcshader-lsp steps: - uses: actions/checkout@v2 - name: Install latest nightly @@ -49,7 +52,7 @@ jobs: toolchain: nightly default: true - name: Build server - run: cargo build --release --out-dir . -Z unstable-options + run: cargo build --release --target ${{ matrix.platforms.target }} --out-dir . -Z unstable-options - name: Upload release file uses: actions/upload-release-asset@v1 env: diff --git a/.github/workflows/server.yml b/.github/workflows/server.yml index d9e762f..5cdc3a3 100644 --- a/.github/workflows/server.yml +++ b/.github/workflows/server.yml @@ -8,16 +8,36 @@ env: CARGO_TERM_COLOR: always jobs: build-and-test: - runs-on: ${{ matrix.os }} + runs-on: ${{ matrix.platforms.os }} defaults: run: working-directory: server strategy: matrix: - os: [ ubuntu-20.04, windows-latest, macos-10.15 ] + platforms: + - os: ubuntu-18.04 + target: x86_64-unknown-linux-gnu + dir: server/mcshader-lsp + artifact: x86_64-linux-mcshader-lsp + - os: windows-latest + target: x86_64-windows-msvc.exe + dir: server/mcshader-lsp.exe + artifact: x86_64-windows-mcshader-lsp.exe + - os: macos-11 + target: x86_64-apple-darwin + dir: server/mcshader-lsp + artifact: x86_64-darwin-mcshader-lsp + - os: macos-11 + target: aarch64-apple-darwin + dir: server/mcshader-lsp + artifact: aarch64-darwin-mcshader-lsp steps: - uses: actions/checkout@v2 - name: Build server - run: cargo build + run: cargo build --target ${{ matrix.platforms.target }} + - uses: actions/upload-artifact@v2 + with: + name: ${{ matrix.platforms.artifact }} + path: ${{ matrix.platforms.dir }} - name: Run tests - run: cargo test + run: cargo test --target ${{ matrix.platforms.target }} From 65422c863f06761bad4cb990094a9a432727a159 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 2 Jan 2022 21:59:44 +0000 Subject: [PATCH 13/56] fix failed compile in https://github.com/Strum355/mcshader-lsp/runs/3884126697 --- server/src/test.rs | 84 +++++++++++++++++++++++----------------------- 1 file changed, 42 insertions(+), 42 deletions(-) diff --git a/server/src/test.rs b/server/src/test.rs index 9105cd7..3c900b2 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -273,8 +273,8 @@ fn test_05_initialize() { fn test_graph_two_connected_nodes() { let mut graph = graph::CachedStableGraph::new(); - let idx1 = graph.add_node(&("sample".to_string().into())); - let idx2 = graph.add_node(&("banana".to_string().into())); + let idx1 = graph.add_node(&PathBuf::from("sample")); + let idx2 = graph.add_node(&PathBuf::from("banana")); graph.add_edge( idx1, idx2, @@ -311,9 +311,9 @@ fn test_graph_two_connected_nodes() { let ancestors = graph.collect_root_ancestors(idx1); assert_eq!(ancestors.len(), 0); - graph.remove_node(&("sample".to_string().into())); + graph.remove_node(&PathBuf::from("sample")); assert_eq!(graph.graph.node_count(), 1); - assert!(graph.find_node(&("sample".to_string().into())).is_none()); + assert!(graph.find_node(&PathBuf::from("sample")).is_none()); let neighbors = graph.child_node_names(idx2); assert_eq!(neighbors.len(), 0); } @@ -323,10 +323,10 @@ fn test_collect_root_ancestors() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); graph.add_edge( idx0, @@ -377,10 +377,10 @@ fn test_collect_root_ancestors() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); graph.add_edge( idx0, @@ -431,10 +431,10 @@ fn test_collect_root_ancestors() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); graph.add_edge( idx0, @@ -487,10 +487,10 @@ fn test_collect_root_ancestors() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); graph.add_edge( idx0, @@ -545,10 +545,10 @@ fn test_graph_dfs() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); graph.add_edge( idx0, @@ -607,14 +607,14 @@ fn test_graph_dfs() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); - let idx4 = graph.add_node(&("4".to_string().into())); - let idx5 = graph.add_node(&("5".to_string().into())); - let idx6 = graph.add_node(&("6".to_string().into())); - let idx7 = graph.add_node(&("7".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + let idx4 = graph.add_node(&PathBuf::from("4")); + let idx5 = graph.add_node(&PathBuf::from("5")); + let idx6 = graph.add_node(&PathBuf::from("6")); + let idx7 = graph.add_node(&PathBuf::from("7")); graph.add_edge( idx0, @@ -749,14 +749,14 @@ fn test_graph_dfs_cycle() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); - let idx2 = graph.add_node(&("2".to_string().into())); - let idx3 = graph.add_node(&("3".to_string().into())); - let idx4 = graph.add_node(&("4".to_string().into())); - let idx5 = graph.add_node(&("5".to_string().into())); - let idx6 = graph.add_node(&("6".to_string().into())); - let idx7 = graph.add_node(&("7".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + let idx4 = graph.add_node(&PathBuf::from("4")); + let idx5 = graph.add_node(&PathBuf::from("5")); + let idx6 = graph.add_node(&PathBuf::from("6")); + let idx7 = graph.add_node(&PathBuf::from("7")); graph.add_edge( idx0, @@ -873,8 +873,8 @@ fn test_graph_dfs_cycle() { { let mut graph = graph::CachedStableGraph::new(); - let idx0 = graph.add_node(&("0".to_string().into())); - let idx1 = graph.add_node(&("1".to_string().into())); + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); graph.add_edge( idx0, From 5fd02b06f4123a5b1e28f6082112f2ef5f6f559f Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 2 Jan 2022 22:06:28 +0000 Subject: [PATCH 14/56] attempt #2 for M1 Mac build: correct targets edition --- .github/workflows/release.yml | 8 ++++++-- .github/workflows/server.yml | 12 ++++++------ 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index c19d649..bae3792 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -34,15 +34,19 @@ jobs: platforms: - os: ubuntu-18.04 target: x86_64-unknown-linux-gnu + artifact: x86_64-unknown-linux-gnu dir: server/mcshader-lsp - os: windows-latest - target: x86_64-windows-msvc.exe + target: x86_64-pc-windows-msvc + artifact: x86_64-windows-msvc.exe dir: server/mcshader-lsp.exe - os: macos-11 target: x86_64-apple-darwin + artifact: x86_64-apple-darwin dir: server/mcshader-lsp - os: macos-11 target: aarch64-apple-darwin + artifact: aarch64-apple-darwin dir: server/mcshader-lsp steps: - uses: actions/checkout@v2 @@ -60,7 +64,7 @@ jobs: with: upload_url: ${{ needs.empty-release.outputs.upload_url }} asset_path: ${{ matrix.platforms.dir }} - asset_name: mcshader-lsp-${{ matrix.platforms.target }} + asset_name: mcshader-lsp-${{ matrix.platforms.artifact }} asset_content_type: application/octet-stream release-vscode-extension: runs-on: ubuntu-20.04 diff --git a/.github/workflows/server.yml b/.github/workflows/server.yml index 5cdc3a3..a371720 100644 --- a/.github/workflows/server.yml +++ b/.github/workflows/server.yml @@ -18,26 +18,26 @@ jobs: - os: ubuntu-18.04 target: x86_64-unknown-linux-gnu dir: server/mcshader-lsp - artifact: x86_64-linux-mcshader-lsp + artifact: x86_64-unknown-linux-gnu - os: windows-latest - target: x86_64-windows-msvc.exe + target: x86_64-pc-windows-msvc dir: server/mcshader-lsp.exe - artifact: x86_64-windows-mcshader-lsp.exe + artifact: x86_64-windows-msvc.exe - os: macos-11 target: x86_64-apple-darwin dir: server/mcshader-lsp - artifact: x86_64-darwin-mcshader-lsp + artifact: x86_64-apple-darwin - os: macos-11 target: aarch64-apple-darwin dir: server/mcshader-lsp - artifact: aarch64-darwin-mcshader-lsp + artifact: aarch64-apple-darwin steps: - uses: actions/checkout@v2 - name: Build server run: cargo build --target ${{ matrix.platforms.target }} - uses: actions/upload-artifact@v2 with: - name: ${{ matrix.platforms.artifact }} + name: mcshader-lsp-${{ matrix.platforms.artifact }} path: ${{ matrix.platforms.dir }} - name: Run tests run: cargo test --target ${{ matrix.platforms.target }} From 57f4b7924bbb3b121f9fd108fcacbe8ddd010aee Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 2 Jan 2022 22:15:21 +0000 Subject: [PATCH 15/56] attempt #3 for M1 Mac build: rust toolchains target edition --- .github/workflows/server.yml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.github/workflows/server.yml b/.github/workflows/server.yml index a371720..ca3bc87 100644 --- a/.github/workflows/server.yml +++ b/.github/workflows/server.yml @@ -33,6 +33,13 @@ jobs: artifact: aarch64-apple-darwin steps: - uses: actions/checkout@v2 + - name: Install latest nightly + uses: actions-rs/toolchain@v1 + with: + toolchain: nightly + default: true + target: ${{ matrix.platforms.target }} + override: true - name: Build server run: cargo build --target ${{ matrix.platforms.target }} - uses: actions/upload-artifact@v2 From 5747a9d9b1cce1ade18fe079a30b6dbf75d4f4b0 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 2 Jan 2022 22:30:24 +0000 Subject: [PATCH 16/56] attempt #4 for M1 Mac build: correct artifact path and skip M1 tests because not running on M1 machine --- .github/workflows/server.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/server.yml b/.github/workflows/server.yml index ca3bc87..8c3e4ee 100644 --- a/.github/workflows/server.yml +++ b/.github/workflows/server.yml @@ -41,10 +41,11 @@ jobs: target: ${{ matrix.platforms.target }} override: true - name: Build server - run: cargo build --target ${{ matrix.platforms.target }} + run: cargo build --target ${{ matrix.platforms.target }} --out-dir . -Z unstable-options - uses: actions/upload-artifact@v2 with: name: mcshader-lsp-${{ matrix.platforms.artifact }} path: ${{ matrix.platforms.dir }} - name: Run tests run: cargo test --target ${{ matrix.platforms.target }} + if: ${{ matrix.platforms.target != 'aarch64-apple-darwin' }} From 554777d0da021c860cc106ec408fd2d37b1ca7d2 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 2 Jan 2022 23:20:37 +0000 Subject: [PATCH 17/56] allow skipping bootstrap step and expose github actions extension build in CI on every push --- .github/workflows/extension.yml | 21 +++++++++++++++++++++ client/src/extension.ts | 7 ++++++- package.json | 10 ++++++++-- server/src/main.rs | 11 +---------- server/src/test.rs | 3 --- 5 files changed, 36 insertions(+), 16 deletions(-) create mode 100644 .github/workflows/extension.yml diff --git a/.github/workflows/extension.yml b/.github/workflows/extension.yml new file mode 100644 index 0000000..ad8ff4c --- /dev/null +++ b/.github/workflows/extension.yml @@ -0,0 +1,21 @@ +name: Build Extension +on: + push: + branches: [ rust-rewrite ] + pull_request: + branches: [ rust-rewrite ] +jobs: + build-vscode-extension: + runs-on: ubuntu-20.04 + steps: + - uses: actions/checkout@v2 + - run: npm i + - uses: HaaLeo/publish-vscode-extension@v0 + id: vsce_build + with: + pat: 'sample text' + dryRun: true + - uses: actions/upload-artifact@v2 + with: + name: vscode-mc-shader.vsix + path: ${{ steps.vsce_build.outputs.vsixPath }} \ No newline at end of file diff --git a/client/src/extension.ts b/client/src/extension.ts index 961c6e8..9845694 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -12,6 +12,7 @@ const platforms: { [key: string]: string } = { 'x64 win32': 'x86_64-windows-msvc', 'x64 linux': 'x86_64-unknown-linux-gnu', 'x64 darwin': 'x86_64-apple-darwin', + 'arm64 darwin': 'aarch64-apple-darwin' } export class Extension { @@ -38,7 +39,11 @@ export class Extension { this.extensionContext = context this.state = new PersistentState(context.globalState) - if(!process.env['MCSHADER_DEBUG']) await this.bootstrap() + if(!process.env['MCSHADER_DEBUG'] && !(vscode.workspace.getConfiguration('mcglsl').get('skipBootstrap') as boolean)) { + await this.bootstrap() + } else { + log.info('skipping language server bootstrap') + } this.registerCommand('graphDot', commands.generateGraphDot) this.registerCommand('restart', commands.restartExtension) diff --git a/package.json b/package.json index 438f0c9..4a4f2ed 100644 --- a/package.json +++ b/package.json @@ -8,7 +8,7 @@ "license": "MIT", "icon": "logo-mini.png", "repository": { - "url": "https://github.com/Strum355/vscode-mc-shader" + "url": "https://github.com/Strum355/mcshader-lsp" }, "engines": { "vscode": "^1.43.0" @@ -59,7 +59,13 @@ ], "configuration": { "title": "Minecraft GLSL Shaders", - "properties": {} + "properties": { + "mcglsl.skipBootstrap": { + "type": "boolean", + "default": false, + "description": "[DEBUG] Enable to skip bootstrapping the language server binary from Github. Set this to use a manually provided language server binary." + } + } } }, "scripts": { diff --git a/server/src/main.rs b/server/src/main.rs index e7d91f4..bc63b7a 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -22,8 +22,6 @@ use path_slash::PathBufExt; use anyhow::{Result, anyhow}; -use chan::WaitGroup; - use regex::Regex; use lazy_static::lazy_static; @@ -57,7 +55,6 @@ fn main() { let mut langserver = MinecraftShaderLanguageServer { endpoint: endpoint_output.clone(), graph: Rc::new(RefCell::new(cache_graph)), - wait: WaitGroup::new(), root: "".into(), command_provider: None, opengl_context: Rc::new(opengl::OpenGlContext::new()) @@ -84,7 +81,6 @@ fn main() { struct MinecraftShaderLanguageServer { endpoint: Endpoint, graph: Rc>, - wait: WaitGroup, root: PathBuf, command_provider: Option, opengl_context: Rc @@ -509,7 +505,7 @@ impl MinecraftShaderLanguageServer { impl LanguageServerHandling for MinecraftShaderLanguageServer { fn initialize(&mut self, params: InitializeParams, completable: MethodCompletable) { - self.wait.add(1); + let capabilities = ServerCapabilities{ document_link_provider: Some(DocumentLinkOptions { @@ -577,10 +573,6 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn workspace_change_configuration(&mut self, params: DidChangeConfigurationParams) { //let config = params.settings.as_object().unwrap().get("mcglsl").unwrap(); - - eprintln!("{:?}", params.settings.as_object().unwrap()); - - self.wait.done(); } fn did_open_text_document(&mut self, params: DidOpenTextDocumentParams) { @@ -628,7 +620,6 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { } fn hover(&mut self, _: TextDocumentPositionParams, _: LSCompletable) { - self.wait.wait(); /* completable.complete(Ok(Hover{ contents: HoverContents::Markup(MarkupContent{ kind: MarkupKind::Markdown, diff --git a/server/src/test.rs b/server/src/test.rs index 3c900b2..4c1075e 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -42,7 +42,6 @@ fn new_temp_server() -> MinecraftShaderLanguageServer { MinecraftShaderLanguageServer { endpoint, graph: Rc::new(RefCell::new(graph::CachedStableGraph::new())), - wait: WaitGroup::new(), root: "".into(), command_provider: None, opengl_context: Rc::new(opengl::MockShaderValidator::new()), @@ -126,8 +125,6 @@ fn test_empty_initialize() { assert_eq!(server.graph.borrow().graph.edge_count(), 0); assert_eq!(server.graph.borrow().graph.node_count(), 0); - assert_eq!(format!("{:?}", server.wait), "WaitGroup { count: 1 }"); - server.endpoint.request_shutdown(); } From cccb5e25f7845de8aa3cd275ebf478883c91bed6 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Mon, 14 Mar 2022 23:04:57 +0000 Subject: [PATCH 18/56] corporate shilling: add LSIF upload action --- .github/workflows/lsif.yml | 14 ++++++++++++++ 1 file changed, 14 insertions(+) create mode 100644 .github/workflows/lsif.yml diff --git a/.github/workflows/lsif.yml b/.github/workflows/lsif.yml new file mode 100644 index 0000000..1192789 --- /dev/null +++ b/.github/workflows/lsif.yml @@ -0,0 +1,14 @@ +name: LSIF +on: + - push +jobs: + index: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v2 + - name: Generate LSIF data + uses: sourcegraph/lsif-rust-action@main + - name: Upload LSIF data + uses: sourcegraph/lsif-upload-action@master + with: + github_token: ${{ secrets.GITHUB_TOKEN }} \ No newline at end of file From 79e107b748752602dd158206c765653ce928ee42 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Mon, 14 Mar 2022 23:06:58 +0000 Subject: [PATCH 19/56] add rustfmt configuration --- .rustfmt.toml | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 .rustfmt.toml diff --git a/.rustfmt.toml b/.rustfmt.toml new file mode 100644 index 0000000..0cb1099 --- /dev/null +++ b/.rustfmt.toml @@ -0,0 +1,3 @@ +edition = "2021" +fn_args_layout = "compressed" +max_width = 140 \ No newline at end of file From a8f00fe9272e876a689e0136fb547c1940e1712a Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Mon, 14 Mar 2022 23:12:40 +0000 Subject: [PATCH 20/56] npm: bump dependency versions --- client/package-lock.json | 1405 ++++++-- client/package.json | 20 +- client/rollup.config.js | 2 + package-lock.json | 6764 ++++++++++++++++++++++++++++---------- package.json | 28 +- 5 files changed, 6168 insertions(+), 2051 deletions(-) diff --git a/client/package-lock.json b/client/package-lock.json index cb94340..061ed07 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -1,314 +1,1095 @@ { - "name": "vscode-mc-shader-client", - "version": "0.0.1", - "lockfileVersion": 1, - "requires": true, - "dependencies": { - "@rollup/plugin-commonjs": { - "version": "17.1.0", - "resolved": "https://registry.npmjs.org/@rollup/plugin-commonjs/-/plugin-commonjs-17.1.0.tgz", - "integrity": "sha512-PoMdXCw0ZyvjpCMT5aV4nkL0QywxP29sODQsSGeDpr/oI49Qq9tRtAsb/LbYbDzFlOydVEqHmmZWFtXJEAX9ew==", - "requires": { - "@rollup/pluginutils": "^3.1.0", - "commondir": "^1.0.1", - "estree-walker": "^2.0.1", - "glob": "^7.1.6", - "is-reference": "^1.2.1", - "magic-string": "^0.25.7", - "resolve": "^1.17.0" - } - }, - "@rollup/plugin-node-resolve": { - "version": "11.1.1", - "resolved": "https://registry.npmjs.org/@rollup/plugin-node-resolve/-/plugin-node-resolve-11.1.1.tgz", - "integrity": "sha512-zlBXR4eRS+2m79TsUZWhsd0slrHUYdRx4JF+aVQm+MI0wsKdlpC2vlDVjmlGvtZY1vsefOT9w3JxvmWSBei+Lg==", - "requires": { - "@rollup/pluginutils": "^3.1.0", - "@types/resolve": "1.17.1", - "builtin-modules": "^3.1.0", - "deepmerge": "^4.2.2", - "is-module": "^1.0.0", - "resolve": "^1.19.0" - } - }, - "@rollup/pluginutils": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-3.1.0.tgz", - "integrity": "sha512-GksZ6pr6TpIjHm8h9lSQ8pi8BE9VeubNT0OMJ3B5uZJ8pz73NPiqOtCog/x2/QzM1ENChPKxMDhiQuRHsqc+lg==", - "requires": { - "@types/estree": "0.0.39", - "estree-walker": "^1.0.1", - "picomatch": "^2.2.2" - }, - "dependencies": { - "estree-walker": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-1.0.1.tgz", - "integrity": "sha512-1fMXF3YP4pZZVozF8j/ZLfvnR8NSIljt56UhbZ5PeeDmmGHpgpdwQt7ITlGvYaQukCvuBRMLEiKiYC+oeIg4cg==" - } - } - }, - "@types/adm-zip": { - "version": "0.4.32", - "resolved": "https://registry.npmjs.org/@types/adm-zip/-/adm-zip-0.4.32.tgz", - "integrity": "sha512-hv1O7ySn+XvP5OeDQcJFWwVb2v+GFGO1A9aMTQ5B/bzxb7WW21O8iRhVdsKKr8QwuiagzGmPP+gsUAYZ6bRddQ==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@types/estree": { - "version": "0.0.39", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.39.tgz", - "integrity": "sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==" - }, - "@types/node": { - "version": "13.7.1", - "resolved": "https://registry.npmjs.org/@types/node/-/node-13.7.1.tgz", - "integrity": "sha512-Zq8gcQGmn4txQEJeiXo/KiLpon8TzAl0kmKH4zdWctPj05nWwp1ClMdAVEloqrQKfaC48PNLdgN/aVaLqUrluA==" - }, - "@types/node-fetch": { - "version": "2.5.4", - "resolved": "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-2.5.4.tgz", - "integrity": "sha512-Oz6id++2qAOFuOlE1j0ouk1dzl3mmI1+qINPNBhi9nt/gVOz0G+13Ao6qjhdF0Ys+eOkhu6JnFmt38bR3H0POQ==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@types/resolve": { - "version": "1.17.1", - "resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.17.1.tgz", - "integrity": "sha512-yy7HuzQhj0dhGpD8RLXSZWEkLsV9ibvxvi6EiJ3bkqLAO1RGo0WbkWQiwpRlSFymTJRz0d3k5LM3kkx8ArDbLw==", - "requires": { - "@types/node": "*" - } - }, - "@types/vscode": { - "version": "1.47.0", - "resolved": "https://registry.npmjs.org/@types/vscode/-/vscode-1.47.0.tgz", - "integrity": "sha512-nJA37ykkz9FYA0ZOQUSc3OZnhuzEW2vUhUEo4MiduUo82jGwwcLfyvmgd/Q7b0WrZAAceojGhZybg319L24bTA==", - "dev": true - }, - "adm-zip": { - "version": "0.4.14", - "resolved": "https://registry.npmjs.org/adm-zip/-/adm-zip-0.4.14.tgz", - "integrity": "sha512-/9aQCnQHF+0IiCl0qhXoK7qs//SwYE7zX8lsr/DNk1BRAHYxeLZPL4pguwK29gUEqasYQjqPtEpDRSWEkdHn9g==" - }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" - }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "builtin-modules": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-3.2.0.tgz", - "integrity": "sha512-lGzLKcioL90C7wMczpkY0n/oART3MbBa8R9OFGE1rJxoVI86u4WAGfEk8Wjv10eKSyTHVGkSo3bvBylCEtk7LA==" - }, - "commondir": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", - "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=" - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "deepmerge": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", - "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==" - }, - "estree-walker": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", - "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==" - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "fsevents": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.1.3.tgz", - "integrity": "sha512-Auw9a4AxqWpa9GUfj370BMPzzyncfBABW8Mab7BGWBYDj4Isgq+cDKtx0i6u9jcX9pQDnswsaaOTgTmA5pEjuQ==", - "optional": true - }, - "function-bind": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", - "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" - }, - "glob": { - "version": "7.1.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", - "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "has": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", - "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", - "requires": { - "function-bind": "^1.1.1" - } - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" - }, - "is-core-module": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.2.0.tgz", - "integrity": "sha512-XRAfAdyyY5F5cOXn7hYQDqh2Xmii+DEfIcQGxK/uNwMHhIkPWO0g8msXcbzLe+MpGoR951MlqM/2iIlU4vKDdQ==", - "requires": { - "has": "^1.0.3" - } - }, - "is-module": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-module/-/is-module-1.0.0.tgz", - "integrity": "sha1-Mlj7afeMFNW4FdZkM2tM/7ZEFZE=" - }, - "is-reference": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/is-reference/-/is-reference-1.2.1.tgz", - "integrity": "sha512-U82MsXXiFIrjCK4otLT+o2NA2Cd2g5MLoOVXUZjIOhLurrRxpEXzI8O0KZHr3IjLvlAH1kTPYSuqer5T9ZVBKQ==", - "requires": { - "@types/estree": "*" - } - }, - "magic-string": { - "version": "0.25.7", - "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.7.tgz", - "integrity": "sha512-4CrMT5DOHTDk4HYDlzmwu4FVCcIYI8gauveasrdCu2IKIFOJ3f0v/8MDGJCDL9oD2ppz/Av1b0Nj345H9M+XIA==", - "requires": { - "sourcemap-codec": "^1.4.4" - } - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "node-fetch": { - "version": "2.6.0", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.0.tgz", - "integrity": "sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA==" - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "1" - } - }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" - }, - "path-parse": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", - "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" - }, - "picomatch": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.2.2.tgz", - "integrity": "sha512-q0M/9eZHzmr0AulXyPwNfZjtwZ/RBZlbN3K3CErVrk50T2ASYI7Bye0EvekFY3IP1Nt2DHu0re+V2ZHIpMkuWg==" - }, - "resolve": { - "version": "1.19.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.19.0.tgz", - "integrity": "sha512-rArEXAgsBG4UgRGcynxWIWKFvh/XZCcS8UJdHhwy91zwAvCZIbcs+vAbflgBnNjYMs/i/i+/Ux6IZhML1yPvxg==", - "requires": { - "is-core-module": "^2.1.0", - "path-parse": "^1.0.6" - } - }, - "rollup": { - "version": "2.38.1", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.38.1.tgz", - "integrity": "sha512-q07T6vU/V1kqM8rGRRyCgEvIQcIAXoKIE5CpkYAlHhfiWM1Iuh4dIPWpIbqFngCK6lwAB2aYHiUVhIbSWHQWhw==", - "requires": { - "fsevents": "~2.1.2" - } - }, - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - }, - "sourcemap-codec": { - "version": "1.4.8", - "resolved": "https://registry.npmjs.org/sourcemap-codec/-/sourcemap-codec-1.4.8.tgz", - "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==" - }, - "vscode-jsonrpc": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-5.0.1.tgz", - "integrity": "sha512-JvONPptw3GAQGXlVV2utDcHx0BiY34FupW/kI6mZ5x06ER5DdPG/tXWMVHjTNULF5uKPOUUD0SaXg5QaubJL0A==" - }, - "vscode-languageclient": { - "version": "6.1.3", - "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-6.1.3.tgz", - "integrity": "sha512-YciJxk08iU5LmWu7j5dUt9/1OLjokKET6rME3cI4BRpiF6HZlusm2ZwPt0MYJ0lV5y43sZsQHhyon2xBg4ZJVA==", - "requires": { - "semver": "^6.3.0", - "vscode-languageserver-protocol": "^3.15.3" - } - }, - "vscode-languageserver-protocol": { - "version": "3.15.3", - "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.3.tgz", - "integrity": "sha512-zrMuwHOAQRhjDSnflWdJG+O2ztMWss8GqUUB8dXLR/FPenwkiBNkMIJJYfSN6sgskvsF0rHAoBowNQfbyZnnvw==", - "requires": { - "vscode-jsonrpc": "^5.0.1", - "vscode-languageserver-types": "3.15.1" - } - }, - "vscode-languageserver-types": { - "version": "3.15.1", - "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.15.1.tgz", - "integrity": "sha512-+a9MPUQrNGRrGU630OGbYVQ+11iOIovjCkqxajPa9w57Sd5ruK8WQNsslzpa0x/QJqC8kRc2DUxWjIFwoNm4ZQ==" - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - } - } + "name": "vscode-mc-shader-client", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "name": "vscode-mc-shader-client", + "dependencies": { + "@rollup/plugin-json": "^4.1.0", + "adm-zip": "^0.5.9", + "encoding": "^0.1.13", + "node-fetch": "^3.2.3", + "vscode-languageclient": "^7.0.0" + }, + "devDependencies": { + "@rollup/plugin-commonjs": "^21.0.2", + "@rollup/plugin-node-resolve": "^13.1.3", + "@types/adm-zip": "^0.4.34", + "@types/node-fetch": "^2.6.1", + "@types/vscode": "^1.65.0", + "rollup": "^2.70.1" + } + }, + "node_modules/@rollup/plugin-commonjs": { + "version": "21.0.2", + "resolved": "https://registry.npmjs.org/@rollup/plugin-commonjs/-/plugin-commonjs-21.0.2.tgz", + "integrity": "sha512-d/OmjaLVO4j/aQX69bwpWPpbvI3TJkQuxoAk7BH8ew1PyoMBLTOuvJTjzG8oEoW7drIIqB0KCJtfFLu/2GClWg==", + "dev": true, + "dependencies": { + "@rollup/pluginutils": "^3.1.0", + "commondir": "^1.0.1", + "estree-walker": "^2.0.1", + "glob": "^7.1.6", + "is-reference": "^1.2.1", + "magic-string": "^0.25.7", + "resolve": "^1.17.0" + }, + "engines": { + "node": ">= 8.0.0" + }, + "peerDependencies": { + "rollup": "^2.38.3" + } + }, + "node_modules/@rollup/plugin-json": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/@rollup/plugin-json/-/plugin-json-4.1.0.tgz", + "integrity": "sha512-yfLbTdNS6amI/2OpmbiBoW12vngr5NW2jCJVZSBEz+H5KfUJZ2M7sDjk0U6GOOdCWFVScShte29o9NezJ53TPw==", + "dependencies": { + "@rollup/pluginutils": "^3.0.8" + }, + "peerDependencies": { + "rollup": "^1.20.0 || ^2.0.0" + } + }, + "node_modules/@rollup/plugin-node-resolve": { + "version": "13.1.3", + "resolved": "https://registry.npmjs.org/@rollup/plugin-node-resolve/-/plugin-node-resolve-13.1.3.tgz", + "integrity": "sha512-BdxNk+LtmElRo5d06MGY4zoepyrXX1tkzX2hrnPEZ53k78GuOMWLqmJDGIIOPwVRIFZrLQOo+Yr6KtCuLIA0AQ==", + "dev": true, + "dependencies": { + "@rollup/pluginutils": "^3.1.0", + "@types/resolve": "1.17.1", + "builtin-modules": "^3.1.0", + "deepmerge": "^4.2.2", + "is-module": "^1.0.0", + "resolve": "^1.19.0" + }, + "engines": { + "node": ">= 10.0.0" + }, + "peerDependencies": { + "rollup": "^2.42.0" + } + }, + "node_modules/@rollup/pluginutils": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-3.1.0.tgz", + "integrity": "sha512-GksZ6pr6TpIjHm8h9lSQ8pi8BE9VeubNT0OMJ3B5uZJ8pz73NPiqOtCog/x2/QzM1ENChPKxMDhiQuRHsqc+lg==", + "dependencies": { + "@types/estree": "0.0.39", + "estree-walker": "^1.0.1", + "picomatch": "^2.2.2" + }, + "engines": { + "node": ">= 8.0.0" + }, + "peerDependencies": { + "rollup": "^1.20.0||^2.0.0" + } + }, + "node_modules/@rollup/pluginutils/node_modules/estree-walker": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-1.0.1.tgz", + "integrity": "sha512-1fMXF3YP4pZZVozF8j/ZLfvnR8NSIljt56UhbZ5PeeDmmGHpgpdwQt7ITlGvYaQukCvuBRMLEiKiYC+oeIg4cg==" + }, + "node_modules/@types/adm-zip": { + "version": "0.4.34", + "resolved": "https://registry.npmjs.org/@types/adm-zip/-/adm-zip-0.4.34.tgz", + "integrity": "sha512-8ToYLLAYhkRfcmmljrKi22gT2pqu7hGMDtORP1emwIEGmgUTZOsaDjzWFzW5N2frcFRz/50CWt4zA1CxJ73pmQ==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/estree": { + "version": "0.0.39", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.39.tgz", + "integrity": "sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==" + }, + "node_modules/@types/node": { + "version": "13.7.1", + "resolved": "https://registry.npmjs.org/@types/node/-/node-13.7.1.tgz", + "integrity": "sha512-Zq8gcQGmn4txQEJeiXo/KiLpon8TzAl0kmKH4zdWctPj05nWwp1ClMdAVEloqrQKfaC48PNLdgN/aVaLqUrluA==", + "dev": true + }, + "node_modules/@types/node-fetch": { + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-2.6.1.tgz", + "integrity": "sha512-oMqjURCaxoSIsHSr1E47QHzbmzNR5rK8McHuNb11BOM9cHcIK3Avy0s/b2JlXHoQGTYS3NsvWzV1M0iK7l0wbA==", + "dev": true, + "dependencies": { + "@types/node": "*", + "form-data": "^3.0.0" + } + }, + "node_modules/@types/resolve": { + "version": "1.17.1", + "resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.17.1.tgz", + "integrity": "sha512-yy7HuzQhj0dhGpD8RLXSZWEkLsV9ibvxvi6EiJ3bkqLAO1RGo0WbkWQiwpRlSFymTJRz0d3k5LM3kkx8ArDbLw==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/vscode": { + "version": "1.65.0", + "resolved": "https://registry.npmjs.org/@types/vscode/-/vscode-1.65.0.tgz", + "integrity": "sha512-wQhExnh2nEzpjDMSKhUvnNmz3ucpd3E+R7wJkOhBNK3No6fG3VUdmVmMOKD0A8NDZDDDiQcLNxe3oGmX5SjJ5w==", + "dev": true + }, + "node_modules/adm-zip": { + "version": "0.5.9", + "resolved": "https://registry.npmjs.org/adm-zip/-/adm-zip-0.5.9.tgz", + "integrity": "sha512-s+3fXLkeeLjZ2kLjCBwQufpI5fuN+kIGBxu6530nVQZGVol0d7Y/M88/xw9HGGUcJjKf8LutN3VPRUBq6N7Ajg==", + "engines": { + "node": ">=6.0" + } + }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true + }, + "node_modules/balanced-match": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/builtin-modules": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-3.2.0.tgz", + "integrity": "sha512-lGzLKcioL90C7wMczpkY0n/oART3MbBa8R9OFGE1rJxoVI86u4WAGfEk8Wjv10eKSyTHVGkSo3bvBylCEtk7LA==", + "dev": true, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dev": true, + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/commondir": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", + "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=", + "dev": true + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" + }, + "node_modules/data-uri-to-buffer": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.0.tgz", + "integrity": "sha512-Vr3mLBA8qWmcuschSLAOogKgQ/Jwxulv3RNE4FXnYWRGujzrRWQI4m12fQqRkwX06C0KanhLr4hK+GydchZsaA==", + "engines": { + "node": ">= 12" + } + }, + "node_modules/deepmerge": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", + "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", + "dev": true, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/encoding": { + "version": "0.1.13", + "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz", + "integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==", + "dependencies": { + "iconv-lite": "^0.6.2" + } + }, + "node_modules/estree-walker": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", + "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", + "dev": true + }, + "node_modules/fetch-blob": { + "version": "3.1.4", + "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.1.4.tgz", + "integrity": "sha512-Eq5Xv5+VlSrYWEqKrusxY1C3Hm/hjeAsCGVG3ft7pZahlUAChpGZT/Ms1WmSLnEAisEXszjzu/s+ce6HZB2VHA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/jimmywarting" + }, + { + "type": "paypal", + "url": "https://paypal.me/jimmywarting" + } + ], + "dependencies": { + "node-domexception": "^1.0.0", + "web-streams-polyfill": "^3.0.3" + }, + "engines": { + "node": "^12.20 || >= 14.13" + } + }, + "node_modules/form-data": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-3.0.1.tgz", + "integrity": "sha512-RHkBKtLWUVwd7SqRIvCZMEvAMoGUp0XU+seQiZejj0COz3RI3hWP4sCv3gZWWLjJTd7rGwcsF5eKZGii0r/hbg==", + "dev": true, + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/formdata-polyfill": { + "version": "4.0.10", + "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", + "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", + "dependencies": { + "fetch-blob": "^3.1.2" + }, + "engines": { + "node": ">=12.20.0" + } + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", + "dev": true + }, + "node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "node_modules/glob": { + "version": "7.1.6", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", + "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/iconv-lite": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.2.tgz", + "integrity": "sha512-2y91h5OpQlolefMPmUlivelittSWy0rP+oYVpn6A7GwVHNE8AWzoYOBNmlwks3LobaJxgHCYZAnyNo2GgpNRNQ==", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "dev": true, + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "node_modules/is-core-module": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.2.0.tgz", + "integrity": "sha512-XRAfAdyyY5F5cOXn7hYQDqh2Xmii+DEfIcQGxK/uNwMHhIkPWO0g8msXcbzLe+MpGoR951MlqM/2iIlU4vKDdQ==", + "dev": true, + "dependencies": { + "has": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-module": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-module/-/is-module-1.0.0.tgz", + "integrity": "sha1-Mlj7afeMFNW4FdZkM2tM/7ZEFZE=", + "dev": true + }, + "node_modules/is-reference": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-reference/-/is-reference-1.2.1.tgz", + "integrity": "sha512-U82MsXXiFIrjCK4otLT+o2NA2Cd2g5MLoOVXUZjIOhLurrRxpEXzI8O0KZHr3IjLvlAH1kTPYSuqer5T9ZVBKQ==", + "dev": true, + "dependencies": { + "@types/estree": "*" + } + }, + "node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/magic-string": { + "version": "0.25.7", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.7.tgz", + "integrity": "sha512-4CrMT5DOHTDk4HYDlzmwu4FVCcIYI8gauveasrdCu2IKIFOJ3f0v/8MDGJCDL9oD2ppz/Av1b0Nj345H9M+XIA==", + "dev": true, + "dependencies": { + "sourcemap-codec": "^1.4.4" + } + }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/node-domexception": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", + "integrity": "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/jimmywarting" + }, + { + "type": "github", + "url": "https://paypal.me/jimmywarting" + } + ], + "engines": { + "node": ">=10.5.0" + } + }, + "node_modules/node-fetch": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.2.3.tgz", + "integrity": "sha512-AXP18u4pidSZ1xYXRDPY/8jdv3RAozIt/WLNR/MBGZAz+xjtlr90RvCnsvHQRiXyWliZF/CpytExp32UU67/SA==", + "dependencies": { + "data-uri-to-buffer": "^4.0.0", + "fetch-blob": "^3.1.4", + "formdata-polyfill": "^4.0.10" + }, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/node-fetch" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/path-parse": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==", + "dev": true + }, + "node_modules/picomatch": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.2.2.tgz", + "integrity": "sha512-q0M/9eZHzmr0AulXyPwNfZjtwZ/RBZlbN3K3CErVrk50T2ASYI7Bye0EvekFY3IP1Nt2DHu0re+V2ZHIpMkuWg==", + "engines": { + "node": ">=8.6" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/resolve": { + "version": "1.19.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.19.0.tgz", + "integrity": "sha512-rArEXAgsBG4UgRGcynxWIWKFvh/XZCcS8UJdHhwy91zwAvCZIbcs+vAbflgBnNjYMs/i/i+/Ux6IZhML1yPvxg==", + "dev": true, + "dependencies": { + "is-core-module": "^2.1.0", + "path-parse": "^1.0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/rollup": { + "version": "2.70.1", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.70.1.tgz", + "integrity": "sha512-CRYsI5EuzLbXdxC6RnYhOuRdtz4bhejPMSWjsFLfVM/7w/85n2szZv6yExqUXsBdz5KT8eoubeyDUDjhLHEslA==", + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=10.0.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.2" + } + }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + }, + "node_modules/semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/sourcemap-codec": { + "version": "1.4.8", + "resolved": "https://registry.npmjs.org/sourcemap-codec/-/sourcemap-codec-1.4.8.tgz", + "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==", + "dev": true + }, + "node_modules/vscode-jsonrpc": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-6.0.0.tgz", + "integrity": "sha512-wnJA4BnEjOSyFMvjZdpiOwhSq9uDoK8e/kpRJDTaMYzwlkrhG1fwDIZI94CLsLzlCK5cIbMMtFlJlfR57Lavmg==", + "engines": { + "node": ">=8.0.0 || >=10.0.0" + } + }, + "node_modules/vscode-languageclient": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-7.0.0.tgz", + "integrity": "sha512-P9AXdAPlsCgslpP9pRxYPqkNYV7Xq8300/aZDpO35j1fJm/ncize8iGswzYlcvFw5DQUx4eVk+KvfXdL0rehNg==", + "dependencies": { + "minimatch": "^3.0.4", + "semver": "^7.3.4", + "vscode-languageserver-protocol": "3.16.0" + }, + "engines": { + "vscode": "^1.52.0" + } + }, + "node_modules/vscode-languageserver-protocol": { + "version": "3.16.0", + "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.16.0.tgz", + "integrity": "sha512-sdeUoAawceQdgIfTI+sdcwkiK2KU+2cbEYA0agzM2uqaUy2UpnnGHtWTHVEtS0ES4zHU0eMFRGN+oQgDxlD66A==", + "dependencies": { + "vscode-jsonrpc": "6.0.0", + "vscode-languageserver-types": "3.16.0" + } + }, + "node_modules/vscode-languageserver-types": { + "version": "3.16.0", + "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.16.0.tgz", + "integrity": "sha512-k8luDIWJWyenLc5ToFQQMaSrqCHiLwyKPHKPQZ5zz21vM+vIVUSvsRpcbiECH4WR88K2XZqc4ScRcZ7nk/jbeA==" + }, + "node_modules/web-streams-polyfill": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.2.0.tgz", + "integrity": "sha512-EqPmREeOzttaLRm5HS7io98goBgZ7IVz79aDvqjD0kYXLtFZTc0T/U6wHTPKyIjb+MdN7DFIIX6hgdBEpWmfPA==", + "engines": { + "node": ">= 8" + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + }, + "node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" + } + }, + "dependencies": { + "@rollup/plugin-commonjs": { + "version": "21.0.2", + "resolved": "https://registry.npmjs.org/@rollup/plugin-commonjs/-/plugin-commonjs-21.0.2.tgz", + "integrity": "sha512-d/OmjaLVO4j/aQX69bwpWPpbvI3TJkQuxoAk7BH8ew1PyoMBLTOuvJTjzG8oEoW7drIIqB0KCJtfFLu/2GClWg==", + "dev": true, + "requires": { + "@rollup/pluginutils": "^3.1.0", + "commondir": "^1.0.1", + "estree-walker": "^2.0.1", + "glob": "^7.1.6", + "is-reference": "^1.2.1", + "magic-string": "^0.25.7", + "resolve": "^1.17.0" + } + }, + "@rollup/plugin-json": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/@rollup/plugin-json/-/plugin-json-4.1.0.tgz", + "integrity": "sha512-yfLbTdNS6amI/2OpmbiBoW12vngr5NW2jCJVZSBEz+H5KfUJZ2M7sDjk0U6GOOdCWFVScShte29o9NezJ53TPw==", + "requires": { + "@rollup/pluginutils": "^3.0.8" + } + }, + "@rollup/plugin-node-resolve": { + "version": "13.1.3", + "resolved": "https://registry.npmjs.org/@rollup/plugin-node-resolve/-/plugin-node-resolve-13.1.3.tgz", + "integrity": "sha512-BdxNk+LtmElRo5d06MGY4zoepyrXX1tkzX2hrnPEZ53k78GuOMWLqmJDGIIOPwVRIFZrLQOo+Yr6KtCuLIA0AQ==", + "dev": true, + "requires": { + "@rollup/pluginutils": "^3.1.0", + "@types/resolve": "1.17.1", + "builtin-modules": "^3.1.0", + "deepmerge": "^4.2.2", + "is-module": "^1.0.0", + "resolve": "^1.19.0" + } + }, + "@rollup/pluginutils": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-3.1.0.tgz", + "integrity": "sha512-GksZ6pr6TpIjHm8h9lSQ8pi8BE9VeubNT0OMJ3B5uZJ8pz73NPiqOtCog/x2/QzM1ENChPKxMDhiQuRHsqc+lg==", + "requires": { + "@types/estree": "0.0.39", + "estree-walker": "^1.0.1", + "picomatch": "^2.2.2" + }, + "dependencies": { + "estree-walker": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-1.0.1.tgz", + "integrity": "sha512-1fMXF3YP4pZZVozF8j/ZLfvnR8NSIljt56UhbZ5PeeDmmGHpgpdwQt7ITlGvYaQukCvuBRMLEiKiYC+oeIg4cg==" + } + } + }, + "@types/adm-zip": { + "version": "0.4.34", + "resolved": "https://registry.npmjs.org/@types/adm-zip/-/adm-zip-0.4.34.tgz", + "integrity": "sha512-8ToYLLAYhkRfcmmljrKi22gT2pqu7hGMDtORP1emwIEGmgUTZOsaDjzWFzW5N2frcFRz/50CWt4zA1CxJ73pmQ==", + "dev": true, + "requires": { + "@types/node": "*" + } + }, + "@types/estree": { + "version": "0.0.39", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.39.tgz", + "integrity": "sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==" + }, + "@types/node": { + "version": "13.7.1", + "resolved": "https://registry.npmjs.org/@types/node/-/node-13.7.1.tgz", + "integrity": "sha512-Zq8gcQGmn4txQEJeiXo/KiLpon8TzAl0kmKH4zdWctPj05nWwp1ClMdAVEloqrQKfaC48PNLdgN/aVaLqUrluA==", + "dev": true + }, + "@types/node-fetch": { + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-2.6.1.tgz", + "integrity": "sha512-oMqjURCaxoSIsHSr1E47QHzbmzNR5rK8McHuNb11BOM9cHcIK3Avy0s/b2JlXHoQGTYS3NsvWzV1M0iK7l0wbA==", + "dev": true, + "requires": { + "@types/node": "*", + "form-data": "^3.0.0" + } + }, + "@types/resolve": { + "version": "1.17.1", + "resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.17.1.tgz", + "integrity": "sha512-yy7HuzQhj0dhGpD8RLXSZWEkLsV9ibvxvi6EiJ3bkqLAO1RGo0WbkWQiwpRlSFymTJRz0d3k5LM3kkx8ArDbLw==", + "dev": true, + "requires": { + "@types/node": "*" + } + }, + "@types/vscode": { + "version": "1.65.0", + "resolved": "https://registry.npmjs.org/@types/vscode/-/vscode-1.65.0.tgz", + "integrity": "sha512-wQhExnh2nEzpjDMSKhUvnNmz3ucpd3E+R7wJkOhBNK3No6fG3VUdmVmMOKD0A8NDZDDDiQcLNxe3oGmX5SjJ5w==", + "dev": true + }, + "adm-zip": { + "version": "0.5.9", + "resolved": "https://registry.npmjs.org/adm-zip/-/adm-zip-0.5.9.tgz", + "integrity": "sha512-s+3fXLkeeLjZ2kLjCBwQufpI5fuN+kIGBxu6530nVQZGVol0d7Y/M88/xw9HGGUcJjKf8LutN3VPRUBq6N7Ajg==" + }, + "asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true + }, + "balanced-match": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + }, + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "builtin-modules": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-3.2.0.tgz", + "integrity": "sha512-lGzLKcioL90C7wMczpkY0n/oART3MbBa8R9OFGE1rJxoVI86u4WAGfEk8Wjv10eKSyTHVGkSo3bvBylCEtk7LA==", + "dev": true + }, + "combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dev": true, + "requires": { + "delayed-stream": "~1.0.0" + } + }, + "commondir": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", + "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=", + "dev": true + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" + }, + "data-uri-to-buffer": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.0.tgz", + "integrity": "sha512-Vr3mLBA8qWmcuschSLAOogKgQ/Jwxulv3RNE4FXnYWRGujzrRWQI4m12fQqRkwX06C0KanhLr4hK+GydchZsaA==" + }, + "deepmerge": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", + "integrity": "sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==", + "dev": true + }, + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", + "dev": true + }, + "encoding": { + "version": "0.1.13", + "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz", + "integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==", + "requires": { + "iconv-lite": "^0.6.2" + } + }, + "estree-walker": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", + "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", + "dev": true + }, + "fetch-blob": { + "version": "3.1.4", + "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.1.4.tgz", + "integrity": "sha512-Eq5Xv5+VlSrYWEqKrusxY1C3Hm/hjeAsCGVG3ft7pZahlUAChpGZT/Ms1WmSLnEAisEXszjzu/s+ce6HZB2VHA==", + "requires": { + "node-domexception": "^1.0.0", + "web-streams-polyfill": "^3.0.3" + } + }, + "form-data": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-3.0.1.tgz", + "integrity": "sha512-RHkBKtLWUVwd7SqRIvCZMEvAMoGUp0XU+seQiZejj0COz3RI3hWP4sCv3gZWWLjJTd7rGwcsF5eKZGii0r/hbg==", + "dev": true, + "requires": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + } + }, + "formdata-polyfill": { + "version": "4.0.10", + "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", + "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", + "requires": { + "fetch-blob": "^3.1.2" + } + }, + "fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", + "dev": true + }, + "fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "optional": true + }, + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "glob": { + "version": "7.1.6", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", + "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "requires": { + "function-bind": "^1.1.1" + } + }, + "iconv-lite": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.2.tgz", + "integrity": "sha512-2y91h5OpQlolefMPmUlivelittSWy0rP+oYVpn6A7GwVHNE8AWzoYOBNmlwks3LobaJxgHCYZAnyNo2GgpNRNQ==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + } + }, + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "dev": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "is-core-module": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.2.0.tgz", + "integrity": "sha512-XRAfAdyyY5F5cOXn7hYQDqh2Xmii+DEfIcQGxK/uNwMHhIkPWO0g8msXcbzLe+MpGoR951MlqM/2iIlU4vKDdQ==", + "dev": true, + "requires": { + "has": "^1.0.3" + } + }, + "is-module": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-module/-/is-module-1.0.0.tgz", + "integrity": "sha1-Mlj7afeMFNW4FdZkM2tM/7ZEFZE=", + "dev": true + }, + "is-reference": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-reference/-/is-reference-1.2.1.tgz", + "integrity": "sha512-U82MsXXiFIrjCK4otLT+o2NA2Cd2g5MLoOVXUZjIOhLurrRxpEXzI8O0KZHr3IjLvlAH1kTPYSuqer5T9ZVBKQ==", + "dev": true, + "requires": { + "@types/estree": "*" + } + }, + "lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "requires": { + "yallist": "^4.0.0" + } + }, + "magic-string": { + "version": "0.25.7", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.7.tgz", + "integrity": "sha512-4CrMT5DOHTDk4HYDlzmwu4FVCcIYI8gauveasrdCu2IKIFOJ3f0v/8MDGJCDL9oD2ppz/Av1b0Nj345H9M+XIA==", + "dev": true, + "requires": { + "sourcemap-codec": "^1.4.4" + } + }, + "mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true + }, + "mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, + "requires": { + "mime-db": "1.52.0" + } + }, + "minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "node-domexception": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", + "integrity": "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==" + }, + "node-fetch": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.2.3.tgz", + "integrity": "sha512-AXP18u4pidSZ1xYXRDPY/8jdv3RAozIt/WLNR/MBGZAz+xjtlr90RvCnsvHQRiXyWliZF/CpytExp32UU67/SA==", + "requires": { + "data-uri-to-buffer": "^4.0.0", + "fetch-blob": "^3.1.4", + "formdata-polyfill": "^4.0.10" + } + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", + "dev": true + }, + "path-parse": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==", + "dev": true + }, + "picomatch": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.2.2.tgz", + "integrity": "sha512-q0M/9eZHzmr0AulXyPwNfZjtwZ/RBZlbN3K3CErVrk50T2ASYI7Bye0EvekFY3IP1Nt2DHu0re+V2ZHIpMkuWg==" + }, + "resolve": { + "version": "1.19.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.19.0.tgz", + "integrity": "sha512-rArEXAgsBG4UgRGcynxWIWKFvh/XZCcS8UJdHhwy91zwAvCZIbcs+vAbflgBnNjYMs/i/i+/Ux6IZhML1yPvxg==", + "dev": true, + "requires": { + "is-core-module": "^2.1.0", + "path-parse": "^1.0.6" + } + }, + "rollup": { + "version": "2.70.1", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.70.1.tgz", + "integrity": "sha512-CRYsI5EuzLbXdxC6RnYhOuRdtz4bhejPMSWjsFLfVM/7w/85n2szZv6yExqUXsBdz5KT8eoubeyDUDjhLHEslA==", + "requires": { + "fsevents": "~2.3.2" + } + }, + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "requires": { + "lru-cache": "^6.0.0" + } + }, + "sourcemap-codec": { + "version": "1.4.8", + "resolved": "https://registry.npmjs.org/sourcemap-codec/-/sourcemap-codec-1.4.8.tgz", + "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==", + "dev": true + }, + "vscode-jsonrpc": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-6.0.0.tgz", + "integrity": "sha512-wnJA4BnEjOSyFMvjZdpiOwhSq9uDoK8e/kpRJDTaMYzwlkrhG1fwDIZI94CLsLzlCK5cIbMMtFlJlfR57Lavmg==" + }, + "vscode-languageclient": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-7.0.0.tgz", + "integrity": "sha512-P9AXdAPlsCgslpP9pRxYPqkNYV7Xq8300/aZDpO35j1fJm/ncize8iGswzYlcvFw5DQUx4eVk+KvfXdL0rehNg==", + "requires": { + "minimatch": "^3.0.4", + "semver": "^7.3.4", + "vscode-languageserver-protocol": "3.16.0" + } + }, + "vscode-languageserver-protocol": { + "version": "3.16.0", + "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.16.0.tgz", + "integrity": "sha512-sdeUoAawceQdgIfTI+sdcwkiK2KU+2cbEYA0agzM2uqaUy2UpnnGHtWTHVEtS0ES4zHU0eMFRGN+oQgDxlD66A==", + "requires": { + "vscode-jsonrpc": "6.0.0", + "vscode-languageserver-types": "3.16.0" + } + }, + "vscode-languageserver-types": { + "version": "3.16.0", + "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.16.0.tgz", + "integrity": "sha512-k8luDIWJWyenLc5ToFQQMaSrqCHiLwyKPHKPQZ5zz21vM+vIVUSvsRpcbiECH4WR88K2XZqc4ScRcZ7nk/jbeA==" + }, + "web-streams-polyfill": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.2.0.tgz", + "integrity": "sha512-EqPmREeOzttaLRm5HS7io98goBgZ7IVz79aDvqjD0kYXLtFZTc0T/U6wHTPKyIjb+MdN7DFIIX6hgdBEpWmfPA==" + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + }, + "yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" + } + } } diff --git a/client/package.json b/client/package.json index 735890c..3d8a93e 100644 --- a/client/package.json +++ b/client/package.json @@ -5,16 +5,18 @@ "rollup": "rollup -c" }, "dependencies": { - "adm-zip": "^0.4.14", - "node-fetch": "^2.6.0", - "vscode-languageclient": "^6.1.3" + "@rollup/plugin-json": "^4.1.0", + "adm-zip": "^0.5.9", + "encoding": "^0.1.13", + "node-fetch": "^3.2.3", + "vscode-languageclient": "^7.0.0" }, "devDependencies": { - "rollup": "^2.38.1", - "@rollup/plugin-commonjs": "^17.1.0", - "@rollup/plugin-node-resolve": "^11.1.1", - "@types/vscode": "^1.47.0", - "@types/adm-zip": "^0.4.32", - "@types/node-fetch": "^2.5.4" + "@rollup/plugin-commonjs": "^21.0.2", + "@rollup/plugin-node-resolve": "^13.1.3", + "@types/adm-zip": "^0.4.34", + "@types/node-fetch": "^2.6.1", + "@types/vscode": "^1.65.0", + "rollup": "^2.70.1" } } diff --git a/client/rollup.config.js b/client/rollup.config.js index 0ea37da..2874703 100644 --- a/client/rollup.config.js +++ b/client/rollup.config.js @@ -1,11 +1,13 @@ import resolve from '@rollup/plugin-node-resolve'; import commonjs from '@rollup/plugin-commonjs'; +import json from '@rollup/plugin-json'; import nodeBuiltins from 'builtin-modules'; /** @type { import('rollup').RollupOptions } */ export default { input: 'out/extension.js', plugins: [ + json(), resolve({ preferBuiltins: true }), diff --git a/package-lock.json b/package-lock.json index b148cd0..329ae5c 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,1749 +1,5075 @@ { - "name": "vscode-mc-shader", - "version": "0.9.2", - "lockfileVersion": 1, - "requires": true, - "dependencies": { - "@babel/code-frame": { - "version": "7.10.4", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.10.4.tgz", - "integrity": "sha512-vG6SvB6oYEhvgisZNFRmRCUkLz11c7rp+tbNTynGqc6mS1d5ATd/sGyV6W0KZZnXRKMTzZDRgQT3Ou9jhpAfUg==", - "dev": true, - "requires": { - "@babel/highlight": "^7.10.4" - } + "name": "vscode-mc-shader", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "version": "0.9.6", + "hasInstallScript": true, + "license": "MIT", + "devDependencies": { + "@types/node": "^17.0.21", + "@typescript-eslint/parser": "^5.15.0", + "concurrently": "^7.0.0", + "eslint": "^8.11.0", + "typescript": "^4.6.2", + "vsce": "^2.7.0" + }, + "engines": { + "vscode": "^1.53.0" + } + }, + "node_modules/@eslint/eslintrc": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.2.1.tgz", + "integrity": "sha512-bxvbYnBPN1Gibwyp6NrpnFzA3YtRL3BBAyEAFVIpNTm2Rn4Vy87GA5M4aSn3InRrlsbX5N0GW7XIx+U4SAEKdQ==", + "dev": true, + "dependencies": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.3.1", + "globals": "^13.9.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.0.4", + "strip-json-comments": "^3.1.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/@humanwhocodes/config-array": { + "version": "0.9.5", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.9.5.tgz", + "integrity": "sha512-ObyMyWxZiCu/yTisA7uzx81s40xR2fD5Cg/2Kq7G02ajkNubJf6BopgDTmDyc3U7sXpNKM8cYOw7s7Tyr+DnCw==", + "dev": true, + "dependencies": { + "@humanwhocodes/object-schema": "^1.2.1", + "debug": "^4.1.1", + "minimatch": "^3.0.4" + }, + "engines": { + "node": ">=10.10.0" + } + }, + "node_modules/@humanwhocodes/object-schema": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz", + "integrity": "sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==", + "dev": true + }, + "node_modules/@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "dependencies": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@types/node": { + "version": "17.0.21", + "resolved": "https://registry.npmjs.org/@types/node/-/node-17.0.21.tgz", + "integrity": "sha512-DBZCJbhII3r90XbQxI8Y9IjjiiOGlZ0Hr32omXIZvwwZ7p4DMMXGrKXVyPfuoBOri9XNtL0UK69jYIBIsRX3QQ==", + "dev": true + }, + "node_modules/@typescript-eslint/parser": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.15.0.tgz", + "integrity": "sha512-NGAYP/+RDM2sVfmKiKOCgJYPstAO40vPAgACoWPO/+yoYKSgAXIFaBKsV8P0Cc7fwKgvj27SjRNX4L7f4/jCKQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/scope-manager": "5.15.0", + "@typescript-eslint/types": "5.15.0", + "@typescript-eslint/typescript-estree": "5.15.0", + "debug": "^4.3.2" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/scope-manager": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.15.0.tgz", + "integrity": "sha512-EFiZcSKrHh4kWk0pZaa+YNJosvKE50EnmN4IfgjkA3bTHElPtYcd2U37QQkNTqwMCS7LXeDeZzEqnsOH8chjSg==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.15.0", + "@typescript-eslint/visitor-keys": "5.15.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/types": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.15.0.tgz", + "integrity": "sha512-yEiTN4MDy23vvsIksrShjNwQl2vl6kJeG9YkVJXjXZnkJElzVK8nfPsWKYxcsGWG8GhurYXP4/KGj3aZAxbeOA==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/typescript-estree": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.15.0.tgz", + "integrity": "sha512-Hb0e3dGc35b75xLzixM3cSbG1sSbrTBQDfIScqdyvrfJZVEi4XWAT+UL/HMxEdrJNB8Yk28SKxPLtAhfCbBInA==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.15.0", + "@typescript-eslint/visitor-keys": "5.15.0", + "debug": "^4.3.2", + "globby": "^11.0.4", + "is-glob": "^4.0.3", + "semver": "^7.3.5", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/visitor-keys": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.15.0.tgz", + "integrity": "sha512-+vX5FKtgvyHbmIJdxMJ2jKm9z2BIlXJiuewI8dsDYMp5LzPUcuTT78Ya5iwvQg3VqSVdmxyM8Anj1Jeq7733ZQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.15.0", + "eslint-visitor-keys": "^3.0.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/acorn": { + "version": "8.7.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.7.0.tgz", + "integrity": "sha512-V/LGr1APy+PXIwKebEWrkZPwoeoF+w1jiOBUmuxuiUIaOHtob8Qc9BTrYo7VuI5fR8tqsy+buA2WFooR5olqvQ==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, + "peerDependencies": { + "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/ansi-regex": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", + "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/aproba": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", + "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==", + "dev": true + }, + "node_modules/are-we-there-yet": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.7.tgz", + "integrity": "sha512-nxwy40TuMiUGqMyRHgCSWZ9FM4VAoRP4xUYSTv5ImRog+h9yISPbVH7H8fASCIzYn9wlEv4zvFL7uKDMCFQm3g==", + "dev": true, + "dependencies": { + "delegates": "^1.0.0", + "readable-stream": "^2.0.6" + } + }, + "node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", + "dev": true + }, + "node_modules/array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/azure-devops-node-api": { + "version": "11.1.1", + "resolved": "https://registry.npmjs.org/azure-devops-node-api/-/azure-devops-node-api-11.1.1.tgz", + "integrity": "sha512-XDG91XzLZ15reP12s3jFkKS8oiagSICjnLwxEYieme4+4h3ZveFOFRA4iYIG40RyHXsiI0mefFYYMFIJbMpWcg==", + "dev": true, + "dependencies": { + "tunnel": "0.0.6", + "typed-rest-client": "^1.8.4" + } + }, + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "node_modules/base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "@babel/helper-validator-identifier": { - "version": "7.10.4", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.10.4.tgz", - "integrity": "sha512-3U9y+43hz7ZM+rzG24Qe2mufW5KhvFg/NhnNph+i9mgCtdTCtMJuI1TMkrIUiK7Ix4PYlRF9I5dhqaLYA/ADXw==", - "dev": true + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, - "@babel/highlight": { - "version": "7.10.4", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.10.4.tgz", - "integrity": "sha512-i6rgnR/YgPEQzZZnbTHHuZdlE8qyoBNalD6F+q4vAFlcMEcqmkoG+mPqJYJCo63qPf74+Y1UZsl3l6f7/RIkmA==", - "dev": true, - "requires": { - "@babel/helper-validator-identifier": "^7.10.4", - "chalk": "^2.0.0", - "js-tokens": "^4.0.0" - }, - "dependencies": { - "chalk": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", - "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", - "dev": true, - "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" - } - }, - "supports-color": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", - "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", - "dev": true, - "requires": { - "has-flag": "^3.0.0" - } - } - } + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/bl": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", + "dev": true, + "dependencies": { + "buffer": "^5.5.0", + "inherits": "^2.0.4", + "readable-stream": "^3.4.0" + } + }, + "node_modules/bl/node_modules/readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/boolbase": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", + "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24=", + "dev": true + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/braces": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", + "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "dev": true, + "dependencies": { + "fill-range": "^7.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "@types/color-name": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@types/color-name/-/color-name-1.1.1.tgz", - "integrity": "sha512-rr+OQyAjxze7GgWrSaJwydHStIhHq2lvY3BOC2Mj7KnzI7XK0Uw1TOOdI9lDoajEbSWLiYgoo4f1R51erQfhPQ==", - "dev": true + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, - "@types/eslint-visitor-keys": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/@types/eslint-visitor-keys/-/eslint-visitor-keys-1.0.0.tgz", - "integrity": "sha512-OCutwjDZ4aFS6PB1UZ988C4YgwlBHJd6wCeQqaLdmadZ/7e+w79+hbMUFC1QXDNCmdyoRfAFdm0RypzwR+Qpag==", - "dev": true + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "node_modules/buffer-crc32": { + "version": "0.2.13", + "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", + "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", + "dev": true, + "engines": { + "node": "*" + } + }, + "node_modules/call-bind": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", + "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1", + "get-intrinsic": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/chalk/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/cheerio": { + "version": "1.0.0-rc.10", + "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0-rc.10.tgz", + "integrity": "sha512-g0J0q/O6mW8z5zxQ3A8E8J1hUgp4SMOvEoW/x84OwyHKe/Zccz83PVT4y5Crcr530FV6NgmKI1qvGTKVl9XXVw==", + "dev": true, + "dependencies": { + "cheerio-select": "^1.5.0", + "dom-serializer": "^1.3.2", + "domhandler": "^4.2.0", + "htmlparser2": "^6.1.0", + "parse5": "^6.0.1", + "parse5-htmlparser2-tree-adapter": "^6.0.1", + "tslib": "^2.2.0" + }, + "engines": { + "node": ">= 6" + }, + "funding": { + "url": "https://github.com/cheeriojs/cheerio?sponsor=1" + } + }, + "node_modules/cheerio-select": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/cheerio-select/-/cheerio-select-1.5.0.tgz", + "integrity": "sha512-qocaHPv5ypefh6YNxvnbABM07KMxExbtbfuJoIie3iZXX1ERwYmJcIiRrr9H05ucQP1k28dav8rpdDgjQd8drg==", + "dev": true, + "dependencies": { + "css-select": "^4.1.3", + "css-what": "^5.0.1", + "domelementtype": "^2.2.0", + "domhandler": "^4.2.0", + "domutils": "^2.7.0" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/cheerio/node_modules/tslib": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.3.1.tgz", + "integrity": "sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw==", + "dev": true + }, + "node_modules/chownr": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", + "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", + "dev": true + }, + "node_modules/cliui": { + "version": "7.0.4", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", + "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", + "dev": true, + "dependencies": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^7.0.0" + } + }, + "node_modules/code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", + "dev": true + }, + "node_modules/commander": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-6.2.1.tgz", + "integrity": "sha512-U7VdrJFnJgo4xjrHpTzu0yrHPGImdsmD95ZlgYSEajAn2JKzDhDTPG9kBTefmObL2w/ngeZnilk+OV9CG3d7UA==", + "dev": true, + "engines": { + "node": ">= 6" + } + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", + "dev": true + }, + "node_modules/concurrently": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-7.0.0.tgz", + "integrity": "sha512-WKM7PUsI8wyXpF80H+zjHP32fsgsHNQfPLw/e70Z5dYkV7hF+rf8q3D+ScWJIEr57CpkO3OWBko6hwhQLPR8Pw==", + "dev": true, + "dependencies": { + "chalk": "^4.1.0", + "date-fns": "^2.16.1", + "lodash": "^4.17.21", + "rxjs": "^6.6.3", + "spawn-command": "^0.0.2-1", + "supports-color": "^8.1.0", + "tree-kill": "^1.2.2", + "yargs": "^16.2.0" + }, + "bin": { + "concurrently": "dist/bin/concurrently.js" + }, + "engines": { + "node": "^12.20.0 || ^14.13.0 || >=16.0.0" + } + }, + "node_modules/concurrently/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/concurrently/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/concurrently/node_modules/chalk/node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/concurrently/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/concurrently/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "node_modules/concurrently/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/console-control-strings": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", + "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=", + "dev": true + }, + "node_modules/core-util-is": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", + "dev": true + }, + "node_modules/cross-spawn": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", + "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "dev": true, + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/css-select": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/css-select/-/css-select-4.2.1.tgz", + "integrity": "sha512-/aUslKhzkTNCQUB2qTX84lVmfia9NyjP3WpDGtj/WxhwBzWBYUV3DgUpurHTme8UTPcPlAD1DJ+b0nN/t50zDQ==", + "dev": true, + "dependencies": { + "boolbase": "^1.0.0", + "css-what": "^5.1.0", + "domhandler": "^4.3.0", + "domutils": "^2.8.0", + "nth-check": "^2.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/css-what": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/css-what/-/css-what-5.1.0.tgz", + "integrity": "sha512-arSMRWIIFY0hV8pIxZMEfmMI47Wj3R/aWpZDDxWYCPEiOMv6tfOrnpDtgxBYPEQD4V0Y/958+1TdC3iWTFcUPw==", + "dev": true, + "engines": { + "node": ">= 6" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/date-fns": { + "version": "2.28.0", + "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.28.0.tgz", + "integrity": "sha512-8d35hViGYx/QH0icHYCeLmsLmMUheMmTyV9Fcm6gvNwdw31yXXH+O85sOBJ+OLnLQMKZowvpKb6FgMIQjcpvQw==", + "dev": true, + "engines": { + "node": ">=0.11" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/date-fns" + } + }, + "node_modules/debug": { + "version": "4.3.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.3.tgz", + "integrity": "sha512-/zxw5+vh1Tfv+4Qn7a5nsbcJKPaSvCDhojn6FEl9vupwK2VCSDtEiEtqr8DFtzYFOdz63LBkxec7DYuc2jon6Q==", + "dev": true, + "dependencies": { + "ms": "2.1.2" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "dev": true, + "dependencies": { + "mimic-response": "^3.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true, + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/deep-is": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", + "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", + "dev": true + }, + "node_modules/delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=", + "dev": true + }, + "node_modules/detect-libc": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.1.tgz", + "integrity": "sha512-463v3ZeIrcWtdgIg6vI6XUncguvr2TnGl4SzDXinkt9mSLpBJKXT3mW6xT3VQdDN11+WVs29pgvivTc4Lp8v+w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/dir-glob": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", + "dev": true, + "dependencies": { + "path-type": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/dom-serializer": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.3.2.tgz", + "integrity": "sha512-5c54Bk5Dw4qAxNOI1pFEizPSjVsx5+bpJKmL2kPn8JhBUq2q09tTCa3mjijun2NfK78NMouDYNMBkOrPZiS+ig==", + "dev": true, + "dependencies": { + "domelementtype": "^2.0.1", + "domhandler": "^4.2.0", + "entities": "^2.0.0" + }, + "funding": { + "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + } + }, + "node_modules/domelementtype": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.2.0.tgz", + "integrity": "sha512-DtBMo82pv1dFtUmHyr48beiuq792Sxohr+8Hm9zoxklYPfa6n0Z3Byjj2IV7bmr2IyqClnqEQhfgHJJ5QF0R5A==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ] + }, + "node_modules/domhandler": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-4.3.0.tgz", + "integrity": "sha512-fC0aXNQXqKSFTr2wDNZDhsEYjCiYsDWl3D01kwt25hm1YIPyDGHvvi3rw+PLqHAl/m71MaiF7d5zvBr0p5UB2g==", + "dev": true, + "dependencies": { + "domelementtype": "^2.2.0" + }, + "engines": { + "node": ">= 4" + }, + "funding": { + "url": "https://github.com/fb55/domhandler?sponsor=1" + } + }, + "node_modules/domutils": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-2.8.0.tgz", + "integrity": "sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==", + "dev": true, + "dependencies": { + "dom-serializer": "^1.0.1", + "domelementtype": "^2.2.0", + "domhandler": "^4.2.0" + }, + "funding": { + "url": "https://github.com/fb55/domutils?sponsor=1" + } + }, + "node_modules/emoji-regex": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "dev": true + }, + "node_modules/end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dev": true, + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/entities": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", + "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", + "dev": true, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "node_modules/escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/eslint": { + "version": "8.11.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.11.0.tgz", + "integrity": "sha512-/KRpd9mIRg2raGxHRGwW9ZywYNAClZrHjdueHcrVDuO3a6bj83eoTirCCk0M0yPwOjWYKHwRVRid+xK4F/GHgA==", + "dev": true, + "dependencies": { + "@eslint/eslintrc": "^1.2.1", + "@humanwhocodes/config-array": "^0.9.2", + "ajv": "^6.10.0", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.2", + "debug": "^4.3.2", + "doctrine": "^3.0.0", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^7.1.1", + "eslint-utils": "^3.0.0", + "eslint-visitor-keys": "^3.3.0", + "espree": "^9.3.1", + "esquery": "^1.4.0", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^6.0.1", + "functional-red-black-tree": "^1.0.1", + "glob-parent": "^6.0.1", + "globals": "^13.6.0", + "ignore": "^5.2.0", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "js-yaml": "^4.1.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.4.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.0.4", + "natural-compare": "^1.4.0", + "optionator": "^0.9.1", + "regexpp": "^3.2.0", + "strip-ansi": "^6.0.1", + "strip-json-comments": "^3.1.0", + "text-table": "^0.2.0", + "v8-compile-cache": "^2.0.3" + }, + "bin": { + "eslint": "bin/eslint.js" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint-scope": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.1.1.tgz", + "integrity": "sha512-QKQM/UXpIiHcLqJ5AOyIW7XZmzjkzQXYE54n1++wb0u9V/abW3l9uQnxX8Z5Xd18xyKIMTUAyQ0k1e8pz6LUrw==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/eslint-utils": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-3.0.0.tgz", + "integrity": "sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA==", + "dev": true, + "dependencies": { + "eslint-visitor-keys": "^2.0.0" + }, + "engines": { + "node": "^10.0.0 || ^12.0.0 || >= 14.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/mysticatea" + }, + "peerDependencies": { + "eslint": ">=5" + } + }, + "node_modules/eslint-utils/node_modules/eslint-visitor-keys": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.1.0.tgz", + "integrity": "sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/eslint-visitor-keys": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.3.0.tgz", + "integrity": "sha512-mQ+suqKJVyeuwGYHAdjMFqjCyfl8+Ldnxuyp3ldiMBFKkvytrXUZWaiPCEav8qDHKty44bD+qV1IP4T+w+xXRA==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/eslint/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/eslint/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/eslint/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/eslint/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "node_modules/eslint/node_modules/escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/eslint/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/eslint/node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/espree": { + "version": "9.3.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.3.1.tgz", + "integrity": "sha512-bvdyLmJMfwkV3NCRl5ZhJf22zBFo1y8bYh3VYb+bfzqNB4Je68P2sSuXyuFquzWLebHpNd2/d5uv7yoP9ISnGQ==", + "dev": true, + "dependencies": { + "acorn": "^8.7.0", + "acorn-jsx": "^5.3.1", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/esquery": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", + "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", + "dev": true, + "dependencies": { + "estraverse": "^5.1.0" + }, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "dependencies": { + "estraverse": "^5.2.0" + }, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/expand-template": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-2.0.3.tgz", + "integrity": "sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "dev": true + }, + "node_modules/fast-glob": { + "version": "3.2.11", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.11.tgz", + "integrity": "sha512-xrO3+1bxSo3ZVHAnqzyuewYT6aMFHRAd4Kcs92MAonjwQZLsK9d0SF1IyQ3k5PoirxTW0Oe/RqFgMQ6TcNE5Ew==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/fast-glob/node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "node_modules/fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", + "dev": true + }, + "node_modules/fastq": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.13.0.tgz", + "integrity": "sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==", + "dev": true, + "dependencies": { + "reusify": "^1.0.4" + } + }, + "node_modules/fd-slicer": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", + "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", + "dev": true, + "dependencies": { + "pend": "~1.2.0" + } + }, + "node_modules/file-entry-cache": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", + "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", + "dev": true, + "dependencies": { + "flat-cache": "^3.0.4" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/fill-range": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", + "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", + "dev": true, + "dependencies": { + "to-regex-range": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/flat-cache": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", + "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", + "dev": true, + "dependencies": { + "flatted": "^3.1.0", + "rimraf": "^3.0.2" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/flatted": { + "version": "3.2.5", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.5.tgz", + "integrity": "sha512-WIWGi2L3DyTUvUrwRKgGi9TwxQMUEqPOPQBVi71R96jZXJdFskXEmf54BoZaS1kknGODoIGASGEzBUYdyMCBJg==", + "dev": true + }, + "node_modules/fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "dev": true + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", + "dev": true + }, + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "node_modules/functional-red-black-tree": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", + "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", + "dev": true + }, + "node_modules/gauge": { + "version": "2.7.4", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", + "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", + "dev": true, + "dependencies": { + "aproba": "^1.0.3", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.0", + "object-assign": "^4.1.0", + "signal-exit": "^3.0.0", + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wide-align": "^1.1.0" + } + }, + "node_modules/gauge/node_modules/ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/gauge/node_modules/is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "dev": true, + "dependencies": { + "number-is-nan": "^1.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/gauge/node_modules/string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "dev": true, + "dependencies": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/gauge/node_modules/strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "dev": true, + "dependencies": { + "ansi-regex": "^2.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/get-caller-file": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", + "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", + "dev": true, + "engines": { + "node": "6.* || 8.* || >= 10.*" + } + }, + "node_modules/get-intrinsic": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.1.tgz", + "integrity": "sha512-kWZrnVM42QCiEA2Ig1bG8zjoIMOgxWwYCEeNdwY6Tv/cOSeGpcoX4pXHfKUxNKVoArnrEr2e9srnAxxGIraS9Q==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1", + "has": "^1.0.3", + "has-symbols": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/github-from-package": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", + "integrity": "sha1-l/tdlr/eiXMxPyDoKI75oWf6ZM4=", + "dev": true + }, + "node_modules/glob": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.0.tgz", + "integrity": "sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.3" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/globals": { + "version": "13.12.1", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.12.1.tgz", + "integrity": "sha512-317dFlgY2pdJZ9rspXDks7073GpDmXdfbM3vYYp0HAMKGDh1FfWPleI2ljVNLQX5M5lXcAslTcPTrOrMEFOjyw==", + "dev": true, + "dependencies": { + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", + "dev": true, + "dependencies": { + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.2.9", + "ignore": "^5.2.0", + "merge2": "^1.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=", + "dev": true + }, + "node_modules/htmlparser2": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-6.1.0.tgz", + "integrity": "sha512-gyyPk6rgonLFEDGoeRgQNaEUvdJ4ktTmmUh/h2t7s+M8oPpIPxgNACWa+6ESR57kXstwqPiCut0V8NRpcwgU7A==", + "dev": true, + "funding": [ + "https://github.com/fb55/htmlparser2?sponsor=1", + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ], + "dependencies": { + "domelementtype": "^2.0.1", + "domhandler": "^4.0.0", + "domutils": "^2.5.2", + "entities": "^2.0.0" + } + }, + "node_modules/ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "@types/json-schema": { - "version": "7.0.5", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.5.tgz", - "integrity": "sha512-7+2BITlgjgDhH0vvwZU/HZJVyk+2XUlvxXe8dFMedNX/aMkaOq++rMAFXc0tM7ij15QaWlbdQASBR9dihi+bDQ==", - "dev": true + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, - "@types/node": { - "version": "10.14.15", - "resolved": "https://registry.npmjs.org/@types/node/-/node-10.14.15.tgz", - "integrity": "sha512-CBR5avlLcu0YCILJiDIXeU2pTw7UK/NIxfC63m7d7CVamho1qDEzXKkOtEauQRPMy6MI8mLozth+JJkas7HY6g==", - "dev": true + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/ignore": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.0.tgz", + "integrity": "sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/import-fresh": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", + "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", + "dev": true, + "dependencies": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", + "dev": true, + "engines": { + "node": ">=0.8.19" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "dev": true, + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "node_modules/ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "dev": true + }, + "node_modules/is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-fullwidth-code-point": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", + "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "dependencies": { + "is-extglob": "^2.1.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true, + "engines": { + "node": ">=0.12.0" + } + }, + "node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "node_modules/isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true + }, + "node_modules/js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dev": true, + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", + "dev": true + }, + "node_modules/keytar": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/keytar/-/keytar-7.9.0.tgz", + "integrity": "sha512-VPD8mtVtm5JNtA2AErl6Chp06JBfy7diFQ7TQQhdpWOl6MrCRB+eRbvAZUsbGQS9kiMq0coJsy0W0vHpDCkWsQ==", + "dev": true, + "hasInstallScript": true, + "dependencies": { + "node-addon-api": "^4.3.0", + "prebuild-install": "^7.0.1" + } + }, + "node_modules/leven": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", + "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/linkify-it": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-3.0.3.tgz", + "integrity": "sha512-ynTsyrFSdE5oZ/O9GEf00kPngmOfVwazR5GKDq6EYfhlpFug3J2zybX56a2PRRpc9P+FuSoGNAwjlbDs9jJBPQ==", + "dev": true, + "dependencies": { + "uc.micro": "^1.0.1" + } + }, + "node_modules/lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "node_modules/lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true + }, + "node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/markdown-it": { + "version": "12.3.2", + "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-12.3.2.tgz", + "integrity": "sha512-TchMembfxfNVpHkbtriWltGWc+m3xszaRD0CZup7GFFhzIgQqxIfn3eGj1yZpfuflzPvfkt611B2Q/Bsk1YnGg==", + "dev": true, + "dependencies": { + "argparse": "^2.0.1", + "entities": "~2.1.0", + "linkify-it": "^3.0.1", + "mdurl": "^1.0.1", + "uc.micro": "^1.0.5" + }, + "bin": { + "markdown-it": "bin/markdown-it.js" + } + }, + "node_modules/markdown-it/node_modules/entities": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.1.0.tgz", + "integrity": "sha512-hCx1oky9PFrJ611mf0ifBLBRW8lUUVRlFolb5gWRfIELabBlbp9xZvrqZLZAs+NxFnbfQoeGd8wDkygjg7U85w==", + "dev": true, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "node_modules/mdurl": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-1.0.1.tgz", + "integrity": "sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4=", + "dev": true + }, + "node_modules/merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/micromatch": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.4.tgz", + "integrity": "sha512-pRmzw/XUcwXGpD9aI9q/0XOwLNygjETJ8y0ao0wdqprrzDa4YnxLcz7fQRZr8voh8V10kGhABbNcHVk5wHgWwg==", + "dev": true, + "dependencies": { + "braces": "^3.0.1", + "picomatch": "^2.2.3" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "dev": true, + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "node_modules/mkdirp-classic": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz", + "integrity": "sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==", + "dev": true + }, + "node_modules/ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", + "dev": true + }, + "node_modules/mute-stream": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", + "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", + "dev": true + }, + "node_modules/napi-build-utils": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-1.0.2.tgz", + "integrity": "sha512-ONmRUqK7zj7DWX0D9ADe03wbwOBZxNAfF20PlGfCWQcD3+/MakShIHrMqx9YwPTfxDdF1zLeL+RGZiR9kGMLdg==", + "dev": true + }, + "node_modules/natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", + "dev": true + }, + "node_modules/node-abi": { + "version": "3.8.0", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.8.0.tgz", + "integrity": "sha512-tzua9qWWi7iW4I42vUPKM+SfaF0vQSLAm4yO5J83mSwB7GeoWrDKC/K+8YCnYNwqP5duwazbw2X9l4m8SC2cUw==", + "dev": true, + "dependencies": { + "semver": "^7.3.5" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/node-addon-api": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-4.3.0.tgz", + "integrity": "sha512-73sE9+3UaLYYFmDsFZnqCInzPyh3MqIwZO9cw58yIqAZhONrrabrYyYe3TuIqtIiOuTXVhsGau8hcrhhwSsDIQ==", + "dev": true + }, + "node_modules/npmlog": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", + "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", + "dev": true, + "dependencies": { + "are-we-there-yet": "~1.1.2", + "console-control-strings": "~1.1.0", + "gauge": "~2.7.3", + "set-blocking": "~2.0.0" + } + }, + "node_modules/nth-check": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.0.1.tgz", + "integrity": "sha512-it1vE95zF6dTT9lBsYbxvqh0Soy4SPowchj0UBGj/V6cTPnXXtQOPUbhZ6CmGzAD/rW22LQK6E96pcdJXk4A4w==", + "dev": true, + "dependencies": { + "boolbase": "^1.0.0" + }, + "funding": { + "url": "https://github.com/fb55/nth-check?sponsor=1" + } + }, + "node_modules/number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/object-inspect": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.0.tgz", + "integrity": "sha512-Ho2z80bVIvJloH+YzRmpZVQe87+qASmBUKZDWgx9cu+KDrX2ZDH/3tMy+gXbZETVGs2M8YdxObOh7XAtim9Y0g==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/optionator": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", + "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", + "dev": true, + "dependencies": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.3" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "dependencies": { + "callsites": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/parse-semver": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/parse-semver/-/parse-semver-1.1.1.tgz", + "integrity": "sha1-mkr9bfBj3Egm+T+6SpnPIj9mbLg=", + "dev": true, + "dependencies": { + "semver": "^5.1.0" + } + }, + "node_modules/parse-semver/node_modules/semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true, + "bin": { + "semver": "bin/semver" + } + }, + "node_modules/parse5": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-6.0.1.tgz", + "integrity": "sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==", + "dev": true + }, + "node_modules/parse5-htmlparser2-tree-adapter": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/parse5-htmlparser2-tree-adapter/-/parse5-htmlparser2-tree-adapter-6.0.1.tgz", + "integrity": "sha512-qPuWvbLgvDGilKc5BoicRovlT4MtYT6JfJyBOMDsKoiT+GiuP5qyrPCnR9HcPECIJJmZh5jRndyNThnhhb/vlA==", + "dev": true, + "dependencies": { + "parse5": "^6.0.1" + } + }, + "node_modules/path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-type": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", + "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/pend": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", + "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=", + "dev": true + }, + "node_modules/picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true, + "engines": { + "node": ">=8.6" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/prebuild-install": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/prebuild-install/-/prebuild-install-7.0.1.tgz", + "integrity": "sha512-QBSab31WqkyxpnMWQxubYAHR5S9B2+r81ucocew34Fkl98FhvKIF50jIJnNOBmAZfyNV7vE5T6gd3hTVWgY6tg==", + "dev": true, + "dependencies": { + "detect-libc": "^2.0.0", + "expand-template": "^2.0.3", + "github-from-package": "0.0.0", + "minimist": "^1.2.3", + "mkdirp-classic": "^0.5.3", + "napi-build-utils": "^1.0.1", + "node-abi": "^3.3.0", + "npmlog": "^4.0.1", + "pump": "^3.0.0", + "rc": "^1.2.7", + "simple-get": "^4.0.0", + "tar-fs": "^2.0.0", + "tunnel-agent": "^0.6.0" + }, + "bin": { + "prebuild-install": "bin.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "dev": true + }, + "node_modules/pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dev": true, + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "node_modules/punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/qs": { + "version": "6.10.3", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.10.3.tgz", + "integrity": "sha512-wr7M2E0OFRfIfJZjKGieI8lBKb7fRCH4Fv5KNPEs7gJ8jadvotdsS08PzOKR7opXhZ/Xkjtt3WF9g38drmyRqQ==", + "dev": true, + "dependencies": { + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "@typescript-eslint/experimental-utils": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/experimental-utils/-/experimental-utils-3.6.1.tgz", - "integrity": "sha512-oS+hihzQE5M84ewXrTlVx7eTgc52eu+sVmG7ayLfOhyZmJ8Unvf3osyFQNADHP26yoThFfbxcibbO0d2FjnYhg==", - "dev": true, - "requires": { - "@types/json-schema": "^7.0.3", - "@typescript-eslint/types": "3.6.1", - "@typescript-eslint/typescript-estree": "3.6.1", - "eslint-scope": "^5.0.0", - "eslint-utils": "^2.0.0" - } + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, - "@typescript-eslint/parser": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-3.6.1.tgz", - "integrity": "sha512-SLihQU8RMe77YJ/jGTqOt0lMq7k3hlPVfp7v/cxMnXA9T0bQYoMDfTsNgHXpwSJM1Iq2aAJ8WqekxUwGv5F67Q==", - "dev": true, - "requires": { - "@types/eslint-visitor-keys": "^1.0.0", - "@typescript-eslint/experimental-utils": "3.6.1", - "@typescript-eslint/types": "3.6.1", - "@typescript-eslint/typescript-estree": "3.6.1", - "eslint-visitor-keys": "^1.1.0" - } + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, + "dependencies": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "bin": { + "rc": "cli.js" + } + }, + "node_modules/rc/node_modules/strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/read": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", + "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", + "dev": true, + "dependencies": { + "mute-stream": "~0.0.4" + }, + "engines": { + "node": ">=0.8" + } + }, + "node_modules/readable-stream": { + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", + "dev": true, + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/regexpp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", + "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/mysticatea" + } + }, + "node_modules/require-directory": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true, + "engines": { + "iojs": ">=1.0.0", + "node": ">=0.10.0" + } + }, + "node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "@typescript-eslint/types": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-3.6.1.tgz", - "integrity": "sha512-NPxd5yXG63gx57WDTW1rp0cF3XlNuuFFB5G+Kc48zZ+51ZnQn9yjDEsjTPQ+aWM+V+Z0I4kuTFKjKvgcT1F7xQ==", - "dev": true + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, - "@typescript-eslint/typescript-estree": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-3.6.1.tgz", - "integrity": "sha512-G4XRe/ZbCZkL1fy09DPN3U0mR6SayIv1zSeBNquRFRk7CnVLgkC2ZPj8llEMJg5Y8dJ3T76SvTGtceytniaztQ==", - "dev": true, - "requires": { - "@typescript-eslint/types": "3.6.1", - "@typescript-eslint/visitor-keys": "3.6.1", - "debug": "^4.1.1", - "glob": "^7.1.6", - "is-glob": "^4.0.1", - "lodash": "^4.17.15", - "semver": "^7.3.2", - "tsutils": "^3.17.1" - }, - "dependencies": { - "glob": { - "version": "7.1.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", - "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", - "dev": true, - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "semver": { - "version": "7.3.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz", - "integrity": "sha512-OrOb32TeeambH6UrhtShmF7CRDqhL6/5XpPNp2DuRH6+9QLw/orhp72j87v8Qa1ScDkvrrBNpZcDejAirJmfXQ==", - "dev": true - } - } + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "queue-microtask": "^1.2.2" + } + }, + "node_modules/rxjs": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", + "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", + "dev": true, + "dependencies": { + "tslib": "^1.9.0" + }, + "engines": { + "npm": ">=2.0.0" + } + }, + "node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, + "node_modules/sax": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", + "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==", + "dev": true + }, + "node_modules/semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", + "dev": true + }, + "node_modules/shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "dev": true, + "dependencies": { + "shebang-regex": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", + "dev": true + }, + "node_modules/simple-concat": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.1.tgz", + "integrity": "sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "@typescript-eslint/visitor-keys": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-3.6.1.tgz", - "integrity": "sha512-qC8Olwz5ZyMTZrh4Wl3K4U6tfms0R/mzU4/5W3XeUZptVraGVmbptJbn6h2Ey6Rb3hOs3zWoAUebZk8t47KGiQ==", - "dev": true, - "requires": { - "eslint-visitor-keys": "^1.1.0" - } + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, - "acorn": { - "version": "7.3.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.3.1.tgz", - "integrity": "sha512-tLc0wSnatxAQHVHUapaHdz72pi9KUyHjq5KyHjGg9Y8Ifdc79pTh2XvI6I1/chZbnM7QtNKzh66ooDogPZSleA==", - "dev": true + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/simple-get": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-4.0.1.tgz", + "integrity": "sha512-brv7p5WgH0jmQJr1ZDDfKDOSeWWg+OVypG99A/5vYGPqJ6pxiaHLy8nxtFjBA7oMa01ebA9gfh1uMCFqOuXxvA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" }, - "acorn-jsx": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.2.0.tgz", - "integrity": "sha512-HiUX/+K2YpkpJ+SzBffkM/AQ2YE03S0U1kjTLVpoJdhZMOWy8qvXVN9JdLqv2QsaQ6MPYQIuNmwD8zOiYUofLQ==", - "dev": true - }, - "ajv": { - "version": "6.12.3", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.3.tgz", - "integrity": "sha512-4K0cK3L1hsqk9xIb2z9vs/XU+PGJZ9PNpJRDS9YLzmNdX6jmVPfamLvTJr0aDAusnHyCHO6MjzlkAsgtqp9teA==", - "dev": true, - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "ansi-colors": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.1.tgz", - "integrity": "sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==", - "dev": true - }, - "ansi-regex": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz", - "integrity": "sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==", - "dev": true + { + "type": "patreon", + "url": "https://www.patreon.com/feross" }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "decompress-response": "^6.0.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" + } + }, + "node_modules/slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/spawn-command": { + "version": "0.0.2-1", + "resolved": "https://registry.npmjs.org/spawn-command/-/spawn-command-0.0.2-1.tgz", + "integrity": "sha1-YvXpRmmBwbeW3Fkpk34RycaSG9A=", + "dev": true + }, + "node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "dependencies": { + "safe-buffer": "~5.1.0" + } + }, + "node_modules/string-width": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", + "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", + "dev": true, + "dependencies": { + "emoji-regex": "^8.0.0", + "is-fullwidth-code-point": "^3.0.0", + "strip-ansi": "^6.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-ansi": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", + "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", + "dev": true, + "dependencies": { + "ansi-regex": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-json-comments": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/supports-color?sponsor=1" + } + }, + "node_modules/supports-color/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/tar-fs": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.1.tgz", + "integrity": "sha512-V0r2Y9scmbDRLCNex/+hYzvp/zyYjvFbHPNgVTKfQvVrb6guiE/fxP+XblDNR011utopbkex2nM4dHNV6GDsng==", + "dev": true, + "dependencies": { + "chownr": "^1.1.1", + "mkdirp-classic": "^0.5.2", + "pump": "^3.0.0", + "tar-stream": "^2.1.4" + } + }, + "node_modules/tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "dev": true, + "dependencies": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/tar-stream/node_modules/readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", + "dev": true + }, + "node_modules/tmp": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz", + "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==", + "dev": true, + "dependencies": { + "rimraf": "^3.0.0" + }, + "engines": { + "node": ">=8.17.0" + } + }, + "node_modules/to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "dependencies": { + "is-number": "^7.0.0" + }, + "engines": { + "node": ">=8.0" + } + }, + "node_modules/tree-kill": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", + "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", + "dev": true, + "bin": { + "tree-kill": "cli.js" + } + }, + "node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/tsutils": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", + "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", + "dev": true, + "dependencies": { + "tslib": "^1.8.1" + }, + "engines": { + "node": ">= 6" + }, + "peerDependencies": { + "typescript": ">=2.8.0 || >= 3.2.0-dev || >= 3.3.0-dev || >= 3.4.0-dev || >= 3.5.0-dev || >= 3.6.0-dev || >= 3.6.0-beta || >= 3.7.0-dev || >= 3.7.0-beta" + } + }, + "node_modules/tunnel": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz", + "integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==", + "dev": true, + "engines": { + "node": ">=0.6.11 <=0.7.0 || >=0.7.3" + } + }, + "node_modules/tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "dev": true, + "dependencies": { + "safe-buffer": "^5.0.1" + }, + "engines": { + "node": "*" + } + }, + "node_modules/type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/type-fest": { + "version": "0.20.2", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", + "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/typed-rest-client": { + "version": "1.8.6", + "resolved": "https://registry.npmjs.org/typed-rest-client/-/typed-rest-client-1.8.6.tgz", + "integrity": "sha512-xcQpTEAJw2DP7GqVNECh4dD+riS+C1qndXLfBCJ3xk0kqprtGN491P5KlmrDbKdtuW8NEcP/5ChxiJI3S9WYTA==", + "dev": true, + "dependencies": { + "qs": "^6.9.1", + "tunnel": "0.0.6", + "underscore": "^1.12.1" + } + }, + "node_modules/typescript": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.6.2.tgz", + "integrity": "sha512-HM/hFigTBHZhLXshn9sN37H085+hQGeJHJ/X7LpBWLID/fbc2acUMfU+lGD98X81sKP+pFa9f0DZmCwB9GnbAg==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=4.2.0" + } + }, + "node_modules/uc.micro": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-1.0.6.tgz", + "integrity": "sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA==", + "dev": true + }, + "node_modules/underscore": { + "version": "1.13.2", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.2.tgz", + "integrity": "sha512-ekY1NhRzq0B08g4bGuX4wd2jZx5GnKz6mKSqFL4nqBlfyMGiG10gDFhDTMEfYmDL6Jy0FUIZp7wiRB+0BP7J2g==", + "dev": true + }, + "node_modules/uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "dependencies": { + "punycode": "^2.1.0" + } + }, + "node_modules/url-join": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/url-join/-/url-join-4.0.1.tgz", + "integrity": "sha512-jk1+QP6ZJqyOiuEI9AEWQfju/nB2Pw466kbA0LEZljHwKeMgd9WrAEgEGxjPDD2+TNbbb37rTyhEfrCXfuKXnA==", + "dev": true + }, + "node_modules/util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true + }, + "node_modules/v8-compile-cache": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", + "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==", + "dev": true + }, + "node_modules/vsce": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/vsce/-/vsce-2.7.0.tgz", + "integrity": "sha512-CKU34wrQlbKDeJCRBkd1a8iwF9EvNxcYMg9hAUH6AxFGR6Wo2IKWwt3cJIcusHxx6XdjDHWlfAS/fJN30uvVnA==", + "dev": true, + "dependencies": { + "azure-devops-node-api": "^11.0.1", + "chalk": "^2.4.2", + "cheerio": "^1.0.0-rc.9", + "commander": "^6.1.0", + "glob": "^7.0.6", + "hosted-git-info": "^4.0.2", + "keytar": "^7.7.0", + "leven": "^3.1.0", + "markdown-it": "^12.3.2", + "mime": "^1.3.4", + "minimatch": "^3.0.3", + "parse-semver": "^1.1.1", + "read": "^1.0.7", + "semver": "^5.1.0", + "tmp": "^0.2.1", + "typed-rest-client": "^1.8.4", + "url-join": "^4.0.1", + "xml2js": "^0.4.23", + "yauzl": "^2.3.1", + "yazl": "^2.2.2" + }, + "bin": { + "vsce": "vsce" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/vsce/node_modules/hosted-git-info": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.1.0.tgz", + "integrity": "sha512-kyCuEOWjJqZuDbRHzL8V93NzQhwIB71oFWSyzVo+KPZI+pnQPPxucdkrOZvkLRnrf5URsQM+IJ09Dw29cRALIA==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/vsce/node_modules/semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true, + "bin": { + "semver": "bin/semver" + } + }, + "node_modules/which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "node-which": "bin/node-which" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/wide-align": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.5.tgz", + "integrity": "sha512-eDMORYaPNZ4sQIuuYPDHdQvf4gyCF9rEEV/yPxGfwPkRodwEgiMUUXTx/dex+Me0wxx53S+NgUHaP7y3MGlDmg==", + "dev": true, + "dependencies": { + "string-width": "^1.0.2 || 2 || 3 || 4" + } + }, + "node_modules/word-wrap": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz", + "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/wrap-ansi": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", + "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/wrap-ansi?sponsor=1" + } + }, + "node_modules/wrap-ansi/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/wrap-ansi/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/wrap-ansi/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + }, + "node_modules/xml2js": { + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/xml2js/-/xml2js-0.4.23.tgz", + "integrity": "sha512-ySPiMjM0+pLDftHgXY4By0uswI3SPKLDw/i3UXbnO8M/p28zqexCUoPmQFrYD+/1BzhGJSs2i1ERWKJAtiLrug==", + "dev": true, + "dependencies": { + "sax": ">=0.6.0", + "xmlbuilder": "~11.0.0" + }, + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/xmlbuilder": { + "version": "11.0.1", + "resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-11.0.1.tgz", + "integrity": "sha512-fDlsI/kFEx7gLvbecc0/ohLG50fugQp8ryHzMTuW9vSa1GJ0XYWKnhsUx7oie3G98+r56aTQIUB4kht42R3JvA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/yargs": { + "version": "16.2.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", + "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", + "dev": true, + "dependencies": { + "cliui": "^7.0.2", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.0", + "y18n": "^5.0.5", + "yargs-parser": "^20.2.2" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/yargs-parser": { + "version": "20.2.9", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.9.tgz", + "integrity": "sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/yauzl": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", + "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", + "dev": true, + "dependencies": { + "buffer-crc32": "~0.2.3", + "fd-slicer": "~1.1.0" + } + }, + "node_modules/yazl": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/yazl/-/yazl-2.5.1.tgz", + "integrity": "sha512-phENi2PLiHnHb6QBVot+dJnaAZ0xosj7p3fWl+znIjBDlnMI2PsZCJZ306BPTFOaHf5qdDEI8x5qFrSOBN5vrw==", + "dev": true, + "dependencies": { + "buffer-crc32": "~0.2.3" + } + } + }, + "dependencies": { + "@eslint/eslintrc": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.2.1.tgz", + "integrity": "sha512-bxvbYnBPN1Gibwyp6NrpnFzA3YtRL3BBAyEAFVIpNTm2Rn4Vy87GA5M4aSn3InRrlsbX5N0GW7XIx+U4SAEKdQ==", + "dev": true, + "requires": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.3.1", + "globals": "^13.9.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.0.4", + "strip-json-comments": "^3.1.1" + } + }, + "@humanwhocodes/config-array": { + "version": "0.9.5", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.9.5.tgz", + "integrity": "sha512-ObyMyWxZiCu/yTisA7uzx81s40xR2fD5Cg/2Kq7G02ajkNubJf6BopgDTmDyc3U7sXpNKM8cYOw7s7Tyr+DnCw==", + "dev": true, + "requires": { + "@humanwhocodes/object-schema": "^1.2.1", + "debug": "^4.1.1", + "minimatch": "^3.0.4" + } + }, + "@humanwhocodes/object-schema": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz", + "integrity": "sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==", + "dev": true + }, + "@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "requires": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + } + }, + "@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true + }, + "@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "requires": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + } + }, + "@types/node": { + "version": "17.0.21", + "resolved": "https://registry.npmjs.org/@types/node/-/node-17.0.21.tgz", + "integrity": "sha512-DBZCJbhII3r90XbQxI8Y9IjjiiOGlZ0Hr32omXIZvwwZ7p4DMMXGrKXVyPfuoBOri9XNtL0UK69jYIBIsRX3QQ==", + "dev": true + }, + "@typescript-eslint/parser": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.15.0.tgz", + "integrity": "sha512-NGAYP/+RDM2sVfmKiKOCgJYPstAO40vPAgACoWPO/+yoYKSgAXIFaBKsV8P0Cc7fwKgvj27SjRNX4L7f4/jCKQ==", + "dev": true, + "requires": { + "@typescript-eslint/scope-manager": "5.15.0", + "@typescript-eslint/types": "5.15.0", + "@typescript-eslint/typescript-estree": "5.15.0", + "debug": "^4.3.2" + } + }, + "@typescript-eslint/scope-manager": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.15.0.tgz", + "integrity": "sha512-EFiZcSKrHh4kWk0pZaa+YNJosvKE50EnmN4IfgjkA3bTHElPtYcd2U37QQkNTqwMCS7LXeDeZzEqnsOH8chjSg==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.15.0", + "@typescript-eslint/visitor-keys": "5.15.0" + } + }, + "@typescript-eslint/types": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.15.0.tgz", + "integrity": "sha512-yEiTN4MDy23vvsIksrShjNwQl2vl6kJeG9YkVJXjXZnkJElzVK8nfPsWKYxcsGWG8GhurYXP4/KGj3aZAxbeOA==", + "dev": true + }, + "@typescript-eslint/typescript-estree": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.15.0.tgz", + "integrity": "sha512-Hb0e3dGc35b75xLzixM3cSbG1sSbrTBQDfIScqdyvrfJZVEi4XWAT+UL/HMxEdrJNB8Yk28SKxPLtAhfCbBInA==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.15.0", + "@typescript-eslint/visitor-keys": "5.15.0", + "debug": "^4.3.2", + "globby": "^11.0.4", + "is-glob": "^4.0.3", + "semver": "^7.3.5", + "tsutils": "^3.21.0" + } + }, + "@typescript-eslint/visitor-keys": { + "version": "5.15.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.15.0.tgz", + "integrity": "sha512-+vX5FKtgvyHbmIJdxMJ2jKm9z2BIlXJiuewI8dsDYMp5LzPUcuTT78Ya5iwvQg3VqSVdmxyM8Anj1Jeq7733ZQ==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.15.0", + "eslint-visitor-keys": "^3.0.0" + } + }, + "acorn": { + "version": "8.7.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.7.0.tgz", + "integrity": "sha512-V/LGr1APy+PXIwKebEWrkZPwoeoF+w1jiOBUmuxuiUIaOHtob8Qc9BTrYo7VuI5fR8tqsy+buA2WFooR5olqvQ==", + "dev": true + }, + "acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, + "requires": {} + }, + "ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + } + }, + "ansi-regex": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", + "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", + "dev": true + }, + "ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, + "requires": { + "color-convert": "^1.9.0" + } + }, + "aproba": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", + "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==", + "dev": true + }, + "are-we-there-yet": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.7.tgz", + "integrity": "sha512-nxwy40TuMiUGqMyRHgCSWZ9FM4VAoRP4xUYSTv5ImRog+h9yISPbVH7H8fASCIzYn9wlEv4zvFL7uKDMCFQm3g==", + "dev": true, + "requires": { + "delegates": "^1.0.0", + "readable-stream": "^2.0.6" + } + }, + "argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", + "dev": true + }, + "array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", + "dev": true + }, + "azure-devops-node-api": { + "version": "11.1.1", + "resolved": "https://registry.npmjs.org/azure-devops-node-api/-/azure-devops-node-api-11.1.1.tgz", + "integrity": "sha512-XDG91XzLZ15reP12s3jFkKS8oiagSICjnLwxEYieme4+4h3ZveFOFRA4iYIG40RyHXsiI0mefFYYMFIJbMpWcg==", + "dev": true, + "requires": { + "tunnel": "0.0.6", + "typed-rest-client": "^1.8.4" + } + }, + "balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "dev": true + }, + "bl": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", + "dev": true, + "requires": { + "buffer": "^5.5.0", + "inherits": "^2.0.4", + "readable-stream": "^3.4.0" + }, + "dependencies": { + "readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "requires": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + } + } + } + }, + "boolbase": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", + "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24=", + "dev": true + }, + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "braces": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", + "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "dev": true, + "requires": { + "fill-range": "^7.0.1" + } + }, + "buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "dev": true, + "requires": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "buffer-crc32": { + "version": "0.2.13", + "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", + "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", + "dev": true + }, + "call-bind": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", + "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", + "dev": true, + "requires": { + "function-bind": "^1.1.1", + "get-intrinsic": "^1.0.2" + } + }, + "callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true + }, + "chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, + "requires": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "dependencies": { + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } + } + }, + "cheerio": { + "version": "1.0.0-rc.10", + "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0-rc.10.tgz", + "integrity": "sha512-g0J0q/O6mW8z5zxQ3A8E8J1hUgp4SMOvEoW/x84OwyHKe/Zccz83PVT4y5Crcr530FV6NgmKI1qvGTKVl9XXVw==", + "dev": true, + "requires": { + "cheerio-select": "^1.5.0", + "dom-serializer": "^1.3.2", + "domhandler": "^4.2.0", + "htmlparser2": "^6.1.0", + "parse5": "^6.0.1", + "parse5-htmlparser2-tree-adapter": "^6.0.1", + "tslib": "^2.2.0" + }, + "dependencies": { + "tslib": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.3.1.tgz", + "integrity": "sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw==", + "dev": true + } + } + }, + "cheerio-select": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/cheerio-select/-/cheerio-select-1.5.0.tgz", + "integrity": "sha512-qocaHPv5ypefh6YNxvnbABM07KMxExbtbfuJoIie3iZXX1ERwYmJcIiRrr9H05ucQP1k28dav8rpdDgjQd8drg==", + "dev": true, + "requires": { + "css-select": "^4.1.3", + "css-what": "^5.0.1", + "domelementtype": "^2.2.0", + "domhandler": "^4.2.0", + "domutils": "^2.7.0" + } + }, + "chownr": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", + "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", + "dev": true + }, + "cliui": { + "version": "7.0.4", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", + "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", + "dev": true, + "requires": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^7.0.0" + } + }, + "code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", + "dev": true + }, + "color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, + "requires": { + "color-name": "1.1.3" + } + }, + "color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", + "dev": true + }, + "commander": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-6.2.1.tgz", + "integrity": "sha512-U7VdrJFnJgo4xjrHpTzu0yrHPGImdsmD95ZlgYSEajAn2JKzDhDTPG9kBTefmObL2w/ngeZnilk+OV9CG3d7UA==", + "dev": true + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", + "dev": true + }, + "concurrently": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-7.0.0.tgz", + "integrity": "sha512-WKM7PUsI8wyXpF80H+zjHP32fsgsHNQfPLw/e70Z5dYkV7hF+rf8q3D+ScWJIEr57CpkO3OWBko6hwhQLPR8Pw==", + "dev": true, + "requires": { + "chalk": "^4.1.0", + "date-fns": "^2.16.1", + "lodash": "^4.17.21", + "rxjs": "^6.6.3", + "spawn-command": "^0.0.2-1", + "supports-color": "^8.1.0", + "tree-kill": "^1.2.2", + "yargs": "^16.2.0" + }, + "dependencies": { "ansi-styles": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", - "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", - "dev": true, - "requires": { - "color-convert": "^1.9.0" - } - }, - "argparse": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", - "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", - "dev": true, - "requires": { - "sprintf-js": "~1.0.2" - } - }, - "astral-regex": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-1.0.0.tgz", - "integrity": "sha512-+Ryf6g3BKoRc7jfp7ad8tM4TtMiaWvbF/1/sQcZPkkS7ag3D5nMBCe2UfOTONtAkaG0tO0ij3C5Lwmf1EiyjHg==", - "dev": true - }, - "azure-devops-node-api": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/azure-devops-node-api/-/azure-devops-node-api-7.2.0.tgz", - "integrity": "sha512-pMfGJ6gAQ7LRKTHgiRF+8iaUUeGAI0c8puLaqHLc7B8AR7W6GJLozK9RFeUHFjEGybC9/EB3r67WPd7e46zQ8w==", - "dev": true, - "requires": { - "os": "0.1.1", - "tunnel": "0.0.4", - "typed-rest-client": "1.2.0", - "underscore": "1.8.3" - } - }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", - "dev": true - }, - "boolbase": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", - "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24=", - "dev": true - }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "dev": true, - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "buffer-crc32": { - "version": "0.2.13", - "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", - "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", - "dev": true - }, - "callsites": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", - "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", - "dev": true - }, - "camelcase": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", - "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", - "dev": true + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "requires": { + "color-convert": "^2.0.1" + } }, "chalk": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz", - "integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==", - "dev": true, - "requires": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "dependencies": { - "ansi-styles": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.2.1.tgz", - "integrity": "sha512-9VGjrMsG1vePxcSweQsN20KY/c4zN0h9fLjqAbwbPfahM3t+NL+M9HC8xeXG2I8pX5NoamTGNuomEUFI7fcUjA==", - "dev": true, - "requires": { - "@types/color-name": "^1.1.1", - "color-convert": "^2.0.1" - } - }, - "color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "requires": { - "color-name": "~1.1.4" - } - }, - "color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, - "has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true - }, - "supports-color": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.1.0.tgz", - "integrity": "sha512-oRSIpR8pxT1Wr2FquTNnGet79b3BWljqOuoW/h4oBhxJ/HUbX5nX6JSruTkvXDCFMwDPvsaTTbvMLKZWSy0R5g==", - "dev": true, - "requires": { - "has-flag": "^4.0.0" - } - } - } - }, - "cheerio": { - "version": "1.0.0-rc.3", - "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0-rc.3.tgz", - "integrity": "sha512-0td5ijfUPuubwLUu0OBoe98gZj8C/AA+RW3v67GPlGOrvxWjZmBXiBCRU+I8VEiNyJzjth40POfHiz2RB3gImA==", - "dev": true, - "requires": { - "css-select": "~1.2.0", - "dom-serializer": "~0.1.1", - "entities": "~1.1.1", - "htmlparser2": "^3.9.1", - "lodash": "^4.15.0", - "parse5": "^3.0.1" - } - }, - "cliui": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-5.0.0.tgz", - "integrity": "sha512-PYeGSEmmHM6zvoef2w8TPzlrnNpXIjTipYK780YswmIP9vjxmd6Y2a3CB2Ks6/AU8NHjZugXvo8w3oWM2qnwXA==", - "dev": true, - "requires": { - "string-width": "^3.1.0", - "strip-ansi": "^5.2.0", - "wrap-ansi": "^5.1.0" + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "dependencies": { + "supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "requires": { + "has-flag": "^4.0.0" + } } + } }, "color-convert": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.2.tgz", - "integrity": "sha512-3NUJZdhMhcdPn8vJ9v2UQJoH0qqoGUkYTgFEPZaPjEtwmmKUfNV46zZmgB2M5M4DCEQHMaCfWHCxiBflLm04Tg==", - "dev": true, - "requires": { - "color-name": "1.1.1" - } + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "requires": { + "color-name": "~1.1.4" + } }, "color-name": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.1.tgz", - "integrity": "sha1-SxQVMEz1ACjqgWQ2Q72C6gWANok=", - "dev": true - }, - "commander": { - "version": "2.20.3", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", - "dev": true - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", - "dev": true - }, - "concurrently": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-5.1.0.tgz", - "integrity": "sha512-9ViZMu3OOCID3rBgU31mjBftro2chOop0G2u1olq1OuwRBVRw/GxHTg80TVJBUTJfoswMmEUeuOg1g1yu1X2dA==", - "dev": true, - "requires": { - "chalk": "^2.4.2", - "date-fns": "^2.0.1", - "lodash": "^4.17.15", - "read-pkg": "^4.0.1", - "rxjs": "^6.5.2", - "spawn-command": "^0.0.2-1", - "supports-color": "^6.1.0", - "tree-kill": "^1.2.2", - "yargs": "^13.3.0" - }, - "dependencies": { - "chalk": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", - "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", - "dev": true, - "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" - }, - "dependencies": { - "supports-color": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", - "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", - "dev": true, - "requires": { - "has-flag": "^3.0.0" - } - } - } - } - } - }, - "cross-spawn": { - "version": "7.0.3", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", - "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", - "dev": true, - "requires": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - } - }, - "css-select": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/css-select/-/css-select-1.2.0.tgz", - "integrity": "sha1-KzoRBTnFNV8c2NMUYj6HCxIeyFg=", - "dev": true, - "requires": { - "boolbase": "~1.0.0", - "css-what": "2.1", - "domutils": "1.5.1", - "nth-check": "~1.0.1" - } - }, - "css-what": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/css-what/-/css-what-2.1.3.tgz", - "integrity": "sha512-a+EPoD+uZiNfh+5fxw2nO9QwFa6nJe2Or35fGY6Ipw1R3R4AGz1d1TEZrCegvw2YTmZ0jXirGYlzxxpYSHwpEg==", - "dev": true - }, - "date-fns": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.9.0.tgz", - "integrity": "sha512-khbFLu/MlzLjEzy9Gh8oY1hNt/Dvxw3J6Rbc28cVoYWQaC1S3YI4xwkF9ZWcjDLscbZlY9hISMr66RFzZagLsA==", - "dev": true - }, - "debug": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.1.1.tgz", - "integrity": "sha512-pYAIzeRo8J6KPEaJ0VWOh5Pzkbw/RetuzehGM7QRRX5he4fPHx2rdKMB256ehJCkX+XRQm16eZLqLNS8RSZXZw==", - "dev": true, - "requires": { - "ms": "^2.1.1" - } - }, - "decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", - "dev": true - }, - "deep-is": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", - "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", - "dev": true - }, - "denodeify": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/denodeify/-/denodeify-1.2.1.tgz", - "integrity": "sha1-OjYof1A05pnnV3kBBSwubJQlFjE=", - "dev": true - }, - "doctrine": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", - "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", - "dev": true, - "requires": { - "esutils": "^2.0.2" - } - }, - "dom-serializer": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-0.1.1.tgz", - "integrity": "sha512-l0IU0pPzLWSHBcieZbpOKgkIn3ts3vAh7ZuFyXNwJxJXk/c4Gwj9xaTJwIDVQCXawWD0qb3IzMGH5rglQaO0XA==", - "dev": true, - "requires": { - "domelementtype": "^1.3.0", - "entities": "^1.1.1" - } - }, - "domelementtype": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-1.3.1.tgz", - "integrity": "sha512-BSKB+TSpMpFI/HOxCNr1O8aMOTZ8hT3pM3GQ0w/mWRmkhEDSFJkkyzz4XQsBV44BChwGkrDfMyjVD0eA2aFV3w==", - "dev": true - }, - "domhandler": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-2.4.2.tgz", - "integrity": "sha512-JiK04h0Ht5u/80fdLMCEmV4zkNh2BcoMFBmZ/91WtYZ8qVXSKjiw7fXMgFPnHcSZgOo3XdinHvmnDUeMf5R4wA==", - "dev": true, - "requires": { - "domelementtype": "1" - } - }, - "domutils": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/domutils/-/domutils-1.5.1.tgz", - "integrity": "sha1-3NhIiib1Y9YQeeSMn3t+Mjc2gs8=", - "dev": true, - "requires": { - "dom-serializer": "0", - "domelementtype": "1" - } - }, - "emoji-regex": { - "version": "7.0.3", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-7.0.3.tgz", - "integrity": "sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA==", - "dev": true - }, - "enquirer": { - "version": "2.3.6", - "resolved": "https://registry.npmjs.org/enquirer/-/enquirer-2.3.6.tgz", - "integrity": "sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg==", - "dev": true, - "requires": { - "ansi-colors": "^4.1.1" - } - }, - "entities": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/entities/-/entities-1.1.2.tgz", - "integrity": "sha512-f2LZMYl1Fzu7YSBKg+RoROelpOaNrcGmE9AZubeDfrCEia483oW4MI4VyFd5VNHIgQ/7qm1I0wUHK1eJnn2y2w==", - "dev": true - }, - "error-ex": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", - "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", - "dev": true, - "requires": { - "is-arrayish": "^0.2.1" - } - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "dev": true - }, - "eslint": { - "version": "7.4.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-7.4.0.tgz", - "integrity": "sha512-gU+lxhlPHu45H3JkEGgYhWhkR9wLHHEXC9FbWFnTlEkbKyZKWgWRLgf61E8zWmBuI6g5xKBph9ltg3NtZMVF8g==", - "dev": true, - "requires": { - "@babel/code-frame": "^7.0.0", - "ajv": "^6.10.0", - "chalk": "^4.0.0", - "cross-spawn": "^7.0.2", - "debug": "^4.0.1", - "doctrine": "^3.0.0", - "enquirer": "^2.3.5", - "eslint-scope": "^5.1.0", - "eslint-utils": "^2.0.0", - "eslint-visitor-keys": "^1.2.0", - "espree": "^7.1.0", - "esquery": "^1.2.0", - "esutils": "^2.0.2", - "file-entry-cache": "^5.0.1", - "functional-red-black-tree": "^1.0.1", - "glob-parent": "^5.0.0", - "globals": "^12.1.0", - "ignore": "^4.0.6", - "import-fresh": "^3.0.0", - "imurmurhash": "^0.1.4", - "is-glob": "^4.0.0", - "js-yaml": "^3.13.1", - "json-stable-stringify-without-jsonify": "^1.0.1", - "levn": "^0.4.1", - "lodash": "^4.17.14", - "minimatch": "^3.0.4", - "natural-compare": "^1.4.0", - "optionator": "^0.9.1", - "progress": "^2.0.0", - "regexpp": "^3.1.0", - "semver": "^7.2.1", - "strip-ansi": "^6.0.0", - "strip-json-comments": "^3.1.0", - "table": "^5.2.3", - "text-table": "^0.2.0", - "v8-compile-cache": "^2.0.3" - }, - "dependencies": { - "ansi-regex": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.0.tgz", - "integrity": "sha512-bY6fj56OUQ0hU1KjFNDQuJFezqKdrAyFdIevADiqrWHwSlbmBNMHp5ak2f40Pm8JTFyM2mqxkG6ngkHO11f/lg==", - "dev": true - }, - "semver": { - "version": "7.3.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz", - "integrity": "sha512-OrOb32TeeambH6UrhtShmF7CRDqhL6/5XpPNp2DuRH6+9QLw/orhp72j87v8Qa1ScDkvrrBNpZcDejAirJmfXQ==", - "dev": true - }, - "strip-ansi": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.0.tgz", - "integrity": "sha512-AuvKTrTfQNYNIctbR1K/YGTR1756GycPsg7b9bdV9Duqur4gv6aKqHXah67Z8ImS7WEz5QVcOtlfW2rZEugt6w==", - "dev": true, - "requires": { - "ansi-regex": "^5.0.0" - } - } - } - }, - "eslint-scope": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.0.tgz", - "integrity": "sha512-iiGRvtxWqgtx5m8EyQUJihBloE4EnYeGE/bz1wSPwJE6tZuJUtHlhqDM4Xj2ukE8Dyy1+HCZ4hE0fzIVMzb58w==", - "dev": true, - "requires": { - "esrecurse": "^4.1.0", - "estraverse": "^4.1.1" - } - }, - "eslint-utils": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-2.1.0.tgz", - "integrity": "sha512-w94dQYoauyvlDc43XnGB8lU3Zt713vNChgt4EWwhXAP2XkBvndfxF0AgIqKOOasjPIPzj9JqgwkwbCYD0/V3Zg==", - "dev": true, - "requires": { - "eslint-visitor-keys": "^1.1.0" - } - }, - "eslint-visitor-keys": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", - "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", - "dev": true - }, - "espree": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-7.1.0.tgz", - "integrity": "sha512-dcorZSyfmm4WTuTnE5Y7MEN1DyoPYy1ZR783QW1FJoenn7RailyWFsq/UL6ZAAA7uXurN9FIpYyUs3OfiIW+Qw==", - "dev": true, - "requires": { - "acorn": "^7.2.0", - "acorn-jsx": "^5.2.0", - "eslint-visitor-keys": "^1.2.0" - } - }, - "esprima": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", - "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", - "dev": true - }, - "esquery": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.3.1.tgz", - "integrity": "sha512-olpvt9QG0vniUBZspVRN6lwB7hOZoTRtT+jzR+tS4ffYx2mzbw+z0XCOk44aaLYKApNX5nMm+E+P6o25ip/DHQ==", - "dev": true, - "requires": { - "estraverse": "^5.1.0" - }, - "dependencies": { - "estraverse": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.1.0.tgz", - "integrity": "sha512-FyohXK+R0vE+y1nHLoBM7ZTyqRpqAlhdZHCWIWEviFLiGB8b04H6bQs8G+XTthacvT8VuwvteiP7RJSxMs8UEw==", - "dev": true - } - } - }, - "esrecurse": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.2.1.tgz", - "integrity": "sha512-64RBB++fIOAXPw3P9cy89qfMlvZEXZkqqJkjqqXIvzP5ezRZjW+lPWjw35UX/3EhUPFYbg5ER4JYgDw4007/DQ==", - "dev": true, - "requires": { - "estraverse": "^4.1.0" - } - }, - "estraverse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", - "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", - "dev": true - }, - "esutils": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", - "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", - "dev": true - }, - "fast-deep-equal": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "dev": true - }, - "fast-json-stable-stringify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", - "dev": true - }, - "fast-levenshtein": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", - "dev": true - }, - "fd-slicer": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", - "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", - "dev": true, - "requires": { - "pend": "~1.2.0" - } - }, - "file-entry-cache": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-5.0.1.tgz", - "integrity": "sha512-bCg29ictuBaKUwwArK4ouCaqDgLZcysCFLmM/Yn/FDoqndh/9vNuQfXRDvTuXKLxfD/JtZQGKFT8MGcJBK644g==", - "dev": true, - "requires": { - "flat-cache": "^2.0.1" - } - }, - "find-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-3.0.0.tgz", - "integrity": "sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==", - "dev": true, - "requires": { - "locate-path": "^3.0.0" - } - }, - "flat-cache": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-2.0.1.tgz", - "integrity": "sha512-LoQe6yDuUMDzQAEH8sgmh4Md6oZnc/7PjtwjNFSzveXqSHt6ka9fPBuso7IGf9Rz4uqnSnWiFH2B/zj24a5ReA==", - "dev": true, - "requires": { - "flatted": "^2.0.0", - "rimraf": "2.6.3", - "write": "1.0.3" - } - }, - "flatted": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/flatted/-/flatted-2.0.2.tgz", - "integrity": "sha512-r5wGx7YeOwNWNlCA0wQ86zKyDLMQr+/RB8xy74M4hTphfmjlijTSSXGuH8rnvKZnfT9i+75zmd8jcKdMR4O6jA==", - "dev": true - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", - "dev": true - }, - "functional-red-black-tree": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", - "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", - "dev": true - }, - "get-caller-file": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", - "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", - "dev": true - }, - "glob": { - "version": "7.1.4", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz", - "integrity": "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==", - "dev": true, - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "glob-parent": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.1.tgz", - "integrity": "sha512-FnI+VGOpnlGHWZxthPGR+QhR78fuiK0sNLkHQv+bL9fQi57lNNdquIbna/WrfROrolq8GK5Ek6BiMwqL/voRYQ==", - "dev": true, - "requires": { - "is-glob": "^4.0.1" - } - }, - "globals": { - "version": "12.4.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-12.4.0.tgz", - "integrity": "sha512-BWICuzzDvDoH54NHKCseDanAhE3CeDorgDL5MT6LMXXj2WCnd9UC2szdk4AWLfjdgNBCXLUanXYcpBBKOSWGwg==", - "dev": true, - "requires": { - "type-fest": "^0.8.1" - } + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true }, "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", - "dev": true - }, - "hosted-git-info": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.8.5.tgz", - "integrity": "sha512-kssjab8CvdXfcXMXVcvsXum4Hwdq9XGtRD3TteMEvEbq0LXyiNQr6AprqKqfeaDXze7SxWvRxdpwE6ku7ikLkg==", - "dev": true - }, - "htmlparser2": { - "version": "3.10.1", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-3.10.1.tgz", - "integrity": "sha512-IgieNijUMbkDovyoKObU1DUhm1iwNYE/fuifEoEHfd1oZKZDaONBSkal7Y01shxsM49R4XaMdGez3WnF9UfiCQ==", - "dev": true, - "requires": { - "domelementtype": "^1.3.1", - "domhandler": "^2.3.0", - "domutils": "^1.5.1", - "entities": "^1.1.1", - "inherits": "^2.0.1", - "readable-stream": "^3.1.1" - } - }, - "ignore": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", - "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", - "dev": true - }, - "import-fresh": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.2.1.tgz", - "integrity": "sha512-6e1q1cnWP2RXD9/keSkxHScg508CdXqXWgWBaETNhyuBFz+kUZlKboh+ISK+bU++DmbHimVBrOz/zzPe0sZ3sQ==", - "dev": true, - "requires": { - "parent-module": "^1.0.0", - "resolve-from": "^4.0.0" - } - }, - "imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", - "dev": true - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "dev": true, - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "dev": true - }, - "is-arrayish": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=", - "dev": true - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true - }, - "is-glob": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz", - "integrity": "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==", - "dev": true, - "requires": { - "is-extglob": "^2.1.1" - } - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", - "dev": true - }, - "js-tokens": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", - "dev": true - }, - "js-yaml": { - "version": "3.14.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.0.tgz", - "integrity": "sha512-/4IbIeHcD9VMHFqDR/gQ7EdZdLimOvW2DdcxFjdyyZ9NsbS+ccrXqVWDtab/lRl5AlUqmpBx8EhPaWR+OtY17A==", - "dev": true, - "requires": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" - } - }, - "json-parse-better-errors": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", - "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==", - "dev": true - }, - "json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true - }, - "json-stable-stringify-without-jsonify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", - "integrity": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", - "dev": true - }, - "leven": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", - "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", - "dev": true - }, - "levn": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", - "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", - "dev": true, - "requires": { - "prelude-ls": "^1.2.1", - "type-check": "~0.4.0" - } - }, - "linkify-it": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-2.2.0.tgz", - "integrity": "sha512-GnAl/knGn+i1U/wjBz3akz2stz+HrHLsxMwHQGofCDfPvlf+gDKN58UtfmUquTY4/MXeE2x7k19KQmeoZi94Iw==", - "dev": true, - "requires": { - "uc.micro": "^1.0.1" - } - }, - "locate-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-3.0.0.tgz", - "integrity": "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==", - "dev": true, - "requires": { - "p-locate": "^3.0.0", - "path-exists": "^3.0.0" - } - }, - "lodash": { - "version": "4.17.15", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz", - "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==", - "dev": true - }, - "markdown-it": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-10.0.0.tgz", - "integrity": "sha512-YWOP1j7UbDNz+TumYP1kpwnP0aEa711cJjrAQrzd0UXlbJfc5aAq0F/PZHjiioqDC1NKgvIMX+o+9Bk7yuM2dg==", - "dev": true, - "requires": { - "argparse": "^1.0.7", - "entities": "~2.0.0", - "linkify-it": "^2.0.0", - "mdurl": "^1.0.1", - "uc.micro": "^1.0.5" - }, - "dependencies": { - "entities": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/entities/-/entities-2.0.3.tgz", - "integrity": "sha512-MyoZ0jgnLvB2X3Lg5HqpFmn1kybDiIfEQmKzTb5apr51Rb+T3KdmMiqa70T+bhGnyv7bQ6WMj2QMHpGMmlrUYQ==", - "dev": true - } - } - }, - "mdurl": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-1.0.1.tgz", - "integrity": "sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4=", - "dev": true - }, - "mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "dev": true - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "dev": true, - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", - "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", - "dev": true - }, - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dev": true, - "requires": { - "minimist": "^1.2.5" - } - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "dev": true - }, - "mute-stream": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", - "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", - "dev": true - }, - "natural-compare": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", - "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", - "dev": true - }, - "normalize-package-data": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", - "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", - "dev": true, - "requires": { - "hosted-git-info": "^2.1.4", - "resolve": "^1.10.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } - }, - "nth-check": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-1.0.2.tgz", - "integrity": "sha512-WeBOdju8SnzPN5vTUJYxYUxLeXpCaVP5i5e0LF8fg7WORF2Wd7wFX/pk0tYZk7s8T+J7VLy0Da6J1+wCT0AtHg==", - "dev": true, - "requires": { - "boolbase": "~1.0.0" - } - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "dev": true, - "requires": { - "wrappy": "1" - } - }, - "optionator": { - "version": "0.9.1", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", - "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", - "dev": true, - "requires": { - "deep-is": "^0.1.3", - "fast-levenshtein": "^2.0.6", - "levn": "^0.4.1", - "prelude-ls": "^1.2.1", - "type-check": "^0.4.0", - "word-wrap": "^1.2.3" - } - }, - "os": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/os/-/os-0.1.1.tgz", - "integrity": "sha1-IIhF6J4ZOtTZcUdLk5R3NqVtE/M=", - "dev": true - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", - "dev": true - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", - "dev": true - }, - "osenv": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz", - "integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==", - "dev": true, - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" - } - }, - "p-limit": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.2.2.tgz", - "integrity": "sha512-WGR+xHecKTr7EbUEhyLSh5Dube9JtdiG78ufaeLxTgpudf/20KqyMioIUZJAezlTIi6evxuoUs9YXc11cU+yzQ==", - "dev": true, - "requires": { - "p-try": "^2.0.0" - } - }, - "p-locate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-3.0.0.tgz", - "integrity": "sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==", - "dev": true, - "requires": { - "p-limit": "^2.0.0" - } - }, - "p-try": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", - "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", - "dev": true - }, - "parent-module": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", - "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", - "dev": true, - "requires": { - "callsites": "^3.0.0" - } - }, - "parse-json": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", - "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", - "dev": true, - "requires": { - "error-ex": "^1.3.1", - "json-parse-better-errors": "^1.0.1" - } - }, - "parse-semver": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/parse-semver/-/parse-semver-1.1.1.tgz", - "integrity": "sha1-mkr9bfBj3Egm+T+6SpnPIj9mbLg=", - "dev": true, - "requires": { - "semver": "^5.1.0" - } - }, - "parse5": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/parse5/-/parse5-3.0.3.tgz", - "integrity": "sha512-rgO9Zg5LLLkfJF9E6CCmXlSE4UVceloys8JrFqCcHloC3usd/kJCyPDwH2SOlzix2j3xaP9sUX3e8+kvkuleAA==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true - }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", - "dev": true - }, - "path-key": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", - "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", - "dev": true - }, - "path-parse": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", - "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==", - "dev": true - }, - "pend": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", - "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=", - "dev": true - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", - "dev": true - }, - "prelude-ls": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", - "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", - "dev": true - }, - "progress": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", - "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", - "dev": true - }, - "punycode": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", - "dev": true - }, - "read": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", - "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", - "dev": true, - "requires": { - "mute-stream": "~0.0.4" - } - }, - "read-pkg": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-4.0.1.tgz", - "integrity": "sha1-ljYlN48+HE1IyFhytabsfV0JMjc=", - "dev": true, - "requires": { - "normalize-package-data": "^2.3.2", - "parse-json": "^4.0.0", - "pify": "^3.0.0" - } - }, - "readable-stream": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", - "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", - "dev": true, - "requires": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - } - }, - "regexpp": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.1.0.tgz", - "integrity": "sha512-ZOIzd8yVsQQA7j8GCSlPGXwg5PfmA1mrq0JP4nGhh54LaKN3xdai/vHUDu74pKwV8OxseMS65u2NImosQcSD0Q==", - "dev": true - }, - "require-directory": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=", - "dev": true - }, - "require-main-filename": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-2.0.0.tgz", - "integrity": "sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==", - "dev": true - }, - "resolve": { - "version": "1.12.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.12.0.tgz", - "integrity": "sha512-B/dOmuoAik5bKcD6s6nXDCjzUKnaDvdkRyAk6rsmsKLipWj4797iothd7jmmUhWTfinVMU+wc56rYKsit2Qy4w==", - "dev": true, - "requires": { - "path-parse": "^1.0.6" - } - }, - "resolve-from": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", - "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", - "dev": true - }, - "rimraf": { - "version": "2.6.3", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", - "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", - "dev": true, - "requires": { - "glob": "^7.1.3" - } - }, - "rxjs": { - "version": "6.5.4", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.5.4.tgz", - "integrity": "sha512-naMQXcgEo3csAEGvw/NydRA0fuS2nDZJiw1YUWFKU7aPPAPGZEsD4Iimit96qwCieH6y614MCLYwdkrWx7z/7Q==", - "dev": true, - "requires": { - "tslib": "^1.9.0" - } - }, - "safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", - "dev": true - }, - "semver": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.0.tgz", - "integrity": "sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA==", - "dev": true - }, - "set-blocking": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", - "dev": true - }, - "shebang-command": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", - "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", - "dev": true, - "requires": { - "shebang-regex": "^3.0.0" - } - }, - "shebang-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", - "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", - "dev": true - }, - "slice-ansi": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-2.1.0.tgz", - "integrity": "sha512-Qu+VC3EwYLldKa1fCxuuvULvSJOKEgk9pi8dZeCVK7TqBfUNTH4sFkk4joj8afVSfAYgJoSOetjx9QWOJ5mYoQ==", - "dev": true, - "requires": { - "ansi-styles": "^3.2.0", - "astral-regex": "^1.0.0", - "is-fullwidth-code-point": "^2.0.0" - } - }, - "spawn-command": { - "version": "0.0.2-1", - "resolved": "https://registry.npmjs.org/spawn-command/-/spawn-command-0.0.2-1.tgz", - "integrity": "sha1-YvXpRmmBwbeW3Fkpk34RycaSG9A=", - "dev": true - }, - "spdx-correct": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", - "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", - "dev": true, - "requires": { - "spdx-expression-parse": "^3.0.0", - "spdx-license-ids": "^3.0.0" - } - }, - "spdx-exceptions": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", - "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==", - "dev": true - }, - "spdx-expression-parse": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.0.tgz", - "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==", - "dev": true, - "requires": { - "spdx-exceptions": "^2.1.0", - "spdx-license-ids": "^3.0.0" - } - }, - "spdx-license-ids": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.5.tgz", - "integrity": "sha512-J+FWzZoynJEXGphVIS+XEh3kFSjZX/1i9gFBaWQcB+/tmpe2qUsSBABpcxqxnAxFdiUFEgAX1bjYGQvIZmoz9Q==", - "dev": true - }, - "sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "string-width": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-3.1.0.tgz", - "integrity": "sha512-vafcv6KjVZKSgz06oM/H6GDBrAtz8vdhQakGjFIvNrHA6y3HCF1CInLy+QLq8dTJPQ1b+KDUqDFctkdRW44e1w==", - "dev": true, - "requires": { - "emoji-regex": "^7.0.1", - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^5.1.0" - } - }, - "string_decoder": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", - "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", - "dev": true, - "requires": { - "safe-buffer": "~5.2.0" - } - }, - "strip-ansi": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", - "integrity": "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA==", - "dev": true, - "requires": { - "ansi-regex": "^4.1.0" - } - }, - "strip-json-comments": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", - "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", - "dev": true + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true + } + } + }, + "console-control-strings": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", + "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=", + "dev": true + }, + "core-util-is": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", + "dev": true + }, + "cross-spawn": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", + "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "dev": true, + "requires": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + } + }, + "css-select": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/css-select/-/css-select-4.2.1.tgz", + "integrity": "sha512-/aUslKhzkTNCQUB2qTX84lVmfia9NyjP3WpDGtj/WxhwBzWBYUV3DgUpurHTme8UTPcPlAD1DJ+b0nN/t50zDQ==", + "dev": true, + "requires": { + "boolbase": "^1.0.0", + "css-what": "^5.1.0", + "domhandler": "^4.3.0", + "domutils": "^2.8.0", + "nth-check": "^2.0.1" + } + }, + "css-what": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/css-what/-/css-what-5.1.0.tgz", + "integrity": "sha512-arSMRWIIFY0hV8pIxZMEfmMI47Wj3R/aWpZDDxWYCPEiOMv6tfOrnpDtgxBYPEQD4V0Y/958+1TdC3iWTFcUPw==", + "dev": true + }, + "date-fns": { + "version": "2.28.0", + "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.28.0.tgz", + "integrity": "sha512-8d35hViGYx/QH0icHYCeLmsLmMUheMmTyV9Fcm6gvNwdw31yXXH+O85sOBJ+OLnLQMKZowvpKb6FgMIQjcpvQw==", + "dev": true + }, + "debug": { + "version": "4.3.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.3.tgz", + "integrity": "sha512-/zxw5+vh1Tfv+4Qn7a5nsbcJKPaSvCDhojn6FEl9vupwK2VCSDtEiEtqr8DFtzYFOdz63LBkxec7DYuc2jon6Q==", + "dev": true, + "requires": { + "ms": "2.1.2" + } + }, + "decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "dev": true, + "requires": { + "mimic-response": "^3.1.0" + } + }, + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true + }, + "deep-is": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", + "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", + "dev": true + }, + "delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=", + "dev": true + }, + "detect-libc": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.1.tgz", + "integrity": "sha512-463v3ZeIrcWtdgIg6vI6XUncguvr2TnGl4SzDXinkt9mSLpBJKXT3mW6xT3VQdDN11+WVs29pgvivTc4Lp8v+w==", + "dev": true + }, + "dir-glob": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", + "dev": true, + "requires": { + "path-type": "^4.0.0" + } + }, + "doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "requires": { + "esutils": "^2.0.2" + } + }, + "dom-serializer": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.3.2.tgz", + "integrity": "sha512-5c54Bk5Dw4qAxNOI1pFEizPSjVsx5+bpJKmL2kPn8JhBUq2q09tTCa3mjijun2NfK78NMouDYNMBkOrPZiS+ig==", + "dev": true, + "requires": { + "domelementtype": "^2.0.1", + "domhandler": "^4.2.0", + "entities": "^2.0.0" + } + }, + "domelementtype": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.2.0.tgz", + "integrity": "sha512-DtBMo82pv1dFtUmHyr48beiuq792Sxohr+8Hm9zoxklYPfa6n0Z3Byjj2IV7bmr2IyqClnqEQhfgHJJ5QF0R5A==", + "dev": true + }, + "domhandler": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-4.3.0.tgz", + "integrity": "sha512-fC0aXNQXqKSFTr2wDNZDhsEYjCiYsDWl3D01kwt25hm1YIPyDGHvvi3rw+PLqHAl/m71MaiF7d5zvBr0p5UB2g==", + "dev": true, + "requires": { + "domelementtype": "^2.2.0" + } + }, + "domutils": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-2.8.0.tgz", + "integrity": "sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==", + "dev": true, + "requires": { + "dom-serializer": "^1.0.1", + "domelementtype": "^2.2.0", + "domhandler": "^4.2.0" + } + }, + "emoji-regex": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "dev": true + }, + "end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dev": true, + "requires": { + "once": "^1.4.0" + } + }, + "entities": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", + "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", + "dev": true + }, + "escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true + }, + "escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", + "dev": true + }, + "eslint": { + "version": "8.11.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.11.0.tgz", + "integrity": "sha512-/KRpd9mIRg2raGxHRGwW9ZywYNAClZrHjdueHcrVDuO3a6bj83eoTirCCk0M0yPwOjWYKHwRVRid+xK4F/GHgA==", + "dev": true, + "requires": { + "@eslint/eslintrc": "^1.2.1", + "@humanwhocodes/config-array": "^0.9.2", + "ajv": "^6.10.0", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.2", + "debug": "^4.3.2", + "doctrine": "^3.0.0", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^7.1.1", + "eslint-utils": "^3.0.0", + "eslint-visitor-keys": "^3.3.0", + "espree": "^9.3.1", + "esquery": "^1.4.0", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^6.0.1", + "functional-red-black-tree": "^1.0.1", + "glob-parent": "^6.0.1", + "globals": "^13.6.0", + "ignore": "^5.2.0", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "js-yaml": "^4.1.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.4.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.0.4", + "natural-compare": "^1.4.0", + "optionator": "^0.9.1", + "regexpp": "^3.2.0", + "strip-ansi": "^6.0.1", + "strip-json-comments": "^3.1.0", + "text-table": "^0.2.0", + "v8-compile-cache": "^2.0.3" + }, + "dependencies": { + "ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "requires": { + "color-convert": "^2.0.1" + } + }, + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + }, + "color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "requires": { + "color-name": "~1.1.4" + } + }, + "color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true + }, + "has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true }, "supports-color": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-6.1.0.tgz", - "integrity": "sha512-qe1jfm1Mg7Nq/NSh6XE24gPXROEVsWHxC1LIx//XNlD9iw7YZQGjZNjYN7xGaEG6iKdA8EtNFW6R0gjnVXp+wQ==", - "dev": true, - "requires": { - "has-flag": "^3.0.0" - } - }, - "table": { - "version": "5.4.6", - "resolved": "https://registry.npmjs.org/table/-/table-5.4.6.tgz", - "integrity": "sha512-wmEc8m4fjnob4gt5riFRtTu/6+4rSe12TpAELNSqHMfF3IqnA+CH37USM6/YR3qRZv7e56kAEAtd6nKZaxe0Ug==", - "dev": true, - "requires": { - "ajv": "^6.10.2", - "lodash": "^4.17.14", - "slice-ansi": "^2.1.0", - "string-width": "^3.0.0" - } - }, - "text-table": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", - "dev": true - }, - "tmp": { - "version": "0.0.29", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.29.tgz", - "integrity": "sha1-8lEl/w3Z2jzLDC3Tce4SiLuRKMA=", - "dev": true, - "requires": { - "os-tmpdir": "~1.0.1" - } - }, - "tree-kill": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", - "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", - "dev": true - }, - "tslib": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.10.0.tgz", - "integrity": "sha512-qOebF53frne81cf0S9B41ByenJ3/IuH8yJKngAX35CmiZySA0khhkovshKK+jGCaMnVomla7gVlIcc3EvKPbTQ==", - "dev": true - }, - "tsutils": { - "version": "3.17.1", - "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.17.1.tgz", - "integrity": "sha512-kzeQ5B8H3w60nFY2g8cJIuH7JDpsALXySGtwGJ0p2LSjLgay3NdIpqq5SoOBe46bKDW2iq25irHCr8wjomUS2g==", - "dev": true, - "requires": { - "tslib": "^1.8.1" - } - }, - "tunnel": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.4.tgz", - "integrity": "sha1-LTeFoVjBdMmhbcLARuxfxfF0IhM=", - "dev": true - }, - "type-check": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", - "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", - "dev": true, - "requires": { - "prelude-ls": "^1.2.1" - } - }, - "type-fest": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.8.1.tgz", - "integrity": "sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==", - "dev": true - }, - "typed-rest-client": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/typed-rest-client/-/typed-rest-client-1.2.0.tgz", - "integrity": "sha512-FrUshzZ1yxH8YwGR29PWWnfksLEILbWJydU7zfIRkyH7kAEzB62uMAl2WY6EyolWpLpVHeJGgQm45/MaruaHpw==", - "dev": true, - "requires": { - "tunnel": "0.0.4", - "underscore": "1.8.3" - } - }, - "typescript": { - "version": "3.9.7", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-3.9.7.tgz", - "integrity": "sha512-BLbiRkiBzAwsjut4x/dsibSTB6yWpwT5qWmC2OfuCg3GgVQCSgMs4vEctYPhsaGtd0AeuuHMkjZ2h2WG8MSzRw==", - "dev": true - }, - "uc.micro": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-1.0.6.tgz", - "integrity": "sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA==", - "dev": true - }, - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", - "dev": true - }, - "uri-js": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", - "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", - "dev": true, - "requires": { - "punycode": "^2.1.0" - } - }, - "url-join": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/url-join/-/url-join-1.1.0.tgz", - "integrity": "sha1-dBxsL0WWxIMNZxhGCSDQySIC3Hg=", - "dev": true - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", - "dev": true - }, - "v8-compile-cache": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.1.1.tgz", - "integrity": "sha512-8OQ9CL+VWyt3JStj7HX7/ciTL2V3Rl1Wf5OL+SNTm0yK1KvtReVulksyeRnCANHHuUxHlQig+JJDlUhBt1NQDQ==", - "dev": true - }, - "validate-npm-package-license": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", - "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", - "dev": true, - "requires": { - "spdx-correct": "^3.0.0", - "spdx-expression-parse": "^3.0.0" - } - }, - "vsce": { - "version": "1.77.0", - "resolved": "https://registry.npmjs.org/vsce/-/vsce-1.77.0.tgz", - "integrity": "sha512-8vOTCI3jGmOm0JJFu/BMAbqxpaSuka4S3hV9E6K5aWBUsDM1SGFExkIxHblnsI8sls43xP61DHorYT+K0F+GFA==", - "dev": true, - "requires": { - "azure-devops-node-api": "^7.2.0", - "chalk": "^2.4.2", - "cheerio": "^1.0.0-rc.1", - "commander": "^2.8.1", - "denodeify": "^1.2.1", - "glob": "^7.0.6", - "leven": "^3.1.0", - "lodash": "^4.17.15", - "markdown-it": "^10.0.0", - "mime": "^1.3.4", - "minimatch": "^3.0.3", - "osenv": "^0.1.3", - "parse-semver": "^1.1.1", - "read": "^1.0.7", - "semver": "^5.1.0", - "tmp": "0.0.29", - "typed-rest-client": "1.2.0", - "url-join": "^1.1.0", - "yauzl": "^2.3.1", - "yazl": "^2.2.2" - }, - "dependencies": { - "chalk": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", - "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", - "dev": true, - "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" - } - }, - "supports-color": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", - "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", - "dev": true, - "requires": { - "has-flag": "^3.0.0" - } - } - } - }, - "which": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", - "dev": true, - "requires": { - "isexe": "^2.0.0" - } - }, - "which-module": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=", - "dev": true - }, - "word-wrap": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz", - "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==", - "dev": true - }, - "wrap-ansi": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-5.1.0.tgz", - "integrity": "sha512-QC1/iN/2/RPVJ5jYK8BGttj5z83LmSKmvbvrXPNCLZSEb32KKVDJDl/MOt2N01qU2H/FkzEa9PKto1BqDjtd7Q==", - "dev": true, - "requires": { - "ansi-styles": "^3.2.0", - "string-width": "^3.0.0", - "strip-ansi": "^5.0.0" - } - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", - "dev": true - }, - "write": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/write/-/write-1.0.3.tgz", - "integrity": "sha512-/lg70HAjtkUgWPVZhZcm+T4hkL8Zbtp1nFNOn3lRrxnlv50SRBv7cR7RqR+GMsd3hUXy9hWBo4CHTbFTcOYwig==", - "dev": true, - "requires": { - "mkdirp": "^0.5.1" - } - }, - "y18n": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-4.0.0.tgz", - "integrity": "sha512-r9S/ZyXu/Xu9q1tYlpsLIsa3EeLXXk0VwlxqTcFRfg9EhMW+17kbt9G0NrgCmhGb5vT2hyhJZLfDGx+7+5Uj/w==", - "dev": true - }, - "yargs": { - "version": "13.3.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-13.3.0.tgz", - "integrity": "sha512-2eehun/8ALW8TLoIl7MVaRUrg+yCnenu8B4kBlRxj3GJGDKU1Og7sMXPNm1BYyM1DOJmTZ4YeN/Nwxv+8XJsUA==", - "dev": true, - "requires": { - "cliui": "^5.0.0", - "find-up": "^3.0.0", - "get-caller-file": "^2.0.1", - "require-directory": "^2.1.1", - "require-main-filename": "^2.0.0", - "set-blocking": "^2.0.0", - "string-width": "^3.0.0", - "which-module": "^2.0.0", - "y18n": "^4.0.0", - "yargs-parser": "^13.1.1" - } - }, - "yargs-parser": { - "version": "13.1.1", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-13.1.1.tgz", - "integrity": "sha512-oVAVsHz6uFrg3XQheFII8ESO2ssAf9luWuAd6Wexsu4F3OtIW0o8IribPXYrD4WC24LWtPrJlGy87y5udK+dxQ==", - "dev": true, - "requires": { - "camelcase": "^5.0.0", - "decamelize": "^1.2.0" - } - }, - "yauzl": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", - "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", - "dev": true, - "requires": { - "buffer-crc32": "~0.2.3", - "fd-slicer": "~1.1.0" - } - }, - "yazl": { - "version": "2.5.1", - "resolved": "https://registry.npmjs.org/yazl/-/yazl-2.5.1.tgz", - "integrity": "sha512-phENi2PLiHnHb6QBVot+dJnaAZ0xosj7p3fWl+znIjBDlnMI2PsZCJZ306BPTFOaHf5qdDEI8x5qFrSOBN5vrw==", - "dev": true, - "requires": { - "buffer-crc32": "~0.2.3" - } + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "requires": { + "has-flag": "^4.0.0" + } } + } + }, + "eslint-scope": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.1.1.tgz", + "integrity": "sha512-QKQM/UXpIiHcLqJ5AOyIW7XZmzjkzQXYE54n1++wb0u9V/abW3l9uQnxX8Z5Xd18xyKIMTUAyQ0k1e8pz6LUrw==", + "dev": true, + "requires": { + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" + } + }, + "eslint-utils": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-3.0.0.tgz", + "integrity": "sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA==", + "dev": true, + "requires": { + "eslint-visitor-keys": "^2.0.0" + }, + "dependencies": { + "eslint-visitor-keys": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.1.0.tgz", + "integrity": "sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==", + "dev": true + } + } + }, + "eslint-visitor-keys": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.3.0.tgz", + "integrity": "sha512-mQ+suqKJVyeuwGYHAdjMFqjCyfl8+Ldnxuyp3ldiMBFKkvytrXUZWaiPCEav8qDHKty44bD+qV1IP4T+w+xXRA==", + "dev": true + }, + "espree": { + "version": "9.3.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.3.1.tgz", + "integrity": "sha512-bvdyLmJMfwkV3NCRl5ZhJf22zBFo1y8bYh3VYb+bfzqNB4Je68P2sSuXyuFquzWLebHpNd2/d5uv7yoP9ISnGQ==", + "dev": true, + "requires": { + "acorn": "^8.7.0", + "acorn-jsx": "^5.3.1", + "eslint-visitor-keys": "^3.3.0" + } + }, + "esquery": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", + "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", + "dev": true, + "requires": { + "estraverse": "^5.1.0" + } + }, + "esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "requires": { + "estraverse": "^5.2.0" + } + }, + "estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true + }, + "esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true + }, + "expand-template": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-2.0.3.tgz", + "integrity": "sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==", + "dev": true + }, + "fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "dev": true + }, + "fast-glob": { + "version": "3.2.11", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.11.tgz", + "integrity": "sha512-xrO3+1bxSo3ZVHAnqzyuewYT6aMFHRAd4Kcs92MAonjwQZLsK9d0SF1IyQ3k5PoirxTW0Oe/RqFgMQ6TcNE5Ew==", + "dev": true, + "requires": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "dependencies": { + "glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "requires": { + "is-glob": "^4.0.1" + } + } + } + }, + "fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", + "dev": true + }, + "fastq": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.13.0.tgz", + "integrity": "sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==", + "dev": true, + "requires": { + "reusify": "^1.0.4" + } + }, + "fd-slicer": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", + "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", + "dev": true, + "requires": { + "pend": "~1.2.0" + } + }, + "file-entry-cache": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", + "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", + "dev": true, + "requires": { + "flat-cache": "^3.0.4" + } + }, + "fill-range": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", + "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", + "dev": true, + "requires": { + "to-regex-range": "^5.0.1" + } + }, + "flat-cache": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", + "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", + "dev": true, + "requires": { + "flatted": "^3.1.0", + "rimraf": "^3.0.2" + } + }, + "flatted": { + "version": "3.2.5", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.5.tgz", + "integrity": "sha512-WIWGi2L3DyTUvUrwRKgGi9TwxQMUEqPOPQBVi71R96jZXJdFskXEmf54BoZaS1kknGODoIGASGEzBUYdyMCBJg==", + "dev": true + }, + "fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "dev": true + }, + "fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", + "dev": true + }, + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "functional-red-black-tree": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", + "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", + "dev": true + }, + "gauge": { + "version": "2.7.4", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", + "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", + "dev": true, + "requires": { + "aproba": "^1.0.3", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.0", + "object-assign": "^4.1.0", + "signal-exit": "^3.0.0", + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wide-align": "^1.1.0" + }, + "dependencies": { + "ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "dev": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "dev": true, + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "dev": true, + "requires": { + "ansi-regex": "^2.0.0" + } + } + } + }, + "get-caller-file": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", + "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", + "dev": true + }, + "get-intrinsic": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.1.tgz", + "integrity": "sha512-kWZrnVM42QCiEA2Ig1bG8zjoIMOgxWwYCEeNdwY6Tv/cOSeGpcoX4pXHfKUxNKVoArnrEr2e9srnAxxGIraS9Q==", + "dev": true, + "requires": { + "function-bind": "^1.1.1", + "has": "^1.0.3", + "has-symbols": "^1.0.1" + } + }, + "github-from-package": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", + "integrity": "sha1-l/tdlr/eiXMxPyDoKI75oWf6ZM4=", + "dev": true + }, + "glob": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.0.tgz", + "integrity": "sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", + "dev": true, + "requires": { + "is-glob": "^4.0.3" + } + }, + "globals": { + "version": "13.12.1", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.12.1.tgz", + "integrity": "sha512-317dFlgY2pdJZ9rspXDks7073GpDmXdfbM3vYYp0HAMKGDh1FfWPleI2ljVNLQX5M5lXcAslTcPTrOrMEFOjyw==", + "dev": true, + "requires": { + "type-fest": "^0.20.2" + } + }, + "globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", + "dev": true, + "requires": { + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.2.9", + "ignore": "^5.2.0", + "merge2": "^1.4.1", + "slash": "^3.0.0" + } + }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "requires": { + "function-bind": "^1.1.1" + } + }, + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "dev": true + }, + "has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=", + "dev": true + }, + "htmlparser2": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-6.1.0.tgz", + "integrity": "sha512-gyyPk6rgonLFEDGoeRgQNaEUvdJ4ktTmmUh/h2t7s+M8oPpIPxgNACWa+6ESR57kXstwqPiCut0V8NRpcwgU7A==", + "dev": true, + "requires": { + "domelementtype": "^2.0.1", + "domhandler": "^4.0.0", + "domutils": "^2.5.2", + "entities": "^2.0.0" + } + }, + "ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "dev": true + }, + "ignore": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.0.tgz", + "integrity": "sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==", + "dev": true + }, + "import-fresh": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", + "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", + "dev": true, + "requires": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + } + }, + "imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", + "dev": true + }, + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", + "dev": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "dev": true + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", + "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", + "dev": true + }, + "is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "requires": { + "is-extglob": "^2.1.1" + } + }, + "is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true + }, + "js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dev": true, + "requires": { + "argparse": "^2.0.1" + } + }, + "json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", + "dev": true + }, + "keytar": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/keytar/-/keytar-7.9.0.tgz", + "integrity": "sha512-VPD8mtVtm5JNtA2AErl6Chp06JBfy7diFQ7TQQhdpWOl6MrCRB+eRbvAZUsbGQS9kiMq0coJsy0W0vHpDCkWsQ==", + "dev": true, + "requires": { + "node-addon-api": "^4.3.0", + "prebuild-install": "^7.0.1" + } + }, + "leven": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", + "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", + "dev": true + }, + "levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "requires": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + } + }, + "linkify-it": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-3.0.3.tgz", + "integrity": "sha512-ynTsyrFSdE5oZ/O9GEf00kPngmOfVwazR5GKDq6EYfhlpFug3J2zybX56a2PRRpc9P+FuSoGNAwjlbDs9jJBPQ==", + "dev": true, + "requires": { + "uc.micro": "^1.0.1" + } + }, + "lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true + }, + "lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "requires": { + "yallist": "^4.0.0" + } + }, + "markdown-it": { + "version": "12.3.2", + "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-12.3.2.tgz", + "integrity": "sha512-TchMembfxfNVpHkbtriWltGWc+m3xszaRD0CZup7GFFhzIgQqxIfn3eGj1yZpfuflzPvfkt611B2Q/Bsk1YnGg==", + "dev": true, + "requires": { + "argparse": "^2.0.1", + "entities": "~2.1.0", + "linkify-it": "^3.0.1", + "mdurl": "^1.0.1", + "uc.micro": "^1.0.5" + }, + "dependencies": { + "entities": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.1.0.tgz", + "integrity": "sha512-hCx1oky9PFrJ611mf0ifBLBRW8lUUVRlFolb5gWRfIELabBlbp9xZvrqZLZAs+NxFnbfQoeGd8wDkygjg7U85w==", + "dev": true + } + } + }, + "mdurl": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-1.0.1.tgz", + "integrity": "sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4=", + "dev": true + }, + "merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true + }, + "micromatch": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.4.tgz", + "integrity": "sha512-pRmzw/XUcwXGpD9aI9q/0XOwLNygjETJ8y0ao0wdqprrzDa4YnxLcz7fQRZr8voh8V10kGhABbNcHVk5wHgWwg==", + "dev": true, + "requires": { + "braces": "^3.0.1", + "picomatch": "^2.2.3" + } + }, + "mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "dev": true + }, + "mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "dev": true + }, + "minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "mkdirp-classic": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz", + "integrity": "sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==", + "dev": true + }, + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", + "dev": true + }, + "mute-stream": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", + "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", + "dev": true + }, + "napi-build-utils": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-1.0.2.tgz", + "integrity": "sha512-ONmRUqK7zj7DWX0D9ADe03wbwOBZxNAfF20PlGfCWQcD3+/MakShIHrMqx9YwPTfxDdF1zLeL+RGZiR9kGMLdg==", + "dev": true + }, + "natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", + "dev": true + }, + "node-abi": { + "version": "3.8.0", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.8.0.tgz", + "integrity": "sha512-tzua9qWWi7iW4I42vUPKM+SfaF0vQSLAm4yO5J83mSwB7GeoWrDKC/K+8YCnYNwqP5duwazbw2X9l4m8SC2cUw==", + "dev": true, + "requires": { + "semver": "^7.3.5" + } + }, + "node-addon-api": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-4.3.0.tgz", + "integrity": "sha512-73sE9+3UaLYYFmDsFZnqCInzPyh3MqIwZO9cw58yIqAZhONrrabrYyYe3TuIqtIiOuTXVhsGau8hcrhhwSsDIQ==", + "dev": true + }, + "npmlog": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", + "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", + "dev": true, + "requires": { + "are-we-there-yet": "~1.1.2", + "console-control-strings": "~1.1.0", + "gauge": "~2.7.3", + "set-blocking": "~2.0.0" + } + }, + "nth-check": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.0.1.tgz", + "integrity": "sha512-it1vE95zF6dTT9lBsYbxvqh0Soy4SPowchj0UBGj/V6cTPnXXtQOPUbhZ6CmGzAD/rW22LQK6E96pcdJXk4A4w==", + "dev": true, + "requires": { + "boolbase": "^1.0.0" + } + }, + "number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", + "dev": true + }, + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", + "dev": true + }, + "object-inspect": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.0.tgz", + "integrity": "sha512-Ho2z80bVIvJloH+YzRmpZVQe87+qASmBUKZDWgx9cu+KDrX2ZDH/3tMy+gXbZETVGs2M8YdxObOh7XAtim9Y0g==", + "dev": true + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "optionator": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", + "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", + "dev": true, + "requires": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.3" + } + }, + "parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "requires": { + "callsites": "^3.0.0" + } + }, + "parse-semver": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/parse-semver/-/parse-semver-1.1.1.tgz", + "integrity": "sha1-mkr9bfBj3Egm+T+6SpnPIj9mbLg=", + "dev": true, + "requires": { + "semver": "^5.1.0" + }, + "dependencies": { + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + } + } + }, + "parse5": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-6.0.1.tgz", + "integrity": "sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==", + "dev": true + }, + "parse5-htmlparser2-tree-adapter": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/parse5-htmlparser2-tree-adapter/-/parse5-htmlparser2-tree-adapter-6.0.1.tgz", + "integrity": "sha512-qPuWvbLgvDGilKc5BoicRovlT4MtYT6JfJyBOMDsKoiT+GiuP5qyrPCnR9HcPECIJJmZh5jRndyNThnhhb/vlA==", + "dev": true, + "requires": { + "parse5": "^6.0.1" + } + }, + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", + "dev": true + }, + "path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "dev": true + }, + "path-type": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", + "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", + "dev": true + }, + "pend": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", + "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=", + "dev": true + }, + "picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true + }, + "prebuild-install": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/prebuild-install/-/prebuild-install-7.0.1.tgz", + "integrity": "sha512-QBSab31WqkyxpnMWQxubYAHR5S9B2+r81ucocew34Fkl98FhvKIF50jIJnNOBmAZfyNV7vE5T6gd3hTVWgY6tg==", + "dev": true, + "requires": { + "detect-libc": "^2.0.0", + "expand-template": "^2.0.3", + "github-from-package": "0.0.0", + "minimist": "^1.2.3", + "mkdirp-classic": "^0.5.3", + "napi-build-utils": "^1.0.1", + "node-abi": "^3.3.0", + "npmlog": "^4.0.1", + "pump": "^3.0.0", + "rc": "^1.2.7", + "simple-get": "^4.0.0", + "tar-fs": "^2.0.0", + "tunnel-agent": "^0.6.0" + } + }, + "prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true + }, + "process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "dev": true + }, + "pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dev": true, + "requires": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true + }, + "qs": { + "version": "6.10.3", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.10.3.tgz", + "integrity": "sha512-wr7M2E0OFRfIfJZjKGieI8lBKb7fRCH4Fv5KNPEs7gJ8jadvotdsS08PzOKR7opXhZ/Xkjtt3WF9g38drmyRqQ==", + "dev": true, + "requires": { + "side-channel": "^1.0.4" + } + }, + "queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true + }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, + "requires": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "dependencies": { + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", + "dev": true + } + } + }, + "read": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", + "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", + "dev": true, + "requires": { + "mute-stream": "~0.0.4" + } + }, + "readable-stream": { + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", + "dev": true, + "requires": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "regexpp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", + "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", + "dev": true + }, + "require-directory": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=", + "dev": true + }, + "resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true + }, + "reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true + }, + "rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "requires": { + "glob": "^7.1.3" + } + }, + "run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "requires": { + "queue-microtask": "^1.2.2" + } + }, + "rxjs": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", + "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", + "dev": true, + "requires": { + "tslib": "^1.9.0" + } + }, + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, + "sax": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", + "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==", + "dev": true + }, + "semver": { + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", + "dev": true + }, + "shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "dev": true, + "requires": { + "shebang-regex": "^3.0.0" + } + }, + "shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "dev": true + }, + "side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dev": true, + "requires": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + } + }, + "signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", + "dev": true + }, + "simple-concat": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.1.tgz", + "integrity": "sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==", + "dev": true + }, + "simple-get": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-4.0.1.tgz", + "integrity": "sha512-brv7p5WgH0jmQJr1ZDDfKDOSeWWg+OVypG99A/5vYGPqJ6pxiaHLy8nxtFjBA7oMa01ebA9gfh1uMCFqOuXxvA==", + "dev": true, + "requires": { + "decompress-response": "^6.0.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" + } + }, + "slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true + }, + "spawn-command": { + "version": "0.0.2-1", + "resolved": "https://registry.npmjs.org/spawn-command/-/spawn-command-0.0.2-1.tgz", + "integrity": "sha1-YvXpRmmBwbeW3Fkpk34RycaSG9A=", + "dev": true + }, + "string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "requires": { + "safe-buffer": "~5.1.0" + } + }, + "string-width": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", + "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", + "dev": true, + "requires": { + "emoji-regex": "^8.0.0", + "is-fullwidth-code-point": "^3.0.0", + "strip-ansi": "^6.0.1" + } + }, + "strip-ansi": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", + "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", + "dev": true, + "requires": { + "ansi-regex": "^5.0.1" + } + }, + "strip-json-comments": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true + }, + "supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, + "requires": { + "has-flag": "^4.0.0" + }, + "dependencies": { + "has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true + } + } + }, + "tar-fs": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.1.tgz", + "integrity": "sha512-V0r2Y9scmbDRLCNex/+hYzvp/zyYjvFbHPNgVTKfQvVrb6guiE/fxP+XblDNR011utopbkex2nM4dHNV6GDsng==", + "dev": true, + "requires": { + "chownr": "^1.1.1", + "mkdirp-classic": "^0.5.2", + "pump": "^3.0.0", + "tar-stream": "^2.1.4" + } + }, + "tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "dev": true, + "requires": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + }, + "dependencies": { + "readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "requires": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + } + } + } + }, + "text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", + "dev": true + }, + "tmp": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz", + "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==", + "dev": true, + "requires": { + "rimraf": "^3.0.0" + } + }, + "to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "requires": { + "is-number": "^7.0.0" + } + }, + "tree-kill": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", + "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", + "dev": true + }, + "tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "tsutils": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", + "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", + "dev": true, + "requires": { + "tslib": "^1.8.1" + } + }, + "tunnel": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz", + "integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==", + "dev": true + }, + "tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "dev": true, + "requires": { + "safe-buffer": "^5.0.1" + } + }, + "type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "requires": { + "prelude-ls": "^1.2.1" + } + }, + "type-fest": { + "version": "0.20.2", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", + "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", + "dev": true + }, + "typed-rest-client": { + "version": "1.8.6", + "resolved": "https://registry.npmjs.org/typed-rest-client/-/typed-rest-client-1.8.6.tgz", + "integrity": "sha512-xcQpTEAJw2DP7GqVNECh4dD+riS+C1qndXLfBCJ3xk0kqprtGN491P5KlmrDbKdtuW8NEcP/5ChxiJI3S9WYTA==", + "dev": true, + "requires": { + "qs": "^6.9.1", + "tunnel": "0.0.6", + "underscore": "^1.12.1" + } + }, + "typescript": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.6.2.tgz", + "integrity": "sha512-HM/hFigTBHZhLXshn9sN37H085+hQGeJHJ/X7LpBWLID/fbc2acUMfU+lGD98X81sKP+pFa9f0DZmCwB9GnbAg==", + "dev": true + }, + "uc.micro": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-1.0.6.tgz", + "integrity": "sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA==", + "dev": true + }, + "underscore": { + "version": "1.13.2", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.2.tgz", + "integrity": "sha512-ekY1NhRzq0B08g4bGuX4wd2jZx5GnKz6mKSqFL4nqBlfyMGiG10gDFhDTMEfYmDL6Jy0FUIZp7wiRB+0BP7J2g==", + "dev": true + }, + "uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "requires": { + "punycode": "^2.1.0" + } + }, + "url-join": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/url-join/-/url-join-4.0.1.tgz", + "integrity": "sha512-jk1+QP6ZJqyOiuEI9AEWQfju/nB2Pw466kbA0LEZljHwKeMgd9WrAEgEGxjPDD2+TNbbb37rTyhEfrCXfuKXnA==", + "dev": true + }, + "util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true + }, + "v8-compile-cache": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", + "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==", + "dev": true + }, + "vsce": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/vsce/-/vsce-2.7.0.tgz", + "integrity": "sha512-CKU34wrQlbKDeJCRBkd1a8iwF9EvNxcYMg9hAUH6AxFGR6Wo2IKWwt3cJIcusHxx6XdjDHWlfAS/fJN30uvVnA==", + "dev": true, + "requires": { + "azure-devops-node-api": "^11.0.1", + "chalk": "^2.4.2", + "cheerio": "^1.0.0-rc.9", + "commander": "^6.1.0", + "glob": "^7.0.6", + "hosted-git-info": "^4.0.2", + "keytar": "^7.7.0", + "leven": "^3.1.0", + "markdown-it": "^12.3.2", + "mime": "^1.3.4", + "minimatch": "^3.0.3", + "parse-semver": "^1.1.1", + "read": "^1.0.7", + "semver": "^5.1.0", + "tmp": "^0.2.1", + "typed-rest-client": "^1.8.4", + "url-join": "^4.0.1", + "xml2js": "^0.4.23", + "yauzl": "^2.3.1", + "yazl": "^2.2.2" + }, + "dependencies": { + "hosted-git-info": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.1.0.tgz", + "integrity": "sha512-kyCuEOWjJqZuDbRHzL8V93NzQhwIB71oFWSyzVo+KPZI+pnQPPxucdkrOZvkLRnrf5URsQM+IJ09Dw29cRALIA==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + } + } + }, + "which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "requires": { + "isexe": "^2.0.0" + } + }, + "wide-align": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.5.tgz", + "integrity": "sha512-eDMORYaPNZ4sQIuuYPDHdQvf4gyCF9rEEV/yPxGfwPkRodwEgiMUUXTx/dex+Me0wxx53S+NgUHaP7y3MGlDmg==", + "dev": true, + "requires": { + "string-width": "^1.0.2 || 2 || 3 || 4" + } + }, + "word-wrap": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz", + "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==", + "dev": true + }, + "wrap-ansi": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", + "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", + "dev": true, + "requires": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + }, + "dependencies": { + "ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "requires": { + "color-convert": "^2.0.1" + } + }, + "color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "requires": { + "color-name": "~1.1.4" + } + }, + "color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + } + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", + "dev": true + }, + "xml2js": { + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/xml2js/-/xml2js-0.4.23.tgz", + "integrity": "sha512-ySPiMjM0+pLDftHgXY4By0uswI3SPKLDw/i3UXbnO8M/p28zqexCUoPmQFrYD+/1BzhGJSs2i1ERWKJAtiLrug==", + "dev": true, + "requires": { + "sax": ">=0.6.0", + "xmlbuilder": "~11.0.0" + } + }, + "xmlbuilder": { + "version": "11.0.1", + "resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-11.0.1.tgz", + "integrity": "sha512-fDlsI/kFEx7gLvbecc0/ohLG50fugQp8ryHzMTuW9vSa1GJ0XYWKnhsUx7oie3G98+r56aTQIUB4kht42R3JvA==", + "dev": true + }, + "y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true + }, + "yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "yargs": { + "version": "16.2.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", + "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", + "dev": true, + "requires": { + "cliui": "^7.0.2", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.0", + "y18n": "^5.0.5", + "yargs-parser": "^20.2.2" + } + }, + "yargs-parser": { + "version": "20.2.9", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.9.tgz", + "integrity": "sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==", + "dev": true + }, + "yauzl": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", + "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", + "dev": true, + "requires": { + "buffer-crc32": "~0.2.3", + "fd-slicer": "~1.1.0" + } + }, + "yazl": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/yazl/-/yazl-2.5.1.tgz", + "integrity": "sha512-phENi2PLiHnHb6QBVot+dJnaAZ0xosj7p3fWl+znIjBDlnMI2PsZCJZ306BPTFOaHf5qdDEI8x5qFrSOBN5vrw==", + "dev": true, + "requires": { + "buffer-crc32": "~0.2.3" + } } + } } diff --git a/package.json b/package.json index 4a4f2ed..abe839c 100644 --- a/package.json +++ b/package.json @@ -11,7 +11,7 @@ "url": "https://github.com/Strum355/mcshader-lsp" }, "engines": { - "vscode": "^1.43.0" + "vscode": "^1.53.0" }, "categories": [ "Linters", @@ -78,22 +78,28 @@ "fix": "eslint 'client/**/*.ts' --fix" }, "devDependencies": { - "@types/node": "^10.14.15", - "@typescript-eslint/parser": "^3.6.1", - "concurrently": "^5.1.0", - "eslint": "^7.4.0", - "typescript": "^3.9.7", - "vsce": "^1.77.0" + "@types/node": "^17.0.21", + "@typescript-eslint/parser": "^5.15.0", + "concurrently": "^7.0.0", + "eslint": "^8.11.0", + "typescript": "^4.6.2", + "vsce": "^2.7.0" }, "eslintConfig": { "parser": "@typescript-eslint/parser", "parserOptions": { - "ecmaVersion": 2020, - "sourceType": "module" + "ecmaVersion": 2020, + "sourceType": "module" }, "rules": { - "semi": ["warn", "never"], - "quotes": ["warn", "single"] + "semi": [ + "warn", + "never" + ], + "quotes": [ + "warn", + "single" + ] } } } From b775bd2cd561f5bf48fc0a6b74dd47f005154058 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Mon, 14 Mar 2022 23:58:49 +0000 Subject: [PATCH 21/56] cargo: bump dependency versions --- server/Cargo.lock | 543 ++++++++++++++++++++++------------------------ server/Cargo.toml | 42 ++-- 2 files changed, 279 insertions(+), 306 deletions(-) diff --git a/server/Cargo.lock b/server/Cargo.lock index 5e8225a..08193a4 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -2,12 +2,6 @@ # It is not intended for manual editing. version = 3 -[[package]] -name = "ab_glyph_rasterizer" -version = "0.1.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9fe5e32de01730eb1f6b7f5b51c17e03e2325bf40a74f754f04f130043affff" - [[package]] name = "aho-corasick" version = "0.7.15" @@ -17,19 +11,6 @@ dependencies = [ "memchr", ] -[[package]] -name = "andrew" -version = "0.3.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8c4afb09dd642feec8408e33f92f3ffc4052946f6b20f32fb99c1f58cd4fa7cf" -dependencies = [ - "bitflags", - "rusttype", - "walkdir", - "xdg", - "xml-rs", -] - [[package]] name = "android_glue" version = "0.2.3" @@ -38,11 +19,11 @@ checksum = "000444226fcff248f2bc4c7625be32c63caccfecc2723a2b9f78a7487a49c407" [[package]] name = "ansi_term" -version = "0.11.0" +version = "0.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ee49baf6cb617b853aa8d93bf420db2383fab46d314482ca2803b40d5fde979b" +checksum = "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2" dependencies = [ - "winapi 0.3.9", + "winapi", ] [[package]] @@ -91,10 +72,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0d8c1fef690941d3e7788d328517591fecc684c084084702d6ff1641e993699a" [[package]] -name = "calloop" -version = "0.6.5" +name = "bumpalo" +version = "3.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b036167e76041694579972c28cf4877b4f92da222560ddb49008937b6a6727c" +checksum = "a4a45a46ab1f2412e53d3a0ade76ffad2025804294569aae387231a0cd6e0899" + +[[package]] +name = "calloop" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf2eec61efe56aa1e813f5126959296933cf0700030e4314786c48779a66ab82" dependencies = [ "log", "nix", @@ -136,22 +123,6 @@ dependencies = [ "rand 0.3.23", ] -[[package]] -name = "cocoa" -version = "0.23.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c54201c07dcf3a5ca33fececb8042aed767ee4bfd5a0235a8ceabcda956044b2" -dependencies = [ - "bitflags", - "block", - "cocoa-foundation", - "core-foundation 0.9.1", - "core-graphics 0.22.2", - "foreign-types", - "libc", - "objc", -] - [[package]] name = "cocoa" version = "0.24.0" @@ -276,10 +247,16 @@ dependencies = [ ] [[package]] -name = "darling" -version = "0.10.2" +name = "cty" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d706e75d87e35569db781a9b5e2416cff1236a47ed380831f959382ccd5f858" +checksum = "b365fabc795046672053e29c954733ec3b05e4be654ab130fe8f1f94d7051f35" + +[[package]] +name = "darling" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d0d720b8683f8dd83c65155f0530560cba68cd2bf395f6513a483caee57ff7f4" dependencies = [ "darling_core", "darling_macro", @@ -287,9 +264,9 @@ dependencies = [ [[package]] name = "darling_core" -version = "0.10.2" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f0c960ae2da4de88a91b2d920c2a7233b400bc33cb28453a2987822d8392519b" +checksum = "7a340f241d2ceed1deb47ae36c4144b2707ec7dd0b649f894cb39bb595986324" dependencies = [ "fnv", "ident_case", @@ -301,9 +278,9 @@ dependencies = [ [[package]] name = "darling_macro" -version = "0.10.2" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9b5a2f4ac4969822c62224815d069952656cadc7084fdca9751e6d959189b72" +checksum = "72c41b3b7352feb3211a0d743dc5700a4e3b60f51bd2b368892d1e0f9a95f44b" dependencies = [ "darling_core", "quote", @@ -322,10 +299,16 @@ dependencies = [ ] [[package]] -name = "difference" -version = "2.0.0" +name = "diff" +version = "0.1.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "524cbf6897b527295dff137cec09ecf3a05f4fddffd7dfcd1585403449e74198" +checksum = "0e25ea47919b1560c4e3b7fe0aaab9becf5b84a10325ddf7db0f0ba5e1026499" + +[[package]] +name = "difflib" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6184e33543162437515c2e2b48714794e37845ec9851711914eec9d308f6ebe8" [[package]] name = "dispatch" @@ -335,18 +318,18 @@ checksum = "bd0c93bb4b0c6d9b77f4435b0ae98c24d17f1c45b2ff844c6151a07256ca923b" [[package]] name = "dlib" -version = "0.4.2" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b11f15d1e3268f140f68d390637d5e76d849782d971ae7063e0da69fe9709a76" +checksum = "ac1b7517328c04c2aa68422fc60a41b92208182142ed04a25879c26c8f878794" dependencies = [ "libloading", ] [[package]] name = "downcast" -version = "0.10.0" +version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4bb454f0228b18c7f4c3b0ebbee346ed9c52e7443b0999cd543ff3571205701d" +checksum = "1435fa1053d8b2fbbe9be7e97eca7f33d37b28409959813daefc1446a14247f1" [[package]] name = "downcast-rs" @@ -355,16 +338,22 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9ea835d29036a4087793836fa931b08837ad5e957da9e23886b29586fb9b6650" [[package]] -name = "fixedbitset" -version = "0.2.0" +name = "either" +version = "1.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "37ab347416e802de484e4d03c7316c48f1ecb56574dfd4a46a80f173ce1de04d" +checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457" + +[[package]] +name = "fixedbitset" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "398ea4fabe40b9b0d885340a2a991a44c8a645624075ad966d21f88688e2b69e" [[package]] name = "float-cmp" -version = "0.8.0" +version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e1267f4ac4f343772758f7b1bdcbe767c218bbab93bb432acbf5162bbf85a6c4" +checksum = "98de4bbd547a563b716d8dfa9aad1cb19bfab00f4fa09a6a4ed21dbcf44ce9c4" dependencies = [ "num-traits", ] @@ -418,22 +407,6 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" -[[package]] -name = "fuchsia-zircon" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" -dependencies = [ - "bitflags", - "fuchsia-zircon-sys", -] - -[[package]] -name = "fuchsia-zircon-sys" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" - [[package]] name = "futures" version = "0.1.30" @@ -462,13 +435,13 @@ dependencies = [ [[package]] name = "glutin" -version = "0.26.0" +version = "0.28.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ae1cbb9176b9151c4ce03f012e3cd1c6c18c4be79edeaeb3d99f5d8085c5fa3" +checksum = "00ea9dbe544bc8a657c4c4a798c2d16cd01b549820e47657297549d28371f6d2" dependencies = [ "android_glue", "cgl", - "cocoa 0.23.0", + "cocoa", "core-foundation 0.9.1", "glutin_egl_sys", "glutin_emscripten_sys", @@ -483,7 +456,7 @@ dependencies = [ "parking_lot", "wayland-client", "wayland-egl", - "winapi 0.3.9", + "winapi", "winit", ] @@ -494,7 +467,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2abb6aa55523480c4adc5a56bbaa249992e2dddb2fc63dc96e04a3355364c211" dependencies = [ "gl_generator", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -544,9 +517,9 @@ dependencies = [ [[package]] name = "hashbrown" -version = "0.9.1" +version = "0.11.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d7afe4a420e3fe79967a00898cc1f4db7c8a49a9333a29f8a4bd76a253d5cd04" +checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e" [[package]] name = "ident_case" @@ -567,9 +540,9 @@ dependencies = [ [[package]] name = "indexmap" -version = "1.6.1" +version = "1.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4fb1fa934250de4de8aef298d81c729a7d33d8c239daa3a7575e6b92bfc7313b" +checksum = "bc633605454125dec4b66843673f01c7df2b89479b32e0ed634e43a91cff62a5" dependencies = [ "autocfg", "hashbrown", @@ -582,15 +555,18 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "61124eeebbd69b8190558df225adf7e4caafce0d743919e5d6b19652314ec5ec" dependencies = [ "cfg-if 1.0.0", + "js-sys", + "wasm-bindgen", + "web-sys", ] [[package]] -name = "iovec" -version = "0.1.4" +name = "itertools" +version = "0.10.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e" +checksum = "a9a9d19fa1e79b6215ff29b9d6880b706147f16e9b1dbb1e4e5947b5b02bc5e3" dependencies = [ - "libc", + "either", ] [[package]] @@ -606,13 +582,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8eaf4bc02d17cbdd7ff4c7438cafcdf7fb9a4613313ad11b4f8fefe7d3fa0130" [[package]] -name = "kernel32-sys" -version = "0.2.2" +name = "js-sys" +version = "0.3.56" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d" +checksum = "a38fc24e30fd564ce974c02bf1d337caddff65be6cc4735a1f7eab22a7440f04" dependencies = [ - "winapi 0.2.8", - "winapi-build", + "wasm-bindgen", ] [[package]] @@ -627,26 +602,20 @@ version = "1.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" -[[package]] -name = "lazycell" -version = "1.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55" - [[package]] name = "libc" -version = "0.2.82" +version = "0.2.119" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "89203f3fba0a3795506acaad8ebce3c80c0af93f994d5a1d7a0b1eeb23271929" +checksum = "1bf2e165bb3457c8e098ea76f3e3bc9db55f87aa90d52d0e6be741470916aaa4" [[package]] name = "libloading" -version = "0.6.6" +version = "0.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e9367bdfa836b7e3cf895867f7a570283444da90562980ec2263d6e1569b16bc" +checksum = "6f84d96438c15fcd6c3f244c8fce01d1e2b9c6b5623e9c711dc9286d8fc92d6a" dependencies = [ "cfg-if 1.0.0", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -660,11 +629,11 @@ dependencies = [ [[package]] name = "log" -version = "0.4.11" +version = "0.4.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4fabed175da42fed1fa0746b0ea71f412aa9d35e76e95e59b192c64b9dc2bf8b" +checksum = "51b9bbe6c47d51fc3e1a9b945965946b4c44142ab8792c50835a980d362c2710" dependencies = [ - "cfg-if 0.1.10", + "cfg-if 1.0.0", ] [[package]] @@ -703,7 +672,7 @@ checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" [[package]] name = "mcshader-lsp" -version = "0.9.5" +version = "0.9.6" dependencies = [ "anyhow", "bit-set", @@ -737,61 +706,49 @@ checksum = "0ee1c47aaa256ecabcaea351eae4a9b01ef39ed810004e298d2511ed284b1525" [[package]] name = "memmap2" -version = "0.1.0" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9b70ca2a6103ac8b665dc150b142ef0e4e89df640c9e6cf295d189c3caebe5a" +checksum = "00b6c2ebff6180198788f5db08d7ce3bc1d0b617176678831a7510825973e357" dependencies = [ "libc", ] +[[package]] +name = "memoffset" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "59accc507f1338036a0477ef61afdae33cde60840f4dfe481319ce3ad116ddf9" +dependencies = [ + "autocfg", +] + [[package]] name = "mio" -version = "0.6.23" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4afd66f5b91bf2a3bc13fad0e21caedac168ca4c707504e75585648ae80e4cc4" +checksum = "ba272f85fa0b41fc91872be579b3bbe0f56b792aa361a380eb669469f68dafb2" dependencies = [ - "cfg-if 0.1.10", - "fuchsia-zircon", - "fuchsia-zircon-sys", - "iovec", - "kernel32-sys", "libc", "log", "miow", - "net2", - "slab", - "winapi 0.2.8", -] - -[[package]] -name = "mio-extras" -version = "2.0.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52403fe290012ce777c4626790c8951324a2b9e3316b3143779c72b029742f19" -dependencies = [ - "lazycell", - "log", - "mio", - "slab", + "ntapi", + "winapi", ] [[package]] name = "miow" -version = "0.2.2" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ebd808424166322d4a38da87083bfddd3ac4c131334ed55856112eb06d46944d" +checksum = "b9f1c5b025cda876f66ef43a113f91ebc9f4ccef34843000e0adf6ebbab84e21" dependencies = [ - "kernel32-sys", - "net2", - "winapi 0.2.8", - "ws2_32-sys", + "winapi", ] [[package]] name = "mockall" -version = "0.9.0" +version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "619634fd9149c4a06e66d8fd9256e85326d8eeee75abee4565ff76c92e4edfe0" +checksum = "3d4d70639a72f972725db16350db56da68266ca368b2a1fe26724a903ad3d6b8" dependencies = [ "cfg-if 1.0.0", "downcast", @@ -804,9 +761,9 @@ dependencies = [ [[package]] name = "mockall_derive" -version = "0.9.0" +version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "83714c95dbf4c24202f0f1b208f0f248e6bd65abfa8989303611a71c0f781548" +checksum = "79ef208208a0dea3f72221e26e904cdc6db2e481d9ade89081ddd494f1dbaa6b" dependencies = [ "cfg-if 1.0.0", "proc-macro2", @@ -816,10 +773,11 @@ dependencies = [ [[package]] name = "ndk" -version = "0.2.1" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5eb167c1febed0a496639034d0c76b3b74263636045db5489eee52143c246e73" +checksum = "96d868f654c72e75f8687572699cdabe755f03effbb62542768e995d5b8d699d" dependencies = [ + "bitflags", "jni-sys", "ndk-sys", "num_enum", @@ -827,24 +785,31 @@ dependencies = [ ] [[package]] -name = "ndk-glue" -version = "0.2.1" +name = "ndk-context" +version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bdf399b8b7a39c6fb153c4ec32c72fd5fe789df24a647f229c239aa7adb15241" +checksum = "4e3c5cc68637e21fe8f077f6a1c9e0b9ca495bb74895226b476310f613325884" + +[[package]] +name = "ndk-glue" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a1c68f70683c5fc9a747a383744206cd371741b2f0b31781ab6770487ec572e2" dependencies = [ "lazy_static", "libc", "log", "ndk", + "ndk-context", "ndk-macro", "ndk-sys", ] [[package]] name = "ndk-macro" -version = "0.2.0" +version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "05d1c6307dc424d0f65b9b06e94f88248e6305726b14729fd67a5e47b2dc481d" +checksum = "0df7ac00c4672f9d5aece54ee3347520b7e20f158656c7db2e6de01902eb7a6c" dependencies = [ "darling", "proc-macro-crate", @@ -855,31 +820,21 @@ dependencies = [ [[package]] name = "ndk-sys" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c44922cb3dbb1c70b5e5f443d63b64363a898564d739ba5198e3a9138442868d" - -[[package]] -name = "net2" -version = "0.2.37" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "391630d12b68002ae1e25e8f974306474966550ad82dac6886fb8910c19568ae" -dependencies = [ - "cfg-if 0.1.10", - "libc", - "winapi 0.3.9", -] +checksum = "e1bcdd74c20ad5d95aacd60ef9ba40fdf77f767051040541df557b7a9b2a2121" [[package]] name = "nix" -version = "0.18.0" +version = "0.22.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "83450fe6a6142ddd95fb064b746083fc4ef1705fe81f64a64e1d4b39f54a1055" +checksum = "e4916f159ed8e5de0082076562152a76b7a1f64a01fd9d1e0fea002c37624faf" dependencies = [ "bitflags", "cc", - "cfg-if 0.1.10", + "cfg-if 1.0.0", "libc", + "memoffset", ] [[package]] @@ -898,6 +853,15 @@ version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "61807f77802ff30975e01f4f071c8ba10c022052f98b3294119f3e615d13e5be" +[[package]] +name = "ntapi" +version = "0.3.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f6bb902e437b6d86e03cce10a7e2af662292c5dfef23b65899ea3ac9354ad44" +dependencies = [ + "winapi", +] + [[package]] name = "num" version = "0.2.1" @@ -977,9 +941,9 @@ dependencies = [ [[package]] name = "num_enum" -version = "0.4.3" +version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca565a7df06f3d4b485494f25ba05da1435950f4dc263440eda7a6fa9b8e36e4" +checksum = "3f9bd055fb730c4f8f4f57d45d35cd6b3f0980535b056dc7ff119cee6a66ed6f" dependencies = [ "derivative", "num_enum_derive", @@ -987,9 +951,9 @@ dependencies = [ [[package]] name = "num_enum_derive" -version = "0.4.3" +version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ffa5a33ddddfee04c0283a7653987d634e880347e96b5b2ed64de07efb59db9d" +checksum = "486ea01961c4a818096de679a8b740b26d9033146ac5291b1c98557658f8cdd9" dependencies = [ "proc-macro-crate", "proc-macro2", @@ -1008,9 +972,9 @@ dependencies = [ [[package]] name = "once_cell" -version = "1.5.2" +version = "1.7.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "13bd41f508810a131401606d54ac32a467c97172d74ba7662562ebba5ad07fa0" +checksum = "af8b08b04175473088b46763e51ee54da5f9a164bc162f615b91bc179dbf15a3" [[package]] name = "osmesa-sys" @@ -1027,16 +991,7 @@ version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "53cdc5b785b7a58c5aad8216b3dfa114df64b0b06ae6e1501cef91df2fbdf8f9" dependencies = [ - "winapi 0.3.9", -] - -[[package]] -name = "owned_ttf_parser" -version = "0.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9f923fb806c46266c02ab4a5b239735c144bdeda724a50ed058e5226f594cde3" -dependencies = [ - "ttf-parser", + "winapi", ] [[package]] @@ -1061,7 +1016,7 @@ dependencies = [ "libc", "redox_syscall", "smallvec", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -1078,9 +1033,9 @@ checksum = "d4fd5641d01c8f18a23da7b6fe29298ff4b55afcccdf78973b24cf3175fee32e" [[package]] name = "petgraph" -version = "0.5.1" +version = "0.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "467d164a6de56270bd7c4d070df81d07beace25012d5103ced4e9ff08d6afdb7" +checksum = "4a13a2fa9d0b63e5f22328828741e523766fff0ee9e779316902290dff3f824f" dependencies = [ "fixedbitset", "indexmap", @@ -1094,12 +1049,13 @@ checksum = "3831453b3449ceb48b6d9c7ad7c96d5ea673e9b470a1dc578c2ce6521230884c" [[package]] name = "predicates" -version = "1.0.6" +version = "2.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "73dd9b7b200044694dfede9edf907c1ca19630908443e9447e624993700c6932" +checksum = "a5aab5be6e4732b473071984b3164dbbfb7a3674d30ea5ff44410b6bcd960c3c" dependencies = [ - "difference", + "difflib", "float-cmp", + "itertools", "normalize-line-endings", "predicates-core", "regex", @@ -1123,39 +1079,40 @@ dependencies = [ [[package]] name = "pretty_assertions" -version = "0.6.1" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3f81e1644e1b54f5a68959a29aa86cde704219254669da328ecfdf6a1f09d427" +checksum = "76d5b548b725018ab5496482b45cb8bef21e9fed1858a6d674e3a8a0f0bb5d50" dependencies = [ "ansi_term", "ctor", - "difference", + "diff", "output_vt100", ] [[package]] name = "proc-macro-crate" -version = "0.1.5" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d6ea3c4595b96363c13943497db34af4460fb474a95c43f4446ad341b8c9785" +checksum = "1ebace6889caf889b4d3f76becee12e90353f2b8c7d875534a71e5742f8f6f83" dependencies = [ + "thiserror", "toml", ] [[package]] name = "proc-macro2" -version = "1.0.24" +version = "1.0.36" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e0704ee1a7e00d7bb417d0770ea303c1bccbabf0ef1667dae92b5967f5f8a71" +checksum = "c7342d5883fbccae1cc37a2353b09c87c9b0f3afd73f5fb9bba687a1f733b029" dependencies = [ "unicode-xid", ] [[package]] name = "quote" -version = "1.0.8" +version = "1.0.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "991431c3519a3f36861882da93630ce66b52918dcf1b8e2fd66b397fc96f28df" +checksum = "864d3e96a899863136fc6e99f3d7cae289dafe43bf2c5ac19b70df7210c0a145" dependencies = [ "proc-macro2", ] @@ -1180,7 +1137,7 @@ dependencies = [ "libc", "rand_core 0.3.1", "rdrand", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -1200,11 +1157,11 @@ checksum = "9c33a3c44ca05fa6f1807d8e6743f3824e8509beca625669633be0acbdf509dc" [[package]] name = "raw-window-handle" -version = "0.3.3" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0a441a7a6c80ad6473bd4b74ec1c9a4c951794285bf941c2126f607c72e48211" +checksum = "fba75eee94a9d5273a68c9e1e105d9cffe1ef700532325788389e5a83e2522b7" dependencies = [ - "libc", + "cty", ] [[package]] @@ -1246,7 +1203,7 @@ version = "0.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7" dependencies = [ - "winapi 0.3.9", + "winapi", ] [[package]] @@ -1280,16 +1237,6 @@ version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7cfffa8a89d8758be2dd5605c5fc62bce055af2491ebf3ce953d4d31512c59fd" -[[package]] -name = "rusttype" -version = "0.9.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dc7c727aded0be18c5b80c1640eae0ac8e396abf6fa8477d96cb37d18ee5ec59" -dependencies = [ - "ab_glyph_rasterizer", - "owned_ttf_parser", -] - [[package]] name = "ryu" version = "1.0.5" @@ -1369,12 +1316,6 @@ dependencies = [ "libc", ] -[[package]] -name = "slab" -version = "0.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c111b5bd5695e56cffe5129854aa230b39c93a305372fdbb2668ca2394eea9f8" - [[package]] name = "smallvec" version = "1.6.1" @@ -1383,11 +1324,10 @@ checksum = "fe0f37c9e8f3c5a4a66ad655a93c74daac4ad00c441533bf5c6e7990bb42604e" [[package]] name = "smithay-client-toolkit" -version = "0.12.2" +version = "0.15.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "316e13a3eb853ce7bf72ad3530dc186cb2005c57c521ef5f4ada5ee4eed74de6" +checksum = "1325f292209cee78d5035530932422a30aa4c8fda1a16593ac083c1de211e68a" dependencies = [ - "andrew", "bitflags", "calloop", "dlib", @@ -1395,6 +1335,7 @@ dependencies = [ "log", "memmap2", "nix", + "pkg-config", "wayland-client", "wayland-cursor", "wayland-protocols", @@ -1402,15 +1343,15 @@ dependencies = [ [[package]] name = "strsim" -version = "0.9.3" +version = "0.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6446ced80d6c486436db5c078dde11a9f73d42b57fb273121e160b84f63d894c" +checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" [[package]] name = "syn" -version = "1.0.60" +version = "1.0.86" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c700597eca8a5a762beb35753ef6b94df201c81cca676604f547495a0d7f0081" +checksum = "8a65b3f4ffa0092e9887669db0eae07941f023991ab58ea44da8fe8e2d511c6b" dependencies = [ "proc-macro2", "quote", @@ -1429,18 +1370,18 @@ dependencies = [ [[package]] name = "thiserror" -version = "1.0.23" +version = "1.0.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "76cc616c6abf8c8928e2fdcc0dbfab37175edd8fb49a4641066ad1364fdab146" +checksum = "602eca064b2d83369e2b2f34b09c70b605402801927c65c11071ac911d299b88" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.23" +version = "1.0.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9be73a2caec27583d0046ef3796c3794f868a5bc813db689eed00c7631275cd1" +checksum = "bad553cc2c78e8de258400763a647e80e6d1b31ee237275d756f6836d204494c" dependencies = [ "proc-macro2", "quote", @@ -1449,11 +1390,11 @@ dependencies = [ [[package]] name = "thread_local" -version = "1.1.0" +version = "1.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bb9bc092d0d51e76b2b19d9d85534ffc9ec2db959a2523cdae0697e2972cd447" +checksum = "5516c27b78311c50bf42c071425c560ac799b11c30b31f87e3081965fe5e0180" dependencies = [ - "lazy_static", + "once_cell", ] [[package]] @@ -1486,12 +1427,6 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a7f741b240f1a48843f9b8e0444fb55fb2a4ff67293b50a9179dfd5ea67f8d41" -[[package]] -name = "ttf-parser" -version = "0.6.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3e5d7cd7ab3e47dda6e56542f4bbf3824c15234958c6e1bd6aaa347e93499fdc" - [[package]] name = "unicode-bidi" version = "0.3.4" @@ -1542,15 +1477,69 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "777182bc735b6424e1a57516d35ed72cb8019d85c8c9bf536dccb3445c1a2f7d" dependencies = [ "same-file", - "winapi 0.3.9", + "winapi", "winapi-util", ] [[package]] -name = "wayland-client" -version = "0.28.3" +name = "wasm-bindgen" +version = "0.2.79" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bdbdbe01d03b2267809f3ed99495b37395387fde789e0f2ebb78e8b43f75b6d7" +checksum = "25f1af7423d8588a3d840681122e72e6a24ddbcb3f0ec385cac0d12d24256c06" +dependencies = [ + "cfg-if 1.0.0", + "wasm-bindgen-macro", +] + +[[package]] +name = "wasm-bindgen-backend" +version = "0.2.79" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b21c0df030f5a177f3cba22e9bc4322695ec43e7257d865302900290bcdedca" +dependencies = [ + "bumpalo", + "lazy_static", + "log", + "proc-macro2", + "quote", + "syn", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-macro" +version = "0.2.79" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2f4203d69e40a52ee523b2529a773d5ffc1dc0071801c87b3d270b471b80ed01" +dependencies = [ + "quote", + "wasm-bindgen-macro-support", +] + +[[package]] +name = "wasm-bindgen-macro-support" +version = "0.2.79" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa8a30d46208db204854cadbb5d4baf5fcf8071ba5bf48190c3e59937962ebc" +dependencies = [ + "proc-macro2", + "quote", + "syn", + "wasm-bindgen-backend", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-shared" +version = "0.2.79" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d958d035c4438e28c70e4321a2911302f10135ce78a9c7834c0cab4123d06a2" + +[[package]] +name = "wayland-client" +version = "0.29.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91223460e73257f697d9e23d401279123d36039a3f7a449e983f123292d4458f" dependencies = [ "bitflags", "downcast-rs", @@ -1564,9 +1553,9 @@ dependencies = [ [[package]] name = "wayland-commons" -version = "0.28.3" +version = "0.29.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "480450f76717edd64ad04a4426280d737fc3d10a236b982df7b1aee19f0e2d56" +checksum = "94f6e5e340d7c13490eca867898c4cec5af56c27a5ffe5c80c6fc4708e22d33e" dependencies = [ "nix", "once_cell", @@ -1576,9 +1565,9 @@ dependencies = [ [[package]] name = "wayland-cursor" -version = "0.28.3" +version = "0.29.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d6eb122c160223a7660feeaf949d0100281d1279acaaed3720eb3c9894496e5f" +checksum = "c52758f13d5e7861fc83d942d3d99bf270c83269575e52ac29e5b73cb956a6bd" dependencies = [ "nix", "wayland-client", @@ -1587,9 +1576,9 @@ dependencies = [ [[package]] name = "wayland-egl" -version = "0.28.3" +version = "0.29.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c653507447113c967a1aeee413699acb42d96d6302ec967c6d51930eae8aa7f5" +checksum = "83281d69ee162b59031c666385e93bde4039ec553b90c4191cdb128ceea29a3a" dependencies = [ "wayland-client", "wayland-sys", @@ -1597,9 +1586,9 @@ dependencies = [ [[package]] name = "wayland-protocols" -version = "0.28.3" +version = "0.29.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "319a82b4d3054dd25acc32d9aee0f84fa95b63bc983fffe4703b6b8d47e01a30" +checksum = "60147ae23303402e41fe034f74fb2c35ad0780ee88a1c40ac09a3be1e7465741" dependencies = [ "bitflags", "wayland-client", @@ -1609,9 +1598,9 @@ dependencies = [ [[package]] name = "wayland-scanner" -version = "0.28.3" +version = "0.29.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7010ba5767b3fcd350decc59055390b4ebe6bd1b9279a9feb1f1888987f1133d" +checksum = "39a1ed3143f7a143187156a2ab52742e89dac33245ba505c17224df48939f9e0" dependencies = [ "proc-macro2", "quote", @@ -1620,9 +1609,9 @@ dependencies = [ [[package]] name = "wayland-sys" -version = "0.28.3" +version = "0.29.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6793834e0c35d11fd96a97297abe03d37be627e1847da52e17d7e0e3b51cc099" +checksum = "d9341df79a8975679188e37dab3889bfa57c44ac2cb6da166f519a81cbe452d4" dependencies = [ "dlib", "lazy_static", @@ -1630,10 +1619,14 @@ dependencies = [ ] [[package]] -name = "winapi" -version = "0.2.8" +name = "web-sys" +version = "0.3.56" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" +checksum = "c060b319f29dd25724f09a2ba1418f142f539b2be99fbf4d2d5a8f7330afb8eb" +dependencies = [ + "js-sys", + "wasm-bindgen", +] [[package]] name = "winapi" @@ -1645,12 +1638,6 @@ dependencies = [ "winapi-x86_64-pc-windows-gnu", ] -[[package]] -name = "winapi-build" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" - [[package]] name = "winapi-i686-pc-windows-gnu" version = "0.4.0" @@ -1663,7 +1650,7 @@ version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178" dependencies = [ - "winapi 0.3.9", + "winapi", ] [[package]] @@ -1674,12 +1661,12 @@ checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" [[package]] name = "winit" -version = "0.24.0" +version = "0.26.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "da4eda6fce0eb84bd0a33e3c8794eb902e1033d0a1d5a31bc4f19b1b4bbff597" +checksum = "9b43cc931d58b99461188607efd7acb2a093e65fc621f54cad78517a6063e73a" dependencies = [ "bitflags", - "cocoa 0.24.0", + "cocoa", "core-foundation 0.9.1", "core-graphics 0.22.2", "core-video-sys", @@ -1689,7 +1676,6 @@ dependencies = [ "libc", "log", "mio", - "mio-extras", "ndk", "ndk-glue", "ndk-sys", @@ -1698,21 +1684,14 @@ dependencies = [ "percent-encoding", "raw-window-handle", "smithay-client-toolkit", + "wasm-bindgen", "wayland-client", - "winapi 0.3.9", + "wayland-protocols", + "web-sys", + "winapi", "x11-dl", ] -[[package]] -name = "ws2_32-sys" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e" -dependencies = [ - "winapi 0.2.8", - "winapi-build", -] - [[package]] name = "x11-dl" version = "2.18.5" @@ -1734,12 +1713,6 @@ dependencies = [ "nom", ] -[[package]] -name = "xdg" -version = "2.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d089681aa106a86fade1b0128fb5daf07d5867a509ab036d99988dec80429a57" - [[package]] name = "xml-rs" version = "0.8.3" diff --git a/server/Cargo.toml b/server/Cargo.toml index cf34f9e..0c6c61d 100644 --- a/server/Cargo.toml +++ b/server/Cargo.toml @@ -2,30 +2,30 @@ name = "mcshader-lsp" version = "0.9.5" authors = ["Noah Santschi-Cooney "] -edition = "2018" +edition = "2021" [dependencies] rust_lsp = { git = "https://github.com/Strum355/RustLSP", branch = "master" } -serde_json = "1.0.61" -serde = "1.0.123" -walkdir = "2.3.1" -petgraph = "0.5.1" -lazy_static = "1.4.0" -regex = "1.4.3" -chan = "0.1.23" -url = "2.2.0" -percent-encoding = "2.1.0" -anyhow = "1.0.38" -bit-set = "0.5.2" -thiserror = "1.0.23" -glutin = "0.26.0" -gl = "0.14.0" -ctor = "0.1.18" -mockall = "0.9.0" -path-slash = "0.1.4" +serde_json = "1.0" +serde = "1.0" +walkdir = "2.3" +petgraph = "0.6" +lazy_static = "1.4" +regex = "1.4" +chan = "0.1" +url = "2.2" +percent-encoding = "2.1" +anyhow = "1.0" +bit-set = "0.5" +thiserror = "1.0" +glutin = "0.28" +gl = "0.14" +ctor = "0.1" +mockall = "0.11" +path-slash = "0.1" [dev-dependencies] -tempdir = "0.3.7" -fs_extra = "1.2.0" +tempdir = "0.3" +fs_extra = "1.2" hamcrest2 = "*" -pretty_assertions = "0.6.1" \ No newline at end of file +pretty_assertions = "1.1" \ No newline at end of file From 7cf009ee61e84ac2f7f7551b8a0396c7534d0220 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Tue, 15 Mar 2022 00:59:16 +0000 Subject: [PATCH 22/56] added base logging infrastructure, more to come SOON --- server/Cargo.lock | 220 +++++++++++++++++++++++++++++++++++++++++- server/Cargo.toml | 7 ++ server/src/logging.rs | 42 ++++++++ server/src/main.rs | 11 ++- server/src/test.rs | 29 +++--- 5 files changed, 292 insertions(+), 17 deletions(-) create mode 100644 server/src/logging.rs diff --git a/server/Cargo.lock b/server/Cargo.lock index 08193a4..dcd1dfb 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -32,6 +32,23 @@ version = "1.0.38" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "afddf7f520a80dbf76e6f50a35bca42a2331ef227a28b3b6dc5c2e2338d114b1" +[[package]] +name = "arc-swap" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c5d78ce20460b82d3fa150275ed9d55e21064fc7951177baacf86a145c4a4b1f" + +[[package]] +name = "atty" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8" +dependencies = [ + "hermit-abi", + "libc", + "winapi", +] + [[package]] name = "autocfg" version = "1.0.1" @@ -310,6 +327,27 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6184e33543162437515c2e2b48714794e37845ec9851711914eec9d308f6ebe8" +[[package]] +name = "dirs-next" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b98cf8ebf19c3d1b223e151f99a4f9f0690dca41414773390fc824184ac833e1" +dependencies = [ + "cfg-if 1.0.0", + "dirs-sys-next", +] + +[[package]] +name = "dirs-sys-next" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ebda144c4fe02d1f7ea1a7d9641b6fc6b580adcfa024ae48797ecdeb6825b4d" +dependencies = [ + "libc", + "redox_users", + "winapi", +] + [[package]] name = "dispatch" version = "0.2.0" @@ -413,6 +451,17 @@ version = "0.1.30" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4c7e4c2612746b0df8fed4ce0c69156021b704c9aefa360311c04e6e9e002eed" +[[package]] +name = "getrandom" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d39cd93900197114fa1fcb7ae84ca742095eed9442088988ae74fa744e930e77" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "wasi", +] + [[package]] name = "gl" version = "0.14.0" @@ -521,6 +570,15 @@ version = "0.11.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e" +[[package]] +name = "hermit-abi" +version = "0.1.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" +dependencies = [ + "libc", +] + [[package]] name = "ident_case" version = "1.0.1" @@ -575,6 +633,12 @@ version = "0.4.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "dd25036021b0de88a0aff6b850051563c6516d0bf53f8638938edbb9de732736" +[[package]] +name = "itoa" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1aab8fc367588b89dcee83ab0fd66b72b50b72fa1904d7095045ace2b0c81c35" + [[package]] name = "jni-sys" version = "0.3.0" @@ -675,6 +739,7 @@ name = "mcshader-lsp" version = "0.9.6" dependencies = [ "anyhow", + "arc-swap", "bit-set", "chan", "ctor", @@ -684,14 +749,20 @@ dependencies = [ "hamcrest2", "lazy_static", "mockall", + "once_cell", "path-slash", "percent-encoding", "petgraph", "pretty_assertions", + "rand 0.8.5", "regex", "rust_lsp", "serde", "serde_json", + "slog", + "slog-atomic", + "slog-scope", + "slog-term", "tempdir", "thiserror", "url", @@ -961,6 +1032,15 @@ dependencies = [ "syn", ] +[[package]] +name = "num_threads" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c539a50b93a303167eded6e8dff5220cd39447409fb659f4cd24b1f72fe4f133" +dependencies = [ + "libc", +] + [[package]] name = "objc" version = "0.2.7" @@ -1014,7 +1094,7 @@ dependencies = [ "cfg-if 1.0.0", "instant", "libc", - "redox_syscall", + "redox_syscall 0.1.57", "smallvec", "winapi", ] @@ -1047,6 +1127,12 @@ version = "0.3.19" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3831453b3449ceb48b6d9c7ad7c96d5ea673e9b470a1dc578c2ce6521230884c" +[[package]] +name = "ppv-lite86" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eb9f9e6e233e5c4a35559a617bf40a4ec447db2e84c20b55a6f83167b7e57872" + [[package]] name = "predicates" version = "2.1.1" @@ -1140,6 +1226,27 @@ dependencies = [ "winapi", ] +[[package]] +name = "rand" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +dependencies = [ + "libc", + "rand_chacha", + "rand_core 0.6.3", +] + +[[package]] +name = "rand_chacha" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" +dependencies = [ + "ppv-lite86", + "rand_core 0.6.3", +] + [[package]] name = "rand_core" version = "0.3.1" @@ -1155,6 +1262,15 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9c33a3c44ca05fa6f1807d8e6743f3824e8509beca625669633be0acbdf509dc" +[[package]] +name = "rand_core" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d34f1408f55294453790c48b2f1ebbb1c5b4b7563eb1f418bcfcfdbb06ebb4e7" +dependencies = [ + "getrandom", +] + [[package]] name = "raw-window-handle" version = "0.4.2" @@ -1179,6 +1295,25 @@ version = "0.1.57" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce" +[[package]] +name = "redox_syscall" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8380fe0152551244f0747b1bf41737e0f8a74f97a14ccefd1148187271634f3c" +dependencies = [ + "bitflags", +] + +[[package]] +name = "redox_users" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "528532f3d801c87aec9def2add9ca802fe569e44a544afe633765267840abe64" +dependencies = [ + "getrandom", + "redox_syscall 0.2.11", +] + [[package]] name = "regex" version = "1.4.3" @@ -1237,6 +1372,12 @@ version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7cfffa8a89d8758be2dd5605c5fc62bce055af2491ebf3ce953d4d31512c59fd" +[[package]] +name = "rustversion" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2cc38e8fa666e2de3c4aba7edeb5ffc5246c1c2ed0e3d17e560aeeba736b23f" + [[package]] name = "ryu" version = "1.0.5" @@ -1290,7 +1431,7 @@ version = "1.0.61" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4fceb2595057b6891a4ee808f70054bd2d12f0e97f1cbb78689b59f676df325a" dependencies = [ - "itoa", + "itoa 0.4.7", "ryu", "serde", ] @@ -1316,6 +1457,46 @@ dependencies = [ "libc", ] +[[package]] +name = "slog" +version = "2.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8347046d4ebd943127157b94d63abb990fcf729dc4e9978927fdf4ac3c998d06" + +[[package]] +name = "slog-atomic" +version = "3.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f6b517f2dda9e1458733eb8350bad1a3632ffed8141be4c0f3d6def899a9b066" +dependencies = [ + "arc-swap", + "slog", +] + +[[package]] +name = "slog-scope" +version = "4.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2f95a4b4c3274cd2869549da82b57ccc930859bdbf5bcea0424bc5f140b3c786" +dependencies = [ + "arc-swap", + "lazy_static", + "slog", +] + +[[package]] +name = "slog-term" +version = "2.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87d29185c55b7b258b4f120eab00f48557d4d9bc814f41713f449d35b0f8977c" +dependencies = [ + "atty", + "slog", + "term", + "thread_local", + "time", +] + [[package]] name = "smallvec" version = "1.6.1" @@ -1368,6 +1549,17 @@ dependencies = [ "remove_dir_all", ] +[[package]] +name = "term" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c59df8ac95d96ff9bede18eb7300b0fda5e5d8d90960e76f8e14ae765eedbf1f" +dependencies = [ + "dirs-next", + "rustversion", + "winapi", +] + [[package]] name = "thiserror" version = "1.0.29" @@ -1397,6 +1589,24 @@ dependencies = [ "once_cell", ] +[[package]] +name = "time" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "004cbc98f30fa233c61a38bc77e96a9106e65c88f2d3bef182ae952027e5753d" +dependencies = [ + "itoa 1.0.1", + "libc", + "num_threads", + "time-macros", +] + +[[package]] +name = "time-macros" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25eb0ca3468fc0acc11828786797f6ef9aa1555e4a211a60d64cc8e4d1be47d6" + [[package]] name = "tinyvec" version = "1.1.0" @@ -1481,6 +1691,12 @@ dependencies = [ "winapi-util", ] +[[package]] +name = "wasi" +version = "0.10.2+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6" + [[package]] name = "wasm-bindgen" version = "0.2.79" diff --git a/server/Cargo.toml b/server/Cargo.toml index 0c6c61d..79d930e 100644 --- a/server/Cargo.toml +++ b/server/Cargo.toml @@ -23,6 +23,13 @@ gl = "0.14" ctor = "0.1" mockall = "0.11" path-slash = "0.1" +slog = { version = "2.7", features = [ "max_level_trace", "release_max_level_trace" ] } +slog-term = "2.9" +slog-scope = "4.4" +slog-atomic = "3.1" +once_cell = "1.7" +rand = "0.8" +arc-swap = "1.5.0" [dev-dependencies] tempdir = "0.3" diff --git a/server/src/logging.rs b/server/src/logging.rs new file mode 100644 index 0000000..cbdb3ca --- /dev/null +++ b/server/src/logging.rs @@ -0,0 +1,42 @@ +use rand::{rngs, Rng}; +use slog::slog_o; +use slog_scope::GlobalLoggerGuard; +use slog_term::{FullFormat, PlainSyncDecorator}; +use std::{cell::RefCell, io::Stderr, sync::Arc}; +use lazy_static::lazy_static; +use slog::*; +use slog_atomic::*; + +fn new_trace_id() -> String { + let rng = CURRENT_RNG.with(|rng| rng.borrow_mut().gen::<[u8; 4]>()); + return format!("{:04x}", u32::from_be_bytes(rng)); +} + +pub fn slog_with_trace_id(f: F) { + slog_scope::scope(&slog_scope::logger().new(slog_o!("trace" => new_trace_id())), || { + f() + }) +} + +pub fn set_logger_with_level(level: Level) -> GlobalLoggerGuard { + let drain = Arc::new(logger_base(level).fuse()); + DRAIN_SWITCH.ctrl().set(drain.clone()); + slog_scope::set_global_logger(Logger::root(drain, o!())) +} + +fn logger_base(level: Level) -> LevelFilter>>> { + let plain = slog_term::PlainSyncDecorator::new(std::io::stderr()); + let drain = slog_term::FullFormat::new(plain).build().fuse(); + drain.filter_level(level) +} + +thread_local! { + static CURRENT_RNG: RefCell = RefCell::new(rngs::ThreadRng::default()); +} + +lazy_static! { + static ref DRAIN_SWITCH: AtomicSwitch<()> = { + let logger = logger_base(Level::Info).fuse(); + AtomicSwitch::new(logger) + }; +} \ No newline at end of file diff --git a/server/src/main.rs b/server/src/main.rs index bc63b7a..1fed784 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -17,6 +17,7 @@ use std::io::{stdin, stdout, BufRead, BufReader}; use std::rc::Rc; use std::fs; use std::iter::{Extend, FromIterator}; +use slog::Level; use path_slash::PathBufExt; @@ -33,6 +34,7 @@ mod dfs; mod merge_views; mod consts; mod opengl; +mod logging; mod url_norm; #[cfg(test)] @@ -46,8 +48,9 @@ lazy_static! { } fn main() { - let stdin = stdin(); + let guard = logging::set_logger_with_level(Level::Info); + let stdin = stdin(); let endpoint_output = LSPEndpoint::create_lsp_output_with_output_stream(stdout); let cache_graph = graph::CachedStableGraph::new(); @@ -57,7 +60,8 @@ fn main() { graph: Rc::new(RefCell::new(cache_graph)), root: "".into(), command_provider: None, - opengl_context: Rc::new(opengl::OpenGlContext::new()) + opengl_context: Rc::new(opengl::OpenGlContext::new()), + _log_guard: Some(guard), }; langserver.command_provider = Some(commands::CustomCommandProvider::new(vec![ @@ -83,7 +87,8 @@ struct MinecraftShaderLanguageServer { graph: Rc>, root: PathBuf, command_provider: Option, - opengl_context: Rc + opengl_context: Rc, + _log_guard: Option, } #[derive(Clone, PartialEq, Eq, Hash)] diff --git a/server/src/test.rs b/server/src/test.rs index 4c1075e..1ba3b7f 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -6,6 +6,8 @@ use std::io::Result; use hamcrest2::prelude::*; use pretty_assertions::assert_eq; +use slog::Logger; +use slog::o; use tempdir::TempDir; use petgraph::algo::is_cyclic_directed; @@ -34,17 +36,20 @@ impl io::Write for StdoutNewline { } } -fn new_temp_server() -> MinecraftShaderLanguageServer { - let endpoint = LSPEndpoint::create_lsp_output_with_output_stream(|| StdoutNewline { - s: Box::new(io::sink()), - }); +fn new_temp_server(opengl_context: Option>) -> MinecraftShaderLanguageServer { + let endpoint = LSPEndpoint::create_lsp_output_with_output_stream(|| StdoutNewline { s: Box::new(io::sink()) }); + + let context = opengl_context.unwrap_or_else(|| Box::new(opengl::MockShaderValidator::new())); + let logger = Logger::root(slog::Discard, o!()); + let guard = slog_scope::set_global_logger(logger); MinecraftShaderLanguageServer { endpoint, graph: Rc::new(RefCell::new(graph::CachedStableGraph::new())), root: "".into(), command_provider: None, - opengl_context: Rc::new(opengl::MockShaderValidator::new()), + opengl_context: context.into(), + _log_guard: Some(guard), } } @@ -80,7 +85,7 @@ fn copy_to_tmp_dir(test_path: &str) -> (Rc, PathBuf) { #[allow(deprecated)] #[test] fn test_empty_initialize() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let tmp_dir = TempDir::new("mcshader").unwrap(); let tmp_path = tmp_dir.path(); @@ -131,7 +136,7 @@ fn test_empty_initialize() { #[allow(deprecated)] #[test] fn test_01_initialize() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let (_tmp_dir, tmp_path) = copy_to_tmp_dir("./testdata/01"); @@ -197,7 +202,7 @@ fn test_01_initialize() { #[test] fn test_05_initialize() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let (_tmp_dir, tmp_path) = copy_to_tmp_dir("./testdata/05"); @@ -902,7 +907,7 @@ fn test_graph_dfs_cycle() { #[test] fn test_generate_merge_list_01() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/01", &mut server); server.endpoint.request_shutdown(); @@ -941,7 +946,7 @@ fn test_generate_merge_list_01() { #[test] fn test_generate_merge_list_02() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/02", &mut server); server.endpoint.request_shutdown(); @@ -1014,7 +1019,7 @@ fn test_generate_merge_list_02() { #[test] fn test_generate_merge_list_03() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/03", &mut server); server.endpoint.request_shutdown(); @@ -1087,7 +1092,7 @@ fn test_generate_merge_list_03() { #[test] fn test_generate_merge_list_04() { - let mut server = new_temp_server(); + let mut server = new_temp_server(None); let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/04", &mut server); server.endpoint.request_shutdown(); From ebab8c899a33229741f720fbab64fd89eb19abdd Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 18 Mar 2022 19:00:42 +0000 Subject: [PATCH 23/56] formatting and adding a buncha log points --- server/src/commands.rs | 69 ++-- server/src/dfs.rs | 51 ++- server/src/graph.rs | 43 ++- server/src/lsp_ext.rs | 2 +- server/src/main.rs | 477 +++++++++++++----------- server/src/merge_views.rs | 86 ++--- server/src/opengl.rs | 48 ++- server/src/test.rs | 753 +++++++++++++------------------------- server/src/url_norm.rs | 42 ++- 9 files changed, 711 insertions(+), 860 deletions(-) diff --git a/server/src/commands.rs b/server/src/commands.rs index 890e4cb..3224c9e 100644 --- a/server/src/commands.rs +++ b/server/src/commands.rs @@ -1,34 +1,37 @@ -use std::{collections::HashMap, path::{Path, PathBuf}}; -use std::rc::Rc; use std::cell::RefCell; use std::fs::OpenOptions; use std::io::prelude::*; +use std::rc::Rc; +use std::{ + collections::HashMap, + path::{Path, PathBuf}, +}; +use petgraph::dot::Config; use serde_json::Value; use petgraph::{dot, graph::NodeIndex}; -use anyhow::{Result, format_err}; +use anyhow::{format_err, Result}; +use slog_scope::info; use std::fs; -use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJson}; use crate::dfs; +use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJson}; pub struct CustomCommandProvider { - commands: HashMap> + commands: HashMap>, } impl CustomCommandProvider { pub fn new(commands: Vec<(&str, Box)>) -> CustomCommandProvider { - CustomCommandProvider{ - commands: commands.into_iter().map(|tup| { - (tup.0.into(), tup.1) - }).collect(), + CustomCommandProvider { + commands: commands.into_iter().map(|tup| (tup.0.into(), tup.1)).collect(), } } - pub fn execute(&self, command: &str, args: Vec, root_path: &Path) -> Result { + pub fn execute(&self, command: &str, args: &[Value], root_path: &Path) -> Result { if self.commands.contains_key(command) { return self.commands.get(command).unwrap().run_command(root_path, args); } @@ -37,43 +40,42 @@ impl CustomCommandProvider { } pub trait Invokeable { - fn run_command(&self, root: &Path, arguments: Vec) -> Result; + fn run_command(&self, root: &Path, arguments: &[Value]) -> Result; } pub struct GraphDotCommand { - pub graph: Rc> + pub graph: Rc>, } impl Invokeable for GraphDotCommand { - fn run_command(&self, root: &Path, _: Vec) -> Result { + fn run_command(&self, root: &Path, _: &[Value]) -> Result { let filepath = root.join("graph.dot"); - eprintln!("generating dot file at {:?}", filepath); - let mut file = OpenOptions::new() - .truncate(true) - .write(true) - .create(true) - .open(filepath) - .unwrap(); + + info!("generating dot file"; "path" => filepath.as_os_str().to_str()); + + let mut file = OpenOptions::new().truncate(true).write(true).create(true).open(filepath).unwrap(); let mut write_data_closure = || -> Result<(), std::io::Error> { let graph = self.graph.as_ref(); file.seek(std::io::SeekFrom::Start(0))?; - file.write_all(dot::Dot::new(&graph.borrow().graph).to_string().as_bytes())?; + file.write_all("digraph {\n\tgraph [splines=ortho]\n\tnode [shape=box]\n".as_bytes())?; + file.write_all(dot::Dot::with_config(&graph.borrow().graph, &[Config::GraphContentOnly]).to_string().as_bytes())?; + file.write_all("\n}".as_bytes())?; file.flush()?; file.seek(std::io::SeekFrom::Start(0))?; Ok(()) }; match write_data_closure() { - Err(err) => Err(format_err!("Error generating graphviz data: {}", err)), - _ => Ok(Value::Null) + Err(err) => Err(format_err!("error generating graphviz data: {}", err)), + _ => Ok(Value::Null), } } } pub struct VirtualMergedDocument { - pub graph: Rc> + pub graph: Rc>, } impl VirtualMergedDocument { @@ -111,7 +113,7 @@ impl VirtualMergedDocument { let source = match fs::read_to_string(&path) { Ok(s) => s, - Err(e) => return Err(format_err!("error reading {:?}: {}", path, e)) + Err(e) => return Err(format_err!("error reading {:?}: {}", path, e)), }; let source = source.replace("\r\n", "\n"); sources.insert(path.clone(), source); @@ -122,7 +124,7 @@ impl VirtualMergedDocument { } impl Invokeable for VirtualMergedDocument { - fn run_command(&self, root: &Path, arguments: Vec) -> Result { + fn run_command(&self, root: &Path, arguments: &[Value]) -> Result { let path = PathBuf::from_json(arguments.get(0).unwrap())?; let file_ancestors = match self.get_file_toplevel_ancestors(&path) { @@ -132,15 +134,15 @@ impl Invokeable for VirtualMergedDocument { }, Err(e) => return Err(e), }; - - //eprintln!("ancestors for {}:\n\t{:?}", path, file_ancestors.iter().map(|e| self.graph.borrow().graph.node_weight(*e).unwrap().clone()).collect::>()); + + //info!("ancestors for {}:\n\t{:?}", path, file_ancestors.iter().map(|e| self.graph.borrow().graph.node_weight(*e).unwrap().clone()).collect::>()); // the set of all filepath->content. TODO: change to Url? let mut all_sources: HashMap = HashMap::new(); // if we are a top-level file (this has to be one of the set defined by Optifine, right?) if file_ancestors.is_empty() { - // gather the list of all descendants + // gather the list of all descendants let root = self.graph.borrow_mut().find_node(&path).unwrap(); let tree = match self.get_dfs_for_node(root) { Ok(tree) => tree, @@ -149,7 +151,7 @@ impl Invokeable for VirtualMergedDocument { let sources = match self.load_sources(&tree) { Ok(s) => s, - Err(e) => return Err(e) + Err(e) => return Err(e), }; all_sources.extend(sources); @@ -157,6 +159,9 @@ impl Invokeable for VirtualMergedDocument { let view = merge_views::generate_merge_list(&tree, &all_sources, &graph); return Ok(serde_json::value::Value::String(view)); } - return Err(format_err!("{:?} is not a top-level file aka has ancestors", path.strip_prefix(root).unwrap())) + return Err(format_err!( + "{:?} is not a top-level file aka has ancestors", + path.strip_prefix(root).unwrap() + )); } -} \ No newline at end of file +} diff --git a/server/src/dfs.rs b/server/src/dfs.rs index b296bd8..908d3bd 100644 --- a/server/src/dfs.rs +++ b/server/src/dfs.rs @@ -10,19 +10,19 @@ struct VisitCount { children: usize, } -/// Performs a depth-first search with duplicates +/// Performs a depth-first search with duplicates pub struct Dfs<'a> { stack: Vec, graph: &'a CachedStableGraph, - cycle: Vec + cycle: Vec, } -impl <'a> Dfs<'a> { +impl<'a> Dfs<'a> { pub fn new(graph: &'a CachedStableGraph, start: NodeIndex) -> Self { Dfs { stack: vec![start], graph, - cycle: Vec::new() + cycle: Vec::new(), } } @@ -42,49 +42,44 @@ impl <'a> Dfs<'a> { for child in children { if prev.node == *child { let cycle_nodes: Vec = self.cycle.iter().map(|n| n.node).collect(); - return Err( - error::CycleError::new(&cycle_nodes, *child, self.graph) - ); + return Err(error::CycleError::new(&cycle_nodes, *child, self.graph)); } } } Ok(()) - } + } } -impl <'a> Iterator for Dfs<'a> { +impl<'a> Iterator for Dfs<'a> { type Item = Result<(NodeIndex, Option), error::CycleError>; fn next(&mut self) -> Option), error::CycleError>> { - let parent = match self.cycle.last() { - Some(p) => Some(p.node), - None => None, - }; + let parent = self.cycle.last().map(|p| p.node); if let Some(node) = self.stack.pop() { - self.cycle.push(VisitCount{ + self.cycle.push(VisitCount { node, children: self.graph.graph.edges(node).count(), touch: 1, }); let mut children = self.graph.child_node_indexes(node); - + if !children.is_empty() { // sort by line number in parent children.sort_by(|x, y| { let graph = &self.graph.graph; let edge1 = graph.edge_weight(graph.find_edge(node, *x).unwrap()).unwrap(); let edge2 = graph.edge_weight(graph.find_edge(node, *y).unwrap()).unwrap(); - + edge2.line.cmp(&edge1.line) }); - + match self.check_for_cycle(&children) { Ok(_) => {} Err(e) => return Some(Err(e)), }; - + for child in children { self.stack.push(child); } @@ -101,9 +96,13 @@ impl <'a> Iterator for Dfs<'a> { pub mod error { use petgraph::stable_graph::NodeIndex; - use std::{fmt::{Debug, Display}, path::PathBuf, error::Error as StdError}; + use std::{ + error::Error as StdError, + fmt::{Debug, Display}, + path::PathBuf, + }; - use crate::{graph::CachedStableGraph, consts}; + use crate::{consts, graph::CachedStableGraph}; use rust_lsp::lsp_types::{Diagnostic, DiagnosticSeverity, Position, Range}; @@ -111,7 +110,7 @@ pub mod error { pub struct CycleError(Vec); impl StdError for CycleError {} - + impl CycleError { pub fn new(nodes: &[NodeIndex], current_node: NodeIndex, graph: &CachedStableGraph) -> Self { let mut resolved_nodes: Vec = nodes.iter().map(|i| graph.get_node(*i)).collect(); @@ -119,22 +118,22 @@ pub mod error { CycleError(resolved_nodes) } } - + impl Display for CycleError { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { let mut disp = String::new(); disp.push_str(format!("Include cycle detected:\n{:?} imports ", self.0[0]).as_str()); - for p in &self.0[1..self.0.len()-1] { + for p in &self.0[1..self.0.len() - 1] { disp.push_str(format!("\n{:?}, which imports ", *p).as_str()); } - disp.push_str(format!("\n{:?}", self.0[self.0.len()-1]).as_str()); + disp.push_str(format!("\n{:?}", self.0[self.0.len() - 1]).as_str()); f.write_str(disp.as_str()) } } impl From for Diagnostic { fn from(e: CycleError) -> Diagnostic { - Diagnostic{ + Diagnostic { severity: Some(DiagnosticSeverity::Error), range: Range::new(Position::new(0, 0), Position::new(0, 500)), source: Some(consts::SOURCE.into()), @@ -153,4 +152,4 @@ pub mod error { format!("{}", e) } } -} \ No newline at end of file +} diff --git a/server/src/graph.rs b/server/src/graph.rs index dd6fa26..39ed80a 100644 --- a/server/src/graph.rs +++ b/server/src/graph.rs @@ -1,9 +1,13 @@ -use petgraph::stable_graph::StableDiGraph; -use petgraph::stable_graph::NodeIndex; -use petgraph::Direction; use petgraph::stable_graph::EdgeIndex; +use petgraph::stable_graph::NodeIndex; +use petgraph::stable_graph::StableDiGraph; +use petgraph::Direction; -use std::{collections::{HashMap, HashSet}, path::{Path, PathBuf}, str::FromStr}; +use std::{ + collections::{HashMap, HashSet}, + path::{Path, PathBuf}, + str::FromStr, +}; use super::IncludePosition; @@ -16,14 +20,14 @@ pub struct CachedStableGraph { pub graph: StableDiGraph, cache: HashMap, // Maps a node index to its abstracted string representation. - // Mainly used as the graph is based on NodeIndex and + // Mainly used as the graph is based on NodeIndex. reverse_index: HashMap, } impl CachedStableGraph { #[allow(clippy::new_without_default)] pub fn new() -> CachedStableGraph { - CachedStableGraph{ + CachedStableGraph { graph: StableDiGraph::new(), cache: HashMap::new(), reverse_index: HashMap::new(), @@ -91,15 +95,21 @@ impl CachedStableGraph { #[allow(dead_code)] pub fn child_node_names(&self, node: NodeIndex) -> Vec { - self.graph.neighbors(node).map(|n| self.reverse_index.get(&n).unwrap().clone()).collect() + self.graph + .neighbors(node) + .map(|n| self.reverse_index.get(&n).unwrap().clone()) + .collect() } pub fn child_node_meta(&self, node: NodeIndex) -> Vec<(PathBuf, IncludePosition)> { - self.graph.neighbors(node).map(|n| { - let edge = self.graph.find_edge(node, n).unwrap(); - let edge_meta = self.graph.edge_weight(edge).unwrap(); - return (self.reverse_index.get(&n).unwrap().clone(), edge_meta.clone()) - }).collect() + self.graph + .neighbors(node) + .map(|n| { + let edge = self.graph.find_edge(node, n).unwrap(); + let edge_meta = self.graph.edge_weight(edge).unwrap(); + return (self.reverse_index.get(&n).unwrap().clone(), edge_meta.clone()); + }) + .collect() } pub fn child_node_indexes(&self, node: NodeIndex) -> Vec { @@ -108,7 +118,10 @@ impl CachedStableGraph { #[allow(dead_code)] pub fn parent_node_names(&self, node: NodeIndex) -> Vec { - self.graph.neighbors_directed(node, Direction::Incoming).map(|n| self.reverse_index.get(&n).unwrap().clone()).collect() + self.graph + .neighbors_directed(node, Direction::Incoming) + .map(|n| self.reverse_index.get(&n).unwrap().clone()) + .collect() } pub fn parent_node_indexes(&self, node: NodeIndex) -> Vec { @@ -129,7 +142,7 @@ impl CachedStableGraph { if node == initial && !visited.is_empty() { return vec![]; } - + let parents = self.parent_node_indexes(node); let mut collection = Vec::with_capacity(parents.len()); @@ -148,4 +161,4 @@ impl CachedStableGraph { collection } -} \ No newline at end of file +} diff --git a/server/src/lsp_ext.rs b/server/src/lsp_ext.rs index a4eb1b0..bcf1198 100644 --- a/server/src/lsp_ext.rs +++ b/server/src/lsp_ext.rs @@ -13,4 +13,4 @@ pub struct StatusParams { pub status: String, pub message: Option, pub icon: Option, -} \ No newline at end of file +} diff --git a/server/src/main.rs b/server/src/main.rs index 1fed784..2aa7c03 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -1,38 +1,48 @@ -use rust_lsp::jsonrpc::{*, method_types::*}; +use rust_lsp::jsonrpc::{method_types::*, *}; use rust_lsp::lsp::*; -use rust_lsp::lsp_types::{*, notification::*}; +use rust_lsp::lsp_types::{notification::*, *}; use petgraph::stable_graph::NodeIndex; -use serde_json::Value; +use serde::Deserialize; +use serde_json::{Value, from_value}; + use url_norm::FromUrl; + use walkdir::WalkDir; -use std::{cell::RefCell, path::{Path, PathBuf}, str::FromStr}; -use std::collections::{HashMap, HashSet}; use std::collections::hash_map::RandomState; +use std::collections::{HashMap, HashSet}; use std::convert::TryFrom; -use std::fmt::{Display, Formatter, Debug}; -use std::io::{stdin, stdout, BufRead, BufReader}; -use std::rc::Rc; +use std::fmt::{Debug, Display, Formatter}; use std::fs; +use std::io::{stdin, stdout, BufRead, BufReader}; use std::iter::{Extend, FromIterator}; +use std::rc::Rc; +use std::str::FromStr; + +use std::{ + cell::RefCell, + path::{Path, PathBuf}, +}; + use slog::Level; +use slog_scope::{debug, error, info, warn}; use path_slash::PathBufExt; -use anyhow::{Result, anyhow}; +use anyhow::{anyhow, Result}; use regex::Regex; use lazy_static::lazy_static; -mod graph; mod commands; -mod lsp_ext; -mod dfs; -mod merge_views; mod consts; +mod dfs; +mod graph; +mod lsp_ext; +mod merge_views; mod opengl; mod logging; mod url_norm; @@ -73,10 +83,10 @@ fn main() { ), ( "virtualMerge", - Box::new(commands::VirtualMergedDocument{ - graph: Rc::clone(&langserver.graph) - }) - ) + Box::new(commands::VirtualMergedDocument { + graph: Rc::clone(&langserver.graph), + }), + ), ])); LSPEndpoint::run_server_from_input(&mut stdin.lock(), endpoint_output, langserver); @@ -110,8 +120,12 @@ impl Display for IncludePosition { } } +#[derive(Debug)] pub enum TreeType { - Fragment, Vertex, Geometry, Compute + Fragment, + Vertex, + Geometry, + Compute, } impl MinecraftShaderLanguageServer { @@ -125,10 +139,12 @@ impl MinecraftShaderLanguageServer { } pub fn gen_initial_graph(&self) { - eprintln!("root of project is {:?}", self.root); + info!("generating graph for current root"; "root" => self.root.to_str().unwrap()); // filter directories and files not ending in any of the 3 extensions - WalkDir::new(&self.root).into_iter().filter_map(|entry| { + WalkDir::new(&self.root) + .into_iter() + .filter_map(|entry| { if entry.is_err() { return None; } @@ -141,29 +157,31 @@ impl MinecraftShaderLanguageServer { let ext = match path.extension() { Some(e) => e, - None => return None, + None => return None, }; + // TODO: include user added extensions if ext != "vsh" && ext != "fsh" && ext != "glsl" && ext != "inc" { return None; } Some(entry.into_path()) - }).for_each(|path| { - // iterate all valid found files, search for includes, add a node into the graph for each - // file and add a file->includes KV into the map - self.add_file_and_includes_to_graph(&path); - }); + }) + .for_each(|path| { + // iterate all valid found files, search for includes, add a node into the graph for each + // file and add a file->includes KV into the map + self.add_file_and_includes_to_graph(&path); + }); - eprintln!("finished building project include graph"); + info!("finished building project include graph"); } fn add_file_and_includes_to_graph(&self, path: &Path) { let includes = self.find_includes(path); - let idx = self.graph.borrow_mut().add_node(&path); + let idx = self.graph.borrow_mut().add_node(path); - //eprintln!("adding {:?} with {:?}", path, includes); + debug!("adding includes for new file"; "file" => path.to_str().unwrap(), "includes" => format!("{:?}", includes)); for include in includes { self.add_include(include, idx); } @@ -186,17 +204,12 @@ impl MinecraftShaderLanguageServer { }) .filter(|line| RE_INCLUDE.is_match(line.1.as_str())) .for_each(|line| { - let cap = RE_INCLUDE - .captures(line.1.as_str()) - .unwrap() - .get(1) - .unwrap(); + let cap = RE_INCLUDE.captures(line.1.as_str()).unwrap().get(1).unwrap(); let start = cap.start(); let end = cap.end(); let mut path: String = cap.as_str().into(); - // TODO: difference between / and not let full_include = if path.starts_with('/') { path = path.strip_prefix('/').unwrap().to_string(); self.root.join("shaders").join(PathBuf::from_slash(&path)) @@ -204,14 +217,7 @@ impl MinecraftShaderLanguageServer { file.parent().unwrap().join(PathBuf::from_slash(&path)) }; - includes.push(( - full_include, - IncludePosition { - line: line.0, - start, - end, - } - )); + includes.push((full_include, IncludePosition { line: line.0, start, end })); }); includes @@ -220,12 +226,10 @@ impl MinecraftShaderLanguageServer { fn update_includes(&self, file: &Path) { let includes = self.find_includes(file); - eprintln!("updating {:?} with {:?}", file, includes); + info!("includes found for file"; "file" => file.to_str().unwrap(), "includes" => format!("{:?}", includes)); - let idx = match self.graph.borrow_mut().find_node(&file) { - None => { - return - }, + let idx = match self.graph.borrow_mut().find_node(file) { + None => return, Some(n) => n, }; @@ -235,7 +239,11 @@ impl MinecraftShaderLanguageServer { let to_be_added = new_children.difference(&prev_children); let to_be_removed = prev_children.difference(&new_children); - eprintln!("removing:\n\t{:?}\nadding:\n\t{:?}", to_be_removed, to_be_added); + debug!( + "include sets diff'd"; + "for removal" => format!("{:?}", to_be_removed), + "for addition" => format!("{:?}", to_be_added) + ); for removal in to_be_removed { let child = self.graph.borrow_mut().find_node(&removal.0).unwrap(); @@ -256,15 +264,25 @@ impl MinecraftShaderLanguageServer { }, Err(e) => return Err(e), }; - - eprintln!("ancestors for {:?}:\n\t{:?}", uri, file_ancestors.iter().map(|e| PathBuf::from_str(&self.graph.borrow().graph.node_weight(*e).unwrap().clone()).unwrap()).collect::>()); + + info!( + "top-level file ancestors found"; + "uri" => uri.to_str().unwrap(), + "ancestors" => format!("{:?}", file_ancestors + .iter() + .map(|e| PathBuf::from_str( + &self.graph.borrow().graph[*e].clone() + ) + .unwrap()) + .collect::>()) + ); // the set of all filepath->content. let mut all_sources: HashMap = HashMap::new(); // the set of filepath->list of diagnostics to report let mut diagnostics: HashMap> = HashMap::new(); - // we want to backfill the diagnostics map with all linked sources + // we want to backfill the diagnostics map with all linked sources let back_fill = |all_sources: &HashMap, diagnostics: &mut HashMap>| { for path in all_sources.keys() { diagnostics.entry(Url::from_file_path(path).unwrap()).or_default(); @@ -273,8 +291,8 @@ impl MinecraftShaderLanguageServer { // if we are a top-level file (this has to be one of the set defined by Optifine, right?) if file_ancestors.is_empty() { - // gather the list of all descendants - let root = self.graph.borrow_mut().find_node(&uri).unwrap(); + // gather the list of all descendants + let root = self.graph.borrow_mut().find_node(uri).unwrap(); let tree = match self.get_dfs_for_node(root) { Ok(tree) => tree, Err(e) => { @@ -283,20 +301,20 @@ impl MinecraftShaderLanguageServer { } }; - all_sources.extend( self.load_sources(&tree)?); + all_sources.extend(self.load_sources(&tree)?); let view = { - let graph = self.graph.borrow(); + let graph = self.graph.borrow(); merge_views::generate_merge_list(&tree, &all_sources, &graph) }; let root_path = self.graph.borrow().get_node(root); let ext = match root_path.extension() { - Some(ext) => ext, + Some(ext) => ext.to_str().unwrap(), None => { back_fill(&all_sources, &mut diagnostics); - return Ok(diagnostics) - }, + return Ok(diagnostics); + } }; let tree_type = if ext == "fsh" { TreeType::Fragment @@ -307,17 +325,20 @@ impl MinecraftShaderLanguageServer { } else if ext == "csh" { TreeType::Compute } else { - eprintln!("got a non fsh|vsh|gsh|csh ({:?}) as a file root ancestor: {:?}", ext, root_path); + warn!( + "got a non fsh|vsh|gsh|csh as a file root ancestor, skipping lint"; + "extension" => ext, "root_ancestor" => root_path.to_str().unwrap() + ); back_fill(&all_sources, &mut diagnostics); - return Ok(diagnostics) + return Ok(diagnostics); }; let stdout = match self.opengl_context.clone().validate(tree_type, view) { Some(s) => s, None => { back_fill(&all_sources, &mut diagnostics); - return Ok(diagnostics) - }, + return Ok(diagnostics); + } }; diagnostics.extend(self.parse_validator_stdout(uri, stdout, "")); } else { @@ -335,8 +356,8 @@ impl MinecraftShaderLanguageServer { let root_path = self.graph.borrow().get_node(*root).clone(); let ext = match root_path.extension() { - Some(ext) => ext, - None => continue + Some(ext) => ext.to_str().unwrap(), + None => continue, }; let tree_type = if ext == "fsh" { TreeType::Fragment @@ -347,7 +368,10 @@ impl MinecraftShaderLanguageServer { } else if ext == "csh" { TreeType::Compute } else { - eprintln!("got a non fsh|vsh|gsh|csh ({:?}) as a file root ancestor: {:?}", ext, root_path); + warn!( + "got a non fsh|vsh|gsh|csh as a file root ancestor, skipping lint"; + "extension" => ext, "root_ancestor" => root_path.to_str().unwrap() + ); continue; }; @@ -358,7 +382,7 @@ impl MinecraftShaderLanguageServer { for tree in all_trees { let view = { - let graph = self.graph.borrow(); + let graph = self.graph.borrow(); merge_views::generate_merge_list(&tree.1, &all_sources, &graph) }; @@ -451,7 +475,7 @@ impl MinecraftShaderLanguageServer { let dfs = dfs::Dfs::new(&graph_ref, root); - dfs.collect::, _>>() + dfs.collect::>() } pub fn load_sources(&self, nodes: &[(NodeIndex, Option)]) -> Result> { @@ -467,7 +491,7 @@ impl MinecraftShaderLanguageServer { let source = match fs::read_to_string(&path) { Ok(s) => s, - Err(e) => return Err(anyhow!("error reading {:?}: {}", path, e)) + Err(e) => return Err(anyhow!("error reading {:?}: {}", path, e)), }; let source = source.replace("\r\n", "\n"); sources.insert(path.clone(), source); @@ -489,86 +513,88 @@ impl MinecraftShaderLanguageServer { } pub fn publish_diagnostic(&self, diagnostics: HashMap>, document_version: Option) { - eprintln!("DIAGNOSTICS:\n{:?}", diagnostics); + // info!("DIAGNOSTICS:\n{:?}", diagnostics); for (uri, diagnostics) in diagnostics { - self.endpoint.send_notification(PublishDiagnostics::METHOD, PublishDiagnosticsParams { - uri, - diagnostics, - version: document_version, - }).expect("failed to publish diagnostics"); + self.endpoint + .send_notification( + PublishDiagnostics::METHOD, + PublishDiagnosticsParams { + uri, + diagnostics, + version: document_version, + }, + ) + .expect("failed to publish diagnostics"); } } fn set_status(&self, status: impl Into, message: impl Into, icon: impl Into) { - self.endpoint.send_notification(lsp_ext::Status::METHOD, lsp_ext::StatusParams { - status: status.into(), - message: Some(message.into()), - icon: Some(icon.into()), - }).unwrap_or(()); + self.endpoint + .send_notification( + lsp_ext::Status::METHOD, + lsp_ext::StatusParams { + status: status.into(), + message: Some(message.into()), + icon: Some(icon.into()), + }, + ) + .unwrap_or(()); } } impl LanguageServerHandling for MinecraftShaderLanguageServer { fn initialize(&mut self, params: InitializeParams, completable: MethodCompletable) { - + logging::slog_with_trace_id(|| { + info!("starting server..."); - let capabilities = ServerCapabilities{ - document_link_provider: Some(DocumentLinkOptions { - resolve_provider: None, - work_done_progress_options: WorkDoneProgressOptions { - work_done_progress: None, - }, - }), - execute_command_provider: Some(ExecuteCommandOptions { - commands: vec!["graphDot".into()], - work_done_progress_options: WorkDoneProgressOptions { - work_done_progress: None, - }, - }), - text_document_sync: Some(TextDocumentSyncCapability::Options( - TextDocumentSyncOptions { - open_close: Some(true), - will_save: None, - will_save_wait_until: None, - change: Some(TextDocumentSyncKind::Full), - save: Some(TextDocumentSyncSaveOptions::SaveOptions(SaveOptions { - include_text: Some(true), - })) - }, - )), - .. ServerCapabilities::default() - }; + let capabilities = ServerCapabilities { + document_link_provider: Some(DocumentLinkOptions { + resolve_provider: None, + work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None }, + }), + execute_command_provider: Some(ExecuteCommandOptions { + commands: vec!["graphDot".into()], + work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None }, + }), + text_document_sync: Some(TextDocumentSyncCapability::Options(TextDocumentSyncOptions { + open_close: Some(true), + will_save: None, + will_save_wait_until: None, + change: Some(TextDocumentSyncKind::Full), + save: Some(TextDocumentSyncSaveOptions::SaveOptions(SaveOptions { include_text: Some(true) })), + })), + ..ServerCapabilities::default() + }; - let root = match params.root_uri { - Some(uri) => PathBuf::from_url(uri), - None => { - completable.complete(Err(MethodError { - code: 42069, - message: "Must be in workspace".into(), - data: InitializeError { - retry: false, - }, - })); - return; - } - }; + let root = match params.root_uri { + Some(uri) => PathBuf::from_url(uri), + None => { + completable.complete(Err(MethodError { + code: 42069, + message: "Must be in workspace".into(), + data: InitializeError { retry: false }, + })); + return; + } + }; - completable.complete(Ok(InitializeResult { - capabilities, - server_info: None, - })); + completable.complete(Ok(InitializeResult { + capabilities, + server_info: None, + })); - self.set_status("loading", "Building dependency graph...", "$(loading~spin)"); + self.set_status("loading", "Building dependency graph...", "$(loading~spin)"); - self.root = root; + self.root = root; - self.gen_initial_graph(); + self.gen_initial_graph(); - self.set_status("ready", "Project initialized", "$(check)"); + self.set_status("ready", "Project initialized", "$(check)"); + }); } fn shutdown(&mut self, _: (), completable: LSCompletable<()>) { - eprintln!("shutting down language server..."); + warn!("shutting down language server..."); completable.complete(Ok(())); } @@ -577,22 +603,25 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { } fn workspace_change_configuration(&mut self, params: DidChangeConfigurationParams) { - //let config = params.settings.as_object().unwrap().get("mcglsl").unwrap(); + logging::slog_with_trace_id(|| { + }); } fn did_open_text_document(&mut self, params: DidOpenTextDocumentParams) { - //eprintln!("opened doc {}", params.text_document.uri); - let path = PathBuf::from_url(params.text_document.uri); - if !path.starts_with(&self.root) { - return - } - if self.graph.borrow_mut().find_node(&path) == None { - self.add_file_and_includes_to_graph(&path); - } - match self.lint(&path) { - Ok(diagnostics) => self.publish_diagnostic(diagnostics, None), - Err(e) => eprintln!("error linting: {}", e), - } + logging::slog_with_trace_id(|| { + //info!("opened doc {}", params.text_document.uri); + let path = PathBuf::from_url(params.text_document.uri); + if !path.starts_with(&self.root) { + return; + } + if self.graph.borrow_mut().find_node(&path) == None { + self.add_file_and_includes_to_graph(&path); + } + match self.lint(&path) { + Ok(diagnostics) => self.publish_diagnostic(diagnostics, None), + Err(e) => error!("error linting"; "error" => format!("{:?}", e), "path" => path.to_str().unwrap()), + } + }); } fn did_change_text_document(&mut self, _: DidChangeTextDocumentParams) {} @@ -600,18 +629,18 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn did_close_text_document(&mut self, _: DidCloseTextDocumentParams) {} fn did_save_text_document(&mut self, params: DidSaveTextDocumentParams) { - //eprintln!("saved doc {}", params.text_document.uri); + logging::slog_with_trace_id(|| { + let path = PathBuf::from_url(params.text_document.uri); + if !path.starts_with(&self.root) { + return; + } + self.update_includes(&path); - let path = PathBuf::from_url(params.text_document.uri); - if !path.starts_with(&self.root) { - return - } - self.update_includes(&path); - - match self.lint(&path) { - Ok(diagnostics) => self.publish_diagnostic(diagnostics, None), - Err(e) => eprintln!("error linting: {}", e), - } + match self.lint(&path) { + Ok(diagnostics) => self.publish_diagnostic(diagnostics, None), + Err(e) => error!("error linting"; "error" => format!("{:?}", e), "path" => path.to_str().unwrap()), + } + }); } fn did_change_watched_files(&mut self, _: DidChangeWatchedFilesParams) {} @@ -635,24 +664,41 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { } fn execute_command(&mut self, params: ExecuteCommandParams, completable: LSCompletable>) { - match self.command_provider.as_ref().unwrap().execute(¶ms.command, params.arguments, &self.root) { - Ok(resp) => { - eprintln!("executed {} successfully", params.command); - self.endpoint.send_notification(ShowMessage::METHOD, ShowMessageParams { - typ: MessageType::Info, - message: format!("Command {} executed successfully.", params.command), - }).expect("failed to send popup/show message notification"); - completable.complete(Ok(Some(resp))) - }, - Err(err) => { - self.endpoint.send_notification(ShowMessage::METHOD, ShowMessageParams { - typ: MessageType::Error, - message: format!("Failed to execute `{}`. Reason: {}", params.command, err), - }).expect("failed to send popup/show message notification"); - eprintln!("failed to execute {}: {}", params.command, err); - completable.complete(Err(MethodError::new(32420, err.to_string(), ()))) - }, - } + logging::slog_with_trace_id(|| { + match self + .command_provider + .as_ref() + .unwrap() + .execute(¶ms.command, ¶ms.arguments, &self.root) + { + Ok(resp) => { + info!("executed command successfully"; "command" => params.command.clone()); + self.endpoint + .send_notification( + ShowMessage::METHOD, + ShowMessageParams { + typ: MessageType::Info, + message: format!("Command {} executed successfully.", params.command), + }, + ) + .expect("failed to send popup/show message notification"); + completable.complete(Ok(Some(resp))) + } + Err(err) => { + error!("failed to execute command"; "command" => params.command.clone(), "error" => format!("{:?}", err)); + self.endpoint + .send_notification( + ShowMessage::METHOD, + ShowMessageParams { + typ: MessageType::Error, + message: format!("Failed to execute `{}`. Reason: {}", params.command, err), + }, + ) + .expect("failed to send popup/show message notification"); + completable.complete(Err(MethodError::new(32420, err.to_string(), ()))) + } + } + }); } fn signature_help(&mut self, _: TextDocumentPositionParams, completable: LSCompletable) { @@ -692,55 +738,52 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { } fn document_link(&mut self, params: DocumentLinkParams, completable: LSCompletable>) { - eprintln!("document link file: {:?}", params.text_document.uri.to_file_path().unwrap()); - // node for current document - let curr_doc = params - .text_document - .uri - .to_file_path() - .unwrap(); - let node = match self.graph.borrow_mut().find_node(&curr_doc) { - Some(n) => n, - None => { - completable.complete(Ok(vec![])); - return - }, - }; + logging::slog_with_trace_id(|| { + // node for current document + let curr_doc = params.text_document.uri.to_file_path().unwrap(); + let node = match self.graph.borrow_mut().find_node(&curr_doc) { + Some(n) => n, + None => { + warn!("document not found in graph"; "path" => curr_doc.to_str().unwrap()); + completable.complete(Ok(vec![])); + return; + } + }; - let edges: Vec = self - .graph - .borrow() - .child_node_indexes(node) - .into_iter() - .filter_map(|child| { - let graph = self.graph.borrow(); - let value = graph.get_edge_meta(node, child); - let path = graph.get_node(child); - let url = match Url::from_file_path(&path) { - Ok(url) => url, - Err(e) => { - eprintln!("error converting {:?} into url: {:?}", path, e); - return None; - } - }; + let edges: Vec = self + .graph + .borrow() + .child_node_indexes(node) + .into_iter() + .filter_map(|child| { + let graph = self.graph.borrow(); + let value = graph.get_edge_meta(node, child); + let path = graph.get_node(child); + let url = match Url::from_file_path(&path) { + Ok(url) => url, + Err(e) => { + error!("error converting into url"; "path" => path.to_str().unwrap(), "error" => format!("{:?}", e)); + return None; + } + }; - Some(DocumentLink { - range: Range::new( - Position::new( - u32::try_from(value.line).unwrap(), - u32::try_from(value.start).unwrap()), - Position::new( - u32::try_from(value.line).unwrap(), - u32::try_from(value.end).unwrap()), - ), - target: Some(url), - //tooltip: Some(url.path().to_string().strip_prefix(self.root.clone().unwrap().as_str()).unwrap().to_string()), - tooltip: None, - data: None, + Some(DocumentLink { + range: Range::new( + Position::new(u32::try_from(value.line).unwrap(), u32::try_from(value.start).unwrap()), + Position::new(u32::try_from(value.line).unwrap(), u32::try_from(value.end).unwrap()), + ), + target: Some(url.clone()), + tooltip: Some(url.path().to_string()), + data: None, + }) }) - }).collect(); - eprintln!("links: {:?}", edges); - completable.complete(Ok(edges)); + .collect(); + debug!("document link results"; + "links" => format!("{:?}", edges.iter().map(|e| (e.range, e.target.as_ref().unwrap().path())).collect::>()), + "path" => curr_doc.to_str().unwrap(), + ); + completable.complete(Ok(edges)); + }); } fn document_link_resolve(&mut self, _: DocumentLink, completable: LSCompletable) { diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index a6c70e2..2566c02 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -1,6 +1,9 @@ -use std::{collections::{HashMap, LinkedList, VecDeque}, path::{Path, PathBuf}}; -use std::iter::Peekable; use std::cmp::min; +use std::iter::Peekable; +use std::{ + collections::{HashMap, LinkedList, VecDeque}, + path::{Path, PathBuf}, +}; use core::slice::Iter; @@ -8,7 +11,7 @@ use petgraph::stable_graph::NodeIndex; use crate::graph::CachedStableGraph; -/// FilialTuple represents a tuple with a parent at index 0 +/// FilialTuple represents a tuple with a parent at index 0 /// and a child at index 1. Parent can be nullable in the case of /// the child being a top level node in the tree. #[derive(PartialEq, Eq, Hash)] @@ -21,9 +24,7 @@ impl From<(Option<&NodeIndex>, NodeIndex)> for FilialTuple { } pub fn generate_merge_list<'a>( - nodes: &'a [(NodeIndex, Option)], - sources: &'a HashMap, - graph: &'a CachedStableGraph + nodes: &'a [(NodeIndex, Option)], sources: &'a HashMap, graph: &'a CachedStableGraph, ) -> String { let mut line_directives: Vec = Vec::new(); @@ -45,17 +46,23 @@ pub fn generate_merge_list<'a>( // stack to keep track of the depth first traversal let mut stack = VecDeque::::new(); - create_merge_views(&mut nodes_iter, &mut merge_list, &mut last_offset_set, graph, sources, &mut line_directives, &mut stack); + create_merge_views( + &mut nodes_iter, + &mut merge_list, + &mut last_offset_set, + graph, + sources, + &mut line_directives, + &mut stack, + ); // now we add a view of the remainder of the root file let offset = *last_offset_set.get(&FilialTuple(None, first)).unwrap(); let len = sources.get(&first_path).unwrap().len(); - merge_list.push_back(&sources.get(&first_path).unwrap()[min(offset, len) ..]); + merge_list.push_back(&sources.get(&first_path).unwrap()[min(offset, len)..]); - let total_len = merge_list.iter().fold(0, |a, b| { - a + b.len() - }); + let total_len = merge_list.iter().fold(0, |a, b| a + b.len()); let mut merged = String::with_capacity(total_len); for slice in merge_list { @@ -66,21 +73,16 @@ pub fn generate_merge_list<'a>( } fn create_merge_views<'a>( - nodes: &mut Peekable)>>, - merge_list: &mut LinkedList<&'a str>, - last_offset_set: &mut HashMap, - graph: &'a CachedStableGraph, - sources: &'a HashMap, - line_directives: &mut Vec, - stack: &mut VecDeque, + nodes: &mut Peekable)>>, merge_list: &mut LinkedList<&'a str>, + last_offset_set: &mut HashMap, graph: &'a CachedStableGraph, sources: &'a HashMap, + line_directives: &mut Vec, stack: &mut VecDeque, ) { - loop { let n = match nodes.next() { Some(n) => n, None => return, }; - + // invariant: never None as only the first element in `nodes` should have a None, which is popped off in the calling function let parent = n.1.unwrap(); let child = n.0; @@ -90,8 +92,10 @@ fn create_merge_views<'a>( let parent_source = sources.get(&parent_path).unwrap(); let (char_for_line, char_following_line) = char_offset_for_line(edge.line, parent_source); - - let offset = *last_offset_set.insert((stack.back(), parent).into(), char_following_line).get_or_insert(0); + + let offset = *last_offset_set + .insert((stack.back(), parent).into(), char_following_line) + .get_or_insert(0); merge_list.push_back(&parent_source[offset..char_for_line]); add_opening_line_directive(&child_path, merge_list, line_directives); @@ -104,21 +108,21 @@ fn create_merge_views<'a>( // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad let offset = { match child_source.ends_with('\n') { - true => child_source.len()-1, + true => child_source.len() - 1, false => child_source.len(), } }; merge_list.push_back(&child_source[..offset]); last_offset_set.insert(FilialTuple(Some(parent), child), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line+2, &parent_path, merge_list, line_directives); + add_closing_line_directive(edge.line + 2, &parent_path, merge_list, line_directives); // if the next pair's parent is not the current pair's parent, we need to bubble up if stack.contains(&next.1.unwrap()) { return; } continue; } - + stack.push_back(parent); create_merge_views(nodes, merge_list, last_offset_set, graph, sources, line_directives, stack); stack.pop_back(); @@ -128,37 +132,37 @@ fn create_merge_views<'a>( // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 let end_offset = { match child_source.ends_with('\n') { - true => 1/* child_source.len()-1 */, - false => 0/* child_source.len() */, + true => 1, /* child_source.len()-1 */ + false => 0, /* child_source.len() */ } }; - if offset < child_source.len()-end_offset { + if offset < child_source.len() - end_offset { // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad merge_list.push_back(&child_source[offset../* std::cmp::max( */child_source.len()-end_offset/* , offset) */]); last_offset_set.insert(FilialTuple(Some(parent), child), 0); } // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line+2, &parent_path, merge_list, line_directives); + add_closing_line_directive(edge.line + 2, &parent_path, merge_list, line_directives); // we need to check the next item at the point of original return further down the callstack if nodes.peek().is_some() && stack.contains(&nodes.peek().unwrap().1.unwrap()) { return; } - }, + } None => { let child_source = sources.get(&child_path).unwrap(); // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad let offset = { match child_source.ends_with('\n') { - true => child_source.len()-1, + true => child_source.len() - 1, false => child_source.len(), } }; merge_list.push_back(&child_source[..offset]); last_offset_set.insert(FilialTuple(Some(parent), child), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line+2, &parent_path, merge_list, line_directives); + add_closing_line_directive(edge.line + 2, &parent_path, merge_list, line_directives); } } } @@ -171,17 +175,17 @@ fn char_offset_for_line(line_num: usize, source: &str) -> (usize, usize) { let mut char_following_line: usize = 0; for (n, line) in source.lines().enumerate() { if n == line_num { - char_following_line += line.len()+1; + char_following_line += line.len() + 1; break; } - char_for_line += line.len()+1; + char_for_line += line.len() + 1; char_following_line = char_for_line; } (char_for_line, char_following_line) } fn add_opening_line_directive(path: &Path, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { - let line_directive = format!("#line 1 \"{}\"\n", path.to_str().unwrap().replace("\\", "\\\\")); + let line_directive = format!("#line 1 \"{}\"\n", path.to_str().unwrap().replace('\\', "\\\\")); line_directives.push(line_directive); unsafe_get_and_insert(merge_list, line_directives); } @@ -190,14 +194,14 @@ fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedL // Optifine doesn't seem to add a leading newline if the previous line was a #line directive let line_directive = if let Some(l) = merge_list.back() { if l.trim().starts_with("#line") { - format!("#line {} \"{}\"\n", line, path.to_str().unwrap().replace("\\", "\\\\")) + format!("#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) } else { - format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace("\\", "\\\\")) + format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) } } else { - format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace("\\", "\\\\")) + format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) }; - + line_directives.push(line_directive); unsafe_get_and_insert(merge_list, line_directives); } @@ -205,7 +209,7 @@ fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedL fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, line_directives: &[String]) { // :^) unsafe { - let vec_ptr_offset = line_directives.as_ptr().add(line_directives.len()-1); + let vec_ptr_offset = line_directives.as_ptr().add(line_directives.len() - 1); merge_list.push_back(&vec_ptr_offset.as_ref().unwrap()[..]); } -} \ No newline at end of file +} diff --git a/server/src/opengl.rs b/server/src/opengl.rs index 13cca4a..d86f4d3 100644 --- a/server/src/opengl.rs +++ b/server/src/opengl.rs @@ -1,5 +1,7 @@ +use std::ffi::{CStr, CString}; use std::ptr; -use std::ffi::{CString, CStr}; + +use slog_scope::{debug, info}; #[cfg(test)] use mockall::automock; @@ -10,31 +12,33 @@ pub trait ShaderValidator { } pub struct OpenGlContext { - _ctx: glutin::Context + _ctx: glutin::Context, } impl OpenGlContext { pub fn new() -> OpenGlContext { let events_loop = glutin::event_loop::EventLoop::new(); - let gl_window = glutin::ContextBuilder::new().build_headless(&*events_loop, glutin::dpi::PhysicalSize::new(1, 1)).unwrap(); - + let gl_window = glutin::ContextBuilder::new() + .build_headless(&*events_loop, glutin::dpi::PhysicalSize::new(1, 1)) + .unwrap(); + let gl_window = unsafe { let gl_window = gl_window.make_current().unwrap(); gl::load_with(|symbol| gl_window.get_proc_address(symbol) as *const _); gl_window }; + let gl_ctx = OpenGlContext { _ctx: gl_window }; + unsafe { - eprintln!( - "Using OpenGL device {} {} {}", - String::from_utf8(CStr::from_ptr(gl::GetString(gl::VENDOR) as *const _).to_bytes().to_vec()).unwrap(), - String::from_utf8(CStr::from_ptr(gl::GetString(gl::VERSION) as *const _).to_bytes().to_vec()).unwrap(), - String::from_utf8(CStr::from_ptr(gl::GetString(gl::RENDERER) as *const _).to_bytes().to_vec()).unwrap() + debug!( + "OpenGL device"; + "vendor" => gl_ctx.vendor(), + "version" => String::from_utf8(CStr::from_ptr(gl::GetString(gl::VERSION) as *const _).to_bytes().to_vec()).unwrap(), + "renderer" => String::from_utf8(CStr::from_ptr(gl::GetString(gl::RENDERER) as *const _).to_bytes().to_vec()).unwrap() ); } - OpenGlContext{ - _ctx: gl_window, - } + gl_ctx } unsafe fn compile_and_get_shader_log(&self, shader: gl::types::GLuint, source: String) -> Option { @@ -49,7 +53,12 @@ impl OpenGlContext { let mut info_len: gl::types::GLint = 0; gl::GetShaderiv(shader, gl::INFO_LOG_LENGTH, &mut info_len); let mut info = vec![0u8; info_len as usize]; - gl::GetShaderInfoLog(shader, info_len as gl::types::GLsizei, ptr::null_mut(), info.as_mut_ptr() as *mut gl::types::GLchar); + gl::GetShaderInfoLog( + shader, + info_len as gl::types::GLsizei, + ptr::null_mut(), + info.as_mut_ptr() as *mut gl::types::GLchar, + ); info.set_len((info_len - 1) as usize); // ignore null for str::from_utf8 Some(String::from_utf8(info).unwrap()) } else { @@ -62,7 +71,7 @@ impl OpenGlContext { impl ShaderValidator for OpenGlContext { fn validate(&self, tree_type: super::TreeType, source: String) -> Option { - unsafe { + let result = unsafe { match tree_type { crate::TreeType::Fragment => { // Fragment shader @@ -81,10 +90,19 @@ impl ShaderValidator for OpenGlContext { } crate::TreeType::Compute => { // Compute shader - let compute_shader= gl::CreateShader(gl::COMPUTE_SHADER); + let compute_shader = gl::CreateShader(gl::COMPUTE_SHADER); self.compile_and_get_shader_log(compute_shader, source) } } + }; + + match &result { + Some(output) => info!("compilation errors reported"; "errors" => format!("`{}`", output.replace('\n', "\\n"))), + None => info!("compilation reported no errors"), } + + result + } + } } diff --git a/server/src/test.rs b/server/src/test.rs index 1ba3b7f..67b883b 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -62,10 +62,10 @@ fn copy_files(files: &str, dest: &TempDir) { copy_items(&files, dest.path().join("shaders"), opts).unwrap(); } -fn copy_to_and_set_root(test_path: &str, server: &mut MinecraftShaderLanguageServer,) -> (Rc, PathBuf) { +fn copy_to_and_set_root(test_path: &str, server: &mut MinecraftShaderLanguageServer) -> (Rc, PathBuf) { let (_tmp_dir, tmp_path) = copy_to_tmp_dir(test_path); - server.root = tmp_path.clone();//format!("{}{}", "file://", tmp_path); + server.root = tmp_path.clone(); //format!("{}{}", "file://", tmp_path); (_tmp_dir, tmp_path) } @@ -119,10 +119,7 @@ fn test_empty_initialize() { } }; - let completable = MethodCompletable::new(ResponseCompletable::new( - Some(Id::Number(1)), - Box::new(on_response), - )); + let completable = MethodCompletable::new(ResponseCompletable::new(Some(Id::Number(1)), Box::new(on_response))); server.initialize(initialize_params, completable); assert_eq!(server.root, tmp_path); @@ -169,10 +166,7 @@ fn test_01_initialize() { } }; - let completable = MethodCompletable::new(ResponseCompletable::new( - Some(Id::Number(1)), - Box::new(on_response), - )); + let completable = MethodCompletable::new(ResponseCompletable::new(Some(Id::Number(1)), Box::new(on_response))); server.initialize(initialize_params, completable); server.endpoint.request_shutdown(); @@ -186,7 +180,7 @@ fn test_01_initialize() { assert_eq!( server.graph.borrow().graph[node1], //format!("{:?}/{}/{}", tmp_path, "shaders", "final.fsh") - tmp_path.join("shaders").join("final.fsh").to_str().unwrap().to_string() + tmp_path.join("shaders").join("final.fsh").to_str().unwrap().to_string() ); assert_eq!( server.graph.borrow().graph[node2], @@ -194,10 +188,7 @@ fn test_01_initialize() { tmp_path.join("shaders").join("common.glsl").to_str().unwrap().to_string() ); - assert_eq!( - server.graph.borrow().graph.edge_weight(edge).unwrap().line, - 2 - ); + assert_eq!(server.graph.borrow().graph.edge_weight(edge).unwrap().line, 2); } #[test] @@ -235,10 +226,7 @@ fn test_05_initialize() { } }; - let completable = MethodCompletable::new(ResponseCompletable::new( - Some(Id::Number(1)), - Box::new(on_response), - )); + let completable = MethodCompletable::new(ResponseCompletable::new(Some(Id::Number(1)), Box::new(on_response))); server.initialize(initialize_params, completable); server.endpoint.request_shutdown(); @@ -250,17 +238,40 @@ fn test_05_initialize() { let pairs: HashSet<(PathBuf, PathBuf)> = vec![ ( tmp_path.join("shaders").join("final.fsh").to_str().unwrap().to_string().into(), - tmp_path.join("shaders").join("common.glsl").to_str().unwrap().to_string().into() + tmp_path.join("shaders").join("common.glsl").to_str().unwrap().to_string().into(), ), ( tmp_path.join("shaders").join("final.fsh").to_str().unwrap().to_string().into(), - tmp_path.join("shaders").join("test").join("banana.glsl").to_str().unwrap().to_string().into() + tmp_path + .join("shaders") + .join("test") + .join("banana.glsl") + .to_str() + .unwrap() + .to_string() + .into(), ), ( - tmp_path.join("shaders").join("test").join("banana.glsl").to_str().unwrap().to_string().into(), - tmp_path.join("shaders").join("test").join("burger.glsl").to_str().unwrap().to_string().into() - ) - ].into_iter().collect(); + tmp_path + .join("shaders") + .join("test") + .join("banana.glsl") + .to_str() + .unwrap() + .to_string() + .into(), + tmp_path + .join("shaders") + .join("test") + .join("burger.glsl") + .to_str() + .unwrap() + .to_string() + .into(), + ), + ] + .into_iter() + .collect(); for edge in server.graph.borrow().graph.edge_indices() { let endpoints = server.graph.borrow().graph.edge_endpoints(edge).unwrap(); @@ -277,15 +288,7 @@ fn test_graph_two_connected_nodes() { let idx1 = graph.add_node(&PathBuf::from("sample")); let idx2 = graph.add_node(&PathBuf::from("banana")); - graph.add_edge( - idx1, - idx2, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx1, idx2, IncludePosition { line: 3, start: 0, end: 0 }); let children = graph.child_node_names(idx1); assert_eq!(children.len(), 1); @@ -330,33 +333,9 @@ fn test_collect_root_ancestors() { let idx2 = graph.add_node(&PathBuf::from("2")); let idx3 = graph.add_node(&PathBuf::from("3")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx2, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx3, - idx1, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx1, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx3, idx1, IncludePosition { line: 4, start: 0, end: 0 }); // 0 3 // |/ @@ -384,33 +363,9 @@ fn test_collect_root_ancestors() { let idx2 = graph.add_node(&PathBuf::from("2")); let idx3 = graph.add_node(&PathBuf::from("3")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx0, - idx2, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx3, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); // 0 // / \ @@ -438,33 +393,9 @@ fn test_collect_root_ancestors() { let idx2 = graph.add_node(&PathBuf::from("2")); let idx3 = graph.add_node(&PathBuf::from("3")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx2, - idx3, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx3, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx2, idx3, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); // 0 // | @@ -494,33 +425,9 @@ fn test_collect_root_ancestors() { let idx2 = graph.add_node(&PathBuf::from("2")); let idx3 = graph.add_node(&PathBuf::from("3")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx2, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx3, - IncludePosition { - line: 6, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx1, idx2, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 6, start: 0, end: 0 }); // 0 // | @@ -552,33 +459,9 @@ fn test_graph_dfs() { let idx2 = graph.add_node(&PathBuf::from("2")); let idx3 = graph.add_node(&PathBuf::from("3")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx0, - idx2, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx3, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); let dfs = dfs::Dfs::new(&graph, idx0); @@ -618,87 +501,15 @@ fn test_graph_dfs() { let idx6 = graph.add_node(&PathBuf::from("6")); let idx7 = graph.add_node(&PathBuf::from("7")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx0, - idx2, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx3, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx4, - IncludePosition { - line: 6, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx2, - idx4, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx2, - idx5, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx3, - idx6, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx4, - idx6, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx6, - idx7, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx1, idx4, IncludePosition { line: 6, start: 0, end: 0 }); + graph.add_edge(idx2, idx4, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx2, idx5, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx3, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx4, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx6, idx7, IncludePosition { line: 4, start: 0, end: 0 }); let dfs = dfs::Dfs::new(&graph, idx0); @@ -718,9 +529,7 @@ fn test_graph_dfs() { // 3 4 5 // \ / // 6 - 7 - let expected_nodes = vec![ - idx0, idx1, idx3, idx6, idx7, idx4, idx6, idx7, idx2, idx5, idx4, idx6, idx7, - ]; + let expected_nodes = vec![idx0, idx1, idx3, idx6, idx7, idx4, idx6, idx7, idx2, idx5, idx4, idx6, idx7]; assert_eq!(expected_nodes, nodes); @@ -760,96 +569,16 @@ fn test_graph_dfs_cycle() { let idx6 = graph.add_node(&PathBuf::from("6")); let idx7 = graph.add_node(&PathBuf::from("7")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx0, - idx2, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx3, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx4, - IncludePosition { - line: 6, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx2, - idx4, - IncludePosition { - line: 5, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx2, - idx5, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx3, - idx6, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx4, - idx6, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx6, - idx7, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx7, - idx4, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx1, idx4, IncludePosition { line: 6, start: 0, end: 0 }); + graph.add_edge(idx2, idx4, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx2, idx5, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx3, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx4, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx6, idx7, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx7, idx4, IncludePosition { line: 4, start: 0, end: 0 }); let mut dfs = dfs::Dfs::new(&graph, idx0); @@ -878,24 +607,8 @@ fn test_graph_dfs_cycle() { let idx0 = graph.add_node(&PathBuf::from("0")); let idx1 = graph.add_node(&PathBuf::from("1")); - graph.add_edge( - idx0, - idx1, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - graph.add_edge( - idx1, - idx0, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx1, idx0, IncludePosition { line: 2, start: 0, end: 0 }); let mut dfs = dfs::Dfs::new(&graph, idx1); @@ -912,22 +625,21 @@ fn test_generate_merge_list_01() { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/01", &mut server); server.endpoint.request_shutdown(); - let final_idx = server.graph.borrow_mut() + let final_idx = server + .graph + .borrow_mut() //.add_node(&format!("{:?}/shaders/final.fsh", tmp_path).try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("final.fsh")); - let common_idx = server.graph.borrow_mut() + let common_idx = server + .graph + .borrow_mut() //.add_node(&format!("{:?}/shaders/common.glsl", tmp_path).try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("common.glsl")); - server.graph.borrow_mut().add_edge( - final_idx, - common_idx, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); + server + .graph + .borrow_mut() + .add_edge(final_idx, common_idx, IncludePosition { line: 2, start: 0, end: 0 }); let nodes = server.get_dfs_for_node(final_idx).unwrap(); let sources = server.load_sources(&nodes).unwrap(); @@ -935,11 +647,18 @@ fn test_generate_merge_list_01() { let graph_borrow = server.graph.borrow(); let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - let merge_file = tmp_path.clone().join( "shaders").join("final.fsh.merge"); + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); - truth = truth.replacen("!!", &tmp_path.clone().join("shaders").join("common.glsl").to_str().unwrap().replace("\\", "\\\\"), 1); - truth = truth.replace("!!", &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace("\\", "\\\\")); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("common.glsl").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); + truth = truth.replace( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + ); assert_eq!(result, truth); } @@ -951,46 +670,39 @@ fn test_generate_merge_list_02() { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/02", &mut server); server.endpoint.request_shutdown(); - let final_idx = server.graph.borrow_mut() + let final_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("final.fsh")); - let test_idx = server.graph.borrow_mut() + let test_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); - let burger_idx = server.graph.borrow_mut() + let burger_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); - let sample_idx = server.graph.borrow_mut() + let sample_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); - server.graph.borrow_mut().add_edge( - final_idx, - sample_idx, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - sample_idx, - burger_idx, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - sample_idx, - test_idx, - IncludePosition { - line: 6, - start: 0, - end: 0, - }, - ); + server + .graph + .borrow_mut() + .add_edge(final_idx, sample_idx, IncludePosition { line: 2, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, burger_idx, IncludePosition { line: 4, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, test_idx, IncludePosition { line: 6, start: 0, end: 0 }); let nodes = server.get_dfs_for_node(final_idx).unwrap(); let sources = server.load_sources(&nodes).unwrap(); @@ -998,21 +710,29 @@ fn test_generate_merge_list_02() { let graph_borrow = server.graph.borrow(); let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - let merge_file = tmp_path.clone().join("shaders").join("final.fsh.merge"); + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); - for file in &[ - "sample.glsl", - "burger.glsl", - "sample.glsl", - "test.glsl", - "sample.glsl", - ] { + for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { let path = tmp_path.clone(); - truth = truth.replacen("!!", &&path.join("shaders").join("utils").join(file).to_str().unwrap().replace("\\", "\\\\"), 1); + truth = truth.replacen( + "!!", + &path + .join("shaders") + .join("utils") + .join(file) + .to_str() + .unwrap() + .replace('\\', "\\\\"), + 1, + ); } - truth = truth.replacen("!!", &&tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace("\\", "\\\\"), 1); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); assert_eq!(result, truth); } @@ -1024,46 +744,39 @@ fn test_generate_merge_list_03() { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/03", &mut server); server.endpoint.request_shutdown(); - let final_idx = server.graph.borrow_mut() + let final_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("final.fsh")); - let test_idx = server.graph.borrow_mut() + let test_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); - let burger_idx = server.graph.borrow_mut() + let burger_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); - let sample_idx = server.graph.borrow_mut() + let sample_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); - server.graph.borrow_mut().add_edge( - final_idx, - sample_idx, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - sample_idx, - burger_idx, - IncludePosition { - line: 4, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - sample_idx, - test_idx, - IncludePosition { - line: 6, - start: 0, - end: 0, - }, - ); + server + .graph + .borrow_mut() + .add_edge(final_idx, sample_idx, IncludePosition { line: 2, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, burger_idx, IncludePosition { line: 4, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, test_idx, IncludePosition { line: 6, start: 0, end: 0 }); let nodes = server.get_dfs_for_node(final_idx).unwrap(); let sources = server.load_sources(&nodes).unwrap(); @@ -1071,21 +784,29 @@ fn test_generate_merge_list_03() { let graph_borrow = server.graph.borrow(); let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - let merge_file = tmp_path.clone().join("shaders").join("final.fsh.merge"); + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); - for file in &[ - "sample.glsl", - "burger.glsl", - "sample.glsl", - "test.glsl", - "sample.glsl", - ] { + for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { let path = tmp_path.clone(); - truth = truth.replacen("!!", &&&path.join("shaders").join("utils").join(file).to_str().unwrap().replace("\\", "\\\\"), 1); + truth = truth.replacen( + "!!", + &path + .join("shaders") + .join("utils") + .join(file) + .to_str() + .unwrap() + .replace('\\', "\\\\"), + 1, + ); } - truth = truth.replacen("!!", &&&tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace("\\", "\\\\"), 1); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); assert_eq!(result, truth); } @@ -1097,58 +818,48 @@ fn test_generate_merge_list_04() { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/04", &mut server); server.endpoint.request_shutdown(); - let final_idx = server.graph.borrow_mut() + let final_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("final.fsh")); - let utilities_idx = server.graph.borrow_mut() + let utilities_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "utilities.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("utilities.glsl")); - let stuff1_idx = server.graph.borrow_mut() + let stuff1_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff1.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("stuff1.glsl")); - let stuff2_idx = server.graph.borrow_mut() + let stuff2_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff2.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("stuff2.glsl")); - let matrices_idx = server.graph.borrow_mut() + let matrices_idx = server + .graph + .borrow_mut() //.add_node(&format!("{}/shaders/lib/{}", tmp_path, "matrices.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("lib").join("matrices.glsl")); - server.graph.borrow_mut().add_edge( - final_idx, - utilities_idx, - IncludePosition { - line: 2, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - utilities_idx, - stuff1_idx, - IncludePosition { - line: 0, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - utilities_idx, - stuff2_idx, - IncludePosition { - line: 1, - start: 0, - end: 0, - }, - ); - server.graph.borrow_mut().add_edge( - final_idx, - matrices_idx, - IncludePosition { - line: 3, - start: 0, - end: 0, - }, - ); + server + .graph + .borrow_mut() + .add_edge(final_idx, utilities_idx, IncludePosition { line: 2, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(utilities_idx, stuff1_idx, IncludePosition { line: 0, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(utilities_idx, stuff2_idx, IncludePosition { line: 1, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(final_idx, matrices_idx, IncludePosition { line: 3, start: 0, end: 0 }); let nodes = server.get_dfs_for_node(final_idx).unwrap(); let sources = server.load_sources(&nodes).unwrap(); @@ -1156,7 +867,7 @@ fn test_generate_merge_list_04() { let graph_borrow = server.graph.borrow(); let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - let merge_file = tmp_path.clone().join("shaders").join("final.fsh.merge"); + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); @@ -1168,12 +879,52 @@ fn test_generate_merge_list_04() { PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), PathBuf::new().join("final.fsh").to_str().unwrap(), PathBuf::new().join("lib").join("matrices.glsl").to_str().unwrap(), - PathBuf::new().join("final.fsh").to_str().unwrap() + PathBuf::new().join("final.fsh").to_str().unwrap(), ] { let path = tmp_path.clone(); //path.f - truth = truth.replacen("!!", &path.join("shaders").join(file).to_str().unwrap().replace("\\", "\\\\"), 1); + truth = truth.replacen("!!", &path.join("shaders").join(file).to_str().unwrap().replace('\\', "\\\\"), 1); } assert_eq!(result, truth); } + +#[test] +fn test_nvidia_diagnostics() { + let mut mockgl = opengl::MockShaderValidator::new(); + mockgl.expect_vendor().returning(|| "NVIDIA".into()); + let server = new_temp_server(Some(Box::new(mockgl))); + + let output = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; + + let results = server.parse_validator_stdout( + &PathBuf::from_str("/home/noah/.minecraft/shaderpacks/test").unwrap(), + output.to_string(), + "", + ); + assert_eq!(results.len(), 1); + let first = results.into_iter().next().unwrap(); + assert_eq!( + first.0, + url::Url::from_file_path("/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh").unwrap() + ); + server.endpoint.request_shutdown(); +} + +#[test] +fn test_amd_diagnostics() { + let mut mockgl = opengl::MockShaderValidator::new(); + mockgl.expect_vendor().returning(|| "ATI Technologies".into()); + let server = new_temp_server(Some(Box::new(mockgl))); + + let output = "ERROR: 0:1: '' : syntax error: #line +ERROR: 0:10: '' : syntax error: #line +ERROR: 0:15: 'varying' : syntax error: syntax error +"; + + let results = server.parse_validator_stdout(&PathBuf::from_str("/home/test").unwrap(), output.to_string(), ""); + assert_eq!(results.len(), 1); + let first = results.into_iter().next().unwrap(); + assert_eq!(first.1.len(), 3); + server.endpoint.request_shutdown(); +} diff --git a/server/src/url_norm.rs b/server/src/url_norm.rs index adc0993..67fe813 100644 --- a/server/src/url_norm.rs +++ b/server/src/url_norm.rs @@ -1,27 +1,38 @@ use std::path::PathBuf; +use slog_scope::trace; +use anyhow::Result; use path_slash::PathBufExt; use url::Url; -use anyhow::Result; pub trait FromUrl { fn from_url(u: Url) -> Self; } pub trait FromJson { - fn from_json(v: &serde_json::value::Value) -> Result where Self: Sized; + fn from_json(v: &serde_json::value::Value) -> Result + where + Self: Sized; } impl FromUrl for PathBuf { #[cfg(target_family = "windows")] fn from_url(u: Url) -> Self { - let path = percent_encoding::percent_decode_str(u.path().strip_prefix("/").unwrap()).decode_utf8().unwrap(); + let path = percent_encoding::percent_decode_str(u.path().strip_prefix('/').unwrap()) + .decode_utf8() + .unwrap(); + + trace!("converted win path from url"; "old" => u.as_str(), "new" => path.to_string()); + PathBuf::from_slash(path) } #[cfg(target_family = "unix")] fn from_url(u: Url) -> Self { let path = percent_encoding::percent_decode_str(u.path()).decode_utf8().unwrap(); + + trace!("converted unix path from url"; "old" => u.as_str(), "new" => path.to_string()); + PathBuf::from_slash(path) } } @@ -29,27 +40,34 @@ impl FromUrl for PathBuf { impl FromJson for PathBuf { #[cfg(target_family = "windows")] fn from_json(v: &serde_json::value::Value) -> Result - where Self: Sized { + where + Self: Sized, + { if !v.is_string() { return Err(anyhow::format_err!("cannot convert {:?} to PathBuf", v)); } let path = v.to_string(); - let path = percent_encoding::percent_decode_str( - path.trim_start_matches('"').trim_end_matches('"').strip_prefix("/").unwrap() - ).decode_utf8()?; + let path = percent_encoding::percent_decode_str(path.trim_start_matches('"').trim_end_matches('"').strip_prefix('/').unwrap()) + .decode_utf8()?; + + trace!("converted win path from json"; "old" => v.to_string(), "new" => path.to_string()); + Ok(PathBuf::from_slash(path)) } #[cfg(target_family = "unix")] fn from_json(v: &serde_json::value::Value) -> Result - where Self: Sized { + where + Self: Sized, + { if !v.is_string() { return Err(anyhow::format_err!("cannot convert {:?} to PathBuf", v)); } let path = v.to_string(); - let path = percent_encoding::percent_decode_str( - path.trim_start_matches('"').trim_end_matches('"') - ).decode_utf8()?; + let path = percent_encoding::percent_decode_str(path.trim_start_matches('"').trim_end_matches('"')).decode_utf8()?; + + trace!("converted unix path from json"; "old" => v.to_string(), "new" => path.to_string()); + Ok(PathBuf::from_slash(path)) } -} \ No newline at end of file +} From 9a9ed21f13aeb62b7ab9d0e5f51e7dff66b2abc9 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 18 Mar 2022 19:11:48 +0000 Subject: [PATCH 24/56] allow configurable log level --- package.json | 6 ++++++ server/src/configuration.rs | 12 ++++++++++++ server/src/main.rs | 15 +++++++++++++++ 3 files changed, 33 insertions(+) create mode 100644 server/src/configuration.rs diff --git a/package.json b/package.json index abe839c..aba6e0a 100644 --- a/package.json +++ b/package.json @@ -64,6 +64,12 @@ "type": "boolean", "default": false, "description": "[DEBUG] Enable to skip bootstrapping the language server binary from Github. Set this to use a manually provided language server binary." + }, + "mcglsl.logLevel": { + "type": "string", + "default": "info", + "enum": ["trace", "debug", "info", "warn", "error"], + "description": "Change the log level of the language server. This change happens live and does not require a restart." } } } diff --git a/server/src/configuration.rs b/server/src/configuration.rs new file mode 100644 index 0000000..779b235 --- /dev/null +++ b/server/src/configuration.rs @@ -0,0 +1,12 @@ +use std::str::FromStr; + +use slog::Level; +use slog_scope::error; + + +pub fn handle_log_level_change(log_level: String, callback: F) { + match Level::from_str(log_level.as_str()) { + Ok(level) => callback(level), + Err(_) => error!("got unexpected log level from config"; "level" => log_level), + }; +} \ No newline at end of file diff --git a/server/src/main.rs b/server/src/main.rs index 2aa7c03..bea1c19 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -40,6 +40,7 @@ use lazy_static::lazy_static; mod commands; mod consts; mod dfs; +mod configuration; mod graph; mod lsp_ext; mod merge_views; @@ -604,6 +605,20 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn workspace_change_configuration(&mut self, params: DidChangeConfigurationParams) { logging::slog_with_trace_id(|| { + #[derive(Deserialize)] + struct Configuration { + #[serde(alias ="logLevel")] + log_level: String + } + + let config: Configuration = from_value(params.settings.as_object().unwrap().get("mcglsl").unwrap().to_owned()).unwrap(); + + info!("got updated configuration"; "config" => params.settings.as_object().unwrap().get("mcglsl").unwrap().to_string()); + + configuration::handle_log_level_change(config.log_level, |level| { + self._log_guard = None; // set to None so Drop is invoked + self._log_guard = Some(logging::set_logger_with_level(level)); + }) }); } From e001b4a8b1d4275804a8f240d842752d587d38e2 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 18 Mar 2022 19:22:17 +0000 Subject: [PATCH 25/56] fixup client imports --- client/src/lspClient.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/lspClient.ts b/client/src/lspClient.ts index 57cc6aa..7751cfa 100644 --- a/client/src/lspClient.ts +++ b/client/src/lspClient.ts @@ -1,5 +1,5 @@ import { ConfigurationTarget, workspace } from 'vscode' -import * as lsp from 'vscode-languageclient' +import * as lsp from 'vscode-languageclient/node' import { Extension } from './extension' import { log, lspOutputChannel } from './log' import { ConfigUpdateParams, statusMethod, StatusParams, updateConfigMethod } from './lspExt' From 86100aa0082eaac06e5ee991af148039a618b7f7 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 19 Mar 2022 20:26:30 +0000 Subject: [PATCH 26/56] chore: reorganizing lsp commands --- client/package-lock.json | 165 ++++++------------ client/package.json | 2 +- client/src/extension.ts | 4 +- server/src/commands/graph_dot.rs | 52 ++++++ .../merged_includes.rs} | 60 +------ server/src/commands/mod.rs | 31 ++++ server/src/main.rs | 32 ++-- server/src/opengl.rs | 2 - server/src/test.rs | 2 +- 9 files changed, 157 insertions(+), 193 deletions(-) create mode 100644 server/src/commands/graph_dot.rs rename server/src/{commands.rs => commands/merged_includes.rs} (63%) create mode 100644 server/src/commands/mod.rs diff --git a/client/package-lock.json b/client/package-lock.json index 061ed07..2a9f363 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -9,7 +9,7 @@ "@rollup/plugin-json": "^4.1.0", "adm-zip": "^0.5.9", "encoding": "^0.1.13", - "node-fetch": "^3.2.3", + "node-fetch": "^2.6.7", "vscode-languageclient": "^7.0.0" }, "devDependencies": { @@ -202,14 +202,6 @@ "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" }, - "node_modules/data-uri-to-buffer": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.0.tgz", - "integrity": "sha512-Vr3mLBA8qWmcuschSLAOogKgQ/Jwxulv3RNE4FXnYWRGujzrRWQI4m12fQqRkwX06C0KanhLr4hK+GydchZsaA==", - "engines": { - "node": ">= 12" - } - }, "node_modules/deepmerge": { "version": "4.2.2", "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", @@ -242,28 +234,6 @@ "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", "dev": true }, - "node_modules/fetch-blob": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.1.4.tgz", - "integrity": "sha512-Eq5Xv5+VlSrYWEqKrusxY1C3Hm/hjeAsCGVG3ft7pZahlUAChpGZT/Ms1WmSLnEAisEXszjzu/s+ce6HZB2VHA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/jimmywarting" - }, - { - "type": "paypal", - "url": "https://paypal.me/jimmywarting" - } - ], - "dependencies": { - "node-domexception": "^1.0.0", - "web-streams-polyfill": "^3.0.3" - }, - "engines": { - "node": "^12.20 || >= 14.13" - } - }, "node_modules/form-data": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/form-data/-/form-data-3.0.1.tgz", @@ -278,17 +248,6 @@ "node": ">= 6" } }, - "node_modules/formdata-polyfill": { - "version": "4.0.10", - "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", - "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", - "dependencies": { - "fetch-blob": "^3.1.2" - }, - "engines": { - "node": ">=12.20.0" - } - }, "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -452,39 +411,23 @@ "node": "*" } }, - "node_modules/node-domexception": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", - "integrity": "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/jimmywarting" - }, - { - "type": "github", - "url": "https://paypal.me/jimmywarting" - } - ], - "engines": { - "node": ">=10.5.0" - } - }, "node_modules/node-fetch": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.2.3.tgz", - "integrity": "sha512-AXP18u4pidSZ1xYXRDPY/8jdv3RAozIt/WLNR/MBGZAz+xjtlr90RvCnsvHQRiXyWliZF/CpytExp32UU67/SA==", + "version": "2.6.7", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", + "integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==", "dependencies": { - "data-uri-to-buffer": "^4.0.0", - "fetch-blob": "^3.1.4", - "formdata-polyfill": "^4.0.10" + "whatwg-url": "^5.0.0" }, "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + "node": "4.x || >=6.0.0" }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/node-fetch" + "peerDependencies": { + "encoding": "^0.1.0" + }, + "peerDependenciesMeta": { + "encoding": { + "optional": true + } } }, "node_modules/once": { @@ -574,6 +517,11 @@ "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==", "dev": true }, + "node_modules/tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=" + }, "node_modules/vscode-jsonrpc": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-6.0.0.tgz", @@ -609,12 +557,18 @@ "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.16.0.tgz", "integrity": "sha512-k8luDIWJWyenLc5ToFQQMaSrqCHiLwyKPHKPQZ5zz21vM+vIVUSvsRpcbiECH4WR88K2XZqc4ScRcZ7nk/jbeA==" }, - "node_modules/web-streams-polyfill": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.2.0.tgz", - "integrity": "sha512-EqPmREeOzttaLRm5HS7io98goBgZ7IVz79aDvqjD0kYXLtFZTc0T/U6wHTPKyIjb+MdN7DFIIX6hgdBEpWmfPA==", - "engines": { - "node": ">= 8" + "node_modules/webidl-conversions": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", + "integrity": "sha1-JFNCdeKnvGvnvIZhHMFq4KVlSHE=" + }, + "node_modules/whatwg-url": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", + "integrity": "sha1-lmRU6HZUYuN2RNNib2dCzotwll0=", + "dependencies": { + "tr46": "~0.0.3", + "webidl-conversions": "^3.0.0" } }, "node_modules/wrappy": { @@ -780,11 +734,6 @@ "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" }, - "data-uri-to-buffer": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.0.tgz", - "integrity": "sha512-Vr3mLBA8qWmcuschSLAOogKgQ/Jwxulv3RNE4FXnYWRGujzrRWQI4m12fQqRkwX06C0KanhLr4hK+GydchZsaA==" - }, "deepmerge": { "version": "4.2.2", "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.2.2.tgz", @@ -811,15 +760,6 @@ "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", "dev": true }, - "fetch-blob": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.1.4.tgz", - "integrity": "sha512-Eq5Xv5+VlSrYWEqKrusxY1C3Hm/hjeAsCGVG3ft7pZahlUAChpGZT/Ms1WmSLnEAisEXszjzu/s+ce6HZB2VHA==", - "requires": { - "node-domexception": "^1.0.0", - "web-streams-polyfill": "^3.0.3" - } - }, "form-data": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/form-data/-/form-data-3.0.1.tgz", @@ -831,14 +771,6 @@ "mime-types": "^2.1.12" } }, - "formdata-polyfill": { - "version": "4.0.10", - "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", - "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", - "requires": { - "fetch-blob": "^3.1.2" - } - }, "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -968,19 +900,12 @@ "brace-expansion": "^1.1.7" } }, - "node-domexception": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", - "integrity": "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==" - }, "node-fetch": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.2.3.tgz", - "integrity": "sha512-AXP18u4pidSZ1xYXRDPY/8jdv3RAozIt/WLNR/MBGZAz+xjtlr90RvCnsvHQRiXyWliZF/CpytExp32UU67/SA==", + "version": "2.6.7", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", + "integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==", "requires": { - "data-uri-to-buffer": "^4.0.0", - "fetch-blob": "^3.1.4", - "formdata-polyfill": "^4.0.10" + "whatwg-url": "^5.0.0" } }, "once": { @@ -1046,6 +971,11 @@ "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==", "dev": true }, + "tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=" + }, "vscode-jsonrpc": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-6.0.0.tgz", @@ -1075,10 +1005,19 @@ "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.16.0.tgz", "integrity": "sha512-k8luDIWJWyenLc5ToFQQMaSrqCHiLwyKPHKPQZ5zz21vM+vIVUSvsRpcbiECH4WR88K2XZqc4ScRcZ7nk/jbeA==" }, - "web-streams-polyfill": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.2.0.tgz", - "integrity": "sha512-EqPmREeOzttaLRm5HS7io98goBgZ7IVz79aDvqjD0kYXLtFZTc0T/U6wHTPKyIjb+MdN7DFIIX6hgdBEpWmfPA==" + "webidl-conversions": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", + "integrity": "sha1-JFNCdeKnvGvnvIZhHMFq4KVlSHE=" + }, + "whatwg-url": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", + "integrity": "sha1-lmRU6HZUYuN2RNNib2dCzotwll0=", + "requires": { + "tr46": "~0.0.3", + "webidl-conversions": "^3.0.0" + } }, "wrappy": { "version": "1.0.2", diff --git a/client/package.json b/client/package.json index 3d8a93e..e40c901 100644 --- a/client/package.json +++ b/client/package.json @@ -8,7 +8,7 @@ "@rollup/plugin-json": "^4.1.0", "adm-zip": "^0.5.9", "encoding": "^0.1.13", - "node-fetch": "^3.2.3", + "node-fetch": "^2.6.7", "vscode-languageclient": "^7.0.0" }, "devDependencies": { diff --git a/client/src/extension.ts b/client/src/extension.ts index 9845694..1742c08 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -1,6 +1,6 @@ import { mkdirSync, promises as fs } from 'fs' import * as vscode from 'vscode' -import * as lsp from 'vscode-languageclient' +import * as lsp from 'vscode-languageclient/node' import * as commands from './commands' import { log } from './log' import { LanguageClient } from './lspClient' @@ -54,7 +54,7 @@ export class Extension { const lspBinary = process.env['MCSHADER_DEBUG'] ? this.context.asAbsolutePath(path.join('server', 'target', 'debug', 'mcshader-lsp')) + (process.platform === 'win32' ? '.exe' : '') : - path.join(this.context.globalStoragePath, 'mcshader-lsp') + path.join(this.context.globalStorageUri.fsPath, 'mcshader-lsp') const filewatcherGlob = this.fileAssociationsToGlob(this.getGLSLFileAssociations()) diff --git a/server/src/commands/graph_dot.rs b/server/src/commands/graph_dot.rs new file mode 100644 index 0000000..dac35e7 --- /dev/null +++ b/server/src/commands/graph_dot.rs @@ -0,0 +1,52 @@ +use std::cell::RefCell; +use std::fs::OpenOptions; +use std::io::prelude::*; +use std::path::Path; +use std::rc::Rc; + +use petgraph::dot::Config; +use serde_json::Value; + +use petgraph::dot; + +use anyhow::{format_err, Result}; +use slog_scope::info; + +use crate::graph::CachedStableGraph; + +use super::Invokeable; + +pub struct GraphDotCommand { + pub graph: Rc>, +} + +impl Invokeable for GraphDotCommand { + fn run_command(&self, root: &Path, _: &[Value]) -> Result { + let filepath = root.join("graph.dot"); + + info!("generating dot file"; "path" => filepath.as_os_str().to_str()); + + let mut file = OpenOptions::new().truncate(true).write(true).create(true).open(filepath).unwrap(); + + let mut write_data_closure = || -> Result<(), std::io::Error> { + let graph = self.graph.as_ref(); + + file.seek(std::io::SeekFrom::Start(0))?; + file.write_all("digraph {\n\tgraph [splines=ortho]\n\tnode [shape=box]\n".as_bytes())?; + file.write_all( + dot::Dot::with_config(&graph.borrow().graph, &[Config::GraphContentOnly]) + .to_string() + .as_bytes(), + )?; + file.write_all("\n}".as_bytes())?; + file.flush()?; + file.seek(std::io::SeekFrom::Start(0))?; + Ok(()) + }; + + match write_data_closure() { + Err(err) => Err(format_err!("error generating graphviz data: {}", err)), + _ => Ok(Value::Null), + } + } +} diff --git a/server/src/commands.rs b/server/src/commands/merged_includes.rs similarity index 63% rename from server/src/commands.rs rename to server/src/commands/merged_includes.rs index 3224c9e..94dcf77 100644 --- a/server/src/commands.rs +++ b/server/src/commands/merged_includes.rs @@ -1,78 +1,22 @@ use std::cell::RefCell; -use std::fs::OpenOptions; -use std::io::prelude::*; use std::rc::Rc; use std::{ collections::HashMap, path::{Path, PathBuf}, }; -use petgraph::dot::Config; use serde_json::Value; -use petgraph::{dot, graph::NodeIndex}; +use petgraph::graph::NodeIndex; use anyhow::{format_err, Result}; -use slog_scope::info; use std::fs; use crate::dfs; use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJson}; -pub struct CustomCommandProvider { - commands: HashMap>, -} - -impl CustomCommandProvider { - pub fn new(commands: Vec<(&str, Box)>) -> CustomCommandProvider { - CustomCommandProvider { - commands: commands.into_iter().map(|tup| (tup.0.into(), tup.1)).collect(), - } - } - - pub fn execute(&self, command: &str, args: &[Value], root_path: &Path) -> Result { - if self.commands.contains_key(command) { - return self.commands.get(command).unwrap().run_command(root_path, args); - } - Err(format_err!("command doesn't exist")) - } -} - -pub trait Invokeable { - fn run_command(&self, root: &Path, arguments: &[Value]) -> Result; -} - -pub struct GraphDotCommand { - pub graph: Rc>, -} - -impl Invokeable for GraphDotCommand { - fn run_command(&self, root: &Path, _: &[Value]) -> Result { - let filepath = root.join("graph.dot"); - - info!("generating dot file"; "path" => filepath.as_os_str().to_str()); - - let mut file = OpenOptions::new().truncate(true).write(true).create(true).open(filepath).unwrap(); - - let mut write_data_closure = || -> Result<(), std::io::Error> { - let graph = self.graph.as_ref(); - - file.seek(std::io::SeekFrom::Start(0))?; - file.write_all("digraph {\n\tgraph [splines=ortho]\n\tnode [shape=box]\n".as_bytes())?; - file.write_all(dot::Dot::with_config(&graph.borrow().graph, &[Config::GraphContentOnly]).to_string().as_bytes())?; - file.write_all("\n}".as_bytes())?; - file.flush()?; - file.seek(std::io::SeekFrom::Start(0))?; - Ok(()) - }; - - match write_data_closure() { - Err(err) => Err(format_err!("error generating graphviz data: {}", err)), - _ => Ok(Value::Null), - } - } -} +use super::Invokeable; pub struct VirtualMergedDocument { pub graph: Rc>, diff --git a/server/src/commands/mod.rs b/server/src/commands/mod.rs new file mode 100644 index 0000000..f12ed9b --- /dev/null +++ b/server/src/commands/mod.rs @@ -0,0 +1,31 @@ +use std::{collections::HashMap, path::Path}; + +use serde_json::Value; + +use anyhow::{format_err, Result}; + +pub mod graph_dot; +pub mod merged_includes; + +pub struct CustomCommandProvider { + commands: HashMap>, +} + +impl CustomCommandProvider { + pub fn new(commands: Vec<(&str, Box)>) -> CustomCommandProvider { + CustomCommandProvider { + commands: commands.into_iter().map(|tup| (tup.0.into(), tup.1)).collect(), + } + } + + pub fn execute(&self, command: &str, args: &[Value], root_path: &Path) -> Result { + if self.commands.contains_key(command) { + return self.commands.get(command).unwrap().run_command(root_path, args); + } + Err(format_err!("command doesn't exist")) + } +} + +pub trait Invokeable { + fn run_command(&self, root: &Path, arguments: &[Value]) -> Result; +} diff --git a/server/src/main.rs b/server/src/main.rs index bea1c19..4ccecc0 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -5,7 +5,7 @@ use rust_lsp::lsp_types::{notification::*, *}; use petgraph::stable_graph::NodeIndex; use serde::Deserialize; -use serde_json::{Value, from_value}; +use serde_json::{from_value, Value}; use url_norm::FromUrl; @@ -38,14 +38,14 @@ use regex::Regex; use lazy_static::lazy_static; mod commands; +mod configuration; mod consts; mod dfs; -mod configuration; mod graph; +mod logging; mod lsp_ext; mod merge_views; mod opengl; -mod logging; mod url_norm; #[cfg(test)] @@ -61,7 +61,6 @@ lazy_static! { fn main() { let guard = logging::set_logger_with_level(Level::Info); - let stdin = stdin(); let endpoint_output = LSPEndpoint::create_lsp_output_with_output_stream(stdout); let cache_graph = graph::CachedStableGraph::new(); @@ -72,25 +71,25 @@ fn main() { root: "".into(), command_provider: None, opengl_context: Rc::new(opengl::OpenGlContext::new()), - _log_guard: Some(guard), + log_guard: Some(guard), }; langserver.command_provider = Some(commands::CustomCommandProvider::new(vec![ ( "graphDot", - Box::new(commands::GraphDotCommand { - graph: Rc::clone(&langserver.graph), + Box::new(commands::graph_dot::GraphDotCommand { + graph: langserver.graph.clone(), }), ), ( "virtualMerge", - Box::new(commands::VirtualMergedDocument { - graph: Rc::clone(&langserver.graph), + Box::new(commands::merged_includes::VirtualMergedDocument { + graph: langserver.graph.clone(), }), ), ])); - LSPEndpoint::run_server_from_input(&mut stdin.lock(), endpoint_output, langserver); + LSPEndpoint::run_server_from_input(&mut stdin().lock(), endpoint_output, langserver); } struct MinecraftShaderLanguageServer { @@ -99,7 +98,7 @@ struct MinecraftShaderLanguageServer { root: PathBuf, command_provider: Option, opengl_context: Rc, - _log_guard: Option, + log_guard: Option, } #[derive(Clone, PartialEq, Eq, Hash)] @@ -607,17 +606,17 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { logging::slog_with_trace_id(|| { #[derive(Deserialize)] struct Configuration { - #[serde(alias ="logLevel")] - log_level: String + #[serde(alias = "logLevel")] + log_level: String, } let config: Configuration = from_value(params.settings.as_object().unwrap().get("mcglsl").unwrap().to_owned()).unwrap(); info!("got updated configuration"; "config" => params.settings.as_object().unwrap().get("mcglsl").unwrap().to_string()); - + configuration::handle_log_level_change(config.log_level, |level| { - self._log_guard = None; // set to None so Drop is invoked - self._log_guard = Some(logging::set_logger_with_level(level)); + self.log_guard = None; // set to None so Drop is invoked + self.log_guard = Some(logging::set_logger_with_level(level)); }) }); } @@ -629,6 +628,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { if !path.starts_with(&self.root) { return; } + if self.graph.borrow_mut().find_node(&path) == None { self.add_file_and_includes_to_graph(&path); } diff --git a/server/src/opengl.rs b/server/src/opengl.rs index d86f4d3..4c9b605 100644 --- a/server/src/opengl.rs +++ b/server/src/opengl.rs @@ -103,6 +103,4 @@ impl ShaderValidator for OpenGlContext { result } - - } } diff --git a/server/src/test.rs b/server/src/test.rs index 67b883b..55b5f14 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -49,7 +49,7 @@ fn new_temp_server(opengl_context: Option>) -> root: "".into(), command_provider: None, opengl_context: context.into(), - _log_guard: Some(guard), + log_guard: Some(guard), } } From d3c0869288e0e36319acc4de48ad734dcc48ca7b Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 19 Mar 2022 22:58:01 +0000 Subject: [PATCH 27/56] =?UTF-8?q?tree-sitter=20fun=20=F0=9F=91=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- client/src/commands.ts | 61 ++++++++++++++++++-- client/src/extension.ts | 1 + package.json | 5 ++ server/Cargo.lock | 22 ++++++++ server/Cargo.toml | 2 + server/src/commands/mod.rs | 5 ++ server/src/commands/parse_tree.rs | 94 +++++++++++++++++++++++++++++++ server/src/main.rs | 12 ++++ server/src/test.rs | 1 + 9 files changed, 198 insertions(+), 5 deletions(-) create mode 100644 server/src/commands/parse_tree.rs diff --git a/client/src/commands.ts b/client/src/commands.ts index 8b90f29..d26c25f 100644 --- a/client/src/commands.ts +++ b/client/src/commands.ts @@ -1,3 +1,4 @@ +import path = require('path') import * as vscode from 'vscode' import * as lsp from 'vscode-languageclient' import { Extension } from './extension' @@ -30,7 +31,7 @@ export function virtualMergedDocument(e: Extension): Command { command: 'virtualMerge', arguments: [path] }) - } catch(e) {} + } catch (e) { } return content } @@ -40,17 +41,67 @@ export function virtualMergedDocument(e: Extension): Command { onDidChange = this.onDidChangeEmitter.event provideTextDocumentContent(uri: vscode.Uri, __: vscode.CancellationToken): vscode.ProviderResult { - return getVirtualDocument(uri.path) + return getVirtualDocument(uri.path.replace('.flattened' + path.extname(uri.path), path.extname(uri.path))) } } e.context.subscriptions.push(vscode.workspace.registerTextDocumentContentProvider('mcglsl', docProvider)) return async () => { - const uri = vscode.window.activeTextEditor.document.uri - const path = vscode.Uri.parse('mcglsl:' + uri.path) + if (vscode.window.activeTextEditor.document.languageId != 'glsl') return + + const uri = vscode.window.activeTextEditor.document.uri.path + .substring(0, vscode.window.activeTextEditor.document.uri.path.lastIndexOf('.')) + + '.flattened.' + + vscode.window.activeTextEditor.document.uri.path + .slice(vscode.window.activeTextEditor.document.uri.path.lastIndexOf('.') + 1) + const path = vscode.Uri.parse(`mcglsl:${uri}`) + const doc = await vscode.workspace.openTextDocument(path) docProvider.onDidChangeEmitter.fire(path) - await vscode.window.showTextDocument(doc, {preview: true}) + await vscode.window.showTextDocument(doc, { + viewColumn: vscode.ViewColumn.Two, + preview: true + }) + } +} + +export function parseTree(e: Extension): Command { + const getVirtualDocument = async (path: string): Promise => { + let content: string = '' + try { + content = await e.lspClient.sendRequest(lsp.ExecuteCommandRequest.type.method, { + command: 'parseTree', + arguments: [path] + }) + } catch (e) { } + + return content + } + + const docProvider = new class implements vscode.TextDocumentContentProvider { + onDidChangeEmitter = new vscode.EventEmitter() + onDidChange = this.onDidChangeEmitter.event + + provideTextDocumentContent(uri: vscode.Uri, __: vscode.CancellationToken): vscode.ProviderResult { + if (uri.path.includes('.flattened.')) return '' + return getVirtualDocument(uri.path.substring(0, uri.path.lastIndexOf('.'))) + } + } + + e.context.subscriptions.push(vscode.workspace.registerTextDocumentContentProvider('mcglsl', docProvider)) + + return async () => { + if (vscode.window.activeTextEditor.document.languageId != 'glsl') return + + const uri = vscode.window.activeTextEditor.document.uri + const path = vscode.Uri.parse(`mcglsl:${uri.path}.ast`) + + const doc = await vscode.workspace.openTextDocument(path) + docProvider.onDidChangeEmitter.fire(path) + await vscode.window.showTextDocument(doc, { + viewColumn: vscode.ViewColumn.Two, + preview: true + }) } } \ No newline at end of file diff --git a/client/src/extension.ts b/client/src/extension.ts index 1742c08..b6219ac 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -48,6 +48,7 @@ export class Extension { this.registerCommand('graphDot', commands.generateGraphDot) this.registerCommand('restart', commands.restartExtension) this.registerCommand('virtualMerge', commands.virtualMergedDocument) + this.registerCommand('parseTree', commands.parseTree) log.info('starting language server...') diff --git a/package.json b/package.json index aba6e0a..b54c790 100644 --- a/package.json +++ b/package.json @@ -41,6 +41,11 @@ "command": "mcglsl.virtualMerge", "title": "Show flattened file", "category": "Minecraft Shader" + }, + { + "command": "mcglsl.parseTree", + "title": "Show parse tree for file", + "category": "Minecraft Shader" } ], "languages": [ diff --git a/server/Cargo.lock b/server/Cargo.lock index dcd1dfb..33edc21 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -765,6 +765,8 @@ dependencies = [ "slog-term", "tempdir", "thiserror", + "tree-sitter", + "tree-sitter-glsl", "url", "walkdir", ] @@ -1631,6 +1633,26 @@ dependencies = [ "serde", ] +[[package]] +name = "tree-sitter" +version = "0.20.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09b3b781640108d29892e8b9684642d2cda5ea05951fd58f0fea1db9edeb9b71" +dependencies = [ + "cc", + "regex", +] + +[[package]] +name = "tree-sitter-glsl" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d20c93432c782c4f66618ffb06669870ac6231a86b1777813a6c97148f1f0fb" +dependencies = [ + "cc", + "tree-sitter", +] + [[package]] name = "treeline" version = "0.1.0" diff --git a/server/Cargo.toml b/server/Cargo.toml index 79d930e..1e02ff5 100644 --- a/server/Cargo.toml +++ b/server/Cargo.toml @@ -30,6 +30,8 @@ slog-atomic = "3.1" once_cell = "1.7" rand = "0.8" arc-swap = "1.5.0" +tree-sitter = "0.20.6" +tree-sitter-glsl = "0.1.2" [dev-dependencies] tempdir = "0.3" diff --git a/server/src/commands/mod.rs b/server/src/commands/mod.rs index f12ed9b..0bb17f1 100644 --- a/server/src/commands/mod.rs +++ b/server/src/commands/mod.rs @@ -3,9 +3,11 @@ use std::{collections::HashMap, path::Path}; use serde_json::Value; use anyhow::{format_err, Result}; +use slog_scope::info; pub mod graph_dot; pub mod merged_includes; +pub mod parse_tree; pub struct CustomCommandProvider { commands: HashMap>, @@ -20,6 +22,9 @@ impl CustomCommandProvider { pub fn execute(&self, command: &str, args: &[Value], root_path: &Path) -> Result { if self.commands.contains_key(command) { + info!("running command"; + "command" => command, + "args" => format!("[{}]", args.iter().map(|v| serde_json::to_string(v).unwrap()).collect::>().join(", "))); return self.commands.get(command).unwrap().run_command(root_path, args); } Err(format_err!("command doesn't exist")) diff --git a/server/src/commands/parse_tree.rs b/server/src/commands/parse_tree.rs new file mode 100644 index 0000000..fb3d9e7 --- /dev/null +++ b/server/src/commands/parse_tree.rs @@ -0,0 +1,94 @@ +use std::{ + cell::RefCell, + fs, + path::{Path, PathBuf}, + rc::Rc, +}; + +use anyhow::{format_err, Result}; +use serde_json::Value; +use slog_scope::warn; +use tree_sitter::{Parser, TreeCursor}; + +use crate::url_norm::FromJson; + +use super::Invokeable; + +pub struct TreeSitterSExpr { + pub tree_sitter: Rc>, +} + +impl Invokeable for TreeSitterSExpr { + fn run_command(&self, _: &Path, arguments: &[Value]) -> Result { + let path = PathBuf::from_json(arguments.get(0).unwrap())?; + + warn!("parsing"; "path" => path.to_str().unwrap().to_string()); + + let source = fs::read_to_string(path)?; + + let tree = match self.tree_sitter.borrow_mut().parse(source, None) { + Some(tree) => tree, + None => return Err(format_err!("tree-sitter parsing resulted in no parse tree")), + }; + + let mut cursor = tree.walk(); + + let rendered = render_parse_tree(&mut cursor); + + Ok(serde_json::value::Value::String(rendered)) + } +} + +fn render_parse_tree(cursor: &mut TreeCursor) -> String { + let mut string = String::new(); + + let mut indent = 0; + let mut visited_children = false; + + loop { + let node = cursor.node(); + + let display_name = if node.is_missing() { + format!("MISSING {}", node.kind()) + } else if node.is_named() { + node.kind().to_string() + } else { + "".to_string() + }; + + if visited_children { + if cursor.goto_next_sibling() { + visited_children = false; + } else if cursor.goto_parent() { + visited_children = true; + indent -= 1; + } else { + break; + } + } else { + if !display_name.is_empty() { + let start = node.start_position(); + let end = node.end_position(); + + let field_name = match cursor.field_name() { + Some(name) => name.to_string() + ": ", + None => "".to_string(), + }; + + string += (" ".repeat(indent) + + format!("{}{} [{}, {}] - [{}, {}]\n", field_name, display_name, start.row, start.column, end.row, end.column) + .trim_start()) + .as_str(); + } + + if cursor.goto_first_child() { + visited_children = false; + indent += 1; + } else { + visited_children = true; + } + } + } + + string +} diff --git a/server/src/main.rs b/server/src/main.rs index 4ccecc0..f0d7032 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -7,6 +7,7 @@ use petgraph::stable_graph::NodeIndex; use serde::Deserialize; use serde_json::{from_value, Value}; +use tree_sitter::Parser; use url_norm::FromUrl; use walkdir::WalkDir; @@ -65,12 +66,16 @@ fn main() { let cache_graph = graph::CachedStableGraph::new(); + let mut parser = Parser::new(); + parser.set_language(tree_sitter_glsl::language()).unwrap(); + let mut langserver = MinecraftShaderLanguageServer { endpoint: endpoint_output.clone(), graph: Rc::new(RefCell::new(cache_graph)), root: "".into(), command_provider: None, opengl_context: Rc::new(opengl::OpenGlContext::new()), + tree_sitter: Rc::new(RefCell::new(parser)), log_guard: Some(guard), }; @@ -87,6 +92,12 @@ fn main() { graph: langserver.graph.clone(), }), ), + ( + "parseTree", + Box::new(commands::parse_tree::TreeSitterSExpr { + tree_sitter: langserver.tree_sitter.clone(), + }), + ), ])); LSPEndpoint::run_server_from_input(&mut stdin().lock(), endpoint_output, langserver); @@ -98,6 +109,7 @@ struct MinecraftShaderLanguageServer { root: PathBuf, command_provider: Option, opengl_context: Rc, + tree_sitter: Rc>, log_guard: Option, } diff --git a/server/src/test.rs b/server/src/test.rs index 55b5f14..53f6598 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -50,6 +50,7 @@ fn new_temp_server(opengl_context: Option>) -> command_provider: None, opengl_context: context.into(), log_guard: Some(guard), + tree_sitter: Rc::new(RefCell::new(Parser::new())), } } From f8dd31ca81a1ee27710370dc514dd38656d47411 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 19 Mar 2022 23:27:33 +0000 Subject: [PATCH 28/56] extract out diagnostics parser. pls submit AMD lint output in github issues --- server/src/diagnostics_parser.rs | 110 +++++++++++++++++++++++++++++++ server/src/main.rs | 78 +--------------------- server/src/opengl.rs | 5 ++ server/src/test.rs | 15 +++-- 4 files changed, 128 insertions(+), 80 deletions(-) create mode 100644 server/src/diagnostics_parser.rs diff --git a/server/src/diagnostics_parser.rs b/server/src/diagnostics_parser.rs new file mode 100644 index 0000000..bc3b965 --- /dev/null +++ b/server/src/diagnostics_parser.rs @@ -0,0 +1,110 @@ +use std::{collections::HashMap, path::Path}; + +use once_cell::sync::OnceCell; + +use regex::Regex; +use rust_lsp::lsp_types::{Diagnostic, DiagnosticSeverity, Position, Range}; +use url::Url; + +use crate::{consts, opengl}; + +static RE_DIAGNOSTIC: OnceCell = OnceCell::new(); +fn diagnostics_regex(vendor: &T) -> &'static Regex +where + T: opengl::ShaderValidator + ?Sized, +{ + RE_DIAGNOSTIC.get_or_init(|| match vendor.vendor().as_str() { + "NVIDIA" => { + Regex::new(r#"^(?P[^?<>*|"]+)\((?P\d+)\) : (?Perror|warning) [A-C]\d+: (?P.+)"#).unwrap() + } + _ => { + Regex::new(r#"^(?PERROR|WARNING): (?P[^?<>*|"\n]+):(?P\d+): '[a-z]*' : (?P.+)$"#).unwrap() + } + }) +} + +static LINE_NUM_OFFSET: OnceCell = OnceCell::new(); +fn line_number_offset(vendor: &T) -> &'static u32 +where + T: opengl::ShaderValidator + ?Sized, +{ + LINE_NUM_OFFSET.get_or_init(|| match vendor.vendor().as_str() { + "ATI Technologies" => 0, + _ => 2, + }) +} + +pub fn parse_diagnostics_output(output: String, uri: &Path, vendor_querier: &T) -> HashMap> +where + T: opengl::ShaderValidator + ?Sized, +{ + let output_lines = output.split('\n'); + let mut diagnostics: HashMap> = HashMap::with_capacity(output_lines.count()); + let output_lines = output.split('\n'); + + for line in output_lines { + let diagnostic_capture = match diagnostics_regex(vendor_querier).captures(line) { + Some(d) => d, + None => continue, + }; + + // info!("match {:?}", diagnostic_capture); + + let msg = diagnostic_capture.name("output").unwrap().as_str(); + + let line = match diagnostic_capture.name("linenum") { + Some(c) => c.as_str().parse::().unwrap_or(0), + None => 0, + } - line_number_offset(vendor_querier); + + // TODO: line matching maybe + /* let line_text = source_lines[line as usize]; + let leading_whitespace = line_text.len() - line_text.trim_start().len(); */ + + let severity = match diagnostic_capture.name("severity") { + Some(c) => match c.as_str().to_lowercase().as_str() { + "error" => DiagnosticSeverity::Error, + "warning" => DiagnosticSeverity::Warning, + _ => DiagnosticSeverity::Information, + }, + _ => DiagnosticSeverity::Information, + }; + + let origin = match diagnostic_capture.name("filepath") { + Some(o) => { + if o.as_str() == "0" { + uri.to_str().unwrap().to_string() + } else { + o.as_str().to_string() + } + } + None => uri.to_str().unwrap().to_string(), + }; + + let diagnostic = Diagnostic { + range: Range::new( + /* Position::new(line, leading_whitespace as u64), + Position::new(line, line_text.len() as u64) */ + Position::new(line, 0), + Position::new(line, 1000), + ), + code: None, + severity: Some(severity), + source: Some(consts::SOURCE.into()), + message: msg.trim().into(), + related_information: None, + tags: None, + code_description: Option::None, + data: Option::None, + }; + + let origin_url = Url::from_file_path(origin).unwrap(); + match diagnostics.get_mut(&origin_url) { + Some(d) => d.push(diagnostic), + None => { + diagnostics.insert(origin_url, vec![diagnostic]); + } + }; + } + diagnostics +} diff --git a/server/src/main.rs b/server/src/main.rs index f0d7032..b470820 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -39,6 +39,7 @@ use regex::Regex; use lazy_static::lazy_static; mod commands; +mod diagnostics_parser; mod configuration; mod consts; mod dfs; @@ -53,7 +54,6 @@ mod url_norm; mod test; lazy_static! { - static ref RE_DIAGNOSTIC: Regex = Regex::new(r#"^(?P[^?<>*|"]+)\((?P\d+)\) : (?Perror|warning) [A-C]\d+: (?P.+)"#).unwrap(); static ref RE_VERSION: Regex = Regex::new(r#"#version [\d]{3}"#).unwrap(); static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); static ref RE_INCLUDE_EXTENSION: Regex = Regex::new(r#"#extension GL_GOOGLE_include_directive ?: ?require"#).unwrap(); @@ -352,7 +352,7 @@ impl MinecraftShaderLanguageServer { return Ok(diagnostics); } }; - diagnostics.extend(self.parse_validator_stdout(uri, stdout, "")); + diagnostics.extend(diagnostics_parser::parse_diagnostics_output(stdout, uri, self.opengl_context.as_ref())); } else { let mut all_trees: Vec<(TreeType, Vec<(NodeIndex, Option<_>)>)> = Vec::new(); @@ -402,7 +402,7 @@ impl MinecraftShaderLanguageServer { Some(s) => s, None => continue, }; - diagnostics.extend(self.parse_validator_stdout(uri, stdout, "")); + diagnostics.extend(diagnostics_parser::parse_diagnostics_output(stdout, uri, self.opengl_context.as_ref())); } }; @@ -410,78 +410,6 @@ impl MinecraftShaderLanguageServer { Ok(diagnostics) } - fn parse_validator_stdout(&self, uri: &Path, stdout: String, _source: &str) -> HashMap> { - let stdout_lines = stdout.split('\n'); - let mut diagnostics: HashMap> = HashMap::with_capacity(stdout_lines.count()); - let stdout_lines = stdout.split('\n'); - - for line in stdout_lines { - let diagnostic_capture = match RE_DIAGNOSTIC.captures(line) { - Some(d) => d, - None => continue - }; - - eprintln!("match {:?}", diagnostic_capture); - - let msg = diagnostic_capture.name("output").unwrap().as_str(); - - let line = match diagnostic_capture.name("linenum") { - Some(c) => c.as_str().parse::().unwrap_or(0), - None => 0, - } - 2; - - // TODO: line matching maybe - /* let line_text = source_lines[line as usize]; - let leading_whitespace = line_text.len() - line_text.trim_start().len(); */ - - let severity = match diagnostic_capture.name("severity") { - Some(c) => match c.as_str() { - "error" => DiagnosticSeverity::Error, - "warning" => DiagnosticSeverity::Warning, - _ => DiagnosticSeverity::Information, - } - _ => DiagnosticSeverity::Information, - }; - - let origin = match diagnostic_capture.name("filepath") { - Some(o) => { - if o.as_str() == "0" { - uri.to_str().unwrap().to_string() - } else { - o.as_str().to_string() - } - }, - None => uri.to_str().unwrap().to_string(), - }; - - let diagnostic = Diagnostic { - range: Range::new( - /* Position::new(line, leading_whitespace as u64), - Position::new(line, line_text.len() as u64) */ - Position::new(line, 0), - Position::new(line, 1000), - ), - code: None, - severity: Some(severity), - source: Some(consts::SOURCE.into()), - message: msg.trim().into(), - related_information: None, - tags: None, - code_description: Option::None, - data: Option::None, - }; - - let origin_url = Url::from_file_path(origin).unwrap(); - match diagnostics.get_mut(&origin_url) { - Some(d) => d.push(diagnostic), - None => { - diagnostics.insert(origin_url, vec![diagnostic]); - }, - }; - } - diagnostics - } - pub fn get_dfs_for_node(&self, root: NodeIndex) -> Result)>, dfs::error::CycleError> { let graph_ref = self.graph.borrow(); diff --git a/server/src/opengl.rs b/server/src/opengl.rs index 4c9b605..e6adba5 100644 --- a/server/src/opengl.rs +++ b/server/src/opengl.rs @@ -9,6 +9,7 @@ use mockall::automock; #[cfg_attr(test, automock)] pub trait ShaderValidator { fn validate(&self, tree_type: super::TreeType, source: String) -> Option; + fn vendor(&self) -> String; } pub struct OpenGlContext { @@ -103,4 +104,8 @@ impl ShaderValidator for OpenGlContext { result } + + fn vendor(&self) -> String { + unsafe { String::from_utf8(CStr::from_ptr(gl::GetString(gl::VENDOR) as *const _).to_bytes().to_vec()).unwrap() } + } } diff --git a/server/src/test.rs b/server/src/test.rs index 53f6598..215a81f 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -6,8 +6,8 @@ use std::io::Result; use hamcrest2::prelude::*; use pretty_assertions::assert_eq; -use slog::Logger; use slog::o; +use slog::Logger; use tempdir::TempDir; use petgraph::algo::is_cyclic_directed; @@ -898,11 +898,12 @@ fn test_nvidia_diagnostics() { let output = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; - let results = server.parse_validator_stdout( - &PathBuf::from_str("/home/noah/.minecraft/shaderpacks/test").unwrap(), + let results = diagnostics_parser::parse_diagnostics_output( output.to_string(), - "", + &PathBuf::from_str("/home/noah/.minecraft/shaderpacks/test").unwrap(), + server.opengl_context.as_ref(), ); + assert_eq!(results.len(), 1); let first = results.into_iter().next().unwrap(); assert_eq!( @@ -923,7 +924,11 @@ ERROR: 0:10: '' : syntax error: #line ERROR: 0:15: 'varying' : syntax error: syntax error "; - let results = server.parse_validator_stdout(&PathBuf::from_str("/home/test").unwrap(), output.to_string(), ""); + let results = diagnostics_parser::parse_diagnostics_output( + output.to_string(), + &PathBuf::from_str("/home/test").unwrap(), + server.opengl_context.as_ref(), + ); assert_eq!(results.len(), 1); let first = results.into_iter().next().unwrap(); assert_eq!(first.1.len(), 3); From d5b0dcffb2265e2888f35056d4c20e5524ce4ec0 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 20 Mar 2022 01:27:45 +0000 Subject: [PATCH 29/56] wip --- server/Cargo.lock | 2 +- server/src/diagnostics_parser.rs | 2 +- server/src/main.rs | 35 +++++++++++++++++++++++++++----- server/src/opengl.rs | 4 ++-- server/src/test.rs | 2 +- 5 files changed, 35 insertions(+), 10 deletions(-) diff --git a/server/Cargo.lock b/server/Cargo.lock index 33edc21..1e22ef2 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -736,7 +736,7 @@ checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" [[package]] name = "mcshader-lsp" -version = "0.9.6" +version = "0.9.5" dependencies = [ "anyhow", "arc-swap", diff --git a/server/src/diagnostics_parser.rs b/server/src/diagnostics_parser.rs index bc3b965..4c6e47f 100644 --- a/server/src/diagnostics_parser.rs +++ b/server/src/diagnostics_parser.rs @@ -14,7 +14,7 @@ where T: opengl::ShaderValidator + ?Sized, { RE_DIAGNOSTIC.get_or_init(|| match vendor.vendor().as_str() { - "NVIDIA" => { + "NVIDIA Corporation" => { Regex::new(r#"^(?P[^?<>*|"]+)\((?P\d+)\) : (?Perror|warning) [A-C]\d+: (?P.+)"#).unwrap() } _ => { diff --git a/server/src/main.rs b/server/src/main.rs index b470820..28039b7 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -7,7 +7,7 @@ use petgraph::stable_graph::NodeIndex; use serde::Deserialize; use serde_json::{from_value, Value}; -use tree_sitter::Parser; +use tree_sitter::{Parser, Point}; use url_norm::FromUrl; use walkdir::WalkDir; @@ -39,10 +39,10 @@ use regex::Regex; use lazy_static::lazy_static; mod commands; -mod diagnostics_parser; mod configuration; mod consts; mod dfs; +mod diagnostics_parser; mod graph; mod logging; mod lsp_ext; @@ -352,7 +352,11 @@ impl MinecraftShaderLanguageServer { return Ok(diagnostics); } }; - diagnostics.extend(diagnostics_parser::parse_diagnostics_output(stdout, uri, self.opengl_context.as_ref())); + diagnostics.extend(diagnostics_parser::parse_diagnostics_output( + stdout, + uri, + self.opengl_context.as_ref(), + )); } else { let mut all_trees: Vec<(TreeType, Vec<(NodeIndex, Option<_>)>)> = Vec::new(); @@ -402,7 +406,11 @@ impl MinecraftShaderLanguageServer { Some(s) => s, None => continue, }; - diagnostics.extend(diagnostics_parser::parse_diagnostics_output(stdout, uri, self.opengl_context.as_ref())); + diagnostics.extend(diagnostics_parser::parse_diagnostics_output( + stdout, + uri, + self.opengl_context.as_ref(), + )); } }; @@ -488,6 +496,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { info!("starting server..."); let capabilities = ServerCapabilities { + definition_provider: Some(OneOf::Left(true)), document_link_provider: Some(DocumentLinkOptions { resolve_provider: None, work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None }, @@ -660,7 +669,23 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { completable.complete(Err(Self::error_not_available(()))); } - fn goto_definition(&mut self, _: TextDocumentPositionParams, completable: LSCompletable>) { + fn goto_definition(&mut self, params: TextDocumentPositionParams, completable: LSCompletable>) { + let source = fs::read_to_string(params.text_document.uri.path()).unwrap(); + let tree = self.tree_sitter.borrow_mut().parse(source, None).unwrap(); + + let node_at_pos = tree.root_node().named_descendant_for_point_range( + Point { + row: params.position.line as usize, + column: params.position.character as usize, + }, + Point { + row: params.position.line as usize, + column: (params.position.character + 1) as usize, + }, + ); + + info!("found a node"; "node" => format!("{:?}", node_at_pos)); + completable.complete(Err(Self::error_not_available(()))); } diff --git a/server/src/opengl.rs b/server/src/opengl.rs index e6adba5..73099ae 100644 --- a/server/src/opengl.rs +++ b/server/src/opengl.rs @@ -1,7 +1,7 @@ use std::ffi::{CStr, CString}; use std::ptr; -use slog_scope::{debug, info}; +use slog_scope::info; #[cfg(test)] use mockall::automock; @@ -32,7 +32,7 @@ impl OpenGlContext { let gl_ctx = OpenGlContext { _ctx: gl_window }; unsafe { - debug!( + info!( "OpenGL device"; "vendor" => gl_ctx.vendor(), "version" => String::from_utf8(CStr::from_ptr(gl::GetString(gl::VERSION) as *const _).to_bytes().to_vec()).unwrap(), diff --git a/server/src/test.rs b/server/src/test.rs index 215a81f..3e95277 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -893,7 +893,7 @@ fn test_generate_merge_list_04() { #[test] fn test_nvidia_diagnostics() { let mut mockgl = opengl::MockShaderValidator::new(); - mockgl.expect_vendor().returning(|| "NVIDIA".into()); + mockgl.expect_vendor().returning(|| "NVIDIA Corporation".into()); let server = new_temp_server(Some(Box::new(mockgl))); let output = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; From 616b7cef745d151732efc391a55647f27996a0fd Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 20 Mar 2022 15:17:32 +0000 Subject: [PATCH 30/56] revert bumping vscode-languageclient, broke restarting --- client/package-lock.json | 136 +++++++++++++++------------------------ client/package.json | 2 +- client/src/extension.ts | 2 +- client/src/lspClient.ts | 2 +- 4 files changed, 55 insertions(+), 87 deletions(-) diff --git a/client/package-lock.json b/client/package-lock.json index 2a9f363..d33cec9 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -10,7 +10,7 @@ "adm-zip": "^0.5.9", "encoding": "^0.1.13", "node-fetch": "^2.6.7", - "vscode-languageclient": "^7.0.0" + "vscode-languageclient": "^6.1.4" }, "devDependencies": { "@rollup/plugin-commonjs": "^21.0.2", @@ -156,12 +156,14 @@ "node_modules/balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", + "dev": true }, "node_modules/brace-expansion": { "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, "dependencies": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" @@ -200,7 +202,8 @@ "node_modules/concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", + "dev": true }, "node_modules/deepmerge": { "version": "4.2.2", @@ -359,17 +362,6 @@ "@types/estree": "*" } }, - "node_modules/lru-cache": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dependencies": { - "yallist": "^4.0.0" - }, - "engines": { - "node": ">=10" - } - }, "node_modules/magic-string": { "version": "0.25.7", "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.7.tgz", @@ -404,6 +396,7 @@ "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "dev": true, "dependencies": { "brace-expansion": "^1.1.7" }, @@ -498,17 +491,11 @@ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "node_modules/semver": { - "version": "7.3.5", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", - "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", - "dependencies": { - "lru-cache": "^6.0.0" - }, + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", "bin": { "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" } }, "node_modules/sourcemap-codec": { @@ -523,39 +510,38 @@ "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=" }, "node_modules/vscode-jsonrpc": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-6.0.0.tgz", - "integrity": "sha512-wnJA4BnEjOSyFMvjZdpiOwhSq9uDoK8e/kpRJDTaMYzwlkrhG1fwDIZI94CLsLzlCK5cIbMMtFlJlfR57Lavmg==", + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-5.0.1.tgz", + "integrity": "sha512-JvONPptw3GAQGXlVV2utDcHx0BiY34FupW/kI6mZ5x06ER5DdPG/tXWMVHjTNULF5uKPOUUD0SaXg5QaubJL0A==", "engines": { "node": ">=8.0.0 || >=10.0.0" } }, "node_modules/vscode-languageclient": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-7.0.0.tgz", - "integrity": "sha512-P9AXdAPlsCgslpP9pRxYPqkNYV7Xq8300/aZDpO35j1fJm/ncize8iGswzYlcvFw5DQUx4eVk+KvfXdL0rehNg==", + "version": "6.1.4", + "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-6.1.4.tgz", + "integrity": "sha512-EUOU+bJu6axmt0RFNo3nrglQLPXMfanbYViJee3Fbn2VuQoX0ZOI4uTYhSRvYLP2vfwTP/juV62P/mksCdTZMA==", "dependencies": { - "minimatch": "^3.0.4", - "semver": "^7.3.4", - "vscode-languageserver-protocol": "3.16.0" + "semver": "^6.3.0", + "vscode-languageserver-protocol": "3.15.3" }, "engines": { - "vscode": "^1.52.0" + "vscode": "^1.41.0" } }, "node_modules/vscode-languageserver-protocol": { - "version": "3.16.0", - "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.16.0.tgz", - "integrity": "sha512-sdeUoAawceQdgIfTI+sdcwkiK2KU+2cbEYA0agzM2uqaUy2UpnnGHtWTHVEtS0ES4zHU0eMFRGN+oQgDxlD66A==", + "version": "3.15.3", + "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.3.tgz", + "integrity": "sha512-zrMuwHOAQRhjDSnflWdJG+O2ztMWss8GqUUB8dXLR/FPenwkiBNkMIJJYfSN6sgskvsF0rHAoBowNQfbyZnnvw==", "dependencies": { - "vscode-jsonrpc": "6.0.0", - "vscode-languageserver-types": "3.16.0" + "vscode-jsonrpc": "^5.0.1", + "vscode-languageserver-types": "3.15.1" } }, "node_modules/vscode-languageserver-types": { - "version": "3.16.0", - "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.16.0.tgz", - "integrity": "sha512-k8luDIWJWyenLc5ToFQQMaSrqCHiLwyKPHKPQZ5zz21vM+vIVUSvsRpcbiECH4WR88K2XZqc4ScRcZ7nk/jbeA==" + "version": "3.15.1", + "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.15.1.tgz", + "integrity": "sha512-+a9MPUQrNGRrGU630OGbYVQ+11iOIovjCkqxajPa9w57Sd5ruK8WQNsslzpa0x/QJqC8kRc2DUxWjIFwoNm4ZQ==" }, "node_modules/webidl-conversions": { "version": "3.0.1", @@ -576,11 +562,6 @@ "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", "dev": true - }, - "node_modules/yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" } }, "dependencies": { @@ -697,12 +678,14 @@ "balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", + "dev": true }, "brace-expansion": { "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, "requires": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" @@ -732,7 +715,8 @@ "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", + "dev": true }, "deepmerge": { "version": "4.2.2", @@ -860,14 +844,6 @@ "@types/estree": "*" } }, - "lru-cache": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "requires": { - "yallist": "^4.0.0" - } - }, "magic-string": { "version": "0.25.7", "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.7.tgz", @@ -896,6 +872,7 @@ "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", + "dev": true, "requires": { "brace-expansion": "^1.1.7" } @@ -958,12 +935,9 @@ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "semver": { - "version": "7.3.5", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", - "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", - "requires": { - "lru-cache": "^6.0.0" - } + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" }, "sourcemap-codec": { "version": "1.4.8", @@ -977,33 +951,32 @@ "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=" }, "vscode-jsonrpc": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-6.0.0.tgz", - "integrity": "sha512-wnJA4BnEjOSyFMvjZdpiOwhSq9uDoK8e/kpRJDTaMYzwlkrhG1fwDIZI94CLsLzlCK5cIbMMtFlJlfR57Lavmg==" + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-5.0.1.tgz", + "integrity": "sha512-JvONPptw3GAQGXlVV2utDcHx0BiY34FupW/kI6mZ5x06ER5DdPG/tXWMVHjTNULF5uKPOUUD0SaXg5QaubJL0A==" }, "vscode-languageclient": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-7.0.0.tgz", - "integrity": "sha512-P9AXdAPlsCgslpP9pRxYPqkNYV7Xq8300/aZDpO35j1fJm/ncize8iGswzYlcvFw5DQUx4eVk+KvfXdL0rehNg==", + "version": "6.1.4", + "resolved": "https://registry.npmjs.org/vscode-languageclient/-/vscode-languageclient-6.1.4.tgz", + "integrity": "sha512-EUOU+bJu6axmt0RFNo3nrglQLPXMfanbYViJee3Fbn2VuQoX0ZOI4uTYhSRvYLP2vfwTP/juV62P/mksCdTZMA==", "requires": { - "minimatch": "^3.0.4", - "semver": "^7.3.4", - "vscode-languageserver-protocol": "3.16.0" + "semver": "^6.3.0", + "vscode-languageserver-protocol": "3.15.3" } }, "vscode-languageserver-protocol": { - "version": "3.16.0", - "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.16.0.tgz", - "integrity": "sha512-sdeUoAawceQdgIfTI+sdcwkiK2KU+2cbEYA0agzM2uqaUy2UpnnGHtWTHVEtS0ES4zHU0eMFRGN+oQgDxlD66A==", + "version": "3.15.3", + "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.3.tgz", + "integrity": "sha512-zrMuwHOAQRhjDSnflWdJG+O2ztMWss8GqUUB8dXLR/FPenwkiBNkMIJJYfSN6sgskvsF0rHAoBowNQfbyZnnvw==", "requires": { - "vscode-jsonrpc": "6.0.0", - "vscode-languageserver-types": "3.16.0" + "vscode-jsonrpc": "^5.0.1", + "vscode-languageserver-types": "3.15.1" } }, "vscode-languageserver-types": { - "version": "3.16.0", - "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.16.0.tgz", - "integrity": "sha512-k8luDIWJWyenLc5ToFQQMaSrqCHiLwyKPHKPQZ5zz21vM+vIVUSvsRpcbiECH4WR88K2XZqc4ScRcZ7nk/jbeA==" + "version": "3.15.1", + "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.15.1.tgz", + "integrity": "sha512-+a9MPUQrNGRrGU630OGbYVQ+11iOIovjCkqxajPa9w57Sd5ruK8WQNsslzpa0x/QJqC8kRc2DUxWjIFwoNm4ZQ==" }, "webidl-conversions": { "version": "3.0.1", @@ -1024,11 +997,6 @@ "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", "dev": true - }, - "yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" } } } diff --git a/client/package.json b/client/package.json index e40c901..7e508dd 100644 --- a/client/package.json +++ b/client/package.json @@ -9,7 +9,7 @@ "adm-zip": "^0.5.9", "encoding": "^0.1.13", "node-fetch": "^2.6.7", - "vscode-languageclient": "^7.0.0" + "vscode-languageclient": "^6.1.4" }, "devDependencies": { "@rollup/plugin-commonjs": "^21.0.2", diff --git a/client/src/extension.ts b/client/src/extension.ts index b6219ac..9133ae5 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -1,6 +1,6 @@ import { mkdirSync, promises as fs } from 'fs' import * as vscode from 'vscode' -import * as lsp from 'vscode-languageclient/node' +import * as lsp from 'vscode-languageclient' import * as commands from './commands' import { log } from './log' import { LanguageClient } from './lspClient' diff --git a/client/src/lspClient.ts b/client/src/lspClient.ts index 7751cfa..57cc6aa 100644 --- a/client/src/lspClient.ts +++ b/client/src/lspClient.ts @@ -1,5 +1,5 @@ import { ConfigurationTarget, workspace } from 'vscode' -import * as lsp from 'vscode-languageclient/node' +import * as lsp from 'vscode-languageclient' import { Extension } from './extension' import { log, lspOutputChannel } from './log' import { ConfigUpdateParams, statusMethod, StatusParams, updateConfigMethod } from './lspExt' From 3957eaed1751ca42625b2d71894e943ba5193025 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Mon, 21 Mar 2022 21:58:11 +0000 Subject: [PATCH 31/56] go-to-def for same-file functions from function calls working --- server/src/main.rs | 40 +++++++------- server/src/navigation.rs | 111 +++++++++++++++++++++++++++++++++++++++ 2 files changed, 133 insertions(+), 18 deletions(-) create mode 100644 server/src/navigation.rs diff --git a/server/src/main.rs b/server/src/main.rs index 28039b7..cbdc30f 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -7,7 +7,7 @@ use petgraph::stable_graph::NodeIndex; use serde::Deserialize; use serde_json::{from_value, Value}; -use tree_sitter::{Parser, Point}; +use tree_sitter::Parser; use url_norm::FromUrl; use walkdir::WalkDir; @@ -48,6 +48,7 @@ mod logging; mod lsp_ext; mod merge_views; mod opengl; +mod navigation; mod url_norm; #[cfg(test)] @@ -670,23 +671,26 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { } fn goto_definition(&mut self, params: TextDocumentPositionParams, completable: LSCompletable>) { - let source = fs::read_to_string(params.text_document.uri.path()).unwrap(); - let tree = self.tree_sitter.borrow_mut().parse(source, None).unwrap(); - - let node_at_pos = tree.root_node().named_descendant_for_point_range( - Point { - row: params.position.line as usize, - column: params.position.character as usize, - }, - Point { - row: params.position.line as usize, - column: (params.position.character + 1) as usize, - }, - ); - - info!("found a node"; "node" => format!("{:?}", node_at_pos)); - - completable.complete(Err(Self::error_not_available(()))); + logging::slog_with_trace_id(|| { + let parser = &mut self.tree_sitter.borrow_mut(); + let parser_ctx = match navigation::ParserContext::new(parser, params.text_document.uri.clone()) { + Ok(ctx) => ctx, + Err(e) => return completable.complete(Err(MethodError{ + code: 42069, + message: format!("error building parser context: {}", e), + data: (), + })), + }; + + match parser_ctx.find_definitions(params.text_document.uri, params.position) { + Ok(locations) => completable.complete(Ok(locations)), + Err(e) => completable.complete(Err(MethodError { + code: 42069, + message: format!("error finding definitions: {}", e), + data: (), + })), + } + }); } fn references(&mut self, _: ReferenceParams, completable: LSCompletable>) { diff --git a/server/src/navigation.rs b/server/src/navigation.rs new file mode 100644 index 0000000..e5bc52c --- /dev/null +++ b/server/src/navigation.rs @@ -0,0 +1,111 @@ +use std::fs::read_to_string; + +use anyhow::Result; +use rust_lsp::lsp_types::{Location, Position, Range}; +use slog_scope::{info, debug}; +use tree_sitter::{Node, Parser, Point, Tree, Query, QueryCursor}; +use url::Url; + +macro_rules! find_function_str { + () => { + r#" + ( + (function_declarator + (identifier) @function) + (#match? @function "{}") + ) + "# + }; +} +pub struct ParserContext<'a> { + source: String, + tree: Tree, + parser: &'a mut Parser, +} + +impl<'a> ParserContext<'a> { + pub fn new(parser: &'a mut Parser, document_uri: Url) -> Result { + let source = read_to_string(document_uri.path())?; + + let tree = parser.parse(&source, None).unwrap(); + + Ok(ParserContext { source, tree, parser }) + } + + pub fn find_definitions(&self, document_uri: Url, point: Position) -> Result> { + let current_node = match self.find_node_at_point(point) { + Some(node) => node, + None => return Ok(vec![]), + }; + + let parent = match current_node.parent() { + Some(parent) => parent, + None => return Ok(vec![]), + }; + + let query = match (current_node.kind(), parent.kind()) { + (_, "call_expression") => { + format!(find_function_str!(), current_node.utf8_text(self.source.as_bytes())?) + } + _ => return Ok(vec![]), + }; + + let ts_query = Query::new(tree_sitter_glsl::language(), query.as_str())?; + + let mut query_cursor = QueryCursor::new(); + + let mut locations = vec![]; + + for m in query_cursor.matches(&ts_query, self.tree.root_node(), self.source.as_bytes()) { + for capture in m.captures { + let start = capture.node.start_position(); + let end = capture.node.end_position(); + + locations.push(Location { + uri: document_uri.clone(), + range: Range { + start: Position { + line: start.row as u32, + character: start.column as u32, + }, + end: Position { + line: end.row as u32, + character: end.column as u32, + }, + }, + }); + } + } + + info!("finished searching for definitions"; "definitions" => format!("{:?}", locations)); + + Ok(locations) + } + + pub fn find_references(&self) -> Result> { + Ok(vec![]) + } + + fn root_node(&self) -> Node { + self.tree.root_node() + } + + fn find_node_at_point(&self, point: Position) -> Option { + match self.root_node().named_descendant_for_point_range( + Point { + row: point.line as usize, + column: (point.character - 1) as usize, + }, + Point { + row: point.line as usize, + column: point.character as usize, + }, + ) { + Some(node) => { + debug!("found a node"; "node" => format!("{:?}", node)); + Some(node) + }, + None => None, + } + } +} From 9a499d581b539bebf2b0d4669cc019a71dab14bd Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Thu, 24 Mar 2022 22:33:51 +0000 Subject: [PATCH 32/56] move tests to their respective files --- server/src/dfs.rs | 181 +++++++++ server/src/diagnostics_parser.rs | 52 +++ server/src/graph.rs | 174 ++++++++ server/src/main.rs | 2 +- server/src/merge_views.rs | 281 +++++++++++++ server/src/test.rs | 659 +------------------------------ 6 files changed, 691 insertions(+), 658 deletions(-) diff --git a/server/src/dfs.rs b/server/src/dfs.rs index 908d3bd..363808e 100644 --- a/server/src/dfs.rs +++ b/server/src/dfs.rs @@ -153,3 +153,184 @@ pub mod error { } } } + +#[cfg(test)] +mod dfs_test { + use std::path::PathBuf; + + use hamcrest2::prelude::*; + use hamcrest2::{assert_that, ok}; + use petgraph::{algo::is_cyclic_directed, graph::NodeIndex}; + + use crate::graph::CachedStableGraph; + use crate::{dfs, IncludePosition}; + + #[test] + fn test_graph_dfs() { + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + + let dfs = dfs::Dfs::new(&graph, idx0); + + let mut collection = Vec::new(); + + for i in dfs { + assert_that!(&i, ok()); + collection.push(i.unwrap()); + } + + let nodes: Vec = collection.iter().map(|n| n.0).collect(); + let parents: Vec> = collection.iter().map(|n| n.1).collect(); + // 0 + // / \ + // 1 2 + // / + // 3 + let expected_nodes = vec![idx0, idx1, idx3, idx2]; + + assert_eq!(expected_nodes, nodes); + + let expected_parents = vec![None, Some(idx0), Some(idx1), Some(idx0)]; + + assert_eq!(expected_parents, parents); + + assert!(!is_cyclic_directed(&graph.graph)); + } + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + let idx4 = graph.add_node(&PathBuf::from("4")); + let idx5 = graph.add_node(&PathBuf::from("5")); + let idx6 = graph.add_node(&PathBuf::from("6")); + let idx7 = graph.add_node(&PathBuf::from("7")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx1, idx4, IncludePosition { line: 6, start: 0, end: 0 }); + graph.add_edge(idx2, idx4, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx2, idx5, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx3, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx4, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx6, idx7, IncludePosition { line: 4, start: 0, end: 0 }); + + let dfs = dfs::Dfs::new(&graph, idx0); + + let mut collection = Vec::new(); + + for i in dfs { + assert_that!(&i, ok()); + collection.push(i.unwrap()); + } + + let nodes: Vec = collection.iter().map(|n| n.0).collect(); + let parents: Vec> = collection.iter().map(|n| n.1).collect(); + // 0 + // / \ + // 1 2 + // / \ / \ + // 3 4 5 + // \ / + // 6 - 7 + let expected_nodes = vec![idx0, idx1, idx3, idx6, idx7, idx4, idx6, idx7, idx2, idx5, idx4, idx6, idx7]; + + assert_eq!(expected_nodes, nodes); + + let expected_parents = vec![ + None, + Some(idx0), + Some(idx1), + Some(idx3), + Some(idx6), + Some(idx1), + Some(idx4), + Some(idx6), + Some(idx0), + Some(idx2), + Some(idx2), + Some(idx4), + Some(idx6), + ]; + + assert_eq!(expected_parents, parents); + + assert!(!is_cyclic_directed(&graph.graph)); + } + } + + #[test] + fn test_graph_dfs_cycle() { + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + let idx4 = graph.add_node(&PathBuf::from("4")); + let idx5 = graph.add_node(&PathBuf::from("5")); + let idx6 = graph.add_node(&PathBuf::from("6")); + let idx7 = graph.add_node(&PathBuf::from("7")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx1, idx4, IncludePosition { line: 6, start: 0, end: 0 }); + graph.add_edge(idx2, idx4, IncludePosition { line: 5, start: 0, end: 0 }); + graph.add_edge(idx2, idx5, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx3, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx4, idx6, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx6, idx7, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx7, idx4, IncludePosition { line: 4, start: 0, end: 0 }); + + let mut dfs = dfs::Dfs::new(&graph, idx0); + + for _ in 0..5 { + if let Some(i) = dfs.next() { + assert_that!(&i, ok()); + } + } + + // 0 + // / \ + // 1 2 + // / \ / \ + // 3 4 5 + // \ / \ + // 6 - 7 + + assert!(is_cyclic_directed(&graph.graph)); + + let next = dfs.next().unwrap(); + assert_that!(next, err()); + } + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx1, idx0, IncludePosition { line: 2, start: 0, end: 0 }); + + let mut dfs = dfs::Dfs::new(&graph, idx1); + + println!("{:?}", dfs.next()); + println!("{:?}", dfs.next()); + println!("{:?}", dfs.next()); + } + } +} diff --git a/server/src/diagnostics_parser.rs b/server/src/diagnostics_parser.rs index 4c6e47f..b473896 100644 --- a/server/src/diagnostics_parser.rs +++ b/server/src/diagnostics_parser.rs @@ -108,3 +108,55 @@ where } diagnostics } + +#[cfg(test)] +mod diagnostics_test { + use std::{path::PathBuf, str::FromStr}; + + use crate::{diagnostics_parser::parse_diagnostics_output, opengl::MockShaderValidator, test::new_temp_server}; + + #[test] + fn test_nvidia_diagnostics() { + let mut mockgl = MockShaderValidator::new(); + mockgl.expect_vendor().returning(|| "NVIDIA Corporation".into()); + let server = new_temp_server(Some(Box::new(mockgl))); + + let output = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; + + let results = parse_diagnostics_output( + output.to_string(), + &PathBuf::from_str("/home/noah/.minecraft/shaderpacks/test").unwrap(), + server.opengl_context.as_ref(), + ); + + assert_eq!(results.len(), 1); + let first = results.into_iter().next().unwrap(); + assert_eq!( + first.0, + url::Url::from_file_path("/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh").unwrap() + ); + server.endpoint.request_shutdown(); + } + + #[test] + fn test_amd_diagnostics() { + let mut mockgl = MockShaderValidator::new(); + mockgl.expect_vendor().returning(|| "ATI Technologies".into()); + let server = new_temp_server(Some(Box::new(mockgl))); + + let output = "ERROR: 0:1: '' : syntax error: #line +ERROR: 0:10: '' : syntax error: #line +ERROR: 0:15: 'varying' : syntax error: syntax error +"; + + let results = parse_diagnostics_output( + output.to_string(), + &PathBuf::from_str("/home/test").unwrap(), + server.opengl_context.as_ref(), + ); + assert_eq!(results.len(), 1); + let first = results.into_iter().next().unwrap(); + assert_eq!(first.1.len(), 3); + server.endpoint.request_shutdown(); + } +} diff --git a/server/src/graph.rs b/server/src/graph.rs index 39ed80a..81f07c1 100644 --- a/server/src/graph.rs +++ b/server/src/graph.rs @@ -162,3 +162,177 @@ impl CachedStableGraph { collection } } + +#[cfg(test)] +mod graph_test { + use std::path::PathBuf; + + use crate::{graph::CachedStableGraph, IncludePosition}; + + #[test] + fn test_graph_two_connected_nodes() { + let mut graph = CachedStableGraph::new(); + + let idx1 = graph.add_node(&PathBuf::from("sample")); + let idx2 = graph.add_node(&PathBuf::from("banana")); + graph.add_edge(idx1, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + + let children = graph.child_node_names(idx1); + assert_eq!(children.len(), 1); + assert_eq!(children[0], Into::::into("banana".to_string())); + + let children = graph.child_node_indexes(idx1); + assert_eq!(children.len(), 1); + assert_eq!(children[0], idx2); + + let parents = graph.parent_node_names(idx1); + assert_eq!(parents.len(), 0); + + let parents = graph.parent_node_names(idx2); + assert_eq!(parents.len(), 1); + assert_eq!(parents[0], Into::::into("sample".to_string())); + + let parents = graph.parent_node_indexes(idx2); + assert_eq!(parents.len(), 1); + assert_eq!(parents[0], idx1); + + let ancestors = graph.collect_root_ancestors(idx2); + assert_eq!(ancestors.len(), 1); + assert_eq!(ancestors[0], idx1); + + let ancestors = graph.collect_root_ancestors(idx1); + assert_eq!(ancestors.len(), 0); + + graph.remove_node(&PathBuf::from("sample")); + assert_eq!(graph.graph.node_count(), 1); + assert!(graph.find_node(&PathBuf::from("sample")).is_none()); + let neighbors = graph.child_node_names(idx2); + assert_eq!(neighbors.len(), 0); + } + + #[test] + fn test_collect_root_ancestors() { + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx1, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx3, idx1, IncludePosition { line: 4, start: 0, end: 0 }); + + // 0 3 + // |/ + // 1 + // | + // 2 + + let roots = graph.collect_root_ancestors(idx2); + assert_eq!(roots, vec![idx3, idx0]); + + let roots = graph.collect_root_ancestors(idx1); + assert_eq!(roots, vec![idx3, idx0]); + + let roots = graph.collect_root_ancestors(idx0); + assert_eq!(roots, vec![]); + + let roots = graph.collect_root_ancestors(idx3); + assert_eq!(roots, vec![]); + } + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + + // 0 + // / \ + // 1 2 + // / + // 3 + + let roots = graph.collect_root_ancestors(idx3); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx2); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx1); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx0); + assert_eq!(roots, vec![]); + } + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx2, idx3, IncludePosition { line: 3, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); + + // 0 + // | + // 1 + // \ + // 2 \ + // \ / + // 3 + + let roots = graph.collect_root_ancestors(idx3); + assert_eq!(roots, vec![idx0, idx2]); + + let roots = graph.collect_root_ancestors(idx2); + assert_eq!(roots, vec![]); + + let roots = graph.collect_root_ancestors(idx1); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx0); + assert_eq!(roots, vec![]); + } + { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + let idx2 = graph.add_node(&PathBuf::from("2")); + let idx3 = graph.add_node(&PathBuf::from("3")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx1, idx2, IncludePosition { line: 4, start: 0, end: 0 }); + graph.add_edge(idx1, idx3, IncludePosition { line: 6, start: 0, end: 0 }); + + // 0 + // | + // 1 + // / \ + // 2 3 + + let roots = graph.collect_root_ancestors(idx3); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx2); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx1); + assert_eq!(roots, vec![idx0]); + + let roots = graph.collect_root_ancestors(idx0); + assert_eq!(roots, vec![]); + } + } +} diff --git a/server/src/main.rs b/server/src/main.rs index cbdc30f..25bd1c8 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -104,7 +104,7 @@ fn main() { LSPEndpoint::run_server_from_input(&mut stdin().lock(), endpoint_output, langserver); } -struct MinecraftShaderLanguageServer { +pub struct MinecraftShaderLanguageServer { endpoint: Endpoint, graph: Rc>, root: PathBuf, diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index 2566c02..4a24065 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -213,3 +213,284 @@ fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, line_directives: &[S merge_list.push_back(&vec_ptr_offset.as_ref().unwrap()[..]); } } + +#[cfg(test)] +mod merge_view_test { + use std::fs; + use std::path::PathBuf; + + use crate::merge_views::generate_merge_list; + use crate::test::{copy_to_and_set_root, new_temp_server}; + use crate::IncludePosition; + + #[test] + fn test_generate_merge_list_01() { + let mut server = new_temp_server(None); + + let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/01", &mut server); + server.endpoint.request_shutdown(); + + let final_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{:?}/shaders/final.fsh", tmp_path).try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("final.fsh")); + let common_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{:?}/shaders/common.glsl", tmp_path).try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("common.glsl")); + + server + .graph + .borrow_mut() + .add_edge(final_idx, common_idx, IncludePosition { line: 2, start: 0, end: 0 }); + + let nodes = server.get_dfs_for_node(final_idx).unwrap(); + let sources = server.load_sources(&nodes).unwrap(); + + let graph_borrow = server.graph.borrow(); + let result = generate_merge_list(&nodes, &sources, &graph_borrow); + + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); + + let mut truth = fs::read_to_string(merge_file).unwrap(); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("common.glsl").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); + truth = truth.replace( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + ); + + assert_eq!(result, truth); + } + + #[test] + fn test_generate_merge_list_02() { + let mut server = new_temp_server(None); + + let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/02", &mut server); + server.endpoint.request_shutdown(); + + let final_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("final.fsh")); + let test_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); + let burger_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); + let sample_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); + + server + .graph + .borrow_mut() + .add_edge(final_idx, sample_idx, IncludePosition { line: 2, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, burger_idx, IncludePosition { line: 4, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, test_idx, IncludePosition { line: 6, start: 0, end: 0 }); + + let nodes = server.get_dfs_for_node(final_idx).unwrap(); + let sources = server.load_sources(&nodes).unwrap(); + + let graph_borrow = server.graph.borrow(); + let result = generate_merge_list(&nodes, &sources, &graph_borrow); + + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); + + let mut truth = fs::read_to_string(merge_file).unwrap(); + + for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { + let path = tmp_path.clone(); + truth = truth.replacen( + "!!", + &path + .join("shaders") + .join("utils") + .join(file) + .to_str() + .unwrap() + .replace('\\', "\\\\"), + 1, + ); + } + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); + + assert_eq!(result, truth); + } + + #[test] + fn test_generate_merge_list_03() { + let mut server = new_temp_server(None); + + let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/03", &mut server); + server.endpoint.request_shutdown(); + + let final_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("final.fsh")); + let test_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); + let burger_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); + let sample_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); + + server + .graph + .borrow_mut() + .add_edge(final_idx, sample_idx, IncludePosition { line: 2, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, burger_idx, IncludePosition { line: 4, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(sample_idx, test_idx, IncludePosition { line: 6, start: 0, end: 0 }); + + let nodes = server.get_dfs_for_node(final_idx).unwrap(); + let sources = server.load_sources(&nodes).unwrap(); + + let graph_borrow = server.graph.borrow(); + let result = generate_merge_list(&nodes, &sources, &graph_borrow); + + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); + + let mut truth = fs::read_to_string(merge_file).unwrap(); + + for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { + let path = tmp_path.clone(); + truth = truth.replacen( + "!!", + &path + .join("shaders") + .join("utils") + .join(file) + .to_str() + .unwrap() + .replace('\\', "\\\\"), + 1, + ); + } + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); + + assert_eq!(result, truth); + } + + #[test] + fn test_generate_merge_list_04() { + let mut server = new_temp_server(None); + + let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/04", &mut server); + server.endpoint.request_shutdown(); + + let final_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("final.fsh")); + let utilities_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "utilities.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("utilities.glsl")); + let stuff1_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff1.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("stuff1.glsl")); + let stuff2_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff2.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("utils").join("stuff2.glsl")); + let matrices_idx = server + .graph + .borrow_mut() + //.add_node(&format!("{}/shaders/lib/{}", tmp_path, "matrices.glsl").try_into().unwrap()); + .add_node(&tmp_path.join("shaders").join("lib").join("matrices.glsl")); + + server + .graph + .borrow_mut() + .add_edge(final_idx, utilities_idx, IncludePosition { line: 2, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(utilities_idx, stuff1_idx, IncludePosition { line: 0, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(utilities_idx, stuff2_idx, IncludePosition { line: 1, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(final_idx, matrices_idx, IncludePosition { line: 3, start: 0, end: 0 }); + + let nodes = server.get_dfs_for_node(final_idx).unwrap(); + let sources = server.load_sources(&nodes).unwrap(); + + let graph_borrow = server.graph.borrow(); + let result = generate_merge_list(&nodes, &sources, &graph_borrow); + + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); + + let mut truth = fs::read_to_string(merge_file).unwrap(); + + for file in &[ + PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), + PathBuf::new().join("utils").join("stuff1.glsl").to_str().unwrap(), + PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), + PathBuf::new().join("utils").join("stuff2.glsl").to_str().unwrap(), + PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), + PathBuf::new().join("final.fsh").to_str().unwrap(), + PathBuf::new().join("lib").join("matrices.glsl").to_str().unwrap(), + PathBuf::new().join("final.fsh").to_str().unwrap(), + ] { + let path = tmp_path.clone(); + //path.f + truth = truth.replacen("!!", &path.join("shaders").join(file).to_str().unwrap().replace('\\', "\\\\"), 1); + } + + assert_eq!(result, truth); + } +} diff --git a/server/src/test.rs b/server/src/test.rs index 3e95277..9a77810 100644 --- a/server/src/test.rs +++ b/server/src/test.rs @@ -3,15 +3,12 @@ use std::fs; use std::io; use std::io::Result; -use hamcrest2::prelude::*; use pretty_assertions::assert_eq; use slog::o; use slog::Logger; use tempdir::TempDir; -use petgraph::algo::is_cyclic_directed; - use fs_extra::{copy_items, dir}; use jsonrpc_common::*; @@ -36,7 +33,7 @@ impl io::Write for StdoutNewline { } } -fn new_temp_server(opengl_context: Option>) -> MinecraftShaderLanguageServer { +pub fn new_temp_server(opengl_context: Option>) -> MinecraftShaderLanguageServer { let endpoint = LSPEndpoint::create_lsp_output_with_output_stream(|| StdoutNewline { s: Box::new(io::sink()) }); let context = opengl_context.unwrap_or_else(|| Box::new(opengl::MockShaderValidator::new())); @@ -63,7 +60,7 @@ fn copy_files(files: &str, dest: &TempDir) { copy_items(&files, dest.path().join("shaders"), opts).unwrap(); } -fn copy_to_and_set_root(test_path: &str, server: &mut MinecraftShaderLanguageServer) -> (Rc, PathBuf) { +pub fn copy_to_and_set_root(test_path: &str, server: &mut MinecraftShaderLanguageServer) -> (Rc, PathBuf) { let (_tmp_dir, tmp_path) = copy_to_tmp_dir(test_path); server.root = tmp_path.clone(); //format!("{}{}", "file://", tmp_path); @@ -282,655 +279,3 @@ fn test_05_initialize() { assert!(contains, "doesn't contain ({:?}, {:?})", first, second); } } - -#[test] -fn test_graph_two_connected_nodes() { - let mut graph = graph::CachedStableGraph::new(); - - let idx1 = graph.add_node(&PathBuf::from("sample")); - let idx2 = graph.add_node(&PathBuf::from("banana")); - graph.add_edge(idx1, idx2, IncludePosition { line: 3, start: 0, end: 0 }); - - let children = graph.child_node_names(idx1); - assert_eq!(children.len(), 1); - assert_eq!(children[0], Into::::into("banana".to_string())); - - let children = graph.child_node_indexes(idx1); - assert_eq!(children.len(), 1); - assert_eq!(children[0], idx2); - - let parents = graph.parent_node_names(idx1); - assert_eq!(parents.len(), 0); - - let parents = graph.parent_node_names(idx2); - assert_eq!(parents.len(), 1); - assert_eq!(parents[0], Into::::into("sample".to_string())); - - let parents = graph.parent_node_indexes(idx2); - assert_eq!(parents.len(), 1); - assert_eq!(parents[0], idx1); - - let ancestors = graph.collect_root_ancestors(idx2); - assert_eq!(ancestors.len(), 1); - assert_eq!(ancestors[0], idx1); - - let ancestors = graph.collect_root_ancestors(idx1); - assert_eq!(ancestors.len(), 0); - - graph.remove_node(&PathBuf::from("sample")); - assert_eq!(graph.graph.node_count(), 1); - assert!(graph.find_node(&PathBuf::from("sample")).is_none()); - let neighbors = graph.child_node_names(idx2); - assert_eq!(neighbors.len(), 0); -} - -#[test] -fn test_collect_root_ancestors() { - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx1, idx2, IncludePosition { line: 3, start: 0, end: 0 }); - graph.add_edge(idx3, idx1, IncludePosition { line: 4, start: 0, end: 0 }); - - // 0 3 - // |/ - // 1 - // | - // 2 - - let roots = graph.collect_root_ancestors(idx2); - assert_eq!(roots, vec![idx3, idx0]); - - let roots = graph.collect_root_ancestors(idx1); - assert_eq!(roots, vec![idx3, idx0]); - - let roots = graph.collect_root_ancestors(idx0); - assert_eq!(roots, vec![]); - - let roots = graph.collect_root_ancestors(idx3); - assert_eq!(roots, vec![]); - } - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); - graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); - - // 0 - // / \ - // 1 2 - // / - // 3 - - let roots = graph.collect_root_ancestors(idx3); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx2); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx1); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx0); - assert_eq!(roots, vec![]); - } - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx2, idx3, IncludePosition { line: 3, start: 0, end: 0 }); - graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); - - // 0 - // | - // 1 - // \ - // 2 \ - // \ / - // 3 - - let roots = graph.collect_root_ancestors(idx3); - assert_eq!(roots, vec![idx0, idx2]); - - let roots = graph.collect_root_ancestors(idx2); - assert_eq!(roots, vec![]); - - let roots = graph.collect_root_ancestors(idx1); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx0); - assert_eq!(roots, vec![]); - } - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx1, idx2, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx1, idx3, IncludePosition { line: 6, start: 0, end: 0 }); - - // 0 - // | - // 1 - // / \ - // 2 3 - - let roots = graph.collect_root_ancestors(idx3); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx2); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx1); - assert_eq!(roots, vec![idx0]); - - let roots = graph.collect_root_ancestors(idx0); - assert_eq!(roots, vec![]); - } -} - -#[test] -fn test_graph_dfs() { - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); - graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); - - let dfs = dfs::Dfs::new(&graph, idx0); - - let mut collection = Vec::new(); - - for i in dfs { - assert_that!(&i, ok()); - collection.push(i.unwrap()); - } - - let nodes: Vec = collection.iter().map(|n| n.0).collect(); - let parents: Vec> = collection.iter().map(|n| n.1).collect(); - // 0 - // / \ - // 1 2 - // / - // 3 - let expected_nodes = vec![idx0, idx1, idx3, idx2]; - - assert_eq!(expected_nodes, nodes); - - let expected_parents = vec![None, Some(idx0), Some(idx1), Some(idx0)]; - - assert_eq!(expected_parents, parents); - - assert!(!is_cyclic_directed(&graph.graph)); - } - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - let idx4 = graph.add_node(&PathBuf::from("4")); - let idx5 = graph.add_node(&PathBuf::from("5")); - let idx6 = graph.add_node(&PathBuf::from("6")); - let idx7 = graph.add_node(&PathBuf::from("7")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); - graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); - graph.add_edge(idx1, idx4, IncludePosition { line: 6, start: 0, end: 0 }); - graph.add_edge(idx2, idx4, IncludePosition { line: 5, start: 0, end: 0 }); - graph.add_edge(idx2, idx5, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx3, idx6, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx4, idx6, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx6, idx7, IncludePosition { line: 4, start: 0, end: 0 }); - - let dfs = dfs::Dfs::new(&graph, idx0); - - let mut collection = Vec::new(); - - for i in dfs { - assert_that!(&i, ok()); - collection.push(i.unwrap()); - } - - let nodes: Vec = collection.iter().map(|n| n.0).collect(); - let parents: Vec> = collection.iter().map(|n| n.1).collect(); - // 0 - // / \ - // 1 2 - // / \ / \ - // 3 4 5 - // \ / - // 6 - 7 - let expected_nodes = vec![idx0, idx1, idx3, idx6, idx7, idx4, idx6, idx7, idx2, idx5, idx4, idx6, idx7]; - - assert_eq!(expected_nodes, nodes); - - let expected_parents = vec![ - None, - Some(idx0), - Some(idx1), - Some(idx3), - Some(idx6), - Some(idx1), - Some(idx4), - Some(idx6), - Some(idx0), - Some(idx2), - Some(idx2), - Some(idx4), - Some(idx6), - ]; - - assert_eq!(expected_parents, parents); - - assert!(!is_cyclic_directed(&graph.graph)); - } -} - -#[test] -fn test_graph_dfs_cycle() { - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - let idx2 = graph.add_node(&PathBuf::from("2")); - let idx3 = graph.add_node(&PathBuf::from("3")); - let idx4 = graph.add_node(&PathBuf::from("4")); - let idx5 = graph.add_node(&PathBuf::from("5")); - let idx6 = graph.add_node(&PathBuf::from("6")); - let idx7 = graph.add_node(&PathBuf::from("7")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx0, idx2, IncludePosition { line: 3, start: 0, end: 0 }); - graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); - graph.add_edge(idx1, idx4, IncludePosition { line: 6, start: 0, end: 0 }); - graph.add_edge(idx2, idx4, IncludePosition { line: 5, start: 0, end: 0 }); - graph.add_edge(idx2, idx5, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx3, idx6, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx4, idx6, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx6, idx7, IncludePosition { line: 4, start: 0, end: 0 }); - graph.add_edge(idx7, idx4, IncludePosition { line: 4, start: 0, end: 0 }); - - let mut dfs = dfs::Dfs::new(&graph, idx0); - - for _ in 0..5 { - if let Some(i) = dfs.next() { - assert_that!(&i, ok()); - } - } - - // 0 - // / \ - // 1 2 - // / \ / \ - // 3 4 5 - // \ / \ - // 6 - 7 - - assert!(is_cyclic_directed(&graph.graph)); - - let next = dfs.next().unwrap(); - assert_that!(next, err()); - } - { - let mut graph = graph::CachedStableGraph::new(); - - let idx0 = graph.add_node(&PathBuf::from("0")); - let idx1 = graph.add_node(&PathBuf::from("1")); - - graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); - graph.add_edge(idx1, idx0, IncludePosition { line: 2, start: 0, end: 0 }); - - let mut dfs = dfs::Dfs::new(&graph, idx1); - - println!("{:?}", dfs.next()); - println!("{:?}", dfs.next()); - println!("{:?}", dfs.next()); - } -} - -#[test] -fn test_generate_merge_list_01() { - let mut server = new_temp_server(None); - - let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/01", &mut server); - server.endpoint.request_shutdown(); - - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{:?}/shaders/final.fsh", tmp_path).try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); - let common_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{:?}/shaders/common.glsl", tmp_path).try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("common.glsl")); - - server - .graph - .borrow_mut() - .add_edge(final_idx, common_idx, IncludePosition { line: 2, start: 0, end: 0 }); - - let nodes = server.get_dfs_for_node(final_idx).unwrap(); - let sources = server.load_sources(&nodes).unwrap(); - - let graph_borrow = server.graph.borrow(); - let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - - let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); - - let mut truth = fs::read_to_string(merge_file).unwrap(); - truth = truth.replacen( - "!!", - &tmp_path.join("shaders").join("common.glsl").to_str().unwrap().replace('\\', "\\\\"), - 1, - ); - truth = truth.replace( - "!!", - &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), - ); - - assert_eq!(result, truth); -} - -#[test] -fn test_generate_merge_list_02() { - let mut server = new_temp_server(None); - - let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/02", &mut server); - server.endpoint.request_shutdown(); - - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); - let test_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); - let burger_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); - let sample_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); - - server - .graph - .borrow_mut() - .add_edge(final_idx, sample_idx, IncludePosition { line: 2, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(sample_idx, burger_idx, IncludePosition { line: 4, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(sample_idx, test_idx, IncludePosition { line: 6, start: 0, end: 0 }); - - let nodes = server.get_dfs_for_node(final_idx).unwrap(); - let sources = server.load_sources(&nodes).unwrap(); - - let graph_borrow = server.graph.borrow(); - let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - - let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); - - let mut truth = fs::read_to_string(merge_file).unwrap(); - - for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { - let path = tmp_path.clone(); - truth = truth.replacen( - "!!", - &path - .join("shaders") - .join("utils") - .join(file) - .to_str() - .unwrap() - .replace('\\', "\\\\"), - 1, - ); - } - truth = truth.replacen( - "!!", - &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), - 1, - ); - - assert_eq!(result, truth); -} - -#[test] -fn test_generate_merge_list_03() { - let mut server = new_temp_server(None); - - let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/03", &mut server); - server.endpoint.request_shutdown(); - - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); - let test_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); - let burger_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); - let sample_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); - - server - .graph - .borrow_mut() - .add_edge(final_idx, sample_idx, IncludePosition { line: 2, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(sample_idx, burger_idx, IncludePosition { line: 4, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(sample_idx, test_idx, IncludePosition { line: 6, start: 0, end: 0 }); - - let nodes = server.get_dfs_for_node(final_idx).unwrap(); - let sources = server.load_sources(&nodes).unwrap(); - - let graph_borrow = server.graph.borrow(); - let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - - let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); - - let mut truth = fs::read_to_string(merge_file).unwrap(); - - for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { - let path = tmp_path.clone(); - truth = truth.replacen( - "!!", - &path - .join("shaders") - .join("utils") - .join(file) - .to_str() - .unwrap() - .replace('\\', "\\\\"), - 1, - ); - } - truth = truth.replacen( - "!!", - &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), - 1, - ); - - assert_eq!(result, truth); -} - -#[test] -fn test_generate_merge_list_04() { - let mut server = new_temp_server(None); - - let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/04", &mut server); - server.endpoint.request_shutdown(); - - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); - let utilities_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "utilities.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("utilities.glsl")); - let stuff1_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff1.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("stuff1.glsl")); - let stuff2_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff2.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("utils").join("stuff2.glsl")); - let matrices_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/lib/{}", tmp_path, "matrices.glsl").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("lib").join("matrices.glsl")); - - server - .graph - .borrow_mut() - .add_edge(final_idx, utilities_idx, IncludePosition { line: 2, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(utilities_idx, stuff1_idx, IncludePosition { line: 0, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(utilities_idx, stuff2_idx, IncludePosition { line: 1, start: 0, end: 0 }); - server - .graph - .borrow_mut() - .add_edge(final_idx, matrices_idx, IncludePosition { line: 3, start: 0, end: 0 }); - - let nodes = server.get_dfs_for_node(final_idx).unwrap(); - let sources = server.load_sources(&nodes).unwrap(); - - let graph_borrow = server.graph.borrow(); - let result = merge_views::generate_merge_list(&nodes, &sources, &graph_borrow); - - let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); - - let mut truth = fs::read_to_string(merge_file).unwrap(); - - for file in &[ - PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), - PathBuf::new().join("utils").join("stuff1.glsl").to_str().unwrap(), - PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), - PathBuf::new().join("utils").join("stuff2.glsl").to_str().unwrap(), - PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), - PathBuf::new().join("final.fsh").to_str().unwrap(), - PathBuf::new().join("lib").join("matrices.glsl").to_str().unwrap(), - PathBuf::new().join("final.fsh").to_str().unwrap(), - ] { - let path = tmp_path.clone(); - //path.f - truth = truth.replacen("!!", &path.join("shaders").join(file).to_str().unwrap().replace('\\', "\\\\"), 1); - } - - assert_eq!(result, truth); -} - -#[test] -fn test_nvidia_diagnostics() { - let mut mockgl = opengl::MockShaderValidator::new(); - mockgl.expect_vendor().returning(|| "NVIDIA Corporation".into()); - let server = new_temp_server(Some(Box::new(mockgl))); - - let output = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; - - let results = diagnostics_parser::parse_diagnostics_output( - output.to_string(), - &PathBuf::from_str("/home/noah/.minecraft/shaderpacks/test").unwrap(), - server.opengl_context.as_ref(), - ); - - assert_eq!(results.len(), 1); - let first = results.into_iter().next().unwrap(); - assert_eq!( - first.0, - url::Url::from_file_path("/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh").unwrap() - ); - server.endpoint.request_shutdown(); -} - -#[test] -fn test_amd_diagnostics() { - let mut mockgl = opengl::MockShaderValidator::new(); - mockgl.expect_vendor().returning(|| "ATI Technologies".into()); - let server = new_temp_server(Some(Box::new(mockgl))); - - let output = "ERROR: 0:1: '' : syntax error: #line -ERROR: 0:10: '' : syntax error: #line -ERROR: 0:15: 'varying' : syntax error: syntax error -"; - - let results = diagnostics_parser::parse_diagnostics_output( - output.to_string(), - &PathBuf::from_str("/home/test").unwrap(), - server.opengl_context.as_ref(), - ); - assert_eq!(results.len(), 1); - let first = results.into_iter().next().unwrap(); - assert_eq!(first.1.len(), 3); - server.endpoint.request_shutdown(); -} From b4a0636d43606c1f49448611461bcc0e0b1abafa Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 25 Mar 2022 01:29:01 +0000 Subject: [PATCH 33/56] replace (NodeIndex, Option) with FilialTuple globally --- server/src/commands/merged_includes.rs | 5 +- server/src/dfs.rs | 6 +- server/src/main.rs | 21 +++--- server/src/merge_views.rs | 93 +++++++++++--------------- 4 files changed, 58 insertions(+), 67 deletions(-) diff --git a/server/src/commands/merged_includes.rs b/server/src/commands/merged_includes.rs index 94dcf77..2f9a185 100644 --- a/server/src/commands/merged_includes.rs +++ b/server/src/commands/merged_includes.rs @@ -14,6 +14,7 @@ use anyhow::{format_err, Result}; use std::fs; use crate::dfs; +use crate::merge_views::FilialTuple; use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJson}; use super::Invokeable; @@ -36,7 +37,7 @@ impl VirtualMergedDocument { Ok(Some(roots)) } - pub fn get_dfs_for_node(&self, root: NodeIndex) -> Result)>, dfs::error::CycleError> { + pub fn get_dfs_for_node(&self, root: NodeIndex) -> Result, dfs::error::CycleError> { let graph_ref = self.graph.borrow(); let dfs = dfs::Dfs::new(&graph_ref, root); @@ -44,7 +45,7 @@ impl VirtualMergedDocument { dfs.collect::, _>>() } - pub fn load_sources(&self, nodes: &[(NodeIndex, Option)]) -> Result> { + pub fn load_sources(&self, nodes: &[FilialTuple]) -> Result> { let mut sources = HashMap::new(); for node in nodes { diff --git a/server/src/dfs.rs b/server/src/dfs.rs index 363808e..acb1c39 100644 --- a/server/src/dfs.rs +++ b/server/src/dfs.rs @@ -1,6 +1,6 @@ use petgraph::stable_graph::NodeIndex; -use crate::graph::CachedStableGraph; +use crate::{graph::CachedStableGraph, merge_views::FilialTuple}; use anyhow::Result; @@ -51,9 +51,9 @@ impl<'a> Dfs<'a> { } impl<'a> Iterator for Dfs<'a> { - type Item = Result<(NodeIndex, Option), error::CycleError>; + type Item = Result; - fn next(&mut self) -> Option), error::CycleError>> { + fn next(&mut self) -> Option> { let parent = self.cycle.last().map(|p| p.node); if let Some(node) = self.stack.pop() { diff --git a/server/src/main.rs b/server/src/main.rs index 25bd1c8..7dcf249 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -1,3 +1,4 @@ +use merge_views::FilialTuple; use rust_lsp::jsonrpc::{method_types::*, *}; use rust_lsp::lsp::*; use rust_lsp::lsp_types::{notification::*, *}; @@ -47,8 +48,8 @@ mod graph; mod logging; mod lsp_ext; mod merge_views; -mod opengl; mod navigation; +mod opengl; mod url_norm; #[cfg(test)] @@ -419,7 +420,7 @@ impl MinecraftShaderLanguageServer { Ok(diagnostics) } - pub fn get_dfs_for_node(&self, root: NodeIndex) -> Result)>, dfs::error::CycleError> { + pub fn get_dfs_for_node(&self, root: NodeIndex) -> Result, dfs::error::CycleError> { let graph_ref = self.graph.borrow(); let dfs = dfs::Dfs::new(&graph_ref, root); @@ -427,7 +428,7 @@ impl MinecraftShaderLanguageServer { dfs.collect::>() } - pub fn load_sources(&self, nodes: &[(NodeIndex, Option)]) -> Result> { + pub fn load_sources(&self, nodes: &[FilialTuple]) -> Result> { let mut sources = HashMap::new(); for node in nodes { @@ -675,13 +676,15 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { let parser = &mut self.tree_sitter.borrow_mut(); let parser_ctx = match navigation::ParserContext::new(parser, params.text_document.uri.clone()) { Ok(ctx) => ctx, - Err(e) => return completable.complete(Err(MethodError{ - code: 42069, - message: format!("error building parser context: {}", e), - data: (), - })), + Err(e) => { + return completable.complete(Err(MethodError { + code: 42069, + message: format!("error building parser context: {}", e), + data: (), + })) + } }; - + match parser_ctx.find_definitions(params.text_document.uri, params.position) { Ok(locations) => completable.complete(Ok(locations)), Err(e) => completable.complete(Err(MethodError { diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index 4a24065..5986a84 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -11,28 +11,22 @@ use petgraph::stable_graph::NodeIndex; use crate::graph::CachedStableGraph; -/// FilialTuple represents a tuple with a parent at index 0 -/// and a child at index 1. Parent can be nullable in the case of +/// FilialTuple represents a tuple with a child at index 0 +/// and a parent at index 1. Parent can be nullable in the case of /// the child being a top level node in the tree. -#[derive(PartialEq, Eq, Hash)] -struct FilialTuple(Option, NodeIndex); +pub type FilialTuple = (NodeIndex, Option); -impl From<(Option<&NodeIndex>, NodeIndex)> for FilialTuple { - fn from(tuple: (Option<&NodeIndex>, NodeIndex)) -> Self { - FilialTuple(tuple.0.copied(), tuple.1) - } -} - -pub fn generate_merge_list<'a>( - nodes: &'a [(NodeIndex, Option)], sources: &'a HashMap, graph: &'a CachedStableGraph, -) -> String { - let mut line_directives: Vec = Vec::new(); +pub fn generate_merge_list<'a>(nodes: &'a [FilialTuple], sources: &'a HashMap, graph: &'a CachedStableGraph) -> String { + // contains additionally inserted lines such as #line and other directives, preamble defines etc + let mut extra_lines: Vec = Vec::new(); + extra_lines.reserve((nodes.len() * 2) + 2); // list of source code views onto the below sources let mut merge_list: LinkedList<&'a str> = LinkedList::new(); - line_directives.reserve(nodes.len() * 2); - + // holds the offset into the child which has been added to the merge list for a parent. + // A child can have multiple parents for a given tree, hence we have to track it for + // a (child, parent) tuple instead of just the child. let mut last_offset_set: HashMap = HashMap::new(); let mut nodes_iter = nodes.iter().peekable(); @@ -41,7 +35,7 @@ pub fn generate_merge_list<'a>( let first = nodes_iter.next().unwrap().0; let first_path = graph.get_node(first); - last_offset_set.insert(FilialTuple(None, first), 0); + last_offset_set.insert((first, None), 0); // stack to keep track of the depth first traversal let mut stack = VecDeque::::new(); @@ -52,12 +46,12 @@ pub fn generate_merge_list<'a>( &mut last_offset_set, graph, sources, - &mut line_directives, + &mut extra_lines, &mut stack, ); // now we add a view of the remainder of the root file - let offset = *last_offset_set.get(&FilialTuple(None, first)).unwrap(); + let offset = *last_offset_set.get(&(first, None)).unwrap(); let len = sources.get(&first_path).unwrap().len(); merge_list.push_back(&sources.get(&first_path).unwrap()[min(offset, len)..]); @@ -65,17 +59,14 @@ pub fn generate_merge_list<'a>( let total_len = merge_list.iter().fold(0, |a, b| a + b.len()); let mut merged = String::with_capacity(total_len); - for slice in merge_list { - merged.push_str(slice); - } + merged.extend(merge_list); merged } fn create_merge_views<'a>( - nodes: &mut Peekable)>>, merge_list: &mut LinkedList<&'a str>, - last_offset_set: &mut HashMap, graph: &'a CachedStableGraph, sources: &'a HashMap, - line_directives: &mut Vec, stack: &mut VecDeque, + nodes: &mut Peekable>, merge_list: &mut LinkedList<&'a str>, last_offset_set: &mut HashMap, + graph: &'a CachedStableGraph, sources: &'a HashMap, extra_lines: &mut Vec, stack: &mut VecDeque, ) { loop { let n = match nodes.next() { @@ -94,10 +85,10 @@ fn create_merge_views<'a>( let (char_for_line, char_following_line) = char_offset_for_line(edge.line, parent_source); let offset = *last_offset_set - .insert((stack.back(), parent).into(), char_following_line) + .insert((parent, stack.back().copied()), char_following_line) .get_or_insert(0); merge_list.push_back(&parent_source[offset..char_for_line]); - add_opening_line_directive(&child_path, merge_list, line_directives); + add_opening_line_directive(&child_path, merge_list, extra_lines); match nodes.peek() { Some(next) => { @@ -113,9 +104,9 @@ fn create_merge_views<'a>( } }; merge_list.push_back(&child_source[..offset]); - last_offset_set.insert(FilialTuple(Some(parent), child), 0); + last_offset_set.insert((child, Some(parent)), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, merge_list, line_directives); + add_closing_line_directive(edge.line + 2, &parent_path, merge_list, extra_lines); // if the next pair's parent is not the current pair's parent, we need to bubble up if stack.contains(&next.1.unwrap()) { return; @@ -124,26 +115,24 @@ fn create_merge_views<'a>( } stack.push_back(parent); - create_merge_views(nodes, merge_list, last_offset_set, graph, sources, line_directives, stack); + create_merge_views(nodes, merge_list, last_offset_set, graph, sources, extra_lines, stack); stack.pop_back(); - let offset = *last_offset_set.get(&FilialTuple(Some(parent), child)).unwrap(); + let offset = *last_offset_set.get(&(child, Some(parent))).unwrap(); let child_source = sources.get(&child_path).unwrap(); // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 - let end_offset = { - match child_source.ends_with('\n') { - true => 1, /* child_source.len()-1 */ - false => 0, /* child_source.len() */ - } + let end_offset = match child_source.ends_with('\n') { + true => 1, /* child_source.len()-1 */ + false => 0, /* child_source.len() */ }; if offset < child_source.len() - end_offset { // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad merge_list.push_back(&child_source[offset../* std::cmp::max( */child_source.len()-end_offset/* , offset) */]); - last_offset_set.insert(FilialTuple(Some(parent), child), 0); + last_offset_set.insert((child, Some(parent)), 0); } // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, merge_list, line_directives); + add_closing_line_directive(edge.line + 2, &parent_path, merge_list, extra_lines); // we need to check the next item at the point of original return further down the callstack if nodes.peek().is_some() && stack.contains(&nodes.peek().unwrap().1.unwrap()) { @@ -153,16 +142,14 @@ fn create_merge_views<'a>( None => { let child_source = sources.get(&child_path).unwrap(); // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad - let offset = { - match child_source.ends_with('\n') { - true => child_source.len() - 1, - false => child_source.len(), - } + let offset = match child_source.ends_with('\n') { + true => child_source.len() - 1, + false => child_source.len(), }; merge_list.push_back(&child_source[..offset]); - last_offset_set.insert(FilialTuple(Some(parent), child), 0); + last_offset_set.insert((child, Some(parent)), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, merge_list, line_directives); + add_closing_line_directive(edge.line + 2, &parent_path, merge_list, extra_lines); } } } @@ -184,13 +171,13 @@ fn char_offset_for_line(line_num: usize, source: &str) -> (usize, usize) { (char_for_line, char_following_line) } -fn add_opening_line_directive(path: &Path, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { +fn add_opening_line_directive(path: &Path, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec) { let line_directive = format!("#line 1 \"{}\"\n", path.to_str().unwrap().replace('\\', "\\\\")); - line_directives.push(line_directive); - unsafe_get_and_insert(merge_list, line_directives); + extra_lines.push(line_directive); + unsafe_get_and_insert(merge_list, extra_lines); } -fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedList<&str>, line_directives: &mut Vec) { +fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec) { // Optifine doesn't seem to add a leading newline if the previous line was a #line directive let line_directive = if let Some(l) = merge_list.back() { if l.trim().starts_with("#line") { @@ -202,14 +189,14 @@ fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedL format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) }; - line_directives.push(line_directive); - unsafe_get_and_insert(merge_list, line_directives); + extra_lines.push(line_directive); + unsafe_get_and_insert(merge_list, extra_lines); } -fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, line_directives: &[String]) { +fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, extra_lines: &[String]) { // :^) unsafe { - let vec_ptr_offset = line_directives.as_ptr().add(line_directives.len() - 1); + let vec_ptr_offset = extra_lines.as_ptr().add(extra_lines.len() - 1); merge_list.push_back(&vec_ptr_offset.as_ref().unwrap()[..]); } } From cb7c9b8b492abaf72de3cef23d0f801cd9313ad0 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Fri, 25 Mar 2022 01:30:48 +0000 Subject: [PATCH 34/56] (probably for AMD) enable 'GL_GOOGLE_cpp_style_line_directive' in preamble --- server/src/merge_views.rs | 60 ++++++++++++++++++++++++++++-- server/testdata/01/final.fsh.merge | 2 + server/testdata/02/final.fsh.merge | 2 + server/testdata/03/final.fsh.merge | 2 + server/testdata/04/final.fsh.merge | 2 + server/testdata/05/final.fsh.merge | 2 + 6 files changed, 67 insertions(+), 3 deletions(-) diff --git a/server/src/merge_views.rs b/server/src/merge_views.rs index 5986a84..e1f6f4a 100644 --- a/server/src/merge_views.rs +++ b/server/src/merge_views.rs @@ -34,8 +34,20 @@ pub fn generate_merge_list<'a>(nodes: &'a [FilialTuple], sources: &'a HashMap::new(); @@ -53,8 +65,8 @@ pub fn generate_merge_list<'a>(nodes: &'a [FilialTuple], sources: &'a HashMap (usize, usize) { (char_for_line, char_following_line) } +fn find_version_offset(source: &str) -> usize { + source + .lines() + .enumerate() + .find(|(_, line)| line.starts_with("#version ")) + .map_or(0, |(i, _)| i) +} + +fn add_preamble<'a>( + version_line_offset: usize, version_char_offset: usize, path: &str, source: &'a str, merge_list: &mut LinkedList<&'a str>, + extra_lines: &mut Vec, +) { + // TODO: Optifine #define preabmle + merge_list.push_back(&source[..version_char_offset]); + let google_line_directive = format!( + "#extension GL_GOOGLE_cpp_style_line_directive : enable\n#line {} \"{}\"\n", + // +2 because 0 indexed but #line is 1 indexed and references the *following* line + version_line_offset + 2, + path, + ); + extra_lines.push(google_line_directive); + unsafe_get_and_insert(merge_list, extra_lines); +} + fn add_opening_line_directive(path: &Path, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec) { let line_directive = format!("#line 1 \"{}\"\n", path.to_str().unwrap().replace('\\', "\\\\")); extra_lines.push(line_directive); @@ -242,6 +278,11 @@ mod merge_view_test { let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); truth = truth.replacen( "!!", &tmp_path.join("shaders").join("common.glsl").to_str().unwrap().replace('\\', "\\\\"), @@ -306,6 +347,12 @@ mod merge_view_test { let mut truth = fs::read_to_string(merge_file).unwrap(); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); + for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { let path = tmp_path.clone(); truth = truth.replacen( @@ -380,6 +427,12 @@ mod merge_view_test { let mut truth = fs::read_to_string(merge_file).unwrap(); + truth = truth.replacen( + "!!", + &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + 1, + ); + for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { let path = tmp_path.clone(); truth = truth.replacen( @@ -464,6 +517,7 @@ mod merge_view_test { let mut truth = fs::read_to_string(merge_file).unwrap(); for file in &[ + PathBuf::new().join("final.fsh").to_str().unwrap(), PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), PathBuf::new().join("utils").join("stuff1.glsl").to_str().unwrap(), PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), diff --git a/server/testdata/01/final.fsh.merge b/server/testdata/01/final.fsh.merge index 609a754..f6cdd6e 100644 --- a/server/testdata/01/final.fsh.merge +++ b/server/testdata/01/final.fsh.merge @@ -1,4 +1,6 @@ #version 120 +#extension GL_GOOGLE_cpp_style_line_directive : enable +#line 2 "!!" #line 1 "!!" float test() { diff --git a/server/testdata/02/final.fsh.merge b/server/testdata/02/final.fsh.merge index 550f1d0..78c9367 100644 --- a/server/testdata/02/final.fsh.merge +++ b/server/testdata/02/final.fsh.merge @@ -1,4 +1,6 @@ #version 120 +#extension GL_GOOGLE_cpp_style_line_directive : enable +#line 2 "!!" #line 1 "!!" int sample() { diff --git a/server/testdata/03/final.fsh.merge b/server/testdata/03/final.fsh.merge index 4277745..a328117 100644 --- a/server/testdata/03/final.fsh.merge +++ b/server/testdata/03/final.fsh.merge @@ -1,4 +1,6 @@ #version 120 +#extension GL_GOOGLE_cpp_style_line_directive : enable +#line 2 "!!" #line 1 "!!" int sample() { diff --git a/server/testdata/04/final.fsh.merge b/server/testdata/04/final.fsh.merge index ff93439..47d97af 100644 --- a/server/testdata/04/final.fsh.merge +++ b/server/testdata/04/final.fsh.merge @@ -1,4 +1,6 @@ #version 120 +#extension GL_GOOGLE_cpp_style_line_directive : enable +#line 2 "!!" #line 1 "!!" #line 1 "!!" diff --git a/server/testdata/05/final.fsh.merge b/server/testdata/05/final.fsh.merge index 1d44edf..724eb5a 100644 --- a/server/testdata/05/final.fsh.merge +++ b/server/testdata/05/final.fsh.merge @@ -1,4 +1,6 @@ #version 120 +#extension GL_GOOGLE_cpp_style_line_directive : enable +#line 2 "!!" #line 1 "!!" float test() { From d3365c3bff01a19f2c6545d9dac5cca5f1a67e61 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 3 Apr 2022 21:31:18 +0100 Subject: [PATCH 35/56] big heckin reworkerino to use the standard #line directive as per spec --- server/Cargo.lock | 63 ++---- server/Cargo.toml | 46 +---- server/Makefile | 2 +- server/logging/Cargo.toml | 13 ++ server/{src/logging.rs => logging/src/lib.rs} | 11 +- server/logging_macro/Cargo.toml | 12 ++ server/logging_macro/src/lib.rs | 24 +++ server/main/Cargo.toml | 35 ++++ server/{ => main}/src/commands/graph_dot.rs | 0 .../src/commands/merged_includes.rs | 4 +- server/{ => main}/src/commands/mod.rs | 0 server/{ => main}/src/commands/parse_tree.rs | 0 server/{ => main}/src/configuration.rs | 0 server/{ => main}/src/consts.rs | 0 server/{ => main}/src/dfs.rs | 2 + server/main/src/diagnostics_parser.rs | 194 ++++++++++++++++++ server/{ => main}/src/graph.rs | 2 + server/{ => main}/src/lsp_ext.rs | 0 server/{ => main}/src/main.rs | 54 +++-- server/{ => main}/src/merge_views.rs | 167 ++++++++++----- server/{ => main}/src/navigation.rs | 4 +- server/{ => main}/src/opengl.rs | 15 +- server/main/src/source_mapper.rs | 52 +++++ server/{ => main}/src/test.rs | 10 +- server/{ => main}/src/url_norm.rs | 0 server/{ => main}/testdata/01/common.glsl | 0 server/{ => main}/testdata/01/final.fsh | 0 server/main/testdata/01/final.fsh.merge | 11 + server/{ => main}/testdata/02/final.fsh | 0 server/{ => main}/testdata/02/final.fsh.merge | 14 +- .../{ => main}/testdata/02/utils/burger.glsl | 0 .../{ => main}/testdata/02/utils/sample.glsl | 0 server/{ => main}/testdata/02/utils/test.glsl | 0 server/{ => main}/testdata/03/final.fsh | 0 server/{ => main}/testdata/03/final.fsh.merge | 14 +- .../{ => main}/testdata/03/utils/burger.glsl | 0 .../{ => main}/testdata/03/utils/sample.glsl | 0 server/{ => main}/testdata/03/utils/test.glsl | 0 server/{ => main}/testdata/04/final.fsh | 0 server/main/testdata/04/final.fsh.merge | 23 +++ .../{ => main}/testdata/04/lib/matrices.glsl | 0 .../{ => main}/testdata/04/utils/stuff1.glsl | 0 .../{ => main}/testdata/04/utils/stuff2.glsl | 0 .../testdata/04/utils/utilities.glsl | 0 server/{ => main}/testdata/05/common.glsl | 0 server/{ => main}/testdata/05/final.fsh | 0 server/{ => main}/testdata/05/final.fsh.merge | 0 .../{ => main}/testdata/05/test/banana.glsl | 0 .../{ => main}/testdata/05/test/burger.glsl | 0 server/src/diagnostics_parser.rs | 162 --------------- server/testdata/01/final.fsh.merge | 13 -- server/testdata/04/final.fsh.merge | 25 --- 52 files changed, 574 insertions(+), 398 deletions(-) create mode 100644 server/logging/Cargo.toml rename server/{src/logging.rs => logging/src/lib.rs} (92%) create mode 100644 server/logging_macro/Cargo.toml create mode 100644 server/logging_macro/src/lib.rs create mode 100644 server/main/Cargo.toml rename server/{ => main}/src/commands/graph_dot.rs (100%) rename server/{ => main}/src/commands/merged_includes.rs (95%) rename server/{ => main}/src/commands/mod.rs (100%) rename server/{ => main}/src/commands/parse_tree.rs (100%) rename server/{ => main}/src/configuration.rs (100%) rename server/{ => main}/src/consts.rs (100%) rename server/{ => main}/src/dfs.rs (99%) create mode 100644 server/main/src/diagnostics_parser.rs rename server/{ => main}/src/graph.rs (99%) rename server/{ => main}/src/lsp_ext.rs (100%) rename server/{ => main}/src/main.rs (93%) rename server/{ => main}/src/merge_views.rs (81%) rename server/{ => main}/src/navigation.rs (94%) rename server/{ => main}/src/opengl.rs (88%) create mode 100644 server/main/src/source_mapper.rs rename server/{ => main}/src/test.rs (98%) rename server/{ => main}/src/url_norm.rs (100%) rename server/{ => main}/testdata/01/common.glsl (100%) rename server/{ => main}/testdata/01/final.fsh (100%) create mode 100644 server/main/testdata/01/final.fsh.merge rename server/{ => main}/testdata/02/final.fsh (100%) rename server/{ => main}/testdata/02/final.fsh.merge (57%) rename server/{ => main}/testdata/02/utils/burger.glsl (100%) rename server/{ => main}/testdata/02/utils/sample.glsl (100%) rename server/{ => main}/testdata/02/utils/test.glsl (100%) rename server/{ => main}/testdata/03/final.fsh (100%) rename server/{ => main}/testdata/03/final.fsh.merge (53%) rename server/{ => main}/testdata/03/utils/burger.glsl (100%) rename server/{ => main}/testdata/03/utils/sample.glsl (100%) rename server/{ => main}/testdata/03/utils/test.glsl (100%) rename server/{ => main}/testdata/04/final.fsh (100%) create mode 100644 server/main/testdata/04/final.fsh.merge rename server/{ => main}/testdata/04/lib/matrices.glsl (100%) rename server/{ => main}/testdata/04/utils/stuff1.glsl (100%) rename server/{ => main}/testdata/04/utils/stuff2.glsl (100%) rename server/{ => main}/testdata/04/utils/utilities.glsl (100%) rename server/{ => main}/testdata/05/common.glsl (100%) rename server/{ => main}/testdata/05/final.fsh (100%) rename server/{ => main}/testdata/05/final.fsh.merge (100%) rename server/{ => main}/testdata/05/test/banana.glsl (100%) rename server/{ => main}/testdata/05/test/burger.glsl (100%) delete mode 100644 server/src/diagnostics_parser.rs delete mode 100644 server/testdata/01/final.fsh.merge delete mode 100644 server/testdata/04/final.fsh.merge diff --git a/server/Cargo.lock b/server/Cargo.lock index 1e22ef2..5584513 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -61,21 +61,6 @@ version = "0.12.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3441f0f7b02788e948e47f457ca01f1d7e6d92c693bc132c22b087d3141c03ff" -[[package]] -name = "bit-set" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6e11e16035ea35e4e5997b393eacbf6f63983188f7a2ad25bfb13465f5ad59de" -dependencies = [ - "bit-vec", -] - -[[package]] -name = "bit-vec" -version = "0.6.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "349f9b6a179ed607305526ca489b34ad0a41aed5f7980fa90eb03160b69598fb" - [[package]] name = "bitflags" version = "1.2.1" @@ -131,15 +116,6 @@ dependencies = [ "libc", ] -[[package]] -name = "chan" -version = "0.1.23" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d14956a3dae065ffaa0d92ece848ab4ced88d32361e7fdfbfd653a5c454a1ed8" -dependencies = [ - "rand 0.3.23", -] - [[package]] name = "cocoa" version = "0.24.0" @@ -700,6 +676,26 @@ dependencies = [ "cfg-if 1.0.0", ] +[[package]] +name = "logging" +version = "0.9.5" +dependencies = [ + "lazy_static", + "rand 0.8.5", + "slog", + "slog-atomic", + "slog-scope", + "slog-term", +] + +[[package]] +name = "logging_macro" +version = "0.9.5" +dependencies = [ + "quote", + "syn", +] + [[package]] name = "lsp-types" version = "0.86.0" @@ -739,30 +735,25 @@ name = "mcshader-lsp" version = "0.9.5" dependencies = [ "anyhow", - "arc-swap", - "bit-set", - "chan", - "ctor", "fs_extra", "gl", "glutin", "hamcrest2", "lazy_static", + "logging", + "logging_macro", "mockall", "once_cell", "path-slash", "percent-encoding", "petgraph", "pretty_assertions", - "rand 0.8.5", "regex", "rust_lsp", "serde", "serde_json", "slog", - "slog-atomic", "slog-scope", - "slog-term", "tempdir", "thiserror", "tree-sitter", @@ -1205,16 +1196,6 @@ dependencies = [ "proc-macro2", ] -[[package]] -name = "rand" -version = "0.3.23" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64ac302d8f83c0c1974bf758f6b041c6c8ada916fbb44a609158ca8b064cc76c" -dependencies = [ - "libc", - "rand 0.4.6", -] - [[package]] name = "rand" version = "0.4.6" diff --git a/server/Cargo.toml b/server/Cargo.toml index 1e02ff5..533392d 100644 --- a/server/Cargo.toml +++ b/server/Cargo.toml @@ -1,40 +1,6 @@ -[package] -name = "mcshader-lsp" -version = "0.9.5" -authors = ["Noah Santschi-Cooney "] -edition = "2021" - -[dependencies] -rust_lsp = { git = "https://github.com/Strum355/RustLSP", branch = "master" } -serde_json = "1.0" -serde = "1.0" -walkdir = "2.3" -petgraph = "0.6" -lazy_static = "1.4" -regex = "1.4" -chan = "0.1" -url = "2.2" -percent-encoding = "2.1" -anyhow = "1.0" -bit-set = "0.5" -thiserror = "1.0" -glutin = "0.28" -gl = "0.14" -ctor = "0.1" -mockall = "0.11" -path-slash = "0.1" -slog = { version = "2.7", features = [ "max_level_trace", "release_max_level_trace" ] } -slog-term = "2.9" -slog-scope = "4.4" -slog-atomic = "3.1" -once_cell = "1.7" -rand = "0.8" -arc-swap = "1.5.0" -tree-sitter = "0.20.6" -tree-sitter-glsl = "0.1.2" - -[dev-dependencies] -tempdir = "0.3" -fs_extra = "1.2" -hamcrest2 = "*" -pretty_assertions = "1.1" \ No newline at end of file +[workspace] +members = [ + "main", + "logging", + "logging_macro" +] \ No newline at end of file diff --git a/server/Makefile b/server/Makefile index 509b9af..867c64c 100644 --- a/server/Makefile +++ b/server/Makefile @@ -4,7 +4,7 @@ watchtest: RUST_BACKTRACE=0 cargo watch -x test -i Makefile test: - RUST_LIB_BACKTRACE=0 RUST_BACKTRACE=0 cargo test + RUST_LIB_BACKTRACE=0 RUST_BACKTRACE=0 cargo test -- --nocapture --color always build: cargo build diff --git a/server/logging/Cargo.toml b/server/logging/Cargo.toml new file mode 100644 index 0000000..0254091 --- /dev/null +++ b/server/logging/Cargo.toml @@ -0,0 +1,13 @@ +[package] +name = "logging" +version = "0.9.5" +authors = ["Noah Santschi-Cooney "] +edition = "2021" + +[dependencies] +slog = { version = "2.7", features = [ "max_level_trace", "release_max_level_trace" ] } +slog-term = "2.9" +slog-scope = "4.4" +slog-atomic = "3.1" +rand = "0.8" +lazy_static = "1.4" \ No newline at end of file diff --git a/server/src/logging.rs b/server/logging/src/lib.rs similarity index 92% rename from server/src/logging.rs rename to server/logging/src/lib.rs index cbdb3ca..36d7f53 100644 --- a/server/src/logging.rs +++ b/server/logging/src/lib.rs @@ -2,7 +2,10 @@ use rand::{rngs, Rng}; use slog::slog_o; use slog_scope::GlobalLoggerGuard; use slog_term::{FullFormat, PlainSyncDecorator}; -use std::{cell::RefCell, io::Stderr, sync::Arc}; +use std::{cell::RefCell, sync::Arc}; + +use std::io::Stderr; + use lazy_static::lazy_static; use slog::*; use slog_atomic::*; @@ -13,9 +16,7 @@ fn new_trace_id() -> String { } pub fn slog_with_trace_id(f: F) { - slog_scope::scope(&slog_scope::logger().new(slog_o!("trace" => new_trace_id())), || { - f() - }) + slog_scope::scope(&slog_scope::logger().new(slog_o!("trace" => new_trace_id())), f) } pub fn set_logger_with_level(level: Level) -> GlobalLoggerGuard { @@ -39,4 +40,4 @@ lazy_static! { let logger = logger_base(Level::Info).fuse(); AtomicSwitch::new(logger) }; -} \ No newline at end of file +} diff --git a/server/logging_macro/Cargo.toml b/server/logging_macro/Cargo.toml new file mode 100644 index 0000000..fdf9b43 --- /dev/null +++ b/server/logging_macro/Cargo.toml @@ -0,0 +1,12 @@ +[package] +name = "logging_macro" +version = "0.9.5" +authors = ["Noah Santschi-Cooney "] +edition = "2021" + +[lib] +proc-macro = true + +[dependencies] +quote = "1.0" +syn = { version = "1.0", features = [ "full" ] } \ No newline at end of file diff --git a/server/logging_macro/src/lib.rs b/server/logging_macro/src/lib.rs new file mode 100644 index 0000000..99052bb --- /dev/null +++ b/server/logging_macro/src/lib.rs @@ -0,0 +1,24 @@ +use proc_macro::TokenStream; +use quote::quote; +use syn::{parse_macro_input, parse_quote, ItemFn}; + +#[proc_macro_attribute] +pub fn log_scope(_args: TokenStream, function: TokenStream) -> TokenStream { + let mut function = parse_macro_input!(function as ItemFn); + + let function_name = function.sig.ident.to_string(); + + let stmts = function.block.stmts; + + function.block = Box::new(parse_quote!({ + use slog::{slog_o, FnValue, Level}; + use std::thread::current; + + let _guard = logging::set_logger_with_level(Level::Trace); + slog_scope::scope(&slog_scope::logger().new(slog_o!("test_name" => #function_name, "thread_num" => FnValue(|_| format!("{:?}", current().id())))), || { + #(#stmts)* + }); + })); + + TokenStream::from(quote!(#function)) +} diff --git a/server/main/Cargo.toml b/server/main/Cargo.toml new file mode 100644 index 0000000..18cc1dd --- /dev/null +++ b/server/main/Cargo.toml @@ -0,0 +1,35 @@ +[package] +name = "mcshader-lsp" +version = "0.9.5" +authors = ["Noah Santschi-Cooney "] +edition = "2021" + +[dependencies] +rust_lsp = { git = "https://github.com/Strum355/RustLSP", branch = "master" } +serde_json = "1.0" +serde = "1.0" +walkdir = "2.3" +petgraph = "0.6" +lazy_static = "1.4" +regex = "1.4" +url = "2.2" +percent-encoding = "2.1" +anyhow = "1.0" +thiserror = "1.0" +glutin = "0.28" +gl = "0.14" +mockall = "0.11" +path-slash = "0.1" +slog = { version = "2.7", features = [ "max_level_trace", "release_max_level_trace" ] } +slog-scope = "4.4" +once_cell = "1.7" +tree-sitter = "0.20.6" +tree-sitter-glsl = "0.1.2" +logging = { path = "../logging" } +logging_macro = { path = "../logging_macro" } + +[dev-dependencies] +tempdir = "0.3" +fs_extra = "1.2" +hamcrest2 = "*" +pretty_assertions = "1.1" \ No newline at end of file diff --git a/server/src/commands/graph_dot.rs b/server/main/src/commands/graph_dot.rs similarity index 100% rename from server/src/commands/graph_dot.rs rename to server/main/src/commands/graph_dot.rs diff --git a/server/src/commands/merged_includes.rs b/server/main/src/commands/merged_includes.rs similarity index 95% rename from server/src/commands/merged_includes.rs rename to server/main/src/commands/merged_includes.rs index 2f9a185..3c9fea8 100644 --- a/server/src/commands/merged_includes.rs +++ b/server/main/src/commands/merged_includes.rs @@ -15,6 +15,7 @@ use std::fs; use crate::dfs; use crate::merge_views::FilialTuple; +use crate::source_mapper::SourceMapper; use crate::{graph::CachedStableGraph, merge_views, url_norm::FromJson}; use super::Invokeable; @@ -100,8 +101,9 @@ impl Invokeable for VirtualMergedDocument { }; all_sources.extend(sources); + let mut source_mapper = SourceMapper::new(all_sources.len()); let graph = self.graph.borrow(); - let view = merge_views::generate_merge_list(&tree, &all_sources, &graph); + let view = merge_views::generate_merge_list(&tree, &all_sources, &graph, &mut source_mapper); return Ok(serde_json::value::Value::String(view)); } return Err(format_err!( diff --git a/server/src/commands/mod.rs b/server/main/src/commands/mod.rs similarity index 100% rename from server/src/commands/mod.rs rename to server/main/src/commands/mod.rs diff --git a/server/src/commands/parse_tree.rs b/server/main/src/commands/parse_tree.rs similarity index 100% rename from server/src/commands/parse_tree.rs rename to server/main/src/commands/parse_tree.rs diff --git a/server/src/configuration.rs b/server/main/src/configuration.rs similarity index 100% rename from server/src/configuration.rs rename to server/main/src/configuration.rs diff --git a/server/src/consts.rs b/server/main/src/consts.rs similarity index 100% rename from server/src/consts.rs rename to server/main/src/consts.rs diff --git a/server/src/dfs.rs b/server/main/src/dfs.rs similarity index 99% rename from server/src/dfs.rs rename to server/main/src/dfs.rs index acb1c39..dfba565 100644 --- a/server/src/dfs.rs +++ b/server/main/src/dfs.rs @@ -166,6 +166,7 @@ mod dfs_test { use crate::{dfs, IncludePosition}; #[test] + #[logging_macro::log_scope] fn test_graph_dfs() { { let mut graph = CachedStableGraph::new(); @@ -272,6 +273,7 @@ mod dfs_test { } #[test] + #[logging_macro::log_scope] fn test_graph_dfs_cycle() { { let mut graph = CachedStableGraph::new(); diff --git a/server/main/src/diagnostics_parser.rs b/server/main/src/diagnostics_parser.rs new file mode 100644 index 0000000..df2f20b --- /dev/null +++ b/server/main/src/diagnostics_parser.rs @@ -0,0 +1,194 @@ +use std::{collections::HashMap, lazy::OnceCell, path::Path}; + +use regex::Regex; +use rust_lsp::lsp_types::{Diagnostic, DiagnosticSeverity, Position, Range}; +use slog_scope::debug; +use url::Url; + +use crate::{ + consts, + graph::CachedStableGraph, + opengl, + source_mapper::{SourceMapper, SourceNum}, +}; + +pub struct DiagnosticsParser<'a, T: opengl::ShaderValidator + ?Sized> { + line_offset: OnceCell, + line_regex: OnceCell, + vendor_querier: &'a T, +} + +impl<'a, T: opengl::ShaderValidator + ?Sized> DiagnosticsParser<'a, T> { + pub fn new(vendor_querier: &'a T) -> Self { + DiagnosticsParser { + line_offset: OnceCell::new(), + line_regex: OnceCell::new(), + vendor_querier, + } + } + + fn get_line_regex(&self) -> &Regex { + self.line_regex.get_or_init(|| match self.vendor_querier.vendor().as_str() { + "NVIDIA Corporation" => { + Regex::new(r#"^(?P\d+)\((?P\d+)\) : (?Perror|warning) [A-C]\d+: (?P.+)"#).unwrap() + } + _ => Regex::new(r#"^(?PERROR|WARNING): (?P[^?<>*|"\n]+):(?P\d+): '[a-z]*' : (?P.+)$"#) + .unwrap(), + }) + } + + fn get_line_offset(&self) -> u32 { + *self.line_offset.get_or_init(|| match self.vendor_querier.vendor().as_str() { + "ATI Technologies" => 0, + _ => 2, + }) + } + + pub fn parse_diagnostics_output( + &self, output: String, uri: &Path, source_mapper: &SourceMapper, graph: &CachedStableGraph, + ) -> HashMap> { + let output_lines = output.split('\n').collect::>(); + let mut diagnostics: HashMap> = HashMap::with_capacity(output_lines.len()); + + debug!("diagnostics regex selected"; "regex" => self.get_line_regex() .as_str()); + + for line in output_lines { + let diagnostic_capture = match self.get_line_regex().captures(line) { + Some(d) => d, + None => continue, + }; + + debug!("found match for output line"; "line" => line, "capture" => format!("{:?}", diagnostic_capture)); + + let msg = diagnostic_capture.name("output").unwrap().as_str(); + + let line = match diagnostic_capture.name("linenum") { + Some(c) => c.as_str().parse::().unwrap_or(0), + None => 0, + } - self.get_line_offset(); + + // TODO: line matching maybe + /* let line_text = source_lines[line as usize]; + let leading_whitespace = line_text.len() - line_text.trim_start().len(); */ + + let severity = match diagnostic_capture.name("severity") { + Some(c) => match c.as_str().to_lowercase().as_str() { + "error" => DiagnosticSeverity::Error, + "warning" => DiagnosticSeverity::Warning, + _ => DiagnosticSeverity::Information, + }, + _ => DiagnosticSeverity::Information, + }; + + let origin = match diagnostic_capture.name("filepath") { + Some(o) => { + let source_num: SourceNum = o.as_str().parse::().unwrap().into(); + let graph_node = source_mapper.get_node(source_num); + graph.get_node(graph_node).to_str().unwrap().to_string() + } + None => uri.to_str().unwrap().to_string(), + }; + + let diagnostic = Diagnostic { + range: Range::new( + /* Position::new(line, leading_whitespace as u64), + Position::new(line, line_text.len() as u64) */ + Position::new(line, 0), + Position::new(line, 1000), + ), + code: None, + severity: Some(severity), + source: Some(consts::SOURCE.into()), + message: msg.trim().into(), + related_information: None, + tags: None, + code_description: Option::None, + data: Option::None, + }; + + let origin_url = Url::from_file_path(origin).unwrap(); + match diagnostics.get_mut(&origin_url) { + Some(d) => d.push(diagnostic), + None => { + diagnostics.insert(origin_url, vec![diagnostic]); + } + }; + } + diagnostics + } +} + +#[cfg(test)] +mod diagnostics_test { + use std::path::PathBuf; + + use slog::{slog_o, Level}; + use url::Url; + + use crate::{ + diagnostics_parser::DiagnosticsParser, opengl::MockShaderValidator, source_mapper::SourceMapper, test::new_temp_server, + }; + + #[test] + #[logging_macro::log_scope] + fn test_nvidia_diagnostics() { + slog_scope::scope(&slog_scope::logger().new(slog_o!("driver" => "nvidia")), || { + let mut mockgl = MockShaderValidator::new(); + mockgl.expect_vendor().returning(|| "NVIDIA Corporation".into()); + let server = new_temp_server(Some(Box::new(mockgl))); + + let output = "0(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; + + #[cfg(target_family = "unix")] + let path: PathBuf = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh".into(); + #[cfg(target_family = "windows")] + let path: PathBuf = "c:\\home\\noah\\.minecraft\\shaderpacks\\test\\shaders\\final.fsh".into(); + + let mut source_mapper = SourceMapper::new(0); + source_mapper.get_num(server.graph.borrow_mut().add_node(&path)); + + let parser = DiagnosticsParser::new(server.opengl_context.as_ref()); + + let results = + parser.parse_diagnostics_output(output.to_string(), path.parent().unwrap(), &source_mapper, &server.graph.borrow()); + + assert_eq!(results.len(), 1); + let first = results.into_iter().next().unwrap(); + assert_eq!(first.0, Url::from_file_path(path).unwrap()); + server.endpoint.request_shutdown(); + }); + } + + #[test] + #[logging_macro::log_scope] + fn test_amd_diagnostics() { + slog_scope::scope(&slog_scope::logger().new(slog_o!("driver" => "amd")), || { + let mut mockgl = MockShaderValidator::new(); + mockgl.expect_vendor().returning(|| "ATI Technologies".into()); + let server = new_temp_server(Some(Box::new(mockgl))); + + let output = "ERROR: 0:1: '' : syntax error: #line +ERROR: 0:10: '' : syntax error: #line +ERROR: 0:15: 'varying' : syntax error: syntax error +"; + + #[cfg(target_family = "unix")] + let path: PathBuf = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh".into(); + #[cfg(target_family = "windows")] + let path: PathBuf = "c:\\home\\noah\\.minecraft\\shaderpacks\\test\\shaders\\final.fsh".into(); + + let mut source_mapper = SourceMapper::new(0); + source_mapper.get_num(server.graph.borrow_mut().add_node(&path)); + + let parser = DiagnosticsParser::new(server.opengl_context.as_ref()); + + let results = + parser.parse_diagnostics_output(output.to_string(), path.parent().unwrap(), &source_mapper, &server.graph.borrow()); + + assert_eq!(results.len(), 1); + let first = results.into_iter().next().unwrap(); + assert_eq!(first.1.len(), 3); + server.endpoint.request_shutdown(); + }); + } +} diff --git a/server/src/graph.rs b/server/main/src/graph.rs similarity index 99% rename from server/src/graph.rs rename to server/main/src/graph.rs index 81f07c1..3891392 100644 --- a/server/src/graph.rs +++ b/server/main/src/graph.rs @@ -170,6 +170,7 @@ mod graph_test { use crate::{graph::CachedStableGraph, IncludePosition}; #[test] + #[logging_macro::log_scope] fn test_graph_two_connected_nodes() { let mut graph = CachedStableGraph::new(); @@ -211,6 +212,7 @@ mod graph_test { } #[test] + #[logging_macro::log_scope] fn test_collect_root_ancestors() { { let mut graph = CachedStableGraph::new(); diff --git a/server/src/lsp_ext.rs b/server/main/src/lsp_ext.rs similarity index 100% rename from server/src/lsp_ext.rs rename to server/main/src/lsp_ext.rs diff --git a/server/src/main.rs b/server/main/src/main.rs similarity index 93% rename from server/src/main.rs rename to server/main/src/main.rs index 7dcf249..ef0b0eb 100644 --- a/server/src/main.rs +++ b/server/main/src/main.rs @@ -1,3 +1,5 @@ +#![feature(once_cell)] + use merge_views::FilialTuple; use rust_lsp::jsonrpc::{method_types::*, *}; use rust_lsp::lsp::*; @@ -45,11 +47,11 @@ mod consts; mod dfs; mod diagnostics_parser; mod graph; -mod logging; mod lsp_ext; mod merge_views; mod navigation; mod opengl; +mod source_mapper; mod url_norm; #[cfg(test)] @@ -317,9 +319,11 @@ impl MinecraftShaderLanguageServer { all_sources.extend(self.load_sources(&tree)?); + let mut source_mapper = source_mapper::SourceMapper::new(all_sources.len()); + let view = { let graph = self.graph.borrow(); - merge_views::generate_merge_list(&tree, &all_sources, &graph) + merge_views::generate_merge_list(&tree, &all_sources, &graph, &mut source_mapper) }; let root_path = self.graph.borrow().get_node(root); @@ -347,18 +351,17 @@ impl MinecraftShaderLanguageServer { return Ok(diagnostics); }; - let stdout = match self.opengl_context.clone().validate(tree_type, view) { + let stdout = match self.compile_shader_source(&view, tree_type, &root_path) { Some(s) => s, None => { back_fill(&all_sources, &mut diagnostics); return Ok(diagnostics); } }; - diagnostics.extend(diagnostics_parser::parse_diagnostics_output( - stdout, - uri, - self.opengl_context.as_ref(), - )); + + let diagnostics_parser = diagnostics_parser::DiagnosticsParser::new(self.opengl_context.as_ref()); + + diagnostics.extend(diagnostics_parser.parse_diagnostics_output(stdout, uri, &source_mapper, &self.graph.borrow())); } else { let mut all_trees: Vec<(TreeType, Vec<(NodeIndex, Option<_>)>)> = Vec::new(); @@ -399,20 +402,22 @@ impl MinecraftShaderLanguageServer { } for tree in all_trees { + // bit over-zealous in allocation but better than having to resize + let mut source_mapper = source_mapper::SourceMapper::new(all_sources.len()); let view = { let graph = self.graph.borrow(); - merge_views::generate_merge_list(&tree.1, &all_sources, &graph) + merge_views::generate_merge_list(&tree.1, &all_sources, &graph, &mut source_mapper) }; - let stdout = match self.opengl_context.clone().validate(tree.0, view) { + let root_path = self.graph.borrow().get_node(tree.1[0].0); + let stdout = match self.compile_shader_source(&view, tree.0, &root_path) { Some(s) => s, None => continue, }; - diagnostics.extend(diagnostics_parser::parse_diagnostics_output( - stdout, - uri, - self.opengl_context.as_ref(), - )); + + let diagnostics_parser = diagnostics_parser::DiagnosticsParser::new(self.opengl_context.as_ref()); + + diagnostics.extend(diagnostics_parser.parse_diagnostics_output(stdout, uri, &source_mapper, &self.graph.borrow())); } }; @@ -420,6 +425,17 @@ impl MinecraftShaderLanguageServer { Ok(diagnostics) } + fn compile_shader_source(&self, source: &str, tree_type: TreeType, path: &Path) -> Option { + let result = self.opengl_context.clone().validate(tree_type, source); + match &result { + Some(output) => { + info!("compilation errors reported"; "errors" => format!("`{}`", output.replace('\n', "\\n")), "tree_root" => path.to_str().unwrap()) + } + None => info!("compilation reported no errors"; "tree_root" => path.to_str().unwrap()), + }; + result + } + pub fn get_dfs_for_node(&self, root: NodeIndex) -> Result, dfs::error::CycleError> { let graph_ref = self.graph.borrow(); @@ -674,22 +690,22 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn goto_definition(&mut self, params: TextDocumentPositionParams, completable: LSCompletable>) { logging::slog_with_trace_id(|| { let parser = &mut self.tree_sitter.borrow_mut(); - let parser_ctx = match navigation::ParserContext::new(parser, params.text_document.uri.clone()) { + let parser_ctx = match navigation::ParserContext::new(parser, ¶ms.text_document.uri) { Ok(ctx) => ctx, Err(e) => { return completable.complete(Err(MethodError { code: 42069, - message: format!("error building parser context: {}", e), + message: format!("error building parser context: {}", e.context(params.text_document.uri)), data: (), })) } }; - match parser_ctx.find_definitions(params.text_document.uri, params.position) { + match parser_ctx.find_definitions(¶ms.text_document.uri, params.position) { Ok(locations) => completable.complete(Ok(locations)), Err(e) => completable.complete(Err(MethodError { code: 42069, - message: format!("error finding definitions: {}", e), + message: format!("error finding definitions: {}", e.context(params.text_document.uri)), data: (), })), } diff --git a/server/src/merge_views.rs b/server/main/src/merge_views.rs similarity index 81% rename from server/src/merge_views.rs rename to server/main/src/merge_views.rs index e1f6f4a..8ddc73f 100644 --- a/server/src/merge_views.rs +++ b/server/main/src/merge_views.rs @@ -10,13 +10,16 @@ use core::slice::Iter; use petgraph::stable_graph::NodeIndex; use crate::graph::CachedStableGraph; +use crate::source_mapper::SourceMapper; /// FilialTuple represents a tuple with a child at index 0 /// and a parent at index 1. Parent can be nullable in the case of /// the child being a top level node in the tree. pub type FilialTuple = (NodeIndex, Option); -pub fn generate_merge_list<'a>(nodes: &'a [FilialTuple], sources: &'a HashMap, graph: &'a CachedStableGraph) -> String { +pub fn generate_merge_list<'a>( + nodes: &'a [FilialTuple], sources: &'a HashMap, graph: &'a CachedStableGraph, source_mapper: &mut SourceMapper, +) -> String { // contains additionally inserted lines such as #line and other directives, preamble defines etc let mut extra_lines: Vec = Vec::new(); extra_lines.reserve((nodes.len() * 2) + 2); @@ -36,18 +39,24 @@ pub fn generate_merge_list<'a>(nodes: &'a [FilialTuple], sources: &'a HashMap::new(); @@ -60,6 +69,7 @@ pub fn generate_merge_list<'a>(nodes: &'a [FilialTuple], sources: &'a HashMap(nodes: &'a [FilialTuple], sources: &'a HashMap( nodes: &mut Peekable>, merge_list: &mut LinkedList<&'a str>, last_offset_set: &mut HashMap, graph: &'a CachedStableGraph, sources: &'a HashMap, extra_lines: &mut Vec, stack: &mut VecDeque, + source_mapper: &mut SourceMapper, ) { loop { let n = match nodes.next() { @@ -100,7 +111,7 @@ fn create_merge_views<'a>( .insert((parent, stack.back().copied()), char_following_line) .get_or_insert(0); merge_list.push_back(&parent_source[offset..char_for_line]); - add_opening_line_directive(&child_path, merge_list, extra_lines); + add_opening_line_directive(&child_path, child, merge_list, extra_lines, source_mapper); match nodes.peek() { Some(next) => { @@ -118,7 +129,7 @@ fn create_merge_views<'a>( merge_list.push_back(&child_source[..offset]); last_offset_set.insert((child, Some(parent)), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, merge_list, extra_lines); + add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines, source_mapper); // if the next pair's parent is not the current pair's parent, we need to bubble up if stack.contains(&next.1.unwrap()) { return; @@ -127,7 +138,16 @@ fn create_merge_views<'a>( } stack.push_back(parent); - create_merge_views(nodes, merge_list, last_offset_set, graph, sources, extra_lines, stack); + create_merge_views( + nodes, + merge_list, + last_offset_set, + graph, + sources, + extra_lines, + stack, + source_mapper, + ); stack.pop_back(); let offset = *last_offset_set.get(&(child, Some(parent))).unwrap(); @@ -144,7 +164,7 @@ fn create_merge_views<'a>( } // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, merge_list, extra_lines); + add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines, source_mapper); // we need to check the next item at the point of original return further down the callstack if nodes.peek().is_some() && stack.contains(&nodes.peek().unwrap().1.unwrap()) { @@ -161,7 +181,7 @@ fn create_merge_views<'a>( merge_list.push_back(&child_source[..offset]); last_offset_set.insert((child, Some(parent)), 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, merge_list, extra_lines); + add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines, source_mapper); } } } @@ -191,38 +211,63 @@ fn find_version_offset(source: &str) -> usize { .map_or(0, |(i, _)| i) } -fn add_preamble<'a>( - version_line_offset: usize, version_char_offset: usize, path: &str, source: &'a str, merge_list: &mut LinkedList<&'a str>, - extra_lines: &mut Vec, -) { - // TODO: Optifine #define preabmle - merge_list.push_back(&source[..version_char_offset]); - let google_line_directive = format!( - "#extension GL_GOOGLE_cpp_style_line_directive : enable\n#line {} \"{}\"\n", - // +2 because 0 indexed but #line is 1 indexed and references the *following* line - version_line_offset + 2, - path, - ); - extra_lines.push(google_line_directive); - unsafe_get_and_insert(merge_list, extra_lines); -} +// fn add_preamble<'a>( +// version_line_offset: usize, version_char_offset: usize, path: &Path, node: NodeIndex, source: &'a str, +// merge_list: &mut LinkedList<&'a str>, extra_lines: &mut Vec, source_mapper: &mut SourceMapper, +// ) { +// // TODO: Optifine #define preabmle +// merge_list.push_back(&source[..version_char_offset]); +// let google_line_directive = format!( +// "#extension GL_GOOGLE_cpp_style_line_directive : enable\n#line {} {} // {}\n", +// // +2 because 0 indexed but #line is 1 indexed and references the *following* line +// version_line_offset + 2, +// source_mapper.get_num(node), +// path.to_str().unwrap().replace('\\', "\\\\"), +// ); +// extra_lines.push(google_line_directive); +// unsafe_get_and_insert(merge_list, extra_lines); +// } -fn add_opening_line_directive(path: &Path, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec) { - let line_directive = format!("#line 1 \"{}\"\n", path.to_str().unwrap().replace('\\', "\\\\")); +fn add_opening_line_directive( + path: &Path, node: NodeIndex, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec, source_mapper: &mut SourceMapper, +) { + let line_directive = format!( + "#line 1 {} // {}\n", + source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ); extra_lines.push(line_directive); unsafe_get_and_insert(merge_list, extra_lines); } -fn add_closing_line_directive(line: usize, path: &Path, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec) { +fn add_closing_line_directive( + line: usize, path: &Path, node: NodeIndex, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec, + source_mapper: &mut SourceMapper, +) { // Optifine doesn't seem to add a leading newline if the previous line was a #line directive let line_directive = if let Some(l) = merge_list.back() { if l.trim().starts_with("#line") { - format!("#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) + format!( + "#line {} {} // {}\n", + line, + source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ) } else { - format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) + format!( + "\n#line {} {} // {}\n", + line, + source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ) } } else { - format!("\n#line {} \"{}\"\n", line, path.to_str().unwrap().replace('\\', "\\\\")) + format!( + "\n#line {} {} // {}\n", + line, + source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ) }; extra_lines.push(line_directive); @@ -243,10 +288,12 @@ mod merge_view_test { use std::path::PathBuf; use crate::merge_views::generate_merge_list; + use crate::source_mapper::SourceMapper; use crate::test::{copy_to_and_set_root, new_temp_server}; use crate::IncludePosition; #[test] + #[logging_macro::log_scope] fn test_generate_merge_list_01() { let mut server = new_temp_server(None); @@ -273,16 +320,17 @@ mod merge_view_test { let sources = server.load_sources(&nodes).unwrap(); let graph_borrow = server.graph.borrow(); - let result = generate_merge_list(&nodes, &sources, &graph_borrow); + let mut source_mapper = SourceMapper::new(0); + let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); - truth = truth.replacen( - "!!", - &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), - 1, - ); + // truth = truth.replacen( + // "!!", + // &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + // 1, + // ); truth = truth.replacen( "!!", &tmp_path.join("shaders").join("common.glsl").to_str().unwrap().replace('\\', "\\\\"), @@ -297,6 +345,7 @@ mod merge_view_test { } #[test] + #[logging_macro::log_scope] fn test_generate_merge_list_02() { let mut server = new_temp_server(None); @@ -341,17 +390,18 @@ mod merge_view_test { let sources = server.load_sources(&nodes).unwrap(); let graph_borrow = server.graph.borrow(); - let result = generate_merge_list(&nodes, &sources, &graph_borrow); + let mut source_mapper = SourceMapper::new(0); + let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); - truth = truth.replacen( - "!!", - &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), - 1, - ); + // truth = truth.replacen( + // "!!", + // &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + // 1, + // ); for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { let path = tmp_path.clone(); @@ -377,6 +427,7 @@ mod merge_view_test { } #[test] + #[logging_macro::log_scope] fn test_generate_merge_list_03() { let mut server = new_temp_server(None); @@ -421,17 +472,18 @@ mod merge_view_test { let sources = server.load_sources(&nodes).unwrap(); let graph_borrow = server.graph.borrow(); - let result = generate_merge_list(&nodes, &sources, &graph_borrow); + let mut source_mapper = SourceMapper::new(0); + let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); - truth = truth.replacen( - "!!", - &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), - 1, - ); + // truth = truth.replacen( + // "!!", + // &tmp_path.join("shaders").join("final.fsh").to_str().unwrap().replace('\\', "\\\\"), + // 1, + // ); for file in &["sample.glsl", "burger.glsl", "sample.glsl", "test.glsl", "sample.glsl"] { let path = tmp_path.clone(); @@ -457,6 +509,7 @@ mod merge_view_test { } #[test] + #[logging_macro::log_scope] fn test_generate_merge_list_04() { let mut server = new_temp_server(None); @@ -510,14 +563,15 @@ mod merge_view_test { let sources = server.load_sources(&nodes).unwrap(); let graph_borrow = server.graph.borrow(); - let result = generate_merge_list(&nodes, &sources, &graph_borrow); + let mut source_mapper = SourceMapper::new(0); + let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); let mut truth = fs::read_to_string(merge_file).unwrap(); for file in &[ - PathBuf::new().join("final.fsh").to_str().unwrap(), + // PathBuf::new().join("final.fsh").to_str().unwrap(), PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), PathBuf::new().join("utils").join("stuff1.glsl").to_str().unwrap(), PathBuf::new().join("utils").join("utilities.glsl").to_str().unwrap(), @@ -528,7 +582,6 @@ mod merge_view_test { PathBuf::new().join("final.fsh").to_str().unwrap(), ] { let path = tmp_path.clone(); - //path.f truth = truth.replacen("!!", &path.join("shaders").join(file).to_str().unwrap().replace('\\', "\\\\"), 1); } diff --git a/server/src/navigation.rs b/server/main/src/navigation.rs similarity index 94% rename from server/src/navigation.rs rename to server/main/src/navigation.rs index e5bc52c..cb90928 100644 --- a/server/src/navigation.rs +++ b/server/main/src/navigation.rs @@ -24,7 +24,7 @@ pub struct ParserContext<'a> { } impl<'a> ParserContext<'a> { - pub fn new(parser: &'a mut Parser, document_uri: Url) -> Result { + pub fn new(parser: &'a mut Parser, document_uri: &Url) -> Result { let source = read_to_string(document_uri.path())?; let tree = parser.parse(&source, None).unwrap(); @@ -32,7 +32,7 @@ impl<'a> ParserContext<'a> { Ok(ParserContext { source, tree, parser }) } - pub fn find_definitions(&self, document_uri: Url, point: Position) -> Result> { + pub fn find_definitions(&self, document_uri: &Url, point: Position) -> Result> { let current_node = match self.find_node_at_point(point) { Some(node) => node, None => return Ok(vec![]), diff --git a/server/src/opengl.rs b/server/main/src/opengl.rs similarity index 88% rename from server/src/opengl.rs rename to server/main/src/opengl.rs index 73099ae..9954e44 100644 --- a/server/src/opengl.rs +++ b/server/main/src/opengl.rs @@ -8,7 +8,7 @@ use mockall::automock; #[cfg_attr(test, automock)] pub trait ShaderValidator { - fn validate(&self, tree_type: super::TreeType, source: String) -> Option; + fn validate(&self, tree_type: super::TreeType, source: &str) -> Option; fn vendor(&self) -> String; } @@ -42,7 +42,7 @@ impl OpenGlContext { gl_ctx } - unsafe fn compile_and_get_shader_log(&self, shader: gl::types::GLuint, source: String) -> Option { + unsafe fn compile_and_get_shader_log(&self, shader: gl::types::GLuint, source: &str) -> Option { let mut success = i32::from(gl::FALSE); let c_str_frag = CString::new(source).unwrap(); gl::ShaderSource(shader, 1, &c_str_frag.as_ptr(), ptr::null()); @@ -71,8 +71,8 @@ impl OpenGlContext { } impl ShaderValidator for OpenGlContext { - fn validate(&self, tree_type: super::TreeType, source: String) -> Option { - let result = unsafe { + fn validate(&self, tree_type: super::TreeType, source: &str) -> Option { + unsafe { match tree_type { crate::TreeType::Fragment => { // Fragment shader @@ -95,14 +95,7 @@ impl ShaderValidator for OpenGlContext { self.compile_and_get_shader_log(compute_shader, source) } } - }; - - match &result { - Some(output) => info!("compilation errors reported"; "errors" => format!("`{}`", output.replace('\n', "\\n"))), - None => info!("compilation reported no errors"), } - - result } fn vendor(&self) -> String { diff --git a/server/main/src/source_mapper.rs b/server/main/src/source_mapper.rs new file mode 100644 index 0000000..efcad0d --- /dev/null +++ b/server/main/src/source_mapper.rs @@ -0,0 +1,52 @@ +use std::{collections::HashMap, fmt::Display}; + +use petgraph::graph::NodeIndex; + +#[derive(Clone, Copy, PartialEq, Eq, Hash)] +pub struct SourceNum(usize); + +impl Display for SourceNum { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + f.write_str(format!("{}", self.0).as_str()) + } +} + +impl From for SourceNum { + fn from(val: usize) -> Self { + SourceNum(val) + } +} + +// Maps from a graph node index to a virtual OpenGL +// source number (for when building the merged source view), +// and in reverse (for when mapping from GLSL error source numbers to their source path). +// What is a source number: https://community.khronos.org/t/what-is-source-string-number/70976 +pub struct SourceMapper { + next: SourceNum, + mapping: HashMap, + reverse_mapping: Vec, +} + +impl SourceMapper { + pub fn new(capacity: usize) -> Self { + SourceMapper { + next: SourceNum(0), + mapping: HashMap::with_capacity(capacity), + reverse_mapping: Vec::with_capacity(capacity), + } + } + + pub fn get_num(&mut self, node: NodeIndex) -> SourceNum { + let num = &*self.mapping.entry(node).or_insert_with(|| { + let next = self.next; + self.next.0 += 1; + self.reverse_mapping.push(node); + next + }); + *num + } + + pub fn get_node(&self, num: SourceNum) -> NodeIndex { + self.reverse_mapping[num.0] + } +} diff --git a/server/src/test.rs b/server/main/src/test.rs similarity index 98% rename from server/src/test.rs rename to server/main/src/test.rs index 9a77810..afb4761 100644 --- a/server/src/test.rs +++ b/server/main/src/test.rs @@ -5,8 +5,6 @@ use std::io::Result; use pretty_assertions::assert_eq; -use slog::o; -use slog::Logger; use tempdir::TempDir; use fs_extra::{copy_items, dir}; @@ -37,8 +35,6 @@ pub fn new_temp_server(opengl_context: Option>) let endpoint = LSPEndpoint::create_lsp_output_with_output_stream(|| StdoutNewline { s: Box::new(io::sink()) }); let context = opengl_context.unwrap_or_else(|| Box::new(opengl::MockShaderValidator::new())); - let logger = Logger::root(slog::Discard, o!()); - let guard = slog_scope::set_global_logger(logger); MinecraftShaderLanguageServer { endpoint, @@ -46,7 +42,7 @@ pub fn new_temp_server(opengl_context: Option>) root: "".into(), command_provider: None, opengl_context: context.into(), - log_guard: Some(guard), + log_guard: None, tree_sitter: Rc::new(RefCell::new(Parser::new())), } } @@ -82,6 +78,7 @@ fn copy_to_tmp_dir(test_path: &str) -> (Rc, PathBuf) { #[allow(deprecated)] #[test] +#[logging_macro::log_scope] fn test_empty_initialize() { let mut server = new_temp_server(None); @@ -130,6 +127,7 @@ fn test_empty_initialize() { #[allow(deprecated)] #[test] +#[logging_macro::log_scope] fn test_01_initialize() { let mut server = new_temp_server(None); @@ -189,7 +187,9 @@ fn test_01_initialize() { assert_eq!(server.graph.borrow().graph.edge_weight(edge).unwrap().line, 2); } +#[allow(deprecated)] #[test] +#[logging_macro::log_scope] fn test_05_initialize() { let mut server = new_temp_server(None); diff --git a/server/src/url_norm.rs b/server/main/src/url_norm.rs similarity index 100% rename from server/src/url_norm.rs rename to server/main/src/url_norm.rs diff --git a/server/testdata/01/common.glsl b/server/main/testdata/01/common.glsl similarity index 100% rename from server/testdata/01/common.glsl rename to server/main/testdata/01/common.glsl diff --git a/server/testdata/01/final.fsh b/server/main/testdata/01/final.fsh similarity index 100% rename from server/testdata/01/final.fsh rename to server/main/testdata/01/final.fsh diff --git a/server/main/testdata/01/final.fsh.merge b/server/main/testdata/01/final.fsh.merge new file mode 100644 index 0000000..7c606b6 --- /dev/null +++ b/server/main/testdata/01/final.fsh.merge @@ -0,0 +1,11 @@ +#version 120 + +#line 1 1 // !! +float test() { + return 0.5; +} +#line 4 0 // !! + +void main() { + gl_FragColor[0] = vec4(0.0); +} \ No newline at end of file diff --git a/server/testdata/02/final.fsh b/server/main/testdata/02/final.fsh similarity index 100% rename from server/testdata/02/final.fsh rename to server/main/testdata/02/final.fsh diff --git a/server/testdata/02/final.fsh.merge b/server/main/testdata/02/final.fsh.merge similarity index 57% rename from server/testdata/02/final.fsh.merge rename to server/main/testdata/02/final.fsh.merge index 78c9367..6e6d776 100644 --- a/server/testdata/02/final.fsh.merge +++ b/server/main/testdata/02/final.fsh.merge @@ -1,28 +1,26 @@ #version 120 -#extension GL_GOOGLE_cpp_style_line_directive : enable -#line 2 "!!" -#line 1 "!!" +#line 1 1 // !! int sample() { return 5; } -#line 1 "!!" +#line 1 2 // !! void burger() { // sample text } -#line 6 "!!" +#line 6 1 // !! -#line 1 "!!" +#line 1 3 // !! float test() { return 3.0; } -#line 8 "!!" +#line 8 1 // !! int sample_more() { return 5; } -#line 4 "!!" +#line 4 0 // !! void main() { gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0); diff --git a/server/testdata/02/utils/burger.glsl b/server/main/testdata/02/utils/burger.glsl similarity index 100% rename from server/testdata/02/utils/burger.glsl rename to server/main/testdata/02/utils/burger.glsl diff --git a/server/testdata/02/utils/sample.glsl b/server/main/testdata/02/utils/sample.glsl similarity index 100% rename from server/testdata/02/utils/sample.glsl rename to server/main/testdata/02/utils/sample.glsl diff --git a/server/testdata/02/utils/test.glsl b/server/main/testdata/02/utils/test.glsl similarity index 100% rename from server/testdata/02/utils/test.glsl rename to server/main/testdata/02/utils/test.glsl diff --git a/server/testdata/03/final.fsh b/server/main/testdata/03/final.fsh similarity index 100% rename from server/testdata/03/final.fsh rename to server/main/testdata/03/final.fsh diff --git a/server/testdata/03/final.fsh.merge b/server/main/testdata/03/final.fsh.merge similarity index 53% rename from server/testdata/03/final.fsh.merge rename to server/main/testdata/03/final.fsh.merge index a328117..f317989 100644 --- a/server/testdata/03/final.fsh.merge +++ b/server/main/testdata/03/final.fsh.merge @@ -1,24 +1,22 @@ #version 120 -#extension GL_GOOGLE_cpp_style_line_directive : enable -#line 2 "!!" -#line 1 "!!" +#line 1 1 // !! int sample() { return 5; } -#line 1 "!!" +#line 1 2 // !! void burger() { // sample text } -#line 6 "!!" +#line 6 1 // !! -#line 1 "!!" +#line 1 3 // !! float test() { return 3.0; } -#line 8 "!!" -#line 4 "!!" +#line 8 1 // !! +#line 4 0 // !! void main() { gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0); diff --git a/server/testdata/03/utils/burger.glsl b/server/main/testdata/03/utils/burger.glsl similarity index 100% rename from server/testdata/03/utils/burger.glsl rename to server/main/testdata/03/utils/burger.glsl diff --git a/server/testdata/03/utils/sample.glsl b/server/main/testdata/03/utils/sample.glsl similarity index 100% rename from server/testdata/03/utils/sample.glsl rename to server/main/testdata/03/utils/sample.glsl diff --git a/server/testdata/03/utils/test.glsl b/server/main/testdata/03/utils/test.glsl similarity index 100% rename from server/testdata/03/utils/test.glsl rename to server/main/testdata/03/utils/test.glsl diff --git a/server/testdata/04/final.fsh b/server/main/testdata/04/final.fsh similarity index 100% rename from server/testdata/04/final.fsh rename to server/main/testdata/04/final.fsh diff --git a/server/main/testdata/04/final.fsh.merge b/server/main/testdata/04/final.fsh.merge new file mode 100644 index 0000000..49da4ac --- /dev/null +++ b/server/main/testdata/04/final.fsh.merge @@ -0,0 +1,23 @@ +#version 120 + +#line 1 1 // !! +#line 1 2 // !! +void stuff1() { + +} +#line 2 1 // !! +#line 1 3 // !! +void stuff2() { + +} +#line 3 1 // !! +#line 4 0 // !! +#line 1 4 // !! +void matrix() { + +} +#line 5 0 // !! + +void main() { + +} \ No newline at end of file diff --git a/server/testdata/04/lib/matrices.glsl b/server/main/testdata/04/lib/matrices.glsl similarity index 100% rename from server/testdata/04/lib/matrices.glsl rename to server/main/testdata/04/lib/matrices.glsl diff --git a/server/testdata/04/utils/stuff1.glsl b/server/main/testdata/04/utils/stuff1.glsl similarity index 100% rename from server/testdata/04/utils/stuff1.glsl rename to server/main/testdata/04/utils/stuff1.glsl diff --git a/server/testdata/04/utils/stuff2.glsl b/server/main/testdata/04/utils/stuff2.glsl similarity index 100% rename from server/testdata/04/utils/stuff2.glsl rename to server/main/testdata/04/utils/stuff2.glsl diff --git a/server/testdata/04/utils/utilities.glsl b/server/main/testdata/04/utils/utilities.glsl similarity index 100% rename from server/testdata/04/utils/utilities.glsl rename to server/main/testdata/04/utils/utilities.glsl diff --git a/server/testdata/05/common.glsl b/server/main/testdata/05/common.glsl similarity index 100% rename from server/testdata/05/common.glsl rename to server/main/testdata/05/common.glsl diff --git a/server/testdata/05/final.fsh b/server/main/testdata/05/final.fsh similarity index 100% rename from server/testdata/05/final.fsh rename to server/main/testdata/05/final.fsh diff --git a/server/testdata/05/final.fsh.merge b/server/main/testdata/05/final.fsh.merge similarity index 100% rename from server/testdata/05/final.fsh.merge rename to server/main/testdata/05/final.fsh.merge diff --git a/server/testdata/05/test/banana.glsl b/server/main/testdata/05/test/banana.glsl similarity index 100% rename from server/testdata/05/test/banana.glsl rename to server/main/testdata/05/test/banana.glsl diff --git a/server/testdata/05/test/burger.glsl b/server/main/testdata/05/test/burger.glsl similarity index 100% rename from server/testdata/05/test/burger.glsl rename to server/main/testdata/05/test/burger.glsl diff --git a/server/src/diagnostics_parser.rs b/server/src/diagnostics_parser.rs deleted file mode 100644 index b473896..0000000 --- a/server/src/diagnostics_parser.rs +++ /dev/null @@ -1,162 +0,0 @@ -use std::{collections::HashMap, path::Path}; - -use once_cell::sync::OnceCell; - -use regex::Regex; -use rust_lsp::lsp_types::{Diagnostic, DiagnosticSeverity, Position, Range}; -use url::Url; - -use crate::{consts, opengl}; - -static RE_DIAGNOSTIC: OnceCell = OnceCell::new(); -fn diagnostics_regex(vendor: &T) -> &'static Regex -where - T: opengl::ShaderValidator + ?Sized, -{ - RE_DIAGNOSTIC.get_or_init(|| match vendor.vendor().as_str() { - "NVIDIA Corporation" => { - Regex::new(r#"^(?P[^?<>*|"]+)\((?P\d+)\) : (?Perror|warning) [A-C]\d+: (?P.+)"#).unwrap() - } - _ => { - Regex::new(r#"^(?PERROR|WARNING): (?P[^?<>*|"\n]+):(?P\d+): '[a-z]*' : (?P.+)$"#).unwrap() - } - }) -} - -static LINE_NUM_OFFSET: OnceCell = OnceCell::new(); -fn line_number_offset(vendor: &T) -> &'static u32 -where - T: opengl::ShaderValidator + ?Sized, -{ - LINE_NUM_OFFSET.get_or_init(|| match vendor.vendor().as_str() { - "ATI Technologies" => 0, - _ => 2, - }) -} - -pub fn parse_diagnostics_output(output: String, uri: &Path, vendor_querier: &T) -> HashMap> -where - T: opengl::ShaderValidator + ?Sized, -{ - let output_lines = output.split('\n'); - let mut diagnostics: HashMap> = HashMap::with_capacity(output_lines.count()); - let output_lines = output.split('\n'); - - for line in output_lines { - let diagnostic_capture = match diagnostics_regex(vendor_querier).captures(line) { - Some(d) => d, - None => continue, - }; - - // info!("match {:?}", diagnostic_capture); - - let msg = diagnostic_capture.name("output").unwrap().as_str(); - - let line = match diagnostic_capture.name("linenum") { - Some(c) => c.as_str().parse::().unwrap_or(0), - None => 0, - } - line_number_offset(vendor_querier); - - // TODO: line matching maybe - /* let line_text = source_lines[line as usize]; - let leading_whitespace = line_text.len() - line_text.trim_start().len(); */ - - let severity = match diagnostic_capture.name("severity") { - Some(c) => match c.as_str().to_lowercase().as_str() { - "error" => DiagnosticSeverity::Error, - "warning" => DiagnosticSeverity::Warning, - _ => DiagnosticSeverity::Information, - }, - _ => DiagnosticSeverity::Information, - }; - - let origin = match diagnostic_capture.name("filepath") { - Some(o) => { - if o.as_str() == "0" { - uri.to_str().unwrap().to_string() - } else { - o.as_str().to_string() - } - } - None => uri.to_str().unwrap().to_string(), - }; - - let diagnostic = Diagnostic { - range: Range::new( - /* Position::new(line, leading_whitespace as u64), - Position::new(line, line_text.len() as u64) */ - Position::new(line, 0), - Position::new(line, 1000), - ), - code: None, - severity: Some(severity), - source: Some(consts::SOURCE.into()), - message: msg.trim().into(), - related_information: None, - tags: None, - code_description: Option::None, - data: Option::None, - }; - - let origin_url = Url::from_file_path(origin).unwrap(); - match diagnostics.get_mut(&origin_url) { - Some(d) => d.push(diagnostic), - None => { - diagnostics.insert(origin_url, vec![diagnostic]); - } - }; - } - diagnostics -} - -#[cfg(test)] -mod diagnostics_test { - use std::{path::PathBuf, str::FromStr}; - - use crate::{diagnostics_parser::parse_diagnostics_output, opengl::MockShaderValidator, test::new_temp_server}; - - #[test] - fn test_nvidia_diagnostics() { - let mut mockgl = MockShaderValidator::new(); - mockgl.expect_vendor().returning(|| "NVIDIA Corporation".into()); - let server = new_temp_server(Some(Box::new(mockgl))); - - let output = "/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh(9) : error C0000: syntax error, unexpected '}', expecting ',' or ';' at token \"}\""; - - let results = parse_diagnostics_output( - output.to_string(), - &PathBuf::from_str("/home/noah/.minecraft/shaderpacks/test").unwrap(), - server.opengl_context.as_ref(), - ); - - assert_eq!(results.len(), 1); - let first = results.into_iter().next().unwrap(); - assert_eq!( - first.0, - url::Url::from_file_path("/home/noah/.minecraft/shaderpacks/test/shaders/final.fsh").unwrap() - ); - server.endpoint.request_shutdown(); - } - - #[test] - fn test_amd_diagnostics() { - let mut mockgl = MockShaderValidator::new(); - mockgl.expect_vendor().returning(|| "ATI Technologies".into()); - let server = new_temp_server(Some(Box::new(mockgl))); - - let output = "ERROR: 0:1: '' : syntax error: #line -ERROR: 0:10: '' : syntax error: #line -ERROR: 0:15: 'varying' : syntax error: syntax error -"; - - let results = parse_diagnostics_output( - output.to_string(), - &PathBuf::from_str("/home/test").unwrap(), - server.opengl_context.as_ref(), - ); - assert_eq!(results.len(), 1); - let first = results.into_iter().next().unwrap(); - assert_eq!(first.1.len(), 3); - server.endpoint.request_shutdown(); - } -} diff --git a/server/testdata/01/final.fsh.merge b/server/testdata/01/final.fsh.merge deleted file mode 100644 index f6cdd6e..0000000 --- a/server/testdata/01/final.fsh.merge +++ /dev/null @@ -1,13 +0,0 @@ -#version 120 -#extension GL_GOOGLE_cpp_style_line_directive : enable -#line 2 "!!" - -#line 1 "!!" -float test() { - return 0.5; -} -#line 4 "!!" - -void main() { - gl_FragColor[0] = vec4(0.0); -} \ No newline at end of file diff --git a/server/testdata/04/final.fsh.merge b/server/testdata/04/final.fsh.merge deleted file mode 100644 index 47d97af..0000000 --- a/server/testdata/04/final.fsh.merge +++ /dev/null @@ -1,25 +0,0 @@ -#version 120 -#extension GL_GOOGLE_cpp_style_line_directive : enable -#line 2 "!!" - -#line 1 "!!" -#line 1 "!!" -void stuff1() { - -} -#line 2 "!!" -#line 1 "!!" -void stuff2() { - -} -#line 3 "!!" -#line 4 "!!" -#line 1 "!!" -void matrix() { - -} -#line 5 "!!" - -void main() { - -} \ No newline at end of file From 3b865dfda2875cdc5804c012bb458bae70893313 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 9 Apr 2022 18:11:50 +0100 Subject: [PATCH 36/56] updated AMD diagnostics regex --- server/main/src/diagnostics_parser.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/server/main/src/diagnostics_parser.rs b/server/main/src/diagnostics_parser.rs index df2f20b..f798827 100644 --- a/server/main/src/diagnostics_parser.rs +++ b/server/main/src/diagnostics_parser.rs @@ -32,7 +32,7 @@ impl<'a, T: opengl::ShaderValidator + ?Sized> DiagnosticsParser<'a, T> { "NVIDIA Corporation" => { Regex::new(r#"^(?P\d+)\((?P\d+)\) : (?Perror|warning) [A-C]\d+: (?P.+)"#).unwrap() } - _ => Regex::new(r#"^(?PERROR|WARNING): (?P[^?<>*|"\n]+):(?P\d+): '[a-z]*' : (?P.+)$"#) + _ => Regex::new(r#"^(?PERROR|WARNING): (?P[^?<>*|"\n]+):(?P\d+): (?:'.*' :|[a-z]+\(#\d+\)) +(?P.+)$"#) .unwrap(), }) } @@ -122,7 +122,7 @@ impl<'a, T: opengl::ShaderValidator + ?Sized> DiagnosticsParser<'a, T> { mod diagnostics_test { use std::path::PathBuf; - use slog::{slog_o, Level}; + use slog::slog_o; use url::Url; use crate::{ From d8cb0465ef623dc42b12e0fc4a2ae5b157ddec80 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 10 Apr 2022 00:28:12 +0100 Subject: [PATCH 37/56] implemented file-local find-refs for functions --- server/main/src/linemap.rs | 80 ++++++++++++++++++ server/main/src/main.rs | 47 +++++++++-- server/main/src/navigation.rs | 153 ++++++++++++++++++++++++++-------- 3 files changed, 239 insertions(+), 41 deletions(-) create mode 100644 server/main/src/linemap.rs diff --git a/server/main/src/linemap.rs b/server/main/src/linemap.rs new file mode 100644 index 0000000..3995100 --- /dev/null +++ b/server/main/src/linemap.rs @@ -0,0 +1,80 @@ +use rust_lsp::lsp_types::Position; + +pub struct LineMap { + positions: Vec, +} + +impl LineMap { + pub fn new(source: &str) -> Self { + let mut positions = vec![0]; + for (i, char) in source.char_indices() { + if char == '\n' { + positions.push(i + 1); + } + } + + LineMap { positions } + } + + pub fn offset_for_position(&self, position: Position) -> usize { + self.positions[position.line as usize] + (position.character as usize) + } +} + +#[cfg(test)] +mod test { + use rust_lsp::lsp_types::Position; + + use crate::linemap::LineMap; + + #[test] + #[logging_macro::log_scope] + fn test_linemap() { + struct Test { + string: &'static str, + pos: Position, + offset: usize, + } + + let cases = vec![ + Test { + string: "sample\ntext", + pos: Position { line: 1, character: 2 }, + offset: 9, + }, + Test { + string: "banana", + pos: Position { line: 0, character: 0 }, + offset: 0, + }, + Test { + string: "banana", + pos: Position { line: 0, character: 1 }, + offset: 1, + }, + Test { + string: "sample\ntext", + pos: Position { line: 1, character: 0 }, + offset: 7, + }, + Test { + string: "sample\n\ttext", + pos: Position { line: 1, character: 2 }, + offset: 9, + }, + Test { + string: "sample\r\ntext", + pos: Position { line: 1, character: 0 }, + offset: 8, + }, + ]; + + for case in cases { + let linemap = LineMap::new(case.string); + + let offset = linemap.offset_for_position(case.pos); + + assert_eq!(offset, case.offset, "{:?}", case.string); + } + } +} diff --git a/server/main/src/main.rs b/server/main/src/main.rs index ef0b0eb..01c4217 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -47,6 +47,7 @@ mod consts; mod dfs; mod diagnostics_parser; mod graph; +mod linemap; mod lsp_ext; mod merge_views; mod navigation; @@ -515,6 +516,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { let capabilities = ServerCapabilities { definition_provider: Some(OneOf::Left(true)), + references_provider: Some(OneOf::Left(true)), document_link_provider: Some(DocumentLinkOptions { resolve_provider: None, work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None }, @@ -689,31 +691,60 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn goto_definition(&mut self, params: TextDocumentPositionParams, completable: LSCompletable>) { logging::slog_with_trace_id(|| { + let path = PathBuf::from_url(params.text_document.uri); + if !path.starts_with(&self.root) { + return; + } let parser = &mut self.tree_sitter.borrow_mut(); - let parser_ctx = match navigation::ParserContext::new(parser, ¶ms.text_document.uri) { + let parser_ctx = match navigation::ParserContext::new(parser, &path) { Ok(ctx) => ctx, Err(e) => { return completable.complete(Err(MethodError { code: 42069, - message: format!("error building parser context: {}", e.context(params.text_document.uri)), + message: format!("error building parser context: error={}, path={:?}", e, path), data: (), })) } }; - match parser_ctx.find_definitions(¶ms.text_document.uri, params.position) { - Ok(locations) => completable.complete(Ok(locations)), + match parser_ctx.find_definitions(&path, params.position) { + Ok(locations) => completable.complete(Ok(locations.unwrap_or_default())), Err(e) => completable.complete(Err(MethodError { code: 42069, - message: format!("error finding definitions: {}", e.context(params.text_document.uri)), + message: format!("error finding definitions: error={}, path={:?}", e, path), data: (), })), } }); } - fn references(&mut self, _: ReferenceParams, completable: LSCompletable>) { - completable.complete(Err(Self::error_not_available(()))); + fn references(&mut self, params: ReferenceParams, completable: LSCompletable>) { + logging::slog_with_trace_id(|| { + let path = PathBuf::from_url(params.text_document_position.text_document.uri); + if !path.starts_with(&self.root) { + return; + } + let parser = &mut self.tree_sitter.borrow_mut(); + let parser_ctx = match navigation::ParserContext::new(parser, &path) { + Ok(ctx) => ctx, + Err(e) => { + return completable.complete(Err(MethodError { + code: 42069, + message: format!("error building parser context: error={}, path={:?}", e, path), + data: (), + })) + } + }; + + match parser_ctx.find_references(&path, params.text_document_position.position) { + Ok(locations) => completable.complete(Ok(locations.unwrap_or_default())), + Err(e) => completable.complete(Err(MethodError { + code: 42069, + message: format!("error finding definitions: error={}, path={:?}", e, path), + data: (), + })), + } + }); } fn document_highlight(&mut self, _: TextDocumentPositionParams, completable: LSCompletable>) { @@ -743,7 +774,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { fn document_link(&mut self, params: DocumentLinkParams, completable: LSCompletable>) { logging::slog_with_trace_id(|| { // node for current document - let curr_doc = params.text_document.uri.to_file_path().unwrap(); + let curr_doc = PathBuf::from_url(params.text_document.uri); let node = match self.graph.borrow_mut().find_node(&curr_doc) { Some(n) => n, None => { diff --git a/server/main/src/navigation.rs b/server/main/src/navigation.rs index cb90928..4dcc93c 100644 --- a/server/main/src/navigation.rs +++ b/server/main/src/navigation.rs @@ -1,18 +1,32 @@ -use std::fs::read_to_string; +use std::{fs::read_to_string, path::Path}; use anyhow::Result; use rust_lsp::lsp_types::{Location, Position, Range}; -use slog_scope::{info, debug}; -use tree_sitter::{Node, Parser, Point, Tree, Query, QueryCursor}; +use slog_scope::{debug, info, trace}; +use tree_sitter::{Node, Parser, Point, Query, QueryCursor, Tree}; use url::Url; -macro_rules! find_function_str { - () => { +use crate::linemap::LineMap; + +macro_rules! find_function_def_str { + () => { r#" ( (function_declarator (identifier) @function) - (#match? @function "{}") + (#match? @function "{}") + ) + "# + }; +} + +macro_rules! find_function_refs_str { + () => { + r#" + ( + (call_expression + (identifier) @call) + (#match? @call "{}") ) "# }; @@ -20,49 +34,56 @@ macro_rules! find_function_str { pub struct ParserContext<'a> { source: String, tree: Tree, + linemap: LineMap, parser: &'a mut Parser, } impl<'a> ParserContext<'a> { - pub fn new(parser: &'a mut Parser, document_uri: &Url) -> Result { - let source = read_to_string(document_uri.path())?; + pub fn new(parser: &'a mut Parser, path: &Path) -> Result { + let source = read_to_string(path)?; let tree = parser.parse(&source, None).unwrap(); - Ok(ParserContext { source, tree, parser }) + let linemap = LineMap::new(&source); + + Ok(ParserContext { + source, + tree, + linemap, + parser, + }) } - pub fn find_definitions(&self, document_uri: &Url, point: Position) -> Result> { + pub fn find_definitions(&self, path: &Path, point: Position) -> Result>> { let current_node = match self.find_node_at_point(point) { Some(node) => node, - None => return Ok(vec![]), + None => return Ok(None), }; let parent = match current_node.parent() { Some(parent) => parent, - None => return Ok(vec![]), + None => return Ok(None), }; let query = match (current_node.kind(), parent.kind()) { (_, "call_expression") => { - format!(find_function_str!(), current_node.utf8_text(self.source.as_bytes())?) + format!(find_function_def_str!(), current_node.utf8_text(self.source.as_bytes())?) } - _ => return Ok(vec![]), + _ => return Ok(None), }; let ts_query = Query::new(tree_sitter_glsl::language(), query.as_str())?; - let mut query_cursor = QueryCursor::new(); let mut locations = vec![]; - for m in query_cursor.matches(&ts_query, self.tree.root_node(), self.source.as_bytes()) { + for m in query_cursor.matches(&ts_query, self.root_node(), self.source.as_bytes()) { for capture in m.captures { let start = capture.node.start_position(); let end = capture.node.end_position(); locations.push(Location { - uri: document_uri.clone(), + uri: Url::from_file_path(path).unwrap(), range: Range { start: Position { line: start.row as u32, @@ -79,32 +100,98 @@ impl<'a> ParserContext<'a> { info!("finished searching for definitions"; "definitions" => format!("{:?}", locations)); - Ok(locations) + Ok(Some(locations)) } - pub fn find_references(&self) -> Result> { - Ok(vec![]) + pub fn find_references(&self, path: &Path, point: Position) -> Result>> { + let current_node = match self.find_node_at_point(point) { + Some(node) => node, + None => return Ok(None), + }; + + let parent = match current_node.parent() { + Some(parent) => parent, + None => return Ok(None), + }; + + let query = match (current_node.kind(), parent.kind()) { + (_, "function_declarator") => { + format!(find_function_refs_str!(), current_node.utf8_text(self.source.as_bytes())?) + } + _ => return Ok(None), + }; + + let ts_query = Query::new(tree_sitter_glsl::language(), query.as_str())?; + let mut query_cursor = QueryCursor::new(); + + let mut locations = vec![]; + + for m in query_cursor.matches(&ts_query, self.root_node(), self.source.as_bytes()) { + for capture in m.captures { + let start = capture.node.start_position(); + let end = capture.node.end_position(); + + locations.push(Location { + uri: Url::from_file_path(path).unwrap(), + range: Range { + start: Position { + line: start.row as u32, + character: start.column as u32, + }, + end: Position { + line: end.row as u32, + character: end.column as u32, + }, + }, + }); + } + } + + Ok(Some(locations)) } fn root_node(&self) -> Node { self.tree.root_node() } - fn find_node_at_point(&self, point: Position) -> Option { - match self.root_node().named_descendant_for_point_range( - Point { - row: point.line as usize, - column: (point.character - 1) as usize, - }, - Point { - row: point.line as usize, - column: point.character as usize, - }, - ) { + fn find_node_at_point(&self, pos: Position) -> Option { + // if we're at the end of an ident, we need to look _back_ one char instead + // for tree-sitter to find the right node. + let look_behind = { + let offset = self.linemap.offset_for_position(pos); + let char_at = self.source.as_bytes()[offset]; + trace!("looking for non-alpha for point adjustment"; + "offset" => offset, + "char" => char_at as char, + "point" => format!("{:?}", pos), + "look_behind" => !char_at.is_ascii_alphabetic()); + !char_at.is_ascii_alphabetic() + }; + + let mut start = Point { + row: pos.line as usize, + column: pos.character as usize, + }; + let mut end = Point { + row: pos.line as usize, + column: pos.character as usize, + }; + + if look_behind { + start.column -= 1; + } else { + end.column += 1; + } + + match self.root_node().named_descendant_for_point_range(start, end) { Some(node) => { - debug!("found a node"; "node" => format!("{:?}", node)); + debug!("found a node"; + "node" => format!("{:?}", node), + "text" => node.utf8_text(self.source.as_bytes()).unwrap(), + "start" => format!("{}", start), + "end" => format!("{}", end)); Some(node) - }, + } None => None, } } From f66f56603abd1d814ffffb7d81e6308adc742ee4 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 10 Apr 2022 20:54:23 +0100 Subject: [PATCH 38/56] implemented file-local go-to-def for variables --- server/main/src/navigation.rs | 137 +++++++++++++++++++++++++--------- 1 file changed, 101 insertions(+), 36 deletions(-) diff --git a/server/main/src/navigation.rs b/server/main/src/navigation.rs index 4dcc93c..884171c 100644 --- a/server/main/src/navigation.rs +++ b/server/main/src/navigation.rs @@ -14,7 +14,7 @@ macro_rules! find_function_def_str { ( (function_declarator (identifier) @function) - (#match? @function "{}") + (#match? @function "^{}$") ) "# }; @@ -26,11 +26,33 @@ macro_rules! find_function_refs_str { ( (call_expression (identifier) @call) - (#match? @call "{}") + (#match? @call "^{}$") ) "# }; } + +macro_rules! find_variable_def_str { + () => { + r#" + ( + [ + (init_declarator + (identifier) @variable) + + (parameter_declaration + (identifier) @variable) + + (declaration + (identifier) @variable) + + (#match? @variable "^{}$") + ] + ) + "# + }; +} + pub struct ParserContext<'a> { source: String, tree: Tree, @@ -65,40 +87,23 @@ impl<'a> ParserContext<'a> { None => return Ok(None), }; - let query = match (current_node.kind(), parent.kind()) { + debug!("matching location lookup method for parent-child tuple"; "parent" => parent.kind(), "child" => current_node.kind()); + + let locations = match (current_node.kind(), parent.kind()) { (_, "call_expression") => { - format!(find_function_def_str!(), current_node.utf8_text(self.source.as_bytes())?) + let query_str = format!(find_function_def_str!(), current_node.utf8_text(self.source.as_bytes())?); + self.simple_global_search(path, &query_str)? + } + ("identifier", "argument_list") | + ("identifier", "field_expression") | + ("identifier", "binary_expression") | + ("identifier", "assignment_expression") => { + self.tree_climbing_search(path, current_node)? } _ => return Ok(None), }; - let ts_query = Query::new(tree_sitter_glsl::language(), query.as_str())?; - let mut query_cursor = QueryCursor::new(); - - let mut locations = vec![]; - - for m in query_cursor.matches(&ts_query, self.root_node(), self.source.as_bytes()) { - for capture in m.captures { - let start = capture.node.start_position(); - let end = capture.node.end_position(); - - locations.push(Location { - uri: Url::from_file_path(path).unwrap(), - range: Range { - start: Position { - line: start.row as u32, - character: start.column as u32, - }, - end: Position { - line: end.row as u32, - character: end.column as u32, - }, - }, - }); - } - } - - info!("finished searching for definitions"; "definitions" => format!("{:?}", locations)); + info!("finished searching for definitions"; "count" => locations.len(), "definitions" => format!("{:?}", locations)); Ok(Some(locations)) } @@ -114,19 +119,79 @@ impl<'a> ParserContext<'a> { None => return Ok(None), }; - let query = match (current_node.kind(), parent.kind()) { + let locations = match (current_node.kind(), parent.kind()) { (_, "function_declarator") => { - format!(find_function_refs_str!(), current_node.utf8_text(self.source.as_bytes())?) + let query_str = format!(find_function_refs_str!(), current_node.utf8_text(self.source.as_bytes())?); + self.simple_global_search(path, &query_str)? } _ => return Ok(None), }; - let ts_query = Query::new(tree_sitter_glsl::language(), query.as_str())?; + info!("finished searching for references"; "count" => locations.len(), "references" => format!("{:?}", locations)); + + Ok(Some(locations)) + } + + fn tree_climbing_search(&self, path: &Path, start_node: Node) -> Result> { + let mut locations = vec![]; + + let node_text = start_node.utf8_text(self.source.as_bytes())?; + + let query_str = format!(find_variable_def_str!(), node_text); + + debug!("built query string"; "query" => &query_str); + + let mut parent = start_node.parent(); + + loop { + if parent.is_none() { + trace!("no more parent left, found nothing"); + break; + } + + let query = Query::new(tree_sitter_glsl::language(), &query_str)?; + let mut query_cursor = QueryCursor::new(); + + trace!("running tree-sitter query for node"; "node" => format!("{:?}", parent.unwrap()), "node_text" => parent.unwrap().utf8_text(self.source.as_bytes()).unwrap()); + + for m in query_cursor.matches(&query, parent.unwrap(), self.source.as_bytes()) { + for capture in m.captures { + let start = capture.node.start_position(); + let end = capture.node.end_position(); + + locations.push(Location { + uri: Url::from_file_path(path).unwrap(), + range: Range { + start: Position { + line: start.row as u32, + character: start.column as u32, + }, + end: Position { + line: end.row as u32, + character: end.column as u32, + }, + }, + }); + } + } + + if !locations.is_empty() { + break; + } + + parent = parent.unwrap().parent(); + } + + Ok(locations) + } + + fn simple_global_search(&self, path: &Path, query_str: &str) -> Result> { + let query = Query::new(tree_sitter_glsl::language(), query_str)?; let mut query_cursor = QueryCursor::new(); let mut locations = vec![]; - for m in query_cursor.matches(&ts_query, self.root_node(), self.source.as_bytes()) { + for m in query_cursor.matches(&query, self.root_node(), self.source.as_bytes()) { for capture in m.captures { let start = capture.node.start_position(); let end = capture.node.end_position(); @@ -147,7 +212,7 @@ impl<'a> ParserContext<'a> { } } - Ok(Some(locations)) + Ok(locations) } fn root_node(&self) -> Node { From 1529460a5ca512aeb6de823e3c630130c320e7c7 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 16 Apr 2022 00:21:10 +0100 Subject: [PATCH 39/56] support document symbols request --- server/Cargo.lock | 427 ++++++++++++-------------- server/main/src/dfs.rs | 2 +- server/main/src/diagnostics_parser.rs | 8 +- server/main/src/main.rs | 41 ++- server/main/src/navigation.rs | 204 ++++++++++-- 5 files changed, 420 insertions(+), 262 deletions(-) diff --git a/server/Cargo.lock b/server/Cargo.lock index 5584513..d6dab7b 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -4,9 +4,9 @@ version = 3 [[package]] name = "aho-corasick" -version = "0.7.15" +version = "0.7.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7404febffaa47dac81aa44dba71523c9d069b1bdc50a77db41195149e17f68e5" +checksum = "1e37cfd5e7657ada45f742d6e99ca5788580b5c529dc78faf11ece6dc702656f" dependencies = [ "memchr", ] @@ -28,9 +28,9 @@ dependencies = [ [[package]] name = "anyhow" -version = "1.0.38" +version = "1.0.56" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "afddf7f520a80dbf76e6f50a35bca42a2331ef227a28b3b6dc5c2e2338d114b1" +checksum = "4361135be9122e0870de935d7c439aef945b9f9ddd4199a553b5270b49c82a27" [[package]] name = "arc-swap" @@ -51,21 +51,15 @@ dependencies = [ [[package]] name = "autocfg" -version = "1.0.1" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cdb031dd78e28731d87d56cc8ffef4a8f36ca26c38fe2de700543e627f8a464a" - -[[package]] -name = "base64" -version = "0.12.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3441f0f7b02788e948e47f457ca01f1d7e6d92c693bc132c22b087d3141c03ff" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" [[package]] name = "bitflags" -version = "1.2.1" +version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cf1de2fe8c75bc145a2f577add951f8134889b4795d47466a54a5c846d691693" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" [[package]] name = "block" @@ -91,9 +85,9 @@ dependencies = [ [[package]] name = "cc" -version = "1.0.66" +version = "1.0.73" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c0496836a84f8d0495758516b8621a622beb77c0fed418570e50764093ced48" +checksum = "2fff2a6927b3bb87f9595d67196a70493f627687a71d87a0d692242c33f58c11" [[package]] name = "cfg-if" @@ -125,8 +119,8 @@ dependencies = [ "bitflags", "block", "cocoa-foundation", - "core-foundation 0.9.1", - "core-graphics 0.22.2", + "core-foundation 0.9.3", + "core-graphics 0.22.3", "foreign-types", "libc", "objc", @@ -140,7 +134,7 @@ checksum = "7ade49b65d560ca58c403a479bb396592b155c0185eada742ee323d1d68d6318" dependencies = [ "bitflags", "block", - "core-foundation 0.9.1", + "core-foundation 0.9.3", "core-graphics-types", "foreign-types", "libc", @@ -159,11 +153,11 @@ dependencies = [ [[package]] name = "core-foundation" -version = "0.9.1" +version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0a89e2ae426ea83155dccf10c0fa6b1463ef6d5fcb44cee0b224a408fa640a62" +checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" dependencies = [ - "core-foundation-sys 0.8.2", + "core-foundation-sys 0.8.3", "libc", ] @@ -175,9 +169,9 @@ checksum = "b3a71ab494c0b5b860bdc8407ae08978052417070c2ced38573a9157ad75b8ac" [[package]] name = "core-foundation-sys" -version = "0.8.2" +version = "0.8.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ea221b5284a47e40033bf9b66f35f984ec0ea2931eb03505246cd27a963f981b" +checksum = "5827cebf4670468b8772dd191856768aedcb1b0278a04f989f7766351917b9dc" [[package]] name = "core-graphics" @@ -193,12 +187,12 @@ dependencies = [ [[package]] name = "core-graphics" -version = "0.22.2" +version = "0.22.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "269f35f69b542b80e736a20a89a05215c0ce80c2c03c514abb2e318b78379d86" +checksum = "2581bbab3b8ffc6fcbd550bf46c355135d16e9ff2a6ea032ad6b9bf1d7efe4fb" dependencies = [ "bitflags", - "core-foundation 0.9.1", + "core-foundation 0.9.3", "core-graphics-types", "foreign-types", "libc", @@ -211,7 +205,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3a68b68b3446082644c91ac778bf50cd4104bfb002b5a6a7c44cca5a2c70788b" dependencies = [ "bitflags", - "core-foundation 0.9.1", + "core-foundation 0.9.3", "foreign-types", "libc", ] @@ -231,9 +225,9 @@ dependencies = [ [[package]] name = "ctor" -version = "0.1.18" +version = "0.1.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "10bcb9d7dcbf7002aaffbb53eac22906b64cdcc127971dcc387d8eb7c95d5560" +checksum = "f877be4f7c9f246b183111634f75baa039715e3f46ce860677d3b19a69fb229c" dependencies = [ "quote", "syn", @@ -247,9 +241,9 @@ checksum = "b365fabc795046672053e29c954733ec3b05e4be654ab130fe8f1f94d7051f35" [[package]] name = "darling" -version = "0.13.1" +version = "0.13.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d0d720b8683f8dd83c65155f0530560cba68cd2bf395f6513a483caee57ff7f4" +checksum = "a01d95850c592940db9b8194bc39f4bc0e89dee5c4265e4b1807c34a9aba453c" dependencies = [ "darling_core", "darling_macro", @@ -257,9 +251,9 @@ dependencies = [ [[package]] name = "darling_core" -version = "0.13.1" +version = "0.13.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a340f241d2ceed1deb47ae36c4144b2707ec7dd0b649f894cb39bb595986324" +checksum = "859d65a907b6852c9361e3185c862aae7fafd2887876799fa55f5f99dc40d610" dependencies = [ "fnv", "ident_case", @@ -271,26 +265,15 @@ dependencies = [ [[package]] name = "darling_macro" -version = "0.13.1" +version = "0.13.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "72c41b3b7352feb3211a0d743dc5700a4e3b60f51bd2b368892d1e0f9a95f44b" +checksum = "9c972679f83bdf9c42bd905396b6c3588a843a17f0f16dfcfa3e2c5d57441835" dependencies = [ "darling_core", "quote", "syn", ] -[[package]] -name = "derivative" -version = "2.1.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eaed5874effa6cde088c644ddcdcb4ffd1511391c5be4fdd7a5ccd02c7e4a183" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] - [[package]] name = "diff" version = "0.1.12" @@ -359,9 +342,9 @@ checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457" [[package]] name = "fixedbitset" -version = "0.4.0" +version = "0.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "398ea4fabe40b9b0d885340a2a991a44c8a645624075ad966d21f88688e2b69e" +checksum = "279fb028e20b3c4c320317955b77c5e0c9701f05a1d309905d6fc702cdc5053e" [[package]] name = "float-cmp" @@ -395,9 +378,9 @@ checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" [[package]] name = "form_urlencoded" -version = "1.0.0" +version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ece68d15c92e84fa4f19d3780f1294e5ca82a78a6d515f1efaabcc144688be00" +checksum = "5fc25a87fa4fd2094bffb06925852034d90a17f0d1e05197d4956d3555752191" dependencies = [ "matches", "percent-encoding", @@ -405,9 +388,9 @@ dependencies = [ [[package]] name = "fragile" -version = "1.0.0" +version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69a039c3498dc930fe810151a34ba0c1c70b02b8625035592e74432f678591f2" +checksum = "e9d758e60b45e8d749c89c1b389ad8aee550f86aa12e2b9298b546dda7a82ab1" [[package]] name = "fs_extra" @@ -423,19 +406,19 @@ checksum = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" [[package]] name = "futures" -version = "0.1.30" +version = "0.1.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c7e4c2612746b0df8fed4ce0c69156021b704c9aefa360311c04e6e9e002eed" +checksum = "3a471a38ef8ed83cd6e40aa59c1ffe17db6855c18e3604d9c4ed8c08ebc28678" [[package]] name = "getrandom" -version = "0.2.5" +version = "0.2.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d39cd93900197114fa1fcb7ae84ca742095eed9442088988ae74fa744e930e77" +checksum = "9be70c98951c83b8d2f8f60d7065fa6d5146873094452a1008da8c2f1e4205ad" dependencies = [ "cfg-if 1.0.0", "libc", - "wasi", + "wasi 0.10.2+wasi-snapshot-preview1", ] [[package]] @@ -467,7 +450,7 @@ dependencies = [ "android_glue", "cgl", "cocoa", - "core-foundation 0.9.1", + "core-foundation 0.9.3", "glutin_egl_sys", "glutin_emscripten_sys", "glutin_gles2_sys", @@ -563,9 +546,9 @@ checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39" [[package]] name = "idna" -version = "0.2.0" +version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "02e2673c30ee86b5b96a9cb52ad15718aa1f966f5ab9ad54a8b95d5ca33120a9" +checksum = "418a0a6fab821475f634efe3ccc45c013f742efe03d853e8d3355d5cb850ecf8" dependencies = [ "matches", "unicode-bidi", @@ -574,9 +557,9 @@ dependencies = [ [[package]] name = "indexmap" -version = "1.7.0" +version = "1.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bc633605454125dec4b66843673f01c7df2b89479b32e0ed634e43a91cff62a5" +checksum = "0f647032dfaa1f8b6dc29bd3edb7bbef4861b8b8007ebb118d6db284fd59f6ee" dependencies = [ "autocfg", "hashbrown", @@ -584,9 +567,9 @@ dependencies = [ [[package]] name = "instant" -version = "0.1.9" +version = "0.1.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "61124eeebbd69b8190558df225adf7e4caafce0d743919e5d6b19652314ec5ec" +checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" dependencies = [ "cfg-if 1.0.0", "js-sys", @@ -603,12 +586,6 @@ dependencies = [ "either", ] -[[package]] -name = "itoa" -version = "0.4.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dd25036021b0de88a0aff6b850051563c6516d0bf53f8638938edbb9de732736" - [[package]] name = "itoa" version = "1.0.1" @@ -623,9 +600,9 @@ checksum = "8eaf4bc02d17cbdd7ff4c7438cafcdf7fb9a4613313ad11b4f8fefe7d3fa0130" [[package]] name = "js-sys" -version = "0.3.56" +version = "0.3.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a38fc24e30fd564ce974c02bf1d337caddff65be6cc4735a1f7eab22a7440f04" +checksum = "671a26f820db17c2a2750743f1dd03bafd15b98c9f30c7c2628c024c05d73397" dependencies = [ "wasm-bindgen", ] @@ -644,15 +621,15 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" [[package]] name = "libc" -version = "0.2.119" +version = "0.2.122" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1bf2e165bb3457c8e098ea76f3e3bc9db55f87aa90d52d0e6be741470916aaa4" +checksum = "ec647867e2bf0772e28c8bcde4f0d19a9216916e890543b5a03ed8ef27b8f259" [[package]] name = "libloading" -version = "0.7.0" +version = "0.7.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6f84d96438c15fcd6c3f244c8fce01d1e2b9c6b5623e9c711dc9286d8fc92d6a" +checksum = "efbc0f03f9a775e9f6aed295c6a1ba2253c5757a9e03d55c6caa46a681abcddd" dependencies = [ "cfg-if 1.0.0", "winapi", @@ -660,18 +637,19 @@ dependencies = [ [[package]] name = "lock_api" -version = "0.4.2" +version = "0.4.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dd96ffd135b2fd7b973ac026d28085defbe8983df057ced3eb4f2130b0831312" +checksum = "327fa5b6a6940e4699ec49a9beae1ea4845c6bab9314e4f84ac68742139d8c53" dependencies = [ + "autocfg", "scopeguard", ] [[package]] name = "log" -version = "0.4.14" +version = "0.4.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51b9bbe6c47d51fc3e1a9b945965946b4c44142ab8792c50835a980d362c2710" +checksum = "6389c490849ff5bc16be905ae24bc913a9c8892e19b2341dbc175e14c341c2b8" dependencies = [ "cfg-if 1.0.0", ] @@ -698,10 +676,9 @@ dependencies = [ [[package]] name = "lsp-types" -version = "0.86.0" -source = "git+https://github.com/gluon-lang/lsp-types?branch=master#1be3254cd8589950a224d92456840c369cd1553a" +version = "0.93.0" +source = "git+https://github.com/gluon-lang/lsp-types?branch=master#36e19b01a385acf475d9fdfaef6738cf76f1a3d8" dependencies = [ - "base64", "bitflags", "serde", "serde_json", @@ -720,15 +697,9 @@ dependencies = [ [[package]] name = "matches" -version = "0.1.8" +version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08" - -[[package]] -name = "maybe-uninit" -version = "2.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" +checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f" [[package]] name = "mcshader-lsp" @@ -764,9 +735,9 @@ dependencies = [ [[package]] name = "memchr" -version = "2.3.4" +version = "2.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0ee1c47aaa256ecabcaea351eae4a9b01ef39ed810004e298d2511ed284b1525" +checksum = "308cc39be01b73d0d18f82a0e7b2a3df85245f84af96fdddc5d202d27e47b86a" [[package]] name = "memmap2" @@ -779,23 +750,30 @@ dependencies = [ [[package]] name = "memoffset" -version = "0.6.4" +version = "0.6.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "59accc507f1338036a0477ef61afdae33cde60840f4dfe481319ce3ad116ddf9" +checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce" dependencies = [ "autocfg", ] [[package]] -name = "mio" -version = "0.8.0" +name = "minimal-lexical" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ba272f85fa0b41fc91872be579b3bbe0f56b792aa361a380eb669469f68dafb2" +checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" + +[[package]] +name = "mio" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "52da4364ffb0e4fe33a9841a98a3f3014fb964045ce4f7a45a398243c8d6b0c9" dependencies = [ "libc", "log", "miow", "ntapi", + "wasi 0.11.0+wasi-snapshot-preview1", "winapi", ] @@ -903,12 +881,12 @@ dependencies = [ [[package]] name = "nom" -version = "6.0.1" +version = "7.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "88034cfd6b4a0d54dd14f4a507eceee36c0b70e5a02236c4e4df571102be17f0" +checksum = "a8903e5a29a317527874d0402f867152a3d21c908bb0b933e416c65e301d4c36" dependencies = [ "memchr", - "version_check", + "minimal-lexical", ] [[package]] @@ -919,9 +897,9 @@ checksum = "61807f77802ff30975e01f4f071c8ba10c022052f98b3294119f3e615d13e5be" [[package]] name = "ntapi" -version = "0.3.6" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3f6bb902e437b6d86e03cce10a7e2af662292c5dfef23b65899ea3ac9354ad44" +checksum = "c28774a7fd2fbb4f0babd8237ce554b73af68021b5f695a3cebd6c59bac0980f" dependencies = [ "winapi", ] @@ -1005,19 +983,18 @@ dependencies = [ [[package]] name = "num_enum" -version = "0.5.4" +version = "0.5.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3f9bd055fb730c4f8f4f57d45d35cd6b3f0980535b056dc7ff119cee6a66ed6f" +checksum = "cf5395665662ef45796a4ff5486c5d41d29e0c09640af4c5f17fd94ee2c119c9" dependencies = [ - "derivative", "num_enum_derive", ] [[package]] name = "num_enum_derive" -version = "0.5.4" +version = "0.5.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "486ea01961c4a818096de679a8b740b26d9033146ac5291b1c98557658f8cdd9" +checksum = "3b0498641e53dd6ac1a4f22547548caa6864cc4933784319cd1775271c5a46ce" dependencies = [ "proc-macro-crate", "proc-macro2", @@ -1027,9 +1004,9 @@ dependencies = [ [[package]] name = "num_threads" -version = "0.1.4" +version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c539a50b93a303167eded6e8dff5220cd39447409fb659f4cd24b1f72fe4f133" +checksum = "aba1801fb138d8e85e11d0fc70baf4fe1cdfffda7c6cd34a854905df588e5ed0" dependencies = [ "libc", ] @@ -1045,9 +1022,9 @@ dependencies = [ [[package]] name = "once_cell" -version = "1.7.2" +version = "1.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af8b08b04175473088b46763e51ee54da5f9a164bc162f615b91bc179dbf15a3" +checksum = "87f3e037eac156d1775da914196f0f37741a274155e34a0b7e427c35d2a2ecb9" [[package]] name = "osmesa-sys" @@ -1060,18 +1037,18 @@ dependencies = [ [[package]] name = "output_vt100" -version = "0.1.2" +version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "53cdc5b785b7a58c5aad8216b3dfa114df64b0b06ae6e1501cef91df2fbdf8f9" +checksum = "628223faebab4e3e40667ee0b2336d34a5b960ff60ea743ddfdbcf7770bcfb66" dependencies = [ "winapi", ] [[package]] name = "parking_lot" -version = "0.11.1" +version = "0.11.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6d7744ac029df22dca6284efe4e898991d28e3085c706c972bcd7da4a27a15eb" +checksum = "7d17b78036a60663b797adeaee46f5c9dfebb86948d1255007a1d6be0271ff99" dependencies = [ "instant", "lock_api", @@ -1080,14 +1057,14 @@ dependencies = [ [[package]] name = "parking_lot_core" -version = "0.8.2" +version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ccb628cad4f84851442432c60ad8e1f607e29752d0bf072cbd0baf28aa34272" +checksum = "d76e8e1493bcac0d2766c42737f34458f1c8c50c0d23bcb24ea953affb273216" dependencies = [ "cfg-if 1.0.0", "instant", "libc", - "redox_syscall 0.1.57", + "redox_syscall", "smallvec", "winapi", ] @@ -1116,9 +1093,9 @@ dependencies = [ [[package]] name = "pkg-config" -version = "0.3.19" +version = "0.3.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3831453b3449ceb48b6d9c7ad7c96d5ea673e9b470a1dc578c2ce6521230884c" +checksum = "1df8c4ec4b0627e53bdf214615ad287367e482558cf84b109250b37464dc03ae" [[package]] name = "ppv-lite86" @@ -1142,25 +1119,25 @@ dependencies = [ [[package]] name = "predicates-core" -version = "1.0.1" +version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fb3dbeaaf793584e29c58c7e3a82bbb3c7c06b63cea68d13b0e3cddc124104dc" +checksum = "da1c2388b1513e1b605fcec39a95e0a9e8ef088f71443ef37099fa9ae6673fcb" [[package]] name = "predicates-tree" -version = "1.0.1" +version = "1.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aee95d988ee893cb35c06b148c80ed2cd52c8eea927f50ba7a0be1a786aeab73" +checksum = "4d86de6de25020a36c6d3643a86d9a6a9f552107c0559c60ea03551b5e16c032" dependencies = [ "predicates-core", - "treeline", + "termtree", ] [[package]] name = "pretty_assertions" -version = "1.1.0" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "76d5b548b725018ab5496482b45cb8bef21e9fed1858a6d674e3a8a0f0bb5d50" +checksum = "c89f989ac94207d048d92db058e4f6ec7342b0971fc58d1271ca148b799b3563" dependencies = [ "ansi_term", "ctor", @@ -1170,9 +1147,9 @@ dependencies = [ [[package]] name = "proc-macro-crate" -version = "1.1.0" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ebace6889caf889b4d3f76becee12e90353f2b8c7d875534a71e5742f8f6f83" +checksum = "e17d47ce914bf4de440332250b0edd23ce48c005f59fab39d3335866b114f11a" dependencies = [ "thiserror", "toml", @@ -1180,18 +1157,18 @@ dependencies = [ [[package]] name = "proc-macro2" -version = "1.0.36" +version = "1.0.37" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c7342d5883fbccae1cc37a2353b09c87c9b0f3afd73f5fb9bba687a1f733b029" +checksum = "ec757218438d5fda206afc041538b2f6d889286160d649a86a24d37e1235afd1" dependencies = [ "unicode-xid", ] [[package]] name = "quote" -version = "1.0.15" +version = "1.0.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "864d3e96a899863136fc6e99f3d7cae289dafe43bf2c5ac19b70df7210c0a145" +checksum = "a1feb54ed693b93a84e14094943b84b7c4eae204c512b7ccb95ab0c66d278ad1" dependencies = [ "proc-macro2", ] @@ -1256,9 +1233,9 @@ dependencies = [ [[package]] name = "raw-window-handle" -version = "0.4.2" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fba75eee94a9d5273a68c9e1e105d9cffe1ef700532325788389e5a83e2522b7" +checksum = "b800beb9b6e7d2df1fe337c9e3d04e3af22a124460fb4c30fcc22c9117cefb41" dependencies = [ "cty", ] @@ -1274,46 +1251,40 @@ dependencies = [ [[package]] name = "redox_syscall" -version = "0.1.57" +version = "0.2.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce" - -[[package]] -name = "redox_syscall" -version = "0.2.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8380fe0152551244f0747b1bf41737e0f8a74f97a14ccefd1148187271634f3c" +checksum = "62f25bc4c7e55e0b0b7a1d43fb893f4fa1361d0abe38b9ce4f323c2adfe6ef42" dependencies = [ "bitflags", ] [[package]] name = "redox_users" -version = "0.4.0" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "528532f3d801c87aec9def2add9ca802fe569e44a544afe633765267840abe64" +checksum = "b033d837a7cf162d7993aded9304e30a83213c648b6e389db233191f891e5c2b" dependencies = [ "getrandom", - "redox_syscall 0.2.11", + "redox_syscall", + "thiserror", ] [[package]] name = "regex" -version = "1.4.3" +version = "1.5.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9251239e129e16308e70d853559389de218ac275b515068abc96829d05b948a" +checksum = "1a11647b6b25ff05a515cb92c365cec08801e83423a235b51e231e1808747286" dependencies = [ "aho-corasick", "memchr", "regex-syntax", - "thread_local", ] [[package]] name = "regex-syntax" -version = "0.6.22" +version = "0.6.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5eb417147ba9860a96cfe72a0b93bf88fee1744b5636ec99ab20c1aa9376581" +checksum = "f497285884f3fcff424ffc933e56d7cbca511def0c9831a7f9b5f6153e3cc89b" [[package]] name = "remove_dir_all" @@ -1327,7 +1298,7 @@ dependencies = [ [[package]] name = "rust_lsp" version = "0.6.0" -source = "git+https://github.com/Strum355/RustLSP?branch=master#1f6d533300fd64a739930fd42f0572328be48469" +source = "git+https://github.com/Strum355/RustLSP?branch=master#22694b563c8bae1a64cf91f91e80c1933693203f" dependencies = [ "log", "lsp-types", @@ -1363,9 +1334,9 @@ checksum = "f2cc38e8fa666e2de3c4aba7edeb5ffc5246c1c2ed0e3d17e560aeeba736b23f" [[package]] name = "ryu" -version = "1.0.5" +version = "1.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "71d301d4193d031abdd79ff7e3dd721168a9572ef3fe51a1517aba235bd8f86e" +checksum = "73b4b750c782965c211b42f022f59af1fbceabdd026623714f104152f1ec149f" [[package]] name = "same-file" @@ -1390,18 +1361,18 @@ checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" [[package]] name = "serde" -version = "1.0.123" +version = "1.0.136" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "92d5161132722baa40d802cc70b15262b98258453e85e5d1d365c757c73869ae" +checksum = "ce31e24b01e1e524df96f1c2fdd054405f8d7376249a5110886fb4b658484789" dependencies = [ "serde_derive", ] [[package]] name = "serde_derive" -version = "1.0.123" +version = "1.0.136" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9391c295d64fc0abb2c556bad848f33cb8296276b1ad2677d1ae1ace4f258f31" +checksum = "08597e7152fcd306f41838ed3e37be9eaeed2b61c42e2117266a554fab4662f9" dependencies = [ "proc-macro2", "quote", @@ -1410,20 +1381,20 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.61" +version = "1.0.79" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4fceb2595057b6891a4ee808f70054bd2d12f0e97f1cbb78689b59f676df325a" +checksum = "8e8d9fa5c3b304765ce1fd9c4c8a3de2c8db365a5b91be52f186efc675681d95" dependencies = [ - "itoa 0.4.7", + "itoa", "ryu", "serde", ] [[package]] name = "serde_repr" -version = "0.1.6" +version = "0.1.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2dc6b7951b17b051f3210b063f12cc17320e2fe30ae05b0fe2a3abb068551c76" +checksum = "98d0516900518c29efa217c298fa1f4e6c6ffc85ae29fd7f4ee48f176e1a9ed5" dependencies = [ "proc-macro2", "quote", @@ -1482,15 +1453,15 @@ dependencies = [ [[package]] name = "smallvec" -version = "1.6.1" +version = "1.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fe0f37c9e8f3c5a4a66ad655a93c74daac4ad00c441533bf5c6e7990bb42604e" +checksum = "f2dd574626839106c320a323308629dcb1acfc96e32a8cba364ddc61ac23ee83" [[package]] name = "smithay-client-toolkit" -version = "0.15.3" +version = "0.15.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1325f292209cee78d5035530932422a30aa4c8fda1a16593ac083c1de211e68a" +checksum = "8a28f16a97fa0e8ce563b2774d1e732dd5d4025d2772c5dba0a41a0f90a29da3" dependencies = [ "bitflags", "calloop", @@ -1513,9 +1484,9 @@ checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" [[package]] name = "syn" -version = "1.0.86" +version = "1.0.91" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a65b3f4ffa0092e9887669db0eae07941f023991ab58ea44da8fe8e2d511c6b" +checksum = "b683b2b825c8eef438b77c36a06dc262294da3d5a5813fac20da149241dcd44d" dependencies = [ "proc-macro2", "quote", @@ -1544,19 +1515,25 @@ dependencies = [ ] [[package]] -name = "thiserror" -version = "1.0.29" +name = "termtree" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "602eca064b2d83369e2b2f34b09c70b605402801927c65c11071ac911d299b88" +checksum = "507e9898683b6c43a9aa55b64259b721b52ba226e0f3779137e50ad114a4c90b" + +[[package]] +name = "thiserror" +version = "1.0.30" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "854babe52e4df1653706b98fcfc05843010039b406875930a70e4d9644e5c417" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.29" +version = "1.0.30" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bad553cc2c78e8de258400763a647e80e6d1b31ee237275d756f6836d204494c" +checksum = "aa32fd3f627f367fe16f893e2597ae3c05020f8bba2666a4e6ea73d377e5714b" dependencies = [ "proc-macro2", "quote", @@ -1574,11 +1551,11 @@ dependencies = [ [[package]] name = "time" -version = "0.3.7" +version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "004cbc98f30fa233c61a38bc77e96a9106e65c88f2d3bef182ae952027e5753d" +checksum = "c2702e08a7a860f005826c6815dcac101b19b5eb330c27fe4a5928fec1d20ddd" dependencies = [ - "itoa 1.0.1", + "itoa", "libc", "num_threads", "time-macros", @@ -1586,15 +1563,15 @@ dependencies = [ [[package]] name = "time-macros" -version = "0.2.3" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "25eb0ca3468fc0acc11828786797f6ef9aa1555e4a211a60d64cc8e4d1be47d6" +checksum = "42657b1a6f4d817cda8e7a0ace261fe0cc946cf3a80314390b22cc61ae080792" [[package]] name = "tinyvec" -version = "1.1.0" +version = "1.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ccf8dbc19eb42fba10e8feaaec282fb50e2c14b2726d6301dbfeed0f73306a6f" +checksum = "2c1c1d5a42b6245520c249549ec267180beaffcc0615401ac8e31853d4b6d8d2" dependencies = [ "tinyvec_macros", ] @@ -1634,41 +1611,32 @@ dependencies = [ "tree-sitter", ] -[[package]] -name = "treeline" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a7f741b240f1a48843f9b8e0444fb55fb2a4ff67293b50a9179dfd5ea67f8d41" - [[package]] name = "unicode-bidi" -version = "0.3.4" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5" -dependencies = [ - "matches", -] +checksum = "1a01404663e3db436ed2746d9fefef640d868edae3cceb81c3b8d5732fda678f" [[package]] name = "unicode-normalization" -version = "0.1.16" +version = "0.1.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a13e63ab62dbe32aeee58d1c5408d35c36c392bba5d9d3142287219721afe606" +checksum = "d54590932941a9e9266f0832deed84ebe1bf2e4c9e4a3554d393d18f5e854bf9" dependencies = [ "tinyvec", ] [[package]] name = "unicode-xid" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f7fe0bb3479651439c9112f72b6c505038574c9fbb575ed1bf3b797fa39dd564" +checksum = "8ccb82d61f80a663efe1f787a51b16b5a51e3314d6ac365b08639f52387b33f3" [[package]] name = "url" -version = "2.2.0" +version = "2.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5909f2b0817350449ed73e8bcd81c8c3c8d9a7a5d8acba4b27db277f1868976e" +checksum = "a507c383b2d33b5fc35d1861e77e6b383d158b2da5e14fe51b83dfedf6fd578c" dependencies = [ "form_urlencoded", "idna", @@ -1677,17 +1645,11 @@ dependencies = [ "serde", ] -[[package]] -name = "version_check" -version = "0.9.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5a972e5669d67ba988ce3dc826706fb0a8b01471c088cb0b6110b805cc36aed" - [[package]] name = "walkdir" -version = "2.3.1" +version = "2.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "777182bc735b6424e1a57516d35ed72cb8019d85c8c9bf536dccb3445c1a2f7d" +checksum = "808cf2735cd4b6866113f648b791c6adc5714537bc222d9347bb203386ffda56" dependencies = [ "same-file", "winapi", @@ -1701,10 +1663,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6" [[package]] -name = "wasm-bindgen" -version = "0.2.79" +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "25f1af7423d8588a3d840681122e72e6a24ddbcb3f0ec385cac0d12d24256c06" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + +[[package]] +name = "wasm-bindgen" +version = "0.2.80" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "27370197c907c55e3f1a9fbe26f44e937fe6451368324e009cba39e139dc08ad" dependencies = [ "cfg-if 1.0.0", "wasm-bindgen-macro", @@ -1712,9 +1680,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-backend" -version = "0.2.79" +version = "0.2.80" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8b21c0df030f5a177f3cba22e9bc4322695ec43e7257d865302900290bcdedca" +checksum = "53e04185bfa3a779273da532f5025e33398409573f348985af9a1cbf3774d3f4" dependencies = [ "bumpalo", "lazy_static", @@ -1727,9 +1695,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro" -version = "0.2.79" +version = "0.2.80" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2f4203d69e40a52ee523b2529a773d5ffc1dc0071801c87b3d270b471b80ed01" +checksum = "17cae7ff784d7e83a2fe7611cfe766ecf034111b49deb850a3dc7699c08251f5" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -1737,9 +1705,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.79" +version = "0.2.80" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfa8a30d46208db204854cadbb5d4baf5fcf8071ba5bf48190c3e59937962ebc" +checksum = "99ec0dc7a4756fffc231aab1b9f2f578d23cd391390ab27f952ae0c9b3ece20b" dependencies = [ "proc-macro2", "quote", @@ -1750,9 +1718,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-shared" -version = "0.2.79" +version = "0.2.80" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3d958d035c4438e28c70e4321a2911302f10135ce78a9c7834c0cab4123d06a2" +checksum = "d554b7f530dee5964d9a9468d95c1f8b8acae4f282807e7d27d4b03099a46744" [[package]] name = "wayland-client" @@ -1839,9 +1807,9 @@ dependencies = [ [[package]] name = "web-sys" -version = "0.3.56" +version = "0.3.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c060b319f29dd25724f09a2ba1418f142f539b2be99fbf4d2d5a8f7330afb8eb" +checksum = "7b17e741662c70c8bd24ac5c5b18de314a2c26c32bf8346ee1e6f53de919c283" dependencies = [ "js-sys", "wasm-bindgen", @@ -1886,8 +1854,8 @@ checksum = "9b43cc931d58b99461188607efd7acb2a093e65fc621f54cad78517a6063e73a" dependencies = [ "bitflags", "cocoa", - "core-foundation 0.9.1", - "core-graphics 0.22.2", + "core-foundation 0.9.3", + "core-graphics 0.22.3", "core-video-sys", "dispatch", "instant", @@ -1913,27 +1881,26 @@ dependencies = [ [[package]] name = "x11-dl" -version = "2.18.5" +version = "2.19.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2bf981e3a5b3301209754218f962052d4d9ee97e478f4d26d4a6eced34c1fef8" +checksum = "ea26926b4ce81a6f5d9d0f3a0bc401e5a37c6ae14a1bfaa8ff6099ca80038c59" dependencies = [ "lazy_static", "libc", - "maybe-uninit", "pkg-config", ] [[package]] name = "xcursor" -version = "0.3.3" +version = "0.3.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3a9a231574ae78801646617cefd13bfe94be907c0e4fa979cfd8b770aa3c5d08" +checksum = "463705a63313cd4301184381c5e8042f0a7e9b4bb63653f216311d4ae74690b7" dependencies = [ "nom", ] [[package]] name = "xml-rs" -version = "0.8.3" +version = "0.8.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b07db065a5cf61a7e4ba64f29e67db906fb1787316516c4e6e5ff0fea1efcd8a" +checksum = "d2d7d3948613f75c98fd9328cfdcc45acc4d360655289d0a7d4ec931392200a3" diff --git a/server/main/src/dfs.rs b/server/main/src/dfs.rs index dfba565..03be1a7 100644 --- a/server/main/src/dfs.rs +++ b/server/main/src/dfs.rs @@ -134,7 +134,7 @@ pub mod error { impl From for Diagnostic { fn from(e: CycleError) -> Diagnostic { Diagnostic { - severity: Some(DiagnosticSeverity::Error), + severity: Some(DiagnosticSeverity::ERROR), range: Range::new(Position::new(0, 0), Position::new(0, 500)), source: Some(consts::SOURCE.into()), message: e.into(), diff --git a/server/main/src/diagnostics_parser.rs b/server/main/src/diagnostics_parser.rs index f798827..978dcd9 100644 --- a/server/main/src/diagnostics_parser.rs +++ b/server/main/src/diagnostics_parser.rs @@ -73,11 +73,11 @@ impl<'a, T: opengl::ShaderValidator + ?Sized> DiagnosticsParser<'a, T> { let severity = match diagnostic_capture.name("severity") { Some(c) => match c.as_str().to_lowercase().as_str() { - "error" => DiagnosticSeverity::Error, - "warning" => DiagnosticSeverity::Warning, - _ => DiagnosticSeverity::Information, + "error" => DiagnosticSeverity::ERROR, + "warning" => DiagnosticSeverity::WARNING, + _ => DiagnosticSeverity::INFORMATION, }, - _ => DiagnosticSeverity::Information, + _ => DiagnosticSeverity::INFORMATION, }; let origin = match diagnostic_capture.name("filepath") { diff --git a/server/main/src/main.rs b/server/main/src/main.rs index 01c4217..90f4d58 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -1,4 +1,5 @@ #![feature(once_cell)] +#![feature(option_get_or_insert_default)] use merge_views::FilialTuple; use rust_lsp::jsonrpc::{method_types::*, *}; @@ -517,6 +518,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { let capabilities = ServerCapabilities { definition_provider: Some(OneOf::Left(true)), references_provider: Some(OneOf::Left(true)), + document_symbol_provider: Some(OneOf::Left(true)), document_link_provider: Some(DocumentLinkOptions { resolve_provider: None, work_done_progress_options: WorkDoneProgressOptions { work_done_progress: None }, @@ -529,7 +531,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { open_close: Some(true), will_save: None, will_save_wait_until: None, - change: Some(TextDocumentSyncKind::Full), + change: Some(TextDocumentSyncKind::FULL), save: Some(TextDocumentSyncSaveOptions::SaveOptions(SaveOptions { include_text: Some(true) })), })), ..ServerCapabilities::default() @@ -661,7 +663,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { .send_notification( ShowMessage::METHOD, ShowMessageParams { - typ: MessageType::Info, + typ: MessageType::INFO, message: format!("Command {} executed successfully.", params.command), }, ) @@ -674,7 +676,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { .send_notification( ShowMessage::METHOD, ShowMessageParams { - typ: MessageType::Error, + typ: MessageType::ERROR, message: format!("Failed to execute `{}`. Reason: {}", params.command, err), }, ) @@ -751,11 +753,38 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { completable.complete(Err(Self::error_not_available(()))); } - fn document_symbols(&mut self, _: DocumentSymbolParams, completable: LSCompletable>) { - completable.complete(Err(Self::error_not_available(()))); + fn document_symbols(&mut self, params: DocumentSymbolParams, completable: LSCompletable) { + logging::slog_with_trace_id(|| { + let path = PathBuf::from_url(params.text_document.uri); + if !path.starts_with(&self.root) { + return; + } + let parser = &mut self.tree_sitter.borrow_mut(); + let parser_ctx = match navigation::ParserContext::new(parser, &path) { + Ok(ctx) => ctx, + Err(e) => { + return completable.complete(Err(MethodError { + code: 42069, + message: format!("error building parser context: error={}, path={:?}", e, path), + data: (), + })) + } + }; + + match parser_ctx.list_symbols(&path) { + Ok(symbols) => completable.complete(Ok(DocumentSymbolResponse::from(symbols.unwrap_or_default()))), + Err(e) => { + return completable.complete(Err(MethodError { + code: 42069, + message: format!("error finding definitions: error={}, path={:?}", e, path), + data: (), + })) + } + } + }); } - fn workspace_symbols(&mut self, _: WorkspaceSymbolParams, completable: LSCompletable>) { + fn workspace_symbols(&mut self, _: WorkspaceSymbolParams, completable: LSCompletable) { completable.complete(Err(Self::error_not_available(()))); } diff --git a/server/main/src/navigation.rs b/server/main/src/navigation.rs index 884171c..d1b3c82 100644 --- a/server/main/src/navigation.rs +++ b/server/main/src/navigation.rs @@ -1,13 +1,60 @@ -use std::{fs::read_to_string, path::Path}; +use std::{collections::HashMap, fs::read_to_string, path::Path, vec}; use anyhow::Result; -use rust_lsp::lsp_types::{Location, Position, Range}; +use rust_lsp::lsp_types::{DocumentSymbol, Location, Position, Range, SymbolKind}; use slog_scope::{debug, info, trace}; use tree_sitter::{Node, Parser, Point, Query, QueryCursor, Tree}; use url::Url; use crate::linemap::LineMap; +#[derive(Clone, Debug, Hash, PartialEq, Eq, Default)] +struct SymbolName(String); + +impl SymbolName { + // construct a new SymbolName from a node and its node ID for overload disambiguating. + fn new(node: &Node, source: &str, node_id: usize) -> Self { + let mut fqname = vec![format!("{}[{}]", node.utf8_text(source.as_bytes()).unwrap(), node_id)]; + + // first node will always have a parent + let mut prev = *node; + let mut node = node.parent().unwrap(); + + loop { + match (node.kind(), prev.kind()) { + ("function_definition", "compound_statement") => { + let func_ident = node.child_by_field_name("declarator").unwrap().child(0).unwrap(); + fqname.push(format!("{}[{}]", func_ident.utf8_text(source.as_bytes()).unwrap(), func_ident.id())); + } + ("struct_specifier", "field_declaration_list") => { + let struct_ident = node.child_by_field_name("name").unwrap(); + fqname.push(format!("{}[{}]", struct_ident.utf8_text(source.as_bytes()).unwrap(), struct_ident.id())); + } + _ => (), + } + + prev = node; + node = match node.parent() { + Some(n) => n, + None => break, + }; + } + + fqname.reverse(); + SymbolName(fqname.join("/")) + } + + fn parent(&self) -> Option { + self.0.rsplit_once('/').map(|(left, _)| SymbolName(left.to_string())) + } +} + +impl slog::Value for SymbolName { + fn serialize(&self, record: &slog::Record, key: slog::Key, serializer: &mut dyn slog::Serializer) -> slog::Result { + self.0.serialize(record, key, serializer) + } +} + macro_rules! find_function_def_str { () => { r#" @@ -35,24 +82,58 @@ macro_rules! find_function_refs_str { macro_rules! find_variable_def_str { () => { r#" - ( - [ - (init_declarator - (identifier) @variable) - - (parameter_declaration - (identifier) @variable) - - (declaration - (identifier) @variable) + [ + (init_declarator + (identifier) @variable) - (#match? @variable "^{}$") - ] - ) + (parameter_declaration + (identifier) @variable) + + (declaration + (identifier) @variable) + + (#match? @variable "^{}$") + ] "# }; } +const LIST_SYMBOLS_STR: &str = r#" + ; global consts + (declaration + (type_qualifier) @const_qualifier + (init_declarator + (identifier) @const_ident)) + (#match? @const_qualifier "^const") + + ; global uniforms, varyings, struct variables etc + (translation_unit + (declaration + (identifier) @ident)) + + ; #defines + (preproc_def + (identifier) @define_ident) + + ; function definitions + (function_declarator + (identifier) @func_ident) + + ; struct definitions + (struct_specifier + (type_identifier) @struct_ident) + + ; struct fields + (struct_specifier + (field_declaration_list + (field_declaration + [ + (field_identifier) @field_ident + (array_declarator + (field_identifier) @field_ident) + ])) @field_list) +"#; + pub struct ParserContext<'a> { source: String, tree: Tree, @@ -76,6 +157,89 @@ impl<'a> ParserContext<'a> { }) } + pub fn list_symbols(&self, _path: &Path) -> Result>> { + let query = Query::new(tree_sitter_glsl::language(), LIST_SYMBOLS_STR)?; + let mut query_cursor = QueryCursor::new(); + + let mut parent_child_vec: Vec<(Option, DocumentSymbol)> = vec![]; + let mut fqname_to_index: HashMap = HashMap::new(); + + for (m, _) in query_cursor.captures(&query, self.root_node(), self.source.as_bytes()) { + if m.captures.is_empty() { + continue; + } + + let mut capture_iter = m.captures.iter(); + + let capture = capture_iter.next().unwrap(); + let capture_name = query.capture_names()[capture.index as usize].as_str(); + + trace!("next capture name"; "name" => capture_name, "capture" => format!("{:?}", capture)); + + let (kind, node) = match capture_name { + "const_qualifier" => (SymbolKind::CONSTANT, capture_iter.next().unwrap().node), + "ident" => (SymbolKind::VARIABLE, capture.node), + "func_ident" => (SymbolKind::FUNCTION, capture.node), + "define_ident" => (SymbolKind::STRING, capture.node), + "struct_ident" => (SymbolKind::STRUCT, capture.node), + "field_list" => (SymbolKind::FIELD, capture_iter.next().unwrap().node), + _ => (SymbolKind::NULL, capture.node), + }; + + let range = Range { + start: Position { + line: node.start_position().row as u32, + character: node.start_position().column as u32, + }, + end: Position { + line: node.end_position().row as u32, + character: node.end_position().column as u32, + }, + }; + + let name = node.utf8_text(self.source.as_bytes()).unwrap().to_string(); + + let fqname = SymbolName::new(&node, self.source.as_str(), node.id()); + + debug!("found symbol"; "node_name" => &name, "kind" => format!("{:?}", kind), "fqname" => &fqname); + + let child_symbol = DocumentSymbol { + name, + detail: None, + kind, + tags: None, + deprecated: None, + range, + selection_range: range, + children: None, + }; + parent_child_vec.push((fqname.parent(), child_symbol)); + trace!("inserting fqname"; "fqname" => &fqname, "index" => parent_child_vec.len() - 1); + fqname_to_index.insert(fqname, parent_child_vec.len() - 1); + } + + // let mut symbols = vec![]; + for i in 1..parent_child_vec.len() { + let (left, right) = parent_child_vec.split_at_mut(i); + let parent = &right[0].0; + let child = &right[0].1; + if let Some(parent) = parent { + trace!("finding parent"; "parent_symbol_name" => &parent, "child" => format!("{:?}", child), "split_point" => i, "left_len" => left.len(), "right_len" => right.len()); + let parent_index = fqname_to_index.get(parent).unwrap(); + let parent_sym = &mut left[*parent_index]; + parent_sym.1.children.get_or_insert_default().push(right[0].1.clone()) + } + } + + let symbols = parent_child_vec + .iter() + .filter(|tuple| tuple.0.is_none()) + .map(|tuple| tuple.1.clone()) + .collect(); + + Ok(Some(symbols)) + } + pub fn find_definitions(&self, path: &Path, point: Position) -> Result>> { let current_node = match self.find_node_at_point(point) { Some(node) => node, @@ -94,12 +258,10 @@ impl<'a> ParserContext<'a> { let query_str = format!(find_function_def_str!(), current_node.utf8_text(self.source.as_bytes())?); self.simple_global_search(path, &query_str)? } - ("identifier", "argument_list") | - ("identifier", "field_expression") | - ("identifier", "binary_expression") | - ("identifier", "assignment_expression") => { - self.tree_climbing_search(path, current_node)? - } + ("identifier", "argument_list") + | ("identifier", "field_expression") + | ("identifier", "binary_expression") + | ("identifier", "assignment_expression") => self.tree_climbing_search(path, current_node)?, _ => return Ok(None), }; From fecc41168abe9d7d898a3b679b8754591bb1f508 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Mon, 18 Apr 2022 01:08:53 +0100 Subject: [PATCH 40/56] fix include merging for when a file imports another file more than once directly --- server/main/src/commands/merged_includes.rs | 4 +- server/main/src/dfs.rs | 22 +- server/main/src/graph.rs | 146 +++-- server/main/src/main.rs | 77 +-- server/main/src/merge_views.rs | 620 +++++++++++--------- server/main/src/navigation.rs | 6 +- server/main/testdata/05/final.fsh.merge | 2 +- server/main/testdata/06/final.fsh | 9 + server/main/testdata/06/final.fsh.merge | 17 + server/main/testdata/06/test.glsl | 3 + 10 files changed, 526 insertions(+), 380 deletions(-) create mode 100644 server/main/testdata/06/final.fsh create mode 100644 server/main/testdata/06/final.fsh.merge create mode 100644 server/main/testdata/06/test.glsl diff --git a/server/main/src/commands/merged_includes.rs b/server/main/src/commands/merged_includes.rs index 3c9fea8..d932213 100644 --- a/server/main/src/commands/merged_includes.rs +++ b/server/main/src/commands/merged_includes.rs @@ -51,7 +51,7 @@ impl VirtualMergedDocument { for node in nodes { let graph = self.graph.borrow(); - let path = graph.get_node(node.0); + let path = graph.get_node(node.child); if sources.contains_key(&path) { continue; @@ -103,7 +103,7 @@ impl Invokeable for VirtualMergedDocument { let mut source_mapper = SourceMapper::new(all_sources.len()); let graph = self.graph.borrow(); - let view = merge_views::generate_merge_list(&tree, &all_sources, &graph, &mut source_mapper); + let view = merge_views::MergeViewBuilder::new(&tree, &all_sources, &graph, &mut source_mapper).build(); return Ok(serde_json::value::Value::String(view)); } return Err(format_err!( diff --git a/server/main/src/dfs.rs b/server/main/src/dfs.rs index 03be1a7..d990bc7 100644 --- a/server/main/src/dfs.rs +++ b/server/main/src/dfs.rs @@ -56,21 +56,21 @@ impl<'a> Iterator for Dfs<'a> { fn next(&mut self) -> Option> { let parent = self.cycle.last().map(|p| p.node); - if let Some(node) = self.stack.pop() { + if let Some(child) = self.stack.pop() { self.cycle.push(VisitCount { - node, - children: self.graph.graph.edges(node).count(), + node: child, + children: self.graph.graph.edges(child).count(), touch: 1, }); - let mut children = self.graph.child_node_indexes(node); + let mut children: Vec = self.graph.child_node_indexes(child).collect(); if !children.is_empty() { // sort by line number in parent children.sort_by(|x, y| { let graph = &self.graph.graph; - let edge1 = graph.edge_weight(graph.find_edge(node, *x).unwrap()).unwrap(); - let edge2 = graph.edge_weight(graph.find_edge(node, *y).unwrap()).unwrap(); + let edge1 = graph.edge_weight(graph.find_edge(child, *x).unwrap()).unwrap(); + let edge2 = graph.edge_weight(graph.find_edge(child, *y).unwrap()).unwrap(); edge2.line.cmp(&edge1.line) }); @@ -87,7 +87,7 @@ impl<'a> Iterator for Dfs<'a> { self.reset_path_to_branch(); } - return Some(Ok((node, parent))); + return Some(Ok(FilialTuple { child, parent })); } None } @@ -189,8 +189,8 @@ mod dfs_test { collection.push(i.unwrap()); } - let nodes: Vec = collection.iter().map(|n| n.0).collect(); - let parents: Vec> = collection.iter().map(|n| n.1).collect(); + let nodes: Vec = collection.iter().map(|n| n.child).collect(); + let parents: Vec> = collection.iter().map(|n| n.parent).collect(); // 0 // / \ // 1 2 @@ -237,8 +237,8 @@ mod dfs_test { collection.push(i.unwrap()); } - let nodes: Vec = collection.iter().map(|n| n.0).collect(); - let parents: Vec> = collection.iter().map(|n| n.1).collect(); + let nodes: Vec = collection.iter().map(|n| n.child).collect(); + let parents: Vec> = collection.iter().map(|n| n.parent).collect(); // 0 // / \ // 1 2 diff --git a/server/main/src/graph.rs b/server/main/src/graph.rs index 3891392..993fae1 100644 --- a/server/main/src/graph.rs +++ b/server/main/src/graph.rs @@ -1,6 +1,7 @@ use petgraph::stable_graph::EdgeIndex; use petgraph::stable_graph::NodeIndex; use petgraph::stable_graph::StableDiGraph; +use petgraph::visit::EdgeRef; use petgraph::Direction; use std::{ @@ -53,20 +54,27 @@ impl CachedStableGraph { } } + // Returns the `PathBuf` for a given `NodeIndex` pub fn get_node(&self, node: NodeIndex) -> PathBuf { PathBuf::from_str(&self.graph[node]).unwrap() } - pub fn get_edge_meta(&self, parent: NodeIndex, child: NodeIndex) -> &IncludePosition { - self.graph.edge_weight(self.graph.find_edge(parent, child).unwrap()).unwrap() - } - - #[allow(dead_code)] - pub fn remove_node(&mut self, name: &Path) { - let idx = self.cache.remove(name); - if let Some(idx) = idx { - self.graph.remove_node(idx); - } + /// returns an iterator over all the `IncludePosition`'s between a parent and its child for all the positions + /// that the child may be imported into the parent, in order of import. + pub fn get_edge_metas(&self, parent: NodeIndex, child: NodeIndex) -> impl Iterator + '_ { + let mut edges = self + .graph + .edges(parent) + .filter_map(move |edge| { + let target = self.graph.edge_endpoints(edge.id()).unwrap().1; + if target != child { + return None; + } + Some(self.graph[edge.id()]) + }) + .collect::>(); + edges.sort_by(|x, y| x.line.cmp(&y.line)); + edges.into_iter() } pub fn add_node(&mut self, name: &Path) -> NodeIndex { @@ -83,54 +91,24 @@ impl CachedStableGraph { self.graph.add_edge(parent, child, meta) } - pub fn remove_edge(&mut self, parent: NodeIndex, child: NodeIndex) { - let edge = self.graph.find_edge(parent, child).unwrap(); - self.graph.remove_edge(edge); - } - - #[allow(dead_code)] - pub fn edge_weights(&self, node: NodeIndex) -> Vec { - self.graph.edges(node).map(|e| e.weight().clone()).collect() - } - - #[allow(dead_code)] - pub fn child_node_names(&self, node: NodeIndex) -> Vec { + pub fn remove_edge(&mut self, parent: NodeIndex, child: NodeIndex, position: IncludePosition) { self.graph - .neighbors(node) - .map(|n| self.reverse_index.get(&n).unwrap().clone()) - .collect() + .edges(parent) + .find(|edge| self.graph.edge_endpoints(edge.id()).unwrap().1 == child && *edge.weight() == position) + .map(|edge| edge.id()) + .and_then(|edge| self.graph.remove_edge(edge)); } - pub fn child_node_meta(&self, node: NodeIndex) -> Vec<(PathBuf, IncludePosition)> { - self.graph - .neighbors(node) - .map(|n| { - let edge = self.graph.find_edge(node, n).unwrap(); - let edge_meta = self.graph.edge_weight(edge).unwrap(); - return (self.reverse_index.get(&n).unwrap().clone(), edge_meta.clone()); - }) - .collect() + pub fn child_node_metas(&self, node: NodeIndex) -> impl Iterator + '_ { + self.graph.neighbors(node).map(move |n| { + let edge = self.graph.find_edge(node, n).unwrap(); + let edge_meta = self.graph.edge_weight(edge).unwrap(); + return (self.reverse_index.get(&n).unwrap().clone(), *edge_meta); + }) } - pub fn child_node_indexes(&self, node: NodeIndex) -> Vec { - self.graph.neighbors(node).collect() - } - - #[allow(dead_code)] - pub fn parent_node_names(&self, node: NodeIndex) -> Vec { - self.graph - .neighbors_directed(node, Direction::Incoming) - .map(|n| self.reverse_index.get(&n).unwrap().clone()) - .collect() - } - - pub fn parent_node_indexes(&self, node: NodeIndex) -> Vec { - self.graph.neighbors_directed(node, Direction::Incoming).collect() - } - - #[allow(dead_code)] - pub fn get_include_meta(&self, node: NodeIndex) -> Vec { - self.graph.edges(node).map(|e| e.weight().clone()).collect() + pub fn child_node_indexes(&self, node: NodeIndex) -> impl Iterator + '_ { + self.graph.neighbors(node) } pub fn collect_root_ancestors(&self, node: NodeIndex) -> Vec { @@ -138,6 +116,11 @@ impl CachedStableGraph { self.get_root_ancestors(node, node, &mut visited) } + // TODO: impl Iterator + fn parent_node_indexes(&self, node: NodeIndex) -> Vec { + self.graph.neighbors_directed(node, Direction::Incoming).collect() + } + fn get_root_ancestors(&self, initial: NodeIndex, node: NodeIndex, visited: &mut HashSet) -> Vec { if node == initial && !visited.is_empty() { return vec![]; @@ -163,10 +146,36 @@ impl CachedStableGraph { } } +#[cfg(test)] +impl CachedStableGraph { + fn parent_node_names(&self, node: NodeIndex) -> Vec { + self.graph + .neighbors_directed(node, Direction::Incoming) + .map(|n| self.reverse_index.get(&n).unwrap().clone()) + .collect() + } + + fn child_node_names(&self, node: NodeIndex) -> Vec { + self.graph + .neighbors(node) + .map(|n| self.reverse_index.get(&n).unwrap().clone()) + .collect() + } + + fn remove_node(&mut self, name: &Path) { + let idx = self.cache.remove(name); + if let Some(idx) = idx { + self.graph.remove_node(idx); + } + } +} + #[cfg(test)] mod graph_test { use std::path::PathBuf; + use petgraph::graph::NodeIndex; + use crate::{graph::CachedStableGraph, IncludePosition}; #[test] @@ -182,7 +191,7 @@ mod graph_test { assert_eq!(children.len(), 1); assert_eq!(children[0], Into::::into("banana".to_string())); - let children = graph.child_node_indexes(idx1); + let children: Vec = graph.child_node_indexes(idx1).collect(); assert_eq!(children.len(), 1); assert_eq!(children[0], idx2); @@ -207,10 +216,33 @@ mod graph_test { graph.remove_node(&PathBuf::from("sample")); assert_eq!(graph.graph.node_count(), 1); assert!(graph.find_node(&PathBuf::from("sample")).is_none()); + let neighbors = graph.child_node_names(idx2); assert_eq!(neighbors.len(), 0); } + #[test] + #[logging_macro::log_scope] + fn test_double_import() { + let mut graph = CachedStableGraph::new(); + + let idx0 = graph.add_node(&PathBuf::from("0")); + let idx1 = graph.add_node(&PathBuf::from("1")); + + graph.add_edge(idx0, idx1, IncludePosition { line: 2, start: 0, end: 0 }); + graph.add_edge(idx0, idx1, IncludePosition { line: 4, start: 0, end: 0 }); + + // 0 + // / \ + // 1 1 + + assert_eq!(2, graph.get_edge_metas(idx0, idx1).count()); + + let mut edge_metas = graph.get_edge_metas(idx0, idx1); + assert_eq!(Some(IncludePosition { line: 2, start: 0, end: 0 }), edge_metas.next()); + assert_eq!(Some(IncludePosition { line: 4, start: 0, end: 0 }), edge_metas.next()); + } + #[test] #[logging_macro::log_scope] fn test_collect_root_ancestors() { @@ -287,10 +319,8 @@ mod graph_test { graph.add_edge(idx1, idx3, IncludePosition { line: 5, start: 0, end: 0 }); // 0 - // | - // 1 - // \ - // 2 \ + // \ + // 2 1 // \ / // 3 diff --git a/server/main/src/main.rs b/server/main/src/main.rs index 90f4d58..a8087ed 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -16,7 +16,6 @@ use url_norm::FromUrl; use walkdir::WalkDir; -use std::collections::hash_map::RandomState; use std::collections::{HashMap, HashSet}; use std::convert::TryFrom; use std::fmt::{Debug, Display, Formatter}; @@ -60,9 +59,7 @@ mod url_norm; mod test; lazy_static! { - static ref RE_VERSION: Regex = Regex::new(r#"#version [\d]{3}"#).unwrap(); static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); - static ref RE_INCLUDE_EXTENSION: Regex = Regex::new(r#"#extension GL_GOOGLE_include_directive ?: ?require"#).unwrap(); } fn main() { @@ -119,10 +116,13 @@ pub struct MinecraftShaderLanguageServer { log_guard: Option, } -#[derive(Clone, PartialEq, Eq, Hash)] +#[derive(Clone, Copy, PartialEq, Eq, Hash)] pub struct IncludePosition { + // the 0-indexed line on which the include lives. line: usize, + // the 0-indexed char offset defining the start of the include path string. start: usize, + // the 0-indexed char offset defining the end of the include path string. end: usize, } @@ -178,8 +178,8 @@ impl MinecraftShaderLanguageServer { None => return None, }; - // TODO: include user added extensions - if ext != "vsh" && ext != "fsh" && ext != "glsl" && ext != "inc" { + // TODO: include user added extensions with a set + if ext != "vsh" && ext != "fsh" && ext != "csh" && ext != "gsh" && ext != "glsl" && ext != "inc" { return None; } @@ -251,8 +251,8 @@ impl MinecraftShaderLanguageServer { Some(n) => n, }; - let prev_children: HashSet<_, RandomState> = HashSet::from_iter(self.graph.borrow().child_node_meta(idx)); - let new_children: HashSet<_, RandomState> = includes.iter().cloned().collect(); + let prev_children: HashSet<_> = HashSet::from_iter(self.graph.borrow().child_node_metas(idx)); + let new_children: HashSet<_> = includes.iter().cloned().collect(); let to_be_added = new_children.difference(&prev_children); let to_be_removed = prev_children.difference(&new_children); @@ -265,7 +265,7 @@ impl MinecraftShaderLanguageServer { for removal in to_be_removed { let child = self.graph.borrow_mut().find_node(&removal.0).unwrap(); - self.graph.borrow_mut().remove_edge(idx, child); + self.graph.borrow_mut().remove_edge(idx, child, removal.1); } for insertion in to_be_added { @@ -325,7 +325,10 @@ impl MinecraftShaderLanguageServer { let view = { let graph = self.graph.borrow(); - merge_views::generate_merge_list(&tree, &all_sources, &graph, &mut source_mapper) + let merged_string = { + merge_views::MergeViewBuilder::new(&tree, &all_sources, &graph, &mut source_mapper).build() + }; + merged_string }; let root_path = self.graph.borrow().get_node(root); @@ -365,7 +368,7 @@ impl MinecraftShaderLanguageServer { diagnostics.extend(diagnostics_parser.parse_diagnostics_output(stdout, uri, &source_mapper, &self.graph.borrow())); } else { - let mut all_trees: Vec<(TreeType, Vec<(NodeIndex, Option<_>)>)> = Vec::new(); + let mut all_trees: Vec<(TreeType, Vec)> = Vec::new(); for root in &file_ancestors { let nodes = match self.get_dfs_for_node(*root) { @@ -408,10 +411,13 @@ impl MinecraftShaderLanguageServer { let mut source_mapper = source_mapper::SourceMapper::new(all_sources.len()); let view = { let graph = self.graph.borrow(); - merge_views::generate_merge_list(&tree.1, &all_sources, &graph, &mut source_mapper) + let merged_string = { + merge_views::MergeViewBuilder::new(&tree.1, &all_sources, &graph, &mut source_mapper).build() + }; + merged_string }; - let root_path = self.graph.borrow().get_node(tree.1[0].0); + let root_path = self.graph.borrow().get_node(tree.1.first().unwrap().child); let stdout = match self.compile_shader_source(&view, tree.0, &root_path) { Some(s) => s, None => continue, @@ -451,7 +457,7 @@ impl MinecraftShaderLanguageServer { for node in nodes { let graph = self.graph.borrow(); - let path = graph.get_node(node.0); + let path = graph.get_node(node.child); if sources.contains_key(&path) { continue; @@ -817,29 +823,30 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { .graph .borrow() .child_node_indexes(node) - .into_iter() - .filter_map(|child| { + .filter_map::, _>(|child| { let graph = self.graph.borrow(); - let value = graph.get_edge_meta(node, child); - let path = graph.get_node(child); - let url = match Url::from_file_path(&path) { - Ok(url) => url, - Err(e) => { - error!("error converting into url"; "path" => path.to_str().unwrap(), "error" => format!("{:?}", e)); - return None; - } - }; - - Some(DocumentLink { - range: Range::new( - Position::new(u32::try_from(value.line).unwrap(), u32::try_from(value.start).unwrap()), - Position::new(u32::try_from(value.line).unwrap(), u32::try_from(value.end).unwrap()), - ), - target: Some(url.clone()), - tooltip: Some(url.path().to_string()), - data: None, - }) + graph.get_edge_metas(node, child).map(|value| { + let path = graph.get_node(child); + let url = match Url::from_file_path(&path) { + Ok(url) => url, + Err(e) => { + error!("error converting into url"; "path" => path.to_str().unwrap(), "error" => format!("{:?}", e)); + return None; + } + }; + + Some(DocumentLink { + range: Range::new( + Position::new(u32::try_from(value.line).unwrap(), u32::try_from(value.start).unwrap()), + Position::new(u32::try_from(value.line).unwrap(), u32::try_from(value.end).unwrap()), + ), + target: Some(url.clone()), + tooltip: Some(url.path().to_string()), + data: None, + }) + }).collect() }) + .flatten() .collect(); debug!("document link results"; "links" => format!("{:?}", edges.iter().map(|e| (e.range, e.target.as_ref().unwrap().path())).collect::>()), diff --git a/server/main/src/merge_views.rs b/server/main/src/merge_views.rs index 8ddc73f..c61e5cc 100644 --- a/server/main/src/merge_views.rs +++ b/server/main/src/merge_views.rs @@ -11,274 +11,335 @@ use petgraph::stable_graph::NodeIndex; use crate::graph::CachedStableGraph; use crate::source_mapper::SourceMapper; +use crate::IncludePosition; -/// FilialTuple represents a tuple with a child at index 0 -/// and a parent at index 1. Parent can be nullable in the case of -/// the child being a top level node in the tree. -pub type FilialTuple = (NodeIndex, Option); +/// FilialTuple represents a tuple (not really) of a child and any legitimate +/// parent. Parent can be nullable in the case of the child being a top level +/// node in the tree. +#[derive(Hash, PartialEq, Eq, Debug, Clone, Copy)] +pub struct FilialTuple { + pub child: NodeIndex, + pub parent: Option, +} -pub fn generate_merge_list<'a>( - nodes: &'a [FilialTuple], sources: &'a HashMap, graph: &'a CachedStableGraph, source_mapper: &mut SourceMapper, -) -> String { - // contains additionally inserted lines such as #line and other directives, preamble defines etc - let mut extra_lines: Vec = Vec::new(); - extra_lines.reserve((nodes.len() * 2) + 2); +/// Merges the source strings according to the nodes comprising a tree of imports into a GLSL source string +/// that can be handed off to the GLSL compiler. +pub struct MergeViewBuilder<'a> { + nodes: &'a [FilialTuple], + nodes_peeker: Peekable>, - // list of source code views onto the below sources - let mut merge_list: LinkedList<&'a str> = LinkedList::new(); + sources: &'a HashMap, + graph: &'a CachedStableGraph, + source_mapper: &'a mut SourceMapper, // holds the offset into the child which has been added to the merge list for a parent. - // A child can have multiple parents for a given tree, hence we have to track it for - // a (child, parent) tuple instead of just the child. - let mut last_offset_set: HashMap = HashMap::new(); - - let mut nodes_iter = nodes.iter().peekable(); - - // invariant: nodes_iter always has _at least_ one element. Can't save a not-file :B - let first = nodes_iter.next().unwrap().0; - let first_path = graph.get_node(first); - let first_source = sources.get(&first_path).unwrap(); - - // seed source_mapper with top-level file - source_mapper.get_num(first); - - let version_line_offset = find_version_offset(first_source); - let version_char_offsets = char_offset_for_line(version_line_offset, first_source); - // add_preamble( - // version_line_offset, - // version_char_offsets.1, - // &first_path, - // first, - // first_source, - // &mut merge_list, - // &mut extra_lines, - // source_mapper, - // ); - - // last_offset_set.insert((first, None), version_char_offsets.1); - last_offset_set.insert((first, None), 0); - - // stack to keep track of the depth first traversal - let mut stack = VecDeque::::new(); - - create_merge_views( - &mut nodes_iter, - &mut merge_list, - &mut last_offset_set, - graph, - sources, - &mut extra_lines, - &mut stack, - source_mapper, - ); - - // now we add a view of the remainder of the root file - let offset = *last_offset_set.get(&(first, None)).unwrap(); - - let len = first_source.len(); - merge_list.push_back(&first_source[min(offset, len)..]); - - let total_len = merge_list.iter().fold(0, |a, b| a + b.len()); - - let mut merged = String::with_capacity(total_len); - merged.extend(merge_list); - - merged + // A child can have multiple parents for a given tree, and be included multiple times + // by the same parent, hence we have to track it for a ((child, parent), line) tuple + // instead of just the child or (child, parent). + last_offset_set: HashMap, + // holds, for any given filial tuple, the iterator yielding all the positions at which the child + // is included into the parent in line-sorted order. This is necessary for files that are imported + // more than once into the same parent, so we can easily get the next include position. + parent_child_edge_iterator: HashMap + 'a)>>, } -fn create_merge_views<'a>( - nodes: &mut Peekable>, merge_list: &mut LinkedList<&'a str>, last_offset_set: &mut HashMap, - graph: &'a CachedStableGraph, sources: &'a HashMap, extra_lines: &mut Vec, stack: &mut VecDeque, - source_mapper: &mut SourceMapper, -) { - loop { - let n = match nodes.next() { - Some(n) => n, - None => return, - }; +impl<'a> MergeViewBuilder<'a> { + pub fn new( + nodes: &'a [FilialTuple], sources: &'a HashMap, graph: &'a CachedStableGraph, source_mapper: &'a mut SourceMapper, + ) -> Self { + MergeViewBuilder { + nodes, + nodes_peeker: nodes.iter().peekable(), + sources, + graph, + source_mapper, + last_offset_set: HashMap::new(), + parent_child_edge_iterator: HashMap::new(), + } + } - // invariant: never None as only the first element in `nodes` should have a None, which is popped off in the calling function - let parent = n.1.unwrap(); - let child = n.0; - let edge = graph.get_edge_meta(parent, child); - let parent_path = graph.get_node(parent).clone(); - let child_path = graph.get_node(child).clone(); + pub fn build(&mut self) -> String { + // contains additionally inserted lines such as #line and other directives, preamble defines etc + let mut extra_lines: Vec = Vec::new(); + extra_lines.reserve((self.nodes.len() * 2) + 2); - let parent_source = sources.get(&parent_path).unwrap(); - let (char_for_line, char_following_line) = char_offset_for_line(edge.line, parent_source); + // list of source code views onto the below sources + let mut merge_list: LinkedList<&'a str> = LinkedList::new(); - let offset = *last_offset_set - .insert((parent, stack.back().copied()), char_following_line) - .get_or_insert(0); - merge_list.push_back(&parent_source[offset..char_for_line]); - add_opening_line_directive(&child_path, child, merge_list, extra_lines, source_mapper); + // invariant: nodes_iter always has _at least_ one element. Can't save a not-file :B + let first = self.nodes_peeker.next().unwrap().child; + let first_path = self.graph.get_node(first); + let first_source = self.sources.get(&first_path).unwrap(); - match nodes.peek() { - Some(next) => { - let next = *next; - // if the next pair's parent is not a child of the current pair, we dump the rest of this childs source - if next.1.unwrap() != child { - let child_source = sources.get(&child_path).unwrap(); - // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad - let offset = { - match child_source.ends_with('\n') { - true => child_source.len() - 1, - false => child_source.len(), + // seed source_mapper with top-level file + self.source_mapper.get_num(first); + + let version_line_offset = self.find_version_offset(first_source); + let _version_char_offsets = self.char_offset_for_line(version_line_offset, first_source); + // add_preamble( + // version_line_offset, + // version_char_offsets.1, + // &first_path, + // first, + // first_source, + // &mut merge_list, + // &mut extra_lines, + // source_mapper, + // ); + + // last_offset_set.insert((first, None), version_char_offsets.1); + self.last_offset_set.insert( + FilialTuple { + child: first, + parent: None, + }, + 0, + ); + + // stack to keep track of the depth first traversal + let mut stack = VecDeque::::new(); + + self.create_merge_views(&mut merge_list, &mut extra_lines, &mut stack); + + // now we add a view of the remainder of the root file + let offset = *self + .last_offset_set + .get(&FilialTuple { + child: first, + parent: None, + }) + .unwrap(); + + let len = first_source.len(); + merge_list.push_back(&first_source[min(offset, len)..]); + + let total_len = merge_list.iter().fold(0, |a, b| a + b.len()); + + let mut merged = String::with_capacity(total_len); + merged.extend(merge_list); + + merged + } + + fn create_merge_views(&mut self, merge_list: &mut LinkedList<&'a str>, extra_lines: &mut Vec, stack: &mut VecDeque) { + loop { + let n = match self.nodes_peeker.next() { + Some(n) => n, + None => return, + }; + + // invariant: never None as only the first element in `nodes` should have a None, which is popped off in the calling function + let (parent, child) = (n.parent.unwrap(), n.child); + // gets the next include position for the filial tuple, seeding if this is the first time querying this tuple + let edge = self + .parent_child_edge_iterator + .entry(*n) + .or_insert_with(|| { + let edge_metas = self.graph.get_edge_metas(parent, child); + Box::new(edge_metas) + }) + .next() + .unwrap(); + let parent_path = self.graph.get_node(parent).clone(); + let child_path = self.graph.get_node(child).clone(); + + let parent_source = self.sources.get(&parent_path).unwrap(); + let (char_for_line, char_following_line) = self.char_offset_for_line(edge.line, parent_source); + + let offset = *self + .last_offset_set + .insert( + FilialTuple { + child: parent, + parent: stack.back().copied(), + }, + char_following_line, + ) + .get_or_insert(0); + merge_list.push_back(&parent_source[offset..char_for_line]); + self.add_opening_line_directive(&child_path, child, merge_list, extra_lines); + + match self.nodes_peeker.peek() { + Some(next) => { + let next = *next; + // if the next pair's parent is not a child of the current pair, we dump the rest of this childs source + if next.parent.unwrap() != child { + let child_source = self.sources.get(&child_path).unwrap(); + // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad + let offset = { + match child_source.ends_with('\n') { + true => child_source.len() - 1, + false => child_source.len(), + } + }; + merge_list.push_back(&child_source[..offset]); + self.last_offset_set.insert( + FilialTuple { + child, + parent: Some(parent), + }, + 0, + ); + // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line + self.add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines); + // if the next pair's parent is not the current pair's parent, we need to bubble up + if stack.contains(&next.parent.unwrap()) { + return; } + continue; + } + + stack.push_back(parent); + self.create_merge_views(merge_list, extra_lines, stack); + stack.pop_back(); + + let offset = *self + .last_offset_set + .get(&FilialTuple { + child, + parent: Some(parent), + }) + .unwrap(); + let child_source = self.sources.get(&child_path).unwrap(); + // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 + let end_offset = match child_source.ends_with('\n') { + true => 1, /* child_source.len()-1 */ + false => 0, /* child_source.len() */ }; - merge_list.push_back(&child_source[..offset]); - last_offset_set.insert((child, Some(parent)), 0); + if offset < child_source.len() - end_offset { + // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad + merge_list.push_back(&child_source[offset../* std::cmp::max( */child_source.len()-end_offset/* , offset) */]); + self.last_offset_set.insert( + FilialTuple { + child, + parent: Some(parent), + }, + 0, + ); + } + // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines, source_mapper); - // if the next pair's parent is not the current pair's parent, we need to bubble up - if stack.contains(&next.1.unwrap()) { + self.add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines); + + // we need to check the next item at the point of original return further down the callstack + if self.nodes_peeker.peek().is_some() && stack.contains(&self.nodes_peeker.peek().unwrap().parent.unwrap()) { return; } - continue; } - - stack.push_back(parent); - create_merge_views( - nodes, - merge_list, - last_offset_set, - graph, - sources, - extra_lines, - stack, - source_mapper, - ); - stack.pop_back(); - - let offset = *last_offset_set.get(&(child, Some(parent))).unwrap(); - let child_source = sources.get(&child_path).unwrap(); - // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 - let end_offset = match child_source.ends_with('\n') { - true => 1, /* child_source.len()-1 */ - false => 0, /* child_source.len() */ - }; - if offset < child_source.len() - end_offset { + None => { + let child_source = self.sources.get(&child_path).unwrap(); // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad - merge_list.push_back(&child_source[offset../* std::cmp::max( */child_source.len()-end_offset/* , offset) */]); - last_offset_set.insert((child, Some(parent)), 0); + let offset = match child_source.ends_with('\n') { + true => child_source.len() - 1, + false => child_source.len(), + }; + merge_list.push_back(&child_source[..offset]); + self.last_offset_set.insert( + FilialTuple { + child, + parent: Some(parent), + }, + 0, + ); + // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line + self.add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines); } - - // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines, source_mapper); - - // we need to check the next item at the point of original return further down the callstack - if nodes.peek().is_some() && stack.contains(&nodes.peek().unwrap().1.unwrap()) { - return; - } - } - None => { - let child_source = sources.get(&child_path).unwrap(); - // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad - let offset = match child_source.ends_with('\n') { - true => child_source.len() - 1, - false => child_source.len(), - }; - merge_list.push_back(&child_source[..offset]); - last_offset_set.insert((child, Some(parent)), 0); - // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line - add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines, source_mapper); } } } -} -// returns the character offset + 1 of the end of line number `line` and the character -// offset + 1 for the end of the line after the previous one -fn char_offset_for_line(line_num: usize, source: &str) -> (usize, usize) { - let mut char_for_line: usize = 0; - let mut char_following_line: usize = 0; - for (n, line) in source.lines().enumerate() { - if n == line_num { - char_following_line += line.len() + 1; - break; + // returns the character offset + 1 of the end of line number `line` and the character + // offset + 1 for the end of the line after the previous one + fn char_offset_for_line(&self, line_num: usize, source: &str) -> (usize, usize) { + let mut char_for_line: usize = 0; + let mut char_following_line: usize = 0; + for (n, line) in source.lines().enumerate() { + if n == line_num { + char_following_line += line.len() + 1; + break; + } + char_for_line += line.len() + 1; + char_following_line = char_for_line; } - char_for_line += line.len() + 1; - char_following_line = char_for_line; + (char_for_line, char_following_line) } - (char_for_line, char_following_line) -} -fn find_version_offset(source: &str) -> usize { - source - .lines() - .enumerate() - .find(|(_, line)| line.starts_with("#version ")) - .map_or(0, |(i, _)| i) -} + fn find_version_offset(&self, source: &str) -> usize { + source + .lines() + .enumerate() + .find(|(_, line)| line.starts_with("#version ")) + .map_or(0, |(i, _)| i) + } -// fn add_preamble<'a>( -// version_line_offset: usize, version_char_offset: usize, path: &Path, node: NodeIndex, source: &'a str, -// merge_list: &mut LinkedList<&'a str>, extra_lines: &mut Vec, source_mapper: &mut SourceMapper, -// ) { -// // TODO: Optifine #define preabmle -// merge_list.push_back(&source[..version_char_offset]); -// let google_line_directive = format!( -// "#extension GL_GOOGLE_cpp_style_line_directive : enable\n#line {} {} // {}\n", -// // +2 because 0 indexed but #line is 1 indexed and references the *following* line -// version_line_offset + 2, -// source_mapper.get_num(node), -// path.to_str().unwrap().replace('\\', "\\\\"), -// ); -// extra_lines.push(google_line_directive); -// unsafe_get_and_insert(merge_list, extra_lines); -// } + // fn add_preamble<'a>( + // version_line_offset: usize, version_char_offset: usize, path: &Path, node: NodeIndex, source: &'a str, + // merge_list: &mut LinkedList<&'a str>, extra_lines: &mut Vec, source_mapper: &mut SourceMapper, + // ) { + // // TODO: Optifine #define preabmle + // merge_list.push_back(&source[..version_char_offset]); + // let google_line_directive = format!( + // "#extension GL_GOOGLE_cpp_style_line_directive : enable\n#line {} {} // {}\n", + // // +2 because 0 indexed but #line is 1 indexed and references the *following* line + // version_line_offset + 2, + // source_mapper.get_num(node), + // path.to_str().unwrap().replace('\\', "\\\\"), + // ); + // extra_lines.push(google_line_directive); + // unsafe_get_and_insert(merge_list, extra_lines); + // } -fn add_opening_line_directive( - path: &Path, node: NodeIndex, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec, source_mapper: &mut SourceMapper, -) { - let line_directive = format!( - "#line 1 {} // {}\n", - source_mapper.get_num(node), - path.to_str().unwrap().replace('\\', "\\\\") - ); - extra_lines.push(line_directive); - unsafe_get_and_insert(merge_list, extra_lines); -} + fn add_opening_line_directive( + &mut self, path: &Path, node: NodeIndex, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec, + ) { + let line_directive = format!( + "#line 1 {} // {}\n", + self.source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ); + extra_lines.push(line_directive); + self.unsafe_get_and_insert(merge_list, extra_lines); + } -fn add_closing_line_directive( - line: usize, path: &Path, node: NodeIndex, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec, - source_mapper: &mut SourceMapper, -) { - // Optifine doesn't seem to add a leading newline if the previous line was a #line directive - let line_directive = if let Some(l) = merge_list.back() { - if l.trim().starts_with("#line") { - format!( - "#line {} {} // {}\n", - line, - source_mapper.get_num(node), - path.to_str().unwrap().replace('\\', "\\\\") - ) + fn add_closing_line_directive( + &mut self, line: usize, path: &Path, node: NodeIndex, merge_list: &mut LinkedList<&str>, extra_lines: &mut Vec, + ) { + // Optifine doesn't seem to add a leading newline if the previous line was a #line directive + let line_directive = if let Some(l) = merge_list.back() { + if l.trim().starts_with("#line") { + format!( + "#line {} {} // {}\n", + line, + self.source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ) + } else { + format!( + "\n#line {} {} // {}\n", + line, + self.source_mapper.get_num(node), + path.to_str().unwrap().replace('\\', "\\\\") + ) + } } else { format!( "\n#line {} {} // {}\n", line, - source_mapper.get_num(node), + self.source_mapper.get_num(node), path.to_str().unwrap().replace('\\', "\\\\") ) + }; + + extra_lines.push(line_directive); + self.unsafe_get_and_insert(merge_list, extra_lines); + } + + fn unsafe_get_and_insert(&self, merge_list: &mut LinkedList<&str>, extra_lines: &[String]) { + // :^) + unsafe { + let vec_ptr_offset = extra_lines.as_ptr().add(extra_lines.len() - 1); + merge_list.push_back(&vec_ptr_offset.as_ref().unwrap()[..]); } - } else { - format!( - "\n#line {} {} // {}\n", - line, - source_mapper.get_num(node), - path.to_str().unwrap().replace('\\', "\\\\") - ) - }; - - extra_lines.push(line_directive); - unsafe_get_and_insert(merge_list, extra_lines); -} - -fn unsafe_get_and_insert(merge_list: &mut LinkedList<&str>, extra_lines: &[String]) { - // :^) - unsafe { - let vec_ptr_offset = extra_lines.as_ptr().add(extra_lines.len() - 1); - merge_list.push_back(&vec_ptr_offset.as_ref().unwrap()[..]); } } @@ -287,7 +348,7 @@ mod merge_view_test { use std::fs; use std::path::PathBuf; - use crate::merge_views::generate_merge_list; + use crate::merge_views::MergeViewBuilder; use crate::source_mapper::SourceMapper; use crate::test::{copy_to_and_set_root, new_temp_server}; use crate::IncludePosition; @@ -300,16 +361,8 @@ mod merge_view_test { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/01", &mut server); server.endpoint.request_shutdown(); - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{:?}/shaders/final.fsh", tmp_path).try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); - let common_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{:?}/shaders/common.glsl", tmp_path).try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("common.glsl")); + let final_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("final.fsh")); + let common_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("common.glsl")); server .graph @@ -321,7 +374,7 @@ mod merge_view_test { let graph_borrow = server.graph.borrow(); let mut source_mapper = SourceMapper::new(0); - let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); + let result = MergeViewBuilder::new(&nodes, &sources, &graph_borrow, &mut source_mapper).build(); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); @@ -352,25 +405,18 @@ mod merge_view_test { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/02", &mut server); server.endpoint.request_shutdown(); - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); + let final_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("final.fsh")); let test_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); let burger_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); let sample_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); server @@ -391,7 +437,7 @@ mod merge_view_test { let graph_borrow = server.graph.borrow(); let mut source_mapper = SourceMapper::new(0); - let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); + let result = MergeViewBuilder::new(&nodes, &sources, &graph_borrow, &mut source_mapper).build(); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); @@ -434,25 +480,18 @@ mod merge_view_test { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/03", &mut server); server.endpoint.request_shutdown(); - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); + let final_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("final.fsh")); let test_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "test.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("test.glsl")); let burger_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "burger.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("burger.glsl")); let sample_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "sample.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("sample.glsl")); server @@ -473,7 +512,7 @@ mod merge_view_test { let graph_borrow = server.graph.borrow(); let mut source_mapper = SourceMapper::new(0); - let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); + let result = MergeViewBuilder::new(&nodes, &sources, &graph_borrow, &mut source_mapper).build(); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); @@ -516,30 +555,22 @@ mod merge_view_test { let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/04", &mut server); server.endpoint.request_shutdown(); - let final_idx = server - .graph - .borrow_mut() - //.add_node(&format!("{}/shaders/{}", tmp_path, "final.fsh").try_into().unwrap()); - .add_node(&tmp_path.join("shaders").join("final.fsh")); + let final_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("final.fsh")); let utilities_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "utilities.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("utilities.glsl")); let stuff1_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff1.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("stuff1.glsl")); let stuff2_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/utils/{}", tmp_path, "stuff2.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("utils").join("stuff2.glsl")); let matrices_idx = server .graph .borrow_mut() - //.add_node(&format!("{}/shaders/lib/{}", tmp_path, "matrices.glsl").try_into().unwrap()); .add_node(&tmp_path.join("shaders").join("lib").join("matrices.glsl")); server @@ -564,7 +595,7 @@ mod merge_view_test { let graph_borrow = server.graph.borrow(); let mut source_mapper = SourceMapper::new(0); - let result = generate_merge_list(&nodes, &sources, &graph_borrow, &mut source_mapper); + let result = MergeViewBuilder::new(&nodes, &sources, &graph_borrow, &mut source_mapper).build(); let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); @@ -587,4 +618,49 @@ mod merge_view_test { assert_eq!(result, truth); } + + #[test] + #[logging_macro::log_scope] + fn test_generate_merge_list_06() { + let mut server = new_temp_server(None); + + let (_tmp_dir, tmp_path) = copy_to_and_set_root("./testdata/06", &mut server); + server.endpoint.request_shutdown(); + + let final_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("final.fsh")); + let test_idx = server.graph.borrow_mut().add_node(&tmp_path.join("shaders").join("test.glsl")); + + server + .graph + .borrow_mut() + .add_edge(final_idx, test_idx, IncludePosition { line: 3, start: 0, end: 0 }); + server + .graph + .borrow_mut() + .add_edge(final_idx, test_idx, IncludePosition { line: 5, start: 0, end: 0 }); + + let nodes = server.get_dfs_for_node(final_idx).unwrap(); + let sources = server.load_sources(&nodes).unwrap(); + + let graph_borrow = server.graph.borrow(); + let mut source_mapper = SourceMapper::new(0); + let result = MergeViewBuilder::new(&nodes, &sources, &graph_borrow, &mut source_mapper).build(); + + let merge_file = tmp_path.join("shaders").join("final.fsh.merge"); + + let mut truth = fs::read_to_string(merge_file).unwrap(); + + for file in &[ + // PathBuf::new().join("final.fsh").to_str().unwrap(), + PathBuf::new().join("test.glsl").to_str().unwrap(), + PathBuf::new().join("final.fsh").to_str().unwrap(), + PathBuf::new().join("test.glsl").to_str().unwrap(), + PathBuf::new().join("final.fsh").to_str().unwrap(), + ] { + let path = tmp_path.clone(); + truth = truth.replacen("!!", &path.join("shaders").join(file).to_str().unwrap().replace('\\', "\\\\"), 1); + } + + assert_eq!(result, truth); + } } diff --git a/server/main/src/navigation.rs b/server/main/src/navigation.rs index d1b3c82..9418e86 100644 --- a/server/main/src/navigation.rs +++ b/server/main/src/navigation.rs @@ -28,7 +28,11 @@ impl SymbolName { } ("struct_specifier", "field_declaration_list") => { let struct_ident = node.child_by_field_name("name").unwrap(); - fqname.push(format!("{}[{}]", struct_ident.utf8_text(source.as_bytes()).unwrap(), struct_ident.id())); + fqname.push(format!( + "{}[{}]", + struct_ident.utf8_text(source.as_bytes()).unwrap(), + struct_ident.id() + )); } _ => (), } diff --git a/server/main/testdata/05/final.fsh.merge b/server/main/testdata/05/final.fsh.merge index 724eb5a..b561479 100644 --- a/server/main/testdata/05/final.fsh.merge +++ b/server/main/testdata/05/final.fsh.merge @@ -1,5 +1,5 @@ #version 120 -#extension GL_GOOGLE_cpp_style_line_directive : enable + #line 2 "!!" #line 1 "!!" diff --git a/server/main/testdata/06/final.fsh b/server/main/testdata/06/final.fsh new file mode 100644 index 0000000..4c2910b --- /dev/null +++ b/server/main/testdata/06/final.fsh @@ -0,0 +1,9 @@ +#version 120 + +#ifdef BANANA +#include "test.glsl" +#else +#include "test.glsl" +#endif + +void main() {} \ No newline at end of file diff --git a/server/main/testdata/06/final.fsh.merge b/server/main/testdata/06/final.fsh.merge new file mode 100644 index 0000000..8ee023e --- /dev/null +++ b/server/main/testdata/06/final.fsh.merge @@ -0,0 +1,17 @@ +#version 120 + +#ifdef BANANA +#line 1 1 // !! +int test() { + return 1; +} +#line 5 0 // !! +#else +#line 1 1 // !! +int test() { + return 1; +} +#line 7 0 // !! +#endif + +void main() {} \ No newline at end of file diff --git a/server/main/testdata/06/test.glsl b/server/main/testdata/06/test.glsl new file mode 100644 index 0000000..4ae7903 --- /dev/null +++ b/server/main/testdata/06/test.glsl @@ -0,0 +1,3 @@ +int test() { + return 1; +} \ No newline at end of file From a7cbaa198bf8bf50eb25830c9574939871024b32 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 23 Apr 2022 22:33:21 +0100 Subject: [PATCH 41/56] v0.9.6 --- CHANGELOG.md | 13 +++++++++++++ logo-mini.png | Bin 27427 -> 24996 bytes package-lock.json | 1 + package.json | 2 +- server/Cargo.lock | 6 +++--- server/logging/Cargo.toml | 2 +- server/logging_macro/Cargo.toml | 2 +- server/main/Cargo.toml | 2 +- 8 files changed, 21 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dbe0f9e..ff0f6f0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,19 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +## [0.9.6] + +### Added + +- MacOS M1 binary releases +- AMD OpenGL driver diagnostics output support. AMD linting is a-go 🚀 +- Tree-sitter based go-to-definition/find-references/document symbols. Currently disabled until stabilized + +### Fixed + +- Another `#include` merging bug when a file is imported twice into another file at different lines + + ## [0.9.5] ### Added diff --git a/logo-mini.png b/logo-mini.png index af16bb8fa2d2c06ae5e9ad4d2fa4720f64a1c1e6..948748b3cf3a3db27e0eaa7d9e6f921e708498e1 100644 GIT binary patch delta 22045 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"] edition = "2021" diff --git a/server/logging_macro/Cargo.toml b/server/logging_macro/Cargo.toml index fdf9b43..d975018 100644 --- a/server/logging_macro/Cargo.toml +++ b/server/logging_macro/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging_macro" -version = "0.9.5" +version = "0.9.6" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/main/Cargo.toml b/server/main/Cargo.toml index 18cc1dd..f815b7c 100644 --- a/server/main/Cargo.toml +++ b/server/main/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mcshader-lsp" -version = "0.9.5" +version = "0.9.6" authors = ["Noah Santschi-Cooney "] edition = "2021" From d43bfec582355fe214a7f546870e0af8b79ac2c0 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sat, 23 Apr 2022 23:15:45 +0100 Subject: [PATCH 42/56] v0.9.6: now with fixed CI --- .github/workflows/release.yml | 10 ++++++---- .github/workflows/server.yml | 1 - CHANGELOG.md | 1 - 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index bae3792..fbe234e 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -34,20 +34,20 @@ jobs: platforms: - os: ubuntu-18.04 target: x86_64-unknown-linux-gnu - artifact: x86_64-unknown-linux-gnu dir: server/mcshader-lsp + artifact: x86_64-unknown-linux-gnu - os: windows-latest target: x86_64-pc-windows-msvc - artifact: x86_64-windows-msvc.exe dir: server/mcshader-lsp.exe + artifact: x86_64-windows-msvc.exe - os: macos-11 target: x86_64-apple-darwin - artifact: x86_64-apple-darwin dir: server/mcshader-lsp + artifact: x86_64-apple-darwin - os: macos-11 target: aarch64-apple-darwin - artifact: aarch64-apple-darwin dir: server/mcshader-lsp + artifact: aarch64-apple-darwin steps: - uses: actions/checkout@v2 - name: Install latest nightly @@ -55,6 +55,8 @@ jobs: with: toolchain: nightly default: true + target: ${{ matrix.platforms.target }} + override: true - name: Build server run: cargo build --release --target ${{ matrix.platforms.target }} --out-dir . -Z unstable-options - name: Upload release file diff --git a/.github/workflows/server.yml b/.github/workflows/server.yml index 8c3e4ee..0e254c7 100644 --- a/.github/workflows/server.yml +++ b/.github/workflows/server.yml @@ -48,4 +48,3 @@ jobs: path: ${{ matrix.platforms.dir }} - name: Run tests run: cargo test --target ${{ matrix.platforms.target }} - if: ${{ matrix.platforms.target != 'aarch64-apple-darwin' }} diff --git a/CHANGELOG.md b/CHANGELOG.md index ff0f6f0..30096bc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -16,7 +16,6 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) - Another `#include` merging bug when a file is imported twice into another file at different lines - ## [0.9.5] ### Added From f45e1a4b873757f40a347a7d4f9321aa49573f64 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 24 Apr 2022 00:05:13 +0100 Subject: [PATCH 43/56] v0.9.7: the real 0.9.6 --- .github/workflows/server.yml | 1 + CHANGELOG.md | 7 ++++ client/src/commands.ts | 6 ++-- client/src/extension.ts | 61 ++++++++++++++++++--------------- client/src/log.ts | 22 ++++++------ client/src/lspClient.ts | 6 ++-- client/src/lspExt.ts | 2 +- client/src/net.ts | 27 ++++++++------- client/src/persistent_state.ts | 2 +- package-lock.json | 4 +-- package.json | 2 +- server/Cargo.lock | 6 ++-- server/logging/Cargo.toml | 2 +- server/logging_macro/Cargo.toml | 2 +- server/main/Cargo.toml | 2 +- 15 files changed, 84 insertions(+), 68 deletions(-) diff --git a/.github/workflows/server.yml b/.github/workflows/server.yml index 0e254c7..8c3e4ee 100644 --- a/.github/workflows/server.yml +++ b/.github/workflows/server.yml @@ -48,3 +48,4 @@ jobs: path: ${{ matrix.platforms.dir }} - name: Run tests run: cargo test --target ${{ matrix.platforms.target }} + if: ${{ matrix.platforms.target != 'aarch64-apple-darwin' }} diff --git a/CHANGELOG.md b/CHANGELOG.md index 30096bc..d44521d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,13 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +## [0.9.7] + +### Fixed + +- Fixed bad release tag format +- Fixed extension silently failing on activation + ## [0.9.6] ### Added diff --git a/client/src/commands.ts b/client/src/commands.ts index d26c25f..bb81105 100644 --- a/client/src/commands.ts +++ b/client/src/commands.ts @@ -56,7 +56,7 @@ export function virtualMergedDocument(e: Extension): Command { + vscode.window.activeTextEditor.document.uri.path .slice(vscode.window.activeTextEditor.document.uri.path.lastIndexOf('.') + 1) const path = vscode.Uri.parse(`mcglsl:${uri}`) - + const doc = await vscode.workspace.openTextDocument(path) docProvider.onDidChangeEmitter.fire(path) await vscode.window.showTextDocument(doc, { @@ -83,7 +83,7 @@ export function parseTree(e: Extension): Command { onDidChangeEmitter = new vscode.EventEmitter() onDidChange = this.onDidChangeEmitter.event - provideTextDocumentContent(uri: vscode.Uri, __: vscode.CancellationToken): vscode.ProviderResult { + provideTextDocumentContent(uri: vscode.Uri, _: vscode.CancellationToken): vscode.ProviderResult { if (uri.path.includes('.flattened.')) return '' return getVirtualDocument(uri.path.substring(0, uri.path.lastIndexOf('.'))) } @@ -96,7 +96,7 @@ export function parseTree(e: Extension): Command { const uri = vscode.window.activeTextEditor.document.uri const path = vscode.Uri.parse(`mcglsl:${uri.path}.ast`) - + const doc = await vscode.workspace.openTextDocument(path) docProvider.onDidChangeEmitter.fire(path) await vscode.window.showTextDocument(doc, { diff --git a/client/src/extension.ts b/client/src/extension.ts index 9133ae5..b1863db 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -6,7 +6,7 @@ import { log } from './log' import { LanguageClient } from './lspClient' import { download, getReleaseInfo } from './net' import { PersistentState } from './persistent_state' -import * as path from 'path' +import * as path from 'path' const platforms: { [key: string]: string } = { 'x64 win32': 'x86_64-windows-msvc', @@ -26,7 +26,7 @@ export class Extension { readonly package: { version: string } = vscode.extensions.getExtension(this.extensionID)!.packageJSON; - + public get context(): vscode.ExtensionContext { return this.extensionContext } @@ -34,13 +34,13 @@ export class Extension { public get lspClient(): lsp.LanguageClient { return this.client } - + public activate = async (context: vscode.ExtensionContext) => { this.extensionContext = context this.state = new PersistentState(context.globalState) - if(!process.env['MCSHADER_DEBUG'] && !(vscode.workspace.getConfiguration('mcglsl').get('skipBootstrap') as boolean)) { - await this.bootstrap() + if (!process.env['MCSHADER_DEBUG'] && !(vscode.workspace.getConfiguration('mcglsl').get('skipBootstrap') as boolean)) { + await this.bootstrap() } else { log.info('skipping language server bootstrap') } @@ -52,31 +52,31 @@ export class Extension { log.info('starting language server...') - const lspBinary = process.env['MCSHADER_DEBUG'] ? - this.context.asAbsolutePath(path.join('server', 'target', 'debug', 'mcshader-lsp')) + - (process.platform === 'win32' ? '.exe' : '') : - path.join(this.context.globalStorageUri.fsPath, 'mcshader-lsp') + const lspBinary = process.env['MCSHADER_DEBUG'] ? + this.context.asAbsolutePath(path.join('server', 'target', 'debug', 'mcshader-lsp')) + + (process.platform === 'win32' ? '.exe' : '') : + path.join(this.context.globalStorageUri.fsPath, 'mcshader-lsp') const filewatcherGlob = this.fileAssociationsToGlob(this.getGLSLFileAssociations()) - + this.client = await new LanguageClient(this, lspBinary, filewatcherGlob).startServer() - + log.info('language server started!') } fileAssociationsToGlob = (associations: string[]): string => { return '**/*.{'.concat( associations.map(s => s.substring(s.indexOf('.'))).join(',') - ) + '}' + ) + '}' } getGLSLFileAssociations = (): string[] => { const exts = ['.fsh', '.vsh', '.gsh', '.glsl'] - const associations = vscode.workspace.getConfiguration('files').get('associations') as {[key: string]: string} - + const associations = vscode.workspace.getConfiguration('files').get('associations') as { [key: string]: string } + Object.keys(associations).forEach((key) => { - if(associations[key] === 'glsl') { - exts.push(key.substring(key.indexOf('*')+1)) + if (associations[key] === 'glsl') { + exts.push(key.substring(key.indexOf('*') + 1)) } }) @@ -85,16 +85,16 @@ export class Extension { registerCommand = (name: string, f: (e: Extension) => commands.Command) => { const cmd = f(this) - this.context.subscriptions.push(vscode.commands.registerCommand('mcglsl.'+name, cmd)) + this.context.subscriptions.push(vscode.commands.registerCommand('mcglsl.' + name, cmd)) } - deactivate = async () => { + deactivate = async () => { await this.lspClient.stop() - while(this.context.subscriptions.length > 0) { + while (this.context.subscriptions.length > 0) { this.context.subscriptions.pop()?.dispose() } } - + public updateStatus = (icon: string, text: string) => { this.statusBarItem?.dispose() this.statusBarItem = vscode.window.createStatusBarItem(vscode.StatusBarAlignment.Left) @@ -102,14 +102,14 @@ export class Extension { this.statusBarItem.show() this.context.subscriptions.push(this.statusBarItem) } - + public clearStatus = () => { this.statusBarItem?.dispose() } private bootstrap = async () => { mkdirSync(this.extensionContext.globalStoragePath, { recursive: true }) - + const dest = path.join(this.extensionContext.globalStoragePath, 'mcshader-lsp' + (process.platform === 'win32' ? '.exe' : '')) const exists = await fs.stat(dest).then(() => true, () => false) if (!exists) await this.state.updateServerVersion(undefined) @@ -123,7 +123,7 @@ export class Extension { log.warn(`incompatible architecture/platform:\n\t${process.arch} ${process.platform}`) return } - + if (release.tag_name === this.state.serverVersion) { log.info('server version is same as extension:\n\t', this.state.serverVersion) return @@ -135,8 +135,8 @@ export class Extension { const userResponse = await vscode.window.showInformationMessage( this.state.serverVersion == undefined ? - `Language server version ${this.package.version} is not installed.` : - `An update is available. Upgrade from ${this.state.serverVersion} to ${release.tag_name}?`, + `Language server version ${this.package.version} is not installed.` : + `An update is available. Upgrade from ${this.state.serverVersion} to ${release.tag_name}?`, 'Download now' ) if (userResponse !== 'Download now') { @@ -145,9 +145,16 @@ export class Extension { } await download(artifact.browser_download_url, dest) - + this.state.updateServerVersion(release.tag_name) } } -export const activate = new Extension().activate \ No newline at end of file +export const activate = async (context: vscode.ExtensionContext) => { + try { + new Extension().activate(context) + } catch (e) { + log.error(`failed to activate extension: ${e}`) + throw(e) + } +} \ No newline at end of file diff --git a/client/src/log.ts b/client/src/log.ts index f9e31ff..880ed52 100644 --- a/client/src/log.ts +++ b/client/src/log.ts @@ -9,33 +9,33 @@ export const log = new class { // Hint: the type [T, ...T[]] means a non-empty array debug(...msg: [unknown, ...unknown[]]): void { - log.write('DEBUG', ...msg) + log.write('DEBUG', ...msg) } info(...msg: [unknown, ...unknown[]]): void { - log.write('INFO ', ...msg) + log.write('INFO ', ...msg) } warn(...msg: [unknown, ...unknown[]]): void { - log.write('WARN ', ...msg) + log.write('WARN ', ...msg) } error(...msg: [unknown, ...unknown[]]): void { - log.write('ERROR', ...msg) + log.write('ERROR', ...msg) } write(label: string, ...messageParts: unknown[]): void { - const message = messageParts.map(log.stringify).join(' ') - const dateTime = new Date().toLocaleString() - log.output.appendLine(`${label} [${dateTime}]: ${message}`) + const message = messageParts.map(log.stringify).join(' ') + const dateTime = new Date().toLocaleString() + log.output.appendLine(`${label} [${dateTime}]: ${message}`) } private stringify(val: unknown): string { - if (typeof val === 'string') return val + if (typeof val === 'string') return val return inspect(val, { - colors: false, - depth: 6, // heuristic - }) + colors: false, + depth: 6, // heuristic + }) } } diff --git a/client/src/lspClient.ts b/client/src/lspClient.ts index 57cc6aa..7d9d2e7 100644 --- a/client/src/lspClient.ts +++ b/client/src/lspClient.ts @@ -11,7 +11,7 @@ export class LanguageClient extends lsp.LanguageClient { super('vscode-mc-shader', 'VSCode MC Shader', { command: lspBinary }, { - documentSelector: [{scheme: 'file', language: 'glsl'}], + documentSelector: [{ scheme: 'file', language: 'glsl' }], outputChannel: lspOutputChannel, synchronize: { configurationSection: 'mcglsl', @@ -28,10 +28,10 @@ export class LanguageClient extends lsp.LanguageClient { this.extension.context.subscriptions.push(this.start()) await this.onReady() - + this.onNotification(updateConfigMethod, this.onUpdateConfig) this.onNotification(statusMethod, this.onStatusChange) - + return this } diff --git a/client/src/lspExt.ts b/client/src/lspExt.ts index ec2c6fe..70b40da 100644 --- a/client/src/lspExt.ts +++ b/client/src/lspExt.ts @@ -12,5 +12,5 @@ export const status = new lsp.NotificationType(statusMethod) export const updateConfigMethod = 'mc-glsl/updateConfig' export type ConfigUpdateParams = { - kv: {key: string, value: string}[] + kv: { key: string, value: string }[] } \ No newline at end of file diff --git a/client/src/net.ts b/client/src/net.ts index 14e1242..74438d0 100644 --- a/client/src/net.ts +++ b/client/src/net.ts @@ -16,20 +16,21 @@ interface GithubRelease { } export async function getReleaseInfo(releaseTag: string): Promise { + log.info('fetching release info for tag', releaseTag) const response = await fetch(`https://api.github.com/repos/strum355/mcshader-lsp/releases/tags/${releaseTag}`, { - headers: {Accept: 'application/vnd.github.v3+json'} + headers: { Accept: 'application/vnd.github.v3+json' } }) const isRelease = (obj: unknown): obj is GithubRelease => { - return obj != null && typeof obj === 'object' + return obj != null && typeof obj === 'object' && typeof (obj as GithubRelease).tag_name === 'string' && Array.isArray((obj as GithubRelease).assets) && (obj as GithubRelease).assets.every((a) => typeof a.name === 'string' && typeof a.browser_download_url === 'string') } const json = await response.json() - if(!isRelease(json)) { - throw new TypeError('Received malformed request from Github Release API ' + JSON.stringify(json)) + if (!isRelease(json)) { + throw new TypeError(`Received malformed request from Github Release API ${JSON.stringify(json)}`) } return json } @@ -50,14 +51,14 @@ export async function download(url: string, downloadDest: string) { message: `${newPercentage.toFixed(0)}%`, increment: newPercentage - lastPercentage }) - + lastPercentage = newPercentage } }) } ) } - + async function downloadFile( url: string, destFilePath: fs.PathLike, @@ -69,21 +70,21 @@ async function downloadFile( log.error({ body: await res.text(), headers: res.headers }) throw new Error(`Got response ${res.status} when trying to download ${url}.`) } - + const totalBytes = Number(res.headers.get('content-length')) - + log.debug('downloading file with', totalBytes, 'bytes size from', url, 'to', destFilePath) - + let readBytes = 0 res.body.on('data', (chunk: Buffer) => { readBytes += chunk.length onProgress(readBytes, totalBytes) }) - + const destFileStream = fs.createWriteStream(destFilePath, { mode: 0o755 }) - + await pipeline(res.body, destFileStream) - + // Don't apply the workaround in fixed versions of nodejs, since the process // freezes on them, the process waits for no-longer emitted `close` event. // The fix was applied in commit 7eed9d6bcc in v13.11.0 @@ -91,7 +92,7 @@ async function downloadFile( // https://github.com/nodejs/node/blob/master/doc/changelogs/CHANGELOG_V13.md const [, major, minor] = /v(\d+)\.(\d+)\.(\d+)/.exec(process.version)! if (+major > 13 || (+major === 13 && +minor >= 11)) return - + await new Promise(resolve => { destFileStream.on('close', resolve) destFileStream.destroy() diff --git a/client/src/persistent_state.ts b/client/src/persistent_state.ts index c54354b..a6bf084 100644 --- a/client/src/persistent_state.ts +++ b/client/src/persistent_state.ts @@ -12,6 +12,6 @@ export class PersistentState { } async updateServerVersion(value: string | undefined) { - await this.state.update('serverVersion', value) + await this.state.update('serverVersion', value) } } \ No newline at end of file diff --git a/package-lock.json b/package-lock.json index 75425e1..8f8b1aa 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,11 +1,11 @@ { "name": "vscode-mc-shader", - "version": "0.9.6", + "version": "0.9.7", "lockfileVersion": 2, "requires": true, "packages": { "": { - "version": "0.9.6", + "version": "0.9.7", "hasInstallScript": true, "license": "MIT", "devDependencies": { diff --git a/package.json b/package.json index 07f4454..7c3ef15 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "vscode-mc-shader", "displayName": "Minecraft GLSL Shaders", "description": "A Visual Studio Code extension for linting/etc Minecraft GLSL Shaders", - "version": "0.9.6", + "version": "0.9.7", "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", diff --git a/server/Cargo.lock b/server/Cargo.lock index 8a5d6d5..5d97dab 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -656,7 +656,7 @@ dependencies = [ [[package]] name = "logging" -version = "0.9.6" +version = "0.9.7" dependencies = [ "lazy_static", "rand 0.8.5", @@ -668,7 +668,7 @@ dependencies = [ [[package]] name = "logging_macro" -version = "0.9.6" +version = "0.9.7" dependencies = [ "quote", "syn", @@ -703,7 +703,7 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f" [[package]] name = "mcshader-lsp" -version = "0.9.6" +version = "0.9.7" dependencies = [ "anyhow", "fs_extra", diff --git a/server/logging/Cargo.toml b/server/logging/Cargo.toml index 44a2884..7b94e66 100644 --- a/server/logging/Cargo.toml +++ b/server/logging/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging" -version = "0.9.6" +version = "0.9.7" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/logging_macro/Cargo.toml b/server/logging_macro/Cargo.toml index d975018..e20d4ed 100644 --- a/server/logging_macro/Cargo.toml +++ b/server/logging_macro/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging_macro" -version = "0.9.6" +version = "0.9.7" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/main/Cargo.toml b/server/main/Cargo.toml index f815b7c..30ad346 100644 --- a/server/main/Cargo.toml +++ b/server/main/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mcshader-lsp" -version = "0.9.6" +version = "0.9.7" authors = ["Noah Santschi-Cooney "] edition = "2021" From 3c58af95fa80f3253854d91e6cc95eb35f7ef199 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 24 Apr 2022 00:55:43 +0100 Subject: [PATCH 44/56] fix logo images because gitattributes treated them as text --- .gitattributes | 3 ++- README.md | 2 +- logo-min.png | Bin 0 -> 25081 bytes logo.png | Bin 1172868 -> 1172883 bytes 4 files changed, 3 insertions(+), 2 deletions(-) create mode 100644 logo-min.png diff --git a/.gitattributes b/.gitattributes index 07764a7..a2eabde 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1 +1,2 @@ -* text eol=lf \ No newline at end of file +* text eol=lf +*.png binary \ No newline at end of file diff --git a/README.md b/README.md index 2465d12..dcad726 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ Currently supported editors: - [Visual Studio Code](https://code.visualstudio.com/) with `vscode-mc-shader` - + ## Features diff --git a/logo-min.png b/logo-min.png new file mode 100644 index 0000000000000000000000000000000000000000..4faf57b43c56bcc9405a43d8b37f44ea7f472801 GIT binary patch literal 25081 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 literal 0 HcmV?d00001 diff --git a/logo.png b/logo.png index bec83b0c6e92ace5cab5058f34840caef1bcdd95..17aba30a5d3ff35bc61381210cc63825914d510a 100644 GIT binary patch delta 178 zcmZoU?LPUmJ8NfvpF3|O%T^Xf8+}IJb_adN?GE}(Wuid#HWwx!W(H!G?b}>f1z8z+ zw;%Up3=}J} delta 150 zcmbPy+P&qpJ4Gy!w(oRd6=dCh+LM*H zyZz=B*6la1uq_qeUjK&8Bd`5L6#MoQQ5+i|Z?CfB+~m`)+s(OMx0~yZ{&ue2T(g_E yFSFx*ExCPC1h-n~_ML0FBiXhKZ{gl-*?#;jHxTmxF)tAF0Wtsf<8KAdd Date: Sun, 24 Apr 2022 21:53:21 +0100 Subject: [PATCH 45/56] fix nvidia diagnostics line offset, once and for all (hopefully) --- server/main/src/diagnostics_parser.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/main/src/diagnostics_parser.rs b/server/main/src/diagnostics_parser.rs index 978dcd9..2c4279b 100644 --- a/server/main/src/diagnostics_parser.rs +++ b/server/main/src/diagnostics_parser.rs @@ -40,7 +40,7 @@ impl<'a, T: opengl::ShaderValidator + ?Sized> DiagnosticsParser<'a, T> { fn get_line_offset(&self) -> u32 { *self.line_offset.get_or_init(|| match self.vendor_querier.vendor().as_str() { "ATI Technologies" => 0, - _ => 2, + _ => 1, }) } From 3b568ea08759e10a9cef0f97e44673dc3b91cb40 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 24 Apr 2022 22:16:45 +0100 Subject: [PATCH 46/56] fix dfs iterator when same file imported multiple times into another --- server/main/src/dfs.rs | 23 ++++----- server/main/src/graph.rs | 28 ++++++----- server/main/src/main.rs | 6 ++- server/main/src/merge_views.rs | 89 +++++++++++++--------------------- 4 files changed, 64 insertions(+), 82 deletions(-) diff --git a/server/main/src/dfs.rs b/server/main/src/dfs.rs index d990bc7..11d3a6f 100644 --- a/server/main/src/dfs.rs +++ b/server/main/src/dfs.rs @@ -63,25 +63,22 @@ impl<'a> Iterator for Dfs<'a> { touch: 1, }); - let mut children: Vec = self.graph.child_node_indexes(child).collect(); + let mut children: Vec<_> = self + .graph + .get_all_child_positions(child) + .collect(); + children.reverse(); if !children.is_empty() { - // sort by line number in parent - children.sort_by(|x, y| { - let graph = &self.graph.graph; - let edge1 = graph.edge_weight(graph.find_edge(child, *x).unwrap()).unwrap(); - let edge2 = graph.edge_weight(graph.find_edge(child, *y).unwrap()).unwrap(); - edge2.line.cmp(&edge1.line) - }); - - match self.check_for_cycle(&children) { + let child_indexes: Vec<_> = children.iter().map(|c| c.0).collect(); + match self.check_for_cycle(&child_indexes) { Ok(_) => {} Err(e) => return Some(Err(e)), }; for child in children { - self.stack.push(child); + self.stack.push(child.0); } } else { self.reset_path_to_branch(); @@ -314,10 +311,10 @@ mod dfs_test { // \ / \ // 6 - 7 - assert!(is_cyclic_directed(&graph.graph)); - let next = dfs.next().unwrap(); assert_that!(next, err()); + + assert!(is_cyclic_directed(&graph.graph)); } { let mut graph = CachedStableGraph::new(); diff --git a/server/main/src/graph.rs b/server/main/src/graph.rs index 993fae1..608a299 100644 --- a/server/main/src/graph.rs +++ b/server/main/src/graph.rs @@ -59,9 +59,9 @@ impl CachedStableGraph { PathBuf::from_str(&self.graph[node]).unwrap() } - /// returns an iterator over all the `IncludePosition`'s between a parent and its child for all the positions + /// Returns an iterator over all the `IncludePosition`'s between a parent and its child for all the positions /// that the child may be imported into the parent, in order of import. - pub fn get_edge_metas(&self, parent: NodeIndex, child: NodeIndex) -> impl Iterator + '_ { + pub fn get_child_positions(&self, parent: NodeIndex, child: NodeIndex) -> impl Iterator + '_ { let mut edges = self .graph .edges(parent) @@ -77,6 +77,18 @@ impl CachedStableGraph { edges.into_iter() } + /// Returns an iterator over all the `(NodeIndex, IncludePosition)` tuples between a node and all its children, in order + /// of import. + pub fn get_all_child_positions(&self, node: NodeIndex) -> impl Iterator + '_ { + let mut edges = self.graph.edges(node).map(|edge| { + let child = self.graph.edge_endpoints(edge.id()).unwrap().1; + (child, self.graph[edge.id()]) + }) + .collect::>(); + edges.sort_by(|x, y| x.1.line.cmp(&y.1.line)); + edges.into_iter() + } + pub fn add_node(&mut self, name: &Path) -> NodeIndex { if let Some(idx) = self.cache.get(name) { return *idx; @@ -99,14 +111,6 @@ impl CachedStableGraph { .and_then(|edge| self.graph.remove_edge(edge)); } - pub fn child_node_metas(&self, node: NodeIndex) -> impl Iterator + '_ { - self.graph.neighbors(node).map(move |n| { - let edge = self.graph.find_edge(node, n).unwrap(); - let edge_meta = self.graph.edge_weight(edge).unwrap(); - return (self.reverse_index.get(&n).unwrap().clone(), *edge_meta); - }) - } - pub fn child_node_indexes(&self, node: NodeIndex) -> impl Iterator + '_ { self.graph.neighbors(node) } @@ -236,9 +240,9 @@ mod graph_test { // / \ // 1 1 - assert_eq!(2, graph.get_edge_metas(idx0, idx1).count()); + assert_eq!(2, graph.get_child_positions(idx0, idx1).count()); - let mut edge_metas = graph.get_edge_metas(idx0, idx1); + let mut edge_metas = graph.get_child_positions(idx0, idx1); assert_eq!(Some(IncludePosition { line: 2, start: 0, end: 0 }), edge_metas.next()); assert_eq!(Some(IncludePosition { line: 4, start: 0, end: 0 }), edge_metas.next()); } diff --git a/server/main/src/main.rs b/server/main/src/main.rs index a8087ed..b5bdc00 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -251,7 +251,9 @@ impl MinecraftShaderLanguageServer { Some(n) => n, }; - let prev_children: HashSet<_> = HashSet::from_iter(self.graph.borrow().child_node_metas(idx)); + let prev_children: HashSet<_> = HashSet::from_iter(self.graph.borrow().get_all_child_positions(idx).map(|tup| { + (self.graph.borrow().get_node(tup.0), tup.1) + })); let new_children: HashSet<_> = includes.iter().cloned().collect(); let to_be_added = new_children.difference(&prev_children); @@ -825,7 +827,7 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { .child_node_indexes(node) .filter_map::, _>(|child| { let graph = self.graph.borrow(); - graph.get_edge_metas(node, child).map(|value| { + graph.get_child_positions(node, child).map(|value| { let path = graph.get_node(child); let url = match Url::from_file_path(&path) { Ok(url) => url, diff --git a/server/main/src/merge_views.rs b/server/main/src/merge_views.rs index c61e5cc..8eec146 100644 --- a/server/main/src/merge_views.rs +++ b/server/main/src/merge_views.rs @@ -8,6 +8,7 @@ use std::{ use core::slice::Iter; use petgraph::stable_graph::NodeIndex; +use slog_scope::debug; use crate::graph::CachedStableGraph; use crate::source_mapper::SourceMapper; @@ -88,13 +89,7 @@ impl<'a> MergeViewBuilder<'a> { // ); // last_offset_set.insert((first, None), version_char_offsets.1); - self.last_offset_set.insert( - FilialTuple { - child: first, - parent: None, - }, - 0, - ); + self.set_last_offset_for_tuple(None, first, 0); // stack to keep track of the depth first traversal let mut stack = VecDeque::::new(); @@ -102,13 +97,8 @@ impl<'a> MergeViewBuilder<'a> { self.create_merge_views(&mut merge_list, &mut extra_lines, &mut stack); // now we add a view of the remainder of the root file - let offset = *self - .last_offset_set - .get(&FilialTuple { - child: first, - parent: None, - }) - .unwrap(); + + let offset = self.get_last_offset_for_tuple(None, first).unwrap(); let len = first_source.len(); merge_list.push_back(&first_source[min(offset, len)..]); @@ -135,8 +125,8 @@ impl<'a> MergeViewBuilder<'a> { .parent_child_edge_iterator .entry(*n) .or_insert_with(|| { - let edge_metas = self.graph.get_edge_metas(parent, child); - Box::new(edge_metas) + let child_positions = self.graph.get_child_positions(parent, child); + Box::new(child_positions) }) .next() .unwrap(); @@ -147,15 +137,16 @@ impl<'a> MergeViewBuilder<'a> { let (char_for_line, char_following_line) = self.char_offset_for_line(edge.line, parent_source); let offset = *self - .last_offset_set - .insert( - FilialTuple { - child: parent, - parent: stack.back().copied(), - }, - char_following_line, - ) + .set_last_offset_for_tuple(stack.back().copied(), parent, char_following_line) .get_or_insert(0); + + debug!("creating view to start child file"; + "parent" => parent_path.to_str().unwrap(), "child" => child_path.to_str().unwrap(), + "grandparent" => stack.back().copied().map(|g| self.graph.get_node(g).to_str().unwrap().to_string()), // self.graph.get_node().to_str().unwrap(), + "last_parent_offset" => offset, "line" => edge.line, "char_for_line" => char_for_line, + "char_following_line" => char_following_line, + ); + merge_list.push_back(&parent_source[offset..char_for_line]); self.add_opening_line_directive(&child_path, child, merge_list, extra_lines); @@ -173,13 +164,7 @@ impl<'a> MergeViewBuilder<'a> { } }; merge_list.push_back(&child_source[..offset]); - self.last_offset_set.insert( - FilialTuple { - child, - parent: Some(parent), - }, - 0, - ); + self.set_last_offset_for_tuple(Some(parent), child, 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line self.add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines); // if the next pair's parent is not the current pair's parent, we need to bubble up @@ -193,29 +178,17 @@ impl<'a> MergeViewBuilder<'a> { self.create_merge_views(merge_list, extra_lines, stack); stack.pop_back(); - let offset = *self - .last_offset_set - .get(&FilialTuple { - child, - parent: Some(parent), - }) - .unwrap(); + let offset = self.get_last_offset_for_tuple(Some(parent), child).unwrap(); let child_source = self.sources.get(&child_path).unwrap(); // this evaluates to false once the file contents have been exhausted aka offset = child_source.len() + 1 let end_offset = match child_source.ends_with('\n') { - true => 1, /* child_source.len()-1 */ - false => 0, /* child_source.len() */ + true => 1, + false => 0, }; if offset < child_source.len() - end_offset { // if ends in \n\n, we want to exclude the last \n for some reason. Ask optilad - merge_list.push_back(&child_source[offset../* std::cmp::max( */child_source.len()-end_offset/* , offset) */]); - self.last_offset_set.insert( - FilialTuple { - child, - parent: Some(parent), - }, - 0, - ); + merge_list.push_back(&child_source[offset..child_source.len() - end_offset]); + self.set_last_offset_for_tuple(Some(parent), child, 0); } // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line @@ -234,13 +207,7 @@ impl<'a> MergeViewBuilder<'a> { false => child_source.len(), }; merge_list.push_back(&child_source[..offset]); - self.last_offset_set.insert( - FilialTuple { - child, - parent: Some(parent), - }, - 0, - ); + self.set_last_offset_for_tuple(Some(parent), child, 0); // +2 because edge.line is 0 indexed but #line is 1 indexed and references the *following* line self.add_closing_line_directive(edge.line + 2, &parent_path, parent, merge_list, extra_lines); } @@ -248,6 +215,18 @@ impl<'a> MergeViewBuilder<'a> { } } + fn set_last_offset_for_tuple(&mut self, parent: Option, child: NodeIndex, offset: usize) -> Option { + debug!("inserting last offset"; + "parent" => parent.map(|p| self.graph.get_node(p).to_str().unwrap().to_string()), + "child" => self.graph.get_node(child).to_str().unwrap().to_string(), + "offset" => offset); + self.last_offset_set.insert(FilialTuple { child, parent }, offset) + } + + fn get_last_offset_for_tuple(&self, parent: Option, child: NodeIndex) -> Option { + self.last_offset_set.get(&FilialTuple { child, parent }).copied() + } + // returns the character offset + 1 of the end of line number `line` and the character // offset + 1 for the end of the line after the previous one fn char_offset_for_line(&self, line_num: usize, source: &str) -> (usize, usize) { From 941822c5c718a446c8f37406b4b546476e37156b Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 24 Apr 2022 22:17:20 +0100 Subject: [PATCH 47/56] hardcode top-level file set avoids unimported non-toplevel fsh/vsh/etc files being treated as toplevel --- server/main/src/main.rs | 79 ++++++++++++++++++++++++++++++++++------- 1 file changed, 66 insertions(+), 13 deletions(-) diff --git a/server/main/src/main.rs b/server/main/src/main.rs index b5bdc00..b151174 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -60,6 +60,54 @@ mod test; lazy_static! { static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); + static ref TOPLEVEL_FILES: HashSet = { + let mut set = HashSet::with_capacity(6864); + for folder in ["shaders/", "shaders/world0/", "shaders/world1/", "shaders/world-1/"] { + for ext in ["fsh", "vsh", "gsh", "csh"] { + set.insert(format!("{}composite.{}", folder, ext).into()); + for i in 1..=99 { + set.insert(format!("{}composite{}.{}", folder, i, ext).into()); + set.insert(format!("{}deferred{}.{}", folder, i, ext).into()); + set.insert(format!("{}prepare{}.{}", folder, i, ext).into()); + set.insert(format!("{}shadowcomp{}.{}", folder, i, ext).into()); + } + set.insert(format!("{}composite_pre.{}", folder, ext).into()); + set.insert(format!("{}deferred.{}", folder, ext).into()); + set.insert(format!("{}deferred_pre.{}", folder, ext).into()); + set.insert(format!("{}final.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_armor_glint.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_basic.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_beaconbeam.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_block.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_clouds.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_damagedblock.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_entities.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_entities_glowing.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_hand.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_hand.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_hand_water.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_item.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_line.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_skybasic.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_skytextured.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_spidereyes.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_terrain.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_terrain_cutout.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_terrain_cutout_mip.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_terrain_solid.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_textured.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_textured_lit.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_water.{}", folder, ext).into()); + set.insert(format!("{}gbuffers_weather.{}", folder, ext).into()); + set.insert(format!("{}prepare.{}", folder, ext).into()); + set.insert(format!("{}shadow.{}", folder, ext).into()); + set.insert(format!("{}shadow_cutout.{}", folder, ext).into()); + set.insert(format!("{}shadow_solid.{}", folder, ext).into()); + set.insert(format!("{}shadowcomp.{}", folder, ext).into()); + } + } + set + }; } fn main() { @@ -156,7 +204,7 @@ impl MinecraftShaderLanguageServer { } } - pub fn gen_initial_graph(&self) { + fn build_initial_graph(&self) { info!("generating graph for current root"; "root" => self.root.to_str().unwrap()); // filter directories and files not ending in any of the 3 extensions @@ -341,6 +389,13 @@ impl MinecraftShaderLanguageServer { return Ok(diagnostics); } }; + + if !TOPLEVEL_FILES.contains(root_path.strip_prefix(&self.root).unwrap()) { + warn!("got a non-valid toplevel file"; "root_ancestor" => root_path.to_str().unwrap(), "stripped" => root_path.strip_prefix(&self.root).unwrap().to_str().unwrap()); + back_fill(&all_sources, &mut diagnostics); + return Ok(diagnostics); + } + let tree_type = if ext == "fsh" { TreeType::Fragment } else if ext == "vsh" { @@ -350,12 +405,7 @@ impl MinecraftShaderLanguageServer { } else if ext == "csh" { TreeType::Compute } else { - warn!( - "got a non fsh|vsh|gsh|csh as a file root ancestor, skipping lint"; - "extension" => ext, "root_ancestor" => root_path.to_str().unwrap() - ); - back_fill(&all_sources, &mut diagnostics); - return Ok(diagnostics); + unreachable!(); }; let stdout = match self.compile_shader_source(&view, tree_type, &root_path) { @@ -387,6 +437,12 @@ impl MinecraftShaderLanguageServer { Some(ext) => ext.to_str().unwrap(), None => continue, }; + + if !TOPLEVEL_FILES.contains(root_path.strip_prefix(&self.root).unwrap()) { + warn!("got a non-valid toplevel file"; "root_ancestor" => root_path.to_str().unwrap(), "stripped" => root_path.strip_prefix(&self.root).unwrap().to_str().unwrap()); + continue; + } + let tree_type = if ext == "fsh" { TreeType::Fragment } else if ext == "vsh" { @@ -396,11 +452,7 @@ impl MinecraftShaderLanguageServer { } else if ext == "csh" { TreeType::Compute } else { - warn!( - "got a non fsh|vsh|gsh|csh as a file root ancestor, skipping lint"; - "extension" => ext, "root_ancestor" => root_path.to_str().unwrap() - ); - continue; + unreachable!(); }; let sources = self.load_sources(&nodes)?; @@ -566,7 +618,8 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { self.root = root; - self.gen_initial_graph(); + + self.build_initial_graph(); self.set_status("ready", "Project initialized", "$(check)"); }); From d8d77ac600beefff18dbac781574f46f75bfaae5 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 24 Apr 2022 22:38:20 +0100 Subject: [PATCH 48/56] release 0.9.8 --- CHANGELOG.md | 8 ++++++++ package-lock.json | 4 ++-- package.json | 2 +- server/Cargo.lock | 6 +++--- server/logging/Cargo.toml | 2 +- server/logging_macro/Cargo.toml | 2 +- server/main/Cargo.toml | 2 +- 7 files changed, 17 insertions(+), 9 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index d44521d..4556908 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,14 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +## [0.9.8] + +### Fixed + +- NVIDIA diagnostics line offset off-by-one due to confusion with erroneous (non-proper) GLSL files resulting in both -1 and -2 offsets appearing to be valid when only the former is. +- Non-toplevel files being treated as toplevel files when they have .fsh/.vsh/etc and not imported into a valid toplevel file. +- Fix issue in the depth-first-search iterator when a file is imported twice into another file with a different include in between. + ## [0.9.7] ### Fixed diff --git a/package-lock.json b/package-lock.json index 8f8b1aa..0659dea 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,11 +1,11 @@ { "name": "vscode-mc-shader", - "version": "0.9.7", + "version": "0.9.8", "lockfileVersion": 2, "requires": true, "packages": { "": { - "version": "0.9.7", + "version": "0.9.8", "hasInstallScript": true, "license": "MIT", "devDependencies": { diff --git a/package.json b/package.json index 7c3ef15..36dbb57 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "vscode-mc-shader", "displayName": "Minecraft GLSL Shaders", "description": "A Visual Studio Code extension for linting/etc Minecraft GLSL Shaders", - "version": "0.9.7", + "version": "0.9.8", "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", diff --git a/server/Cargo.lock b/server/Cargo.lock index 5d97dab..6139526 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -656,7 +656,7 @@ dependencies = [ [[package]] name = "logging" -version = "0.9.7" +version = "0.9.8" dependencies = [ "lazy_static", "rand 0.8.5", @@ -668,7 +668,7 @@ dependencies = [ [[package]] name = "logging_macro" -version = "0.9.7" +version = "0.9.8" dependencies = [ "quote", "syn", @@ -703,7 +703,7 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f" [[package]] name = "mcshader-lsp" -version = "0.9.7" +version = "0.9.8" dependencies = [ "anyhow", "fs_extra", diff --git a/server/logging/Cargo.toml b/server/logging/Cargo.toml index 7b94e66..3714c9e 100644 --- a/server/logging/Cargo.toml +++ b/server/logging/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging" -version = "0.9.7" +version = "0.9.8" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/logging_macro/Cargo.toml b/server/logging_macro/Cargo.toml index e20d4ed..efce6d8 100644 --- a/server/logging_macro/Cargo.toml +++ b/server/logging_macro/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging_macro" -version = "0.9.7" +version = "0.9.8" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/main/Cargo.toml b/server/main/Cargo.toml index 30ad346..824a69b 100644 --- a/server/main/Cargo.toml +++ b/server/main/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mcshader-lsp" -version = "0.9.7" +version = "0.9.8" authors = ["Noah Santschi-Cooney "] edition = "2021" From c737409fdebd02a54f088ce672f97849a10208dc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?B=C3=A1lint?= Date: Fri, 29 Apr 2022 08:04:34 +0200 Subject: [PATCH 49/56] Doesn't detect vsh files yet --- package-lock.json | 1 + server/main/src/main.rs | 100 ++++++++++++++++++++++------------------ 2 files changed, 55 insertions(+), 46 deletions(-) diff --git a/package-lock.json b/package-lock.json index 0659dea..f455284 100644 --- a/package-lock.json +++ b/package-lock.json @@ -5,6 +5,7 @@ "requires": true, "packages": { "": { + "name": "vscode-mc-shader", "version": "0.9.8", "hasInstallScript": true, "license": "MIT", diff --git a/server/main/src/main.rs b/server/main/src/main.rs index b151174..ab6b8ac 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -58,53 +58,61 @@ mod url_norm; #[cfg(test)] mod test; +pub fn is_top_level(path: &Path) -> bool { + let path = path.as_os_str().to_str().unwrap().replace("\\", "/"); + if !RE_WORLD_FOLDER.is_match(&path) { + return false; + } + let parts: Vec<&str> = path.split("/").collect(); + let len = parts.len(); + (len == 3 || len == 2) && TOPLEVEL_FILES.contains(parts[len - 1]) +} + lazy_static! { static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); - static ref TOPLEVEL_FILES: HashSet = { - let mut set = HashSet::with_capacity(6864); - for folder in ["shaders/", "shaders/world0/", "shaders/world1/", "shaders/world-1/"] { - for ext in ["fsh", "vsh", "gsh", "csh"] { - set.insert(format!("{}composite.{}", folder, ext).into()); - for i in 1..=99 { - set.insert(format!("{}composite{}.{}", folder, i, ext).into()); - set.insert(format!("{}deferred{}.{}", folder, i, ext).into()); - set.insert(format!("{}prepare{}.{}", folder, i, ext).into()); - set.insert(format!("{}shadowcomp{}.{}", folder, i, ext).into()); - } - set.insert(format!("{}composite_pre.{}", folder, ext).into()); - set.insert(format!("{}deferred.{}", folder, ext).into()); - set.insert(format!("{}deferred_pre.{}", folder, ext).into()); - set.insert(format!("{}final.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_armor_glint.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_basic.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_beaconbeam.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_block.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_clouds.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_damagedblock.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_entities.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_entities_glowing.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_hand.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_hand.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_hand_water.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_item.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_line.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_skybasic.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_skytextured.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_spidereyes.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain_cutout.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain_cutout_mip.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain_solid.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_textured.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_textured_lit.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_water.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_weather.{}", folder, ext).into()); - set.insert(format!("{}prepare.{}", folder, ext).into()); - set.insert(format!("{}shadow.{}", folder, ext).into()); - set.insert(format!("{}shadow_cutout.{}", folder, ext).into()); - set.insert(format!("{}shadow_solid.{}", folder, ext).into()); - set.insert(format!("{}shadowcomp.{}", folder, ext).into()); + static ref RE_WORLD_FOLDER: Regex = Regex::new(r#"^shaders(/world-?\d+)?"#).unwrap(); + static ref TOPLEVEL_FILES: HashSet = { + let mut set = HashSet::with_capacity(1716); + for ext in ["fsh", "vsh", "gsh", "csh"] { + set.insert(format!("composite.{}", ext)); + set.insert(format!("deferred.{}", ext)); + set.insert(format!("prepare.{}", ext)); + set.insert(format!("shadowcomp.{}", ext)); + for i in 1..=99 { + set.insert(format!("composite{}.{}", i, ext)); + set.insert(format!("deferred{}.{}", i, ext)); + set.insert(format!("prepare{}.{}", i, ext)); + set.insert(format!("shadowcomp{}.{}", i, ext)); } + set.insert(format!("composite_pre.{}", ext)); + set.insert(format!("deferred_pre.{}", ext)); + set.insert(format!("final.{}", ext)); + set.insert(format!("gbuffers_armor_glint.{}", ext)); + set.insert(format!("gbuffers_basic.{}", ext)); + set.insert(format!("gbuffers_beaconbeam.{}", ext)); + set.insert(format!("gbuffers_block.{}", ext)); + set.insert(format!("gbuffers_clouds.{}", ext)); + set.insert(format!("gbuffers_damagedblock.{}", ext)); + set.insert(format!("gbuffers_entities.{}", ext)); + set.insert(format!("gbuffers_entities_glowing.{}", ext)); + set.insert(format!("gbuffers_hand.{}", ext)); + set.insert(format!("gbuffers_hand_water.{}", ext)); + set.insert(format!("gbuffers_item.{}", ext)); + set.insert(format!("gbuffers_line.{}", ext)); + set.insert(format!("gbuffers_skybasic.{}", ext)); + set.insert(format!("gbuffers_skytextured.{}", ext)); + set.insert(format!("gbuffers_spidereyes.{}", ext)); + set.insert(format!("gbuffers_terrain.{}", ext)); + set.insert(format!("gbuffers_terrain_cutout.{}", ext)); + set.insert(format!("gbuffers_terrain_cutout_mip.{}", ext)); + set.insert(format!("gbuffers_terrain_solid.{}", ext)); + set.insert(format!("gbuffers_textured.{}", ext)); + set.insert(format!("gbuffers_textured_lit.{}", ext)); + set.insert(format!("gbuffers_water.{}", ext)); + set.insert(format!("gbuffers_weather.{}", ext)); + set.insert(format!("shadow.{}", ext)); + set.insert(format!("shadow_cutout.{}", ext)); + set.insert(format!("shadow_solid.{}", ext)); } set }; @@ -390,7 +398,7 @@ impl MinecraftShaderLanguageServer { } }; - if !TOPLEVEL_FILES.contains(root_path.strip_prefix(&self.root).unwrap()) { + if !is_top_level(root_path.strip_prefix(&self.root).unwrap()) { warn!("got a non-valid toplevel file"; "root_ancestor" => root_path.to_str().unwrap(), "stripped" => root_path.strip_prefix(&self.root).unwrap().to_str().unwrap()); back_fill(&all_sources, &mut diagnostics); return Ok(diagnostics); @@ -438,7 +446,7 @@ impl MinecraftShaderLanguageServer { None => continue, }; - if !TOPLEVEL_FILES.contains(root_path.strip_prefix(&self.root).unwrap()) { + if !is_top_level(root_path.strip_prefix(&self.root).unwrap()) { warn!("got a non-valid toplevel file"; "root_ancestor" => root_path.to_str().unwrap(), "stripped" => root_path.strip_prefix(&self.root).unwrap().to_str().unwrap()); continue; } From f8cc2eed2252996180f0f5269c3b06b640bb9dae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?B=C3=A1lint?= Date: Fri, 29 Apr 2022 08:04:34 +0200 Subject: [PATCH 50/56] Fixed issue with modded worlds --- package-lock.json | 1 + server/main/src/main.rs | 100 ++++++++++++++++++++++------------------ 2 files changed, 55 insertions(+), 46 deletions(-) diff --git a/package-lock.json b/package-lock.json index 0659dea..f455284 100644 --- a/package-lock.json +++ b/package-lock.json @@ -5,6 +5,7 @@ "requires": true, "packages": { "": { + "name": "vscode-mc-shader", "version": "0.9.8", "hasInstallScript": true, "license": "MIT", diff --git a/server/main/src/main.rs b/server/main/src/main.rs index b151174..ab6b8ac 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -58,53 +58,61 @@ mod url_norm; #[cfg(test)] mod test; +pub fn is_top_level(path: &Path) -> bool { + let path = path.as_os_str().to_str().unwrap().replace("\\", "/"); + if !RE_WORLD_FOLDER.is_match(&path) { + return false; + } + let parts: Vec<&str> = path.split("/").collect(); + let len = parts.len(); + (len == 3 || len == 2) && TOPLEVEL_FILES.contains(parts[len - 1]) +} + lazy_static! { static ref RE_INCLUDE: Regex = Regex::new(r#"^(?:\s)*?(?:#include) "(.+)"\r?"#).unwrap(); - static ref TOPLEVEL_FILES: HashSet = { - let mut set = HashSet::with_capacity(6864); - for folder in ["shaders/", "shaders/world0/", "shaders/world1/", "shaders/world-1/"] { - for ext in ["fsh", "vsh", "gsh", "csh"] { - set.insert(format!("{}composite.{}", folder, ext).into()); - for i in 1..=99 { - set.insert(format!("{}composite{}.{}", folder, i, ext).into()); - set.insert(format!("{}deferred{}.{}", folder, i, ext).into()); - set.insert(format!("{}prepare{}.{}", folder, i, ext).into()); - set.insert(format!("{}shadowcomp{}.{}", folder, i, ext).into()); - } - set.insert(format!("{}composite_pre.{}", folder, ext).into()); - set.insert(format!("{}deferred.{}", folder, ext).into()); - set.insert(format!("{}deferred_pre.{}", folder, ext).into()); - set.insert(format!("{}final.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_armor_glint.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_basic.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_beaconbeam.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_block.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_clouds.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_damagedblock.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_entities.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_entities_glowing.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_hand.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_hand.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_hand_water.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_item.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_line.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_skybasic.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_skytextured.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_spidereyes.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain_cutout.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain_cutout_mip.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_terrain_solid.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_textured.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_textured_lit.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_water.{}", folder, ext).into()); - set.insert(format!("{}gbuffers_weather.{}", folder, ext).into()); - set.insert(format!("{}prepare.{}", folder, ext).into()); - set.insert(format!("{}shadow.{}", folder, ext).into()); - set.insert(format!("{}shadow_cutout.{}", folder, ext).into()); - set.insert(format!("{}shadow_solid.{}", folder, ext).into()); - set.insert(format!("{}shadowcomp.{}", folder, ext).into()); + static ref RE_WORLD_FOLDER: Regex = Regex::new(r#"^shaders(/world-?\d+)?"#).unwrap(); + static ref TOPLEVEL_FILES: HashSet = { + let mut set = HashSet::with_capacity(1716); + for ext in ["fsh", "vsh", "gsh", "csh"] { + set.insert(format!("composite.{}", ext)); + set.insert(format!("deferred.{}", ext)); + set.insert(format!("prepare.{}", ext)); + set.insert(format!("shadowcomp.{}", ext)); + for i in 1..=99 { + set.insert(format!("composite{}.{}", i, ext)); + set.insert(format!("deferred{}.{}", i, ext)); + set.insert(format!("prepare{}.{}", i, ext)); + set.insert(format!("shadowcomp{}.{}", i, ext)); } + set.insert(format!("composite_pre.{}", ext)); + set.insert(format!("deferred_pre.{}", ext)); + set.insert(format!("final.{}", ext)); + set.insert(format!("gbuffers_armor_glint.{}", ext)); + set.insert(format!("gbuffers_basic.{}", ext)); + set.insert(format!("gbuffers_beaconbeam.{}", ext)); + set.insert(format!("gbuffers_block.{}", ext)); + set.insert(format!("gbuffers_clouds.{}", ext)); + set.insert(format!("gbuffers_damagedblock.{}", ext)); + set.insert(format!("gbuffers_entities.{}", ext)); + set.insert(format!("gbuffers_entities_glowing.{}", ext)); + set.insert(format!("gbuffers_hand.{}", ext)); + set.insert(format!("gbuffers_hand_water.{}", ext)); + set.insert(format!("gbuffers_item.{}", ext)); + set.insert(format!("gbuffers_line.{}", ext)); + set.insert(format!("gbuffers_skybasic.{}", ext)); + set.insert(format!("gbuffers_skytextured.{}", ext)); + set.insert(format!("gbuffers_spidereyes.{}", ext)); + set.insert(format!("gbuffers_terrain.{}", ext)); + set.insert(format!("gbuffers_terrain_cutout.{}", ext)); + set.insert(format!("gbuffers_terrain_cutout_mip.{}", ext)); + set.insert(format!("gbuffers_terrain_solid.{}", ext)); + set.insert(format!("gbuffers_textured.{}", ext)); + set.insert(format!("gbuffers_textured_lit.{}", ext)); + set.insert(format!("gbuffers_water.{}", ext)); + set.insert(format!("gbuffers_weather.{}", ext)); + set.insert(format!("shadow.{}", ext)); + set.insert(format!("shadow_cutout.{}", ext)); + set.insert(format!("shadow_solid.{}", ext)); } set }; @@ -390,7 +398,7 @@ impl MinecraftShaderLanguageServer { } }; - if !TOPLEVEL_FILES.contains(root_path.strip_prefix(&self.root).unwrap()) { + if !is_top_level(root_path.strip_prefix(&self.root).unwrap()) { warn!("got a non-valid toplevel file"; "root_ancestor" => root_path.to_str().unwrap(), "stripped" => root_path.strip_prefix(&self.root).unwrap().to_str().unwrap()); back_fill(&all_sources, &mut diagnostics); return Ok(diagnostics); @@ -438,7 +446,7 @@ impl MinecraftShaderLanguageServer { None => continue, }; - if !TOPLEVEL_FILES.contains(root_path.strip_prefix(&self.root).unwrap()) { + if !is_top_level(root_path.strip_prefix(&self.root).unwrap()) { warn!("got a non-valid toplevel file"; "root_ancestor" => root_path.to_str().unwrap(), "stripped" => root_path.strip_prefix(&self.root).unwrap().to_str().unwrap()); continue; } From 0768abb1220a7b496761e9847a6b499c816e1084 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?B=C3=A1lint?= Date: Fri, 29 Apr 2022 19:02:15 +0200 Subject: [PATCH 51/56] Replaced slash conversion with lib function --- server/main/src/main.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/server/main/src/main.rs b/server/main/src/main.rs index ab6b8ac..7798e53 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -7,6 +7,7 @@ use rust_lsp::lsp::*; use rust_lsp::lsp_types::{notification::*, *}; use petgraph::stable_graph::NodeIndex; +use path_slash::PathExt; use serde::Deserialize; use serde_json::{from_value, Value}; @@ -59,7 +60,7 @@ mod url_norm; mod test; pub fn is_top_level(path: &Path) -> bool { - let path = path.as_os_str().to_str().unwrap().replace("\\", "/"); + let path = path.to_slash().unwrap(); if !RE_WORLD_FOLDER.is_match(&path) { return false; } From 05e52fc8d08c80dddf60abe144222de5ae604928 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tristan=20Dani=C3=ABl=20Maat?= Date: Thu, 18 Aug 2022 04:09:50 +0100 Subject: [PATCH 52/56] Fix crashes when run with eglot as a client This just handles ConfigurationDidChange events in which the "mcglsl" key wasn't set without crashing, by ignoring them; if the configuration changed, but none of our configuration changed, there's nothing we need to update. Obviously there is still a lot that can go wrong here, but this allows running the language server with https://github.com/joaotavora/eglot, as that language server sends a ConfigurationDidChange on startup if any configuration is set (including for other language servers). --- server/main/src/main.rs | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/server/main/src/main.rs b/server/main/src/main.rs index 7798e53..91b1292 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -651,14 +651,16 @@ impl LanguageServerHandling for MinecraftShaderLanguageServer { log_level: String, } - let config: Configuration = from_value(params.settings.as_object().unwrap().get("mcglsl").unwrap().to_owned()).unwrap(); + if let Some(settings) = params.settings.as_object().unwrap().get("mcglsl") { + let config: Configuration = from_value(settings.to_owned()).unwrap(); - info!("got updated configuration"; "config" => params.settings.as_object().unwrap().get("mcglsl").unwrap().to_string()); + info!("got updated configuration"; "config" => params.settings.as_object().unwrap().get("mcglsl").unwrap().to_string()); - configuration::handle_log_level_change(config.log_level, |level| { - self.log_guard = None; // set to None so Drop is invoked - self.log_guard = Some(logging::set_logger_with_level(level)); - }) + configuration::handle_log_level_change(config.log_level, |level| { + self.log_guard = None; // set to None so Drop is invoked + self.log_guard = Some(logging::set_logger_with_level(level)); + }) + } }); } From b6da5c97fb1a41f5452bd1f2ec26373b1512e424 Mon Sep 17 00:00:00 2001 From: GeForceLegend <512287858@qq.com> Date: Sun, 5 Feb 2023 09:54:56 +0800 Subject: [PATCH 53/56] Update to latest rust nightly I'm not sure if these 2 packages are same since I can't find any document direct to std::lazy::OnceCell --- client/src/extension.ts | 2 +- server/main/src/diagnostics_parser.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/client/src/extension.ts b/client/src/extension.ts index b1863db..87efbc3 100644 --- a/client/src/extension.ts +++ b/client/src/extension.ts @@ -25,7 +25,7 @@ export class Extension { readonly package: { version: string - } = vscode.extensions.getExtension(this.extensionID)!.packageJSON; + } = vscode.extensions.getExtension(this.extensionID)!.packageJSON public get context(): vscode.ExtensionContext { return this.extensionContext diff --git a/server/main/src/diagnostics_parser.rs b/server/main/src/diagnostics_parser.rs index 2c4279b..2f61b64 100644 --- a/server/main/src/diagnostics_parser.rs +++ b/server/main/src/diagnostics_parser.rs @@ -1,4 +1,4 @@ -use std::{collections::HashMap, lazy::OnceCell, path::Path}; +use std::{collections::HashMap, cell::OnceCell, path::Path}; use regex::Regex; use rust_lsp::lsp_types::{Diagnostic, DiagnosticSeverity, Position, Range}; From 78b6a6ef1dd1587b05f05de96bc793739b9b3826 Mon Sep 17 00:00:00 2001 From: GeForceLegend <512287858@qq.com> Date: Sun, 5 Feb 2023 09:56:56 +0800 Subject: [PATCH 54/56] Added highlight support for csh with suffixes Compute shader with _a to _z suffix can get highlighted now --- server/main/src/main.rs | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/server/main/src/main.rs b/server/main/src/main.rs index 91b1292..119dbdc 100644 --- a/server/main/src/main.rs +++ b/server/main/src/main.rs @@ -115,6 +115,21 @@ lazy_static! { set.insert(format!("shadow_cutout.{}", ext)); set.insert(format!("shadow_solid.{}", ext)); } + let base_char_num = 'a' as u8; + for suffix_num in 0u8..=25u8 { + let suffix_char = (base_char_num + suffix_num) as char; + set.insert(format!("composite_{}.csh", suffix_char)); + set.insert(format!("deferred_{}.csh", suffix_char)); + set.insert(format!("prepare_{}.csh", suffix_char)); + set.insert(format!("shadowcomp_{}.csh", suffix_char)); + for i in 1..=99 { + let total_suffix = format!("{}_{}", i, suffix_char); + set.insert(format!("composite{}.csh", total_suffix)); + set.insert(format!("deferred{}.csh", total_suffix)); + set.insert(format!("prepare{}.csh", total_suffix)); + set.insert(format!("shadowcomp{}.csh", total_suffix)); + } + } set }; } From 4dd55423556fdb73cab92476066833c939e4c9ef Mon Sep 17 00:00:00 2001 From: GeForceLegend <512287858@qq.com> Date: Sun, 5 Feb 2023 10:53:28 +0800 Subject: [PATCH 55/56] Fixed icons --- README.md | 2 +- package.json | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index dcad726..74fb1d5 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Minecraft GLSL Shaders Language Server ## mcshader-lsp -[![Marketplace Version](https://vsmarketplacebadge.apphb.com/version/strum355.vscode-mc-shader.svg)](https://marketplace.visualstudio.com/items?itemName=strum355.vscode-mc-shader) [![Installs](https://vsmarketplacebadge.apphb.com/installs/strum355.vscode-mc-shader.svg)](https://marketplace.visualstudio.com/items?itemName=strum355.vscode-mc-shader) +[![Marketplace Version](https://img.shields.io/visual-studio-marketplace/v/strum355.vscode-mc-shader.svg)](https://marketplace.visualstudio.com/items?itemName=strum355.vscode-mc-shader) [![Installs](https://img.shields.io/visual-studio-marketplace/i/strum355.vscode-mc-shader.svg)](https://marketplace.visualstudio.com/items?itemName=strum355.vscode-mc-shader) [![license](https://img.shields.io/github/license/Strum355/vscode-mc-shader.svg)](https://github.com/Strum355/mcshader-lsp) [![Issues](https://img.shields.io/github/issues-raw/Strum355/mcshader-lsp.svg)](https://github.com/Strum355/mcshader-lsp/issues) [![Build Status](https://img.shields.io/drone/build/Strum355/mcshader-lsp)](https://cloud.drone.io/Strum355/mcshader-lsp) diff --git a/package.json b/package.json index 36dbb57..36312f3 100644 --- a/package.json +++ b/package.json @@ -6,7 +6,7 @@ "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", - "icon": "logo-mini.png", + "icon": "logo-min.png", "repository": { "url": "https://github.com/Strum355/mcshader-lsp" }, From 85cbb6d81e9e70aadaf94bd2b8eb9a8c54818269 Mon Sep 17 00:00:00 2001 From: Noah Santschi-Cooney Date: Sun, 12 Feb 2023 16:32:38 +0000 Subject: [PATCH 56/56] release 0.9.9 --- CHANGELOG.md | 12 ++++++++++++ package.json | 2 +- server/Cargo.lock | 6 +++--- server/logging/Cargo.toml | 2 +- server/logging_macro/Cargo.toml | 2 +- server/main/Cargo.toml | 2 +- 6 files changed, 19 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4556908..d7e089d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,18 @@ All notable changes to the "vscode-mc-shader" extension will be documented in th The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +## [0.9.9] + +### Added + +- Support for mod world folders, outside the standard world{-1,0,1}. +- Support for compute shader files ending in \_a to \_z. + +### Fixed + +- Crash when running with eglot as LSP client. +- Extension icon client not displaying (encoding issue). + ## [0.9.8] ### Fixed diff --git a/package.json b/package.json index 36312f3..0ecfe79 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "vscode-mc-shader", "displayName": "Minecraft GLSL Shaders", "description": "A Visual Studio Code extension for linting/etc Minecraft GLSL Shaders", - "version": "0.9.8", + "version": "0.9.9", "publisher": "Strum355", "author": "Noah Santschi-Cooney (Strum355)", "license": "MIT", diff --git a/server/Cargo.lock b/server/Cargo.lock index 6139526..05c839a 100644 --- a/server/Cargo.lock +++ b/server/Cargo.lock @@ -656,7 +656,7 @@ dependencies = [ [[package]] name = "logging" -version = "0.9.8" +version = "0.9.9" dependencies = [ "lazy_static", "rand 0.8.5", @@ -668,7 +668,7 @@ dependencies = [ [[package]] name = "logging_macro" -version = "0.9.8" +version = "0.9.9" dependencies = [ "quote", "syn", @@ -703,7 +703,7 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f" [[package]] name = "mcshader-lsp" -version = "0.9.8" +version = "0.9.9" dependencies = [ "anyhow", "fs_extra", diff --git a/server/logging/Cargo.toml b/server/logging/Cargo.toml index 3714c9e..2abdf7e 100644 --- a/server/logging/Cargo.toml +++ b/server/logging/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging" -version = "0.9.8" +version = "0.9.9" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/logging_macro/Cargo.toml b/server/logging_macro/Cargo.toml index efce6d8..f1e6957 100644 --- a/server/logging_macro/Cargo.toml +++ b/server/logging_macro/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "logging_macro" -version = "0.9.8" +version = "0.9.9" authors = ["Noah Santschi-Cooney "] edition = "2021" diff --git a/server/main/Cargo.toml b/server/main/Cargo.toml index 824a69b..3aa68c2 100644 --- a/server/main/Cargo.toml +++ b/server/main/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mcshader-lsp" -version = "0.9.8" +version = "0.9.9" authors = ["Noah Santschi-Cooney "] edition = "2021"