Error transforming object
I'm having some trouble doing transforming some data
3 Replies
const MyAssets = scope({
  Asset: {
    token: "string",
    amount: type("string").pipe((s, ctx) => {
      try {
        return BigInt(s);
      } catch {
        return ctx.error("a valid non-decimal number");
      }
    }),
  },
  Assets: {
    assets: "Asset[]>=1",
  },
})
  .export()
  .Assets.pipe((o) => {
    const assets = o.assets.reduce<Record<string, bigint>>((acc, asset) => {
      acc[asset.token] = asset.amount;
      return acc;
    }, {});
    return { ...o, assets };
  });
test("can parse MyAssets", (t) => {
  const data = MyAssets({ assets: [{ token: "a", amount: "1" }] });
  if (data instanceof type.errors) return t.fail(data.summary);
  t.truthy(data);
});
const MyAssets = scope({
  Asset: {
    token: "string",
    amount: type("string").pipe((s, ctx) => {
      try {
        return BigInt(s);
      } catch {
        return ctx.error("a valid non-decimal number");
      }
    }),
  },
  Assets: {
    assets: "Asset[]>=1",
  },
})
  .export()
  .Assets.pipe((o) => {
    const assets = o.assets.reduce<Record<string, bigint>>((acc, asset) => {
      acc[asset.token] = asset.amount;
      return acc;
    }, {});
    return { ...o, assets };
  });
test("can parse MyAssets", (t) => {
  const data = MyAssets({ assets: [{ token: "a", amount: "1" }] });
  if (data instanceof type.errors) return t.fail(data.summary);
  t.truthy(data);
});
  Error thrown in test:
  TypeError {
    message: 'Cannot read properties of undefined (reading \'amount\')',
  }
  Error thrown in test:
  TypeError {
    message: 'Cannot read properties of undefined (reading \'amount\')',
  }
amount doens't include the pipe, then it works:
const MyAssets = scope({
  Asset: {
    token: "string",
    amount: "string",
  },
  Assets: {
    assets: "Asset[]>=1",
  },
})
  .export()
  .Assets.pipe((o) => {
    const assets = o.assets.reduce<Record<string, bigint>>((acc, asset) => {
      acc[asset.token] = BigInt(asset.amount);
      return acc;
    }, {});
    return { ...o, assets };
  });
const MyAssets = scope({
  Asset: {
    token: "string",
    amount: "string",
  },
  Assets: {
    assets: "Asset[]>=1",
  },
})
  .export()
  .Assets.pipe((o) => {
    const assets = o.assets.reduce<Record<string, bigint>>((acc, asset) => {
      acc[asset.token] = BigInt(asset.amount);
      return acc;
    }, {});
    return { ...o, assets };
  });
assets instead of transforming, it works:
const MyAssets = scope({
  Asset: {
    token: "string",
    amount: type("string").pipe((s, ctx) => {
      try {
        return BigInt(s);
      } catch {
        return ctx.error("a valid non-decimal number");
      }
    }),
  },
  Assets: {
    assets: "Asset[]>=1",
  },
})
  .export()
  .Assets.pipe((o) => {
    const assets = o.assets.reduce<Record<string, bigint>>((acc, asset) => {
      acc[asset.token] = asset.amount;
      return acc;
    }, {});
    return { ...o, assets2: assets };
  });
const MyAssets = scope({
  Asset: {
    token: "string",
    amount: type("string").pipe((s, ctx) => {
      try {
        return BigInt(s);
      } catch {
        return ctx.error("a valid non-decimal number");
      }
    }),
  },
  Assets: {
    assets: "Asset[]>=1",
  },
})
  .export()
  .Assets.pipe((o) => {
    const assets = o.assets.reduce<Record<string, bigint>>((acc, asset) => {
      acc[asset.token] = asset.amount;
      return acc;
    }, {});
    return { ...o, assets2: assets };
  });
const Assets = scope({
  Asset: {
    token: "string",
    amount: type("string").pipe((s, ctx) => {
      try {
        return BigInt(s);
      } catch {
        return ctx.error("a valid non-decimal number");
      }
    }),
  },
  Assets: "Asset[]",
})
  .export()
  .Assets.pipe((a) =>
    a.reduce<Record<string, bigint>>((assets, asset) => {
      assets[asset.token] = asset.amount;
      return assets;
    }, {})
  );
const MyAssets = scope({
  AssetsType: Assets,
  Assets: {
    assets: "AssetsType",
  },
}).export().Assets;
const Assets = scope({
  Asset: {
    token: "string",
    amount: type("string").pipe((s, ctx) => {
      try {
        return BigInt(s);
      } catch {
        return ctx.error("a valid non-decimal number");
      }
    }),
  },
  Assets: "Asset[]",
})
  .export()
  .Assets.pipe((a) =>
    a.reduce<Record<string, bigint>>((assets, asset) => {
      assets[asset.token] = asset.amount;
      return assets;
    }, {})
  );
const MyAssets = scope({
  AssetsType: Assets,
  Assets: {
    assets: "AssetsType",
  },
}).export().Assets;
const MyAssets = (() => {
  const MyAssets = scope({
    Asset: {
      token: "string",
      amount: type("string").pipe((s, ctx) => {
        try {
          return BigInt(s);
        } catch {
          return ctx.error("a valid non-decimal number");
        }
      }),
    },
    Assets: {
      assets: "Asset[]>=1",
    },
  }).export().Assets;
  return (data: unknown) => {
    const result = MyAssets(data);
    if (result instanceof type.errors) return result;
    return {
      ...result,
      assets: result.assets.reduce<Record<string, bigint>>((acc, asset) => {
        acc[asset.token] = asset.amount;
        return acc;
      }, {}),
    };
  };
})();
test("can parse MyAssets", (t) => {
  const data = MyAssets({ assets: [{ token: "a", amount: "1" }] });
  if (data instanceof type.errors) return t.fail(data.summary);
  t.truthy(data);
});
const MyAssets = (() => {
  const MyAssets = scope({
    Asset: {
      token: "string",
      amount: type("string").pipe((s, ctx) => {
        try {
          return BigInt(s);
        } catch {
          return ctx.error("a valid non-decimal number");
        }
      }),
    },
    Assets: {
      assets: "Asset[]>=1",
    },
  }).export().Assets;
  return (data: unknown) => {
    const result = MyAssets(data);
    if (result instanceof type.errors) return result;
    return {
      ...result,
      assets: result.assets.reduce<Record<string, bigint>>((acc, asset) => {
        acc[asset.token] = asset.amount;
        return acc;
      }, {}),
    };
  };
})();
test("can parse MyAssets", (t) => {
  const data = MyAssets({ assets: [{ token: "a", amount: "1" }] });
  if (data instanceof type.errors) return t.fail(data.summary);
  t.truthy(data);
});
Will need to investigate this one more, can you log it as a GitHub issue? You can log the other one as well though that should be more straightforward to repro/fix
GitHub
Error transforming object: Cannot read properties of undefined · Is...
Report a bug 🔎 Search Terms pipe transform 🧩 Context ArkType version: 2.0.0-dev.13 TypeScript version (5.1+): 5.3.3 Other context you think may be relevant (JS flavor, OS, etc.): 🧑💻 Repro const My...