# Ocean.sol

Github link: <https://github.com/Shell-Protocol/Shell-Protocol/blob/main/src/ocean/Ocean.sol>

## WRAPPED\_ETHER\_ID()

```solidity
/// @notice this is the oceanId used for shETH
/// @dev hexadecimal(ascii("shETH"))
uint256 public immutable WRAPPED_ETHER_ID;
```

This function is automatically created because `WRAPPED_ETHER_ID` variable is declared as `public`.&#x20;

It should...

1. Return the Ocean ID for Ether (Wrapping Ether into Ocean would result in shETH, so it would be a shETH ID actually).

## unwrapFeeDivisor()

```solidity
/// @notice Used to calculate the unwrap fee
/// unwrapFee = unwrapAmount / unwrapFeeDivisor
/// Because this uses integer division, the fee is always rounded down
/// If unwrapAmount < unwrapFeeDivisor, unwrapFee == 0
uint256 public unwrapFeeDivisor;
```

This function is automatically created because `unwrapFeeDivisor` variable is declared as `public`. A fee is charged by the Ocean on each unwrap.

It should...

1. Return the correct unwrap fee divisor.

## doInteraction()

{% code overflow="wrap" %}

```solidity
/**
* @notice Execute interactions `interaction`
* @notice Does not need ids because a single interaction does not require
*  the accounting system
* @dev MUST HAVE nonReentrant modifier.
* @dev call to _doInteraction() binds msg.sender to userAddress
* @param interaction Executed to produce a set of balance updates
*/
function doInteraction(
    Interaction calldata interaction
) external override nonReentrant returns (
    uint256 burnId,
    uint256 burnAmount,
    uint256 mintId,
    uint256 mintAmount
);
```

{% endcode %}

| Parameter Name | Type               | Description                                                                   |
| -------------- | ------------------ | ----------------------------------------------------------------------------- |
| interaction    | Interaction struct | one of nine different interactions types encoded via the `Interaction` struct |

Interaction Struct Params:

| Parameter Name            | Type    | Description                                                                                                                     |
| ------------------------- | ------- | ------------------------------------------------------------------------------------------------------------------------------- |
| interactionTypeAndAddress | bytes32 | a bytes32 array that combines both the interaction type and the address of the external contract called during this interaction |
| inputToken                | uint256 | input token Ocean ID                                                                                                            |
| outputToken               | uint256 | output token Ocean ID                                                                                                           |
| specifiedAmount           | uint256 | amount of the specified token                                                                                                   |
| metadata                  | bytes32 | bytes32 array of arbitrary data, during 721/1155 and wraps and unwraps we use this filed to pass token ID                       |

This function executes a single interaction.&#x20;

It should...

1. Execute a single forwarded interaction.

## doMultipleInteractions()

{% code overflow="wrap" %}

```solidity
/**
* @notice Execute interactions `interactions` with tokens `ids`
* @notice ids must include all tokens invoked during the transaction
* @notice ids are used for memory allocation in the intra-transaction
*  accounting system.
* @dev MUST HAVE nonReentrant modifier.
* @dev call to _doMultipleInteractions() binds msg.sender to userAddress
* @param interactions Executed to produce a set of balance updates
* @param ids Ocean IDs of the tokens invoked by the interactions.
*/
function doMultipleInteractions(
    Interaction[] calldata interactions,
    uint256[] calldata ids
) external payable override nonReentrant returns (
    uint256[] memory burnIds,
    uint256[] memory burnAmounts,
    uint256[] memory mintIds,
    uint256[] memory mintAmounts
);
```

{% endcode %}

| Parameter Name | Type                  | Description                                                                                                         |
| -------------- | --------------------- | ------------------------------------------------------------------------------------------------------------------- |
| interactions   | Interaction struct\[] | an array of interactions which can be one of nine different interactions types encoded via the `Interaction` struct |
| ids            | uint256\[]            | an array of tokens Ocean IDs used by the interactions forwarded by the interactions param                           |

Interaction Struct Params:

| Parameter Name            | Type    | Description                                                                                                                     |
| ------------------------- | ------- | ------------------------------------------------------------------------------------------------------------------------------- |
| interactionTypeAndAddress | bytes32 | a bytes32 array that combines both the interaction type and the address of the external contract called during this interaction |
| inputToken                | uint256 | input token Ocean ID                                                                                                            |
| outputToken               | uint256 | output token Ocean ID                                                                                                           |
| specifiedAmount           | uint256 | amount of the specified token                                                                                                   |
| metadata                  | bytes32 | bytes32 array of arbitrary data, during 721/1155 and wraps and unwraps we use this filed to pass token ID                       |

This function executes multiple interactions in order they were stacked in the array of interactions. Use this function to compose different interactions, i.e. Ocean native primitives.

It should...

1. Execute a a list of forwarded interactions.

## forwardedDoInteraction()

{% code overflow="wrap" %}

