Repository navigation
[Bug] Lossless JSON snapshots change raw values into objects: exact-integer transport #8810
Replies: 3 comments 1 reply
这条要能被修,关键是说清"快照"应当保真到什么程度1. 你指出的矛盾是实在的你写:lossless-JSON 校验器接受真正的 ⇒ 这属于"校验与变换的口径不一致":校验认为它合法,变换却改了它的种类。这类问题比单纯的四舍五入更难发现,因为它不改变"是否合法",只改变"它是什么"——你的定位是对的。 2. 建议把诉求落在"契约"上,而不是某个函数建议这样写(可判定):
两条择一是关键:现在的组合(校验放行 + 变换降级)是唯一不可接受的那一种——它让"校验通过"失去意义。把这一句写出来,维护者不必猜你要哪种语义。 3. 请补三样(能让它落到一行)
4. 为什么值得独立跟踪(你的理由我认同)你写"这值得独立于 input-number rounding 单独跟踪"——对:四舍五入是精度问题,而这是类型问题。前者可以靠"提高精度"缓解,后者会让下游拿到错误类型(例如把整数当对象解析)。建议把这一层区分写进正文的第一段,否则容易被合并进那条更显眼的精度讨论里而被稀释。 5. 你的用例很有说服力,建议保留"AI4S 涉及范畴论、需要精确整数系数"——给出真实用例(而不是抽象地谈 lossless),是这类"类型保真"报告最缺的东西:它说明了为什么"变成对象"是不可接受的。请保留,并补一句"该对象在下游会被怎样误用"(例如被当作结构体解析),影响面就完整了。 一条边界我没有核对 lossless-JSON 的实现(你引的是行为,不是行号)。上面是按你的描述给出的契约级定位——补上第 3 节三样之后,这条就能落到"改校验"或"改变换"这一个选择上。 |
|
I've published an opt-in tool-side implementation: dsh-exact-integers (MIT), with a separate plugin showcase discussion. Exact-integer fields are declared as canonical decimal strings in tool schemas, decoded to To answer the request above for a minimal reproduction, I verified the following with the published import {
isJsonValue,
snapshotJsonValue,
} from '@deepseek-ai/dsh-util-values';
const raw = JSON.rawJSON(((1n << 80n) + 1n).toString());
const copy = snapshotJsonValue(raw);
console.log(isJsonValue(raw)); // true
console.log(JSON.isRawJSON(raw)); // true
console.log(JSON.isRawJSON(copy)); // false
console.log(JSON.stringify(raw)); // 1208925819614629174706177
console.log(JSON.stringify(copy)); // {"rawJSON":"1208925819614629174706177"}The public plugin suite has 18 synthetic tests, including actual DSH tool execution, streamed arguments from a scripted provider, plain/compressed JSONL persistence, replay and resume. CI passes on Node 22.19 and 24; these tests do not call a live model. The plugin provides an explicit string-based transport contract. The core snapshot-contract issue remains separate: accepting a raw JSON value and copying it into a plain object changes its serialized JSON kind. Preserving the supported kind and literal, or explicitly rejecting unsupported raw JSON values, would make that boundary predictable. |
你给的符号我核到了——而且它正是工具结果那条路,所以核心问题应当继续挂着1. 核实结果(
|
Uh oh!
There was an error while loading. Please reload this page.
DSH's lossless-JSON validator currently accepts genuine
JSON.rawJSONvalues, but its snapshot helper changes them into ordinary objects. A JSON number can therefore become a JSON object despite successful validation.This deserves tracking independently of input-number rounding. The motivating use case is AI4S involving category theory, where exact integer coefficients must retain their mathematical value. The reproduction uses only public DSH code and generic values.
Reproduction
Verified on Node.js v22.23.2 against upstream commit
5badb15009ae1756c3afe0ae0cef1faafc290ccc. From a checkout of that revision:Actual output:
No model, credentials, or application code is required. The same type change occurs with nested arrays, negative integers, and even
JSON.rawJSON('7').Expected: either explicitly reject unsupported raw-JSON values or preserve their JSON meaning in a detached snapshot. Successful validation should not silently change the value's type. This expectation does not require arbitrary-precision arithmetic inside DSH.
Cause and affected boundary
snapshotJsonValuecopies the enumerablerawJSONproperty into an ordinary object, losing the original object's special JSON serialization behavior.The helper is used for argument and result materialization in
packages/core/tools/src/index.ts. Preserving integer tokens during parsing alone would therefore be insufficient if the proposed representation subsequently goes through this snapshot path.Related discussion: #6002 reports tool-argument rounding in
JSON.parse. The current parser still rounds9007199254740993to9007199254740992. The snapshot issue above is a separate failure with an already-exact input. It was initially noted in a comment there and is being moved here for independent tracking.Exact-integer support and a possible plugin
The immediate snapshot defect can be addressed independently of a broader exact-number feature. For that broader feature, a small, opt-in plugin or tool-author helper could provide an explicit exact-integer representation at tool boundaries. A schema-declared decimal string is one possible representation; it preserves digits without requiring a JavaScript
number.Such a plugin must operate before information is lost. Ordinary execution hooks receive parsed arguments, so converting an already-rounded number to a string or
BigIntcannot recover its original digits. A plugin should not claim to transparently repair all existing tools.Useful acceptance coverage would include:
{"rawJSON":"..."}objects remaining ordinary objects, distinct from genuine raw-JSON values.Feedback on the intended raw-JSON contract and the appropriate extension boundary for opt-in exact integers would help keep a community plugin small and compatible with DSH.
Validation scope
I executed the current upstream value helpers directly and reproduced five raw-JSON cases: positive/negative large integers, a small integer, a boolean, and a string. Ordinary safe numbers, an approximate
1e30, decimal strings, plainrawJSON-named objects, and text content retain their serialized values; nativeBigIntis explicitly rejected. I also checked the extracted unchanged argument-parser body.A full current-version agent/provider/session test was not run. The dispatch/history/replay checks above are proposed acceptance coverage, not claimed completed validation. The plugin is a proposal, not an implemented or published artifact.
All reactions