솔리디티의 payable
은 두 종류로 나뉩니다
// address payable
payable(address);
address payable public owner;
// function payable
function sellItem() external payable {}
address payable
은 주소의 타입을 지정하는 것을 뜻합니다transfer()
와 send()
함수)이 내장됩니다function payable
은 함수의 속성을 지정합니다payable
을 선언한 함수에서만 이더를 보낼 수 있습니다payable
로 선언된 함수는 외부에서 호출될 때 이더를 전송하는 기능을 수행할 수 있게 됩니다간단한 마켓 기능을 구현해보면서 두 payable
속성을 이해해봅시다
[appleShop.sol]
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract AppleShop {
// myApple[key] = value, 기본값 0이 할당됩니다
mapping(address=> uint256) myApple;
function buy() public payable {
myApple[msg.sender] += 1;
}
// 내가 가진 사과갯수 표시 (call)
function get() public view returns(uint256) {
return myApple[msg.sender];
}
// 전체 환불. 갯수를 지정하고 싶다면 매개변수를 받아야 합니다
function sell() public payable {
uint256 refund = myApple[msg.sender] * 10 ** 18;
myApple[msg.sender] = 0;
// payable() ~ 인자는 어드레스(string), 리턴값은 어카운트(object)로 이해하기
// transfer ~ CA가 가진 이더를 사용자 어카운트에 전달하는 payable 내장 메서드
payable(msg.sender).transfer(refund);
}
}
[AppleShop.jsx]
import AppleShopContract from "../contracts/AppleShop.json";
import { useState, useEffect } from "react";
const AppleShop = ({ web3, account }) => {
const [deployed, setDeployed] = useState(null);
const [apple, setApple] = useState(0);
const buy = async () => {
await deployed.methods.buy().send({
from : account,
value : web3.utils.toWei('1', 'ether') // 이더는 CA에 전달됩니다
})
}
const sell = async () => {
await deployed.methods.sell().send({
from : account,
})
}
useEffect(() => {
if (!deployed) return;
deployed.methods.get().call().then(setApple);
}, [deployed]);
useEffect(() => {
if (!web3) return;
const instance = new web3.eth.Contract(
AppleShopContract.abi,
AppleShopContract.networks[1685407833552].address // window.ethereum에서 chainId로 가져올 수도 있습니다
);
setDeployed(instance);
}, []);
return (
<>
<h2>사과 가격: 1 ETH</h2>
<h2>현재 계정 : {account}</h2>
<div>
내가 가진 사과 갯수 : {apple}
<br />
<button onClick={buy}>Buy</button>
</div>
<div>
총 사과 판매 가격 1 ETH
<br />
<button onClick={sell}>Sell</button>
</div>
</>
);
};
buy()
실행 후 CA의 밸런스
sell()
실행 후 CA의 밸런스