From 62abfff43946455b7db55b924ed0bffd0a81e6ea Mon Sep 17 00:00:00 2001 From: imxyy_soope_ Date: Wed, 14 Jan 2026 18:39:36 +0800 Subject: [PATCH] fix: make update operator lazy --- nix-js/runtime-ts/src/helpers.ts | 10 +++++----- nix-js/runtime-ts/src/operators.ts | 22 +++++++++++++++++++++- 2 files changed, 26 insertions(+), 6 deletions(-) diff --git a/nix-js/runtime-ts/src/helpers.ts b/nix-js/runtime-ts/src/helpers.ts index 2fdb5f5..9d51239 100644 --- a/nix-js/runtime-ts/src/helpers.ts +++ b/nix-js/runtime-ts/src/helpers.ts @@ -50,7 +50,7 @@ export const select = (obj: NixValue, attrpath: NixValue[]): NixValue => { let attrs = forceAttrs(obj); for (const attr of attrpath.slice(0, -1)) { - const key = forceString(attr) + const key = forceString(attr); if (!(key in attrs)) { throw new Error(`Attribute '${key}' not found`); } @@ -63,7 +63,7 @@ export const select = (obj: NixValue, attrpath: NixValue[]): NixValue => { attrs = cur; } - const last = forceString(attrpath[attrpath.length - 1]) + const last = forceString(attrpath[attrpath.length - 1]); if (!(last in attrs)) { throw new Error(`Attribute '${last}' not found`); } @@ -74,9 +74,9 @@ export const selectWithDefault = (obj: NixValue, attrpath: NixValue[], default_v let attrs = forceAttrs(obj); for (const attr of attrpath.slice(0, -1)) { - const key = forceString(attr) + const key = forceString(attr); if (!(key in attrs)) { - return default_val + return default_val; } const cur = force(attrs[key]); if (!isAttrs(cur)) { @@ -87,7 +87,7 @@ export const selectWithDefault = (obj: NixValue, attrpath: NixValue[], default_v const last = forceString(attrpath[attrpath.length - 1]); if (last in attrs) { - return attrs[last] + return attrs[last]; } return default_val; }; diff --git a/nix-js/runtime-ts/src/operators.ts b/nix-js/runtime-ts/src/operators.ts index 234a760..cc40496 100644 --- a/nix-js/runtime-ts/src/operators.ts +++ b/nix-js/runtime-ts/src/operators.ts @@ -175,6 +175,26 @@ export const op = { }, update: (a: NixValue, b: NixValue): NixAttrs => { - return { ...forceAttrs(a), ...forceAttrs(b) }; + const forcedA = forceAttrs(a); + const forcedB = forceAttrs(b); + const newAttrs: NixAttrs = {}; + + for (const key in forcedA) { + Object.defineProperty(newAttrs, key, { + get: () => force(forcedA[key]), + enumerable: true, + configurable: true, + }); + } + + for (const key in forcedB) { + Object.defineProperty(newAttrs, key, { + get: () => force(forcedB[key]), + enumerable: true, + configurable: true, + }); + } + + return newAttrs; }, };