Skip to content
This repository has been archived by the owner on Aug 31, 2023. It is now read-only.

Commit

Permalink
chore: handle TsNonNullAssertionAssignment
Browse files Browse the repository at this point in the history
  • Loading branch information
kaioduarte committed Nov 23, 2022
1 parent 0130c75 commit 0fb3782
Show file tree
Hide file tree
Showing 3 changed files with 170 additions and 32 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@ use rome_analyze::context::RuleContext;
use rome_analyze::{declare_rule, ActionCategory, Ast, Rule, RuleDiagnostic};
use rome_console::markup;
use rome_diagnostics::Applicability;
use rome_js_syntax::{JsAnyExpression, TsNonNullAssertionExpression};
use rome_rowan::{AstNode, BatchMutationExt};
use rome_js_syntax::{
JsAnyAssignment, JsAnyExpression, TsNonNullAssertionAssignment, TsNonNullAssertionExpression,
};
use rome_rowan::{declare_node_union, AstNode, BatchMutationExt};

use crate::JsRuleAction;

Expand Down Expand Up @@ -52,18 +54,59 @@ declare_rule! {
}
}

declare_node_union! {
pub(crate) TsAnyNonNullAssertion = TsNonNullAssertionAssignment | TsNonNullAssertionExpression
}

impl Rule for NoExtraNonNullAssertion {
type Query = Ast<TsNonNullAssertionExpression>;
type Query = Ast<TsAnyNonNullAssertion>;
type State = ();
type Signals = Option<Self::State>;
type Options = ();

fn run(ctx: &RuleContext<Self>) -> Self::Signals {
let node = ctx.query();
let parent = node.parent::<JsAnyExpression>()?;

if has_extra_non_null_assertion(parent)? {
return Some(());
match node {
TsAnyNonNullAssertion::TsNonNullAssertionAssignment(_) => {
let parent = node.parent::<JsAnyAssignment>()?;

// Cases considered as invalid:
// - TsNonNullAssertionAssignment > TsNonNullAssertionAssignment
let has_extra_non_assertion = match parent {
JsAnyAssignment::TsNonNullAssertionAssignment(_) => true,
_ => false,
};

if has_extra_non_assertion {
return Some(());
}
}
TsAnyNonNullAssertion::TsNonNullAssertionExpression(_) => {
let parent = node.parent::<JsAnyExpression>()?;

// Cases considered as invalid:
// - TsNonNullAssertionAssignment > TsNonNullAssertionExpression
// - TsNonNullAssertionExpression > TsNonNullAssertionExpression
// - JsCallExpression[optional] > TsNonNullAssertionExpression
// - JsStaticMemberExpression[optional] > TsNonNullAssertionExpression
let has_extra_non_assertion = match parent.omit_parentheses() {
JsAnyExpression::JsAssignmentExpression(expr) => expr
.left()
.ok()?
.as_js_any_assignment()?
.as_ts_non_null_assertion_assignment()
.is_some(),
JsAnyExpression::TsNonNullAssertionExpression(_) => true,
JsAnyExpression::JsStaticMemberExpression(expr) => expr.is_optional(),
JsAnyExpression::JsCallExpression(expr) => expr.is_optional(),
_ => false,
};

if has_extra_non_assertion {
return Some(());
}
}
}

None
Expand All @@ -83,7 +126,16 @@ impl Rule for NoExtraNonNullAssertion {
let mut mutation = ctx.root().begin();
let node = ctx.query();

mutation.remove_token(node.excl_token().ok()?);
let excl_token = match node {
TsAnyNonNullAssertion::TsNonNullAssertionAssignment(assignment) => {
assignment.excl_token().ok()?
}
TsAnyNonNullAssertion::TsNonNullAssertionExpression(expression) => {
expression.excl_token().ok()?
}
};

mutation.remove_token(excl_token);

Some(JsRuleAction {
category: ActionCategory::QuickFix,
Expand All @@ -93,28 +145,3 @@ impl Rule for NoExtraNonNullAssertion {
})
}
}

/// Verify if a given expression has an extra non-null assertion.
///
/// Cases considered as invalid:
/// - TsNonNullAssertionExpression > TsNonNullAssertionExpression
/// - JsCallExpression[optional] > TsNonNullAssertionExpression
/// - JsStaticMemberExpression[optional] > TsNonNullAssertionExpression
fn has_extra_non_null_assertion(expression: JsAnyExpression) -> Option<bool> {
match expression.omit_parentheses() {
JsAnyExpression::TsNonNullAssertionExpression(_) => return Some(true),
JsAnyExpression::JsStaticMemberExpression(static_member_exp) => {
if static_member_exp.is_optional() {
return Some(true);
}
}
JsAnyExpression::JsCallExpression(call_exp) => {
if call_exp.is_optional() {
return Some(true);
}
}
_ => {}
}

Some(false)
}
Original file line number Diff line number Diff line change
Expand Up @@ -38,3 +38,11 @@ case10!!.prop = null;
case11!?.[computedField];

case12!?.[a.b!!];

case13!!! = null

case14!! = null

if (case15!!) {}

if (!case16!!) {}
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,14 @@ case11!?.[computedField];

case12!?.[a.b!!];

case13!!! = null

case14!! = null

if (case15!!) {}

if (!case16!!) {}

```
# Diagnostics
Expand Down Expand Up @@ -260,6 +268,7 @@ invalid.ts:40:11 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━
> 40 │ case12!?.[a.b!!];
^^^^
41
42 │ case13!!! = null

i Safe fix: Remove extra non-null assertion.

Expand All @@ -268,4 +277,98 @@ invalid.ts:40:11 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━

```
```
invalid.ts:42:1 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

! Forbidden extra non-null assertion.

40 │ case12!?.[a.b!!];
41
> 42 │ case13!!! = null
^^^^^^^^
43
44 │ case14!! = null

i Safe fix: Remove extra non-null assertion.

42 │ case13!!!·=·null
-

```
```
invalid.ts:42:1 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

! Forbidden extra non-null assertion.

40 │ case12!?.[a.b!!];
41
> 42 │ case13!!! = null
^^^^^^^
43
44 │ case14!! = null

i Safe fix: Remove extra non-null assertion.

42 │ case13!!!·=·null
-

```
```
invalid.ts:44:1 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

! Forbidden extra non-null assertion.

42 │ case13!!! = null
43
> 44 │ case14!! = null
^^^^^^^
45
46if (case15!!) {}

i Safe fix: Remove extra non-null assertion.

44 │ case14!!·=·null
-

```
```
invalid.ts:46:5 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

! Forbidden extra non-null assertion.

44 │ case14!! = null
45
> 46if (case15!!) {}
^^^^^^^
47
48if (!case16!!) {}

i Safe fix: Remove extra non-null assertion.

46if·(case15!!)·{}
-

```
```
invalid.ts:48:6 lint/nursery/noExtraNonNullAssertion FIXABLE ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

! Forbidden extra non-null assertion.

46if (case15!!) {}
47
> 48if (!case16!!) {}
^^^^^^^
49

i Safe fix: Remove extra non-null assertion.

48if·(!case16!!)·{}
-

```

0 comments on commit 0fb3782

Please sign in to comment.