Skip to content
This repository was archived by the owner on Dec 12, 2024. It is now read-only.

Commit a643467

Browse files
committed
feat: add lp example
1 parent 990123c commit a643467

File tree

1 file changed

+195
-2
lines changed

1 file changed

+195
-2
lines changed

pages/cookbook/dexes/dedust.mdx

Lines changed: 195 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,6 @@
22

33
import { Callout } from 'nextra-theme-docs';
44

5-
{/* See: https://nextra.site/docs/guide/built-ins */}
6-
75
[DeDust](https://dedust.io) is a decentralized exchange (DEX) and automated market maker (AMM) built natively on [TON Blockchain](https://ton.org) and [DeDust Protocol 2.0](https://docs.dedust.io/reference/tlb-schemes). DeDust is designed with a meticulous attention to user experience (UX), gas efficiency, and extensibility.
86

97
## Swaps
@@ -152,3 +150,198 @@ fun makeJettonSwap() {
152150
});
153151
}
154152
```
153+
154+
155+
## Liquidity Provisioning
156+
157+
To provide liquidity to a specific DeDust pool, you must supply both assets. After doing so, the pool issues LP tokens to the depositor's address.
158+
159+
You can read more about liquidity provisioning on [DeDust documentation](https://docs.dedust.io/docs/liquidity-provisioning).
160+
161+
```tact
162+
const PoolTypeVolatile: Int = 0;
163+
const PoolTypeStable: Int = 1;
164+
165+
const AssetTypeNative: Int = 0b0000;
166+
const AssetTypeJetton: Int = 0b0001;
167+
168+
const JettonProvideLpGas: Int = ton("0.5");
169+
const JettonProvideLpGasFwd: Int = ton("0.4");
170+
const TonProvideLpGas: Int = ton("0.15");
171+
172+
const JettonMaster: Address = address("kQDkRHlWaibL7Tww48T6xAUFevPflca7i8TIiQTacBmnDOrb");
173+
//const JettonMasterRaw: RawAddress = JettonMaster.toRaw(); TODO: maybe there is contants evaluation in tact? Did not find anything
174+
const JettonVault: Address = address("kQDcUuH4xhKejjilZAIeGuBh5JRWpzbVDcO9Qfh_Q_K4q9vk");
175+
const TonVault: Address = address("EQDa4VOnTYlLvDJ0gZjNYm5PXfSmmtL6Vs6A_CZEtXCNICq_");
176+
177+
struct RawAddress {
178+
workchain: Int as uint8;
179+
hash: Int as uint256;
180+
}
181+
182+
extends fun toRaw(self: Address): RawAddress {
183+
let addressSlice: Slice = self.asSlice();
184+
185+
addressSlice.skipBits(3);
186+
return RawAddress {
187+
workchain: addressSlice.loadUint(8),
188+
hash: addressSlice.loadUint(256),
189+
}
190+
}
191+
192+
message(0xf8a7ea5) JettonTransfer {
193+
queryId: Int as uint64;
194+
amount: Int as coins;
195+
destination: Address;
196+
responseDestination: Address?;
197+
customPayload: Cell? = null;
198+
forwardTonAmount: Int as coins;
199+
forwardPayload: Cell?;
200+
}
201+
202+
struct Asset {
203+
type: Int as uint4;
204+
workchain: Int? as uint8 = null;
205+
hash: Int? as uint256 = null;
206+
}
207+
208+
extends fun build(self: Asset): Cell {
209+
let assetBuilder = beginCell()
210+
.storeUint(self.type, 4);
211+
212+
if (self.type == AssetTypeNative) {
213+
return assetBuilder.endCell();
214+
}
215+
if (self.type == AssetTypeJetton) {
216+
return assetBuilder
217+
.storeUint(self.workchain!!, 8)
218+
.storeUint(self.hash!!, 256)
219+
.endCell();
220+
}
221+
222+
require(false, "Unknown asset type");
223+
return beginCell().endCell();
224+
}
225+
226+
message(0x40e108d6) JettonDepositLiquidity {
227+
poolType: Int as uint1; // PoolType
228+
asset0: Asset;
229+
asset1: Asset;
230+
minimalLpAmount: Int as coins = 0;
231+
targetBalances0: Int as coins;
232+
targetBalances1: Int as coins;
233+
fulfillPayload: Cell? = null;
234+
rejectPayload: Cell? = null;
235+
}
236+
237+
extends fun build(self: JettonDepositLiquidity): Cell {
238+
return beginCell()
239+
.storeUint(0x40e108d6, 32)
240+
.storeUint(self.poolType, 1)
241+
.storeSlice(self.asset0.build().asSlice())
242+
.storeSlice(self.asset1.build().asSlice())
243+
.storeCoins(self.minimalLpAmount)
244+
.storeCoins(self.targetBalances0)
245+
.storeCoins(self.targetBalances1)
246+
.storeMaybeRef(self.fulfillPayload)
247+
.storeMaybeRef(self.rejectPayload)
248+
.endCell();
249+
}
250+
251+
message(0xd55e4686) NativeDepositLiquidity {
252+
queryId: Int as uint64;
253+
amount: Int as coins;
254+
poolType: Int as uint1;
255+
asset0: Asset;
256+
asset1: Asset;
257+
minimalLpAmount: Int as coins = 0;
258+
targetBalances0: Int as coins;
259+
targetBalances1: Int as coins;
260+
fulfillPayload: Cell? = null;
261+
rejectPayload: Cell? = null;
262+
}
263+
264+
extends fun build(self: NativeDepositLiquidity): Cell {
265+
return beginCell()
266+
.storeUint(0xd55e4686, 32)
267+
.storeUint(self.queryId, 64)
268+
.storeCoins(self.amount)
269+
.storeUint(self.poolType, 1)
270+
.storeSlice(self.asset0.build().asSlice())
271+
.storeSlice(self.asset1.build().asSlice())
272+
.storeRef(
273+
beginCell()
274+
.storeCoins(self.minimalLpAmount)
275+
.storeCoins(self.targetBalances0)
276+
.storeCoins(self.targetBalances1)
277+
.endCell()
278+
)
279+
.storeMaybeRef(self.fulfillPayload)
280+
.storeMaybeRef(self.rejectPayload)
281+
.endCell();
282+
}
283+
284+
285+
message ProvideLp {
286+
myJettonWalletAddress: Address; // calculated offchain for ease of example, in real world scenarios should be calculated onchain
287+
}
288+
289+
contract Example {
290+
receive() {}
291+
receive(msg: ProvideLp) {
292+
let jettonMasterRaw: RawAddress = JettonMaster.toRaw();
293+
294+
// Step 1. Prepare input
295+
let jettonAmount = ton("1");
296+
let tonAmount = ton("1");
297+
298+
let asset0 = Asset{
299+
type: AssetTypeNative,
300+
};
301+
let asset1 = Asset{
302+
type: AssetTypeJetton,
303+
workchain: jettonMasterRaw.workchain,
304+
hash: jettonMasterRaw.hash,
305+
};
306+
307+
// Step 2. Deposit Jetton to Vault
308+
let jettonDepositBody = JettonDepositLiquidity{
309+
poolType: PoolTypeVolatile,
310+
asset0,
311+
asset1,
312+
targetBalances0: tonAmount,
313+
targetBalances1: jettonAmount,
314+
}.build();
315+
316+
send(SendParameters{
317+
to: msg.myJettonWalletAddress,
318+
value: JettonProvideLpGas,
319+
body: JettonTransfer{
320+
queryId: 42,
321+
amount: jettonAmount,
322+
destination: JettonVault,
323+
responseDestination: myAddress(),
324+
forwardTonAmount: JettonProvideLpGasFwd,
325+
forwardPayload: jettonDepositBody,
326+
}.toCell()
327+
});
328+
329+
// Step 3. Deposit TON to Vault
330+
let nativeDepositBody = NativeDepositLiquidity{
331+
queryId: 42,
332+
amount: tonAmount,
333+
poolType: PoolTypeVolatile,
334+
asset0,
335+
asset1,
336+
targetBalances0: tonAmount,
337+
targetBalances1: jettonAmount,
338+
}.build();
339+
340+
send(SendParameters{
341+
to: TonVault,
342+
value: tonAmount + TonProvideLpGas,
343+
body: nativeDepositBody,
344+
});
345+
}
346+
}
347+
```

0 commit comments

Comments
 (0)