From 165b112d28abcdd5e2119cfbbc763646c24c1ce2 Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Fri, 13 Jan 2023 21:49:18 -0800 Subject: [PATCH 1/6] Add test cases --- ...lause(useunknownincatchvariables=false).js | 144 ++++++++++++++++++ ...(useunknownincatchvariables=false).symbols | 92 +++++++++++ ...se(useunknownincatchvariables=false).types | 102 +++++++++++++ ...Clause(useunknownincatchvariables=true).js | 144 ++++++++++++++++++ ...e(useunknownincatchvariables=true).symbols | 92 +++++++++++ ...use(useunknownincatchvariables=true).types | 102 +++++++++++++ .../cases/compiler/destructureCatchClause.ts | 38 +++++ 7 files changed, 714 insertions(+) create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types create mode 100644 tests/cases/compiler/destructureCatchClause.ts diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js new file mode 100644 index 0000000000000..6ac0c8e21b1ff --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js @@ -0,0 +1,144 @@ +//// [destructureCatchClause.ts] +try {} catch ({ x }) { x } +try {} catch ([ x ]) { x } + +try {} catch ({ a: { x } }) { x } +try {} catch ({ a: [ x ] }) { x } + +try {} catch ([{ x }]) { x } +try {} catch ([[ x ]]) { x } + +try {} catch ({ a: { b: { c: { x }} }}) { x } + + +try {} catch ({ x }: any) { x } +try {} catch ([ x ]: any) { x } + +try {} catch ({ a: { x } }: any) { x } +try {} catch ({ a: [ x ] }: any) { x } + +try {} catch ([{ x }]: any) { x } +try {} catch ([[ x ]]: any) { x } + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + +try {} catch ({ x }: unknown) { x } +try {} catch ([ x ]: unknown) { x } + +try {} catch ({ a: { x } }: unknown) { x } +try {} catch ({ a: [ x ] }: unknown) { x } + +try {} catch ([{ x }]: unknown) { x } +try {} catch ([[ x ]]: unknown) { x } + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + + +//// [destructureCatchClause.js] +"use strict"; +try { } +catch (_a) { + var x = _a.x; + x; +} +try { } +catch (_b) { + var x = _b[0]; + x; +} +try { } +catch (_c) { + var x = _c.a.x; + x; +} +try { } +catch (_d) { + var x = _d.a[0]; + x; +} +try { } +catch (_e) { + var x = _e[0].x; + x; +} +try { } +catch (_f) { + var x = _f[0][0]; + x; +} +try { } +catch (_g) { + var x = _g.a.b.c.x; + x; +} +try { } +catch (_h) { + var x = _h.x; + x; +} +try { } +catch (_j) { + var x = _j[0]; + x; +} +try { } +catch (_k) { + var x = _k.a.x; + x; +} +try { } +catch (_l) { + var x = _l.a[0]; + x; +} +try { } +catch (_m) { + var x = _m[0].x; + x; +} +try { } +catch (_o) { + var x = _o[0][0]; + x; +} +try { } +catch (_p) { + var x = _p.a.b.c.x; + x; +} +try { } +catch (_q) { + var x = _q.x; + x; +} +try { } +catch (_r) { + var x = _r[0]; + x; +} +try { } +catch (_s) { + var x = _s.a.x; + x; +} +try { } +catch (_t) { + var x = _t.a[0]; + x; +} +try { } +catch (_u) { + var x = _u[0].x; + x; +} +try { } +catch (_v) { + var x = _v[0][0]; + x; +} +try { } +catch (_w) { + var x = _w.a.b.c.x; + x; +} diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols new file mode 100644 index 0000000000000..7114b11b24fa2 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols @@ -0,0 +1,92 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +try {} catch ({ x }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) + +try {} catch ([ x ]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) + +try {} catch ({ a: { x } }) { x } +>a : Symbol(a) +>x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) + +try {} catch ({ a: [ x ] }) { x } +>a : Symbol(a) +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) + +try {} catch ([{ x }]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) + +try {} catch ([[ x ]]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>a : Symbol(a) +>b : Symbol(b) +>c : Symbol(c) +>x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) + + +try {} catch ({ x }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) + +try {} catch ([ x ]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) + +try {} catch ({ a: { x } }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) + +try {} catch ({ a: [ x ] }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) + +try {} catch ([{ x }]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) + +try {} catch ([[ x ]]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) + + +try {} catch ({ x }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) + +try {} catch ([ x ]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) + +try {} catch ({ a: { x } }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) + +try {} catch ({ a: [ x ] }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) + +try {} catch ([{ x }]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) + +try {} catch ([[ x ]]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) + diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types new file mode 100644 index 0000000000000..86440ea0482e8 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types @@ -0,0 +1,102 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +try {} catch ({ x }) { x } +>x : any +>x : any + +try {} catch ([ x ]) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]) { x } +>x : any +>x : any + +try {} catch ([[ x ]]) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + + +try {} catch ({ x }: any) { x } +>x : any +>x : any + +try {} catch ([ x ]: any) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }: any) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }: any) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]: any) { x } +>x : any +>x : any + +try {} catch ([[ x ]]: any) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + + +try {} catch ({ x }: unknown) { x } +>x : any +>x : any + +try {} catch ([ x ]: unknown) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }: unknown) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }: unknown) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]: unknown) { x } +>x : any +>x : any + +try {} catch ([[ x ]]: unknown) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js new file mode 100644 index 0000000000000..6ac0c8e21b1ff --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js @@ -0,0 +1,144 @@ +//// [destructureCatchClause.ts] +try {} catch ({ x }) { x } +try {} catch ([ x ]) { x } + +try {} catch ({ a: { x } }) { x } +try {} catch ({ a: [ x ] }) { x } + +try {} catch ([{ x }]) { x } +try {} catch ([[ x ]]) { x } + +try {} catch ({ a: { b: { c: { x }} }}) { x } + + +try {} catch ({ x }: any) { x } +try {} catch ([ x ]: any) { x } + +try {} catch ({ a: { x } }: any) { x } +try {} catch ({ a: [ x ] }: any) { x } + +try {} catch ([{ x }]: any) { x } +try {} catch ([[ x ]]: any) { x } + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + +try {} catch ({ x }: unknown) { x } +try {} catch ([ x ]: unknown) { x } + +try {} catch ({ a: { x } }: unknown) { x } +try {} catch ({ a: [ x ] }: unknown) { x } + +try {} catch ([{ x }]: unknown) { x } +try {} catch ([[ x ]]: unknown) { x } + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + + +//// [destructureCatchClause.js] +"use strict"; +try { } +catch (_a) { + var x = _a.x; + x; +} +try { } +catch (_b) { + var x = _b[0]; + x; +} +try { } +catch (_c) { + var x = _c.a.x; + x; +} +try { } +catch (_d) { + var x = _d.a[0]; + x; +} +try { } +catch (_e) { + var x = _e[0].x; + x; +} +try { } +catch (_f) { + var x = _f[0][0]; + x; +} +try { } +catch (_g) { + var x = _g.a.b.c.x; + x; +} +try { } +catch (_h) { + var x = _h.x; + x; +} +try { } +catch (_j) { + var x = _j[0]; + x; +} +try { } +catch (_k) { + var x = _k.a.x; + x; +} +try { } +catch (_l) { + var x = _l.a[0]; + x; +} +try { } +catch (_m) { + var x = _m[0].x; + x; +} +try { } +catch (_o) { + var x = _o[0][0]; + x; +} +try { } +catch (_p) { + var x = _p.a.b.c.x; + x; +} +try { } +catch (_q) { + var x = _q.x; + x; +} +try { } +catch (_r) { + var x = _r[0]; + x; +} +try { } +catch (_s) { + var x = _s.a.x; + x; +} +try { } +catch (_t) { + var x = _t.a[0]; + x; +} +try { } +catch (_u) { + var x = _u[0].x; + x; +} +try { } +catch (_v) { + var x = _v[0][0]; + x; +} +try { } +catch (_w) { + var x = _w.a.b.c.x; + x; +} diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols new file mode 100644 index 0000000000000..7114b11b24fa2 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols @@ -0,0 +1,92 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +try {} catch ({ x }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) + +try {} catch ([ x ]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) + +try {} catch ({ a: { x } }) { x } +>a : Symbol(a) +>x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) + +try {} catch ({ a: [ x ] }) { x } +>a : Symbol(a) +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) + +try {} catch ([{ x }]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) + +try {} catch ([[ x ]]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>a : Symbol(a) +>b : Symbol(b) +>c : Symbol(c) +>x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) + + +try {} catch ({ x }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) + +try {} catch ([ x ]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) + +try {} catch ({ a: { x } }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) + +try {} catch ({ a: [ x ] }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) + +try {} catch ([{ x }]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) + +try {} catch ([[ x ]]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) + + +try {} catch ({ x }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) + +try {} catch ([ x ]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) + +try {} catch ({ a: { x } }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) + +try {} catch ({ a: [ x ] }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) + +try {} catch ([{ x }]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) + +try {} catch ([[ x ]]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) + diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types new file mode 100644 index 0000000000000..e05619e7269a0 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types @@ -0,0 +1,102 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +try {} catch ({ x }) { x } +>x : unknown +>x : unknown + +try {} catch ([ x ]) { x } +>x : unknown +>x : unknown + +try {} catch ({ a: { x } }) { x } +>a : any +>x : unknown +>x : unknown + +try {} catch ({ a: [ x ] }) { x } +>a : any +>x : unknown +>x : unknown + +try {} catch ([{ x }]) { x } +>x : unknown +>x : unknown + +try {} catch ([[ x ]]) { x } +>x : unknown +>x : unknown + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>a : any +>b : any +>c : any +>x : unknown +>x : unknown + + +try {} catch ({ x }: any) { x } +>x : unknown +>x : unknown + +try {} catch ([ x ]: any) { x } +>x : unknown +>x : unknown + +try {} catch ({ a: { x } }: any) { x } +>a : any +>x : unknown +>x : unknown + +try {} catch ({ a: [ x ] }: any) { x } +>a : any +>x : unknown +>x : unknown + +try {} catch ([{ x }]: any) { x } +>x : unknown +>x : unknown + +try {} catch ([[ x ]]: any) { x } +>x : unknown +>x : unknown + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>a : any +>b : any +>c : any +>x : unknown +>x : unknown + + +try {} catch ({ x }: unknown) { x } +>x : unknown +>x : unknown + +try {} catch ([ x ]: unknown) { x } +>x : unknown +>x : unknown + +try {} catch ({ a: { x } }: unknown) { x } +>a : any +>x : unknown +>x : unknown + +try {} catch ({ a: [ x ] }: unknown) { x } +>a : any +>x : unknown +>x : unknown + +try {} catch ([{ x }]: unknown) { x } +>x : unknown +>x : unknown + +try {} catch ([[ x ]]: unknown) { x } +>x : unknown +>x : unknown + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>a : any +>b : any +>c : any +>x : unknown +>x : unknown + diff --git a/tests/cases/compiler/destructureCatchClause.ts b/tests/cases/compiler/destructureCatchClause.ts new file mode 100644 index 0000000000000..cb82ea54b4d68 --- /dev/null +++ b/tests/cases/compiler/destructureCatchClause.ts @@ -0,0 +1,38 @@ +// @strict: true +// @useUnknownInCatchVariables: true, false + + +try {} catch ({ x }) { x } +try {} catch ([ x ]) { x } + +try {} catch ({ a: { x } }) { x } +try {} catch ({ a: [ x ] }) { x } + +try {} catch ([{ x }]) { x } +try {} catch ([[ x ]]) { x } + +try {} catch ({ a: { b: { c: { x }} }}) { x } + + +try {} catch ({ x }: any) { x } +try {} catch ([ x ]: any) { x } + +try {} catch ({ a: { x } }: any) { x } +try {} catch ({ a: [ x ] }: any) { x } + +try {} catch ([{ x }]: any) { x } +try {} catch ([[ x ]]: any) { x } + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + +try {} catch ({ x }: unknown) { x } +try {} catch ([ x ]: unknown) { x } + +try {} catch ({ a: { x } }: unknown) { x } +try {} catch ({ a: [ x ] }: unknown) { x } + +try {} catch ([{ x }]: unknown) { x } +try {} catch ([[ x ]]: unknown) { x } + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } From f877b232b0e8cdeaf90e47d90516967dced8a0c2 Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Fri, 13 Jan 2023 22:53:59 -0800 Subject: [PATCH 2/6] Treat catch clauses the same as other variable declarations --- src/compiler/checker.ts | 25 +++--- .../catchClauseWithTypeAnnotation.errors.txt | 12 ++- .../catchClauseWithTypeAnnotation.js | 8 +- .../catchClauseWithTypeAnnotation.symbols | 4 +- .../catchClauseWithTypeAnnotation.types | 4 +- ...eunknownincatchvariables=false).errors.txt | 60 +++++++++++++ ...lause(useunknownincatchvariables=false).js | 2 + ...(useunknownincatchvariables=false).symbols | 90 +++++++++---------- ...se(useunknownincatchvariables=false).types | 1 + ...seunknownincatchvariables=true).errors.txt | 81 +++++++++++++++++ ...Clause(useunknownincatchvariables=true).js | 2 + ...e(useunknownincatchvariables=true).symbols | 90 +++++++++---------- ...use(useunknownincatchvariables=true).types | 85 +++++++++--------- .../reference/destructuringCatch.symbols | 1 - ...ocCatchClauseWithTypeAnnotation.errors.txt | 12 ++- .../jsdocCatchClauseWithTypeAnnotation.js | 8 +- ...jsdocCatchClauseWithTypeAnnotation.symbols | 4 +- .../jsdocCatchClauseWithTypeAnnotation.types | 4 +- .../redeclareParameterInCatchBlock.symbols | 2 - .../cases/compiler/destructureCatchClause.ts | 2 +- .../jsdocCatchClauseWithTypeAnnotation.ts | 4 +- .../catchClauseWithTypeAnnotation.ts | 4 +- 22 files changed, 327 insertions(+), 178 deletions(-) create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).errors.txt create mode 100644 tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).errors.txt diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 3f4d60657e404..67ee06ee08e41 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10205,7 +10205,16 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { const isOptional = includeOptionality && isOptionalDeclaration(declaration); // Use type from type annotation if one is present - const declaredType = tryGetTypeFromEffectiveTypeNode(declaration); + let declaredType = tryGetTypeFromEffectiveTypeNode(declaration); + if (isCatchClauseVariableDeclarationOrBindingElement(declaration)) { + if (declaredType) { + // If the catch clause is explicitly annotated with any or unknown, accept it, otherwise error. + return isTypeAny(declaredType) || declaredType === unknownType ? declaredType : errorType; + } + // If the catch clause is not explicitly annotated, treat it as though it were explicitly + // annotated with unknown or any, depending on useUnknownInCatchVariables. + declaredType = useUnknownInCatchVariables ? unknownType : anyType; + } if (declaredType) { return addOptionality(declaredType, isProperty, isOptional); } @@ -10867,15 +10876,6 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { // Handle catch clause variables Debug.assertIsDefined(symbol.valueDeclaration); const declaration = symbol.valueDeclaration; - if (isCatchClauseVariableDeclarationOrBindingElement(declaration)) { - const typeNode = getEffectiveTypeAnnotationNode(declaration); - if (typeNode === undefined) { - return useUnknownInCatchVariables ? unknownType : anyType; - } - const type = getTypeOfNode(typeNode); - // an errorType will make `checkTryStatement` issue an error - return isTypeAny(type) || type === unknownType ? type : errorType; - } // Handle export default expressions if (isSourceFile(declaration) && isJsonSourceFile(declaration)) { if (!declaration.statements.length) { @@ -41178,9 +41178,10 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { // Grammar checking if (catchClause.variableDeclaration) { const declaration = catchClause.variableDeclaration; - const typeNode = getEffectiveTypeAnnotationNode(getRootDeclaration(declaration)); + checkVariableLikeDeclaration(declaration); + const typeNode = getEffectiveTypeAnnotationNode(declaration); if (typeNode) { - const type = getTypeForVariableLikeDeclaration(declaration, /*includeOptionality*/ false, CheckMode.Normal); + const type = getTypeFromTypeNode(typeNode); if (type && !(type.flags & TypeFlags.AnyOrUnknown)) { grammarErrorOnFirstToken(typeNode, Diagnostics.Catch_clause_variable_type_annotation_must_be_any_or_unknown_if_specified); } diff --git a/tests/baselines/reference/catchClauseWithTypeAnnotation.errors.txt b/tests/baselines/reference/catchClauseWithTypeAnnotation.errors.txt index 870a7cf87080a..0ab7fa4399a94 100644 --- a/tests/baselines/reference/catchClauseWithTypeAnnotation.errors.txt +++ b/tests/baselines/reference/catchClauseWithTypeAnnotation.errors.txt @@ -4,11 +4,13 @@ tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.t tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(20,23): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(29,29): error TS2492: Cannot redeclare identifier 'x' in catch clause. tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(30,29): error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type 'boolean', but here has type 'string'. +tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(36,22): error TS2339: Property 'x' does not exist on type '{}'. +tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(37,22): error TS2339: Property 'x' does not exist on type '{}'. tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(38,27): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts(39,27): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. -==== tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts (8 errors) ==== +==== tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts (10 errors) ==== type any1 = any; type unknown1 = unknown; @@ -57,8 +59,12 @@ tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.t try { } catch ({ x }) { } // should be OK try { } catch ({ x }: any) { x.foo; } // should be OK try { } catch ({ x }: any1) { x.foo;} // should be OK - try { } catch ({ x }: unknown) { console.log(x); } // should be OK - try { } catch ({ x }: unknown1) { console.log(x); } // should be OK + try { } catch ({ x }: unknown) { console.log(x); } // error in the destructure + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. + try { } catch ({ x }: unknown1) { console.log(x); } // error in the destructure + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. try { } catch ({ x }: object) { } // error in the type ~~~~~~ !!! error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. diff --git a/tests/baselines/reference/catchClauseWithTypeAnnotation.js b/tests/baselines/reference/catchClauseWithTypeAnnotation.js index 0337d65b43713..06de0b2667287 100644 --- a/tests/baselines/reference/catchClauseWithTypeAnnotation.js +++ b/tests/baselines/reference/catchClauseWithTypeAnnotation.js @@ -34,8 +34,8 @@ function fn(x: boolean) { try { } catch ({ x }) { } // should be OK try { } catch ({ x }: any) { x.foo; } // should be OK try { } catch ({ x }: any1) { x.foo;} // should be OK - try { } catch ({ x }: unknown) { console.log(x); } // should be OK - try { } catch ({ x }: unknown1) { console.log(x); } // should be OK + try { } catch ({ x }: unknown) { console.log(x); } // error in the destructure + try { } catch ({ x }: unknown1) { console.log(x); } // error in the destructure try { } catch ({ x }: object) { } // error in the type try { } catch ({ x }: Error) { } // error in the type } @@ -124,12 +124,12 @@ function fn(x) { catch (_d) { var x_5 = _d.x; console.log(x_5); - } // should be OK + } // error in the destructure try { } catch (_e) { var x_6 = _e.x; console.log(x_6); - } // should be OK + } // error in the destructure try { } catch (_f) { var x_7 = _f.x; diff --git a/tests/baselines/reference/catchClauseWithTypeAnnotation.symbols b/tests/baselines/reference/catchClauseWithTypeAnnotation.symbols index 08eaec37b70e9..062d98db83d8b 100644 --- a/tests/baselines/reference/catchClauseWithTypeAnnotation.symbols +++ b/tests/baselines/reference/catchClauseWithTypeAnnotation.symbols @@ -112,14 +112,14 @@ function fn(x: boolean) { >any1 : Symbol(any1, Decl(catchClauseWithTypeAnnotation.ts, 0, 0)) >x : Symbol(x, Decl(catchClauseWithTypeAnnotation.ts, 34, 20)) - try { } catch ({ x }: unknown) { console.log(x); } // should be OK + try { } catch ({ x }: unknown) { console.log(x); } // error in the destructure >x : Symbol(x, Decl(catchClauseWithTypeAnnotation.ts, 35, 20)) >console.log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --)) >console : Symbol(console, Decl(lib.dom.d.ts, --, --)) >log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --)) >x : Symbol(x, Decl(catchClauseWithTypeAnnotation.ts, 35, 20)) - try { } catch ({ x }: unknown1) { console.log(x); } // should be OK + try { } catch ({ x }: unknown1) { console.log(x); } // error in the destructure >x : Symbol(x, Decl(catchClauseWithTypeAnnotation.ts, 36, 20)) >unknown1 : Symbol(unknown1, Decl(catchClauseWithTypeAnnotation.ts, 0, 16)) >console.log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --)) diff --git a/tests/baselines/reference/catchClauseWithTypeAnnotation.types b/tests/baselines/reference/catchClauseWithTypeAnnotation.types index d0de759bbbd79..03eb73cfd268e 100644 --- a/tests/baselines/reference/catchClauseWithTypeAnnotation.types +++ b/tests/baselines/reference/catchClauseWithTypeAnnotation.types @@ -126,7 +126,7 @@ function fn(x: boolean) { >x : any >foo : any - try { } catch ({ x }: unknown) { console.log(x); } // should be OK + try { } catch ({ x }: unknown) { console.log(x); } // error in the destructure >x : any >console.log(x) : void >console.log : (...data: any[]) => void @@ -134,7 +134,7 @@ function fn(x: boolean) { >log : (...data: any[]) => void >x : any - try { } catch ({ x }: unknown1) { console.log(x); } // should be OK + try { } catch ({ x }: unknown1) { console.log(x); } // error in the destructure >x : any >console.log(x) : void >console.log : (...data: any[]) => void diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).errors.txt b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).errors.txt new file mode 100644 index 0000000000000..4abdc153ef7f3 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).errors.txt @@ -0,0 +1,60 @@ +tests/cases/compiler/destructureCatchClause.ts(26,17): error TS2339: Property 'x' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(27,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(29,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(30,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(32,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(33,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(35,17): error TS2339: Property 'a' does not exist on type 'unknown'. + + +==== tests/cases/compiler/destructureCatchClause.ts (7 errors) ==== + // These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. + try {} catch ({ x }) { x } + try {} catch ([ x ]) { x } + + try {} catch ({ a: { x } }) { x } + try {} catch ({ a: [ x ] }) { x } + + try {} catch ([{ x }]) { x } + try {} catch ([[ x ]]) { x } + + try {} catch ({ a: { b: { c: { x }} }}) { x } + + + try {} catch ({ x }: any) { x } + try {} catch ([ x ]: any) { x } + + try {} catch ({ a: { x } }: any) { x } + try {} catch ({ a: [ x ] }: any) { x } + + try {} catch ([{ x }]: any) { x } + try {} catch ([[ x ]]: any) { x } + + try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + + try {} catch ({ x }: unknown) { x } + ~ +!!! error TS2339: Property 'x' does not exist on type 'unknown'. + try {} catch ([ x ]: unknown) { x } + ~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { x } }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + try {} catch ({ a: [ x ] }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + + try {} catch ([{ x }]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + try {} catch ([[ x ]]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + \ No newline at end of file diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js index 6ac0c8e21b1ff..3bc5c8c19a1ed 100644 --- a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js @@ -1,4 +1,5 @@ //// [destructureCatchClause.ts] +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } try {} catch ([ x ]) { x } @@ -37,6 +38,7 @@ try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } //// [destructureCatchClause.js] "use strict"; +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try { } catch (_a) { var x = _a.x; diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols index 7114b11b24fa2..2960cf2258d0a 100644 --- a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols @@ -1,92 +1,88 @@ === tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) - -try {} catch ([ x ]) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) >x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) -try {} catch ({ a: { x } }) { x } ->a : Symbol(a) ->x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) +try {} catch ([ x ]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) -try {} catch ({ a: [ x ] }) { x } ->a : Symbol(a) +try {} catch ({ a: { x } }) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) >x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) -try {} catch ([{ x }]) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) +try {} catch ({ a: [ x ] }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) -try {} catch ([[ x ]]) { x } +try {} catch ([{ x }]) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) >x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) +try {} catch ([[ x ]]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) + try {} catch ({ a: { b: { c: { x }} }}) { x } ->a : Symbol(a) ->b : Symbol(b) ->c : Symbol(c) ->x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) try {} catch ({ x }: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) - -try {} catch ([ x ]: any) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) >x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) -try {} catch ({ a: { x } }: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) +try {} catch ([ x ]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) -try {} catch ({ a: [ x ] }: any) { x } +try {} catch ({ a: { x } }: any) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) >x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) -try {} catch ([{ x }]: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) +try {} catch ({ a: [ x ] }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) -try {} catch ([[ x ]]: any) { x } +try {} catch ([{ x }]: any) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) >x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) +try {} catch ([[ x ]]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) + try {} catch ({ a: { b: { c: { x }} }}: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) try {} catch ({ x }: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) - -try {} catch ([ x ]: unknown) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) >x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) -try {} catch ({ a: { x } }: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) +try {} catch ([ x ]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) -try {} catch ({ a: [ x ] }: unknown) { x } +try {} catch ({ a: { x } }: unknown) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) >x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) -try {} catch ([{ x }]: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) +try {} catch ({ a: [ x ] }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) -try {} catch ([[ x ]]: unknown) { x } +try {} catch ([{ x }]: unknown) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) >x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) +try {} catch ([[ x ]]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) + try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types index 86440ea0482e8..4dd4691a22d4b 100644 --- a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types @@ -1,4 +1,5 @@ === tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } >x : any >x : any diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).errors.txt b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).errors.txt new file mode 100644 index 0000000000000..e4bde57c99f32 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).errors.txt @@ -0,0 +1,81 @@ +tests/cases/compiler/destructureCatchClause.ts(2,17): error TS2339: Property 'x' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(3,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(5,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(6,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(8,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(9,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(11,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(26,17): error TS2339: Property 'x' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(27,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(29,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(30,17): error TS2339: Property 'a' does not exist on type 'unknown'. +tests/cases/compiler/destructureCatchClause.ts(32,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(33,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(35,17): error TS2339: Property 'a' does not exist on type 'unknown'. + + +==== tests/cases/compiler/destructureCatchClause.ts (14 errors) ==== + // These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. + try {} catch ({ x }) { x } + ~ +!!! error TS2339: Property 'x' does not exist on type 'unknown'. + try {} catch ([ x ]) { x } + ~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { x } }) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + try {} catch ({ a: [ x ] }) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + + try {} catch ([{ x }]) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + try {} catch ([[ x ]]) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { b: { c: { x }} }}) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + + + try {} catch ({ x }: any) { x } + try {} catch ([ x ]: any) { x } + + try {} catch ({ a: { x } }: any) { x } + try {} catch ({ a: [ x ] }: any) { x } + + try {} catch ([{ x }]: any) { x } + try {} catch ([[ x ]]: any) { x } + + try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + + try {} catch ({ x }: unknown) { x } + ~ +!!! error TS2339: Property 'x' does not exist on type 'unknown'. + try {} catch ([ x ]: unknown) { x } + ~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { x } }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + try {} catch ({ a: [ x ] }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + + try {} catch ([{ x }]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + try {} catch ([[ x ]]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type 'unknown'. + \ No newline at end of file diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js index 6ac0c8e21b1ff..3bc5c8c19a1ed 100644 --- a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js @@ -1,4 +1,5 @@ //// [destructureCatchClause.ts] +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } try {} catch ([ x ]) { x } @@ -37,6 +38,7 @@ try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } //// [destructureCatchClause.js] "use strict"; +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try { } catch (_a) { var x = _a.x; diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols index 7114b11b24fa2..2960cf2258d0a 100644 --- a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols @@ -1,92 +1,88 @@ === tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 0, 15)) - -try {} catch ([ x ]) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) >x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) -try {} catch ({ a: { x } }) { x } ->a : Symbol(a) ->x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 3, 20)) +try {} catch ([ x ]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) -try {} catch ({ a: [ x ] }) { x } ->a : Symbol(a) +try {} catch ({ a: { x } }) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) >x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) -try {} catch ([{ x }]) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 6, 16)) +try {} catch ({ a: [ x ] }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) -try {} catch ([[ x ]]) { x } +try {} catch ([{ x }]) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) >x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) +try {} catch ([[ x ]]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) + try {} catch ({ a: { b: { c: { x }} }}) { x } ->a : Symbol(a) ->b : Symbol(b) ->c : Symbol(c) ->x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 9, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) try {} catch ({ x }: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 12, 15)) - -try {} catch ([ x ]: any) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) >x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) -try {} catch ({ a: { x } }: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 15, 20)) +try {} catch ([ x ]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) -try {} catch ({ a: [ x ] }: any) { x } +try {} catch ({ a: { x } }: any) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) >x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) -try {} catch ([{ x }]: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 18, 16)) +try {} catch ({ a: [ x ] }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) -try {} catch ([[ x ]]: any) { x } +try {} catch ([{ x }]: any) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) >x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) +try {} catch ([[ x ]]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) + try {} catch ({ a: { b: { c: { x }} }}: any) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 21, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) try {} catch ({ x }: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 24, 15)) - -try {} catch ([ x ]: unknown) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) >x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) -try {} catch ({ a: { x } }: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 27, 20)) +try {} catch ([ x ]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) -try {} catch ({ a: [ x ] }: unknown) { x } +try {} catch ({ a: { x } }: unknown) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) >x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) -try {} catch ([{ x }]: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 30, 16)) +try {} catch ({ a: [ x ] }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) -try {} catch ([[ x ]]: unknown) { x } +try {} catch ([{ x }]: unknown) { x } >x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) >x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) +try {} catch ([[ x ]]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) + try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } ->x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) ->x : Symbol(x, Decl(destructureCatchClause.ts, 33, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types index e05619e7269a0..4dd4691a22d4b 100644 --- a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types +++ b/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types @@ -1,102 +1,103 @@ === tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([ x ]) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: { x } }) { x } >a : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: [ x ] }) { x } >a : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([{ x }]) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([[ x ]]) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: { b: { c: { x }} }}) { x } >a : any >b : any >c : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ x }: any) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([ x ]: any) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: { x } }: any) { x } >a : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: [ x ] }: any) { x } >a : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([{ x }]: any) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([[ x ]]: any) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: { b: { c: { x }} }}: any) { x } >a : any >b : any >c : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ x }: unknown) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([ x ]: unknown) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: { x } }: unknown) { x } >a : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: [ x ] }: unknown) { x } >a : any ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([{ x }]: unknown) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ([[ x ]]: unknown) { x } ->x : unknown ->x : unknown +>x : any +>x : any try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } >a : any >b : any >c : any ->x : unknown ->x : unknown +>x : any +>x : any diff --git a/tests/baselines/reference/destructuringCatch.symbols b/tests/baselines/reference/destructuringCatch.symbols index a78beb8d776de..d11e899fa67a6 100644 --- a/tests/baselines/reference/destructuringCatch.symbols +++ b/tests/baselines/reference/destructuringCatch.symbols @@ -31,7 +31,6 @@ try { >z : Symbol(z, Decl(destructuringCatch.ts, 15, 20)) } catch ([{x: [y], z}]) { ->x : Symbol(x) >y : Symbol(y, Decl(destructuringCatch.ts, 17, 13)) >z : Symbol(z, Decl(destructuringCatch.ts, 17, 16)) diff --git a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.errors.txt b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.errors.txt index ee77d6e3decb9..d79c2ef44fae0 100644 --- a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.errors.txt +++ b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.errors.txt @@ -3,11 +3,13 @@ tests/cases/conformance/jsdoc/foo.js(21,54): error TS2339: Property 'foo' does n tests/cases/conformance/jsdoc/foo.js(22,31): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. tests/cases/conformance/jsdoc/foo.js(23,31): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. tests/cases/conformance/jsdoc/foo.js(35,7): error TS2492: Cannot redeclare identifier 'err' in catch clause. +tests/cases/conformance/jsdoc/foo.js(46,45): error TS2339: Property 'x' does not exist on type '{}'. +tests/cases/conformance/jsdoc/foo.js(47,45): error TS2339: Property 'x' does not exist on type '{}'. tests/cases/conformance/jsdoc/foo.js(48,31): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. tests/cases/conformance/jsdoc/foo.js(49,31): error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. -==== tests/cases/conformance/jsdoc/foo.js (7 errors) ==== +==== tests/cases/conformance/jsdoc/foo.js (9 errors) ==== /** * @typedef {any} Any */ @@ -63,8 +65,12 @@ tests/cases/conformance/jsdoc/foo.js(49,31): error TS1196: Catch clause variable try { } catch ({ x }) { } // should be OK try { } catch (/** @type {any} */ { x }) { x.foo; } // should be OK try { } catch (/** @type {Any} */ { x }) { x.foo;} // should be OK - try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // should be OK - try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // error in the destructure + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. + try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // error in the destructure + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. try { } catch (/** @type {Error} */ { x }) { } // error in the type ~~~~~ !!! error TS1196: Catch clause variable type annotation must be 'any' or 'unknown' if specified. diff --git a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.js b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.js index ce948d9011690..a40d78cc084d0 100644 --- a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.js +++ b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.js @@ -44,8 +44,8 @@ function fn() { try { } catch ({ x }) { } // should be OK try { } catch (/** @type {any} */ { x }) { x.foo; } // should be OK try { } catch (/** @type {Any} */ { x }) { x.foo;} // should be OK - try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // should be OK - try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // error in the destructure + try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // error in the destructure try { } catch (/** @type {Error} */ { x }) { } // error in the type try { } catch (/** @type {object} */ { x }) { } // error in the type } @@ -132,11 +132,11 @@ function fn() { try { } catch ( /** @type {unknown} */{ x }) { console.log(x); - } // should be OK + } // error in the destructure try { } catch ( /** @type {Unknown} */{ x }) { console.log(x); - } // should be OK + } // error in the destructure try { } catch ( /** @type {Error} */{ x }) { } // error in the type try { } diff --git a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.symbols b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.symbols index 5b722006126c2..f6758e368eb11 100644 --- a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.symbols +++ b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.symbols @@ -110,14 +110,14 @@ function fn() { >x : Symbol(x, Decl(foo.js, 44, 39)) >x : Symbol(x, Decl(foo.js, 44, 39)) - try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // error in the destructure >x : Symbol(x, Decl(foo.js, 45, 43)) >console.log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --)) >console : Symbol(console, Decl(lib.dom.d.ts, --, --)) >log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --)) >x : Symbol(x, Decl(foo.js, 45, 43)) - try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // error in the destructure >x : Symbol(x, Decl(foo.js, 46, 43)) >console.log : Symbol(Console.log, Decl(lib.dom.d.ts, --, --)) >console : Symbol(console, Decl(lib.dom.d.ts, --, --)) diff --git a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.types b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.types index f79e074df4cc2..ef4af916177b4 100644 --- a/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.types +++ b/tests/baselines/reference/jsdocCatchClauseWithTypeAnnotation.types @@ -131,7 +131,7 @@ function fn() { >x : any >foo : any - try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // error in the destructure >x : any >console.log(x) : void >console.log : (...data: any[]) => void @@ -139,7 +139,7 @@ function fn() { >log : (...data: any[]) => void >x : any - try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // error in the destructure >x : any >console.log(x) : void >console.log : (...data: any[]) => void diff --git a/tests/baselines/reference/redeclareParameterInCatchBlock.symbols b/tests/baselines/reference/redeclareParameterInCatchBlock.symbols index 8885cf240e5b0..2ac579f8b990d 100644 --- a/tests/baselines/reference/redeclareParameterInCatchBlock.symbols +++ b/tests/baselines/reference/redeclareParameterInCatchBlock.symbols @@ -31,9 +31,7 @@ try { try { } catch ({ a: x, b: x }) { ->a : Symbol(a) >x : Symbol(x, Decl(redeclareParameterInCatchBlock.ts, 20, 10)) ->b : Symbol(b) >x : Symbol(x, Decl(redeclareParameterInCatchBlock.ts, 20, 16)) } diff --git a/tests/cases/compiler/destructureCatchClause.ts b/tests/cases/compiler/destructureCatchClause.ts index cb82ea54b4d68..8fd33a665c3ab 100644 --- a/tests/cases/compiler/destructureCatchClause.ts +++ b/tests/cases/compiler/destructureCatchClause.ts @@ -1,7 +1,7 @@ // @strict: true // @useUnknownInCatchVariables: true, false - +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. try {} catch ({ x }) { x } try {} catch ([ x ]) { x } diff --git a/tests/cases/conformance/jsdoc/jsdocCatchClauseWithTypeAnnotation.ts b/tests/cases/conformance/jsdoc/jsdocCatchClauseWithTypeAnnotation.ts index 1b9982073f2ec..b47776eb1d9c4 100644 --- a/tests/cases/conformance/jsdoc/jsdocCatchClauseWithTypeAnnotation.ts +++ b/tests/cases/conformance/jsdoc/jsdocCatchClauseWithTypeAnnotation.ts @@ -50,8 +50,8 @@ function fn() { try { } catch ({ x }) { } // should be OK try { } catch (/** @type {any} */ { x }) { x.foo; } // should be OK try { } catch (/** @type {Any} */ { x }) { x.foo;} // should be OK - try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // should be OK - try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // should be OK + try { } catch (/** @type {unknown} */ { x }) { console.log(x); } // error in the destructure + try { } catch (/** @type {Unknown} */ { x }) { console.log(x); } // error in the destructure try { } catch (/** @type {Error} */ { x }) { } // error in the type try { } catch (/** @type {object} */ { x }) { } // error in the type } diff --git a/tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts b/tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts index d7517e021d1fc..6f3bd6a4c15db 100644 --- a/tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts +++ b/tests/cases/conformance/statements/tryStatements/catchClauseWithTypeAnnotation.ts @@ -33,8 +33,8 @@ function fn(x: boolean) { try { } catch ({ x }) { } // should be OK try { } catch ({ x }: any) { x.foo; } // should be OK try { } catch ({ x }: any1) { x.foo;} // should be OK - try { } catch ({ x }: unknown) { console.log(x); } // should be OK - try { } catch ({ x }: unknown1) { console.log(x); } // should be OK + try { } catch ({ x }: unknown) { console.log(x); } // error in the destructure + try { } catch ({ x }: unknown1) { console.log(x); } // error in the destructure try { } catch ({ x }: object) { } // error in the type try { } catch ({ x }: Error) { } // error in the type } From 6a21dd6d18e42b8ea288ab99aaa91d250a21bbf7 Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Sat, 14 Jan 2023 10:10:43 -0800 Subject: [PATCH 3/6] Also test non-strict mode --- ...eunknownincatchvariables=false).errors.txt | 60 ++++++++ ...false,useunknownincatchvariables=false).js | 145 ++++++++++++++++++ ...useunknownincatchvariables=false).symbols} | 0 ...e,useunknownincatchvariables=false).types} | 0 ...seunknownincatchvariables=true).errors.txt | 81 ++++++++++ ...=false,useunknownincatchvariables=true).js | 145 ++++++++++++++++++ ...,useunknownincatchvariables=true).symbols} | 0 ...se,useunknownincatchvariables=true).types} | 0 ...unknownincatchvariables=false).errors.txt} | 0 ...true,useunknownincatchvariables=false).js} | 0 ...,useunknownincatchvariables=false).symbols | 88 +++++++++++ ...ue,useunknownincatchvariables=false).types | 103 +++++++++++++ ...eunknownincatchvariables=true).errors.txt} | 0 ...=true,useunknownincatchvariables=true).js} | 0 ...e,useunknownincatchvariables=true).symbols | 88 +++++++++++ ...rue,useunknownincatchvariables=true).types | 103 +++++++++++++ .../cases/compiler/destructureCatchClause.ts | 2 +- 17 files changed, 814 insertions(+), 1 deletion(-) create mode 100644 tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).errors.txt create mode 100644 tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).js rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=false).symbols => destructureCatchClause(strict=false,useunknownincatchvariables=false).symbols} (100%) rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=false).types => destructureCatchClause(strict=false,useunknownincatchvariables=false).types} (100%) create mode 100644 tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).errors.txt create mode 100644 tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).js rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=true).symbols => destructureCatchClause(strict=false,useunknownincatchvariables=true).symbols} (100%) rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=true).types => destructureCatchClause(strict=false,useunknownincatchvariables=true).types} (100%) rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=false).errors.txt => destructureCatchClause(strict=true,useunknownincatchvariables=false).errors.txt} (100%) rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=false).js => destructureCatchClause(strict=true,useunknownincatchvariables=false).js} (100%) create mode 100644 tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).symbols create mode 100644 tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).types rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=true).errors.txt => destructureCatchClause(strict=true,useunknownincatchvariables=true).errors.txt} (100%) rename tests/baselines/reference/{destructureCatchClause(useunknownincatchvariables=true).js => destructureCatchClause(strict=true,useunknownincatchvariables=true).js} (100%) create mode 100644 tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).symbols create mode 100644 tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).types diff --git a/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).errors.txt b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).errors.txt new file mode 100644 index 0000000000000..d12b90899b81a --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).errors.txt @@ -0,0 +1,60 @@ +tests/cases/compiler/destructureCatchClause.ts(26,17): error TS2339: Property 'x' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(27,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(29,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(30,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(32,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(33,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(35,17): error TS2339: Property 'a' does not exist on type '{}'. + + +==== tests/cases/compiler/destructureCatchClause.ts (7 errors) ==== + // These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. + try {} catch ({ x }) { x } + try {} catch ([ x ]) { x } + + try {} catch ({ a: { x } }) { x } + try {} catch ({ a: [ x ] }) { x } + + try {} catch ([{ x }]) { x } + try {} catch ([[ x ]]) { x } + + try {} catch ({ a: { b: { c: { x }} }}) { x } + + + try {} catch ({ x }: any) { x } + try {} catch ([ x ]: any) { x } + + try {} catch ({ a: { x } }: any) { x } + try {} catch ({ a: [ x ] }: any) { x } + + try {} catch ([{ x }]: any) { x } + try {} catch ([[ x ]]: any) { x } + + try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + + try {} catch ({ x }: unknown) { x } + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. + try {} catch ([ x ]: unknown) { x } + ~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { x } }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + try {} catch ({ a: [ x ] }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + + try {} catch ([{ x }]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + try {} catch ([[ x ]]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + \ No newline at end of file diff --git a/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).js b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).js new file mode 100644 index 0000000000000..3ed7d276575d4 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).js @@ -0,0 +1,145 @@ +//// [destructureCatchClause.ts] +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try {} catch ({ x }) { x } +try {} catch ([ x ]) { x } + +try {} catch ({ a: { x } }) { x } +try {} catch ({ a: [ x ] }) { x } + +try {} catch ([{ x }]) { x } +try {} catch ([[ x ]]) { x } + +try {} catch ({ a: { b: { c: { x }} }}) { x } + + +try {} catch ({ x }: any) { x } +try {} catch ([ x ]: any) { x } + +try {} catch ({ a: { x } }: any) { x } +try {} catch ({ a: [ x ] }: any) { x } + +try {} catch ([{ x }]: any) { x } +try {} catch ([[ x ]]: any) { x } + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + +try {} catch ({ x }: unknown) { x } +try {} catch ([ x ]: unknown) { x } + +try {} catch ({ a: { x } }: unknown) { x } +try {} catch ({ a: [ x ] }: unknown) { x } + +try {} catch ([{ x }]: unknown) { x } +try {} catch ([[ x ]]: unknown) { x } + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + + +//// [destructureCatchClause.js] +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try { } +catch (_a) { + var x = _a.x; + x; +} +try { } +catch (_b) { + var x = _b[0]; + x; +} +try { } +catch (_c) { + var x = _c.a.x; + x; +} +try { } +catch (_d) { + var x = _d.a[0]; + x; +} +try { } +catch (_e) { + var x = _e[0].x; + x; +} +try { } +catch (_f) { + var x = _f[0][0]; + x; +} +try { } +catch (_g) { + var x = _g.a.b.c.x; + x; +} +try { } +catch (_h) { + var x = _h.x; + x; +} +try { } +catch (_j) { + var x = _j[0]; + x; +} +try { } +catch (_k) { + var x = _k.a.x; + x; +} +try { } +catch (_l) { + var x = _l.a[0]; + x; +} +try { } +catch (_m) { + var x = _m[0].x; + x; +} +try { } +catch (_o) { + var x = _o[0][0]; + x; +} +try { } +catch (_p) { + var x = _p.a.b.c.x; + x; +} +try { } +catch (_q) { + var x = _q.x; + x; +} +try { } +catch (_r) { + var x = _r[0]; + x; +} +try { } +catch (_s) { + var x = _s.a.x; + x; +} +try { } +catch (_t) { + var x = _t.a[0]; + x; +} +try { } +catch (_u) { + var x = _u[0].x; + x; +} +try { } +catch (_v) { + var x = _v[0][0]; + x; +} +try { } +catch (_w) { + var x = _w.a.b.c.x; + x; +} diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).symbols similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).symbols rename to tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).symbols diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).types similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).types rename to tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=false).types diff --git a/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).errors.txt b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).errors.txt new file mode 100644 index 0000000000000..ba5cff5148ec4 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).errors.txt @@ -0,0 +1,81 @@ +tests/cases/compiler/destructureCatchClause.ts(2,17): error TS2339: Property 'x' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(3,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(5,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(6,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(8,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(9,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(11,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(26,17): error TS2339: Property 'x' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(27,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(29,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(30,17): error TS2339: Property 'a' does not exist on type '{}'. +tests/cases/compiler/destructureCatchClause.ts(32,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(33,15): error TS2461: Type 'unknown' is not an array type. +tests/cases/compiler/destructureCatchClause.ts(35,17): error TS2339: Property 'a' does not exist on type '{}'. + + +==== tests/cases/compiler/destructureCatchClause.ts (14 errors) ==== + // These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. + try {} catch ({ x }) { x } + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. + try {} catch ([ x ]) { x } + ~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { x } }) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + try {} catch ({ a: [ x ] }) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + + try {} catch ([{ x }]) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + try {} catch ([[ x ]]) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { b: { c: { x }} }}) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + + + try {} catch ({ x }: any) { x } + try {} catch ([ x ]: any) { x } + + try {} catch ({ a: { x } }: any) { x } + try {} catch ({ a: [ x ] }: any) { x } + + try {} catch ([{ x }]: any) { x } + try {} catch ([[ x ]]: any) { x } + + try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + + try {} catch ({ x }: unknown) { x } + ~ +!!! error TS2339: Property 'x' does not exist on type '{}'. + try {} catch ([ x ]: unknown) { x } + ~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { x } }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + try {} catch ({ a: [ x ] }: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + + try {} catch ([{ x }]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + try {} catch ([[ x ]]: unknown) { x } + ~~~~~~~ +!!! error TS2461: Type 'unknown' is not an array type. + + try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + ~ +!!! error TS2339: Property 'a' does not exist on type '{}'. + \ No newline at end of file diff --git a/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).js b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).js new file mode 100644 index 0000000000000..3ed7d276575d4 --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).js @@ -0,0 +1,145 @@ +//// [destructureCatchClause.ts] +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try {} catch ({ x }) { x } +try {} catch ([ x ]) { x } + +try {} catch ({ a: { x } }) { x } +try {} catch ({ a: [ x ] }) { x } + +try {} catch ([{ x }]) { x } +try {} catch ([[ x ]]) { x } + +try {} catch ({ a: { b: { c: { x }} }}) { x } + + +try {} catch ({ x }: any) { x } +try {} catch ([ x ]: any) { x } + +try {} catch ({ a: { x } }: any) { x } +try {} catch ({ a: [ x ] }: any) { x } + +try {} catch ([{ x }]: any) { x } +try {} catch ([[ x ]]: any) { x } + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } + + +try {} catch ({ x }: unknown) { x } +try {} catch ([ x ]: unknown) { x } + +try {} catch ({ a: { x } }: unknown) { x } +try {} catch ({ a: [ x ] }: unknown) { x } + +try {} catch ([{ x }]: unknown) { x } +try {} catch ([[ x ]]: unknown) { x } + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } + + +//// [destructureCatchClause.js] +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try { } +catch (_a) { + var x = _a.x; + x; +} +try { } +catch (_b) { + var x = _b[0]; + x; +} +try { } +catch (_c) { + var x = _c.a.x; + x; +} +try { } +catch (_d) { + var x = _d.a[0]; + x; +} +try { } +catch (_e) { + var x = _e[0].x; + x; +} +try { } +catch (_f) { + var x = _f[0][0]; + x; +} +try { } +catch (_g) { + var x = _g.a.b.c.x; + x; +} +try { } +catch (_h) { + var x = _h.x; + x; +} +try { } +catch (_j) { + var x = _j[0]; + x; +} +try { } +catch (_k) { + var x = _k.a.x; + x; +} +try { } +catch (_l) { + var x = _l.a[0]; + x; +} +try { } +catch (_m) { + var x = _m[0].x; + x; +} +try { } +catch (_o) { + var x = _o[0][0]; + x; +} +try { } +catch (_p) { + var x = _p.a.b.c.x; + x; +} +try { } +catch (_q) { + var x = _q.x; + x; +} +try { } +catch (_r) { + var x = _r[0]; + x; +} +try { } +catch (_s) { + var x = _s.a.x; + x; +} +try { } +catch (_t) { + var x = _t.a[0]; + x; +} +try { } +catch (_u) { + var x = _u[0].x; + x; +} +try { } +catch (_v) { + var x = _v[0][0]; + x; +} +try { } +catch (_w) { + var x = _w.a.b.c.x; + x; +} diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).symbols similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).symbols rename to tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).symbols diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types b/tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).types similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).types rename to tests/baselines/reference/destructureCatchClause(strict=false,useunknownincatchvariables=true).types diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).errors.txt b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).errors.txt similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).errors.txt rename to tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).errors.txt diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).js similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=false).js rename to tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).js diff --git a/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).symbols b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).symbols new file mode 100644 index 0000000000000..2960cf2258d0a --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).symbols @@ -0,0 +1,88 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try {} catch ({ x }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) + +try {} catch ([ x ]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) + +try {} catch ({ a: { x } }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) + +try {} catch ({ a: [ x ] }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) + +try {} catch ([{ x }]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) + +try {} catch ([[ x ]]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) + + +try {} catch ({ x }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) + +try {} catch ([ x ]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) + +try {} catch ({ a: { x } }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) + +try {} catch ({ a: [ x ] }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) + +try {} catch ([{ x }]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) + +try {} catch ([[ x ]]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) + + +try {} catch ({ x }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) + +try {} catch ([ x ]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) + +try {} catch ({ a: { x } }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) + +try {} catch ({ a: [ x ] }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) + +try {} catch ([{ x }]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) + +try {} catch ([[ x ]]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) + diff --git a/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).types b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).types new file mode 100644 index 0000000000000..4dd4691a22d4b --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=false).types @@ -0,0 +1,103 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try {} catch ({ x }) { x } +>x : any +>x : any + +try {} catch ([ x ]) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]) { x } +>x : any +>x : any + +try {} catch ([[ x ]]) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + + +try {} catch ({ x }: any) { x } +>x : any +>x : any + +try {} catch ([ x ]: any) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }: any) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }: any) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]: any) { x } +>x : any +>x : any + +try {} catch ([[ x ]]: any) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + + +try {} catch ({ x }: unknown) { x } +>x : any +>x : any + +try {} catch ([ x ]: unknown) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }: unknown) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }: unknown) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]: unknown) { x } +>x : any +>x : any + +try {} catch ([[ x ]]: unknown) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).errors.txt b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).errors.txt similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).errors.txt rename to tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).errors.txt diff --git a/tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).js similarity index 100% rename from tests/baselines/reference/destructureCatchClause(useunknownincatchvariables=true).js rename to tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).js diff --git a/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).symbols b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).symbols new file mode 100644 index 0000000000000..2960cf2258d0a --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).symbols @@ -0,0 +1,88 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try {} catch ({ x }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 1, 15)) + +try {} catch ([ x ]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 2, 15)) + +try {} catch ({ a: { x } }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 4, 20)) + +try {} catch ({ a: [ x ] }) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 5, 20)) + +try {} catch ([{ x }]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 7, 16)) + +try {} catch ([[ x ]]) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 8, 16)) + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 10, 30)) + + +try {} catch ({ x }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 13, 15)) + +try {} catch ([ x ]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 14, 15)) + +try {} catch ({ a: { x } }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 16, 20)) + +try {} catch ({ a: [ x ] }: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 17, 20)) + +try {} catch ([{ x }]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 19, 16)) + +try {} catch ([[ x ]]: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 20, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 22, 30)) + + +try {} catch ({ x }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 25, 15)) + +try {} catch ([ x ]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 26, 15)) + +try {} catch ({ a: { x } }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 28, 20)) + +try {} catch ({ a: [ x ] }: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 29, 20)) + +try {} catch ([{ x }]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 31, 16)) + +try {} catch ([[ x ]]: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 32, 16)) + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) +>x : Symbol(x, Decl(destructureCatchClause.ts, 34, 30)) + diff --git a/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).types b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).types new file mode 100644 index 0000000000000..4dd4691a22d4b --- /dev/null +++ b/tests/baselines/reference/destructureCatchClause(strict=true,useunknownincatchvariables=true).types @@ -0,0 +1,103 @@ +=== tests/cases/compiler/destructureCatchClause.ts === +// These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. +try {} catch ({ x }) { x } +>x : any +>x : any + +try {} catch ([ x ]) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]) { x } +>x : any +>x : any + +try {} catch ([[ x ]]) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + + +try {} catch ({ x }: any) { x } +>x : any +>x : any + +try {} catch ([ x ]: any) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }: any) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }: any) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]: any) { x } +>x : any +>x : any + +try {} catch ([[ x ]]: any) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}: any) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + + +try {} catch ({ x }: unknown) { x } +>x : any +>x : any + +try {} catch ([ x ]: unknown) { x } +>x : any +>x : any + +try {} catch ({ a: { x } }: unknown) { x } +>a : any +>x : any +>x : any + +try {} catch ({ a: [ x ] }: unknown) { x } +>a : any +>x : any +>x : any + +try {} catch ([{ x }]: unknown) { x } +>x : any +>x : any + +try {} catch ([[ x ]]: unknown) { x } +>x : any +>x : any + +try {} catch ({ a: { b: { c: { x }} }}: unknown) { x } +>a : any +>b : any +>c : any +>x : any +>x : any + diff --git a/tests/cases/compiler/destructureCatchClause.ts b/tests/cases/compiler/destructureCatchClause.ts index 8fd33a665c3ab..4a8a18d12e69c 100644 --- a/tests/cases/compiler/destructureCatchClause.ts +++ b/tests/cases/compiler/destructureCatchClause.ts @@ -1,4 +1,4 @@ -// @strict: true +// @strict: true, false // @useUnknownInCatchVariables: true, false // These are okay with useUnknownInCatchVariables=false, but not okay with useUnknownInCatchVariables=true. From c7a4c134c37df20b55780fd4594335101cf1bd4f Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Tue, 17 Jan 2023 14:13:41 -0800 Subject: [PATCH 4/6] Return early --- src/compiler/checker.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 67ee06ee08e41..f2db029ba32cb 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10205,7 +10205,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { const isOptional = includeOptionality && isOptionalDeclaration(declaration); // Use type from type annotation if one is present - let declaredType = tryGetTypeFromEffectiveTypeNode(declaration); + const declaredType = tryGetTypeFromEffectiveTypeNode(declaration); if (isCatchClauseVariableDeclarationOrBindingElement(declaration)) { if (declaredType) { // If the catch clause is explicitly annotated with any or unknown, accept it, otherwise error. @@ -10213,7 +10213,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { } // If the catch clause is not explicitly annotated, treat it as though it were explicitly // annotated with unknown or any, depending on useUnknownInCatchVariables. - declaredType = useUnknownInCatchVariables ? unknownType : anyType; + return useUnknownInCatchVariables ? unknownType : anyType; } if (declaredType) { return addOptionality(declaredType, isProperty, isOptional); From 838da0d41bd4ce09d8bfa8e4573d89a6b310bc1e Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Wed, 18 Jan 2023 11:56:51 -0800 Subject: [PATCH 5/6] Remove comment --- src/compiler/checker.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index e0e9e85b8f450..3a852acad0ad9 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10886,7 +10886,6 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { members.set("exports" as __String, result); return createAnonymousType(symbol, members, emptyArray, emptyArray, emptyArray); } - // Handle catch clause variables Debug.assertIsDefined(symbol.valueDeclaration); const declaration = symbol.valueDeclaration; // Handle export default expressions From b4ae1c2afed36a56821828172e96270f3810c29b Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Wed, 18 Jan 2023 11:45:06 -0800 Subject: [PATCH 6/6] Fix error in tsserver with semantic tokens enabled --- src/compiler/checker.ts | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 3a852acad0ad9..dcceeb49701f3 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -27078,6 +27078,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { isFunctionLike(node) && !getImmediatelyInvokedFunctionExpression(node) || node.kind === SyntaxKind.ModuleBlock || node.kind === SyntaxKind.SourceFile || + node.kind === SyntaxKind.CatchClause || node.kind === SyntaxKind.PropertyDeclaration)!; } @@ -27450,6 +27451,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { const isParameter = getRootDeclaration(declaration).kind === SyntaxKind.Parameter; const declarationContainer = getControlFlowContainer(declaration); let flowContainer = getControlFlowContainer(node); + const isCatch = flowContainer.kind === SyntaxKind.CatchClause; const isOuterVariable = flowContainer !== declarationContainer; const isSpreadDestructuringAssignmentTarget = node.parent && node.parent.parent && isSpreadAssignment(node.parent) && isDestructuringAssignmentTarget(node.parent.parent); const isModuleExports = symbol.flags & SymbolFlags.ModuleExports; @@ -27464,7 +27466,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { // We only look for uninitialized variables in strict null checking mode, and only when we can analyze // the entire control flow graph from the variable's declaration (i.e. when the flow container and // declaration container are the same). - const assumeInitialized = isParameter || isAlias || isOuterVariable || isSpreadDestructuringAssignmentTarget || isModuleExports || isSameScopedBindingElement(node, declaration) || + const assumeInitialized = isParameter || isCatch || isAlias || isOuterVariable || isSpreadDestructuringAssignmentTarget || isModuleExports || isSameScopedBindingElement(node, declaration) || type !== autoType && type !== autoArrayType && (!strictNullChecks || (type.flags & (TypeFlags.AnyOrUnknown | TypeFlags.Void)) !== 0 || isInTypeQuery(node) || isInAmbientOrTypeNode(node) || node.parent.kind === SyntaxKind.ExportSpecifier) || node.parent.kind === SyntaxKind.NonNullExpression ||