From f382baa5dc89b7076b5614f46e0ad85c7c0ffa50 Mon Sep 17 00:00:00 2001 From: He1pa <18012015693@163.com> Date: Mon, 11 Sep 2023 12:01:54 +0800 Subject: [PATCH] use a function to encapsulate the display style of function signatures and schema definition --- kclvm/sema/src/builtin/string.rs | 1 - kclvm/sema/src/builtin/system_module.rs | 67 ----------- kclvm/tools/src/LSP/src/hover.rs | 141 ++++++++++++------------ 3 files changed, 73 insertions(+), 136 deletions(-) diff --git a/kclvm/sema/src/builtin/string.rs b/kclvm/sema/src/builtin/string.rs index b551c4799..2e636abeb 100644 --- a/kclvm/sema/src/builtin/string.rs +++ b/kclvm/sema/src/builtin/string.rs @@ -419,7 +419,6 @@ register_string_member! { None, ) strip => Type::function( - Some(Rc::new(Type::STR)), Rc::new(Type::STR), &[ diff --git a/kclvm/sema/src/builtin/system_module.rs b/kclvm/sema/src/builtin/system_module.rs index c95ed30bd..da8f59513 100644 --- a/kclvm/sema/src/builtin/system_module.rs +++ b/kclvm/sema/src/builtin/system_module.rs @@ -129,7 +129,6 @@ register_net_member! { None, ) fqdn => Type::function( - None, Type::str_ref(), &[ @@ -144,7 +143,6 @@ register_net_member! { None, ) parse_IP => Type::function( - None, Type::str_ref(), &[ @@ -159,7 +157,6 @@ register_net_member! { None, ) IP_string => Type::function( - None, Type::str_ref(), &[ @@ -174,7 +171,6 @@ register_net_member! { None, ) to_IP4 => Type::function( - None, Type::str_ref(), &[ @@ -189,7 +185,6 @@ register_net_member! { None, ) to_IP16 => Type::function( - None, Type::str_ref(), &[ @@ -204,7 +199,6 @@ register_net_member! { None, ) is_IPv4 => Type::function( - None, Type::bool_ref(), &[ @@ -219,7 +213,6 @@ register_net_member! { None, ) is_IP =>Type::function( - None, Type::bool_ref(), &[ @@ -234,7 +227,6 @@ register_net_member! { None, ) is_loopback_IP =>Type::function( - None, Type::bool_ref(), &[ @@ -249,7 +241,6 @@ register_net_member! { None, ) is_multicast_IP =>Type::function( - None, Type::bool_ref(), &[ @@ -264,7 +255,6 @@ register_net_member! { None, ) is_interface_local_multicast_IP => Type::function( - None, Type::bool_ref(), &[ @@ -279,7 +269,6 @@ register_net_member! { None, ) is_link_local_multicast_IP =>Type::function( - None, Type::bool_ref(), &[ @@ -294,7 +283,6 @@ register_net_member! { None, ) is_link_local_unicast_IP =>Type::function( - None, Type::bool_ref(), &[ @@ -309,7 +297,6 @@ register_net_member! { None, ) is_global_unicast_IP =>Type::function( - None, Type::bool_ref(), &[ @@ -324,7 +311,6 @@ register_net_member! { None, ) is_unspecified_IP => Type::function( - None, Type::bool_ref(), &[ @@ -357,7 +343,6 @@ macro_rules! register_manifests_member { } register_manifests_member! { yaml_stream => Type::function( - None, Type::any_ref(), &[ @@ -419,7 +404,6 @@ macro_rules! register_math_member { } register_math_member! { ceil => Type::function( - None, Type::int_ref(), &[ @@ -434,7 +418,6 @@ register_math_member! { None, ) factorial => Type::function( - None, Type::int_ref(), &[ @@ -449,7 +432,6 @@ register_math_member! { None, ) floor => Type::function( - None, Type::int_ref(), &[ @@ -464,7 +446,6 @@ register_math_member! { None, ) gcd => Type::function( - None, Type::int_ref(), &[ @@ -484,7 +465,6 @@ register_math_member! { None, ) isfinite => Type::function( - None, Type::bool_ref(), &[ @@ -499,7 +479,6 @@ register_math_member! { None, ) isinf => Type::function( - None, Type::bool_ref(), &[ @@ -514,7 +493,6 @@ register_math_member! { None, ) isnan => Type::function( - None, Type::bool_ref(), &[ @@ -529,7 +507,6 @@ register_math_member! { None, ) modf => Type::function( - None, Type::list_ref(Type::float_ref()), &[ @@ -544,7 +521,6 @@ register_math_member! { None, ) exp => Type::function( - None, Type::float_ref(), &[ @@ -559,7 +535,6 @@ register_math_member! { None, ) expm1 => Type::function( - None, Type::float_ref(), &[ @@ -574,7 +549,6 @@ register_math_member! { None, ) log => Type::function( - None, Type::float_ref(), &[ @@ -594,7 +568,6 @@ register_math_member! { None, ) log1p => Type::function( - None, Type::float_ref(), &[ @@ -609,7 +582,6 @@ register_math_member! { None, ) log2 => Type::function( - None, Type::float_ref(), &[ @@ -624,7 +596,6 @@ register_math_member! { None, ) log10 => Type::function( - None, Type::float_ref(), &[ @@ -639,7 +610,6 @@ register_math_member! { None, ) pow => Type::function( - None, Type::float_ref(), &[ @@ -659,7 +629,6 @@ register_math_member! { None, ) sqrt => Type::function( - None, Type::float_ref(), &[ @@ -692,7 +661,6 @@ macro_rules! register_datetime_member { } register_datetime_member! { ticks => Type::function( - None, Type::float_ref(), &[], @@ -701,7 +669,6 @@ register_datetime_member! { None, ) date => Type::function( - None, Type::str_ref(), &[], @@ -710,7 +677,6 @@ register_datetime_member! { None, ) now => Type::function( - None, Type::str_ref(), &[], @@ -719,7 +685,6 @@ register_datetime_member! { None, ) today => Type::function( - None, Type::str_ref(), &[], @@ -747,7 +712,6 @@ macro_rules! register_regex_member { } register_regex_member! { replace => Type::function( - None, Type::str_ref(), &[ @@ -777,7 +741,6 @@ register_regex_member! { None, ) match => Type::function( - None, Type::bool_ref(), &[ @@ -797,7 +760,6 @@ register_regex_member! { None, ) compile => Type::function( - None, Type::bool_ref(), &[ @@ -812,7 +774,6 @@ register_regex_member! { None, ) findall => Type::function( - None, Type::list_ref(Type::str_ref()), &[ @@ -832,7 +793,6 @@ register_regex_member! { None, ) search => Type::function( - None, Type::bool_ref(), &[ @@ -852,7 +812,6 @@ register_regex_member! { None, ) split => Type::function( - None, Type::list_ref(Type::str_ref()), &[ @@ -895,7 +854,6 @@ macro_rules! register_yaml_member { } register_yaml_member! { encode => Type::function( - None, Type::str_ref(), &[ @@ -925,7 +883,6 @@ register_yaml_member! { Some(1), ) decode => Type::function( - None, Type::any_ref(), &[ @@ -940,7 +897,6 @@ register_yaml_member! { None, ) dump_to_file => Type::function( - None, Type::str_ref(), &[ @@ -993,7 +949,6 @@ macro_rules! register_json_member { } register_json_member! { encode => Type::function( - None, Type::str_ref(), &[ @@ -1028,7 +983,6 @@ register_json_member! { Some(1), ) decode => Type::function( - None, Type::any_ref(), &[ @@ -1043,7 +997,6 @@ register_json_member! { None, ) dump_to_file => Type::function( - None, Type::str_ref(), &[ @@ -1101,7 +1054,6 @@ macro_rules! register_crypto_member { } register_crypto_member! { md5 => Type::function( - None, Type::str_ref(), &[ @@ -1121,7 +1073,6 @@ register_crypto_member! { None, ) sha1 => Type::function( - None, Type::str_ref(), &[ @@ -1141,7 +1092,6 @@ register_crypto_member! { None, ) sha224 => Type::function( - None, Type::str_ref(), &[ @@ -1161,7 +1111,6 @@ register_crypto_member! { None, ) sha256 => Type::function( - None, Type::str_ref(), &[ @@ -1181,7 +1130,6 @@ register_crypto_member! { None, ) sha384 => Type::function( - None, Type::str_ref(), &[ @@ -1201,7 +1149,6 @@ register_crypto_member! { None, ) sha512 => Type::function( - None, Type::str_ref(), &[ @@ -1274,7 +1221,6 @@ register_units_member! { Ti => Type::INT Pi => Type::INT to_n => Type::function( - None, Type::str_ref(), &[ @@ -1289,7 +1235,6 @@ register_units_member! { None, ) to_u => Type::function( - None, Type::str_ref(), &[ @@ -1304,7 +1249,6 @@ register_units_member! { None, ) to_m => Type::function( - None, Type::str_ref(), &[ @@ -1319,7 +1263,6 @@ register_units_member! { None, ) to_K => Type::function( - None, Type::str_ref(), &[ @@ -1334,7 +1277,6 @@ register_units_member! { None, ) to_M => Type::function( - None, Type::str_ref(), &[ @@ -1349,7 +1291,6 @@ register_units_member! { None, ) to_G => Type::function( - None, Type::str_ref(), &[ @@ -1364,7 +1305,6 @@ register_units_member! { None, ) to_T => Type::function( - None, Type::str_ref(), &[ @@ -1379,7 +1319,6 @@ register_units_member! { None, ) to_P => Type::function( - None, Type::str_ref(), &[ @@ -1394,7 +1333,6 @@ register_units_member! { None, ) to_Ki => Type::function( - None, Type::str_ref(), &[ @@ -1409,7 +1347,6 @@ register_units_member! { None, ) to_Mi => Type::function( - None, Type::str_ref(), &[ @@ -1424,7 +1361,6 @@ register_units_member! { None, ) to_Gi => Type::function( - None, Type::str_ref(), &[ @@ -1439,7 +1375,6 @@ register_units_member! { None, ) to_Ti => Type::function( - None, Type::str_ref(), &[ @@ -1454,7 +1389,6 @@ register_units_member! { None, ) to_Pi => Type::function( - None, Type::str_ref(), &[ @@ -1487,7 +1421,6 @@ macro_rules! register_collection_member { } register_collection_member! { union_all => Type::function( - None, Type::any_ref(), &[ diff --git a/kclvm/tools/src/LSP/src/hover.rs b/kclvm/tools/src/LSP/src/hover.rs index ac1832c6c..ac8554d5b 100644 --- a/kclvm/tools/src/LSP/src/hover.rs +++ b/kclvm/tools/src/LSP/src/hover.rs @@ -1,9 +1,8 @@ -use indexmap::IndexSet; use kclvm_ast::ast::Program; use kclvm_error::Position as KCLPos; use kclvm_sema::{ resolver::scope::{ProgramScope, ScopeObjectKind}, - ty::FunctionType, + ty::{FunctionType, SchemaType}, }; use lsp_types::{Hover, HoverContents, MarkedString}; @@ -18,70 +17,18 @@ pub(crate) fn hover( ) -> Option { match program.pos_to_stmt(kcl_pos) { Some(node) => { - let mut docs: IndexSet = IndexSet::new(); + let mut docs: Vec = vec![]; if let Some(def) = find_def(node, kcl_pos, prog_scope) { if let crate::goto_def::Definition::Object(obj) = def { match obj.kind { ScopeObjectKind::Definition => { - // Schema Definition hover - // ``` - // pkg - // schema Foo(Base) - // ----------------- - // doc - // ----------------- - // Attributes: - // attr1: type - // attr2? type - // ``` - let schema_ty = obj.ty.into_schema_type(); - let base: String = if let Some(base) = schema_ty.base { - format!("({})", base.name) - } else { - "".to_string() - }; - docs.insert(format!( - "{}\n\nschema {}{}", - schema_ty.pkgpath, schema_ty.name, base - )); - if !schema_ty.doc.is_empty() { - docs.insert(schema_ty.doc.clone()); - } - let mut attrs = vec!["Attributes:".to_string()]; - for (name, attr) in schema_ty.attrs { - attrs.push(format!( - "{}{}:{}", - name, - if attr.is_optional { "?" } else { "" }, - format!(" {}", attr.ty.ty_str()), - )); - } - docs.insert(attrs.join("\n\n")); + docs.extend(build_schema_hover_content(&obj.ty.into_schema_type())) } ScopeObjectKind::FunctionCall => { let ty = obj.ty.clone(); match &ty.kind { kclvm_sema::ty::TypeKind::Function(func_ty) => { - // system package function - // ``` - // pkg - // function func_name(arg1: type, arg2: type, ..) -> type - // ----------------- - // doc - // ``` - // if let Some(pkg) = &func_ty.pkg{ - // docs.insert(pkg.clone()); - // } - if let Some(ty) = &func_ty.self_ty { - let self_ty = format!("{}\n\n", ty.ty_str()); - docs.insert(self_ty); - } - let func_sig = build_func_sig_str(func_ty, obj.name); - docs.insert(func_sig); - - if !func_ty.doc.is_empty() { - docs.insert(func_ty.doc.clone()); - } + docs.extend(build_func_hover_content(func_ty, obj.name)) } _ => {} } @@ -91,9 +38,9 @@ pub(crate) fn hover( // ``` // name: type //``` - docs.insert(format!("{}: {}", obj.name, obj.ty.ty_str())); + docs.push(format!("{}: {}", obj.name, obj.ty.ty_str())); if let Some(doc) = obj.doc { - docs.insert(doc); + docs.push(doc); } } } @@ -107,7 +54,7 @@ pub(crate) fn hover( // Convert docs to Hover. This function will convert to // None, Scalar or Array according to the number of positions -fn docs_to_hover(docs: IndexSet) -> Option { +fn docs_to_hover(docs: Vec) -> Option { match docs.len() { 0 => None, 1 => Some(Hover { @@ -125,22 +72,80 @@ fn docs_to_hover(docs: IndexSet) -> Option { } } -fn build_func_sig_str(func_ty: &FunctionType, name: String) -> String { - let mut result = format!("fn {}(", name); +// Build hover content for schema definition +// Schema Definition hover +// ``` +// pkg +// schema Foo(Base) +// ----------------- +// doc +// ----------------- +// Attributes: +// attr1: type +// attr2? type +// ``` +fn build_schema_hover_content(schema_ty: &SchemaType) -> Vec { + let mut docs = vec![]; + let base: String = if let Some(base) = &schema_ty.base { + format!("({})", base.name) + } else { + "".to_string() + }; + docs.push(format!( + "{}\n\nschema {}{}", + schema_ty.pkgpath, schema_ty.name, base + )); + if !schema_ty.doc.is_empty() { + docs.push(schema_ty.doc.clone()); + } + let mut attrs = vec!["Attributes:".to_string()]; + for (name, attr) in &schema_ty.attrs { + attrs.push(format!( + "{}{}:{}", + name, + if attr.is_optional { "?" } else { "" }, + format!(" {}", attr.ty.ty_str()), + )); + } + docs.push(attrs.join("\n\n")); + docs +} + +// Build hover content for function call +// ``` +// pkg +// ----------------- +// function func_name(arg1: type, arg2: type, ..) -> type +// ----------------- +// doc +// ``` +fn build_func_hover_content(func_ty: &FunctionType, name: String) -> Vec { + let mut docs = vec![]; + if let Some(ty) = &func_ty.self_ty { + let self_ty = format!("{}\n\n", ty.ty_str()); + docs.push(self_ty); + } + + let mut sig = format!("fn {}(", name); if func_ty.params.is_empty() { - result.push_str(")"); + sig.push_str(")"); } else { for (i, p) in func_ty.params.iter().enumerate() { - result.push_str(&format!("{}: {}", p.name, p.ty.ty_str())); + sig.push_str(&format!("{}: {}", p.name, p.ty.ty_str())); if i != func_ty.params.len() - 1 { - result.push_str(", "); + sig.push_str(", "); } } - result.push_str(")"); + sig.push_str(")"); + } + sig.push_str(&format!(" -> {}", func_ty.return_ty.ty_str())); + docs.push(sig); + + if !func_ty.doc.is_empty() { + docs.push(func_ty.doc.clone()); } - result.push_str(&format!(" -> {}", func_ty.return_ty.ty_str())); - result + docs } #[cfg(test)]