摘要:加入以太坊生態(tài)系統(tǒng),一起征服世界。數(shù)字,字符串等要注意的第二件事是以太坊中的是位。一旦你掌握了這些東西,我個(gè)人會(huì)認(rèn)為你是一個(gè)有能力的以太坊開(kāi)發(fā)者
我經(jīng)常構(gòu)建使用以太坊的Web應(yīng)用程序,我理所當(dāng)然地認(rèn)為每天都使用的是神奇的工具集。我們的生態(tài)系統(tǒng)正在迅速發(fā)展,我認(rèn)為很多新人都感到不知所措。以太坊是一項(xiàng)了不起的技術(shù),但它也是新生的,而且根本沒(méi)有足夠的時(shí)間讓專(zhuān)業(yè)知識(shí)充分滲透。我希望人們知道以太坊開(kāi)發(fā)實(shí)際上與現(xiàn)代Web開(kāi)發(fā)人員工作流程非常兼容——將以太坊功能集成到任何Web應(yīng)用程序中相對(duì)容易,你可以從今天開(kāi)始。
因?yàn)槲艺J(rèn)為自己是以太坊的高手,可以向主流開(kāi)發(fā)者展示方向,我決定將一堆分散的知識(shí)放到一個(gè)地方(我知道不是非常去中心化)。你當(dāng)然需要在每一步都查閱相應(yīng)的文檔,但我希望本文將向你展示如何將所有內(nèi)容(或多或少)放在一起。
如果你準(zhǔn)備好學(xué)習(xí),請(qǐng)讓我為你提供方向和指南。加入以太坊生態(tài)系統(tǒng),一起征服世界。
獲取區(qū)塊鏈有很多客戶端可供選擇,但我建議不要擔(dān)心geth 、parity與pyethapp(即將到來(lái)的python客戶端代表?。?。對(duì)于那些只想要一個(gè)可復(fù)用的區(qū)塊鏈以便可以開(kāi)始構(gòu)建東西(例如你)的人,我建議testrpc滿足你的所有開(kāi)發(fā)需求。安裝完成后,可以使用以下命令啟動(dòng)它:
testrpc
恭喜你,這就有一個(gè)區(qū)塊鏈了。請(qǐng)注意,默認(rèn)情況下,testrpc不會(huì)挖掘塊,但-b標(biāo)志允許你指定塊間隔(例如1秒)。我喜歡這種配置有很多原因,我不會(huì)介入,但請(qǐng)記住它是可用的。
與區(qū)塊鏈交互一旦你的區(qū)塊鏈旋轉(zhuǎn),你需要一種與它交談的方法。 你可能已經(jīng)下載了web3.js。 如果你沒(méi)有,你必須下載新的。好吧,繼續(xù)并確保安裝了web3,然后打開(kāi)一個(gè)config.js文件并將其放入其中:
var web3 = require("web3"); var web3_provider = "http://localhost:8545"; var _web3 = new web3(); _web3.setProvider(new web3.providers.HttpProvider(web3_provider)); exports.web3 = _web3;
任何時(shí)候你想與后端服務(wù)器上的區(qū)塊鏈交互,只需要這樣做:
var config = require("./config.js"); config.web3.eth.X
可以在此處找到X(即你想要的任何web3 API函數(shù))。
寫(xiě)智能合約我會(huì)在這里為你節(jié)省一些時(shí)間:你將使用solidity來(lái)編寫(xiě)智能合約。如果你認(rèn)為智能合約是可怕的,沒(méi)必要。對(duì)于許多應(yīng)用程序,只要遵循一條規(guī)則,它實(shí)際上非常簡(jiǎn)單:保持合約簡(jiǎn)單。
有兩個(gè)原因,你總是始終保持合約絕對(duì)簡(jiǎn)單,因?yàn)楸仨氝@樣:
每次計(jì)算/存儲(chǔ)操作都需要gas,等于以太幣,等于貨幣。我們正在談?wù)撝Ц?.05美元和1.50美元之間的差異來(lái)調(diào)用你的合約。以太坊的觀點(diǎn)不是要替換你的數(shù)據(jù)庫(kù)(至少在我看來(lái)不是這樣),所以保持邏輯簡(jiǎn)短和存儲(chǔ)最小化。
更復(fù)雜=更多地方出錯(cuò)。當(dāng)你的代碼負(fù)責(zé)人們的錢(qián)并且無(wú)法回滾時(shí),這很糟糕。請(qǐng)花一點(diǎn)時(shí)間只讓有用的話寫(xiě)在其中。
好的,簡(jiǎn)單的合約——得到它。讓我們繼續(xù)。
部署智能合約如果你還沒(méi)有聽(tīng)說(shuō)過(guò)truffle,那么現(xiàn)在一定要看一下。我喜歡在truffle目錄中管理我的測(cè)試者合約。關(guān)于這一點(diǎn)的巧妙之處在于,你可以輕松地將其用于測(cè)試框架。在package.json中考慮這個(gè)腳本:
"scripts": { "test": "cd truffle && truffle deploy && truffle test ./myTruffleTest.js && cd .. && npm run myOtherTests" }
這樣做:1.部署合約,2.運(yùn)行truffle測(cè)試,3.運(yùn)行常規(guī)測(cè)試——所有這些都在同一個(gè)腳本中!
請(qǐng)注意,你的truffle測(cè)試是“特殊的”,因?yàn)樗鼈儠?huì)在測(cè)試范圍內(nèi)注入一堆很酷的區(qū)塊鏈內(nèi)容。有多種方法可以將此信息傳遞給你的測(cè)試套件的其余部分。我個(gè)人使用truffle測(cè)試將合約地址保存到配置文件中,然后將該配置導(dǎo)入到我常規(guī)mocha測(cè)試中。只要我有正確的地址,我就可以通過(guò)web3.js在任何測(cè)試中與我的合約進(jìn)行交互。無(wú)論如何,你會(huì)發(fā)現(xiàn)什么最適合你。
回到主要內(nèi)容。你可以通過(guò)轉(zhuǎn)到truffle目錄并鍵入以下內(nèi)容來(lái)部署智能合約:
truffle deploy
請(qǐng)注意,testrpc必須在另一個(gè)窗口中運(yùn)行!
這將打印你剛剛部署的合約的地址,稍后你將需要該地址。正如我所提到的,你總是可以在truffle測(cè)試中以編程方式保存這個(gè)地址,但是現(xiàn)在你可以將它復(fù)制并粘貼到你的config.js文件中:
exports.contract_addr = "0xe73e8e0a4442e140aea87a4b150ef07b82492500"進(jìn)行智能合約調(diào)用
既然我們有合約,我們需要調(diào)用它。好的,這個(gè)看起來(lái)很簡(jiǎn)陋——我們將用純十六進(jìn)制字符串調(diào)用合約。當(dāng)然有l(wèi)ibraries可以讓這更容易,但是當(dāng)涉及到合約調(diào)用時(shí),我就開(kāi)始要講課了。請(qǐng)記住,我是你的領(lǐng)路人。
首先要注意的是,所有內(nèi)容都必須是十六進(jìn)制的。數(shù)字,字符串等要注意的第二件事是以太坊中的words是256位。這意味著你需要用零填充所有內(nèi)容到64個(gè)字符。需要注意的第三件事是必須在函數(shù)定義中規(guī)范地聲明類(lèi)型。
好吧,這真的挺亂。我們來(lái)看一個(gè)例子,更好理解:
function add(uint x, uint y) public constant returns (uint) { return x + y; }
假設(shè)你要做個(gè)加法如1加2,以下是你調(diào)用此函數(shù)的方法:
1.獲取封裝好的規(guī)范函數(shù)定義的keccak 256哈希的前4個(gè)字節(jié)。
說(shuō)什么?好吧,我沒(méi)有做到這一點(diǎn),但你可以在這個(gè)網(wǎng)站上輸入你的功能聲明并取前8個(gè)字符。規(guī)范是什么意思?好吧,在以太坊中有規(guī)范類(lèi)型和速記類(lèi)型(例如uint256是uint的規(guī)范類(lèi)型)。我實(shí)際上不知道它們的定義在哪里,但是查看以太坊ABI定義的例子以及這篇文章。
無(wú)論如何,這就是我們的定義:
add(uint256,uint256)
返回keccak256哈希:
771602f7f25ce61b0d4f2430f7e4789bfd9e6e4029613fda01b7f2c89fbf44ad
其中前4個(gè)字節(jié)(8個(gè)字符)是:
771602f7
2.將參數(shù)填充為256位
這個(gè)更容易掌握:
x = 1是:
0000000000000000000000000000000000000000000000000000000000000001
y = 2是:
0000000000000000000000000000000000000000000000000000000000000002
他們?cè)谝黄鹗牵?/p>
00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002
3.將所有內(nèi)容打包在一起并添加0x前綴
自定義:
0x771602f700000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002
現(xiàn)在我們有了有效負(fù)載,我們可以通過(guò)web3調(diào)用合約:
var config = require("./config.js"); var call = "0x771602f700000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002" var to = config.contract_addr; var res = config.web3.eth.call({ to: to, data: call });
在那之后,你應(yīng)該返回res=3。實(shí)際上,你會(huì)得到一個(gè)BigNumber對(duì)象:
res.toString() >"3"
你可能應(yīng)該閱讀此內(nèi)容以了解有關(guān)在整個(gè)應(yīng)用中使用BigNumbers的原因。
好的,你可以使用我之前提到的庫(kù)。
等等,我們還沒(méi)有完成!我剛剛告訴你如何調(diào)用合約。但是,如果你想寫(xiě)入些東西(即更新?tīng)顟B(tài))怎么辦?以上的是不行的!你需要使用私鑰簽署一個(gè)交易,但在此之前,你需要一些以太。
設(shè)置帳戶我們回到truffle吧。在我們的測(cè)試中,需要添加如下內(nèi)容:
var keys = require(`${process.cwd()}/../test/keys.json`); it("Should send me some ether.", function() { assert.notEqual(keys.me.addr, null); var eth = 1*Math.pow(10, 18); var sendObj = { from: accounts[0], value: eth, to: keys.me.addr } Promise.resolve(web3.eth.sendTransaction(sendObj)) .then(function(txHash) { assert.notEqual(txHash, null); return web3.eth.getBalance(keys.me.addr) }) .then(function(balance) { assert.notEqual(balance.toNumber(), 0); }) })
重要提示:我們實(shí)際發(fā)送1個(gè)以太,這與10^18 wei相同。我們總是使用wei值進(jìn)行調(diào)用/交易。
現(xiàn)在,我在這里跳過(guò)一步。你需要先獲得以太坊帳戶,該帳戶來(lái)自你生成的私人/公共密鑰對(duì)。我喜歡使用eth-lightwallet在后端進(jìn)行密鑰管理。
為了簡(jiǎn)單起見(jiàn),讓我假裝在不斷增長(zhǎng)的config.js中硬編碼這個(gè)變量:
exports.me = { addr: "0x29f2f6405e6a307baded0b0672745691358e3ee6", pkey: "8c2bcfce3d9c4f215fcae9b215eb7c95831da0219ebfe0bb909eb951c3134515" }
強(qiáng)制性提醒:永遠(yuǎn)不要共享你的私鑰,將其上傳到github,或者如果有任何資金就將其發(fā)布在Medium上。
回到測(cè)試,你可以看到以太被從accounts[0](默認(rèn)情況下有一堆以太)移動(dòng)到你的配置文件中的me.addr。
與智能合約進(jìn)行交易現(xiàn)在你的帳戶已經(jīng)有了一些以太,現(xiàn)在是時(shí)候花錢(qián)了。有三種方式可以用以太:
1.將其作為Value發(fā)送到另一個(gè)地址。
2.調(diào)用更新合約函數(shù)去更新網(wǎng)絡(luò)狀態(tài),這需要gas來(lái)激勵(lì)礦工處理你的更新。
3.調(diào)用更新合約狀態(tài),但也接受以太幣來(lái)支付(僅供參考,用solidity修正)——將發(fā)送Value,你還必須支付gas費(fèi)用。
我們接下來(lái)要做的是第2種。假設(shè)我們有以下函數(shù)來(lái)跟蹤用戶的余額:
function addUserBalance(uint balance) public returns (bool) { if (!accounts[msg.sender]) { throw; } if (accounts[msg.sender].balance + balance < accounts[msg.sender].balance) { throw; } accounts[msg.sender].balance += balance; return true; }
注意第二個(gè)if語(yǔ)句,這是必要的,因?yàn)榧雍蜏p在solidity會(huì)導(dǎo)致數(shù)值溢出和下溢——小心!還要注意在函數(shù)范圍內(nèi)的未聲明的msg對(duì)象。
當(dāng)我們通過(guò)發(fā)送交易調(diào)用此函數(shù)時(shí),我們要求更新網(wǎng)絡(luò)的全局狀態(tài)以說(shuō)明以下內(nèi)容:
在合約范圍內(nèi),msg.sender帳戶的余額已經(jīng)增加了balance。
我們沒(méi)有權(quán)力自己更新?tīng)顟B(tài),所以需要一個(gè)礦工做這件事。我們用gas向他或她支付這項(xiàng)服務(wù),這意味著付出以太。
要正確調(diào)用此函數(shù),我們需要再次使用ABI:
addUserBalance(uint256) --> 22526328 --> 0x225263280000000000000000000000000000000000000000000000000000000000000001
我們使用這些數(shù)據(jù)來(lái)形成一個(gè)未簽名的交易:
var data = "0x225263280000000000000000000000000000000000000000000000000000000000000001"; var nonce = config.web3.eth.getTransactionCount(keys.me.addr); var gasPrice = 20 * Math.pow(10, 9); var gasLimit = 100000; var txn = { from: config.me.addr, to: config.contract_address, gas: `0x${gasLimit.toString(16)}`, gasPrice: `0x${gasPrice.toString(16)}`, data: data, nonce: `0x${nonce.toString(16)}`, value: "0x0" }
如上所述,需要gas進(jìn)行交易(即更新?tīng)顟B(tài))。gas*gasPrice是礦工執(zhí)行交易可能花費(fèi)的金額。如果操作成本高于你提供的成本,則交易將不會(huì)更新?tīng)顟B(tài),并且礦工將保留你的所有g(shù)as費(fèi)用。如果使用的gas少于所用gas,則退還余額。
如果我們將此對(duì)象提交給網(wǎng)絡(luò),它將失敗,因?yàn)闆](méi)有證據(jù)表明我實(shí)際上正在授權(quán)此交易。誰(shuí)知道,有些陌生人可能會(huì)將我的余額更新為10億(雖然目前還不清楚為什么有人會(huì)這樣做)。
無(wú)論如何,我需要做的是用我的私鑰簽署交易。還記得你在配置文件中內(nèi)容,我告訴過(guò)你不要與任何人分享嗎?這樣做:
var Tx = require("ethereumjs-tx"); var privateKey = Buffer.from(config.me.pkey, "hex") var tx = new Tx(txn); tx.sign(privateKey); var serializedTx = tx.serialize();
在這里,使用我最喜歡的庫(kù)之一,根據(jù)你的私鑰簽署一個(gè)交易對(duì)象。這應(yīng)該返回如下內(nèi)容:
0xf8aa808504a817c800830f424094a0f68379088f9aee95ba5c9d178693b874c4cd6880b844a9059cbb000000000000000000000000053b2188b0b100e68299708864e2ccecb62cdf0d000000000000000000000000000000000000000000000000000000746a5288001ca01f683f083c2d7c741a1218efc0144adc1749125a9ca53134b06353a8e4ef72afa07c50fb59647ff8b8895b75795b0f51de745fa5987b985f7d1025eb346755bca0
最后,我們可以通過(guò)web3將其提交給區(qū)塊鏈。它將返回一個(gè)交易哈希,它只是提供的交易的哈希值(這非常重要的是,不能證明交易是成功的?。?/p>
var txHash = config.web3.eth.sendRawTransaction(raw_txn);
看起來(lái)像這樣:
0xac8914ecb06b333a9e655a85a0cd0cccddb8ac627098e7c40877d27a130a7293
現(xiàn)在的這一步,嚴(yán)格來(lái)說(shuō)是可選的,但對(duì)于驗(yàn)證你的交易是否已被接受和處理非常重要:獲取你的交易收據(jù)。
var txReceipt = config.web3.eth.getTransactionReceipt(txHash);
如果返回null,則你的交易未被提?。赡苁悄闶褂缅e(cuò)誤的私鑰進(jìn)行了簽名?)。如果它不為null,可能仍有各種其他失敗情況,來(lái)看看你的交易。
好的,有一條線索——如果你的gasUsed等于發(fā)送的gas,則意味著你的函數(shù)調(diào)用失敗了。這意味著1.你沒(méi)有提供足夠的gas或者同時(shí)2.你的合約遇到了throw。
總結(jié)我知道,這是很多內(nèi)容。
如果你感覺(jué)太多了,我建議你慢慢來(lái),并使用這篇文章作為參考。你可能需要花費(fèi)大量時(shí)間閱讀文檔。
也就是說(shuō),我上面描述的是80%的內(nèi)容。一旦你掌握了這些東西,我個(gè)人會(huì)認(rèn)為你是一個(gè)有能力的以太坊開(kāi)發(fā)者。
如果你有興趣,可以開(kāi)始修修補(bǔ)補(bǔ)!這些工具變得越來(lái)越好,并且從未如此容易地進(jìn)入。歡迎上岸。
更新:我已經(jīng)為你創(chuàng)建了一個(gè)repo來(lái)展示本文中介紹的大部分內(nèi)容。
如果希望快速進(jìn)行以太坊開(kāi)發(fā),那請(qǐng)看我們精心打造的教程:
以太坊入門(mén)教程,主要介紹智能合約與dapp應(yīng)用開(kāi)發(fā),適合入門(mén)。
其他區(qū)塊鏈教程如下:
以太坊開(kāi)發(fā)進(jìn)階教程,主要是介紹使用node.js、mongodb、區(qū)塊鏈、ipfs實(shí)現(xiàn)去中心化電商DApp實(shí)戰(zhàn),適合進(jìn)階。
java以太坊開(kāi)發(fā)教程,主要是針對(duì)java和android程序員進(jìn)行區(qū)塊鏈以太坊開(kāi)發(fā)的web3j詳解。
python以太坊,主要是針對(duì)python工程師使用web3.py進(jìn)行區(qū)塊鏈以太坊開(kāi)發(fā)的詳解。
php以太坊,主要是介紹使用php進(jìn)行智能合約開(kāi)發(fā)交互,進(jìn)行賬號(hào)創(chuàng)建、交易、轉(zhuǎn)賬、代幣開(kāi)發(fā)以及過(guò)濾器和事件等內(nèi)容。
C#以太坊,主要講解如何使用C#開(kāi)發(fā)基于.Net的以太坊應(yīng)用,包括賬戶管理、狀態(tài)與交易、智能合約開(kāi)發(fā)與交互、過(guò)濾器和事件等。
php比特幣開(kāi)發(fā)教程,本課程面向初學(xué)者,內(nèi)容即涵蓋比特幣的核心概念,例如區(qū)塊鏈存儲(chǔ)、去中心化共識(shí)機(jī)制、密鑰與腳本、交易與UTXO等,同時(shí)也詳細(xì)講解如何在Php代碼中集成比特幣支持功能,例如創(chuàng)建地址、管理錢(qián)包、構(gòu)造裸交易等,是Php工程師不可多得的比特幣開(kāi)發(fā)學(xué)習(xí)課程。
EOS入門(mén)教程,本課程幫助你快速入門(mén)EOS區(qū)塊鏈去中心化應(yīng)用的開(kāi)發(fā),內(nèi)容涵蓋EOS工具鏈、賬戶與錢(qián)包、發(fā)行代幣、智能合約開(kāi)發(fā)與部署、使用代碼與智能合約交互等核心知識(shí)點(diǎn),最后綜合運(yùn)用各知識(shí)點(diǎn)完成一個(gè)便簽DApp的開(kāi)發(fā)。
匯智網(wǎng)原創(chuàng)翻譯,轉(zhuǎn)載請(qǐng)標(biāo)明出處。這里是原文
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/97968.html
摘要:加入以太坊生態(tài)系統(tǒng),一起征服世界。數(shù)字,字符串等要注意的第二件事是以太坊中的是位。一旦你掌握了這些東西,我個(gè)人會(huì)認(rèn)為你是一個(gè)有能力的以太坊開(kāi)發(fā)者 我經(jīng)常構(gòu)建使用以太坊的Web應(yīng)用程序,我理所當(dāng)然地認(rèn)為每天都使用的是神奇的工具集。我們的生態(tài)系統(tǒng)正在迅速發(fā)展,我認(rèn)為很多新人都感到不知所措。以太坊是一項(xiàng)了不起的技術(shù),但它也是新生的,而且根本沒(méi)有足夠的時(shí)間讓專(zhuān)業(yè)知識(shí)充分滲透。我希望人們知道以太...
摘要:以太坊,主要講解如何使用開(kāi)發(fā)基于的以太坊應(yīng)用,包括賬戶管理狀態(tài)與交易智能合約開(kāi)發(fā)與交互過(guò)濾器和事件等。 Android應(yīng)用程序以太坊錢(qián)包生成,要做的工作不少,不過(guò)如果我們一步一步來(lái)應(yīng)該也比較清楚: 1.在app/build.gradle中集成以下依賴(lài)項(xiàng): compile (org.web3j:core-android:2.2.1) web3j核心是用于從服務(wù)器下載以太坊區(qū)塊鏈數(shù)據(jù)的核心...
摘要:以太坊,主要講解如何使用開(kāi)發(fā)基于的以太坊應(yīng)用,包括賬戶管理狀態(tài)與交易智能合約開(kāi)發(fā)與交互過(guò)濾器和事件等。 Android應(yīng)用程序以太坊錢(qián)包生成,要做的工作不少,不過(guò)如果我們一步一步來(lái)應(yīng)該也比較清楚: 1.在app/build.gradle中集成以下依賴(lài)項(xiàng): compile (org.web3j:core-android:2.2.1) web3j核心是用于從服務(wù)器下載以太坊區(qū)塊鏈數(shù)據(jù)的核心...
摘要:是企業(yè)與區(qū)塊鏈相遇的地方。的框架旨在成為開(kāi)發(fā)區(qū)塊鏈解決方案的支柱。以太坊,主要是針對(duì)工程師使用進(jìn)行區(qū)塊鏈以太坊開(kāi)發(fā)的詳解。 如果你想將區(qū)塊鏈合并到一個(gè)Java項(xiàng)目中,現(xiàn)在我們來(lái)看看就是這個(gè)細(xì)分領(lǐng)域中三個(gè)最大的OSS玩家。 好的伙計(jì)們,我們都聽(tīng)說(shuō)過(guò)比特幣,以太坊或其他加密貨幣,其中有一些時(shí)髦的名字圍繞著我們常見(jiàn)的新聞,但我們作為Java開(kāi)發(fā)人員知道如何輕松地與這些區(qū)塊鏈技術(shù)進(jìn)行交互嗎?以...
閱讀 1448·2023-04-25 19:51
閱讀 1936·2019-08-30 15:55
閱讀 1748·2019-08-30 15:44
閱讀 2707·2019-08-30 13:58
閱讀 2702·2019-08-29 16:37
閱讀 1082·2019-08-29 15:34
閱讀 4017·2019-08-29 11:05
閱讀 2633·2019-08-28 17:51