Skip to content

Commit ab39a62

Browse files
authoredMar 23, 2025··
feat(ts/fast-strip): Add start/end span information (#10251)
**Description:** Note: This PR does not include a fix for the parser diagnostics. **Related issue:** - Closes #10188
1 parent 549e38d commit ab39a62

File tree

2 files changed

+61
-26
lines changed

2 files changed

+61
-26
lines changed
 

‎bindings/binding_typescript_wasm/__tests__/__snapshots__/transform.js.snap

+40-20
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,13 @@
33
exports[`transform in strip-only mode should not emit 'Caused by: failed to parse' 1`] = `
44
{
55
"code": "InvalidSyntax",
6-
"column": 23,
6+
"endColumn": 30,
7+
"endLine": 1,
78
"filename": "test.ts",
8-
"line": 1,
99
"message": "await isn't allowed in non-async function",
1010
"snippet": "Promise",
11+
"startColumn": 23,
12+
"startLine": 1,
1113
}
1214
`;
1315

@@ -40,24 +42,28 @@ exports[`transform in strip-only mode should remove declare enum 3`] = `
4042
exports[`transform in strip-only mode should report correct error for syntax error 1`] = `
4143
{
4244
"code": "InvalidSyntax",
43-
"column": 25,
45+
"endColumn": 31,
46+
"endLine": 1,
4447
"filename": "test.ts",
45-
"line": 1,
4648
"message": "Expected ';', '}' or <eof>",
4749
"snippet": "syntax",
50+
"startColumn": 25,
51+
"startLine": 1,
4852
}
4953
`;
5054

5155
exports[`transform in strip-only mode should report correct error for unsupported syntax 1`] = `
5256
{
5357
"code": "UnsupportedSyntax",
54-
"column": 0,
58+
"endColumn": 21,
59+
"endLine": 3,
5560
"filename": "test.ts",
56-
"line": 1,
5761
"message": "TypeScript enum is not supported in strip-only mode",
5862
"snippet": "enum Foo {
5963
a, b
6064
}",
65+
"startColumn": 0,
66+
"startLine": 1,
6167
}
6268
`;
6369

@@ -117,77 +123,91 @@ exports[`transform in strip-only mode should strip type declarations 1`] = `
117123
exports[`transform in strip-only mode should throw an error when it encounters a module 1`] = `
118124
{
119125
"code": "UnsupportedSyntax",
120-
"column": 0,
126+
"endColumn": 10,
127+
"endLine": 1,
121128
"filename": "test.ts",
122-
"line": 1,
123129
"message": "\`module\` keyword is not supported. Use \`namespace\` instead.",
124130
"snippet": "module foo",
131+
"startColumn": 0,
132+
"startLine": 1,
125133
}
126134
`;
127135

128136
exports[`transform in strip-only mode should throw an error when it encounters a module 2`] = `
129137
{
130138
"code": "UnsupportedSyntax",
131-
"column": 8,
139+
"endColumn": 18,
140+
"endLine": 1,
132141
"filename": "test.ts",
133-
"line": 1,
134142
"message": "\`module\` keyword is not supported. Use \`namespace\` instead.",
135143
"snippet": "module foo",
144+
"startColumn": 8,
145+
"startLine": 1,
136146
}
137147
`;
138148

139149
exports[`transform in strip-only mode should throw an error when it encounters a namespace 1`] = `
140150
{
141151
"code": "UnsupportedSyntax",
142-
"column": 0,
152+
"endColumn": 37,
153+
"endLine": 1,
143154
"filename": "test.ts",
144-
"line": 1,
145155
"message": "TypeScript namespace declaration is not supported in strip-only mode",
146156
"snippet": "namespace Foo { export const m = 1; }",
157+
"startColumn": 0,
158+
"startLine": 1,
147159
}
148160
`;
149161

150162
exports[`transform in strip-only mode should throw an error when it encounters an enum 1`] = `
151163
{
152164
"code": "UnsupportedSyntax",
153-
"column": 0,
165+
"endColumn": 11,
166+
"endLine": 1,
154167
"filename": "test.ts",
155-
"line": 1,
156168
"message": "TypeScript enum is not supported in strip-only mode",
157169
"snippet": "enum Foo {}",
170+
"startColumn": 0,
171+
"startLine": 1,
158172
}
159173
`;
160174

