import type { Page } from "playwright"; import { isDualAddressPatchEnabled } from "@/lib/rpa/env"; import { INJECT_REACT_STATE } from "@/workers/rpa/fix-place/browser-eval-scripts"; import { DUAL_ADDRESS_PATCH_INIT } from "@/workers/rpa/inject/dual-address-patch-init"; export { DUAL_ADDRESS_PATCH_INIT }; export type DualAddressVaultEntry = { placeId: string; location: Record; description: string; }; type RegisterArg = { side: "pickup" | "delivery"; payload: DualAddressVaultEntry; }; export async function registerDualAddressInPage( page: Page, side: "pickup" | "delivery", payload: DualAddressVaultEntry, ): Promise { return page.evaluate( ({ side: sideArg, payload: entry }: RegisterArg) => { const api = ( window as Window & { __rpaDualAddressApi?: { register: ( s: string, p: { placeId: string; location: Record; description: string }, ) => boolean; }; } ).__rpaDualAddressApi; if (!api?.register) { return false; } return !!api.register(sideArg, { placeId: entry.placeId, location: entry.location, description: entry.description, }); }, { side, payload }, ); } export async function preservePickupInWidget(page: Page): Promise { return page.evaluate(() => { const api = ( window as Window & { __rpaDualAddressApi?: { preservePickup: () => boolean }; } ).__rpaDualAddressApi; if (!api?.preservePickup) { return false; } return !!api.preservePickup(); }); } export async function releasePickupInputInWidget(page: Page): Promise { return page.evaluate(() => { const api = ( window as Window & { __rpaDualAddressApi?: { releasePickupInput: () => boolean }; } ).__rpaDualAddressApi; if (!api?.releasePickupInput) { return false; } return !!api.releasePickupInput(); }); } export async function preserveDualAddressInWidget(page: Page): Promise { return page.evaluate(() => { const api = ( window as Window & { __rpaDualAddressApi?: { preserveBoth: () => boolean }; } ).__rpaDualAddressApi; if (!api?.preserveBoth) { return false; } return !!api.preserveBoth(); }); } export async function readDualAddressPatchStats( page: Page, ): Promise> { return page.evaluate(() => { const api = ( window as Window & { __rpaDualAddressApi?: { stats: () => Record }; } ).__rpaDualAddressApi; if (!api?.stats) { return { installed: false }; } return { installed: true, ...api.stats() }; }); } /** pickup commit 后:vault + React setState + 释放派送输入框 */ export async function applyPickupDualAddressPatch( page: Page, payload: DualAddressVaultEntry, ): Promise { if (!isDualAddressPatchEnabled()) { return; } const statsBefore = await readDualAddressPatchStats(page); const registered = await registerDualAddressInPage(page, "pickup", payload); const injected = await page.evaluate(INJECT_REACT_STATE, { sideArg: "pickup", pid: payload.placeId, loc: payload.location, desc: payload.description, }); await releasePickupInputInWidget(page); await page.waitForTimeout(500); const preserved = await preservePickupInWidget(page); console.log("[rpa] dual-address-patch:pickup", { statsBefore, registered, injected, preserved, }); } /** delivery 填写前/后巩固双地址 */ export async function applyDeliveryDualAddressPatch( page: Page, pickup: DualAddressVaultEntry, delivery: DualAddressVaultEntry, ): Promise { if (!isDualAddressPatchEnabled()) { return; } await registerDualAddressInPage(page, "pickup", pickup); await preservePickupInWidget(page); const deliveryRegistered = await registerDualAddressInPage( page, "delivery", delivery, ); const deliveryInjected = await page.evaluate(INJECT_REACT_STATE, { sideArg: "delivery", pid: delivery.placeId, loc: delivery.location, desc: delivery.description, }); const both = await preserveDualAddressInWidget(page); console.log("[rpa] dual-address-patch:delivery", { deliveryRegistered, deliveryInjected, both, }); }