Sometimes you don't know which type will come as function argument/variable value/object property value.
As example JSON.parse
. This function can return array of any types, object with any properties or any valid JSON value like string, number, boolean and etc.
const anything = JSON.parse('{ "name": null }');
The most general type in Hegel is unknown
. You can imagine this type as "Universal Set". It means that all possible values in JavaScript has unknown
type. It's a supertype for all types in Hegel type system.
const anyNumber: unknown = 2;const anyString: unknown = "something";const anything: unknown = class User {};
If you already familiar with TypeScript or Flow.js, this type has the same semantic as
unknown
in TS ormixed
in Flow.js
But, as you can understand, you can assign concrete type to wider type, but you can't assign wider type to a concrete type.
const concreteType: string = "I'm good for unknown";const wideType: unknown = "I'm too wide for string";const iCanBeUnknown: unknown = concreteType;const andICanBeString: string = concreteType;const andICanBeUnknownToo: unknown = wideType;const butCantBeString: string = wideType;
Also, it means that you can't use unknown type as an argument for function which is waiting for some concrete type:
function waitingFor(value: string) {return `Awesome ${value}`;}const anything: unknown = 4;// Error: Type "unknown" is incompatible with type "string"const result = waitingFor(anything);
Or operator:
function waitingFor(value: unknown) {// Error: Type "unknown" is incompatible with type "string"return `Awesome ${value}`;}const result = waitingFor(class User {});
Actually, Hegel provides ability to refine type.