```solidity
/**
* @notice Execute interactions `interactions` on behalf of `userAddress`
* @notice Does not need ids because a single interaction does not require
*  the overhead of the intra-transaction accounting system
* @dev MUST HAVE nonReentrant modifier.
* @dev MUST HAVE onlyApprovedForwarder modifer.
* @dev call to _doMultipleInteractions() forwards the userAddress
* @param interaction Executed to produce a set of balance updates
* @param userAddress interactions are executed on behalf of this address
*/
function forwardedDoInteraction(
    Interaction calldata interaction,
    address userAddress
)
external override nonReentrant onlyApprovedForwarder(userAddress) returns (
    uint256 burnId,
    uint256 burnAmount,
    uint256 mintId,
    uint256 mintAmount
);
```

{% endcode %}

| Parameter Name | Type               | Description                                                                   |
| -------------- | ------------------ | ----------------------------------------------------------------------------- |
| interaction    | Interaction struct | one of nine different interactions types encoded via the `Interaction` struct |
| userAddress    | address            | address on which behalf to  execute interactions                              |

Interaction Struct Params:

<table><thead><tr><th>Parameter Name</th><th width="297.3333333333333">Type</th><th>Description</th></tr></thead><tbody><tr><td>interactionTypeAndAddress</td><td>bytes32</td><td>a bytes32 array that combines both the interaction type and the address of the external contract called during this interaction</td></tr><tr><td>inputToken</td><td>uint256</td><td>input token Ocean ID</td></tr><tr><td>outputToken</td><td>uint256</td><td>output token Ocean ID</td></tr><tr><td>specifiedAmount</td><td>uint256</td><td>amount of the specified token</td></tr><tr><td>metadata</td><td>bytes32</td><td>bytes32 array of arbitrary data, during 721/1155 and wraps and unwraps we use this filed to pass token ID</td></tr></tbody></table>

This function executes a single interaction on behalf the address that was forwarded as `userAddress` param.

It should...

1. Revert if address forwarded as `userAddress` param hasn't approved message sender to pass interactions on its behalf via i`sApprovedForAll` ERC1155 method.
2. Execute a single forwarded interaction.

## forwardedDoMultipleInteractions()

{% code overflow="wrap" %}

```solidity
/**
* @notice Execute interactions `interactions` with tokens `ids` on behalf of `userAddress`
* @notice ids must include all tokens invoked during the transaction
* @notice ids are used for memory allocation in the intra-transaction
*  accounting system.
* @dev MUST HAVE nonReentrant modifier.
* @dev MUST HAVE onlyApprovedForwarder modifer.
* @dev call to _doMultipleInteractions() forwards the userAddress
* @param interactions Executed to produce a set of balance updates
* @param ids Ocean IDs of the tokens invoked by the interactions.
* @param userAddress interactions are executed on behalf of this address
*/
function forwardedDoMultipleInteractions(
    Interaction[] calldata interactions,
    uint256[] calldata ids,
    address userAddress
)
external payable override nonReentrant onlyApprovedForwarder(userAddress) returns (
    uint256[] memory burnIds,
    uint256[] memory burnAmounts,
    uint256[] memory mintIds,
    uint256[] memory mintAmounts
);
```

{% endcode %}

| Parameter Name | Type                  | Description                                                                                                         |
| -------------- | --------------------- | ------------------------------------------------------------------------------------------------------------------- |
| interactions   | Interaction struct\[] | an array of interactions which can be one of nine different interactions types encoded via the `Interaction` struct |
| ids            | unit256\[]            | an array of interaction IDs forwarded by the first param Interaction struct\[]                                      |
| userAddress    | address               | address on which behalf to  execute interactions                                                                    |

Interaction Struct Params:

<table><thead><tr><th>Parameter Name</th><th width="297.3333333333333">Type</th><th>Description</th></tr></thead><tbody><tr><td>interactionTypeAndAddress</td><td>bytes32</td><td>a bytes32 array that combines both the interaction type and the address of the external contract called during this interaction</td></tr><tr><td>inputToken</td><td>uint256</td><td>input token Ocean ID</td></tr><tr><td>outputToken</td><td>uint256</td><td>output token Ocean ID</td></tr><tr><td>specifiedAmount</td><td>uint256</td><td>amount of the specified token</td></tr><tr><td>metadata</td><td>bytes32</td><td>bytes32 array of arbitrary data, during 721/1155 and wraps and unwraps we use this filed to pass token ID</td></tr></tbody></table>

This function executes multiple interactions in order they were stacked in the array of interactions  on behalf the address that was forwarded as the `userAddress` param. Use this function to compose different interactions, i.e. Ocean native primitives.

It should...

1. Revert if address forwarded as `userAddress` param hasn't approved message sender to pass interactions on its behalf via i`sApprovedForAll` ERC1155 method.
2. Execute a single forwarded interaction.

## registerNewTokens()

