Skip to content

Commit 3b5c899

Browse files
committed
feat(minifier): implement folding String.prototype.replace
1 parent bbb5d6a commit 3b5c899

File tree

1 file changed

+37
-2
lines changed

1 file changed

+37
-2
lines changed

crates/oxc_minifier/src/ast_passes/peephole_replace_known_methods.rs

Lines changed: 37 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -88,7 +88,9 @@ impl PeepholeReplaceKnownMethods {
8888
"charCodeAt" => {
8989
Self::try_fold_string_char_code_at(call_expr.span, call_expr, string_lit, ctx)
9090
}
91-
"replace" => None,
91+
"replace" => {
92+
Self::try_fold_string_replace(call_expr.span, call_expr, string_lit, ctx)
93+
}
9294
"replaceAll" => None,
9395
_ => None,
9496
};
@@ -244,6 +246,40 @@ impl PeepholeReplaceKnownMethods {
244246
NumberBase::Decimal,
245247
)))
246248
}
249+
fn try_fold_string_replace<'a>(
250+
span: Span,
251+
call_expr: &CallExpression<'a>,
252+
string_lit: &StringLiteral<'a>,
253+
ctx: &mut TraverseCtx<'a>,
254+
) -> Option<Expression<'a>> {
255+
if call_expr.arguments.len() != 2 {
256+
return None;
257+
}
258+
259+
let search_value = call_expr.arguments.first().unwrap();
260+
let search_value = match search_value {
261+
Argument::SpreadElement(_) => return None,
262+
match_expression!(Argument) => {
263+
Ctx(ctx).get_side_free_string_value(search_value.to_expression())?
264+
}
265+
};
266+
let replace_value = call_expr.arguments.get(1).unwrap();
267+
let replace_value = match replace_value {
268+
Argument::SpreadElement(_) => return None,
269+
match_expression!(Argument) => {
270+
Ctx(ctx).get_side_free_string_value(replace_value.to_expression())?
271+
}
272+
};
273+
274+
if replace_value.contains('$') {
275+
return None;
276+
}
277+
278+
let result =
279+
string_lit.value.as_str().cow_replacen(search_value.as_ref(), &replace_value, 1);
280+
281+
Some(ctx.ast.expression_from_string_literal(ctx.ast.string_literal(span, result)))
282+
}
247283
}
248284

249285
/// Port from: <https://github.com/google/closure-compiler/blob/master/test/com/google/javascript/jscomp/PeepholeReplaceKnownMethodsTest.java>
@@ -394,7 +430,6 @@ mod test {
394430
}
395431

396432
#[test]
397-
#[ignore]
398433
fn test_fold_string_replace() {
399434
fold("'c'.replace('c','x')", "'x'");
400435
fold("'ac'.replace('c','x')", "'ax'");

0 commit comments

Comments
 (0)