optimize: type check
This commit is contained in:
@@ -2,11 +2,16 @@
|
||||
* Conversion and serialization builtin functions
|
||||
*/
|
||||
|
||||
import { addBuiltContext, mkStringWithContext, type NixStringContext } from "../string-context";
|
||||
import {
|
||||
addBuiltContext,
|
||||
mkStringWithContext,
|
||||
type NixStringContext,
|
||||
StringWithContext,
|
||||
} from "../string-context";
|
||||
import { force, isThunk } from "../thunk";
|
||||
import { forceFunction, forceStringNoCtx } from "../type-assert";
|
||||
import type { NixString, NixValue } from "../types";
|
||||
import { HAS_CONTEXT, IS_PATH, isNixPath, isStringWithContext } from "../types";
|
||||
import { isNixPath, isStringWithContext, NixPath } from "../types";
|
||||
import { isAttrs, isPath, typeOf } from "./type-check";
|
||||
|
||||
export const fromJSON = (e: NixValue): NixValue => {
|
||||
@@ -306,13 +311,13 @@ export const nixValueToJson = (
|
||||
if (typeof v === "number") return v;
|
||||
if (typeof v === "boolean") return v;
|
||||
if (typeof v === "string") return v;
|
||||
if (typeof v === "object" && HAS_CONTEXT in v) {
|
||||
if (v instanceof StringWithContext) {
|
||||
for (const elem of v.context) {
|
||||
outContext.add(elem);
|
||||
}
|
||||
return v.value;
|
||||
}
|
||||
if (typeof v === "object" && IS_PATH in v) {
|
||||
if (v instanceof NixPath) {
|
||||
if (copyToStore) {
|
||||
const storePath = Deno.core.ops.op_copy_path_to_store(v.value);
|
||||
outContext.add(storePath);
|
||||
|
||||
@@ -11,8 +11,8 @@ import {
|
||||
forceStringNoCtx,
|
||||
forceStringValue,
|
||||
} from "../type-assert";
|
||||
import type { NixAttrs, NixPath, NixString, NixValue } from "../types";
|
||||
import { CatchableError, IS_PATH, isNixPath } from "../types";
|
||||
import type { NixAttrs, NixString, NixValue } from "../types";
|
||||
import { CatchableError, isNixPath, NixPath } from "../types";
|
||||
import { coerceToPath, coerceToString, StringCoercionMode } from "./conversion";
|
||||
import { baseNameOf } from "./path";
|
||||
import { isAttrs, isPath, isString } from "./type-check";
|
||||
@@ -475,13 +475,13 @@ export const findFile =
|
||||
suffix.length > 0 ? Deno.core.ops.op_resolve_path(suffix, resolvedPath) : resolvedPath;
|
||||
|
||||
if (Deno.core.ops.op_path_exists(candidatePath)) {
|
||||
return { [IS_PATH]: true, value: candidatePath };
|
||||
return new NixPath(candidatePath);
|
||||
}
|
||||
}
|
||||
|
||||
if (lookupPathStr.startsWith("nix/")) {
|
||||
// FIXME: special path type
|
||||
return { [IS_PATH]: true, value: `<${lookupPathStr}>` };
|
||||
return new NixPath(`<${lookupPathStr}>`);
|
||||
}
|
||||
|
||||
throw new CatchableError(`file '${lookupPathStr}' was not found in the Nix search path`);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { IS_PATH, type NixPath } from "./types";
|
||||
import { NixPath } from "./types";
|
||||
|
||||
const canonicalizePath = (path: string): string => {
|
||||
const parts: string[] = [];
|
||||
@@ -30,7 +30,7 @@ const canonicalizePath = (path: string): string => {
|
||||
};
|
||||
|
||||
export const mkPath = (value: string): NixPath => {
|
||||
return { [IS_PATH]: true, value: canonicalizePath(value) };
|
||||
return new NixPath(canonicalizePath(value));
|
||||
};
|
||||
|
||||
export const getPathValue = (p: NixPath): string => {
|
||||
|
||||
@@ -22,18 +22,22 @@ export type StringContextElem = StringContextOpaque | StringContextDrvDeep | Str
|
||||
|
||||
export type NixStringContext = Set<string>;
|
||||
|
||||
export interface StringWithContext {
|
||||
readonly [HAS_CONTEXT]: true;
|
||||
export class StringWithContext {
|
||||
readonly [HAS_CONTEXT] = true as const;
|
||||
value: string;
|
||||
context: NixStringContext;
|
||||
constructor(value: string, context: NixStringContext) {
|
||||
this.value = value;
|
||||
this.context = context;
|
||||
}
|
||||
}
|
||||
|
||||
export const isStringWithContext = (v: NixStrictValue): v is StringWithContext => {
|
||||
return typeof v === "object" && v !== null && HAS_CONTEXT in v;
|
||||
return v instanceof StringWithContext;
|
||||
};
|
||||
|
||||
export const mkStringWithContext = (value: string, context: NixStringContext): StringWithContext => {
|
||||
return { [HAS_CONTEXT]: true, value, context };
|
||||
return new StringWithContext(value, context);
|
||||
};
|
||||
|
||||
export const mkPlainString = (value: string): string => value;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { isAttrs, isList } from "./builtins/type-check";
|
||||
import { HAS_CONTEXT } from "./string-context";
|
||||
import type { NixAttrs, NixStrictValue, NixThunkInterface, NixValue } from "./types";
|
||||
import { IS_PATH } from "./types";
|
||||
import { StringWithContext } from "./string-context";
|
||||
import type { NixAttrs, NixStrictValue, NixValue } from "./types";
|
||||
import { NixPath } from "./types";
|
||||
|
||||
export const IS_THUNK = Symbol("is_thunk");
|
||||
|
||||
@@ -21,8 +21,7 @@ export const DEBUG_THUNKS = { enabled: true };
|
||||
* - Evaluating (blackhole): func is undefined, result is undefined
|
||||
* - Evaluated: func is undefined, result is defined
|
||||
*/
|
||||
export class NixThunk implements NixThunkInterface {
|
||||
[key: symbol]: unknown;
|
||||
export class NixThunk {
|
||||
readonly [IS_THUNK] = true as const;
|
||||
func: (() => NixValue) | undefined;
|
||||
result: NixStrictValue | undefined;
|
||||
@@ -42,8 +41,8 @@ export class NixThunk implements NixThunkInterface {
|
||||
}
|
||||
}
|
||||
|
||||
export const isThunk = (value: NixValue): value is NixThunkInterface => {
|
||||
return value !== null && typeof value === "object" && IS_THUNK in value && value[IS_THUNK] === true;
|
||||
export const isThunk = (value: NixValue): value is NixThunk => {
|
||||
return value instanceof NixThunk;
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -112,7 +111,7 @@ export const force = (value: NixValue): NixStrictValue => {
|
||||
}
|
||||
};
|
||||
|
||||
export const createThunk = (func: () => NixValue, label?: string): NixThunkInterface => {
|
||||
export const createThunk = (func: () => NixValue, label?: string): NixThunk => {
|
||||
return new NixThunk(func, label);
|
||||
};
|
||||
|
||||
@@ -142,7 +141,7 @@ export const forceDeep = (value: NixValue, seen: WeakSet<object> = new WeakSet()
|
||||
seen.add(forced);
|
||||
}
|
||||
|
||||
if (HAS_CONTEXT in forced || IS_PATH in forced) {
|
||||
if (forced instanceof StringWithContext || forced instanceof NixPath) {
|
||||
return forced;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,18 +1,21 @@
|
||||
import { HAS_CONTEXT, isStringWithContext, type StringWithContext } from "./string-context";
|
||||
import { type CYCLE_MARKER, force, IS_THUNK } from "./thunk";
|
||||
import { type CYCLE_MARKER, force, type NixThunk } from "./thunk";
|
||||
import { forceAttrs, forceStringNoCtx } from "./type-assert";
|
||||
export { HAS_CONTEXT, isStringWithContext };
|
||||
export type { StringWithContext };
|
||||
|
||||
export const IS_PATH = Symbol("IS_PATH");
|
||||
|
||||
export interface NixPath {
|
||||
readonly [IS_PATH]: true;
|
||||
export class NixPath {
|
||||
readonly [IS_PATH] = true as const;
|
||||
value: string;
|
||||
constructor(value: string) {
|
||||
this.value = value;
|
||||
}
|
||||
}
|
||||
|
||||
export const isNixPath = (v: NixStrictValue): v is NixPath => {
|
||||
return typeof v === "object" && v !== null && IS_PATH in v;
|
||||
return v instanceof NixPath;
|
||||
};
|
||||
|
||||
export type NixInt = bigint;
|
||||
@@ -109,12 +112,6 @@ export const mkAttrsWithPos = (
|
||||
return attrs;
|
||||
};
|
||||
|
||||
export interface NixThunkInterface {
|
||||
readonly [IS_THUNK]: true;
|
||||
func: (() => NixValue) | undefined;
|
||||
result: NixStrictValue | undefined;
|
||||
}
|
||||
|
||||
export type NixPrimitive = NixNull | NixBool | NixInt | NixFloat | NixString;
|
||||
export type NixValue =
|
||||
| NixPrimitive
|
||||
@@ -122,8 +119,8 @@ export type NixValue =
|
||||
| NixList
|
||||
| NixAttrs
|
||||
| NixFunction
|
||||
| NixThunkInterface
|
||||
| NixThunk
|
||||
| typeof CYCLE_MARKER;
|
||||
export type NixStrictValue = Exclude<NixValue, NixThunkInterface>;
|
||||
export type NixStrictValue = Exclude<NixValue, NixThunk>;
|
||||
|
||||
export class CatchableError extends Error {}
|
||||
|
||||
Reference in New Issue
Block a user