Merge pull request #45 from kbwo/feat/toml-config

Configuration with external file
This commit is contained in:
Kodai Kabasawa 2024-11-10 15:50:51 +09:00 committed by GitHub
commit 520a7e4c5f
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
11 changed files with 235 additions and 193 deletions

15
.testingls.toml Normal file
View file

@ -0,0 +1,15 @@
enableWorkspaceDiagnostics = true
[adapterCommand.rust]
path = "testing-ls-adapter"
extra_arg = [
"--test-kind=cargo-test",
"--workspace"
]
include = [
"/**/*.rs"
]
exclude = [
"/demo/**/*"
]
workspace_dir = "."

View file

@ -1,15 +1,5 @@
{
"testing.enable": true,
"testing.fileTypes": ["rust"],
"testing.adapterCommand": {
"rust": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=cargo-test", "--workspace"],
"include": ["/**/*.rs"],
"exclude": ["/demo/**/*"],
"workspace_dir": "."
}
},
"testing.enableWorkspaceDiagnostics": true,
"testing.server.path": "testing-language-server",
"testing.trace.server": "verbose"

75
Cargo.lock generated
View file

@ -256,6 +256,12 @@ dependencies = [
"windows-sys 0.48.0",
]
[[package]]
name = "equivalent"
version = "1.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
[[package]]
name = "errno"
version = "0.3.8"
@ -322,6 +328,12 @@ dependencies = [
"walkdir",
]
[[package]]
name = "hashbrown"
version = "0.15.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3a9bfc1af68b1726ea47d3d5109de126281def866b33970e10fbab11b5dafab3"
[[package]]
name = "heck"
version = "0.4.1"
@ -383,6 +395,16 @@ dependencies = [
"winapi-util",
]
[[package]]
name = "indexmap"
version = "2.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "707907fe3c25f5424cce2cb7e1cbcafee6bdbe735ca90ef77c29e84591e5b9da"
dependencies = [
"equivalent",
"hashbrown",
]
[[package]]
name = "itoa"
version = "1.0.11"
@ -630,6 +652,15 @@ dependencies = [
"syn",
]
[[package]]
name = "serde_spanned"
version = "0.6.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "87607cb1398ed59d48732e575a4c28a7a8ebf2454b964fe3f224f2afc07909e1"
dependencies = [
"serde",
]
[[package]]
name = "sharded-slab"
version = "0.1.7"
@ -732,6 +763,7 @@ dependencies = [
"serde_json",
"strum",
"thiserror",
"toml",
"tracing",
"tracing-appender",
"tracing-subscriber",
@ -838,6 +870,40 @@ version = "0.1.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20"
[[package]]
name = "toml"
version = "0.8.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a1ed1f98e3fdc28d6d910e6737ae6ab1a93bf1985935a1193e68f93eeb68d24e"
dependencies = [
"serde",
"serde_spanned",
"toml_datetime",
"toml_edit",
]
[[package]]
name = "toml_datetime"
version = "0.6.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0dd7358ecb8fc2f8d014bf86f6f638ce72ba252a2c3a2572f2a795f1d23efb41"
dependencies = [
"serde",
]
[[package]]
name = "toml_edit"
version = "0.22.22"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4ae48d6208a266e853d946088ed816055e556cc6028c5e8e2b84d9fa5dd7c7f5"
dependencies = [
"indexmap",
"serde",
"serde_spanned",
"toml_datetime",
"winnow",
]
[[package]]
name = "tracing"
version = "0.1.40"
@ -1209,6 +1275,15 @@ version = "0.52.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bec47e5bfd1bff0eeaf6d8b485cc1074891a197ab4225d504cb7a1ab88b02bf0"
[[package]]
name = "winnow"
version = "0.6.20"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "36c1fec1a2bb5866f07c25f68c26e565c4c200aebb96d7e55710c19d3e8ac49b"
dependencies = [
"memchr",
]
[[package]]
name = "xml-rs"
version = "0.8.21"

View file

@ -48,3 +48,4 @@ glob = { workspace = true }
globwalk = "0.9.1"
tree-sitter-php = "0.22.8"
chrono = "0.4.38"
toml = "0.8.19"

111
README.md
View file

@ -33,17 +33,69 @@ cargo install testing-ls-adapter
## Configuration
### Required settings for all editors
You need to prepare .testingls.toml. See [this](./demo/.testingls.toml) for an example of the configuration.
```.testingls.toml
enableWorkspaceDiagnostics = true
[adapterCommand.cargo-test]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=cargo-test"]
include = ["/**/src/**/*.rs"]
exclude = ["/**/target/**"]
[adapterCommand.cargo-nextest]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=cargo-nextest"]
include = ["/**/src/**/*.rs"]
exclude = ["/**/target/**"]
[adapterCommand.jest]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=jest"]
include = ["/jest/*.js"]
exclude = ["/jest/**/node_modules/**/*"]
[adapterCommand.vitest]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=vitest"]
include = ["/vitest/*.test.ts", "/vitest/config/**/*.test.ts"]
exclude = ["/vitest/**/node_modules/**/*"]
[adapterCommand.deno]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=deno"]
include = ["/deno/*.ts"]
exclude = []
[adapterCommand.go]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=go-test"]
include = ["/**/*.go"]
exclude = []
[adapterCommand.node-test]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=node-test"]
include = ["/node-test/*.test.js"]
exclude = []
[adapterCommand.phpunit]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=phpunit"]
include = ["/**/*Test.php"]
exclude = ["/phpunit/vendor/**/*.php"]
```
### VSCode
Install from [VSCode Marketplace](https://marketplace.visualstudio.com/items?itemName=kbwo.testing-language-server).
You should set `adapterCommand` in `initializationOptions` for each project.
You can see the example in [settings.json](./demo/.vscode/settings.json).
### coc.nvim
Install from `:CocInstall coc-testing-ls`.
You should set `adapterCommand` in `initializationOptions` for each project.
You can see the example in [See more example](./demo/.vim/coc-settings.json)
You can see the example in [See more example](./.vim/coc-settings.json)
### Neovim (nvim-lspconfig)
@ -55,26 +107,8 @@ local util = require "lspconfig/util"
configs.testing_ls = {
default_config = {
cmd = { "testing-language-server" },
filetypes = { "rust" },
root_dir = util.root_pattern(".git", "Cargo.toml"),
init_options = {
enable = true,
fileTypes = {"rust"},
adapterCommand = {
-- See test execution settings for each project
-- This configuration assumes a Rust project
rust = {
path = "testing-ls-adapter",
extra_arg = { "--test-kind=cargo-test", "--workspace" },
include = { "/demo/**/src/**/*.rs"},
exclude = { "/**/target/**"},
}
},
enableWorkspaceDiagnostics = true,
trace = {
server = "verbose"
}
}
filetypes = {},
root_dir = util.root_pattern(".testingls.toml", ".git" ),
},
docs = {
description = [[
@ -91,35 +125,6 @@ lspconfig.testing_ls.setup{}
### Helix
See [language.toml](./demo/.helix/language.toml).
## ⚠️ Breaking Changes (2024-10-25)
The configuration structure for adapter commands has been changed:
**Before:**
```json
"adapterCommand": {
"rust": [
{
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=cargo-test"]
// ...
}
]
}
```
**After:**
```json
"adapterCommand": {
"rust": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=cargo-test"]
// ...
}
}
```
The array wrapper has been removed to simplify the configuration structure. Please update your settings accordingly.
## Adapter

View file

@ -2,32 +2,6 @@
command = "testing-language-server"
args = []
[language-server.testing-ls.config.adapterCommand]
cargo-test = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=cargo-test"], include = ["/**/src/**/*.rs"], exclude = ["/**/target/**"] }
]
cargo-nextest = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=cargo-nextest"], include = ["/**/src/**/*.rs"], exclude = ["/**/target/**"] }
]
jest = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=jest"], include = ["/jest/*.js"], exclude = ["/jest/**/node_modules/**/*"] }
]
vitest = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=vitest"], include = ["/vitest/*.test.ts", "/vitest/config/**/*.test.ts"], exclude = ["/vitest/**/node_modules/**/*"] }
]
deno = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=deno"], include = ["/deno/*.ts"], exclude = [] }
]
go = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=go-test"], include = ["/**/*.go"], exclude = [] }
]
node-test = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=node-test"], include = ["/node-test/*.test.js"], exclude = [] }
]
phpunit = [
{ path = "testing-ls-adapter", extra_arg = ["--test-kind=phpunit"], include = ["/**/*Test.php"], exclude = ["/phpunit/vendor/**/*.php"] }
]
[[language]]
name = "rust"
language-servers = [ { name = "testing-ls", only-features = [ "diagnostics" ] }, "rust-analyzer" ]

49
demo/.testingls.toml Normal file
View file

@ -0,0 +1,49 @@
enableWorkspaceDiagnostics = true
[adapterCommand.cargo-test]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=cargo-test"]
include = ["/**/src/**/*.rs"]
exclude = ["/**/target/**"]
[adapterCommand.cargo-nextest]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=cargo-nextest"]
include = ["/**/src/**/*.rs"]
exclude = ["/**/target/**"]
[adapterCommand.jest]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=jest"]
include = ["/jest/*.js"]
exclude = ["/jest/**/node_modules/**/*"]
[adapterCommand.vitest]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=vitest"]
include = ["/vitest/*.test.ts", "/vitest/config/**/*.test.ts"]
exclude = ["/vitest/**/node_modules/**/*"]
[adapterCommand.deno]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=deno"]
include = ["/deno/*.ts"]
exclude = []
[adapterCommand.go]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=go-test"]
include = ["/**/*.go"]
exclude = []
[adapterCommand.node-test]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=node-test"]
include = ["/node-test/*.test.js"]
exclude = []
[adapterCommand.phpunit]
path = "testing-ls-adapter"
extra_arg = ["--test-kind=phpunit"]
include = ["/**/*Test.php"]
exclude = ["/phpunit/vendor/**/*.php"]

View file

@ -3,59 +3,14 @@
"testing": {
"command": "testing-language-server",
"trace.server": "verbose",
"filetypes": ["rust", "javascript", "go", "typescript", "php"],
"initializationOptions": {
"adapterCommand": {
"cargo-test": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=cargo-test"],
"include": ["/**/src/**/*.rs"],
"exclude": ["/**/target/**"]
},
"cargo-nextest": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=cargo-nextest"],
"include": ["/**/src/**/*.rs"],
"exclude": ["/**/target/**"]
},
"jest": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=jest"],
"include": ["/jest/*.js"],
"exclude": ["/jest/**/node_modules/**/*"]
},
"vitest": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=vitest"],
"include": ["/vitest/*.test.ts", "/vitest/config/**/*.test.ts"],
"exclude": ["/vitest/**/node_modules/**/*"]
},
"deno": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=deno"],
"include": ["/deno/*.ts"],
"exclude": []
},
"go": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=go-test"],
"include": ["/**/*.go"],
"exclude": []
},
"node-test": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=node-test"],
"include": ["/node-test/*.test.js"],
"exclude": []
},
"phpunit": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=phpunit"],
"include": ["/**/*Test.php"],
"exclude": ["/phpunit/vendor/**/*.php"]
}
}
}
"filetypes": [
"rust",
"javascript",
"go",
"typescript",
"php"
],
"initializationOptions": {}
}
},
"deno.enable": false,

