fix: a swap deadline later than a date can hold is stated in words (closes #437)
decode() rendered the Deadline line with toISOString(), which throws on a date past 275760-09-13, the last a JavaScript date can hold. A later deadline, such as the uint256 maximum, therefore left the whole swap undecoded, with nothing saying why. That line now reads "After 275760-09-13 00:00:00 (no deadline in practice)". Model: opus-5-5
This commit was merged in pull request #441.
This commit is contained in:
@@ -1022,6 +1022,12 @@ unwraps the WETH it did not spend shows USDC. The token permission warning on
|
|||||||
the signature screen has its own amount wording, including `Unknown`; the
|
the signature screen has its own amount wording, including `Unknown`; the
|
||||||
SignApproval section below describes it.
|
SignApproval section below describes it.
|
||||||
|
|
||||||
|
The swap's `Deadline` line is the router's deadline as a UTC date and time, e.g.
|
||||||
|
`2026-02-27 08:25:51`. A JavaScript date reaches only to 275760-09-13 00:00:00
|
||||||
|
UTC, so a later deadline, such as the `uint256` maximum, reads
|
||||||
|
`After 275760-09-13 00:00:00 (no deadline in practice)` rather than leaving the
|
||||||
|
whole swap undecoded.
|
||||||
|
|
||||||
#### Partial USD totals
|
#### Partial USD totals
|
||||||
|
|
||||||
Prices are fetched for the top 25 tokens only, so an address can hold assets the
|
Prices are fetched for the top 25 tokens only, so an address can hold assets the
|
||||||
|
|||||||
@@ -45,6 +45,12 @@ but the review is broader than any of them.
|
|||||||
|
|
||||||
# Completed Steps
|
# Completed Steps
|
||||||
|
|
||||||
|
- 2026-10-04: A swap whose deadline is later than a JavaScript date can hold is
|
||||||
|
decoded ([#437](https://git.eeqj.de/sneak/AutistMask/issues/437)). A date
|
||||||
|
reaches only to 275760-09-13, so a later deadline, such as the `uint256`
|
||||||
|
maximum, made the `Deadline` line throw, and the approval screen showed the
|
||||||
|
swap as an undecoded contract call with nothing saying why. That line now
|
||||||
|
reads `After 275760-09-13 00:00:00 (no deadline in practice)`.
|
||||||
- 2026-10-04: The swap decoder reads two router zeros the way the router does
|
- 2026-10-04: The swap decoder reads two router zeros the way the router does
|
||||||
([#415](https://git.eeqj.de/sneak/AutistMask/issues/415)). A V2 exact-in
|
([#415](https://git.eeqj.de/sneak/AutistMask/issues/415)). A V2 exact-in
|
||||||
`amountIn` of zero means an earlier step already sent the tokens to the pair;
|
`amountIn` of zero means an earlier step already sent the tokens to the pair;
|
||||||
|
|||||||
@@ -724,10 +724,15 @@ function decode(data, toAddress, sources) {
|
|||||||
|
|
||||||
details.push({ label: "Steps", value: commandNames.join(" \u2192 ") });
|
details.push({ label: "Steps", value: commandNames.join(" \u2192 ") });
|
||||||
|
|
||||||
|
// A JavaScript date reaches only to 275760-09-13 00:00:00 UTC. A
|
||||||
|
// later deadline, such as the uint256 maximum, makes an invalid date,
|
||||||
|
// and toISOString() throws on one, so that deadline is said in words.
|
||||||
const deadlineDate = new Date(Number(deadline) * 1000);
|
const deadlineDate = new Date(Number(deadline) * 1000);
|
||||||
details.push({
|
details.push({
|
||||||
label: "Deadline",
|
label: "Deadline",
|
||||||
value: deadlineDate.toISOString().replace("T", " ").slice(0, 19),
|
value: isNaN(deadlineDate.getTime())
|
||||||
|
? "After 275760-09-13 00:00:00 (no deadline in practice)"
|
||||||
|
: deadlineDate.toISOString().replace("T", " ").slice(0, 19),
|
||||||
});
|
});
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|||||||
@@ -554,6 +554,33 @@ describe("uniswap decoder", () => {
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test("shows the deadline as a UTC date and time", () => {
|
||||||
|
const result = uniswap.decode(FIRST_SWAP_CALLDATA, ROUTER_ADDR);
|
||||||
|
expect(detail(result, "Deadline").value).toBe("2026-02-27 08:25:51");
|
||||||
|
});
|
||||||
|
|
||||||
|
// A JavaScript date cannot hold this deadline. It used to make the whole
|
||||||
|
// swap undecoded.
|
||||||
|
test("a deadline of the uint256 maximum is stated in words", () => {
|
||||||
|
const data = buildExecute(
|
||||||
|
"0x08", // V2_SWAP_EXACT_IN
|
||||||
|
[
|
||||||
|
encodeV2SwapExactIn(USER_ADDR, 1000000n, 500000000000000n, [
|
||||||
|
USDT_ADDR,
|
||||||
|
WETH_ADDR,
|
||||||
|
]),
|
||||||
|
],
|
||||||
|
2n ** 256n - 1n,
|
||||||
|
);
|
||||||
|
|
||||||
|
const result = uniswap.decode(data, ROUTER_ADDR);
|
||||||
|
expect(result).not.toBeNull();
|
||||||
|
expect(result.name).toBe("Swap USDT \u2192 WETH");
|
||||||
|
expect(detail(result, "Deadline").value).toBe(
|
||||||
|
"After 275760-09-13 00:00:00 (no deadline in practice)",
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
test("formats permit amount when not unlimited", () => {
|
test("formats permit amount when not unlimited", () => {
|
||||||
const data = buildExecute(
|
const data = buildExecute(
|
||||||
"0x0a",
|
"0x0a",
|
||||||
|
|||||||
Reference in New Issue
Block a user