feat: enhance order handling in LighterGateway and introduce order identity normalization for improved precision and consistency

This commit is contained in:
discountry
2025-11-12 19:17:04 +08:00
parent 1baee3a207
commit e7f6341961
11 changed files with 318 additions and 40 deletions
+26
View File
@@ -0,0 +1,26 @@
import { describe, expect, it } from "vitest";
import { shouldResetMarketOrders } from "../../src/exchanges/lighter/order-feed";
describe("shouldResetMarketOrders", () => {
it("always resets on snapshots", () => {
expect(shouldResetMarketOrders([{ id: 1 }], true)).toBe(true);
expect(shouldResetMarketOrders([], true)).toBe(true);
expect(shouldResetMarketOrders(null, true)).toBe(true);
});
it("resets when array bucket is empty", () => {
expect(shouldResetMarketOrders([], false)).toBe(true);
expect(shouldResetMarketOrders([{}], false)).toBe(false);
});
it("resets when object bucket has no keys", () => {
expect(shouldResetMarketOrders({}, false)).toBe(true);
expect(shouldResetMarketOrders({ a: 1 }, false)).toBe(false);
});
it("does not reset for non-empty updates", () => {
expect(shouldResetMarketOrders([{ order_index: "1" }], false)).toBe(false);
expect(shouldResetMarketOrders(null, false)).toBe(false);
expect(shouldResetMarketOrders(undefined, false)).toBe(false);
});
});
+23
View File
@@ -0,0 +1,23 @@
import { describe, expect, it } from "vitest";
import { normalizeOrderIdentity, orderIdentityEquals } from "../../src/exchanges/lighter/order-identity";
describe("order identity helpers", () => {
it("treats large numeric strings as distinct values", () => {
const first = "27584547724798440";
const second = "27584547724798442";
expect(orderIdentityEquals(first, second)).toBe(false);
expect(orderIdentityEquals(first, first)).toBe(true);
});
it("considers numeric inputs equal to their string counterparts", () => {
expect(orderIdentityEquals(123456789, "123456789")).toBe(true);
});
it("normalizes whitespace-only identifiers to null", () => {
expect(normalizeOrderIdentity(" ")).toBeNull();
});
it("falls back to truncated integers for floating inputs", () => {
expect(normalizeOrderIdentity(42.9)).toBe("42");
});
});
+36
View File
@@ -0,0 +1,36 @@
import { describe, expect, it } from "vitest";
import { lighterOrderToAster } from "../../src/exchanges/lighter/mappers";
import type { LighterOrder } from "../../src/exchanges/lighter/types";
function createOrder(overrides: Partial<LighterOrder> = {}): LighterOrder {
return {
order_index: 1,
client_order_index: 1,
market_index: 99,
initial_base_amount: "0.1",
remaining_base_amount: "0.1",
price: "154.86",
type: "limit",
reduce_only: "No",
side: "buy",
...overrides,
} as LighterOrder;
}
describe("lighterOrderToAster", () => {
it("treats textual reduce_only flags correctly", () => {
const nonReduce = lighterOrderToAster("USDJPY", createOrder({ reduce_only: "No" }));
expect(nonReduce.reduceOnly).toBe(false);
const reduce = lighterOrderToAster("USDJPY", createOrder({ reduce_only: "Yes" }));
expect(reduce.reduceOnly).toBe(true);
});
it("uses numeric is_ask flag for side inference", () => {
const sell = lighterOrderToAster("USDJPY", createOrder({ is_ask: 1 }));
expect(sell.side).toBe("SELL");
const buy = lighterOrderToAster("USDJPY", createOrder({ is_ask: 0 }));
expect(buy.side).toBe("BUY");
});
});