From 5e17df077ba7fa4d84aa851ddd83c97b96668fbe Mon Sep 17 00:00:00 2001 From: Hong Jiarong Date: Wed, 17 Dec 2025 19:47:24 +0800 Subject: [PATCH] rename dead code to unused --- crates/tinymist-cli/src/cmd/query.rs | 2 +- crates/tinymist-lint/src/lib.rs | 20 +++---- .../src/{dead_code => unused}/collector.rs | 10 ++-- .../src/{dead_code => unused}/diagnostic.rs | 15 +++-- .../src/{dead_code.rs => unused/mod.rs} | 60 +++++++++---------- crates/tinymist-query/src/analysis.rs | 8 +-- crates/tinymist-query/src/analysis/global.rs | 19 +++--- crates/tinymist/src/config.rs | 31 +++++----- crates/tinymist/src/project.rs | 2 +- editors/vscode/package.json | 18 +++--- locales/tinymist-vscode.toml | 12 ++-- 11 files changed, 96 insertions(+), 101 deletions(-) rename crates/tinymist-lint/src/{dead_code => unused}/collector.rs (97%) rename crates/tinymist-lint/src/{dead_code => unused}/diagnostic.rs (90%) rename crates/tinymist-lint/src/{dead_code.rs => unused/mod.rs} (88%) diff --git a/crates/tinymist-cli/src/cmd/query.rs b/crates/tinymist-cli/src/cmd/query.rs index 25445b77a..131981ab5 100644 --- a/crates/tinymist-cli/src/cmd/query.rs +++ b/crates/tinymist-cli/src/cmd/query.rs @@ -80,7 +80,7 @@ pub fn query_main(mut cmds: QueryCommands) -> Result<()> { _ => tinymist_query::ColorTheme::Light, }, lint: config.lint.when().clone(), - dead_code: config.lint.dead_code_config(), + unused: config.lint.unused_config(), periscope: None, local_packages: Arc::default(), tokens_caches: Arc::default(), diff --git a/crates/tinymist-lint/src/lib.rs b/crates/tinymist-lint/src/lib.rs index fc1812153..eaf0f15d5 100644 --- a/crates/tinymist-lint/src/lib.rs +++ b/crates/tinymist-lint/src/lib.rs @@ -1,8 +1,8 @@ //! A linter for Typst. -mod dead_code; +mod unused; -pub use dead_code::DeadCodeConfig; +pub use unused::UnusedConfig; /// Hint added to diagnostics for documented exported functions, to mark them as /// likely public API. @@ -49,30 +49,30 @@ pub fn lint_file( known_issues: KnownIssues, ) -> LintInfo { let cross_file_refs: FxHashSet> = FxHashSet::default(); - let dead_code_config = DeadCodeConfig::default(); - lint_file_with_dead_code_config( + let unused_config = UnusedConfig::default(); + lint_file_with_unused_config( world, ei, ti, known_issues, &cross_file_refs, - &dead_code_config, + &unused_config, ) } -/// Performs linting check on file with a custom dead-code configuration. -pub fn lint_file_with_dead_code_config( +/// Performs linting check on file with a custom unused configuration. +pub fn lint_file_with_unused_config( world: &LspWorld, ei: &ExprInfo, ti: Arc, known_issues: KnownIssues, cross_file_refs: &FxHashSet>, - dead_code_config: &DeadCodeConfig, + unused_config: &UnusedConfig, ) -> LintInfo { let mut diagnostics = Linter::new(world, ei.clone(), ti, known_issues).lint(ei.source.root()); - let dead_code_diags = dead_code::check_dead_code(world, ei, cross_file_refs, dead_code_config); - diagnostics.extend(dead_code_diags); + let unused_diags = unused::check_unused(world, ei, cross_file_refs, unused_config); + diagnostics.extend(unused_diags); LintInfo { revision: ei.revision, diff --git a/crates/tinymist-lint/src/dead_code/collector.rs b/crates/tinymist-lint/src/unused/collector.rs similarity index 97% rename from crates/tinymist-lint/src/dead_code/collector.rs rename to crates/tinymist-lint/src/unused/collector.rs index 170491057..d6113eeaf 100644 --- a/crates/tinymist-lint/src/dead_code/collector.rs +++ b/crates/tinymist-lint/src/unused/collector.rs @@ -1,4 +1,4 @@ -//! Definition collector for dead code analysis. +//! Definition collector for unused declaration analysis. use rustc_hash::FxHashSet; use tinymist_analysis::{ @@ -64,10 +64,10 @@ struct DefinitionCollector<'a> { impl<'a> DefinitionCollector<'a> { fn collect_exports(&mut self) { for (_name, expr) in self.ei.exports.iter() { - if let Some(decl) = Self::extract_decl(expr) { - if decl.is_def() { - self.add_definition(decl, DefScope::Exported); - } + if let Some(decl) = Self::extract_decl(expr) + && decl.is_def() + { + self.add_definition(decl, DefScope::Exported); } } } diff --git a/crates/tinymist-lint/src/dead_code/diagnostic.rs b/crates/tinymist-lint/src/unused/diagnostic.rs similarity index 90% rename from crates/tinymist-lint/src/dead_code/diagnostic.rs rename to crates/tinymist-lint/src/unused/diagnostic.rs index 2f849e94b..398333c31 100644 --- a/crates/tinymist-lint/src/dead_code/diagnostic.rs +++ b/crates/tinymist-lint/src/unused/diagnostic.rs @@ -1,4 +1,4 @@ -//! Diagnostic generator for dead code warnings. +//! Diagnostic generator for unused declaration warnings. //! //! This module creates user-friendly diagnostic messages for unused //! definitions, with appropriate hints and severity levels. @@ -81,15 +81,14 @@ pub fn generate_diagnostic( } // Add kind-specific hints - if let DefKind::Function = def_info.kind { - if matches!(def_info.scope, DefScope::Exported) - && ei.docstrings.contains_key(&def_info.decl) - { - diag = diag.with_hint(DOCUMENTED_EXPORTED_FUNCTION_HINT); - diag = diag.with_hint( + if let DefKind::Function = def_info.kind + && matches!(def_info.scope, DefScope::Exported) + && ei.docstrings.contains_key(&def_info.decl) + { + diag = diag.with_hint(DOCUMENTED_EXPORTED_FUNCTION_HINT); + diag = diag.with_hint( "if this is intended public API, you can ignore this diagnostic; otherwise consider removing it", ); - } } if is_module_like { diff --git a/crates/tinymist-lint/src/dead_code.rs b/crates/tinymist-lint/src/unused/mod.rs similarity index 88% rename from crates/tinymist-lint/src/dead_code.rs rename to crates/tinymist-lint/src/unused/mod.rs index 732e8bc5e..4a28c1fde 100644 --- a/crates/tinymist-lint/src/dead_code.rs +++ b/crates/tinymist-lint/src/unused/mod.rs @@ -1,4 +1,4 @@ -//! Dead code detection for Typst. +//! Unused declaration detection for Typst. mod collector; mod diagnostic; @@ -26,9 +26,9 @@ struct ImportUsageInfo { module_used_decls: FxHashSet>, } -/// Configuration for dead code detection. +/// Configuration for unused declaration detection. #[derive(Debug, Clone, Hash)] -pub struct DeadCodeConfig { +pub struct UnusedConfig { /// Whether to check exported but unused symbols. pub check_exported: bool, /// Whether to check unused function parameters. @@ -37,7 +37,7 @@ pub struct DeadCodeConfig { pub exceptions: Vec, } -impl Default for DeadCodeConfig { +impl Default for UnusedConfig { fn default() -> Self { Self { check_exported: false, @@ -47,11 +47,11 @@ impl Default for DeadCodeConfig { } } -pub fn check_dead_code( +pub fn check_unused( world: &LspWorld, ei: &ExprInfo, cross_file_refs: &FxHashSet>, - config: &DeadCodeConfig, + config: &UnusedConfig, ) -> DiagnosticVec { let mut diagnostics = EcoVec::new(); @@ -129,10 +129,8 @@ pub fn check_dead_code( _ => !has_references(&def_info.decl), }; - if is_unused { - if let Some(diag) = generate_diagnostic(&def_info, world, ei) { - diagnostics.push(diag); - } + if is_unused && let Some(diag) = generate_diagnostic(&def_info, world, ei) { + diagnostics.push(diag); } } @@ -157,26 +155,24 @@ fn compute_import_usage(definitions: &[DefInfo], ei: &ExprInfo) -> ImportUsageIn if matches!( def.decl.as_ref(), Decl::ModuleImport(_) | Decl::ModuleAlias(_) - ) { - if let Some(r) = ei.resolves.get(&def.span) { - let fid = r - .root - .as_ref() - .and_then(|expr| expr.file_id()) - .or_else(|| r.step.as_ref().and_then(|expr| expr.file_id())); - if let Some(fid) = fid { - module_targets.insert(def.decl.clone(), fid); - } + ) && let Some(r) = ei.resolves.get(&def.span) + { + let fid = r + .root + .as_ref() + .and_then(|expr| expr.file_id()) + .or_else(|| r.step.as_ref().and_then(|expr| expr.file_id())); + if let Some(fid) = fid { + module_targets.insert(def.decl.clone(), fid); } } - if matches!(def.decl.as_ref(), Decl::ImportAlias(_)) { - if let Some(alias_ref) = ei.resolves.get(&def.span) { - if let Some(Expr::Decl(step_decl)) = alias_ref.step.as_ref() { - alias_links.insert(def.decl.clone(), step_decl.clone()); - shadowed.insert(step_decl.clone()); - } - } + if matches!(def.decl.as_ref(), Decl::ImportAlias(_)) + && let Some(alias_ref) = ei.resolves.get(&def.span) + && let Some(Expr::Decl(step_decl)) = alias_ref.step.as_ref() + { + alias_links.insert(def.decl.clone(), step_decl.clone()); + shadowed.insert(step_decl.clone()); } } @@ -195,10 +191,10 @@ fn compute_import_usage(definitions: &[DefInfo], ei: &ExprInfo) -> ImportUsageIn .collect(); while let Some(alias) = worklist.pop() { - if let Some(target) = alias_links.get(&alias) { - if used.insert(target.clone()) { - worklist.push(target.clone()); - } + if let Some(target) = alias_links.get(&alias) + && used.insert(target.clone()) + { + worklist.push(target.clone()); } } @@ -309,7 +305,7 @@ fn collect_used_decls(reference: &RefExpr, used: &mut FxHashSet>) } } -fn should_skip_definition(def_info: &DefInfo, config: &DeadCodeConfig) -> bool { +fn should_skip_definition(def_info: &DefInfo, config: &UnusedConfig) -> bool { if matches!(def_info.scope, DefScope::Exported) && !config.check_exported { return true; } diff --git a/crates/tinymist-query/src/analysis.rs b/crates/tinymist-query/src/analysis.rs index d76be80d9..73f46c60f 100644 --- a/crates/tinymist-query/src/analysis.rs +++ b/crates/tinymist-query/src/analysis.rs @@ -629,7 +629,7 @@ mod call_info_tests { mod lint_tests { use std::collections::BTreeMap; - use tinymist_lint::{DeadCodeConfig, KnownIssues}; + use tinymist_lint::{KnownIssues, UnusedConfig}; use crate::tests::*; @@ -671,11 +671,11 @@ mod lint_tests { let ti = ctx.type_check(&source); let cross_file_refs = rustc_hash::FxHashSet::default(); - let dead_code_config = DeadCodeConfig { + let dead_code_config = UnusedConfig { check_exported: true, - ..DeadCodeConfig::default() + ..UnusedConfig::default() }; - let result = tinymist_lint::lint_file_with_dead_code_config( + let result = tinymist_lint::lint_file_with_unused_config( ctx.world(), &ei, ti, diff --git a/crates/tinymist-query/src/analysis/global.rs b/crates/tinymist-query/src/analysis/global.rs index 250446d8c..88f331f91 100644 --- a/crates/tinymist-query/src/analysis/global.rs +++ b/crates/tinymist-query/src/analysis/global.rs @@ -14,7 +14,7 @@ use tinymist_analysis::stats::AllocStats; use tinymist_analysis::syntax::classify_def_loosely; use tinymist_analysis::ty::{BuiltinTy, InsTy, term_value}; use tinymist_analysis::{analyze_expr_, analyze_import_}; -use tinymist_lint::{DeadCodeConfig, KnownIssues, LintInfo}; +use tinymist_lint::{KnownIssues, LintInfo, UnusedConfig}; use tinymist_project::{LspComputeGraph, LspWorld, TaskWhen}; use tinymist_std::hash::{FxDashMap, hash128}; use tinymist_std::typst::TypstDocument; @@ -83,8 +83,8 @@ pub struct Analysis { pub color_theme: ColorTheme, /// When to trigger the lint. pub lint: TaskWhen, - /// Configuration for dead code detection. - pub dead_code: DeadCodeConfig, + /// Configuration for unused declaration detection. + pub unused: UnusedConfig, /// The periscope provider. pub periscope: Option>, /// The global worker resources for analysis. @@ -839,23 +839,22 @@ impl SharedContext { let ei = self.expr_stage(source); let ti = self.type_check(source); let guard = self.query_stat(source.id(), "lint"); - self.slot.lint.compute( - hash128(&(&ei, &ti, issues, &self.analysis.dead_code)), - |_| { + self.slot + .lint + .compute(hash128(&(&ei, &ti, issues, &self.analysis.unused)), |_| { guard.miss(); let cross_file_refs = self.compute_cross_file_references(source.id(), &ei); - tinymist_lint::lint_file_with_dead_code_config( + tinymist_lint::lint_file_with_unused_config( self.world(), &ei, ti, issues.clone(), &cross_file_refs, - &self.analysis.dead_code, + &self.analysis.unused, ) - }, - ) + }) } /// Computes which declarations from the current file are referenced by other files. diff --git a/crates/tinymist/src/config.rs b/crates/tinymist/src/config.rs index 1a27546d5..7d8d59b61 100644 --- a/crates/tinymist/src/config.rs +++ b/crates/tinymist/src/config.rs @@ -980,13 +980,14 @@ pub struct LintFeat { pub enabled: Option, /// When to trigger the lint checks. pub when: Option, - /// Dead code detection options. + /// Unused declaration detection options. #[serde( default, - rename = "deadCode", + rename = "unused", + alias = "deadCode", deserialize_with = "deserialize_null_default" )] - pub dead_code: DeadCodeFeat, + pub unused: UnusedFeat, } impl LintFeat { @@ -999,26 +1000,26 @@ impl LintFeat { self.when.as_ref().unwrap_or(&TaskWhen::OnSave) } - /// Gets the dead-code lint configuration derived from `lint.deadCode`. - pub fn dead_code_config(&self) -> tinymist_lint::DeadCodeConfig { - let mut config = tinymist_lint::DeadCodeConfig::default(); - if let Some(check_exported) = self.dead_code.check_exported { + /// Gets the unused lint configuration derived from `lint.unused`. + pub fn unused_config(&self) -> tinymist_lint::UnusedConfig { + let mut config = tinymist_lint::UnusedConfig::default(); + if let Some(check_exported) = self.unused.check_exported { config.check_exported = check_exported; } - if let Some(check_params) = self.dead_code.check_params { + if let Some(check_params) = self.unused.check_params { config.check_params = check_params; } - if let Some(exceptions) = &self.dead_code.exceptions { + if let Some(exceptions) = &self.unused.exceptions { config.exceptions = exceptions.clone(); } config } } -/// Dead code detection options under `lint.deadCode`. +/// Unused declaration detection options under `lint.unused`. #[derive(Debug, Default, Clone, Deserialize)] #[serde(rename_all = "camelCase")] -pub struct DeadCodeFeat { +pub struct UnusedFeat { /// Whether to check module-level (exported) symbols. pub check_exported: Option, /// Whether to check unused function parameters. @@ -1311,10 +1312,10 @@ mod tests { test_good_config("lint"); test_good_config("lint.enabled"); test_good_config("lint.when"); - test_good_config("lint.deadCode"); - test_good_config("lint.deadCode.checkExported"); - test_good_config("lint.deadCode.checkParams"); - test_good_config("lint.deadCode.exceptions"); + test_good_config("lint.unused"); + test_good_config("lint.unused.checkExported"); + test_good_config("lint.unused.checkParams"); + test_good_config("lint.unused.exceptions"); test_good_config("preview"); test_good_config("preview.browsing"); diff --git a/crates/tinymist/src/project.rs b/crates/tinymist/src/project.rs index 967578745..5fbcd308b 100644 --- a/crates/tinymist/src/project.rs +++ b/crates/tinymist/src/project.rs @@ -177,7 +177,7 @@ impl ServerState { _ => tinymist_query::ColorTheme::Light, }, lint: config.lint.when().clone(), - dead_code: config.lint.dead_code_config(), + unused: config.lint.unused_config(), periscope: periscope_args.map(|args| { let r = TypstPeriscopeProvider(PeriscopeRenderer::new(args)); Arc::new(r) as Arc diff --git a/editors/vscode/package.json b/editors/vscode/package.json index 2366f0f6e..e246cbe88 100644 --- a/editors/vscode/package.json +++ b/editors/vscode/package.json @@ -454,21 +454,21 @@ "%extension.tinymist.config.tinymist.lint.when.string.enum.onType%" ] }, - "tinymist.lint.deadCode.checkExported": { - "title": "%extension.tinymist.config.tinymist.lint.deadCode.checkExported.title%", - "markdownDescription": "%extension.tinymist.config.tinymist.lint.deadCode.checkExported.desc%", + "tinymist.lint.unused.checkExported": { + "title": "%extension.tinymist.config.tinymist.lint.unused.checkExported.title%", + "markdownDescription": "%extension.tinymist.config.tinymist.lint.unused.checkExported.desc%", "type": "boolean", "default": false }, - "tinymist.lint.deadCode.checkParams": { - "title": "%extension.tinymist.config.tinymist.lint.deadCode.checkParams.title%", - "markdownDescription": "%extension.tinymist.config.tinymist.lint.deadCode.checkParams.desc%", + "tinymist.lint.unused.checkParams": { + "title": "%extension.tinymist.config.tinymist.lint.unused.checkParams.title%", + "markdownDescription": "%extension.tinymist.config.tinymist.lint.unused.checkParams.desc%", "type": "boolean", "default": true }, - "tinymist.lint.deadCode.exceptions": { - "title": "%extension.tinymist.config.tinymist.lint.deadCode.exceptions.title%", - "markdownDescription": "%extension.tinymist.config.tinymist.lint.deadCode.exceptions.desc%", + "tinymist.lint.unused.exceptions": { + "title": "%extension.tinymist.config.tinymist.lint.unused.exceptions.title%", + "markdownDescription": "%extension.tinymist.config.tinymist.lint.unused.exceptions.desc%", "type": "array", "items": { "type": "string" diff --git a/locales/tinymist-vscode.toml b/locales/tinymist-vscode.toml index 1eaee02f2..f4ca7b65c 100644 --- a/locales/tinymist-vscode.toml +++ b/locales/tinymist-vscode.toml @@ -1603,26 +1603,26 @@ zh = "保存文件时执行代码检查" en = "Perform lint checks on type" zh = "标记文件时执行代码检查" -[extension.tinymist.config.tinymist.lint.deadCode.checkExported.title] +[extension.tinymist.config.tinymist.lint.unused.checkExported.title] en = "Check exported symbols" zh = "检查导出符号" -[extension.tinymist.config.tinymist.lint.deadCode.checkExported.desc] +[extension.tinymist.config.tinymist.lint.unused.checkExported.desc] en = "Whether to check module-level (exported) symbols for being unused." zh = "是否检查模块级(导出)符号是否未使用。" -[extension.tinymist.config.tinymist.lint.deadCode.checkParams.title] +[extension.tinymist.config.tinymist.lint.unused.checkParams.title] en = "Check unused parameters" zh = "检查未使用参数" -[extension.tinymist.config.tinymist.lint.deadCode.checkParams.desc] +[extension.tinymist.config.tinymist.lint.unused.checkParams.desc] en = "Whether to check unused function parameters." zh = "是否检查未使用的函数参数。" -[extension.tinymist.config.tinymist.lint.deadCode.exceptions.title] +[extension.tinymist.config.tinymist.lint.unused.exceptions.title] en = "Dead code exceptions" zh = "死代码例外规则" -[extension.tinymist.config.tinymist.lint.deadCode.exceptions.desc] +[extension.tinymist.config.tinymist.lint.unused.exceptions.desc] en = "Glob-like patterns for exceptions (e.g., \"test_*\", \"_*\")." zh = "用于例外的类似 glob 的模式(例如 \"test_*\"、\"_*\")。"