<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/">
  <channel>
    <title>Cedar Piano</title>
    <link>https://cedarpiano.fyi/</link>
    <description>Recent content on Cedar Piano</description>
    <generator>Hugo</generator>
    <language>en-us</language>
    <copyright>Public domain (CC0)</copyright>
    <lastBuildDate>Sat, 15 Aug 2026 11:30:00 +0200</lastBuildDate>
    <atom:link href="https://cedarpiano.fyi/index.xml" rel="self" type="application/rss+xml" />
    <item>
      <title>Adding a Tip Jar to a Webpage</title>
      <link>https://cedarpiano.fyi/posts/tipjar-webpage/</link>
      <pubDate>Sat, 15 Aug 2026 11:30:00 +0200</pubDate>
      <guid>https://cedarpiano.fyi/posts/tipjar-webpage/</guid>
      <description>&lt;p&gt;The previous tutorials drove the &lt;code&gt;TipJar&lt;/code&gt; contract entirely from the shell. This
one puts it behind a webpage: a Connect button, a tip form, a live balance, and
a withdraw button that only appears for the owner.&lt;/p&gt;
&lt;p&gt;The browser flow is:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; class=&#34;chroma&#34;&gt;&lt;code class=&#34;language-text&#34; data-lang=&#34;text&#34;&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;Webpage → ethers.js → MetaMask → Anvil → TipJar contract
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;MetaMask holds the keys and signs the transactions. &lt;strong&gt;No private key goes
anywhere near the JavaScript.&lt;/strong&gt; Frontend source is visible to anyone who visits
the page, so a key in it is a key you have given away.&lt;/p&gt;</description>
    </item>
    <item>
      <title>Invariant Testing with Foundry</title>
      <link>https://cedarpiano.fyi/posts/invariant-testing-foundry/</link>
      <pubDate>Sat, 15 Aug 2026 11:00:00 +0200</pubDate>
      <guid>https://cedarpiano.fyi/posts/invariant-testing-foundry/</guid>
      <description>&lt;p&gt;Unit tests check that a function does what you expected. Invariant tests check
something harder: that a property of your contract holds no matter what anybody
does to it. This tutorial writes both kinds against a &lt;code&gt;TipJar&lt;/code&gt; contract, watches
the invariant catch a bug every unit test missed, and then shows why the
obvious invariant is still wrong.&lt;/p&gt;
&lt;p&gt;It follows on from
&lt;a href=&#34;https://cedarpiano.fyi/posts/smart-contract-foundry/&#34;&gt;Writing a Smart Contract with Foundry&lt;/a&gt;, and
picks up exactly where that one ends. Its sibling,
&lt;a href=&#34;https://cedarpiano.fyi/posts/tipjar-webpage/&#34;&gt;Adding a Tip Jar to a Webpage&lt;/a&gt;, takes the same contract
in the other direction and puts a browser frontend on it. Neither depends on the
other.&lt;/p&gt;</description>
    </item>
    <item>
      <title>Writing a Smart Contract with Foundry</title>
      <link>https://cedarpiano.fyi/posts/smart-contract-foundry/</link>
      <pubDate>Sat, 15 Aug 2026 10:30:00 +0200</pubDate>
      <guid>https://cedarpiano.fyi/posts/smart-contract-foundry/</guid>
      <description>&lt;p&gt;This tutorial writes, tests, deploys, and drives a &lt;code&gt;TipJar&lt;/code&gt; smart contract
entirely from the command line.&lt;/p&gt;
&lt;p&gt;It follows on from
&lt;a href=&#34;https://cedarpiano.fyi/posts/ethereum-command-line/&#34;&gt;Ethereum from the Command Line&lt;/a&gt;, which covers
Anvil, accounts, transactions, and blocks. You do not have to have read it —
the Prerequisites below get you to the same starting point — but it explains
most of what this one assumes. Two tutorials follow on from this one:
&lt;a href=&#34;https://cedarpiano.fyi/posts/tipjar-webpage/&#34;&gt;Adding a Tip Jar to a Webpage&lt;/a&gt; puts a frontend on the
contract, and &lt;a href=&#34;https://cedarpiano.fyi/posts/invariant-testing-foundry/&#34;&gt;Invariant Testing with Foundry&lt;/a&gt;
tests it harder.&lt;/p&gt;</description>
    </item>
    <item>
      <title>Ethereum from the Command Line</title>
      <link>https://cedarpiano.fyi/posts/ethereum-command-line/</link>
      <pubDate>Sat, 15 Aug 2026 10:00:00 +0200</pubDate>
      <guid>https://cedarpiano.fyi/posts/ethereum-command-line/</guid>
      <description>&lt;p&gt;This tutorial explores an Ethereum blockchain entirely from the shell —
accounts, transactions, blocks, gas, and units — using a local test chain and
then the real network. There is no Solidity here, and no frontend.&lt;/p&gt;
&lt;p&gt;Writing and deploying a contract is the subject of the follow-up,
&lt;a href=&#34;https://cedarpiano.fyi/posts/smart-contract-foundry/&#34;&gt;Writing a Smart Contract with Foundry&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;ethereum&#34;&gt;Ethereum&lt;/h2&gt;
&lt;p&gt;A blockchain is a shared, append-only ledger that nobody owns. What makes one
&lt;em&gt;programmable&lt;/em&gt; is the ability to put code on it — a &lt;strong&gt;smart contract&lt;/strong&gt;, which is
a program with its own address, its own storage, and its own balance. Once
deployed, it runs exactly as written for anyone who calls it, and no single
party can quietly change it or stop it.&lt;/p&gt;</description>
    </item>
  </channel>
</rss>
