2020-07-23 15:26:25 -05:00
|
|
|
mod testdir;
|
2018-09-01 12:21:11 -05:00
|
|
|
mod support;
|
|
|
|
|
2020-04-23 11:50:25 -05:00
|
|
|
use std::{collections::HashMap, path::PathBuf, time::Instant};
|
2019-01-10 15:37:10 -06:00
|
|
|
|
2019-01-14 04:55:56 -06:00
|
|
|
use lsp_types::{
|
2020-05-10 12:25:37 -05:00
|
|
|
notification::DidOpenTextDocument,
|
2020-06-05 08:49:12 -05:00
|
|
|
request::{CodeActionRequest, Completion, Formatting, GotoTypeDefinition, HoverRequest},
|
2020-05-10 12:25:37 -05:00
|
|
|
CodeActionContext, CodeActionParams, CompletionParams, DidOpenTextDocumentParams,
|
|
|
|
DocumentFormattingParams, FormattingOptions, GotoDefinitionParams, HoverParams,
|
|
|
|
PartialResultParams, Position, Range, TextDocumentItem, TextDocumentPositionParams,
|
|
|
|
WorkDoneProgressParams,
|
2019-01-03 07:43:47 -06:00
|
|
|
};
|
2020-05-10 12:25:37 -05:00
|
|
|
use rust_analyzer::lsp_ext::{OnEnter, Runnables, RunnablesParams};
|
2018-12-06 14:07:31 -06:00
|
|
|
use serde_json::json;
|
2019-12-07 05:46:36 -06:00
|
|
|
use test_utils::skip_slow_tests;
|
2018-09-01 12:21:11 -05:00
|
|
|
|
2020-07-23 15:26:25 -05:00
|
|
|
use crate::{
|
|
|
|
support::{project, Project},
|
|
|
|
testdir::TestDir,
|
|
|
|
};
|
2018-09-01 12:21:11 -05:00
|
|
|
|
2020-02-18 06:53:02 -06:00
|
|
|
const PROFILE: &str = "";
|
2019-05-29 02:33:09 -05:00
|
|
|
// const PROFILE: &'static str = "*@3>100";
|
2018-09-02 06:46:15 -05:00
|
|
|
|
2019-01-10 11:13:08 -06:00
|
|
|
#[test]
|
|
|
|
fn completes_items_from_standard_library() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2019-01-10 15:37:10 -06:00
|
|
|
let project_start = Instant::now();
|
2019-08-19 07:41:18 -05:00
|
|
|
let server = Project::with_fixture(
|
2019-01-10 11:13:08 -06:00
|
|
|
r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2019-01-10 11:13:08 -06:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/lib.rs
|
2019-01-10 15:37:10 -06:00
|
|
|
use std::collections::Spam;
|
2019-01-10 11:13:08 -06:00
|
|
|
"#,
|
2019-08-19 07:41:18 -05:00
|
|
|
)
|
|
|
|
.with_sysroot(true)
|
|
|
|
.server();
|
2019-03-07 08:46:17 -06:00
|
|
|
server.wait_until_workspace_is_loaded();
|
2019-01-10 15:37:10 -06:00
|
|
|
eprintln!("loading took {:?}", project_start.elapsed());
|
|
|
|
let completion_start = Instant::now();
|
|
|
|
let res = server.send_request::<Completion>(CompletionParams {
|
2019-07-07 13:13:13 -05:00
|
|
|
text_document_position: TextDocumentPositionParams::new(
|
|
|
|
server.doc_id("src/lib.rs"),
|
|
|
|
Position::new(0, 23),
|
|
|
|
),
|
2019-01-10 15:37:10 -06:00
|
|
|
context: None,
|
2019-12-11 11:34:01 -06:00
|
|
|
partial_result_params: PartialResultParams::default(),
|
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2019-01-10 15:37:10 -06:00
|
|
|
});
|
2020-06-11 04:04:09 -05:00
|
|
|
assert!(res.to_string().contains("HashMap"));
|
2019-01-10 15:37:10 -06:00
|
|
|
eprintln!("completion took {:?}", completion_start.elapsed());
|
2019-01-10 11:13:08 -06:00
|
|
|
}
|
|
|
|
|
2018-09-02 08:36:03 -05:00
|
|
|
#[test]
|
|
|
|
fn test_runnables_project() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2019-04-13 13:33:49 -05:00
|
|
|
let code = r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /foo/Cargo.toml
|
2018-09-02 08:36:03 -05:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /foo/src/lib.rs
|
2018-09-02 08:36:03 -05:00
|
|
|
pub fn foo() {}
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /foo/tests/spam.rs
|
2018-09-02 08:36:03 -05:00
|
|
|
#[test]
|
|
|
|
fn test_eggs() {}
|
2019-04-13 13:33:49 -05:00
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /bar/Cargo.toml
|
2019-04-13 13:33:49 -05:00
|
|
|
[package]
|
|
|
|
name = "bar"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /bar/src/main.rs
|
2019-04-13 13:33:49 -05:00
|
|
|
fn main() {}
|
|
|
|
"#;
|
|
|
|
|
|
|
|
let server = Project::with_fixture(code).root("foo").root("bar").server();
|
|
|
|
|
2019-03-07 08:46:17 -06:00
|
|
|
server.wait_until_workspace_is_loaded();
|
2018-09-02 08:36:03 -05:00
|
|
|
server.request::<Runnables>(
|
2020-03-12 15:28:26 -05:00
|
|
|
RunnablesParams { text_document: server.doc_id("foo/tests/spam.rs"), position: None },
|
2018-12-06 14:07:31 -06:00
|
|
|
json!([
|
2020-06-02 11:02:58 -05:00
|
|
|
{
|
|
|
|
"args": {
|
|
|
|
"cargoArgs": ["test", "--package", "foo", "--test", "spam"],
|
|
|
|
"executableArgs": ["test_eggs", "--exact", "--nocapture"],
|
|
|
|
"workspaceRoot": server.path().join("foo")
|
2019-04-13 12:45:21 -05:00
|
|
|
},
|
2020-06-02 11:02:58 -05:00
|
|
|
"kind": "cargo",
|
|
|
|
"label": "test test_eggs",
|
|
|
|
"location": {
|
|
|
|
"targetRange": {
|
|
|
|
"end": { "character": 17, "line": 1 },
|
2020-04-26 03:40:13 -05:00
|
|
|
"start": { "character": 0, "line": 0 }
|
|
|
|
},
|
2020-06-02 11:02:58 -05:00
|
|
|
"targetSelectionRange": {
|
|
|
|
"end": { "character": 12, "line": 1 },
|
|
|
|
"start": { "character": 3, "line": 1 }
|
2018-10-25 05:42:53 -05:00
|
|
|
},
|
2020-06-02 11:02:58 -05:00
|
|
|
"targetUri": "file:///[..]/tests/spam.rs"
|
2018-10-25 05:42:53 -05:00
|
|
|
}
|
2020-06-02 11:02:58 -05:00
|
|
|
},
|
|
|
|
{
|
|
|
|
"args": {
|
2020-07-29 07:35:27 -05:00
|
|
|
"cargoArgs": ["check", "--package", "foo", "--all-targets"],
|
2020-06-02 11:02:58 -05:00
|
|
|
"executableArgs": [],
|
|
|
|
"workspaceRoot": server.path().join("foo")
|
|
|
|
},
|
|
|
|
"kind": "cargo",
|
2020-07-29 07:35:27 -05:00
|
|
|
"label": "cargo check -p foo --all-targets"
|
2020-06-02 11:02:58 -05:00
|
|
|
},
|
|
|
|
{
|
|
|
|
"args": {
|
2020-07-29 07:35:27 -05:00
|
|
|
"cargoArgs": ["test", "--package", "foo", "--all-targets"],
|
2020-06-02 11:02:58 -05:00
|
|
|
"executableArgs": [],
|
|
|
|
"workspaceRoot": server.path().join("foo")
|
|
|
|
},
|
|
|
|
"kind": "cargo",
|
2020-07-29 07:35:27 -05:00
|
|
|
"label": "cargo test -p foo --all-targets"
|
2020-06-02 11:02:58 -05:00
|
|
|
}
|
2020-03-12 15:28:26 -05:00
|
|
|
]),
|
2018-09-02 08:36:03 -05:00
|
|
|
);
|
|
|
|
}
|
2018-12-06 14:26:23 -06:00
|
|
|
|
2018-12-29 13:09:42 -06:00
|
|
|
#[test]
|
|
|
|
fn test_format_document() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2018-12-29 13:09:42 -06:00
|
|
|
let server = project(
|
|
|
|
r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2018-12-29 13:09:42 -06:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/lib.rs
|
2018-12-29 13:09:42 -06:00
|
|
|
mod bar;
|
|
|
|
|
|
|
|
fn main() {
|
|
|
|
}
|
|
|
|
|
|
|
|
pub use std::collections::HashMap;
|
|
|
|
"#,
|
|
|
|
);
|
2019-03-07 08:46:17 -06:00
|
|
|
server.wait_until_workspace_is_loaded();
|
2018-12-29 13:09:42 -06:00
|
|
|
|
|
|
|
server.request::<Formatting>(
|
|
|
|
DocumentFormattingParams {
|
|
|
|
text_document: server.doc_id("src/lib.rs"),
|
|
|
|
options: FormattingOptions {
|
|
|
|
tab_size: 4,
|
|
|
|
insert_spaces: false,
|
2019-12-11 11:34:01 -06:00
|
|
|
insert_final_newline: None,
|
|
|
|
trim_final_newlines: None,
|
|
|
|
trim_trailing_whitespace: None,
|
2018-12-29 13:09:42 -06:00
|
|
|
properties: HashMap::new(),
|
|
|
|
},
|
2019-12-11 11:34:01 -06:00
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2018-12-29 13:09:42 -06:00
|
|
|
},
|
|
|
|
json!([
|
|
|
|
{
|
|
|
|
"newText": r#"mod bar;
|
|
|
|
|
|
|
|
fn main() {}
|
|
|
|
|
|
|
|
pub use std::collections::HashMap;
|
|
|
|
"#,
|
|
|
|
"range": {
|
2020-06-23 15:27:24 -05:00
|
|
|
"end": { "character": 0, "line": 6 },
|
|
|
|
"start": { "character": 0, "line": 0 }
|
2018-12-29 13:09:42 -06:00
|
|
|
}
|
|
|
|
}
|
|
|
|
]),
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2019-12-04 16:05:01 -06:00
|
|
|
#[test]
|
|
|
|
fn test_format_document_2018() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2019-12-04 16:05:01 -06:00
|
|
|
let server = project(
|
|
|
|
r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2019-12-04 16:05:01 -06:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
edition = "2018"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/lib.rs
|
2019-12-04 16:05:01 -06:00
|
|
|
mod bar;
|
|
|
|
|
|
|
|
async fn test() {
|
|
|
|
}
|
|
|
|
|
|
|
|
fn main() {
|
|
|
|
}
|
|
|
|
|
|
|
|
pub use std::collections::HashMap;
|
|
|
|
"#,
|
|
|
|
);
|
|
|
|
server.wait_until_workspace_is_loaded();
|
|
|
|
|
|
|
|
server.request::<Formatting>(
|
|
|
|
DocumentFormattingParams {
|
|
|
|
text_document: server.doc_id("src/lib.rs"),
|
|
|
|
options: FormattingOptions {
|
|
|
|
tab_size: 4,
|
|
|
|
insert_spaces: false,
|
|
|
|
properties: HashMap::new(),
|
2019-12-11 11:34:01 -06:00
|
|
|
insert_final_newline: None,
|
|
|
|
trim_final_newlines: None,
|
|
|
|
trim_trailing_whitespace: None,
|
2019-12-04 16:05:01 -06:00
|
|
|
},
|
2019-12-11 11:34:01 -06:00
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2019-12-04 16:05:01 -06:00
|
|
|
},
|
|
|
|
json!([
|
|
|
|
{
|
|
|
|
"newText": r#"mod bar;
|
|
|
|
|
|
|
|
async fn test() {}
|
|
|
|
|
|
|
|
fn main() {}
|
|
|
|
|
|
|
|
pub use std::collections::HashMap;
|
|
|
|
"#,
|
|
|
|
"range": {
|
2020-06-23 15:27:24 -05:00
|
|
|
"end": { "character": 0, "line": 9 },
|
|
|
|
"start": { "character": 0, "line": 0 }
|
2019-12-04 16:05:01 -06:00
|
|
|
}
|
|
|
|
}
|
|
|
|
]),
|
|
|
|
);
|
|
|
|
}
|
2019-12-07 05:46:36 -06:00
|
|
|
|
2018-12-06 14:26:23 -06:00
|
|
|
#[test]
|
|
|
|
fn test_missing_module_code_action() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2018-12-06 14:26:23 -06:00
|
|
|
let server = project(
|
|
|
|
r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2018-12-06 14:26:23 -06:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/lib.rs
|
2018-12-06 14:26:23 -06:00
|
|
|
mod bar;
|
|
|
|
|
|
|
|
fn main() {}
|
|
|
|
"#,
|
|
|
|
);
|
2019-03-07 08:46:17 -06:00
|
|
|
server.wait_until_workspace_is_loaded();
|
2019-02-08 05:49:43 -06:00
|
|
|
let empty_context = || CodeActionContext { diagnostics: Vec::new(), only: None };
|
2019-03-05 15:29:23 -06:00
|
|
|
server.request::<CodeActionRequest>(
|
|
|
|
CodeActionParams {
|
|
|
|
text_document: server.doc_id("src/lib.rs"),
|
|
|
|
range: Range::new(Position::new(0, 4), Position::new(0, 7)),
|
|
|
|
context: empty_context(),
|
2019-12-11 11:34:01 -06:00
|
|
|
partial_result_params: PartialResultParams::default(),
|
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2019-03-05 15:29:23 -06:00
|
|
|
},
|
2020-05-19 13:27:14 -05:00
|
|
|
json!([{
|
|
|
|
"edit": {
|
|
|
|
"documentChanges": [
|
2019-03-05 15:29:23 -06:00
|
|
|
{
|
2020-05-19 13:27:14 -05:00
|
|
|
"kind": "create",
|
|
|
|
"uri": "file:///[..]/src/bar.rs"
|
2019-03-05 15:29:23 -06:00
|
|
|
}
|
2020-05-19 13:27:14 -05:00
|
|
|
]
|
2019-03-05 15:29:23 -06:00
|
|
|
},
|
2020-07-11 18:12:42 -05:00
|
|
|
"isPreferred": false,
|
2020-05-17 20:03:40 -05:00
|
|
|
"kind": "quickfix",
|
2020-05-05 13:55:12 -05:00
|
|
|
"title": "Create module"
|
2020-05-19 13:27:14 -05:00
|
|
|
}]),
|
2019-03-05 15:29:23 -06:00
|
|
|
);
|
|
|
|
|
|
|
|
server.request::<CodeActionRequest>(
|
|
|
|
CodeActionParams {
|
|
|
|
text_document: server.doc_id("src/lib.rs"),
|
|
|
|
range: Range::new(Position::new(2, 4), Position::new(2, 7)),
|
|
|
|
context: empty_context(),
|
2019-12-11 11:34:01 -06:00
|
|
|
partial_result_params: PartialResultParams::default(),
|
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2019-03-05 15:29:23 -06:00
|
|
|
},
|
|
|
|
json!([]),
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn test_missing_module_code_action_in_json_project() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2020-07-23 15:26:25 -05:00
|
|
|
let tmp_dir = TestDir::new();
|
2019-03-07 10:25:35 -06:00
|
|
|
|
|
|
|
let path = tmp_dir.path();
|
|
|
|
|
|
|
|
let project = json!({
|
|
|
|
"roots": [path],
|
2019-10-05 07:55:27 -05:00
|
|
|
"crates": [ {
|
|
|
|
"root_module": path.join("src/lib.rs"),
|
|
|
|
"deps": [],
|
|
|
|
"edition": "2015",
|
2020-07-23 11:57:27 -05:00
|
|
|
"cfg": [ "cfg_atom_1", "feature=\"cfg_1\""],
|
2019-10-05 07:55:27 -05:00
|
|
|
} ]
|
2019-03-07 10:25:35 -06:00
|
|
|
});
|
|
|
|
|
2019-03-05 15:29:23 -06:00
|
|
|
let code = format!(
|
|
|
|
r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /rust-project.json
|
2019-03-07 10:25:35 -06:00
|
|
|
{PROJECT}
|
2019-03-05 15:29:23 -06:00
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/lib.rs
|
2019-03-05 15:29:23 -06:00
|
|
|
mod bar;
|
|
|
|
|
2019-03-07 10:25:35 -06:00
|
|
|
fn main() {{}}
|
2019-03-05 15:29:23 -06:00
|
|
|
"#,
|
2019-03-07 10:25:35 -06:00
|
|
|
PROJECT = project.to_string(),
|
2019-03-05 15:29:23 -06:00
|
|
|
);
|
2019-04-13 13:33:49 -05:00
|
|
|
|
|
|
|
let server = Project::with_fixture(&code).tmp_dir(tmp_dir).server();
|
|
|
|
|
2019-03-07 08:46:17 -06:00
|
|
|
server.wait_until_workspace_is_loaded();
|
2019-03-05 15:29:23 -06:00
|
|
|
let empty_context = || CodeActionContext { diagnostics: Vec::new(), only: None };
|
2018-12-06 14:26:23 -06:00
|
|
|
server.request::<CodeActionRequest>(
|
|
|
|
CodeActionParams {
|
|
|
|
text_document: server.doc_id("src/lib.rs"),
|
2018-12-27 03:54:59 -06:00
|
|
|
range: Range::new(Position::new(0, 4), Position::new(0, 7)),
|
2018-12-06 14:26:23 -06:00
|
|
|
context: empty_context(),
|
2019-12-11 11:34:01 -06:00
|
|
|
partial_result_params: PartialResultParams::default(),
|
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2018-12-06 14:26:23 -06:00
|
|
|
},
|
2020-05-19 13:27:14 -05:00
|
|
|
json!([{
|
|
|
|
"edit": {
|
|
|
|
"documentChanges": [
|
2018-12-06 14:26:23 -06:00
|
|
|
{
|
2020-05-19 13:27:14 -05:00
|
|
|
"kind": "create",
|
|
|
|
"uri": "file://[..]/src/bar.rs"
|
2018-12-06 14:26:23 -06:00
|
|
|
}
|
2020-05-19 13:27:14 -05:00
|
|
|
]
|
2019-02-24 04:53:35 -06:00
|
|
|
},
|
2020-07-11 18:12:42 -05:00
|
|
|
"isPreferred": false,
|
2020-05-17 20:03:40 -05:00
|
|
|
"kind": "quickfix",
|
2020-05-05 13:55:12 -05:00
|
|
|
"title": "Create module"
|
2020-05-19 13:27:14 -05:00
|
|
|
}]),
|
2018-12-06 14:26:23 -06:00
|
|
|
);
|
|
|
|
|
|
|
|
server.request::<CodeActionRequest>(
|
|
|
|
CodeActionParams {
|
|
|
|
text_document: server.doc_id("src/lib.rs"),
|
2018-12-27 03:54:59 -06:00
|
|
|
range: Range::new(Position::new(2, 4), Position::new(2, 7)),
|
2018-12-06 14:26:23 -06:00
|
|
|
context: empty_context(),
|
2019-12-11 11:34:01 -06:00
|
|
|
partial_result_params: PartialResultParams::default(),
|
|
|
|
work_done_progress_params: WorkDoneProgressParams::default(),
|
2018-12-06 14:26:23 -06:00
|
|
|
},
|
|
|
|
json!([]),
|
|
|
|
);
|
|
|
|
}
|
2019-05-27 06:20:11 -05:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn diagnostics_dont_block_typing() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2019-05-27 06:20:11 -05:00
|
|
|
let librs: String = (0..10).map(|i| format!("mod m{};", i)).collect();
|
2020-06-22 10:30:23 -05:00
|
|
|
let libs: String = (0..10).map(|i| format!("//- /src/m{}.rs\nfn foo() {{}}\n\n", i)).collect();
|
2019-08-19 07:41:18 -05:00
|
|
|
let server = Project::with_fixture(&format!(
|
2019-05-27 06:20:11 -05:00
|
|
|
r#"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2019-05-27 06:20:11 -05:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/lib.rs
|
2019-05-27 06:20:11 -05:00
|
|
|
{}
|
|
|
|
|
|
|
|
{}
|
|
|
|
|
|
|
|
fn main() {{}}
|
|
|
|
"#,
|
|
|
|
librs, libs
|
2019-08-19 07:41:18 -05:00
|
|
|
))
|
|
|
|
.with_sysroot(true)
|
|
|
|
.server();
|
|
|
|
|
2019-05-27 06:20:11 -05:00
|
|
|
server.wait_until_workspace_is_loaded();
|
|
|
|
for i in 0..10 {
|
|
|
|
server.notification::<DidOpenTextDocument>(DidOpenTextDocumentParams {
|
|
|
|
text_document: TextDocumentItem {
|
|
|
|
uri: server.doc_id(&format!("src/m{}.rs", i)).uri,
|
|
|
|
language_id: "rust".to_string(),
|
|
|
|
version: 0,
|
|
|
|
text: "/// Docs\nfn foo() {}".to_string(),
|
|
|
|
},
|
|
|
|
});
|
|
|
|
}
|
|
|
|
let start = std::time::Instant::now();
|
|
|
|
server.request::<OnEnter>(
|
|
|
|
TextDocumentPositionParams {
|
|
|
|
text_document: server.doc_id("src/m0.rs"),
|
|
|
|
position: Position { line: 0, character: 5 },
|
|
|
|
},
|
2020-05-25 07:12:53 -05:00
|
|
|
json!([{
|
|
|
|
"insertTextFormat": 2,
|
|
|
|
"newText": "\n/// $0",
|
|
|
|
"range": {
|
|
|
|
"end": { "character": 5, "line": 0 },
|
|
|
|
"start": { "character": 5, "line": 0 }
|
2020-05-21 07:26:44 -05:00
|
|
|
}
|
2020-05-25 07:12:53 -05:00
|
|
|
}]),
|
2019-05-27 06:20:11 -05:00
|
|
|
);
|
2019-05-27 06:41:14 -05:00
|
|
|
let elapsed = start.elapsed();
|
|
|
|
assert!(elapsed.as_millis() < 2000, "typing enter took {:?}", elapsed);
|
2019-05-27 06:20:11 -05:00
|
|
|
}
|
2019-08-20 10:26:07 -05:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn preserves_dos_line_endings() {
|
2019-12-07 05:46:36 -06:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2019-08-20 10:26:07 -05:00
|
|
|
let server = Project::with_fixture(
|
2019-08-20 10:53:59 -05:00
|
|
|
&"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2019-08-20 10:26:07 -05:00
|
|
|
[package]
|
2019-08-20 10:53:59 -05:00
|
|
|
name = \"foo\"
|
|
|
|
version = \"0.0.0\"
|
2019-08-20 10:26:07 -05:00
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/main.rs
|
2019-08-20 10:26:07 -05:00
|
|
|
/// Some Docs\r\nfn main() {}
|
2019-08-20 10:53:59 -05:00
|
|
|
",
|
2019-08-20 10:26:07 -05:00
|
|
|
)
|
|
|
|
.server();
|
2020-07-02 09:47:42 -05:00
|
|
|
server.wait_until_workspace_is_loaded();
|
2019-08-20 10:26:07 -05:00
|
|
|
|
|
|
|
server.request::<OnEnter>(
|
|
|
|
TextDocumentPositionParams {
|
|
|
|
text_document: server.doc_id("src/main.rs"),
|
|
|
|
position: Position { line: 0, character: 8 },
|
|
|
|
},
|
2020-05-25 07:12:53 -05:00
|
|
|
json!([{
|
|
|
|
"insertTextFormat": 2,
|
|
|
|
"newText": "\r\n/// $0",
|
|
|
|
"range": {
|
|
|
|
"end": { "line": 0, "character": 8 },
|
|
|
|
"start": { "line": 0, "character": 8 }
|
2020-05-21 07:26:44 -05:00
|
|
|
}
|
2020-05-25 07:12:53 -05:00
|
|
|
}]),
|
2019-08-20 10:26:07 -05:00
|
|
|
);
|
|
|
|
}
|
2020-03-31 12:16:25 -05:00
|
|
|
|
|
|
|
#[test]
|
2020-05-05 07:53:18 -05:00
|
|
|
fn out_dirs_check() {
|
2020-03-31 12:16:25 -05:00
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
let server = Project::with_fixture(
|
|
|
|
r###"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /Cargo.toml
|
2020-03-31 12:16:25 -05:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /build.rs
|
2020-03-31 12:16:25 -05:00
|
|
|
use std::{env, fs, path::Path};
|
|
|
|
|
|
|
|
fn main() {
|
|
|
|
let out_dir = env::var_os("OUT_DIR").unwrap();
|
|
|
|
let dest_path = Path::new(&out_dir).join("hello.rs");
|
|
|
|
fs::write(
|
|
|
|
&dest_path,
|
|
|
|
r#"pub fn message() -> &'static str { "Hello, World!" }"#,
|
|
|
|
)
|
|
|
|
.unwrap();
|
2020-05-05 07:53:18 -05:00
|
|
|
println!("cargo:rustc-cfg=atom_cfg");
|
|
|
|
println!("cargo:rustc-cfg=featlike=\"set\"");
|
2020-03-31 12:16:25 -05:00
|
|
|
println!("cargo:rerun-if-changed=build.rs");
|
|
|
|
}
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /src/main.rs
|
2020-06-05 08:49:12 -05:00
|
|
|
#[rustc_builtin_macro] macro_rules! include {}
|
2020-06-27 07:31:19 -05:00
|
|
|
#[rustc_builtin_macro] macro_rules! include_str {}
|
2020-06-05 08:49:12 -05:00
|
|
|
#[rustc_builtin_macro] macro_rules! concat {}
|
|
|
|
#[rustc_builtin_macro] macro_rules! env {}
|
|
|
|
|
2020-03-31 12:16:25 -05:00
|
|
|
include!(concat!(env!("OUT_DIR"), "/hello.rs"));
|
|
|
|
|
2020-05-05 07:53:18 -05:00
|
|
|
#[cfg(atom_cfg)]
|
|
|
|
struct A;
|
|
|
|
#[cfg(bad_atom_cfg)]
|
|
|
|
struct A;
|
|
|
|
#[cfg(featlike = "set")]
|
|
|
|
struct B;
|
|
|
|
#[cfg(featlike = "not_set")]
|
|
|
|
struct B;
|
|
|
|
|
|
|
|
fn main() {
|
|
|
|
let va = A;
|
|
|
|
let vb = B;
|
2020-06-05 08:49:12 -05:00
|
|
|
let should_be_str = message();
|
2020-06-27 07:31:19 -05:00
|
|
|
let another_str = include_str!("main.rs");
|
2020-05-05 07:53:18 -05:00
|
|
|
}
|
2020-03-31 12:16:25 -05:00
|
|
|
"###,
|
|
|
|
)
|
|
|
|
.with_config(|config| {
|
2020-04-01 11:41:43 -05:00
|
|
|
config.cargo.load_out_dirs_from_check = true;
|
2020-03-31 12:16:25 -05:00
|
|
|
})
|
|
|
|
.server();
|
|
|
|
server.wait_until_workspace_is_loaded();
|
2020-06-05 08:49:12 -05:00
|
|
|
let res = server.send_request::<HoverRequest>(HoverParams {
|
2020-04-26 15:05:22 -05:00
|
|
|
text_document_position_params: TextDocumentPositionParams::new(
|
|
|
|
server.doc_id("src/main.rs"),
|
2020-06-27 07:31:19 -05:00
|
|
|
Position::new(19, 10),
|
|
|
|
),
|
|
|
|
work_done_progress_params: Default::default(),
|
|
|
|
});
|
|
|
|
assert!(res.to_string().contains("&str"));
|
|
|
|
let res = server.send_request::<HoverRequest>(HoverParams {
|
|
|
|
text_document_position_params: TextDocumentPositionParams::new(
|
|
|
|
server.doc_id("src/main.rs"),
|
|
|
|
Position::new(20, 10),
|
2020-04-26 15:05:22 -05:00
|
|
|
),
|
|
|
|
work_done_progress_params: Default::default(),
|
|
|
|
});
|
2020-06-05 08:49:12 -05:00
|
|
|
assert!(res.to_string().contains("&str"));
|
2020-05-05 07:53:18 -05:00
|
|
|
server.request::<GotoTypeDefinition>(
|
|
|
|
GotoDefinitionParams {
|
|
|
|
text_document_position_params: TextDocumentPositionParams::new(
|
|
|
|
server.doc_id("src/main.rs"),
|
2020-06-27 07:31:19 -05:00
|
|
|
Position::new(17, 9),
|
2020-05-05 07:53:18 -05:00
|
|
|
),
|
|
|
|
work_done_progress_params: Default::default(),
|
|
|
|
partial_result_params: Default::default(),
|
|
|
|
},
|
|
|
|
json!([{
|
|
|
|
"originSelectionRange": {
|
2020-06-27 07:31:19 -05:00
|
|
|
"end": { "character": 10, "line": 17 },
|
|
|
|
"start": { "character": 8, "line": 17 }
|
2020-05-05 07:53:18 -05:00
|
|
|
},
|
|
|
|
"targetRange": {
|
2020-06-27 07:31:19 -05:00
|
|
|
"end": { "character": 9, "line": 8 },
|
|
|
|
"start": { "character": 0, "line": 7 }
|
2020-05-05 07:53:18 -05:00
|
|
|
},
|
|
|
|
"targetSelectionRange": {
|
2020-06-27 07:31:19 -05:00
|
|
|
"end": { "character": 8, "line": 8 },
|
|
|
|
"start": { "character": 7, "line": 8 }
|
2020-05-05 07:53:18 -05:00
|
|
|
},
|
|
|
|
"targetUri": "file:///[..]src/main.rs"
|
|
|
|
}]),
|
|
|
|
);
|
|
|
|
server.request::<GotoTypeDefinition>(
|
|
|
|
GotoDefinitionParams {
|
|
|
|
text_document_position_params: TextDocumentPositionParams::new(
|
|
|
|
server.doc_id("src/main.rs"),
|
2020-06-27 07:31:19 -05:00
|
|
|
Position::new(18, 9),
|
2020-05-05 07:53:18 -05:00
|
|
|
),
|
|
|
|
work_done_progress_params: Default::default(),
|
|
|
|
partial_result_params: Default::default(),
|
|
|
|
},
|
|
|
|
json!([{
|
|
|
|
"originSelectionRange": {
|
2020-06-27 07:31:19 -05:00
|
|
|
"end": { "character": 10, "line": 18 },
|
|
|
|
"start": { "character": 8, "line": 18 }
|
2020-05-05 07:53:18 -05:00
|
|
|
},
|
|
|
|
"targetRange": {
|
2020-06-27 07:31:19 -05:00
|
|
|
"end": { "character": 9, "line": 12 },
|
|
|
|
"start": { "character": 0, "line":11 }
|
2020-05-05 07:53:18 -05:00
|
|
|
},
|
|
|
|
"targetSelectionRange": {
|
2020-06-27 07:31:19 -05:00
|
|
|
"end": { "character": 8, "line": 12 },
|
|
|
|
"start": { "character": 7, "line": 12 }
|
2020-05-05 07:53:18 -05:00
|
|
|
},
|
|
|
|
"targetUri": "file:///[..]src/main.rs"
|
|
|
|
}]),
|
|
|
|
);
|
2020-03-31 12:16:25 -05:00
|
|
|
}
|
2020-04-12 11:05:45 -05:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn resolve_proc_macro() {
|
|
|
|
if skip_slow_tests() {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
let server = Project::with_fixture(
|
|
|
|
r###"
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /foo/Cargo.toml
|
2020-04-12 11:05:45 -05:00
|
|
|
[package]
|
|
|
|
name = "foo"
|
|
|
|
version = "0.0.0"
|
|
|
|
edition = "2018"
|
|
|
|
[dependencies]
|
|
|
|
bar = {path = "../bar"}
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /foo/src/main.rs
|
2020-04-12 11:05:45 -05:00
|
|
|
use bar::Bar;
|
|
|
|
trait Bar {
|
|
|
|
fn bar();
|
|
|
|
}
|
|
|
|
#[derive(Bar)]
|
|
|
|
struct Foo {}
|
|
|
|
fn main() {
|
|
|
|
Foo::bar();
|
|
|
|
}
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /bar/Cargo.toml
|
2020-04-12 11:05:45 -05:00
|
|
|
[package]
|
|
|
|
name = "bar"
|
|
|
|
version = "0.0.0"
|
|
|
|
edition = "2018"
|
|
|
|
|
|
|
|
[lib]
|
|
|
|
proc-macro = true
|
|
|
|
|
2020-06-22 10:30:23 -05:00
|
|
|
//- /bar/src/lib.rs
|
2020-04-12 11:05:45 -05:00
|
|
|
extern crate proc_macro;
|
|
|
|
use proc_macro::{Delimiter, Group, Ident, Span, TokenStream, TokenTree};
|
|
|
|
macro_rules! t {
|
|
|
|
($n:literal) => {
|
|
|
|
TokenTree::from(Ident::new($n, Span::call_site()))
|
|
|
|
};
|
|
|
|
({}) => {
|
|
|
|
TokenTree::from(Group::new(Delimiter::Brace, TokenStream::new()))
|
|
|
|
};
|
|
|
|
(()) => {
|
|
|
|
TokenTree::from(Group::new(Delimiter::Parenthesis, TokenStream::new()))
|
|
|
|
};
|
|
|
|
}
|
|
|
|
#[proc_macro_derive(Bar)]
|
|
|
|
pub fn foo(_input: TokenStream) -> TokenStream {
|
|
|
|
// We hard code the output here for preventing to use any deps
|
|
|
|
let mut res = TokenStream::new();
|
|
|
|
|
|
|
|
// impl Bar for Foo { fn bar() {} }
|
|
|
|
let mut tokens = vec![t!("impl"), t!("Bar"), t!("for"), t!("Foo")];
|
|
|
|
let mut fn_stream = TokenStream::new();
|
|
|
|
fn_stream.extend(vec![t!("fn"), t!("bar"), t!(()), t!({})]);
|
|
|
|
tokens.push(Group::new(Delimiter::Brace, fn_stream).into());
|
|
|
|
res.extend(tokens);
|
|
|
|
res
|
|
|
|
}
|
|
|
|
|
|
|
|
"###,
|
|
|
|
)
|
|
|
|
.with_config(|config| {
|
2020-04-23 11:50:25 -05:00
|
|
|
let macro_srv_path = PathBuf::from(env!("CARGO_BIN_EXE_rust-analyzer"));
|
2020-04-12 11:05:45 -05:00
|
|
|
|
|
|
|
config.cargo.load_out_dirs_from_check = true;
|
2020-04-23 11:50:25 -05:00
|
|
|
config.proc_macro_srv = Some((macro_srv_path, vec!["proc-macro".into()]));
|
2020-04-12 11:05:45 -05:00
|
|
|
})
|
|
|
|
.root("foo")
|
|
|
|
.root("bar")
|
|
|
|
.server();
|
|
|
|
server.wait_until_workspace_is_loaded();
|
2020-04-26 15:05:22 -05:00
|
|
|
let res = server.send_request::<HoverRequest>(HoverParams {
|
|
|
|
text_document_position_params: TextDocumentPositionParams::new(
|
|
|
|
server.doc_id("foo/src/main.rs"),
|
|
|
|
Position::new(7, 9),
|
|
|
|
),
|
|
|
|
work_done_progress_params: Default::default(),
|
|
|
|
});
|
2020-04-12 11:05:45 -05:00
|
|
|
|
|
|
|
let value = res.get("contents").unwrap().get("value").unwrap().to_string();
|
2020-05-25 22:18:45 -05:00
|
|
|
assert_eq!(value, r#""```rust\nfoo::Bar\n```\n\n```rust\nfn bar()\n```""#)
|
2020-04-12 11:05:45 -05:00
|
|
|
}
|