본문 바로가기
Blockchain

[Blockchain] 이더리움 Geth 사용 방법

by 개발자 염상진 2022. 7. 5.

로컬 테스트넷에서 Geth 실행하는 방법

Geth를 로컬 테스트넷에서 실행하기 위해서는 먼저 데이터 디렉토리 + genesis.json 파일이 준비되어야 합니다. 데이터 디렉토리에서는 송수신한 블록 데이터 및 계정 정보를 저장하게 됩니다. genesis.json 파일은 블록체인의 Genesis 블록 정보가 저장됩니다.

git에서 Clone한 go-ethereum 프로젝트 내에 test_data 디렉토리를 생성하고, genesis.json 파일을 생성합니다.

 

 

정상적으로 이더리움 블록체인에 접속 가능한지 확인합니다.

$ geth

 

 

 

이더리움 테스트넷에서 사용할 계정 생성

다음 명령을 입력한 후 2번의 password를 입력하면 정상적으로 account가 생성됩니다. Public Key가 생성되는데, 이 키는 genesis.json 파일에서 사용하게 되므로 복사해둬야 합니다.

$ geth --datadir test_data account new

Password: 
Repeat password: 

Your new key was generated

Public address of the key:   [계정 공개키]
Path of the secret key file: test_data/keystore/UTC--2022-07-05T09-31-52.070080860Z--4d3ef63064ccc938a80791a0d80df671aceae315

- You can share your public address with anyone. Others need it to interact with you.
- You must NEVER share the secret key with anyone! The key controls access to your funds!
- You must BACKUP your key file! Without the key, it's impossible to access account funds!
- You must REMEMBER your password! Without the password, it's impossible to decrypt the key!

 

계정을 생성한 후 생성된 계정 목록을 다음 명령으로 확인할 수 있습니다. 

$ geth --datadir test_data account list
INFO [07-05|18:33:42.793] Maximum peer count                       ETH=50 LES=0 total=50
INFO [07-05|18:33:42.793] Smartcard socket not found, disabling    err="stat /run/pcscd/pcscd.comm: no such file or directory"
INFO [07-05|18:33:42.794] Set global gas cap                       cap=50,000,000
Account #0: {4d3ef63064ccc938a80791a0d80df671aceae315} keystore:///root/go-ethereum/test_data/test_data/keystore/UTC--2022-07-05T09-31-52.070080860Z--4d3ef63064ccc938a80791a0d80df671aceae315

 

 

Genesis Block 생성하는 방법

블록체인을 시작하기 위해서는 genesis Block을 생성해야 합니다. 앞에서 생성했던 genesis.json 파일에 아래 내용을 입력합니다. 계정을 생성할 때 반환된 공개주소를 계정 주소값으로 입력합니다.

$ vim genesis.json

{
        "config":{
                "chainId" : 8484,
                "homesteadBlock" : 0,
                "eip150Block": 0,
                "eip155Block": 0,
                "eip158Block": 0
        },
        "difficulty" : "20",
        "gasLimit" : "2100000",
        "alloc" : {
                "계정 주소값": {"balance" : "300000"}
        }
}
  • config : 이더리움 관련 설정을 포함합니다.
  • config.chainId : 현재 chain을 구별하는 값입니다. 유효한 데이터 전송을 악의적으로 반복시켜 공격하는 replay attack을 방지합니다. 
  • config.homesteadBlock : 이더리움은 <프론티어><홈스테드><메트로폴리스><세레니티> 4단계 로드맵을 가지고 있습니다. 속성값 0은 true를 의미합니다. 
  • config.eip155Block : EIP(Ethereum Improvement Proposal)은 개발자들이 이더리움을 발전시키기 위해 아이디어를 제안하는 것을 의미합니다. EIP155는 replay attack을 방지하기 위한 아이디어입니다. 
  • config.eip150Block : EIP150은 IO가 많이 발생하는 작업에 대한 가스 변경 비용을 위한 설정.
  • config.eip158Block : EIP158은 계정의 상태가 변경되고, 변경된 결과값에 의해 계정의 논스와 밸런스가 0이 되고 code / storage가 빈값이 되는 경우 계정을 삭제하자는 아이디어 입니다.
  • difficulty : 채굴 난이도를 의미합니다. 높은 값일 수록 난이도가 올라갑니다. 테스트넷에서는 높은 난이도가 불필요하므로 낮은 값을 할당합니다.
  • gasLimit : 블록마다 담을 수 있는 가스 한도를 설정합니다. 즉, 하나의 블록에 담을 수 있는 트랜잭션의 량을 설정합니다. 값이 클 수록 많은 트랜잭션을 블록에 담을 수 있습니다. 
  • alloc : genesis block이 생성되면서 동시에 할당된 주소로 밸런스가 할당됩니다. alloc에서 사용하는 값의 단위는 wei 입니다. 

 

 

  • parentHash : 부모 블록의 해시값 / genesis block은 부모 블록이 존재하지 않습니다.
  • coinbase : genesis block 채굴시 주어지는 보상. 
  • nounce, mixhash : 블록이 정당하게 채굴되었는지 증명. mixhash는 nounce 값을 찾기 위한 중간 계산값으로 공격자가 부당한 nounce값으로 블록을 생성하는 경우를 적발합니다. 단 genesis block은 채굴을 통해 생성하지 않고 json 파일로 생성하기 때문에 mixhash 및 nounce 값이 필요하지 않습니다. 
  • timestamp : 블록이 생성된 시점을 나타냅니다. 블록간 생성 간격이 짧다면 난이도가 쉽다는 뜻이므로 난이도가 조절됩니다.

 

Genesis Block 생성 및 초기화

아래 명령어로 위에서 작성한 genesis.json 파일을 실행해 제네시스 블록을 생성하고 초기화 합니다.

$ geth --datadir test_data init test_data/genesis.json

root@8a8da77d4483:~/go-ethereum/test_data# geth --datadir test_data init ./genesis.json
INFO [07-05|21:56:15.789] Maximum peer count                       ETH=50 LES=0 total=50
INFO [07-05|21:56:15.791] Smartcard socket not found, disabling    err="stat /run/pcscd/pcscd.comm: no such file or directory"
INFO [07-05|21:56:15.797] Set global gas cap                       cap=50,000,000
INFO [07-05|21:56:15.800] Allocated cache and file handles         database=/root/go-ethereum/test_data/test_data/geth/chaindata cache=16.00MiB handles=16
INFO [07-05|21:56:15.831] Opened ancient database                  database=/root/go-ethereum/test_data/test_data/geth/chaindata/ancient readonly=false
INFO [07-05|21:56:15.831] Writing custom genesis block 
INFO [07-05|21:56:15.833] Persisted trie from memory database      nodes=1 size=142.00B time="834.046µs" gcnodes=0 gcsize=0.00B gctime=0s livenodes=1 livesize=0.00B
INFO [07-05|21:56:15.834] Successfully wrote genesis state         database=chaindata hash=9a4612..be0494
INFO [07-05|21:56:15.834] Allocated cache and file handles         database=/root/go-ethereum/test_data/test_data/geth/lightchaindata cache=16.00MiB handles=16
INFO [07-05|21:56:15.864] Opened ancient database                  database=/root/go-ethereum/test_data/test_data/geth/lightchaindata/ancient readonly=false
INFO [07-05|21:56:15.864] Writing custom genesis block 
INFO [07-05|21:56:15.868] Persisted trie from memory database      nodes=1 size=142.00B time="524.732µs" gcnodes=0 gcsize=0.00B gctime=0s livenodes=1 livesize=0.00B
INFO [07-05|21:56:15.870] Successfully wrote genesis state         database=lightchaindata hash=9a4612..be0494

 

현재 생성된 test_data 디렉토리의 구조는 다음과 같습니다.