View file

@ -1,50 +1,12 @@
{
"testing.enable": true,
"filetypes": ["rust", "javascript", "go", "typescript", "php"],
"testing.adapterCommand": {
"cargo-nextest": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=cargo-nextest"],
"include": ["/**/src/**/*.rs"],
"exclude": ["/**/target/**"]
},
"jest": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=jest"],
"include": ["/jest/*.js"],
"exclude": ["/jest/**/node_modules/**/*"]
},
"vitest": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=vitest"],
"include": ["/vitest/*.test.ts", "/vitest/config/**/*.test.ts"],
"exclude": ["/vitest/**/node_modules/**/*"]
},
"deno": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=deno"],
"include": ["/deno/*.ts"],
"exclude": []
},
"go": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=go-test"],
"include": ["/**/*.go"],
"exclude": []
},
"node-test": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=node-test"],
"include": ["/node-test/*.test.js"],
"exclude": []
},
"phpunit": {
"path": "testing-ls-adapter",
"extra_arg": ["--test-kind=phpunit"],
"include": ["/**/*Test.php"],
"exclude": ["/phpunit/vendor/**/*.php"]
}
},
"filetypes": [
"rust",
"javascript",
"go",
"typescript",
"php"
],
"testing.enableWorkspaceDiagnostics": true,
"testing.server.path": "testing-language-server",
"testing.trace.server": "verbose"

View file

@ -31,6 +31,7 @@ fn extract_uri(params: &Value) -> Result<String, serde_json::Error> {
}
fn main_loop(server: &mut TestingLS) -> Result<(), LSError> {
let mut is_workspace_checked = false;
loop {
let mut size = 0;
'read_header: loop {
@ -93,6 +94,7 @@ fn main_loop(server: &mut TestingLS) -> Result<(), LSError> {
std::process::exit(0);
}
"workspace/diagnostic" => {
is_workspace_checked = true;
server.diagnose_workspace()?;
}
"textDocument/diagnostic" | "textDocument/didSave" => {
@ -100,6 +102,10 @@ fn main_loop(server: &mut TestingLS) -> Result<(), LSError> {
server.check_file(&uri, false)?;
}
"textDocument/didOpen" => {
if !is_workspace_checked {
is_workspace_checked = true;
server.diagnose_workspace()?;
}
let uri = extract_textdocument_uri(params)?;
if server.refreshing_needed(&uri) {
server.refresh_workspaces_cache()?;

View file

@ -14,6 +14,8 @@ use std::path::PathBuf;
use std::process::Command;
use std::process::Output;
const TOML_FILE_NAME: &str = ".testingls.toml";
#[derive(Deserialize, Default)]
#[serde(rename_all = "camelCase")]
pub struct InitializedOptions {
@ -136,12 +138,20 @@ impl TestingLS {
&self,
options: Option<&Value>,
) -> Result<InitializedOptions, LSError> {
if let Some(options) = options {
Ok(serde_json::from_value(options.clone())?)
} else {
Err(LSError::Any(anyhow::anyhow!(
"Invalid initialization options"
)))
let project_dir = self.project_dir()?;
let toml_path = project_dir.join(TOML_FILE_NAME);
let toml_content = std::fs::read_to_string(toml_path);
match toml_content {
Ok(toml_content) => Ok(toml::from_str::<InitializedOptions>(&toml_content).unwrap()),
Err(_) => {
if let Some(options) = options {
Ok(serde_json::from_value(options.clone())?)
} else {
Err(LSError::Any(anyhow::anyhow!(
"Invalid initialization options"
)))
}
}
}
}