79402421

Date: 2025-01-31 10:23:44
Score: 1
Natty:
Report link

The reason Readonly appears not to function as you expect with primitive types like string, number, and boolean is due to what Readonly is designed to do and how primitive types are handled in JavaScript and TypeScript.

Here's a breakdown:

Purpose of Readonly: The Readonly utility type in TypeScript is designed to make all properties of an object type T readonly. It operates at the level of object properties. When you apply Readonly to an interface or a type representing an object, it changes the type definition such that you cannot reassign values to the properties of objects of that type.

Primitive Types vs. Object Types:

Primitive types (string, number, boolean, symbol, bigint, null, undefined) in JavaScript and TypeScript are passed by value. When you pass a primitive value to a function, the function receives a copy of that value. Any modifications you make to the parameter within the function do not affect the original value outside the function's scope.

Object types (including objects, arrays, and functions) are passed by reference. When you pass an object to a function, the function receives a reference to the original object. If the function modifies properties of this object, those changes are reflected in the original object outside the function.

Why Readonly Doesn't Prevent Reassignment of Primitive Parameters: In your inspect function examples with primitives:

inspect((str: Readonly) => { str = New string // Can change }) Use code with caution. TypeScript Here, Readonly for the str parameter doesn't prevent you from reassigning the variable str within the function. This is because:

Readonly itself doesn't fundamentally alter the nature of the string type in this context. It's still just a string.

You are reassigning the local variable str within the function's scope. Readonly is not designed to prevent reassignment of function parameters themselves, especially when dealing with primitives passed by value.

Readonly's effect is to prevent you from modifying properties of an object. Primitives don't have properties in the same way objects do.

Why Readonly Works for Object Properties: In your object example:

inspect<{str: string, num: number, bool: boolean}>((obj: Readonly<{str: string, num: number, bool: boolean}>) => { obj.str = New string // Can't change; yields compile time error }) Use code with caution. TypeScript Here, Readonly<{str: string, num: number, bool: boolean}> does work as expected. It makes the str, num, and bool properties of the obj parameter readonly. TypeScript's compiler will prevent you from reassigning these properties because Readonly modifies the type definition of the object to enforce readonly access to its properties.

Is there a way to make it work for primitive types?

Not in the way you might be thinking with Readonly. Readonly is specifically for object properties. There's no direct TypeScript feature using Readonly or a similar utility to prevent you from reassigning a primitive parameter variable within a function's body.

For primitive types passed by value, the fact that they are passed by value already provides a form of "readonly" behavior in terms of the original value outside the function. Modifying the parameter within the function doesn't affect the original value.

If you want to ensure that a function parameter, even if it's a primitive, is not intended to be reassigned within the function for code clarity or to signal intent, you could rely on code style, naming conventions (like using const if possible within the function body for local variables derived from the parameter), or code review practices. However, TypeScript itself doesn't provide a mechanism via Readonly or similar to enforce this kind of "parameter immutability" for primitives in terms of preventing reassignment of the parameter variable within the function's scope.

In summary: Readonly is for making object properties readonly. It doesn't prevent reassignment of function parameters themselves, especially when they are primitive types passed by value. For primitives, the pass-by-value mechanism inherently prevents modifications within a function from affecting the original value outside, which is a different form of "immutability" but not enforced by Readonly.

Reasons:
  • Blacklisted phrase (1): Is there a way
  • Long answer (-1):
  • Has code block (-0.5):
  • Contains question mark (0.5):
  • Low reputation (1):
Posted by: Jest1s