mirror of
https://github.com/lune-org/lune.git
synced 2024-12-12 13:00:37 +00:00
Try to automatically add typedefs to vscode settings or print them out
This commit is contained in:
parent
85bbcaabaa
commit
f7d82f08b0
4 changed files with 87 additions and 15 deletions
2
.vscode/settings.json
vendored
2
.vscode/settings.json
vendored
|
@ -2,8 +2,6 @@
|
|||
// Luau - disable Roblox features, enable Lune typedefs & requires
|
||||
"luau-lsp.sourcemap.enabled": false,
|
||||
"luau-lsp.types.roblox": false,
|
||||
"luau-lsp.types.definitionFiles": ["luneTypes.d.luau"],
|
||||
"luau-lsp.types.documentationFiles": ["luneDocs.json"],
|
||||
"luau-lsp.require.mode": "relativeToFile",
|
||||
// Luau - ignore type defs file in docs dir and dev scripts we use
|
||||
"luau-lsp.ignoreGlobs": [
|
||||
|
|
|
@ -1,12 +1,18 @@
|
|||
use std::process::ExitCode;
|
||||
use std::{
|
||||
borrow::BorrowMut,
|
||||
collections::HashMap,
|
||||
path::{Path, PathBuf},
|
||||
process::ExitCode,
|
||||
};
|
||||
|
||||
use anyhow::{Context, Result};
|
||||
use clap::{CommandFactory, Parser};
|
||||
use serde_json::Value as JsonValue;
|
||||
|
||||
use include_dir::{include_dir, Dir};
|
||||
use lune::Lune;
|
||||
use tokio::{
|
||||
fs::read as read_to_vec,
|
||||
fs::{self, read as read_to_vec},
|
||||
io::{stdin, AsyncReadExt},
|
||||
};
|
||||
|
||||
|
@ -81,6 +87,7 @@ impl Cli {
|
|||
self
|
||||
}
|
||||
|
||||
#[allow(clippy::too_many_lines)]
|
||||
pub async fn run(self) -> Result<ExitCode> {
|
||||
// List files in `lune` and `.lune` directories, if wanted
|
||||
// This will also exit early and not run anything else
|
||||
|
@ -124,7 +131,43 @@ impl Cli {
|
|||
return Ok(ExitCode::FAILURE);
|
||||
}
|
||||
if self.setup {
|
||||
generate_typedef_files_from_definitions(&TYPEDEFS_DIR).await?;
|
||||
let generated_paths =
|
||||
generate_typedef_files_from_definitions(&TYPEDEFS_DIR).await?;
|
||||
let settings_json_path = PathBuf::from(".vscode/settings.json");
|
||||
let message = match fs::metadata(&settings_json_path).await {
|
||||
Ok(meta) if meta.is_file() => {
|
||||
if try_add_generated_typedefs_vscode(&settings_json_path, &generated_paths).await.is_err() {
|
||||
"These files can be added to your LSP settings for autocomplete and documentation."
|
||||
} else {
|
||||
"These files have now been added to your workspace LSP settings for Visual Studio Code."
|
||||
}
|
||||
}
|
||||
_ => "These files can be added to your LSP settings for autocomplete and documentation.",
|
||||
};
|
||||
// HACK: We should probably just be serializing this hashmap to print it out, but
|
||||
// that does not guarantee sorting and the sorted version is much easier to read
|
||||
let mut sorted_names = generated_paths
|
||||
.keys()
|
||||
.map(ToString::to_string)
|
||||
.collect::<Vec<_>>();
|
||||
sorted_names.sort_unstable();
|
||||
println!(
|
||||
"Typedefs have been generated in the following locations:\n{{\n{}\n}}\n{message}",
|
||||
sorted_names
|
||||
.iter()
|
||||
.map(|name| {
|
||||
let path = generated_paths.get(name).unwrap();
|
||||
format!(
|
||||
" \"@lune/{}\": \"{}\",",
|
||||
name,
|
||||
path.canonicalize().unwrap().display()
|
||||
)
|
||||
})
|
||||
.collect::<Vec<_>>()
|
||||
.join("\n")
|
||||
.strip_suffix(',')
|
||||
.unwrap()
|
||||
);
|
||||
}
|
||||
}
|
||||
if self.script_path.is_none() {
|
||||
|
@ -172,3 +215,29 @@ impl Cli {
|
|||
})
|
||||
}
|
||||
}
|
||||
|
||||
async fn try_add_generated_typedefs_vscode(
|
||||
settings_json_path: &Path,
|
||||
generated_paths: &HashMap<String, PathBuf>,
|
||||
) -> Result<()> {
|
||||
// FUTURE: Use a jsonc or json5 to read this file instead since it may contain comments and fail
|
||||
let settings_json_contents = fs::read(settings_json_path).await?;
|
||||
let mut settings_changed: bool = false;
|
||||
let mut settings_json: JsonValue = serde_json::from_slice(&settings_json_contents)?;
|
||||
if let JsonValue::Object(settings) = settings_json.borrow_mut() {
|
||||
if let Some(JsonValue::Object(aliases)) = settings.get_mut("luau-lsp.require.fileAliases") {
|
||||
for (name, path) in generated_paths {
|
||||
settings_changed = true;
|
||||
aliases.insert(
|
||||
format!("@lune/{name}"),
|
||||
JsonValue::String(path.canonicalize().unwrap().to_string_lossy().to_string()),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
if settings_changed {
|
||||
let settings_json_new = serde_json::to_vec_pretty(&settings_json)?;
|
||||
fs::write(settings_json_path, settings_json_new).await?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
use std::collections::HashMap;
|
||||
use std::{collections::HashMap, path::PathBuf};
|
||||
|
||||
use anyhow::Result;
|
||||
use include_dir::Dir;
|
||||
|
@ -15,7 +15,9 @@ pub async fn generate_gitbook_dir_from_definitions(dir: &Dir<'_>) -> Result<()>
|
|||
gitbook_dir::generate_from_type_definitions(definitions).await
|
||||
}
|
||||
|
||||
pub async fn generate_typedef_files_from_definitions(dir: &Dir<'_>) -> Result<()> {
|
||||
pub async fn generate_typedef_files_from_definitions(
|
||||
dir: &Dir<'_>,
|
||||
) -> Result<HashMap<String, PathBuf>> {
|
||||
let definitions = read_typedefs_dir(dir)?;
|
||||
typedef_files::generate_from_type_definitions(definitions).await
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
use std::{collections::HashMap, fmt::Write};
|
||||
use std::{collections::HashMap, fmt::Write, path::PathBuf};
|
||||
|
||||
use anyhow::{Context, Result};
|
||||
use directories::UserDirs;
|
||||
|
@ -13,7 +13,7 @@ const GENERATED_COMMENT_TAG: &str = "--!strict";
|
|||
#[allow(clippy::too_many_lines)]
|
||||
pub async fn generate_from_type_definitions(
|
||||
api_reference: HashMap<String, DefinitionsTree>,
|
||||
) -> Result<()> {
|
||||
) -> Result<HashMap<String, PathBuf>> {
|
||||
let mut dirs_to_write = Vec::new();
|
||||
let mut files_to_write = Vec::new();
|
||||
// Create the typedefs dir in the users cache dir
|
||||
|
@ -21,7 +21,7 @@ pub async fn generate_from_type_definitions(
|
|||
.context("Failed to find user home directory")?
|
||||
.home_dir()
|
||||
.join(".lune")
|
||||
.join("typedefs")
|
||||
.join(".typedefs")
|
||||
.join(env!("CARGO_PKG_VERSION"));
|
||||
dirs_to_write.push(cache_dir.clone());
|
||||
// Make typedef files
|
||||
|
@ -36,8 +36,8 @@ pub async fn generate_from_type_definitions(
|
|||
category_name.to_lowercase(),
|
||||
env!("CARGO_PKG_VERSION")
|
||||
)?;
|
||||
write_tree(&mut contents, category_name, category_tree)?;
|
||||
files_to_write.push((path, contents));
|
||||
write_tree(&mut contents, category_name.to_string(), category_tree)?;
|
||||
files_to_write.push((category_name.to_lowercase(), path, contents));
|
||||
}
|
||||
// Write all dirs and files only when we know generation was successful
|
||||
let futs_dirs = dirs_to_write
|
||||
|
@ -45,12 +45,15 @@ pub async fn generate_from_type_definitions(
|
|||
.map(create_dir_all)
|
||||
.collect::<Vec<_>>();
|
||||
let futs_files = files_to_write
|
||||
.drain(..)
|
||||
.map(|(path, contents)| write(path, contents))
|
||||
.iter()
|
||||
.map(|(_, path, contents)| write(path, contents))
|
||||
.collect::<Vec<_>>();
|
||||
try_join_all(futs_dirs).await?;
|
||||
try_join_all(futs_files).await?;
|
||||
Ok(())
|
||||
Ok(files_to_write
|
||||
.drain(..)
|
||||
.map(|(name, path, _)| (name, path))
|
||||
.collect::<HashMap<_, _>>())
|
||||
}
|
||||
|
||||
fn make_return_table_item(item: &DefinitionsItem) -> Result<String> {
|
||||
|
|
Loading…
Reference in a new issue