You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
functionfoo(data: string|Uint8Array|ArrayBuffer): number{if(typeofdata==="string"){data=newTextEncoder().encode(data);}elseif(!ArrayBuffer.isView(data)){data=newUint8Array(data);}// At this point, `data` _should_ be Uint8Array, because ArrayBuffer.isView() returns `false` for `ArrayBuffer. Instead, `data` is still typed as `Uint8Array | ArrayBuffer`.returndata.length;}
🙁 Actual behavior
The data variable is not being narrowed to a Uint8Array by the time it reaches the return statement. This is causing both an Intellisense error, as well as a build error.
🙂 Expected behavior
In the above code, I would expect data to be correctly narrowed to a UInt8Array by the time we reach the return line. Given that ArrayBuffer.isView() returns true for Uint8Array and false for ArrayBuffer, the if / else if guarantees that data must be Uint8Array at the return.
I can confirm this behavior by running the code as plain JS in the DevTools console:
function foo(data)
{
if (typeof data === "string")
{
console.log("string");
data = new TextEncoder().encode(data);
}
else if (!ArrayBuffer.isView(data))
{
console.log("arraybuffer");
data = new Uint8Array(data);
}
else
{
console.log("uint8array");
}
return data.length;
}
< foo("hello")
> string
> 5
< foo(new Uint8Array())
> uint8array
> 0
< foo(new Uint8Array().buffer)
> arraybuffer
> 0
Additional information about the issue
No response
The text was updated successfully, but these errors were encountered:
In the above code, I would expect data to be correctly narrowed to a UInt8Array by the time we reach the return line. Given that ArrayBuffer.isView() returns true for Uint8Array and false for ArrayBuffer,
The problem is that it's possible (from a structural typing point of view) that data is an ArrayBuffer & ArrayBufferView, in which case isView would return true for a value inhabiting the ArrayBuffer part of the union.
@RyanCavanaugh Is that related to the typed-array types being structurally compatible with ArrayBuffer (a complaint for which there are several existing issues that I don't feel like looking up at present)
🔎 Search Terms
ArrayBuffer, ArrayBuffer.isView, type narrow
🕗 Version & Regression Information
This is the behavior in every version I tried, including the nightly version.
I've reviewed the FAQ on type narrowing, but I do not believe it applies to the issue at hand. It could be related to https://github.com/Microsoft/TypeScript/wiki/FAQ#why-doesnt-isfoox-narrow-x-to-foo-when-isfoo-is-a-type-guard, but given that the section is not filled out ("TODO") it is unclear whether this is the same issue.
⏯ Playground Link
https://www.typescriptlang.org/play?ts=5.5.0-dev.20240327#code/GYVwdgxgLglg9mABMOcAUATAhlLAuRAZygCcYwBzRAH0QFVyoAOAQRJKwE8bE2POAQiGDAApiQCUBMCAC2AI3EAoAN5LEGxDGCI0UTgAdRcHdlyIAvFcQAiYmUo2J6zWs3vEZrJcRhRAd0QAFVEADygAUUg4DHE0CQA6UWjYzBwsCQBuFw0AXxzEUQAbQlEtHTQAQj4uIRFxBJhCADUYALTcCWd3Nw8NLx8-QIYwZhrODozs93z3AoB6ed4oRCgACybEAzhGABpEAAMvA8QAfUI1uBAijFPERXpGVnYufcUILBBS3hfBYTESI0Wm1-PFECRRFAQCQwIRDsAsCVRCcUCRDuM6gCEogAJKwqCiLAYfZHdInTbEGBFIqrQyiDCILBwg4jMa-HgY-7iA4JAoQqEwzzpBJFZIUdbZXJAA
💻 Code
🙁 Actual behavior
The
data
variable is not being narrowed to aUint8Array
by the time it reaches thereturn
statement. This is causing both an Intellisense error, as well as a build error.🙂 Expected behavior
In the above code, I would expect
data
to be correctly narrowed to aUInt8Array
by the time we reach thereturn
line. Given thatArrayBuffer.isView()
returnstrue
forUint8Array
andfalse
forArrayBuffer
, theif / else if
guarantees thatdata
must beUint8Array
at thereturn
.I can confirm this behavior by running the code as plain JS in the DevTools console:
Additional information about the issue
No response
The text was updated successfully, but these errors were encountered: