드디어 수업에 web3.js를 시작했다. 스마트 컨트랙트와 react의 연결, 블록체인상 데이터를 react와 어떻게 연결시키는지 궁금했는데 난이도는 좀 있을 것 같다.
일단 시작은 PowerShell로 시작(윈도우 기준).
npm -v
node -v
npm view web3 version
npm view react version
각 종 버전 확인
위에서는 npm view web3 version 입력하니 1.8.1이라고 나왔지만(카이카스 지갑 연동하면서 설치된건지?) 후에
const Web3 = require("web3");
명령어를 입력하니
Uncaught Error: Cannot find module 'web3'
에러가 나서 결국 web3를 다시 설치.
npm install web3
다시 순서로 돌아가서
node
const Web3 = require("web3");
를 입력하면 undefined가 뜸.
Web3
를 입력하면
[Function: Web3] {
version: '1.8.1',
utils: {
_fireError: [Function: _fireError],
_jsonInterfaceMethodToString: [Function: _jsonInterfaceMethodToString],
_flattenTypes: [Function: _flattenTypes],
randomHex: [Function: randomHex],
BN: [Function: BNwrapped],
isBN: [Function: isBN],
isBigNumber: [Function: isBigNumber],
isHex: [Function: isHex],
isHexStrict: [Function: isHexStrict],
sha3: [Function: sha3] { _Hash: [Function: keccak256] },
sha3Raw: [Function: sha3Raw],
keccak256: [Function: sha3] { _Hash: [Function: keccak256] },
soliditySha3: [Function: soliditySha3],
soliditySha3Raw: [Function: soliditySha3Raw],
encodePacked: [Function: encodePacked],
isAddress: [Function: isAddress],
checkAddressChecksum: [Function: checkAddressChecksum],
toChecksumAddress: [Function: toChecksumAddress],
toHex: [Function: toHex],
toBN: [Function: toBN],
bytesToHex: [Function: bytesToHex],
hexToBytes: [Function: hexToBytes],
hexToNumberString: [Function: hexToNumberString],
hexToNumber: [Function: hexToNumber],
toDecimal: [Function: hexToNumber],
numberToHex: [Function: numberToHex],
fromDecimal: [Function: numberToHex],
hexToUtf8: [Function: hexToUtf8],
hexToString: [Function: hexToUtf8],
toUtf8: [Function: hexToUtf8],
stripHexPrefix: [Function: stripHexPrefix],
utf8ToHex: [Function: utf8ToHex],
stringToHex: [Function: utf8ToHex],
fromUtf8: [Function: utf8ToHex],
hexToAscii: [Function: hexToAscii],
toAscii: [Function: hexToAscii],
asciiToHex: [Function: asciiToHex],
fromAscii: [Function: asciiToHex],
unitMap: {
noether: '0',
wei: '1',
kwei: '1000',
Kwei: '1000',
babbage: '1000',
femtoether: '1000',
mwei: '1000000',
Mwei: '1000000',
lovelace: '1000000',
picoether: '1000000',
gwei: '1000000000',
Gwei: '1000000000',
shannon: '1000000000',
nanoether: '1000000000',
nano: '1000000000',
szabo: '1000000000000',
microether: '1000000000000',
micro: '1000000000000',
finney: '1000000000000000',
milliether: '1000000000000000',
milli: '1000000000000000',
ether: '1000000000000000000',
kether: '1000000000000000000000',
grand: '1000000000000000000000',
mether: '1000000000000000000000000',
gether: '1000000000000000000000000000',
tether: '1000000000000000000000000000000'
},
toWei: [Function: toWei],
fromWei: [Function: fromWei],
padLeft: [Function: leftPad],
leftPad: [Function: leftPad],
padRight: [Function: rightPad],
rightPad: [Function: rightPad],
toTwosComplement: [Function: toTwosComplement],
isBloom: [Function: isBloom],
isUserEthereumAddressInBloom: [Function: isUserEthereumAddressInBloom],
isContractAddressInBloom: [Function: isContractAddressInBloom],
isTopic: [Function: isTopic],
isTopicInBloom: [Function: isTopicInBloom],
isInBloom: [Function: isInBloom],
compareBlockNumbers: [Function: compareBlockNumbers],
toNumber: [Function: toNumber]
},
modules: {
Eth: [Function: Eth] { givenProvider: null, providers: [Object] },
Net: [Function: Net] { givenProvider: null, providers: [Object] },
Personal: [Function: Personal] { givenProvider: null, providers: [Object] },
Shh: [Function: Shh] { givenProvider: null, providers: [Object] },
Bzz: [Function: Bzz] { givenProvider: null }
},
givenProvider: null,
providers: {
WebsocketProvider: [Function: WebsocketProvider],
HttpProvider: [Function: HttpProvider],
IpcProvider: [Function: IpcProvider]
}
}
막 뜸
Web3.modules.Eth
입력
[Function: Eth] {
givenProvider: null,
providers: {
WebsocketProvider: [Function: WebsocketProvider],
HttpProvider: [Function: HttpProvider],
IpcProvider: [Function: IpcProvider]
}
}
뜸
const web3 = new Web3("https://cloudflare-eth.com");
Provider가 https://cloudflare-eth.com. 이 안에 우리가 다루는것들이 들어감(메인넷에서 진행할지, 테스트넷에서 진행할지 등등)
이제 소문자 web3를 입력하면
web3
Web3 {
currentProvider: [Getter/Setter],
_requestManager: RequestManager {
provider: HttpProvider {
withCredentials: undefined,
timeout: 0,
headers: undefined,
agent: undefined,
connected: false,
host: 'https://cloudflare-eth.com',
httpsAgent: [Agent]
},
providers: {
WebsocketProvider: [Function: WebsocketProvider],
HttpProvider: [Function: HttpProvider],
IpcProvider: [Function: IpcProvider]
},
subscriptions: Map(0) {}
},
givenProvider: null,
providers: {
WebsocketProvider: [Function: WebsocketProvider],
HttpProvider: [Function: HttpProvider],
IpcProvider: [Function: IpcProvider]
},
_provider: HttpProvider {
withCredentials: undefined,
timeout: 0,
headers: undefined,
agent: undefined,
connected: false,
host: 'https://cloudflare-eth.com',
httpsAgent: Agent {
_events: [Object: null prototype],
_eventsCount: 2,
_maxListeners: undefined,
defaultPort: 443,
protocol: 'https:',
options: [Object: null prototype],
requests: [Object: null prototype] {},
sockets: [Object: null prototype] {},
freeSockets: [Object: null prototype] {},
keepAliveMsecs: 1000,
keepAlive: true,
maxSockets: Infinity,
maxFreeSockets: 256,
scheduling: 'lifo',
maxTotalSockets: Infinity,
totalSocketCount: 0,
maxCachedSessions: 100,
_sessionCache: [Object],
[Symbol(kCapture)]: false
}
},
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
BatchRequest: [Function: bound Batch],
extend: [Function: ex] {
formatters: {
inputDefaultBlockNumberFormatter: [Function: inputDefaultBlockNumberFormatter], inputBlockNumberFormatter: [Function: inputBlockNumberFormatter],
inputCallFormatter: [Function: inputCallFormatter],
inputTransactionFormatter: [Function: inputTransactionFormatter],
inputAddressFormatter: [Function: inputAddressFormatter],
inputPostFormatter: [Function: inputPostFormatter],
inputLogFormatter: [Function: inputLogFormatter],
inputSignFormatter: [Function: inputSignFormatter],
inputStorageKeysFormatter: [Function: inputStorageKeysFormatter],
outputProofFormatter: [Function: outputProofFormatter],
outputBigNumberFormatter: [Function: outputBigNumberFormatter],
outputTransactionFormatter: [Function: outputTransactionFormatter],
outputTransactionReceiptFormatter: [Function: outputTransactionReceiptFormatter],
outputBlockFormatter: [Function: outputBlockFormatter],
outputLogFormatter: [Function: outputLogFormatter],
outputPostFormatter: [Function: outputPostFormatter],
outputSyncingFormatter: [Function: outputSyncingFormatter]
},
utils: {
_fireError: [Function: _fireError],
_jsonInterfaceMethodToString: [Function: _jsonInterfaceMethodToString],
_flattenTypes: [Function: _flattenTypes],
randomHex: [Function: randomHex],
BN: [Function: BNwrapped],
isBN: [Function: isBN],
isBigNumber: [Function: isBigNumber],
isHex: [Function: isHex],
isHexStrict: [Function: isHexStrict],
sha3: [Function],
sha3Raw: [Function: sha3Raw],
keccak256: [Function],
soliditySha3: [Function: soliditySha3],
soliditySha3Raw: [Function: soliditySha3Raw],
encodePacked: [Function: encodePacked],
isAddress: [Function: isAddress],
checkAddressChecksum: [Function: checkAddressChecksum],
toChecksumAddress: [Function: toChecksumAddress],
toHex: [Function: toHex],
toBN: [Function: toBN],
bytesToHex: [Function: bytesToHex],
hexToBytes: [Function: hexToBytes],
hexToNumberString: [Function: hexToNumberString],
hexToNumber: [Function: hexToNumber],
toDecimal: [Function: hexToNumber],
numberToHex: [Function: numberToHex],
fromDecimal: [Function: numberToHex],
hexToUtf8: [Function: hexToUtf8],
hexToString: [Function: hexToUtf8],
toUtf8: [Function: hexToUtf8],
stripHexPrefix: [Function: stripHexPrefix],
utf8ToHex: [Function: utf8ToHex],
stringToHex: [Function: utf8ToHex],
fromUtf8: [Function: utf8ToHex],
hexToAscii: [Function: hexToAscii],
toAscii: [Function: hexToAscii],
asciiToHex: [Function: asciiToHex],
fromAscii: [Function: asciiToHex],
unitMap: [Object],
toWei: [Function: toWei],
fromWei: [Function: fromWei],
padLeft: [Function: leftPad],
leftPad: [Function: leftPad],
padRight: [Function: rightPad],
rightPad: [Function: rightPad],
toTwosComplement: [Function: toTwosComplement],
isBloom: [Function: isBloom],
isUserEthereumAddressInBloom: [Function: isUserEthereumAddressInBloom],
isContractAddressInBloom: [Function: isContractAddressInBloom],
isTopic: [Function: isTopic],
isTopicInBloom: [Function: isTopicInBloom],
isInBloom: [Function: isInBloom],
compareBlockNumbers: [Function: compareBlockNumbers],
toNumber: [Function: toNumber]
},
Method: [Function: Method]
},
version: '1.8.1',
utils: {
_fireError: [Function: _fireError],
_jsonInterfaceMethodToString: [Function: _jsonInterfaceMethodToString],
_flattenTypes: [Function: _flattenTypes],
randomHex: [Function: randomHex],
BN: [Function: BNwrapped],
isBN: [Function: isBN],
isBigNumber: [Function: isBigNumber],
isHex: [Function: isHex],
isHexStrict: [Function: isHexStrict],
sha3: [Function: sha3] { _Hash: [Function: keccak256] },
sha3Raw: [Function: sha3Raw],
keccak256: [Function: sha3] { _Hash: [Function: keccak256] },
soliditySha3: [Function: soliditySha3],
soliditySha3Raw: [Function: soliditySha3Raw],
encodePacked: [Function: encodePacked],
isAddress: [Function: isAddress],
checkAddressChecksum: [Function: checkAddressChecksum],
toChecksumAddress: [Function: toChecksumAddress],
toHex: [Function: toHex],
toBN: [Function: toBN],
bytesToHex: [Function: bytesToHex],
hexToBytes: [Function: hexToBytes],
hexToNumberString: [Function: hexToNumberString],
hexToNumber: [Function: hexToNumber],
toDecimal: [Function: hexToNumber],
numberToHex: [Function: numberToHex],
fromDecimal: [Function: numberToHex],
hexToUtf8: [Function: hexToUtf8],
hexToString: [Function: hexToUtf8],
toUtf8: [Function: hexToUtf8],
stripHexPrefix: [Function: stripHexPrefix],
utf8ToHex: [Function: utf8ToHex],
stringToHex: [Function: utf8ToHex],
fromUtf8: [Function: utf8ToHex],
hexToAscii: [Function: hexToAscii],
toAscii: [Function: hexToAscii],
asciiToHex: [Function: asciiToHex],
fromAscii: [Function: asciiToHex],
unitMap: {
noether: '0',
wei: '1',
kwei: '1000',
Kwei: '1000',
babbage: '1000',
femtoether: '1000',
mwei: '1000000',
Mwei: '1000000',
lovelace: '1000000',
picoether: '1000000',
gwei: '1000000000',
Gwei: '1000000000',
shannon: '1000000000',
nanoether: '1000000000',
nano: '1000000000',
szabo: '1000000000000',
microether: '1000000000000',
micro: '1000000000000',
finney: '1000000000000000',
milliether: '1000000000000000',
milli: '1000000000000000',
ether: '1000000000000000000',
kether: '1000000000000000000000',
grand: '1000000000000000000000',
mether: '1000000000000000000000000',
gether: '1000000000000000000000000000',
tether: '1000000000000000000000000000000'
},
toWei: [Function: toWei],
fromWei: [Function: fromWei],
padLeft: [Function: leftPad],
leftPad: [Function: leftPad],
padRight: [Function: rightPad],
rightPad: [Function: rightPad],
toTwosComplement: [Function: toTwosComplement],
isBloom: [Function: isBloom],
isUserEthereumAddressInBloom: [Function: isUserEthereumAddressInBloom],
isContractAddressInBloom: [Function: isContractAddressInBloom],
isTopic: [Function: isTopic],
isTopicInBloom: [Function: isTopicInBloom],
isInBloom: [Function: isInBloom],
compareBlockNumbers: [Function: compareBlockNumbers],
toNumber: [Function: toNumber]
},
eth: <ref *1> Eth {
currentProvider: [Getter/Setter],
_requestManager: RequestManager {
provider: [HttpProvider],
providers: [Object],
subscriptions: Map(0) {}
},
givenProvider: null,
providers: {
WebsocketProvider: [Function: WebsocketProvider],
HttpProvider: [Function: HttpProvider],
IpcProvider: [Function: IpcProvider]
},
_provider: HttpProvider {
withCredentials: undefined,
timeout: 0,
headers: undefined,
agent: undefined,
connected: false,
host: 'https://cloudflare-eth.com',
httpsAgent: [Agent]
},
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
BatchRequest: [Function: bound Batch],
extend: [Function: ex] {
formatters: [Object],
utils: [Object],
Method: [Function: Method]
},
handleRevert: [Getter/Setter],
defaultCommon: [Getter/Setter],
defaultHardfork: [Getter/Setter],
defaultChain: [Getter/Setter],
transactionPollingTimeout: [Getter/Setter],
transactionPollingInterval: [Getter/Setter],
transactionConfirmationBlocks: [Getter/Setter],
transactionBlockTimeout: [Getter/Setter],
blockHeaderTimeout: [Getter/Setter],
defaultAccount: [Getter/Setter],
defaultBlock: [Getter/Setter],
maxListenersWarningThreshold: [Getter/Setter],
clearSubscriptions: [Function: bound ],
removeSubscriptionById: [Function: bound ],
net: Net {
currentProvider: [Getter/Setter],
_requestManager: [RequestManager],
givenProvider: null,
providers: [Object],
_provider: [HttpProvider],
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
BatchRequest: [Function: bound Batch],
extend: [Function],
getId: [Function],
isListening: [Function],
getPeerCount: [Function],
getNetworkType: [Function: bound getNetworkType]
},
accounts: Accounts {
currentProvider: [Getter/Setter],
_requestManager: [RequestManager],
givenProvider: null,
providers: [Object],
_provider: [HttpProvider],
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
_ethereumCall: [Object],
wallet: [Wallet]
},
personal: Personal {
currentProvider: [Getter/Setter],
_requestManager: [RequestManager],
givenProvider: null,
providers: [Object],
_provider: [HttpProvider],
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
BatchRequest: [Function: bound Batch],
extend: [Function],
net: [Net],
defaultAccount: [Getter/Setter],
defaultBlock: [Getter/Setter],
getAccounts: [Function],
newAccount: [Function],
unlockAccount: [Function],
lockAccount: [Function],
importRawKey: [Function],
sendTransaction: [Function],
signTransaction: [Function],
sign: [Function],
ecRecover: [Function]
},
Contract: [Function: Contract] {
setProvider: [Function (anonymous)],
defaultAccount: null,
defaultBlock: 'latest',
transactionBlockTimeout: 50,
transactionConfirmationBlocks: 24,
transactionPollingTimeout: 750,
transactionPollingInterval: 1000,
blockHeaderTimeout: 10,
handleRevert: false,
_requestManager: [RequestManager],
_ethAccounts: [Accounts],
currentProvider: [HttpProvider]
},
Iban: [class Iban],
abi: ABICoder {},
ens: ENS {
eth: [Circular *1],
_detectedAddress: null,
_lastSyncCheck: null,
registry: [Getter],
resolverMethodHandler: [Getter],
registryAddress: [Getter/Setter]
},
getNodeInfo: [Function: send] { method: [Method], request: [Function: bound ] },
getProtocolVersion: [Function: send] { method: [Method], request: [Function: bound ] },
getCoinbase: [Function: send] { method: [Method], request: [Function: bound ] },
isMining: [Function: send] { method: [Method], request: [Function: bound ] },
getHashrate: [Function: send] { method: [Method], request: [Function: bound ] },
isSyncing: [Function: send] { method: [Method], request: [Function: bound ] },
getGasPrice: [Function: send] { method: [Method], request: [Function: bound ] },
getFeeHistory: [Function: send] { method: [Method], request: [Function: bound ] },
getAccounts: [Function: send] { method: [Method], request: [Function: bound ] },
getBlockNumber: [Function: send] { method: [Method], request: [Function: bound ] },
getBalance: [Function: send] { method: [Method], request: [Function: bound ] },
getStorageAt: [Function: send] { method: [Method], request: [Function: bound ] }, getCode: [Function: send] { method: [Method], request: [Function: bound ] },
getBlock: [Function: send] { method: [Method], request: [Function: bound ] },
getUncle: [Function: send] { method: [Method], request: [Function: bound ] },
getBlockTransactionCount: [Function: send] { method: [Method], request: [Function: bound ] },
getBlockUncleCount: [Function: send] { method: [Method], request: [Function: bound ] },
getTransaction: [Function: send] { method: [Method], request: [Function: bound ] },
getTransactionFromBlock: [Function: send] { method: [Method], request: [Function: bound ] },
getTransactionReceipt: [Function: send] { method: [Method], request: [Function: bound ] },
getTransactionCount: [Function: send] { method: [Method], request: [Function: bound ] },
sendSignedTransaction: [Function: send] { method: [Method], request: [Function: bound ] },
signTransaction: [Function: send] { method: [Method], request: [Function: bound ] },
sendTransaction: [Function: send] { method: [Method], request: [Function: bound ] },
sign: [Function: send] { method: [Method], request: [Function: bound ] },
call: [Function: send] { method: [Method], request: [Function: bound ] },
estimateGas: [Function: send] { method: [Method], request: [Function: bound ] },
submitWork: [Function: send] { method: [Method], request: [Function: bound ] },
getWork: [Function: send] { method: [Method], request: [Function: bound ] },
getPastLogs: [Function: send] { method: [Method], request: [Function: bound ] },
getChainId: [Function: send] { method: [Method], request: [Function: bound ] },
requestAccounts: [Function: send] { method: [Method], request: [Function: bound ] },
getProof: [Function: send] { method: [Method], request: [Function: bound ] },
getPendingTransactions: [Function: send] { method: [Method], request: [Function: bound ] },
createAccessList: [Function: send] { method: [Method], request: [Function: bound ] },
subscribe: [Function (anonymous)]
},
shh: Shh {
currentProvider: [Getter/Setter],
_requestManager: RequestManager {
provider: [HttpProvider],
providers: [Object],
subscriptions: Map(0) {}
},
givenProvider: null,
providers: {
WebsocketProvider: [Function: WebsocketProvider],
HttpProvider: [Function: HttpProvider],
IpcProvider: [Function: IpcProvider]
},
_provider: HttpProvider {
withCredentials: undefined,
timeout: 0,
headers: undefined,
agent: undefined,
connected: false,
host: 'https://cloudflare-eth.com',
httpsAgent: [Agent]
},
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
BatchRequest: [Function: bound Batch],
extend: [Function: ex] {
formatters: [Object],
utils: [Object],
Method: [Function: Method]
},
net: Net {
currentProvider: [Getter/Setter],
_requestManager: [RequestManager],
givenProvider: null,
providers: [Object],
_provider: [HttpProvider],
setProvider: [Function (anonymous)],
setRequestManager: [Function (anonymous)],
BatchRequest: [Function: bound Batch],
extend: [Function],
getId: [Function],
isListening: [Function],
getPeerCount: [Function]
},
subscribe: [Function (anonymous)],
getVersion: [Function: send] { method: [Method], request: [Function: bound ] },
getInfo: [Function: send] { method: [Method], request: [Function: bound ] },
setMaxMessageSize: [Function: send] { method: [Method], request: [Function: bound ] },
setMinPoW: [Function: send] { method: [Method], request: [Function: bound ] },
markTrustedPeer: [Function: send] { method: [Method], request: [Function: bound ] },
newKeyPair: [Function: send] { method: [Method], request: [Function: bound ] },
addPrivateKey: [Function: send] { method: [Method], request: [Function: bound ] },
deleteKeyPair: [Function: send] { method: [Method], request: [Function: bound ] },
hasKeyPair: [Function: send] { method: [Method], request: [Function: bound ] },
getPublicKey: [Function: send] { method: [Method], request: [Function: bound ] }, getPrivateKey: [Function: send] { method: [Method], request: [Function: bound ] },
newSymKey: [Function: send] { method: [Method], request: [Function: bound ] },
addSymKey: [Function: send] { method: [Method], request: [Function: bound ] },
generateSymKeyFromPassword: [Function: send] { method: [Method], request: [Function: bound ] },
hasSymKey: [Function: send] { method: [Method], request: [Function: bound ] },
getSymKey: [Function: send] { method: [Method], request: [Function: bound ] },
deleteSymKey: [Function: send] { method: [Method], request: [Function: bound ] }, newMessageFilter: [Function: send] { method: [Method], request: [Function: bound ] },
getFilterMessages: [Function: send] { method: [Method], request: [Function: bound ] },
deleteMessageFilter: [Function: send] { method: [Method], request: [Function: bound ] },
post: [Function: send] { method: [Method], request: [Function: bound ] },
unsubscribe: [Function: send] { method: [Method], request: [Function: bound ] }
},
bzz: Bzz {
givenProvider: null,
currentProvider: null,
isAvailable: [Function (anonymous)],
upload: [Function (anonymous)],
download: [Function (anonymous)]
}
}
이렇게 엄청난 정보가 들어온다. 자세히 살펴보면 각 종 함수나 이더단위, 등등 이 들어있는 것 같다.
더 자세히 eth에 관해 보고싶으면
web3.eth
를 입력하면 하면 된다.
https://web3js.readthedocs.io/en/v1.8.1/index.html 를 들어가면 api Reference들을 자세히 볼수있다.
실습을 하나 해보면
현재 이더에 마지막 블록의 번호를 가져오고싶으면
https://web3js.readthedocs.io/en/v1.8.1/web3-eth.html#getblocknumber
사용방법이 나와있다.
이더 체인상 마지막 블록의 번호를 가져오고싶으면 getBlockNumber함수를 써서 ()안에 콜백함수를 넣거나함수 뒤에 콜백함수를 붙인다
web3.eth.getBlockNumber(function(error, result){console.log(result)}
web3.eth.getBlockNumber().then(console.log);
특정 블록의 정보를 가져오고 싶으면 getBlock함수를 사용
https://web3js.readthedocs.io/en/v1.8.1/web3-eth.html#getblock
web3.eth.getBlock(1613800, function(error, result){console.log(result)})
web3.eth.getBlock(1613885).then(console.log)