Since it is possible in dfusion to place orders without having a balance it allows for some interesting concepts that can be described as “a trade-strategy”, “simple market-making” or “programmable orders”.
A simple example of this is a strategy to market make on stable coins. A user can select a bunch of stable coins they trust (trust to maintain a value of e.g. 1$) and create a bunch of orders that trade any of those stable coins against any other as long as they make a spread on the trade. It is sufficient to provide any of the stable coins into this strategy. As soon as stable coin A gets exchanged into stable coin B this will “activate” all orders from “B”.
In this strategy, the full amount that is given is used at one price level. A strategy might be price sensitive. A simple example is the x*y=k formula, made popular by unisawp. Simplified it means, the more the price of token A drops the more to buy of token A with token B.
This can be achieved by dividing up capital into different accounts. Those different accounts would each trade A and B against each other at a specific price level. They would have a spread - so trading A to B and B back to A would result in a profit of 2 times the spread.
Uniswap describes a continuous supply and demand curve - with this strategy the curve can be approximated by a step function. The big advantage is that ANY curve can be used and even just parts of a curve.
If those orders would be placed per trader it would lead to many orders. If a trader want to market make $/ETH in the range from $100 to $200 with 1% spread it would result in 100 different accounts that each creates an order to e.g. buy ETH for $145 and sell ETH for at $146. So in aggregate, it would be 100 accounts that each place 2 orders. If the trader spends 1k in total each account would be funded with $10. Since the system can only handle 25 orders per batch small orders will be excluded if the system runs at capacity. The system can scale much bigger if the same order types are aggregated into larger orders. So we could have one larger order (or accounts with multiple orders) owned by a pool of traders. This ownership can be expressed as tokens (like pool shares in uniswap).
Implementing pool contracts:
Let’s consider a simple pool that is selling all DAI for USDc with 0.5% spread and selling all USDc for 0.5% spread to DAI as well.
A smart contract would just place to standing order with unlimited volume that is valid forever. A trader deposit into the pool. The pool deposits into dfusion. Implicitly this deposit will increase the order size. At the moment of deposit, the trader needs to get allocated pool shares. At the moment of deposit, the contract can calculate the ratio of outstanding pool shares and the current balance in the contract. The user will get an allocation of pool shares at this rate (minus the spread to avoid effectively trading with the pool by deposit and withdrawal). A small issue might be that at the moment of the deposit the pool contract did already engaged in a trade, but the solver has not submitted the trade yet. Now you could deposit into a pool that you know did a profitable trade in the previous batch. But you can still join under the conditions before this trade happened.
Potentially a bigger issue - a solver might have submitted a solution (potentially with unrealistic prices) that will get reverted. In this case, you join the pool under the assumption that it just did a very profitable trade but the trade will get reverted. Or alternatively, you can join under the assumption that the pool just did a horrible trade and you will get much better conditions than you should since the trade gets reverted.
One way to solve that issue would be to only allow joining the pool in minutes 4-5 when the previous batch is final. In practice, it might be hard enough to pull off this attack to just accept the risk. In can be eliminated by the user defining a max price they are willing to pay for pool shares.
A withdrawal can be implemented as follows: a user can lock their pool shares to withdrawal a token or a combination of tokens they want. The issue here is that at the moment of withdrawal (unless in minute 4-5) it will not be in any case clear what tokens the pool has (since they may be traded away in the current trade).
Example - the user had 100 shares representing 100 tokens of A and B. The user could decide to withdraw 50 and 50. At the moment of withdrawal, the account might even have that balance. Right after the trade, the solver submits a solution that converts all A to B. Now in the next batch the user will only be able to withdrawal B. There needs to be a way to convert the remaining A withdrawal into B.