root@8a8da77d4483:~/go-ethereum/test_data# tree ./  
./
|-- genesis.json
`-- test_data
    |-- geth
    |   |-- LOCK
    |   |-- chaindata
    |   |   |-- 000001.log
    |   |   |-- CURRENT
    |   |   |-- LOCK
    |   |   |-- LOG
    |   |   |-- MANIFEST-000000
    |   |   `-- ancient
    |   |       |-- FLOCK
    |   |       |-- bodies.0000.cdat
    |   |       |-- bodies.cidx
    |   |       |-- bodies.meta
    |   |       |-- diffs.0000.rdat
    |   |       |-- diffs.meta
    |   |       |-- diffs.ridx
    |   |       |-- hashes.0000.rdat
    |   |       |-- hashes.meta
    |   |       |-- hashes.ridx
    |   |       |-- headers.0000.cdat
    |   |       |-- headers.cidx
    |   |       |-- headers.meta
    |   |       |-- receipts.0000.cdat
    |   |       |-- receipts.cidx
    |   |       `-- receipts.meta
    |   |-- lightchaindata
    |   |   |-- 000001.log
    |   |   |-- CURRENT
    |   |   |-- LOCK
    |   |   |-- LOG
    |   |   |-- MANIFEST-000000
    |   |   `-- ancient
    |   |       |-- FLOCK
    |   |       |-- bodies.0000.cdat
    |   |       |-- bodies.cidx
    |   |       |-- bodies.meta
    |   |       |-- diffs.0000.rdat
    |   |       |-- diffs.meta
    |   |       |-- diffs.ridx
    |   |       |-- hashes.0000.rdat
    |   |       |-- hashes.meta
    |   |       |-- hashes.ridx
    |   |       |-- headers.0000.cdat
    |   |       |-- headers.cidx
    |   |       |-- headers.meta
    |   |       |-- receipts.0000.cdat
    |   |       |-- receipts.cidx
    |   |       `-- receipts.meta
    |   `-- nodekey
    `-- keystore
        `-- UTC--2022-07-05T09-31-52.070080860Z--4d3ef63064ccc938a80791a0d80df671aceae315

7 directories, 46 files

 

Geth 실행하기

genesis block을 생성했다면 geth를 실행합니다.

$ geth --networkid 8484 --nodiscover --datadir test_data -allow-insecure-unlock --http.addr 0.0.0.0 --http --http.port 8545 --http.corsdomain "*" --http.api="db,eth,net,web3,personal,web3,miner,admin" --miner.threads 1 console 2>> test_data/geth.log
  • --datadir test_data : 데이터 디렉토리 지정
  • networkid 8484 : 네트워크 식별자
  • http :과거 rpc에서 http로 변경됨
  • http.addr "ip" : 현재 사용중인 IP를 입력합니다.
  • http.port "port" : 사용하고자 하는 port 번호를 입력합니다.
  • http.corsdomain "*" : 접속 가능한 RPC 클라이언트 URL을 지정합니다. "*"(와일드카드)는 전체 허용을 의미합니다.
  • -nodiscover : 생성자 노드를 다른 노드에서 검색 못하게 막는 옵션입니다. 제네시스 블록과 네트워크 ID의 블록들이 연결되는 것을 방지합니다.
  • http.api "db,eth,net,web3,personal" : RPC에 접근 가능한 API 들을 지정합니다. geth 내에서 사용가능한 명령어들입니다.
  • -maxpeers 0 : 생성자 노드에 연결 가능한 노드의 수를 지정합니다. 0이면 다른 노드들과 연결하지 않습니다.
  • console : 대화형 자바스크립트 콘솔
  • 2>> /home/ngle/data_testnet/geth.log : 에러를 해당 경로의 파일에 저장합니다. 로그 옵션입니다.

 

정상적으로 실행되었다면 Geth Javascript console 화면을 확인할 수 있습니다.

Welcome to the Geth JavaScript console!

instance: Geth/v1.10.20-stable-8f2416a8/linux-amd64/go1.18.1
coinbase: 0x4d3ef63064ccc938a80791a0d80df671aceae315
at block: 0 (Thu Jan 01 1970 09:00:00 GMT+0900 (KST))
 datadir: /root/go-ethereum/test_data/test_data
 modules: admin:1.0 debug:1.0 eth:1.0 ethash:1.0 miner:1.0 net:1.0 personal:1.0 rpc:1.0 txpool:1.0 web3:1.0

To exit, press ctrl-d or type exit
>

 

 

 

Etherbase 설정하는 방법

이더리움에는 2가지 계정이 존재합니다. EOA(Externally Owned Account)는 일반 사용자가 사용하는 계정입니다. 비밀키로 관리되며 이더를 송금하거나 컨트랙트를 실행할 수 있습니다. Contract 계정은 컨트랙트를 블록체인에 배포할 때 생성됩니다. 

 

새로운  EOA 계정 추가하는 방법

geth console에서 EOA를 생성하는 명령입니다.

> personal.newAccount('password')
"0x1a9d8ca79769da4e7fd27e94f688e6438761f14a"

기존 계정 확인

