Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ERC1155 and ERC721 Floor Wrappers #79

Open
wants to merge 24 commits into
base: master
Choose a base branch
from
Open

Conversation

ScreamingHawk
Copy link
Contributor

Wrapper contracts to enable collection wide "floor" trading for ERC1155 and ERC721 tokens via Niftyswap.

Copy link
Contributor

@PhABC PhABC left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Reviewed both wrapper files and they are great. One thing is that people can currently send ERC-721 that aren't wrapped to the contract and people would be able to claim them via withdraw, which might be a benefit?

}

function initialize(address tokenAddr) external {
if (initialized || msg.sender != factory) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know this is for being on the "safe side" but I don't think initialized is needed here. With msg.sender + token != address(0) should be enough.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How about going further and only relying on msg.sender != factory? Will be safe since the factory will only ever call this function once immediately after creation.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

token != address(0) has practically no additional cost (since the store has to be written too anyway), you are right that msg.sender != factory should be enough, but having an extra "correctness" check doesn't hurt in this case.

* @param data Data to pass to ERC-1155 receiver.
* @notice Users must first approve this contract address on the ERC-1155 contract.
*/
function deposit(uint256[] memory tokenIds, uint256[] memory tokenAmounts, address recipient, bytes calldata data)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not just use the ERC1155 callback for this? With this approach you always need to do an approve, and by using a callback you can also support wrapping by just sending to this contract.

Copy link
Contributor Author

@ScreamingHawk ScreamingHawk Mar 30, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This function signature is nice because it allowed deposits to be swapped immediately.

tokenIds, sellAmounts, exchangeAddr, NiftyswapTestHelper.encodeSellTokens(USER, prices[0], block.timestamp)

To enable this with the ERC1155 Received callback I'd need to do some manual parsing of the data which feels messy.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Keep in mind decoding data is a pattern that we already use heavily on Niftyswap, you can implement it in a "clean" way be using abi.decode and a struct definition.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was worried about tightly coupling Niftyswap structs to the wrapper implementation. Found a way around it so I prefer this approach now too.

@ScreamingHawk ScreamingHawk force-pushed the floor-wrappers branch 2 times, most recently from 19cba2b to c9e2f37 Compare April 3, 2023 00:59
@ScreamingHawk ScreamingHawk requested a review from Agusx1211 April 3, 2023 21:13
Copy link
Member

@Agusx1211 Agusx1211 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me, just this small comment

}

if (_ids.length != 1) {
revert InvalidERC1155Received();
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this code reachable? the wrapper implements a single token ID, so you shouldn't be able to test this.
If so then it should be better to use an assert(_ids.length == 1).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It could be called with multiple token ids if the amounts are 0.

safeBatchTransferFrom(_from, _to, [1, 2, 3], [0, 0, 0])

We could override the transfer functions and check for id length there instead. That would be more gas efficient too

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

^ In progress. Blocked by 0xsequence/erc-1155#101

_deposit(_amounts, _data);
} else if (msg.sender == address(this)) {
// Withdraw
if (_ids.length != 1) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same here, this should be an assert

@ScreamingHawk
Copy link
Contributor Author

This PR is becoming stale. Shall we merge this @Agusx1211 @acrylix @PhABC ?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants