zl程序教程

您现在的位置是:首页 >  其他

当前栏目

NFT铸造拍卖交易平台怎么开发?合约部署流程

流程部署开发 怎么 合约 NFT 拍卖 交易平台
2023-06-13 09:15:26 时间

拍卖,顾名思义就是在规定的时间和场所,按照一定的章程和规则,将要拍卖的货物向买主进行展示,公开叫价竞购,最后由拍卖人把货物卖给出价最高的买主的一种交易方式。传统的拍卖一般都是实体物品,随着nft的发展,拍卖从传统的实物衍生到了nft数字艺术,也给疫情之下的拍卖行业寻求了一条转型之路。

对于nft,更多的是尝试创建和购买,拍卖接触的相对较少,区块链上有公链和测试链,公链是需要费用,测试链就不用,为了演示,今天就用一款开源的工具FInger NFT来给大家演示一下nft拍卖怎么进行出价购买。

我们模拟一个拍卖合约,其中在这个程序中,并且初始便定义了商品信息,跟拍卖时间和起拍价,对于这三个东西,我们都是可以直接修改的,自己根据需求定义一个函数,用于推送商品等。

//SPDX-License-Identifier: MIT
pragma solidity ^0.8.7;
 
//定义合约名为auction
contract auction{
 
    //定义拍卖行
    address payable public Auctioneer;
 
    //定义商品基本信息
    mapping(uint256 => string) commodity;
 
    //定义商品处于的状态
    mapping(uint256 => string) state;
 
    //状态池
    mapping(uint256 => uint256) Astate;
 
    //定义商品的归属人
    mapping(uint256 => address) belong;
 
    //定义买方交易金额的买方地址
    mapping(uint256 => address payable) maxAdd;
 
    //定义买方支付的交易金额
    mapping(uint256 => uint256) bond;
 
    //定义拍卖开始时间
    uint256 timeStamp;
 
    //定义拍卖结束时间
    uint256 endtime;
 
    //定义起拍价
    uint256 StartPrice;
 
    //定义拍卖时长
    uint256 AuctionTime;
 
    //定义出价记录的结构体
    struct Bidder {
        address addr; //出价者地址
        uint256 amount; //出价金额
        uint256 bidAt; //出价时间
    }
 
    //定义映射,用于记录不同编号商品对应的出价记录
    mapping(uint256 => Bidder[]) record;
 
    //单个出价记录
    Bidder bidder;
 
    //出价记录数组
    Bidder[] bidders;
 
    //变量初始化
    constructor (address _owner){
        //拍卖发起人(拍卖行)
        Auctioneer = payable(_owner);
 
        //商品信息初始化
        commodity[0] = "xuperchain Lamborghini";
        commodity[1] = "xuperchain Benz";
        commodity[2] = "xuperchain BMW";
 
        //商品的状态初始化
        state[0] = "To be auctioned";          //定义待拍卖状态
        state[1] = "Under auction";            //定义拍卖中状态
        state[2] = "Successfully Sold";        //定义成功出售状态
        state[3] = "Flow beat";                //定义流拍状态
        
        //拍卖时长初始化
        AuctionTime = 10 minutes;
        
        //商品价格初始化
        StartPrice = 100;
    }
 
   
 
    //定义 Authentication 函数修饰器,用于在执行函数时,用于判断是否为合约发起人
    modifier Authentication{
        require (Auctioneer == msg.sender, "You're not an auction promoter");
        _;
    }
 
    /*
    @notice 将商品上架
    @dev 商品状态必须为 "To be auctioned"
    @param uint8 numb -商品编号
    */
    function PutOnShelves(uint8 numb) public Authentication{
 
        //使用require对商品状态进行判断,当商品状态不为0时,说明我们的商品已经上架过并进行了其他操作
        require (Astate[numb] == 0, "The goods are under auction or have been sold");
 
        //使用require判断目前是否还有其他的商品正在进行拍卖
        require (timeStamp == 0 && endtime == 0, "Currently, there are goods under auction");
 
        //使用require判断当前商品是否存在
        require(bytes(commodity[numb]).length != 0,"The current product does not exist");
 
        //修改商品状态
        Astate[numb] = 1;
 
        //定义商品开始拍卖时间
        timeStamp= block.timestamp;
 
        //定义结束时间,为开始拍卖的十分钟后
        endtime = block.timestamp + 10 minutes;
 
        //商品归属者转移
        belong[numb] = Auctioneer;
    }
    
    /*
    @notice 实现买方对拍卖中的商品进行加价
    @dev 在 msg.value 中设置的加价的金额应该大于默认值 100
    @param uint8 numb -商品编号
    */
    function MarkUp (uint8 numb) public payable {
 
        //使用require对加价者身份进行判断,拍卖方无法对已上架的商品进行加价
        require(msg.sender != Auctioneer ,"The product is already in the auction, you cannot increase the price");
 
        //使用require判断当前时间是否在拍卖时间内
        require(block.timestamp < endtime && block.timestamp > timeStamp,"It'numb not auction time yet");
 
        //使用require对当前商品的状态进行判断,加价的商品需要是正在拍卖的商品
        require(Astate[numb] == 1, "The current commodity auction has ended");
 
        //对加价判断是否为第一次出价
        if(bond[numb] == 0){
 
            //使用require判断第一次加价的金额不能低于起拍价
            require(msg.value > StartPrice,"Your bid amount must be greater than the starting price");
        }
 
        //使用require对加价金额判断不能低于上一次出价
        require(msg.value > bond[numb], "Your bid amount must be greater than the current price");
 
        //调用AmoutRollback函数,将上一个出价者的交易金额退回,并收取当前出价者的交易金额
        AmountRollback(numb);
 
        //调用AddTransaction函数,保存商品的出价记录
        AddTransaction(numb);
 
        //满足以上条件则说明买方的价格满足加价的要求,将当前的商品归属转移至此买方的地址
        belong[numb] = msg.sender;
    }
 
    /*
    @notice 实现将买方支付的保证金退回
    @param uint8 numb -商品编号
    */
    function AmountRollback(uint8 numb) internal {
 
        //将上一个支付交易金额退回
        maxAdd[numb].transfer(bond[numb]);
 
        //收取当前出价者的交易金额
        bond[numb] = msg.value;
 
        //记录出价者的地址
        maxAdd[numb] = payable(msg.sender);
    }
 
    /*
    @notice 实现记录商品的交易记录
    @param uint8 numb -商品编号
    */
    function AddTransaction(uint8 numb) internal {
 
        //将出价者的地址,金额,出价时间戳,添加进bidder
        bidder = Bidder(msg.sender,msg.value,block.timestamp);
        bidders.push(bidder);
        record[numb] = bidders;
    }
 
    /*
    @notice 实现修改商品的状态为  ”成功出售状态“ 或 ”流拍状态“
    @param uint8 numb -商品编号
    */
    function closeAuction(uint8 numb) public Authentication{
 
        //使用require对当前时间跟拍卖发起时间进行比较,判断当前是否处于拍卖结束
        require(block.timestamp > endtime, "Auction in progress");
 
        //通过if语句进行判断,当前商品的归属是否是拍卖发起人
        if (belong[numb] == Auctioneer){
 
            //修改状态为流拍
            Astate[numb] = 3;
        }else{
 
            //将商品状态修改为成功拍卖
            Astate[numb] = 2;
        }
 
        //重置商品起拍时间
        timeStamp = 0;
 
        //重置商品结束拍卖时间
        endtime = 0;
    }
 
    /*
    @notice 实现获取商品归属者
    @param uint8 numb -商品编号
    @return address -商品拥有者的地址
    */
    function getBelong(uint8 numb) public view Authentication returns(address){
        return belong[numb];
    }
 
    /*
    @notice 实现获取当前地址
    */
    function getSender() public view returns(address){
        return msg.sender;
    }
 
    /*
    @notice 实现获取对应商品的最高叫价
    @param uint8 numb -商品编号
    @return uint256 -商品最高叫价
    */
    function getMaxMoney(uint8 numb)public view returns(uint256){
 
        //使用require对商品的状态进行判断,需要对在拍卖的商品才能查询当前最高叫价
        require (Astate[numb] == 1 ,"The current product is not available");
 
        //没有买方出价,则返回商品初始价格
        if(bond[numb] == 0){
            return StartPrice;
        }else{
            return bond[numb];
        }
        
    }
    /*
    @notice 实现获取对应商品的状态
    @param uint8 numb -商品编号
    @return string -商品状态
    */
    function getStatus(uint8 numb)public view returns(string memory){
        return state[Astate[numb]];
    }
 
    /*
    @notice 实现获取对应编号的商品信息
    @parma uint8 numb -商品编号
    @return string -商品的名称
            uint256 -拍卖时长
            uint256 -起拍价格
            uint256 -拍卖结束时间
    */
    function getItemInformation(uint8 numb)public view returns(string memory,uint256,uint256,uint256){
 
        return (commodity[numb],AuctionTime,StartPrice,endtime);
    }
 
    /*
    @notice 实现获取对应编号的拍卖记录
    @dev 该方法只能有交易发起者调用
    @param uint8 numb -商品编号
    @return Bidder[] -交易记录的数组
    */
    function getRecord(uint8 numb) public view Authentication returns (Bidder[] memory){
        return record[numb];
    }
 
     /*
    @notice 实现拍卖发起人提取保证金
    @dev 该方法只能有交易发起者调用
    @param uint8 numb -商品编号
    */
    function getAuctionMoney(uint8 numb) public payable Authentication{
 
        //使用require判断商品拍卖是否结束
        require(block.timestamp > endtime, "The current auction is not over yet. You can't extract");
 
        //使用require判断商品是否成功出售
        require(Astate[numb] == 2 ,"Your product was not successfully sold");
 
        //使用require判断保证金内是否还有余额
        require(bond[numb] != 0, "You have initiated transaction amount withdrawal");
 
        //拍卖发起人提取保证金
        payable(msg.sender).transfer(bond[numb]);
 
        //重置保证金为0
        bond[numb] = 0;
    }
 
    /*
    @notice 销毁合约
    @dev 该方法只能由合约发起者调用,并且该方法只有在拍卖全部结束后才能调用,调用后合约将被销毁
    */
    function destroy() public virtual Authentication{
        for (uint256 i;i < 3;i++){
            require(Astate[i] != 1 && bond[i] == 0,"The goods are still in the auction or you haven't withdrawn the amount");
        }
    }
}