I want to protect the object content of a constant from being changed at runtime. This affects both the change in the object structure and the content of the object. The method of choice here is Object.freeze.
interface iRO<T> {
readonly [key: string]: T | null;
}
const nc: iRO<HTMLElement> = {
main: document.querySelector("body"),
aside: document.querySelector("body > aside"),
}
const go: iRO<HTMLElement> = Object.seal({
main: document.querySelector("body"),
aside: document.querySelector("body > aside"),
})
const nogo: iRO<HTMLElement> = Object.freeze({
main: document.querySelector("body"),
aside: document.querySelector("body > aside"),
})
As an example, I have given three constants with the same content. With the constants "nc" and "go" the compilation works fine. The compiler complains at "nogo":
»Type 'Readonly<{ main: HTMLBodyElement | null; aside: Element | null; }>' is not assignable to type 'iRO'. Property 'aside' is incompatible with index signature. Type 'Element | null' is not assignable to type 'HTMLElement | null'. Type 'Element' is missing the following properties from type 'HTMLElement': accessKey, accessKeyLabel, autocapitalize, dir, and 107 more.«
I do not understand that. Object.freeze should just as little influence the assigned type as its little brother Object.seal?
Here's a Typescript Playground