<p>我曾经不止一次在以前的文章中鼓励大家在开发 dapp 时使用 <a href="https://docs.ethers.io/v5/">Ethers.js</a>,但时至今日却还没有一篇专门的文章来介绍它,这多少有些说不过去。于是,我决定用两篇文章的篇幅来谈谈它的开发使用。</p>
<p>这两篇文章以当前最新的 v5 版本为基础,采用问题驱动形式,涵盖了 dapp 开发中面临的主要开发主题。</p>
<p>在本篇中,你可以了解到:</p>
<ul>
<li>安装过程可能面临的问题</li>
<li>如何与 Web3Modal 搭配使用</li>
<li>human readable abi 和只读合约方法调用</li>
<li>读写合约调用以及 gas 相关问题</li>
<li>如何确定交易的状态</li>
<li>如何调用使用了 struct 的合约方法</li>
<li>常见的 UNPREDICTABLE_GAS_LIMIT 错误如何解决</li>
</ul>
<p>下篇则重点关注合约事件、历史、签名等相关内容。</p>
<p>作为开发者的你,假如在寻找让你能快速上手 Ethers.js 的使用,同时又能看到不那么小儿科的例子,那么本系列应该成为你的选择。</p>
<p>那么,让我们进入正题吧!</p>
<h2 id="安装">安装</h2>
<p>通常,这里没什么好说的,按照文档上面的指示来就好了:</p>
<div class="highlight"><pre tabindex="0" style="color:#586e75;background-color:#eee8d5;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-shell" data-lang="shell"><span style="display:flex;"><span>npm install --save ethers
</span></span></code></pre></div><p>但是,在极个别的情况下,尤其是采用某些前端框架时,按照以上方式安装可能会导致无法正确初始化 <code>provider</code>。此时,可以求助于另一种很容易被我们这些经过现代前端框架“洗脑”后的开发者所忽视的方法:最原始的 <script> 引入方式。</p>
<div class="highlight"><pre tabindex="0" style="color:#586e75;background-color:#eee8d5;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-html" data-lang="html"><span style="display:flex;"><span><<span style="color:#268bd2;font-weight:bold">script</span>
</span></span><span style="display:flex;"><span> <span style="color:#268bd2">src</span>=<span style="color:#2aa198">"https://cdn.jsdelivr.net/npm/ethers@5.1.4/dist/ethers.umd.min.js"</span>
</span></span><span style="display:flex;"><span> <span style="color:#268bd2">type</span>=<span style="color:#2aa198">"application/javascript"</span>
</span></span><span style="display:flex;"><span>></<span style="color:#268bd2;font-weight:bold">script</span>>
</span></span></code></pre></div><p>然后,通过下面的代码引用 <code>ethers</code> 对象而非常见的 <code>import</code>:</p>
<div class="highlight"><pre tabindex="0" style="color:#586e75;background-color:#eee8d5;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-ts" data-lang="ts"><span style="display:flex;"><span><span style="color:#859900">const</span> <span style="color:#268bd2">ethers</span> = <span style="color:#cb4b16">window</span>.<span style="color:#268bd2">ethers</span>;
</span></span></code></pre></div><p>这种方式有一个副作用:在一些现代编辑器中,如 vscode ,无法利用其代码联想功能。因此,第一种方式应该成为你的首选,除非没得办法。</p>
<p>最后请注意:<script> 引入方式仅限于前端。对于后端代码(假如仍然使用 js / ts 的话),采用 <code>npm i</code> 方式即可。</p>
<h2 id="连接钱包">连接钱包</h2>
<p>严格来讲,本节的标题采用另一种说法更合适:“连接以太坊”。但由于“连接钱包”通俗易懂,故采用之。</p>
<p>所谓连接,可以从两个维度来说明:</p>
<ul>
<li>发生地点:前端 or 后端</li>
<li>连接目的:只读调用 or 发起交易</li>
</ul>
<p>在 Ethers.js 中,与之相关的类有三个:</p>
<ul>
<li>provider,面向只读操作</li>
<li>signer,发起交易时必需</li>
<li>wallet,signer 的子类</li>
</ul>
<h3 id="在前端连接">在前端连接</h3>
<p>一般来讲,从前端连接,有以下的特点:</p>
<ul>
<li>通常会对接用户已安装的钱包或钱包插件,如 MetaMask</li>
<li>一般都会涉及到读写操作</li>
</ul>
<p>这里的步骤是:</p>
<ul>
<li>先创建 <code>Web3Provider</code> 实例,它可以应付一般的只读操作。</li>
<li>如果需要发起交易或签名,则可以通过 <code>provider.getSigner()</code> 来得到 <code>signer</code>,通过它来完成剩下的操作。</li>
</ul>
<p>由于本节的关注点是连接钱包,因此让我们先来看看第一步:获取 <code>Web3Provider</code>。</p>
<p>对于前端应用,建议配合 <a href="https://web3modal.com/">Web3Modal</a> 来使用,因为它对于常见的 provider 提供了统一的接口,并可和 Ethers.js 搭配使用。但是,使用时需注意:</p>
<ul>
<li>它依赖 react ,若你采用的是非 react 框架,需要注意。</li>
<li>使用不同的 provider 前需安装,这意味着支持的 provider 越多,那么应用构建之后的包会越大。</li>
</ul>
<p>然而,这两个问题可以用同样方式来解决:最原始的 <script> 引入方式。采用这种方式,不仅可以规避必须安装 react 的限制,同时也避免了需静态打包各个 provider ,将其延迟到应用加载页面时。因为我个人目前偏好 svelte ,这种做法已经在实际中得到了应用,效果良好。</p>
<p>下面示例采用 <script> 引入方式的做法,但很容易改造成通过 <code>npm i</code> 方式引入的代码:忽略第一步,采用 <code>import</code> 方式而非 <code>window</code> 引用对象。</p>
本文是付费文章,剩余内容请访问以下链接支付之后继续阅读:
付费链接
(已付费:38)