```solidity
/**
* @dev Registered Tokens are tokens issued directly on the ocean's 1155 ledger.
* @dev These are tokens that cannot be wrapped or unwrapped.
* @dev We don't validate the inputs.  The happy path usage is for callers
*  to obtain authority over tokens that have their ids derived from
*  successive nonces.
*
*  registerNewTokens(0, n):
*      _calculateOceanId(caller, 0)
*      _calculateOceanId(caller, 1)
*      ...
*      _calculateOceanId(caller, n)
*
*  Since the ocean tracks the one to one relationship of:
*    token => authority
*  but not the one to many relationship of:
*    authority => tokens
*  it is nice UX to be able to re-derive the tokens on the fly from the
*  authority's address and successive (predictable) nonces are used.
*
*  However, if the caller wants to use this interface in a different way,
*  they could easily make a call like:
*  registerNewTokens($SOME_NUMBER, 1); to use $SOME_NUMBER
*  as the nonce.  A user could request to buy an in-ocean nft with a
*  specific seed value, and the external contract gains authority over
*  this id on the fly in order to sell it.
*
*  If the caller tries to reassert authority over a token they've already
*  registered, they just waste gas.  If a caller expects to create
*  new tokens over time, it should track how many tokens it has already
*  created
* @dev the guiding philosophy is to track only essential information in
*  the Ocean's state, and let users (both EOAs and contracts) track other
*  information as they see fit.
* @param currentNumberOfTokens the starting nonce
* @param numberOfAdditionalTokens the number of new tokens registered
* @return oceanIds Ocean IDs of the tokens the caller now has authority over
*/
function registerNewTokens(
   uint256 currentNumberOfTokens,
   uint256 numberOfAdditionalTokens
) external override returns (
   uint256[] memory oceanIds
);
```

| Parameter Name           | Type    | Description                                  |
| ------------------------ | ------- | -------------------------------------------- |
| currentNumberOfTokens    | uint256 | current number of tokens as a starting nonce |
| numberOfAdditionalTokens | unit256 | the number of new tokens to be registered    |

This functions should register new tokens that are issued directly on the Ocean's ERC-1155 ledger.

## supportsInterface()

A standard implementation of ERC165 supportsInterface method which checks for `IERC1155`, `IERC1155MetadataURI` or `IERC165` implementations. For more details see check the official [EIP-165 page](https://eips.ethereum.org/EIPS/eip-165) or OpenZeppelin [Introspection page](https://docs.openzeppelin.com/contracts/3.x/api/introspection).

## Other methods

Below is a list of other public and external methods accessible in the Ocean smart contract, which may not be as relevant. Most of these methods are implemented as part of the ERC-1155 specification.

### uri()

This function is an implementation of the ERC-1155 `uri` method. For more details, check the  Metadata section of the [EIP-1155 page](https://eips.ethereum.org/EIPS/eip-1155#metadata).

### onERC721Received()

This function is an implementation of the `onERC721Received` method from the `IERC721Receiver` interface contract. For more details, check the interface ERC721TokenReceiver part of the [specification section](https://eips.ethereum.org/EIPS/eip-721#specification) of the EIP-721 page.

### onERC1155Received()

This function is an implementation of the `onERC1155Received` method from the `IERC1155TokenReceiver` interface contract. For more details, check the [ERC-1155 Token Receiver section](https://eips.ethereum.org/EIPS/eip-1155#erc-1155-token-receiver) of the EIP-1155 page.

### onERC1155BatchReceived()

This function is an implementation of the `onERC1155BatchReceived` method from the `IERC1155TokenReceiver` interface contract. For more details check the [ERC-1155 Token Receiver section](https://eips.ethereum.org/EIPS/eip-1155#erc-1155-token-receiver) of the EIP-1155 page.

### balanceOf()

This function is an implementation of the `balanceOf` method from the `IERC1155` interface contract. For more details, check the [specification section](https://eips.ethereum.org/EIPS/eip-1155#specification) of the EIP-1155 page.

### balanceOfBatch()

This function is an implementation of the `balanceOfBatch` method from the `IERC1155` interface contract. For more details, check the [specification](https://eips.ethereum.org/EIPS/eip-1155#specification) and [Batch Balance](https://eips.ethereum.org/EIPS/eip-1155#batch-balance) sections of the EIP-1155 page.

### setApprovalForAll()

This function is an implementation of the `setApprovalForAll` method from the `IERC1155` interface contract. For more details, check the [specification](https://eips.ethereum.org/EIPS/eip-1155#specification) and [Approval](https://eips.ethereum.org/EIPS/eip-1155#approval) sections of the EIP-1155 page.

### isApprovedForAll()

This function is an implementation of the `isApprovedForAll` method from the `IERC1155` interface contract. For more details, check the [specification](https://eips.ethereum.org/EIPS/eip-1155#specification) and [Approval](https://eips.ethereum.org/EIPS/eip-1155#approval) sections of the EIP-1155 page.

### safeTransferFrom()

This function is an implementation of the `safeTransferFrom` method from the `IERC1155` interface contract. For more details, check the [specification](https://eips.ethereum.org/EIPS/eip-1155#specification) and [Safe Transfer Rules](https://eips.ethereum.org/EIPS/eip-1155#safe-transfer-rules) sections of the EIP-1155 page.

### safeBatchTransferFrom()

This function is an implementation of the `safeBatchTransferFrom` method from the `IERC1155` interface contract. For more details, check the [specification](https://eips.ethereum.org/EIPS/eip-1155#specification) and [Batch Transfers](https://eips.ethereum.org/EIPS/eip-1155#batch-transfers) sections of the EIP-1155 page.
