안녕하세요~ 날씨가 엄청 시원해졌네요~
이번에는 이더리움 컨트렉트에 대해 간단하게 알아보겠습니다.
이더리움 컨트렉트의 특징은 아래와 같습니다.
단일거래로 블럭체인에 디플로이 됨
변하지않는 주소로 유일하게 식별가능
한번 디플로이되면 코드가 안 변함
트랜젝션을 통해 데이터를 보낼 수 있음
콜포인트를 통해 함수를 제공하는 것처럼 할 수 있음
-> 이렇게 코딩하면 컨트렉트 데이터 변경 가능
-> 이렇게 코딩하면 데이터에 대한 정보 호출 가능
-> 이렇게 코딩하면 특정 공개키 또는 기타 제약조건으로 제한 가능코드에서 다른 지시가 없으면 2개의 개별 인스턴스는 같은 컨트렉트라도 서로에 대한 정보가 없으며 상호 작용하지 않음
다른 지시가 없으면 주어진 컨트렉트를 추적하는 중앙 등록(central registry)이 없음
특히 컨트렉트 인스턴스가 디플로이된 주소를 잊어버릴 경우 블록체인 바이트 코드나 보낸사람 주소나 다른 방법으로 찾아야 함
배포되기 전, 이더리움 컨트렉트는 자바 클래스 컴파일처럼 바이트코드 바이너리 타입이 필요합니다.
- 상위언어로 만들어진 코드
- 이 코드는 컴파일러에 의해 바이트코드와 함수 디스크립트 셋(Application Binary Interface)로 컴파일
- 바이트코드는 다른 매개변수와 함께 트렌젝션으로 압축
- 트렌젝션은 어카운트 디플로잉 컨트렉트가 승인
- 승인 된 트렌젝션이 블록체인에 접수 됨
- 이 트렌젝션을 수행하는 블록이 마이닝 됨
직접 한번 해보기로 하죠~ 우선 컴파일러를 설치합니다.
$ sudo apt-get install -y solc
[그림 3-1] 컴파일 버전 확인
[그림 3-1] 처럼 “solc --version”을 입력하면 버전을 확인 하실 수 있습니다.
지난번에 “net42” 연습에서 geth로그들 올라가는데 입력하기 불편하셨을껍니다.
$ geth --datadir ~/.ethereum/net42 --networkid 42 console
$ geth attach ipc:/home/XXX/.ethereum/net42/geth.ipc
이렇게 하시면 조금 편한 환경이 될 것입니다. XXX는 각자 컴퓨터 사용자 이름입니다.
Faucet 디플로이를 해볼껀데, 힘든 방법으로 해서 왜 Faucet이 약간의 이더가 필요한지 확인할 수 있습니다. 아래 코드를 “Faucet.sol”로 저장합니다.
pragma solidity ^0.4.11;
contract Faucet {
address public owner;
uint256 sendAmount;
function Faucet() payable {
owner = msg.sender;
sendAmount = 1 ether;
}
function getBalance() returns (uint) {
return this.balance;
}
function getWei() {
msg.sender.transfer(sendAmount);
}
function sendWei(address toWhom) {
toWhom.transfer(sendAmount);
}
function getSendAmount() returns (uint256) {
return sendAmount;
}
function killMe() returns (bool) {
require(msg.sender == owner);
suicide(owner);
return true;
}
function () payable {}
}
뭘 만들꺼냐면 블록체인으로 보내는 바이트코드나 바이너리와 컨트렉트가 디플로이 되면서 상호작용하는 ABI를 만드려고 합니다.
JQ도 인스톨합니다. JQ는 JSON 컨텐츠를 다루는데 도움을 줍니다.
$ sudo apt-get install jq
[그림 3-2] JQ 사용
$ solc --combined-json abi,bin Faucet.sol > Faucet.json
로 보내주고
$ cat Faucet.json | jq '.'
해주면 [그림 3-2]처럼 나오는데 bin key는 바이트코드로 식별되고, abi key는 함수 인터페이스를 설명하고 있는데 사용자에게 친숙한 방식으로 호출 할 수 있습니다.
Geth 콘솔에서 사용하기 위해서 “$ cat Faucet.json”를 입력하면 [그림 3-3] 처럼 나오는데 복사를 해두세요
[그림 3-3] Faucet.json
[그림 3-4] Faucet 콘솔 창 입력
Geth 콘솔 창에서 [그림 3-4]처럼 아까 복사한 것을 붙여줍니다. faucetCompiled변수는 geth 콘솔을 나가면 사라집니다.
[그림 3-5] 컨트렉트 상호작용 준비
사용가능한 메소드를 정의하고 인터페이스에게 전달할껀데 [그림 3-5]처럼 ABI 인터페이스가 문자열 형식으로 작성되었으므로 붙여줍니다. 복잡한 자바스크립트 객체를 볼 수 잇는데 이제부터 Web3 컨트렉트 객체로 참조할 것 입니다. 아직 디플로이 되지 않았기 때문에 이 Web3 컨트렉트 객체는 인스턴스가 아닙니다.
Geth는 컴파일된 컨트렉트를 디플로이하는 기능이 있는데 약간의 이더가 필요합니다. 마이닝을 시작하시고~ [그림 3-6] 처럼 나오게 됩니다.
[그림 3-6] 컨트렉트 디플로이
var deployTransationObject = { from: eth.coinbase, data: "0x" + faucetCompiled.contracts["Faucet.sol:Faucet"].bin, value: web3.toWei(1, "ether"), gas: 1000000 };
var faucetInstancePartial = faucetContract.new(deployTransationObject);
잘 안보일꺼 같아서 크게 한번 더 적었습니다. eth.coinbase 언락은 하셨죠?
컨트렉트가 디플로이 인스턴스를 트렌젝션으로 보내고 Web3 컨트랙트 인스턴스를 반환했지만 주소가 부족하네요. 주소를 즉시 알아야하지만 설정하지 않았기 때문에 아직 채굴되지 않았네요.
[그림 3-7] 컨트렉트 주소 확인
반환된 주소는 우리 컨트렉트의 변경 불가능한 고유한 주소 인데 보낸사람의 트렌젝션 nonce와 보낸사람 주소 해시 값으로부터 계산 됩니다.
[그림 3-8] Faucet 주소 확인
[그림 3-9] 디플로이 위치 코드 확인
[그림 3-9]와 같이 이 코드를 faucetCompiled.contracts [ "Faucet.sol : Faucet"]. bin과 비교하면 deployedBinary의 전체 길이와 일치한다는 것을 알 수 있습니다.
지금까지 이더리움 컨트렉트에 대해서 소개해봤는데요~
조만간? 좀 더 심화된 이더리움 컨트렉트 내용도 포스팅 할 수 있지 않을까?하고 생각해 봅니다~
질문은 언제든지 환영입니다~
thanks for information!
Downvoting a post can decrease pending rewards and make it less visible. Common reasons:
Submit
you're welcome
Downvoting a post can decrease pending rewards and make it less visible. Common reasons:
Submit