161175
exports[`transform in transform mode shoud throw an object even with deprecatedTsModuleAsError = true 1`] = `
162176
{
163177
"code": "UnsupportedSyntax",
164-
"column": 0,
178+
"endColumn": 8,
179+
"endLine": 1,
165180
"filename": "<anon>",
166-
"line": 1,
167181
"message": "\`module\` keyword is not supported. Use \`namespace\` instead.",
168182
"snippet": "module F",
183+
"startColumn": 0,
184+
"startLine": 1,
169185
}
170186
`;
171187

172188
exports[`transform in transform mode should throw an error when it encounters a declared module 1`] = `
173189
{
174190
"code": "UnsupportedSyntax",
175-
"column": 8,
191+
"endColumn": 18,
192+
"endLine": 1,
176193
"filename": "test.ts",
177-
"line": 1,
178194
"message": "\`module\` keyword is not supported. Use \`namespace\` instead.",
179195
"snippet": "module foo",
196+
"startColumn": 8,
197+
"startLine": 1,
180198
}
181199
`;
182200

183201
exports[`transform in transform mode should throw an error when it encounters a module 1`] = `
184202
{
185203
"code": "UnsupportedSyntax",
186-
"column": 0,
204+
"endColumn": 10,
205+
"endLine": 1,
187206
"filename": "test.ts",
188-
"line": 1,
189207
"message": "\`module\` keyword is not supported. Use \`namespace\` instead.",
190208
"snippet": "module foo",
209+
"startColumn": 0,
210+
"startLine": 1,
191211
}
192212
`;
193213

‎bindings/binding_typescript_wasm/src/lib.rs

+21-6
Original file line numberDiff line numberDiff line change
@@ -114,25 +114,32 @@ impl Emitter for LockedWriter {
114114
None => None,
115115
};
116116

117-
let loc = d
117+
let start = d
118118
.span
119119
.primary_span()
120120
.and_then(|span| self.cm.try_lookup_char_pos(span.lo()).ok());
121121

122+
let end = d
123+
.span
124+
.primary_span()
125+
.and_then(|span| self.cm.try_lookup_char_pos(span.hi()).ok());
126+
122127
let snippet = d
123128
.span
124129
.primary_span()
125130
.and_then(|span| self.cm.span_to_snippet(span).ok());
126131

127-
let filename = loc.as_ref().map(|loc| loc.file.name.to_string());
132+
let filename = start.as_ref().map(|loc| loc.file.name.to_string());
128133

129134
let error = JsonDiagnostic {
130135
code: error_code.map(|s| s.to_string()),
131136
message: d.message[0].0.to_string(),
132137
snippet,
133138
filename,
134-
line: loc.as_ref().map(|loc| loc.line),
135-
column: loc.as_ref().map(|loc| loc.col_display),
139+
start_line: start.as_ref().map(|loc| loc.line),
140+
start_column: start.as_ref().map(|loc| loc.col_display),
141+
end_line: end.as_ref().map(|loc| loc.line),
142+
end_column: end.as_ref().map(|loc| loc.col_display),
136143
children,
137144
};
138145

@@ -145,6 +152,7 @@ impl Emitter for LockedWriter {
145152
}
146153

147154
#[derive(Serialize)]
155+
#[serde(rename_all = "camelCase")]
148156
struct JsonDiagnostic {
149157
/// Error code
150158
#[serde(skip_serializing_if = "Option::is_none")]
@@ -158,17 +166,24 @@ struct JsonDiagnostic {
158166
filename: Option<String>,
159167

160168
#[serde(skip_serializing_if = "Option::is_none")]
161-
line: Option<usize>,
169+
start_line: Option<usize>,
162170
#[serde(skip_serializing_if = "Option::is_none")]
163-
column: Option<usize>,
171+
start_column: Option<usize>,
172+
173+
#[serde(skip_serializing_if = "Option::is_none")]
174+
end_line: Option<usize>,
175+
#[serde(skip_serializing_if = "Option::is_none")]
176+
end_column: Option<usize>,
164177

165178
#[serde(skip_serializing_if = "Vec::is_empty")]
166179
children: Vec<JsonSubdiagnostic>,
167180
}
168181

169182
#[derive(Serialize)]
183+
#[serde(rename_all = "camelCase")]
170184
struct JsonSubdiagnostic {
171185
message: String,
186+
#[serde(skip_serializing_if = "Option::is_none")]
172187
snippet: Option<String>,
173188
filename: String,
174189
line: usize,

0 commit comments

Comments
 (0)
Please sign in to comment.