Skip to content

Commit 144036b

Browse files
committed
support if statement assignment
1 parent e800c2a commit 144036b

File tree

7 files changed

+717
-187
lines changed

7 files changed

+717
-187
lines changed

packages/eslint-plugin/docs/rules/prefer-nullish-coalescing.mdx

Lines changed: 52 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,54 @@ This rule reports when you may consider replacing:
1717
- An `||` operator with `??`
1818
- An `||=` operator with `??=`
1919
- Ternary expressions (`?:`) that are equivalent to `||` or `??` with `??`
20+
- Assignment expressions (`=`) that can be safely replaced by `??=`
21+
22+
## Examples
23+
24+
<Tabs>
25+
<TabItem value="❌ Incorrect">
26+
27+
```ts
28+
declare const a: string | null;
29+
declare const b: string | null;
30+
31+
const c = a || b;
32+
33+
declare let foo: { a: string } | null;
34+
declare function makeFoo(): { a: string };
35+
36+
function lazyInitializeFooByTruthiness() {
37+
if (!foo) {
38+
foo = makeFoo();
39+
}
40+
}
41+
42+
function lazyInitializeFooByNullCheck() {
43+
if (foo == null) {
44+
foo = makeFoo();
45+
}
46+
}
47+
```
48+
49+
</TabItem>
50+
<TabItem value="✅ Correct">
51+
52+
```ts
53+
declare const a: string | null;
54+
declare const b: string | null;
55+
56+
const c = a ?? b;
57+
58+
declare let foo: { a: string } | null;
59+
declare function makeFoo(): { a: string };
60+
61+
function lazyInitializeFoo() {
62+
foo ??= makeFoo();
63+
}
64+
```
65+
66+
</TabItem>
67+
</Tabs>
2068

2169
:::caution
2270
This rule will not work as expected if [`strictNullChecks`](https://www.typescriptlang.org/tsconfig#strictNullChecks) is not enabled.
@@ -84,7 +132,7 @@ Examples of code for this rule with `{ ignoreConditionalTests: false }`:
84132
<TabItem value="❌ Incorrect">
85133

86134
```ts option='{ "ignoreConditionalTests": false }'
87-
declare const a: string | null;
135+
declare let a: string | null;
88136
declare const b: string | null;
89137

90138
if (a || b) {
@@ -102,7 +150,7 @@ a || b ? true : false;
102150
<TabItem value="✅ Correct">
103151

104152
```ts option='{ "ignoreConditionalTests": false }'
105-
declare const a: string | null;
153+
declare let a: string | null;
106154
declare const b: string | null;
107155

108156
if (a ?? b) {
@@ -133,7 +181,7 @@ Examples of code for this rule with `{ ignoreMixedLogicalExpressions: false }`:
133181
<TabItem value="❌ Incorrect">
134182

135183
```ts option='{ "ignoreMixedLogicalExpressions": false }'
136-
declare const a: string | null;
184+
declare let a: string | null;
137185
declare const b: string | null;
138186
declare const c: string | null;
139187
declare const d: string | null;
@@ -149,7 +197,7 @@ a || (b && c && d);
149197
<TabItem value="✅ Correct">
150198

151199
```ts option='{ "ignoreMixedLogicalExpressions": false }'
152-
declare const a: string | null;
200+
declare let a: string | null;
153201
declare const b: string | null;
154202
declare const c: string | null;
155203
declare const d: string | null;

packages/eslint-plugin/src/rules/consistent-type-exports.ts

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -203,13 +203,11 @@ export default createRule<Options, MessageIds>({
203203
// Cache the first encountered exports for the package. We will need to come
204204
// back to these later when fixing the problems.
205205
if (node.exportKind === 'type') {
206-
if (sourceExports.typeOnlyNamedExport == null) {
207-
// The export is a type export
208-
sourceExports.typeOnlyNamedExport = node;
209-
}
210-
} else if (sourceExports.valueOnlyNamedExport == null) {
206+
// The export is a type export
207+
sourceExports.typeOnlyNamedExport ??= node;
208+
} else {
211209
// The export is a value export
212-
sourceExports.valueOnlyNamedExport = node;
210+
sourceExports.valueOnlyNamedExport ??= node;
213211
}
214212

215213
// Next for the current export, we will separate type/value specifiers.

packages/eslint-plugin/src/rules/no-unsafe-return.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -80,9 +80,7 @@ export default createRule({
8080
ts.isArrowFunction(functionTSNode)
8181
? getContextualType(checker, functionTSNode)
8282
: services.getTypeAtLocation(functionNode);
83-
if (!functionType) {
84-
functionType = services.getTypeAtLocation(functionNode);
85-
}
83+
functionType ??= services.getTypeAtLocation(functionNode);
8684
const callSignatures = tsutils.getCallSignaturesOfType(functionType);
8785
// If there is an explicit type annotation *and* that type matches the actual
8886
// function return type, we shouldn't complain (it's intentional, even if unsafe)

0 commit comments

Comments
 (0)