Skip to content

Commit

Permalink
Add get_environment and render_as_load to the LspContext
Browse files Browse the repository at this point in the history
Summary: Required in future diffs to do auto-insertion of loads and to do completion of globals.

Reviewed By: lmvasquezg

Differential Revision: D47208502

fbshipit-source-id: 68c8cdcccf1515c32738e4412d03d18c2d27df55
  • Loading branch information
ndmitchell authored and facebook-github-bot committed Jul 4, 2023
1 parent 2b4ac54 commit d21c3ad
Show file tree
Hide file tree
Showing 3 changed files with 97 additions and 1 deletion.
14 changes: 14 additions & 0 deletions starlark/bin/eval.rs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ use starlark::docs::get_registered_starlark_docs;
use starlark::docs::render_docs_as_code;
use starlark::docs::Doc;
use starlark::docs::DocItem;
use starlark::docs::DocModule;
use starlark::environment::FrozenModule;
use starlark::environment::Globals;
use starlark::environment::Module;
Expand Down Expand Up @@ -352,6 +353,19 @@ impl LspContext for Context {
) -> anyhow::Result<Option<LspUrl>> {
Ok(self.builtin_symbols.get(symbol).cloned())
}

fn render_as_load(
&self,
_target: &LspUrl,
_current_file: &LspUrl,
_workspace_root: Option<&Path>,
) -> anyhow::Result<String> {
Err(anyhow::anyhow!("Not yet implemented, render_as_load"))
}

fn get_environment(&self, _uri: &LspUrl) -> DocModule {
DocModule::default()
}
}

pub(crate) fn globals() -> Globals {
Expand Down
18 changes: 17 additions & 1 deletion starlark/src/lsp/server.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ use serde::Serializer;

use crate::codemap::ResolvedSpan;
use crate::codemap::Span;
use crate::docs::DocModule;
use crate::lsp::definition::Definition;
use crate::lsp::definition::DottedDefinition;
use crate::lsp::definition::IdentifierDefinition;
Expand Down Expand Up @@ -272,7 +273,19 @@ pub trait LspContext {
workspace_root: Option<&Path>,
) -> anyhow::Result<LspUrl>;

/// Resolve a string literal into a Url and a function that specifies a locaction within that
/// Render the target URL to use as a path in a `load()` statement. If `target` is
/// in the same package as `current_file`, the result is a relative path.
///
/// `target` is the file that should be loaded by `load()`.
/// `current_file` is the file that the `load()` statement will be inserted into.
fn render_as_load(
&self,
target: &LspUrl,
current_file: &LspUrl,
workspace_root: Option<&Path>,
) -> anyhow::Result<String>;

/// Resolve a string literal into a Url and a function that specifies a location within that
/// target file.
///
/// This can be used for things like file paths in string literals, build targets, etc.
Expand All @@ -296,6 +309,9 @@ pub trait LspContext {
Ok(result)
}

/// Get the preloaded environment for a particular file.
fn get_environment(&self, uri: &LspUrl) -> DocModule;

/// Get the LSPUrl for a global symbol if possible.
///
/// The current file is provided in case different files have different global symbols
Expand Down
66 changes: 66 additions & 0 deletions starlark/src/lsp/test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,8 @@ use crate::docs::render_docs_as_code;
use crate::docs::Doc;
use crate::docs::DocFunction;
use crate::docs::DocItem;
use crate::docs::DocMember;
use crate::docs::DocModule;
use crate::docs::Identifier;
use crate::docs::Location;
use crate::errors::EvalMessage;
Expand Down Expand Up @@ -95,6 +97,14 @@ enum ResolveLoadError {
WrongScheme(String, LspUrl),
}

#[derive(thiserror::Error, Debug)]
enum RenderLoadError {
#[error("Path `{}` provided, which does not seem to contain a filename", .0.display())]
MissingTargetFilename(PathBuf),
#[error("Urls `{}` and `{}` was expected to be of type `{}`", .1, .2, .0)]
WrongScheme(String, LspUrl, LspUrl),
}

#[derive(thiserror::Error, Debug)]
pub(crate) enum TestServerError {
#[error("Attempted to set the contents of a file with a non-absolute path `{}`", .0.display())]
Expand Down Expand Up @@ -170,6 +180,51 @@ impl LspContext for TestServerContext {
}
}

fn render_as_load(
&self,
target: &LspUrl,
current_file: &LspUrl,
workspace_root: Option<&Path>,
) -> anyhow::Result<String> {
match (target, current_file) {
(LspUrl::File(target_path), LspUrl::File(current_file_path)) => {
let target_package = target_path.parent();
let current_file_package = current_file_path.parent();
let target_filename = target_path.file_name();

// If both are in the same package, return a relative path.
if matches!((target_package, current_file_package), (Some(a), Some(b)) if a == b) {
return match target_filename {
Some(filename) => Ok(format!(":{}", filename.to_string_lossy())),
None => {
Err(RenderLoadError::MissingTargetFilename(target_path.clone()).into())
}
};
}

let target_path = workspace_root
.and_then(|root| target_path.strip_prefix(root).ok())
.unwrap_or(target_path);

Ok(format!(
"//{}:{}",
target_package
.map(|path| path.to_string_lossy())
.unwrap_or_default(),
target_filename
.unwrap_or(target_path.as_os_str())
.to_string_lossy()
))
}
_ => Err(RenderLoadError::WrongScheme(
"file://".to_owned(),
target.clone(),
current_file.clone(),
)
.into()),
}
}

fn resolve_string_literal(
&self,
literal: &str,
Expand Down Expand Up @@ -228,6 +283,17 @@ impl LspContext for TestServerContext {
) -> anyhow::Result<Option<LspUrl>> {
Ok(self.builtin_symbols.get(symbol).cloned())
}

fn get_environment(&self, _uri: &LspUrl) -> DocModule {
DocModule {
docs: None,
members: self
.builtin_symbols
.keys()
.map(|name| (name.clone(), DocMember::Function(DocFunction::default())))
.collect(),
}
}
}

/// A server for use in testing that provides helpers for sending requests, correlating
Expand Down

0 comments on commit d21c3ad

Please sign in to comment.