mirror of
https://github.com/danbulant/oxc
synced 2026-05-24 12:21:58 +00:00
fix(linter): false positive in no-return-assign (#6128)
This commit is contained in:
parent
ae539af675
commit
e7e8eada69
2 changed files with 106 additions and 83 deletions
|
|
@ -6,8 +6,10 @@ use serde_json::Value;
|
||||||
|
|
||||||
use crate::{context::LintContext, rule::Rule, AstNode};
|
use crate::{context::LintContext, rule::Rule, AstNode};
|
||||||
|
|
||||||
fn no_return_assign_diagnostic(span: Span, message: &str) -> OxcDiagnostic {
|
fn no_return_assign_diagnostic(span: Span, message: &'static str) -> OxcDiagnostic {
|
||||||
OxcDiagnostic::warn(message.to_string()).with_label(span)
|
OxcDiagnostic::warn(message)
|
||||||
|
.with_label(span)
|
||||||
|
.with_help("Did you mean to use `==` instead of `=`?")
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Default, Clone)]
|
#[derive(Debug, Default, Clone)]
|
||||||
|
|
@ -39,7 +41,7 @@ declare_oxc_lint!(
|
||||||
/// ```
|
/// ```
|
||||||
NoReturnAssign,
|
NoReturnAssign,
|
||||||
style,
|
style,
|
||||||
suggestion
|
pending // TODO: add a suggestion
|
||||||
);
|
);
|
||||||
|
|
||||||
fn is_sentinel_node(ast_kind: AstKind) -> bool {
|
fn is_sentinel_node(ast_kind: AstKind) -> bool {
|
||||||
|
|
@ -60,7 +62,9 @@ impl Rule for NoReturnAssign {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn run<'a>(&self, node: &AstNode<'a>, ctx: &LintContext<'a>) {
|
fn run<'a>(&self, node: &AstNode<'a>, ctx: &LintContext<'a>) {
|
||||||
if let AstKind::AssignmentExpression(_) = node.kind() {
|
let AstKind::AssignmentExpression(assign) = node.kind() else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
if !self.always_disallow_assignment_in_return
|
if !self.always_disallow_assignment_in_return
|
||||||
&& ctx
|
&& ctx
|
||||||
.nodes()
|
.nodes()
|
||||||
|
|
@ -69,6 +73,7 @@ impl Rule for NoReturnAssign {
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut parent_node = ctx.nodes().parent_node(node.id());
|
let mut parent_node = ctx.nodes().parent_node(node.id());
|
||||||
while parent_node.is_some_and(|parent| !is_sentinel_node(parent.kind())) {
|
while parent_node.is_some_and(|parent| !is_sentinel_node(parent.kind())) {
|
||||||
parent_node = ctx.nodes().parent_node(parent_node.unwrap().id());
|
parent_node = ctx.nodes().parent_node(parent_node.unwrap().id());
|
||||||
|
|
@ -77,22 +82,23 @@ impl Rule for NoReturnAssign {
|
||||||
match parent.kind() {
|
match parent.kind() {
|
||||||
AstKind::ReturnStatement(_) => {
|
AstKind::ReturnStatement(_) => {
|
||||||
ctx.diagnostic(no_return_assign_diagnostic(
|
ctx.diagnostic(no_return_assign_diagnostic(
|
||||||
parent.span(),
|
assign.span(),
|
||||||
"Return statement should not contain an assignment.",
|
"Return statements should not contain an assignment.",
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
AstKind::ArrowFunctionExpression(_) => {
|
AstKind::ArrowFunctionExpression(arrow) => {
|
||||||
|
if arrow.expression {
|
||||||
ctx.diagnostic(no_return_assign_diagnostic(
|
ctx.diagnostic(no_return_assign_diagnostic(
|
||||||
parent.span(),
|
assign.span(),
|
||||||
"Arrow function should not return an assignment.",
|
"Arrow functions should not return an assignment.",
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
}
|
||||||
_ => (),
|
_ => (),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test() {
|
fn test() {
|
||||||
|
|
@ -116,6 +122,7 @@ fn test() {
|
||||||
"function x() { return function y() { result = a * b }; }",
|
"function x() { return function y() { result = a * b }; }",
|
||||||
Some(serde_json::json!(["always"])),
|
Some(serde_json::json!(["always"])),
|
||||||
),
|
),
|
||||||
|
("() => { a = b; }", None),
|
||||||
("() => { return (result = a * b); }", Some(serde_json::json!(["except-parens"]))),
|
("() => { return (result = a * b); }", Some(serde_json::json!(["except-parens"]))),
|
||||||
("() => (result = a * b)", Some(serde_json::json!(["except-parens"]))),
|
("() => (result = a * b)", Some(serde_json::json!(["except-parens"]))),
|
||||||
("const foo = (a,b,c) => ((a = b), c)", None),
|
("const foo = (a,b,c) => ((a = b), c)", None),
|
||||||
|
|
|
||||||
|
|
@ -1,111 +1,127 @@
|
||||||
---
|
---
|
||||||
source: crates/oxc_linter/src/tester.rs
|
source: crates/oxc_linter/src/tester.rs
|
||||||
---
|
---
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:23]
|
||||||
1 │ function x() { return result = a * b; };
|
1 │ function x() { return result = a * b; };
|
||||||
· ──────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:23]
|
||||||
1 │ function x() { return (result) = (a * b); };
|
1 │ function x() { return (result) = (a * b); };
|
||||||
· ──────────────────────────
|
· ──────────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:23]
|
||||||
1 │ function x() { return result = a * b; };
|
1 │ function x() { return result = a * b; };
|
||||||
· ──────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:23]
|
||||||
1 │ function x() { return (result) = (a * b); };
|
1 │ function x() { return (result) = (a * b); };
|
||||||
· ──────────────────────────
|
· ──────────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:9]
|
╭─[no_return_assign.tsx:1:16]
|
||||||
1 │ () => { return result = a * b; }
|
1 │ () => { return result = a * b; }
|
||||||
· ──────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Arrow function should not return an assignment.
|
⚠ eslint(no-return-assign): Arrow functions should not return an assignment.
|
||||||
╭─[no_return_assign.tsx:1:1]
|
╭─[no_return_assign.tsx:1:7]
|
||||||
1 │ () => result = a * b
|
1 │ () => result = a * b
|
||||||
· ────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:23]
|
||||||
1 │ function x() { return result = a * b; };
|
1 │ function x() { return result = a * b; };
|
||||||
· ──────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:24]
|
||||||
1 │ function x() { return (result = a * b); };
|
1 │ function x() { return (result = a * b); };
|
||||||
· ────────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:1:16]
|
╭─[no_return_assign.tsx:1:34]
|
||||||
1 │ function x() { return result || (result = a * b); };
|
1 │ function x() { return result || (result = a * b); };
|
||||||
· ──────────────────────────────────
|
· ──────────────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:2:20]
|
╭─[no_return_assign.tsx:2:27]
|
||||||
1 │ function foo(){
|
1 │ function foo(){
|
||||||
2 │ return a = b
|
2 │ return a = b
|
||||||
· ────────────
|
· ─────
|
||||||
3 │ }
|
3 │ }
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:2:20]
|
╭─[no_return_assign.tsx:2:27]
|
||||||
1 │ function doSomething() {
|
1 │ function doSomething() {
|
||||||
2 │ return foo = bar && foo > 0;
|
2 │ return foo = bar && foo > 0;
|
||||||
· ────────────────────────────
|
· ────────────────────
|
||||||
3 │ }
|
3 │ }
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:2:20]
|
╭─[no_return_assign.tsx:2:27]
|
||||||
1 │ function doSomething() {
|
1 │ function doSomething() {
|
||||||
2 │ ╭─▶ return foo = function(){
|
2 │ ╭─▶ return foo = function(){
|
||||||
3 │ │ return (bar = bar1)
|
3 │ │ return (bar = bar1)
|
||||||
4 │ ╰─▶ }
|
4 │ ╰─▶ }
|
||||||
5 │ }
|
5 │ }
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
╭─[no_return_assign.tsx:2:20]
|
|
||||||
1 │ function doSomething() {
|
|
||||||
2 │ return foo = () => a
|
|
||||||
· ────────────────────
|
|
||||||
3 │ }
|
|
||||||
╰────
|
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Arrow function should not return an assignment.
|
|
||||||
╭─[no_return_assign.tsx:2:27]
|
╭─[no_return_assign.tsx:2:27]
|
||||||
1 │ function doSomething() {
|
1 │ function doSomething() {
|
||||||
2 │ return () => a = () => b
|
2 │ return foo = () => a
|
||||||
· ─────────────────
|
· ─────────────
|
||||||
3 │ }
|
3 │ }
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Return statement should not contain an assignment.
|
⚠ eslint(no-return-assign): Arrow functions should not return an assignment.
|
||||||
╭─[no_return_assign.tsx:3:24]
|
╭─[no_return_assign.tsx:2:33]
|
||||||
|
1 │ function doSomething() {
|
||||||
|
2 │ return () => a = () => b
|
||||||
|
· ───────────
|
||||||
|
3 │ }
|
||||||
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
|
⚠ eslint(no-return-assign): Return statements should not contain an assignment.
|
||||||
|
╭─[no_return_assign.tsx:3:31]
|
||||||
2 │ return function bar(b){
|
2 │ return function bar(b){
|
||||||
3 │ return a = b
|
3 │ return a = b
|
||||||
· ────────────
|
· ─────
|
||||||
4 │ }
|
4 │ }
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
||||||
⚠ eslint(no-return-assign): Arrow function should not return an assignment.
|
⚠ eslint(no-return-assign): Arrow functions should not return an assignment.
|
||||||
╭─[no_return_assign.tsx:1:20]
|
╭─[no_return_assign.tsx:1:27]
|
||||||
1 │ const foo = (a) => (b) => a = b
|
1 │ const foo = (a) => (b) => a = b
|
||||||
· ────────────
|
· ─────
|
||||||
╰────
|
╰────
|
||||||
|
help: Did you mean to use `==` instead of `=`?
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue