Skip to content

Commit 4283beb

Browse files
committed
fix(no_invalid_regexp): support inside function calls
1 parent ac2aa57 commit 4283beb

File tree

1 file changed

+55
-21
lines changed

1 file changed

+55
-21
lines changed

src/rules/no_invalid_regexp.rs

Lines changed: 55 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,10 @@ use super::{Context, LintRule};
55
use crate::js_regex::*;
66
use crate::Program;
77
use crate::ProgramRef;
8-
use deno_ast::swc::ast::Expr;
98
use deno_ast::swc::ast::ExprOrSpread;
10-
use deno_ast::swc::visit::noop_visit_type;
9+
use deno_ast::swc::ast::{Callee, Expr};
1110
use deno_ast::swc::visit::Visit;
11+
use deno_ast::swc::visit::{noop_visit_type, VisitWith};
1212
use deno_ast::SourceRange;
1313
use deno_ast::SourceRangedForSpanned;
1414

@@ -74,18 +74,24 @@ impl<'c, 'view> NoInvalidRegexpVisitor<'c, 'view> {
7474
args: &[ExprOrSpread],
7575
range: SourceRange,
7676
) {
77-
if let Expr::Ident(ident) = callee {
78-
if ident.sym != *"RegExp" || args.is_empty() {
79-
return;
80-
}
81-
if let Some(pattern) = &check_expr_for_string_literal(&args[0].expr) {
82-
if args.len() > 1 {
83-
if let Some(flags) = &check_expr_for_string_literal(&args[1].expr) {
84-
self.check_regex(pattern, flags, range);
85-
return;
77+
match callee {
78+
Expr::Ident(ident) => {
79+
if ident.sym != *"RegExp" || args.is_empty() {
80+
return;
81+
}
82+
if let Some(pattern) = &check_expr_for_string_literal(&args[0].expr) {
83+
if args.len() > 1 {
84+
if let Some(flags) = &check_expr_for_string_literal(&args[1].expr) {
85+
self.check_regex(pattern, flags, range);
86+
return;
87+
}
8688
}
89+
self.check_regex(pattern, "", range);
8790
}
88-
self.check_regex(pattern, "", range);
91+
}
92+
_ => {
93+
callee.visit_children_with(self);
94+
args.visit_children_with(self);
8995
}
9096
}
9197
}
@@ -120,19 +126,21 @@ impl<'c, 'view> Visit for NoInvalidRegexpVisitor<'c, 'view> {
120126
}
121127

122128
fn visit_call_expr(&mut self, call_expr: &deno_ast::swc::ast::CallExpr) {
123-
if let deno_ast::swc::ast::Callee::Expr(expr) = &call_expr.callee {
124-
self.handle_call_or_new_expr(expr, &call_expr.args, call_expr.range());
129+
match &call_expr.callee {
130+
Callee::Super(_) => call_expr.args.visit_children_with(self),
131+
Callee::Expr(expr) => {
132+
self.handle_call_or_new_expr(expr, &call_expr.args, call_expr.range());
133+
}
134+
_ => {}
125135
}
126136
}
127137

128138
fn visit_new_expr(&mut self, new_expr: &deno_ast::swc::ast::NewExpr) {
129-
if new_expr.args.is_some() {
130-
self.handle_call_or_new_expr(
131-
&new_expr.callee,
132-
new_expr.args.as_ref().unwrap(),
133-
new_expr.range(),
134-
);
135-
}
139+
self.handle_call_or_new_expr(
140+
&new_expr.callee,
141+
new_expr.args.as_ref().unwrap_or(&vec![]),
142+
new_expr.range(),
143+
);
136144
}
137145
}
138146

@@ -193,6 +201,32 @@ let re = new RegExp('foo', x);",
193201
r"/(?<a>a)\k</": [{ col: 0, message: MESSAGE, hint: HINT }],
194202
r"/(?<!a){1}/": [{ col: 0, message: MESSAGE, hint: HINT }],
195203
r"/(a)(a)(a)(a)(a)(a)(a)(a)(a)(a)\11/u": [{ col: 0, message: MESSAGE, hint: HINT }],
204+
r"
205+
((_) => [
206+
/+/,
207+
RegExp('+'),
208+
new RegExp('+'),
209+
])([
210+
/+/,
211+
RegExp('+'),
212+
new RegExp('+'),
213+
]);": [
214+
{ line: 3, col: 2, message: MESSAGE, hint: HINT },
215+
{ line: 4, col: 2, message: MESSAGE, hint: HINT },
216+
{ line: 5, col: 2, message: MESSAGE, hint: HINT },
217+
{ line: 7, col: 2, message: MESSAGE, hint: HINT },
218+
{ line: 8, col: 2, message: MESSAGE, hint: HINT },
219+
{ line: 9, col: 2, message: MESSAGE, hint: HINT }],
220+
r"
221+
new function () {
222+
return /+/;
223+
};": [{ line: 3, col: 9, message: MESSAGE, hint: HINT }],
224+
r"
225+
class C extends RegExp {
226+
constructor() {
227+
super(/+/);
228+
}
229+
}": [{ line: 4, col: 10, message: MESSAGE, hint: HINT }],
196230
}
197231
}
198232
}

0 commit comments

Comments
 (0)