mirror of
https://github.com/zed-industries/zed.git
synced 2026-05-31 19:05:00 +07:00
languages: Add inline values support for JavaScript, TypeScript, and TSX (#40914)
Adds debugger inline values support for JavaScript, TypeScript, and TSX languages. Release Notes: - debugger: Add inline value support for Javascript, TypeScript, and TSX --------- Co-authored-by: Anthony <anthony@zed.dev>
This commit is contained in:
parent
ef306245e0
commit
b7cc597d28
4 changed files with 329 additions and 1 deletions
|
|
@ -3,7 +3,10 @@ use std::{path::Path, sync::Arc};
|
|||
use dap::{Scope, StackFrame, Variable, requests::Variables};
|
||||
use editor::{Editor, EditorMode, MultiBuffer};
|
||||
use gpui::{BackgroundExecutor, TestAppContext, VisualTestContext};
|
||||
use language::{Language, LanguageConfig, LanguageMatcher, tree_sitter_python, tree_sitter_rust};
|
||||
use language::{
|
||||
Language, LanguageConfig, LanguageMatcher, tree_sitter_python, tree_sitter_rust,
|
||||
tree_sitter_typescript,
|
||||
};
|
||||
use project::{FakeFs, Project};
|
||||
use serde_json::json;
|
||||
use unindent::Unindent as _;
|
||||
|
|
@ -2272,3 +2275,257 @@ fn main() {
|
|||
)
|
||||
.await;
|
||||
}
|
||||
|
||||
fn javascript_lang() -> Language {
|
||||
let debug_variables_query = include_str!("../../../languages/src/javascript/debugger.scm");
|
||||
Language::new(
|
||||
LanguageConfig {
|
||||
name: "JavaScript".into(),
|
||||
matcher: LanguageMatcher {
|
||||
path_suffixes: vec!["js".to_string()],
|
||||
..Default::default()
|
||||
},
|
||||
..Default::default()
|
||||
},
|
||||
Some(tree_sitter_typescript::LANGUAGE_TYPESCRIPT.into()),
|
||||
)
|
||||
.with_debug_variables_query(debug_variables_query)
|
||||
.unwrap()
|
||||
}
|
||||
|
||||
fn typescript_lang() -> Language {
|
||||
let debug_variables_query = include_str!("../../../languages/src/typescript/debugger.scm");
|
||||
Language::new(
|
||||
LanguageConfig {
|
||||
name: "TypeScript".into(),
|
||||
matcher: LanguageMatcher {
|
||||
path_suffixes: vec!["ts".to_string()],
|
||||
..Default::default()
|
||||
},
|
||||
..Default::default()
|
||||
},
|
||||
Some(tree_sitter_typescript::LANGUAGE_TYPESCRIPT.into()),
|
||||
)
|
||||
.with_debug_variables_query(debug_variables_query)
|
||||
.unwrap()
|
||||
}
|
||||
|
||||
fn tsx_lang() -> Language {
|
||||
let debug_variables_query = include_str!("../../../languages/src/tsx/debugger.scm");
|
||||
Language::new(
|
||||
LanguageConfig {
|
||||
name: "TSX".into(),
|
||||
matcher: LanguageMatcher {
|
||||
path_suffixes: vec!["tsx".to_string()],
|
||||
..Default::default()
|
||||
},
|
||||
..Default::default()
|
||||
},
|
||||
Some(tree_sitter_typescript::LANGUAGE_TSX.into()),
|
||||
)
|
||||
.with_debug_variables_query(debug_variables_query)
|
||||
.unwrap()
|
||||
}
|
||||
|
||||
#[gpui::test]
|
||||
async fn test_javascript_inline_values(executor: BackgroundExecutor, cx: &mut TestAppContext) {
|
||||
let variables = [
|
||||
("x", "10"),
|
||||
("y", "20"),
|
||||
("sum", "30"),
|
||||
("message", "Hello"),
|
||||
];
|
||||
|
||||
let before = r#"
|
||||
function calculate() {
|
||||
const x = 10;
|
||||
const y = 20;
|
||||
const sum = x + y;
|
||||
const message = "Hello";
|
||||
console.log(message, "Sum:", sum);
|
||||
}
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
let after = r#"
|
||||
function calculate() {
|
||||
const x: 10 = 10;
|
||||
const y: 20 = 20;
|
||||
const sum: 30 = x: 10 + y: 20;
|
||||
const message: Hello = "Hello";
|
||||
console.log(message, "Sum:", sum);
|
||||
}
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
test_inline_values_util(
|
||||
&variables,
|
||||
&[],
|
||||
&before,
|
||||
&after,
|
||||
None,
|
||||
javascript_lang(),
|
||||
executor,
|
||||
cx,
|
||||
)
|
||||
.await;
|
||||
}
|
||||
|
||||
#[gpui::test]
|
||||
async fn test_typescript_inline_values(executor: BackgroundExecutor, cx: &mut TestAppContext) {
|
||||
let variables = [
|
||||
("count", "42"),
|
||||
("name", "Alice"),
|
||||
("result", "84"),
|
||||
("i", "3"),
|
||||
];
|
||||
|
||||
let before = r#"
|
||||
function processData(count: number, name: string): number {
|
||||
let result = count * 2;
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
let after = r#"
|
||||
function processData(count: number, name: string): number {
|
||||
let result: 84 = count: 42 * 2;
|
||||
for (let i: 3 = 0; i: 3 < 5; i: 3++) {
|
||||
console.log(i);
|
||||
}
|
||||
return result: 84;
|
||||
}
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
test_inline_values_util(
|
||||
&variables,
|
||||
&[],
|
||||
&before,
|
||||
&after,
|
||||
None,
|
||||
typescript_lang(),
|
||||
executor,
|
||||
cx,
|
||||
)
|
||||
.await;
|
||||
}
|
||||
|
||||
#[gpui::test]
|
||||
async fn test_tsx_inline_values(executor: BackgroundExecutor, cx: &mut TestAppContext) {
|
||||
let variables = [("count", "5"), ("message", "Hello React")];
|
||||
|
||||
let before = r#"
|
||||
const Counter = () => {
|
||||
const count = 5;
|
||||
const message = "Hello React";
|
||||
return (
|
||||
<div>
|
||||
<p>{message}</p>
|
||||
<span>{count}</span>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
let after = r#"
|
||||
const Counter = () => {
|
||||
const count: 5 = 5;
|
||||
const message: Hello React = "Hello React";
|
||||
return (
|
||||
<div>
|
||||
<p>{message: Hello React}</p>
|
||||
<span>{count}</span>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
test_inline_values_util(
|
||||
&variables,
|
||||
&[],
|
||||
&before,
|
||||
&after,
|
||||
None,
|
||||
tsx_lang(),
|
||||
executor,
|
||||
cx,
|
||||
)
|
||||
.await;
|
||||
}
|
||||
|
||||
#[gpui::test]
|
||||
async fn test_javascript_arrow_functions(executor: BackgroundExecutor, cx: &mut TestAppContext) {
|
||||
let variables = [("x", "42"), ("result", "84")];
|
||||
|
||||
let before = r#"
|
||||
const double = (x) => {
|
||||
const result = x * 2;
|
||||
return result;
|
||||
};
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
let after = r#"
|
||||
const double = (x) => {
|
||||
const result: 84 = x: 42 * 2;
|
||||
return result: 84;
|
||||
};
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
test_inline_values_util(
|
||||
&variables,
|
||||
&[],
|
||||
&before,
|
||||
&after,
|
||||
None,
|
||||
javascript_lang(),
|
||||
executor,
|
||||
cx,
|
||||
)
|
||||
.await;
|
||||
}
|
||||
|
||||
#[gpui::test]
|
||||
async fn test_typescript_for_in_loop(executor: BackgroundExecutor, cx: &mut TestAppContext) {
|
||||
let variables = [("key", "name"), ("obj", "{name: 'test'}")];
|
||||
|
||||
let before = r#"
|
||||
function iterate() {
|
||||
const obj = {name: 'test'};
|
||||
for (const key in obj) {
|
||||
console.log(key);
|
||||
}
|
||||
}
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
let after = r#"
|
||||
function iterate() {
|
||||
const obj: {name: 'test'} = {name: 'test'};
|
||||
for (const key: name in obj) {
|
||||
console.log(key);
|
||||
}
|
||||
}
|
||||
"#
|
||||
.unindent();
|
||||
|
||||
test_inline_values_util(
|
||||
&variables,
|
||||
&[],
|
||||
&before,
|
||||
&after,
|
||||
None,
|
||||
typescript_lang(),
|
||||
executor,
|
||||
cx,
|
||||
)
|
||||
.await;
|
||||
}
|
||||
|
|
|
|||
23
crates/languages/src/javascript/debugger.scm
Normal file
23
crates/languages/src/javascript/debugger.scm
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
(lexical_declaration (variable_declarator name: (identifier) @debug-variable))
|
||||
|
||||
(for_in_statement left: (identifier) @debug-variable)
|
||||
(for_statement initializer: (lexical_declaration (variable_declarator name: (identifier) @debug-variable)))
|
||||
|
||||
(binary_expression left: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
(binary_expression right: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(unary_expression argument: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
(update_expression argument: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(return_statement (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(parenthesized_expression (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(array (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(pair value: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(member_expression object: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(statement_block) @debug-scope
|
||||
(program) @debug-scope
|
||||
25
crates/languages/src/tsx/debugger.scm
Normal file
25
crates/languages/src/tsx/debugger.scm
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
(lexical_declaration (variable_declarator name: (identifier) @debug-variable))
|
||||
|
||||
(for_in_statement left: (identifier) @debug-variable)
|
||||
(for_statement initializer: (lexical_declaration (variable_declarator name: (identifier) @debug-variable)))
|
||||
|
||||
(binary_expression left: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
(binary_expression right: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(unary_expression argument: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
(update_expression argument: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(return_statement (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(parenthesized_expression (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(jsx_expression (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(array (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(pair value: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(member_expression object: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(statement_block) @debug-scope
|
||||
(program) @debug-scope
|
||||
23
crates/languages/src/typescript/debugger.scm
Normal file
23
crates/languages/src/typescript/debugger.scm
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
(lexical_declaration (variable_declarator name: (identifier) @debug-variable))
|
||||
|
||||
(for_in_statement left: (identifier) @debug-variable)
|
||||
(for_statement initializer: (lexical_declaration (variable_declarator name: (identifier) @debug-variable)))
|
||||
|
||||
(binary_expression left: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
(binary_expression right: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(unary_expression argument: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
(update_expression argument: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(return_statement (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(parenthesized_expression (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(array (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(pair value: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(member_expression object: (identifier) @debug-variable (#not-match? @debug-variable "^[A-Z]"))
|
||||
|
||||
(statement_block) @debug-scope
|
||||
(program) @debug-scope
|
||||
Loading…
Reference in a new issue