> eth.accounts
["0x4d3ef63064ccc938a80791a0d80df671aceae315", "0x1a9d8ca79769da4e7fd27e94f688e6438761f14a"]

 

채굴 보상 계정 선택하기(Etherbase)

이더리움에서 채굴시 보상받는 계정은 Etherbase입니다. Etherbase를 설정하기 위해서는 eth.coinbase 변수에 저장해야 합니다. 디폴트 값은 eth.accounts[0]이 지정됩니다. 새로 생성한 계정을 Etherbase로 설정합니다.

> miner.setEtherbase(personal.listAccounts[1]);
true

계정 잔고 확인하기

잔액 단위는 wei입니다.

> eth.getBalance(eth.accounts[0])
300000

잔액 단위를 변경할 수 있습니다. 

> web3.fromWei(eth.getBalance(eth.accounts[0]), 'ether')
3e-13

 

생성된 블록 개수 조회

> eth.blockNumber
0

 

N 번째 블록 조회

0번째 블록은 제네시스 블록입니다.

>  eth.getBlock(0)
{
  difficulty: 20,
  extraData: "0x",
  gasLimit: 2100000,
  gasUsed: 0,
  hash: "0x9a4612f7ee07f0769f9b976ce5fccff2ffa09207a97a17cb9d008f170bbe0494",
  logsBloom: "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
  miner: "0x0000000000000000000000000000000000000000",
  mixHash: "0x0000000000000000000000000000000000000000000000000000000000000000",
  nonce: "0x0000000000000000",
  number: 0,
  parentHash: "0x0000000000000000000000000000000000000000000000000000000000000000",
  receiptsRoot: "0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421",
  sha3Uncles: "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347",
  size: 504,
  stateRoot: "0xa5a0b65df588b85b9c6ac613e01ffaf793715180082300ee6a1a00958cae0916",
  timestamp: 0,
  totalDifficulty: 20,
  transactions: [],
  transactionsRoot: "0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421",
  uncles: []
}

 

계정 상태 조회

계정의 잠김 상태를 확인할 수 있습니다.

> personal.listWallets[0].status
"Locked"

계정 해제하는 방법

> personal.unlockAccount(eth.accounts[0])
Unlock account 0x4d3ef63064ccc938a80791a0d80df671aceae315
Passphrase: 
true
personal.unlockAccount('주소', '비밀번호', '유효기간) // 0은 geth 종료시 까지 unlock 유지

> personal.unlockAccount(eth.accounts[1], 'password', 0)
true

 

 

이더리움 채굴하는 방법

위에서 이더리움 채굴 보상 계정을 선택했습니다. 채굴을 진행하면 해당 계정으로 시작합니다. miner.start(N)으로 채굴을 시작합니다. N은 스레드 개수입니다.

> miner.setEtherbase(eth.accounts[1])
true


> miner.start(10)
null

 

채굴을 시작하면 이더리움 테스트 네트워크 내 블록개수가 증가하는 것을 확인할 수 있습니다.

> eth.blockNumber
5
> eth.blockNumber
6
> eth.blockNumber
7

채굴 종료는 miner.stop()을 사용합니다.

> miner.stop()
null

 

 

 

 

 

 

[Blockchain] 이더리움 Geth 설치 방법(Ubuntu Docker)

Ubuntu 환경에서 이더리움 Geth 클라이언트를 실행할 수 있습니다. 우분투 환경은 Docker Hub에서 이미지를 가져와서 실행합니다. 물론 자체적으로 우분투를 메인 OS로 사용하시면 바로 Geth를 실행해

about-tech.tistory.com

 

 

[Blockchain] 클레이튼(Klaytn) 블록체인 이란?

제3자의 개입 없이 모든 사람이 연결될 수 있고, 분산화된 형태로 데이터를 관리할 수 있게 됩니다. 중개자가 없으므로, 각 참여자들은 하나의 합의에 이르러야 이해관계 조정이 가능해지고, 전

about-tech.tistory.com

 

 

[Blockchain] 채굴(Mining)이란?

블록체인에서 채굴(Mining)이란 블록체인 네트워크 상에서 발생하는 트랜잭션들을 검증하고, 분산원장에 기록하는 행위를 통해 보상으로 암호화폐를 얻는 과정입니다. 땅에 묻혀 있는 광물을 캐

about-tech.tistory.com

 

댓글