Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: LSP autocompletion for use statement #5704

Merged
merged 27 commits into from
Aug 9, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
8b97e1d
Autocomplete first segment in use path
asterite Aug 8, 2024
823850a
Autocomplete other segments of a use statement
asterite Aug 8, 2024
47c2cb3
Complete types and values
asterite Aug 8, 2024
189f4fc
Show everything in a module's scope
asterite Aug 8, 2024
d9f1b8c
Actually, only suggest direct children for now
asterite Aug 8, 2024
a2bf2bc
Remove `forall ...` from function type
asterite Aug 8, 2024
dc45168
Add a test
asterite Aug 8, 2024
b8441c7
More tests
asterite Aug 8, 2024
ad55762
Don't suggest crate completions on `crate::`
asterite Aug 8, 2024
16dd3b5
Fix tests
asterite Aug 8, 2024
296467e
Suggest "crate::"
asterite Aug 8, 2024
de6cd1c
Autocomplete in use tree
asterite Aug 8, 2024
d70fbff
Complete after colons in use tree
asterite Aug 8, 2024
522f748
Some fixes
asterite Aug 8, 2024
3c82b82
Produce an error when a path has trailing colons
asterite Aug 9, 2024
879c4ec
Consider submodules
asterite Aug 9, 2024
6899df5
Use current module_id
asterite Aug 9, 2024
7bfa5cd
Take a sad test and make it better
asterite Aug 9, 2024
0d4c7e4
Correctly handle super autocompletions
asterite Aug 9, 2024
ab47733
Use `crate_completion_item` in tests
asterite Aug 9, 2024
b02928d
Remove log function
asterite Aug 9, 2024
9bd0b0c
Merge branch 'master' into ab/lsp-use-completion
asterite Aug 9, 2024
621fa84
Remove unused `value_idents`
asterite Aug 9, 2024
5371634
clippy
asterite Aug 9, 2024
2afa955
clippy
asterite Aug 9, 2024
3b3b610
Clean up some comments
asterite Aug 9, 2024
785e476
Some fixes regarding `crate::` and looking up modules from the root m…
asterite Aug 9, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions compiler/noirc_frontend/src/hir/def_map/module_data.rs
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,10 @@ impl ModuleData {
&self.scope
}

pub fn definitions(&self) -> &ItemScope {
&self.definitions
}

fn declare(
&mut self,
name: Ident,
Expand Down
2 changes: 2 additions & 0 deletions compiler/noirc_frontend/src/parser/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@ pub enum ParserErrorReason {
ExpectedFieldName(Token),
#[error("expected a pattern but found a type - {0}")]
ExpectedPatternButFoundType(Token),
#[error("expected an identifier after ::")]
ExpectedIdentifierAfterColons,
#[error("Expected a ; separating these two statements")]
MissingSeparatingSemi,
#[error("constrain keyword is deprecated")]
Expand Down
30 changes: 28 additions & 2 deletions compiler/noirc_frontend/src/parser/parser/path.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,19 @@ pub fn path_no_turbofish() -> impl NoirParser<Path> {
}

fn path_inner<'a>(segment: impl NoirParser<PathSegment> + 'a) -> impl NoirParser<Path> + 'a {
let segments = segment.separated_by(just(Token::DoubleColon)).at_least(1);
let segments = segment
.separated_by(just(Token::DoubleColon))
.at_least(1)
.then(just(Token::DoubleColon).then_ignore(none_of(Token::LeftBrace).rewind()).or_not())
.validate(|(path_segments, trailing_colons), span, emit_error| {
if trailing_colons.is_some() {
emit_error(ParserError::with_reason(
ParserErrorReason::ExpectedIdentifierAfterColons,
span,
));
}
path_segments
});
let make_path = |kind| move |segments, span| Path { segments, kind, span };

let prefix = |key| keyword(key).ignore_then(just(Token::DoubleColon));
Expand Down Expand Up @@ -69,7 +81,7 @@ mod test {
use super::*;
use crate::parser::{
parse_type,
parser::test_helpers::{parse_all_failing, parse_with},
parser::test_helpers::{parse_all_failing, parse_recover, parse_with},
};

#[test]
Expand Down Expand Up @@ -111,4 +123,18 @@ mod test {
vec!["crate", "crate::std::crate", "foo::bar::crate", "foo::dep"],
);
}

#[test]
fn parse_path_with_trailing_colons() {
let src = "foo::bar::";

let (path, errors) = parse_recover(path_no_turbofish(), src);
let path = path.unwrap();
assert_eq!(path.segments.len(), 2);
assert_eq!(path.segments[0].ident.0.contents, "foo");
assert_eq!(path.segments[1].ident.0.contents, "bar");

assert_eq!(errors.len(), 1);
assert_eq!(errors[0].message, "expected an identifier after ::");
}
}
23 changes: 15 additions & 8 deletions tooling/lsp/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@ use fm::{codespan_files as files, FileManager};
use fxhash::FxHashSet;
use lsp_types::{
request::{
DocumentSymbolRequest, HoverRequest, InlayHintRequest, PrepareRenameRequest, References,
Rename,
Completion, DocumentSymbolRequest, HoverRequest, InlayHintRequest, PrepareRenameRequest,
References, Rename,
},
CodeLens,
};
Expand All @@ -36,7 +36,10 @@ use nargo_toml::{find_file_manifest, resolve_workspace_from_toml, PackageSelecti
use noirc_driver::{file_manager_with_stdlib, prepare_crate, NOIR_ARTIFACT_VERSION_STRING};
use noirc_frontend::{
graph::{CrateId, CrateName},
hir::{def_map::parse_file, Context, FunctionNameMatch, ParsedFiles},
hir::{
def_map::{parse_file, CrateDefMap},
Context, FunctionNameMatch, ParsedFiles,
},
node_interner::NodeInterner,
parser::ParserError,
ParsedModule,
Expand All @@ -48,11 +51,11 @@ use notifications::{
on_did_open_text_document, on_did_save_text_document, on_exit, on_initialized,
};
use requests::{
on_code_lens_request, on_document_symbol_request, on_formatting, on_goto_declaration_request,
on_goto_definition_request, on_goto_type_definition_request, on_hover_request, on_initialize,
on_inlay_hint_request, on_prepare_rename_request, on_profile_run_request,
on_references_request, on_rename_request, on_shutdown, on_test_run_request, on_tests_request,
LspInitializationOptions,
on_code_lens_request, on_completion_request, on_document_symbol_request, on_formatting,
on_goto_declaration_request, on_goto_definition_request, on_goto_type_definition_request,
on_hover_request, on_initialize, on_inlay_hint_request, on_prepare_rename_request,
on_profile_run_request, on_references_request, on_rename_request, on_shutdown,
on_test_run_request, on_tests_request, LspInitializationOptions,
};
use serde_json::Value as JsonValue;
use thiserror::Error;
Expand All @@ -62,6 +65,7 @@ mod notifications;
mod requests;
mod solver;
mod types;
mod utils;

#[cfg(test)]
mod test_utils;
Expand All @@ -86,6 +90,7 @@ pub struct LspState {
cached_lenses: HashMap<String, Vec<CodeLens>>,
cached_definitions: HashMap<String, NodeInterner>,
cached_parsed_files: HashMap<PathBuf, (usize, (ParsedModule, Vec<ParserError>))>,
cached_def_maps: HashMap<String, BTreeMap<CrateId, CrateDefMap>>,
options: LspInitializationOptions,
}

Expand All @@ -103,6 +108,7 @@ impl LspState {
cached_definitions: HashMap::new(),
open_documents_count: 0,
cached_parsed_files: HashMap::new(),
cached_def_maps: HashMap::new(),
options: Default::default(),
}
}
Expand Down Expand Up @@ -136,6 +142,7 @@ impl NargoLspService {
.request::<Rename, _>(on_rename_request)
.request::<HoverRequest, _>(on_hover_request)
.request::<InlayHintRequest, _>(on_inlay_hint_request)
.request::<Completion, _>(on_completion_request)
.notification::<notification::Initialized>(on_initialized)
.notification::<notification::DidChangeConfiguration>(on_did_change_configuration)
.notification::<notification::DidOpenTextDocument>(on_did_open_text_document)
Expand Down
6 changes: 3 additions & 3 deletions tooling/lsp/src/notifications/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ pub(super) fn on_did_change_configuration(
ControlFlow::Continue(())
}

pub(super) fn on_did_open_text_document(
pub(crate) fn on_did_open_text_document(
state: &mut LspState,
params: DidOpenTextDocumentParams,
) -> ControlFlow<Result<(), async_lsp::Error>> {
Expand Down Expand Up @@ -153,8 +153,8 @@ pub(crate) fn process_workspace_for_noir_document(
Some(&file_path),
);
state.cached_lenses.insert(document_uri.to_string(), collected_lenses);

state.cached_definitions.insert(package_root_dir, context.def_interner);
state.cached_definitions.insert(package_root_dir.clone(), context.def_interner);
state.cached_def_maps.insert(package_root_dir.clone(), context.def_maps);

let fm = &context.file_manager;
let files = fm.as_file_map();
Expand Down
Loading
Loading