Skip to content

Commit

Permalink
move contract usage description from readme to msg.rs
Browse files Browse the repository at this point in the history
  • Loading branch information
sotnikov-s committed Jun 27, 2024
1 parent 4604e57 commit 781f430
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 55 deletions.
54 changes: 4 additions & 50 deletions contracts/dao/neutron-flashloans/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,65 +2,19 @@

## Overview

The `neutron-flashloans` contract facilitates providing flash loans to smart contracts operating on the Neutron network.

A flash loan is a type of uncollateralized loan in the cryptocurrency and decentralized finance (DeFi) space. It allows
borrowers to borrow funds without providing any collateral, on the condition that the loan is repaid within the same
transaction. If the borrower fails to repay the loan by the end of the transaction, the entire transaction is
reversed, effectively canceling the loan. Flash loans are typically used for arbitrage, collateral swapping, and
refinancing, taking advantage of price discrepancies or temporary liquidity needs without requiring long-term capital.

## Usage

To get a flash loan, a `RequestLoan` message needs to be sent to the `neutron-flashloans` contract:

```rust
struct RequestLoan {
/// The amount that the borrower contract requests; there should be no
/// duplicate denoms and no zero amounts.
amount: Vec<Coin>,
}
```

The sender needs to be a smart-contract that implements a handler for the `ProcessLoan` message:

```rust
#[cw_serde]
pub enum BorrowerInterface {
ProcessLoan {
/// Specifies the address to which the borrower must return the loan amount AND pay the fees.
return_address: Addr,
/// Specifies the loan amount which the borrower must return to the return_address.
loan_amount: Vec<Coin>,
/// Specifies the fee which the borrower must pay to the return_address.
fee: Vec<Coin>,
}
}
```

Upon receiving the `RequestLoan` message, the `neutron-flashloans` contract will transfer the requested amount to the
borrower and send a `ProcessLoan` message. The borrower can execute any logic within its `ProcessLoan` handler but must
return the `loan_amount` plus the `fee` to the `return_address`. Failure to do so will result in the entire transaction
being reverted.

## Implementation
The `neutron-flashloans` contract facilitates providing flash loans to smart contracts operating on the Neutron network.

The `neutron-flashloans` contract does not hold any funds. Instead, it uses `authz` permission from the `source` address
to execute `/cosmos.bank.v1beta1.MsgSend` on its behalf. For Neutron, the `source` address must be set to the Treasury (
DAO core) contract address.
## Usage

* The `RequestLoan` handler ensures there is no active loan, validates the loan amount (no duplicate or zero coins),
calculates the expected balance (current balance + fee) of the source after repayment, and records the loan details in
storage. If the `source` does not have the requested amount of funds, an error will be returned. Finally, it instructs
the source to send the requested amount to the borrower via `authz`, encapsulated in a `stargate message`. This
message is submitted as a submessage with a `reply_on_success` strategy, meaning if it fails, the transaction is
reverted.
* Upon successful execution of the `/cosmos.bank.v1beta1.MsgSend` message, the `neutron-flashloans` contract sends
a `ProcessLoan` submessage with a `reply_on_success` strategy to the borrower contract.
* After receiving a successful reply to the `ProcessLoan` message, the `neutron-flashloans` contract verifies that the
borrower has returned the funds and paid the fee, then it deletes the loan information.
See the `neutron-flashloans` contract's [interface](https://github.com/neutron-org/neutron-dao/blob/main/contracts/dao/neutron-flashloans/src/msg.rs) in order to get familiar with all requirements, limitations and usage guidelines.

## Security advice
### Security advice

When writing a borrower contract, ensure that the `ProcessLoan` handler has proper permissions. It should only be
callable when your contract has previously requested a loan and only by the `neutron-flashloans` contract.
20 changes: 15 additions & 5 deletions contracts/dao/neutron-flashloans/src/msg.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,15 @@ pub struct InstantiateMsg {

#[cw_serde]
pub enum ExecuteMsg {
/// The main entry point of the flashloan contract. The caller of the `RequestLoan` message is
/// expected to be a smart contract that implements the `BorrowerInterface`.
///
/// This handler processes valiation of the request, records the loan details in storage, sends
/// requested funds to the caller and then invokes the caller's `ProcessLoan` handler. After the
/// `ProcessLoan` execution, the flashloans contract checks whether the borrower has done all
/// required payments (loan + fee). If check fails, the entire transaction will be reverted.
///
/// Borrower cannot request another loan until `ProcessLoan` execution has been finished.
RequestLoan {
/// The amount that the borrower contract requests; there should be no
/// duplicate denoms and no zero amounts.
Expand All @@ -31,13 +40,14 @@ pub enum ExecuteMsg {
},
}

/// Defines the interface for the borrowing contract. The borrowing
/// contract is required to implement a handler for the ProcessLoan message,
/// and to return loan_amount + fee to the return_address after executing its
/// custom logic, otherwise an error will be raised, and the whole transaction
/// will be rolled back.
/// Defines the interface for the borrowing contract — a contract that is capable of taking loans
/// from the flashloan contract.
#[cw_serde]
pub enum BorrowerInterface {
/// The handler the borrower should place the loan usage logic within. At the time of this
/// handler execution, the borrower will have the requested amount of funds received. The
/// borrower must return the `loan_amount` plus the `fee` to the `return_address` by the end
/// of this handler.
ProcessLoan {
/// Specifies the address to which the borrower must return the loan amount AND pay the fees.
return_address: Addr,
Expand Down

0 comments on commit 781f430

Please sign in to comment.