@pafi-dev/trading 0.1.3 → 0.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +44 -20
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -72,37 +72,61 @@ show a soft "unavailable" UI state without 500-ing.
|
|
|
72
72
|
|
|
73
73
|
#### Frontend "quote review" pattern
|
|
74
74
|
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
`GET /quote?chainId&pointToken&amount` on a 400 ms debounce after each
|
|
79
|
-
keystroke and render a card with `pointAmount → estimatedUsdtOut −
|
|
80
|
-
gasFeeUsdt = netUsdtOut` plus the `exchangeRate`.
|
|
75
|
+
Quotes are pure on-chain reads (Uniswap V4 Quoter via Base RPC) — **no
|
|
76
|
+
auth, no issuer-side state, nothing to proxy through the issuer
|
|
77
|
+
backend.** Call `handleQuote` directly from the browser / React Native.
|
|
81
78
|
|
|
82
79
|
```tsx
|
|
83
|
-
|
|
80
|
+
import { TradingHandlers, fetchPafiPools } from "@pafi-dev/trading";
|
|
81
|
+
import { createPublicClient, http, formatUnits } from "viem";
|
|
82
|
+
import { base } from "viem/chains";
|
|
83
|
+
|
|
84
|
+
const trading = new TradingHandlers({
|
|
85
|
+
provider: createPublicClient({ chain: base, transport: http(RPC_URL) }),
|
|
86
|
+
chainId: 8453,
|
|
87
|
+
});
|
|
84
88
|
|
|
85
89
|
useEffect(() => {
|
|
86
|
-
if (
|
|
90
|
+
if (amount <= 0n) return setQuote(null);
|
|
87
91
|
const t = setTimeout(async () => {
|
|
88
|
-
const
|
|
89
|
-
const
|
|
90
|
-
|
|
92
|
+
const pools = await fetchPafiPools(8453, POINT_TOKEN);
|
|
93
|
+
const result = await trading.handleQuote({
|
|
94
|
+
chainId: 8453,
|
|
95
|
+
pointTokenAddress: POINT_TOKEN,
|
|
96
|
+
amount,
|
|
97
|
+
pools,
|
|
98
|
+
});
|
|
99
|
+
setQuote(result);
|
|
91
100
|
}, 400);
|
|
92
101
|
return () => clearTimeout(t);
|
|
93
|
-
}, [amount
|
|
102
|
+
}, [amount]);
|
|
94
103
|
|
|
95
|
-
//
|
|
96
|
-
//
|
|
97
|
-
// quote.
|
|
98
|
-
//
|
|
99
|
-
// quote.quoteError
|
|
104
|
+
// Render:
|
|
105
|
+
// In: formatUnits(amount, 18) PT
|
|
106
|
+
// You receive: formatUnits(quote.estimatedUsdtOut, 6) USDT
|
|
107
|
+
// Rate: estimatedUsdtOut · 1e18 / amount / 1e6 USDT per 1 PT
|
|
108
|
+
// On `quote.quoteError === "QUOTE_UNAVAILABLE"` → hide the Swap CTA.
|
|
100
109
|
```
|
|
101
110
|
|
|
102
|
-
|
|
111
|
+
Why client-direct (no `GET /quote` HTTP hop):
|
|
112
|
+
|
|
113
|
+
- The quoter is stateless and reads from the public RPC — there's no
|
|
114
|
+
secret to hide and nothing to validate against an issuer's database.
|
|
115
|
+
- One fewer round-trip on every keystroke (debounce hits the Quoter
|
|
116
|
+
directly, ~150 ms vs. ~400 ms via a backend proxy).
|
|
117
|
+
- The quote stays internally consistent with the swap path that
|
|
118
|
+
`handleSwap` will pick — both use the same `findBestQuote()` call
|
|
119
|
+
under the hood with the same `pools` array, so what the user sees in
|
|
120
|
+
the review card is what they get on submit.
|
|
121
|
+
|
|
122
|
+
> **Operator fee in USDT** is **NOT** part of the quote — it's an
|
|
123
|
+
> issuer-policy concern decided at swap-build time. If you want a
|
|
124
|
+
> "net out after fee" preview, fetch the issuer's gas-fee endpoint
|
|
125
|
+
> separately and subtract on the client.
|
|
126
|
+
|
|
127
|
+
Reference implementation lives in
|
|
103
128
|
[`privy-pimlico-eip7702-example/app/components/WalletPanel.tsx`](https://github.com/pacific-finance/pafi-backend/blob/main/privy-pimlico-eip7702-example/app/components/WalletPanel.tsx)
|
|
104
|
-
(search for `Quote review`).
|
|
105
|
-
issuer backend exposes — no extra SDK call needed on the client.
|
|
129
|
+
(search for `Quote review`).
|
|
106
130
|
|
|
107
131
|
---
|
|
108
132
|
|