<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" ><generator uri="https://jekyllrb.com/" version="3.10.0">Jekyll</generator><link href="http://landongrindheim.com/feed.xml" rel="self" type="application/atom+xml" /><link href="http://landongrindheim.com/" rel="alternate" type="text/html" /><updated>2024-11-11T16:08:43+00:00</updated><id>http://landongrindheim.com/feed.xml</id><title type="html">Landon Grindheim</title><subtitle>Landon Grindheim - Software craftsman. Striving for simplicity and elegance.</subtitle><entry><title type="html">One Developer’s Journey Bringing Dependabot to GitHub Enterprise Server</title><link href="http://landongrindheim.com/2022/06/07/one-developers-journey-bringing-dependabot-to-github-enterprise-server.html" rel="alternate" type="text/html" title="One Developer’s Journey Bringing Dependabot to GitHub Enterprise Server" /><published>2022-06-07T00:00:00+00:00</published><updated>2022-06-07T00:00:00+00:00</updated><id>http://landongrindheim.com/2022/06/07/one-developers-journey-bringing-dependabot-to-github-enterprise-server</id><content type="html" xml:base="http://landongrindheim.com/2022/06/07/one-developers-journey-bringing-dependabot-to-github-enterprise-server.html"><![CDATA[]]></content><author><name></name></author><summary type="html"><![CDATA[]]></summary></entry><entry><title type="html">Git Bisect by Example</title><link href="http://landongrindheim.com/2019/06/28/git-bisect-by-example.html" rel="alternate" type="text/html" title="Git Bisect by Example" /><published>2019-06-28T00:00:00+00:00</published><updated>2019-06-28T00:00:00+00:00</updated><id>http://landongrindheim.com/2019/06/28/git-bisect-by-example</id><content type="html" xml:base="http://landongrindheim.com/2019/06/28/git-bisect-by-example.html"><![CDATA[<h3 id="tldr">TL;DR</h3>
<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>git bisect start
git bisect bad &lt;bad-commit-sha&gt;
git bisect good &lt;safe-commit-sha&gt;
git bisect run &lt;command-proving-existence-of-bug&gt;
...
git bisect reset
</code></pre></div></div>
<h3 id="introduction">Introduction</h3>
<p><a href="https://git-scm.com/docs/git-bisect"><code class="language-plaintext highlighter-rouge">git bisect</code></a> can be used to find the
commit that introduced a bug. It’s a multi-step process, and, like a lot of
Git’s user interface, can appear intimidating. However, I think it’s actually
pretty user-friendly, and hope that by the end of this walk-through that you’ll
feel comfortable enough to add it to your debugging arsenal.</p>

<h3 id="when-to-reach-for-git-bisect">When to reach for <code class="language-plaintext highlighter-rouge">git bisect</code></h3>

<p>If you’ve got a bug in your codebase, but you’re not sure when it was
introduced, <code class="language-plaintext highlighter-rouge">git bisect</code> just might be your new best friend. Let’s pretend we’ve
got the following set of commits.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nv">$ </span>git log <span class="nt">--oneline</span> <span class="nt">--reverse</span>
9a7ba42 We know everything is great here 😄
01f0396 Everything is still 👌
33f470a Oh no! A bug was introduced here 😬
9f676bb <span class="o">(</span>HEAD -&gt; master<span class="o">)</span> The bug still exists 🙁
</code></pre></div></div>

<p>We know that the world was once okay, and that it isn’t now. Something changed.
If only we could find out when things broke. <code class="language-plaintext highlighter-rouge">git bisect</code> to the rescue!</p>

<h3 id="lets-do-this">Let’s do this!</h3>

<p>First things first, we need to tell Git that we’re ready to start.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>git bisect start
</code></pre></div></div>

<p>Next, we’ll give Git the sha of a commit which we know is in a bad state. Most
of the time this will be the latest commit (<code class="language-plaintext highlighter-rouge">HEAD</code>). In the example above, we
know there’s a bug as recently as <code class="language-plaintext highlighter-rouge">9f676bb</code>. Let’s use that.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>git bisect bad 9f676bb
</code></pre></div></div>

<p>Next, we need to tell Git the last known good state. Since we know our bug
wasn’t around in <code class="language-plaintext highlighter-rouge">9a7ba42</code>, we’ll use that.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>git bisect good 9a7ba42
</code></pre></div></div>

<p>Now comes the exciting part! We’ll provide a command which will be used by Git
to find the commit which introduced the bug. For simplicity’s sake, I’ll use
<code class="language-plaintext highlighter-rouge">rspec</code>, but it can be anything so long as it returns a non-zero exit code when
there is a problem, and a zero exit code when everything is okay.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>git bisect run bundle <span class="nb">exec </span>rspec
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">git bisect</code> will do its thing, performing a <a href="https://en.wikipedia.org/wiki/Binary_search_algorithm">binary search</a>
to find the offending commit. You should see something like this:</p>

<p><img src="/images/git-bisect-run.gif" alt="git-bisect" /></p>

<p>What if you have a bug, but no test to surface it? Git still has you covered! If
you can’t write a test, you can walk Git through the process by performing
manual tests then feeding Git the result by issuing <code class="language-plaintext highlighter-rouge">git bisect bad</code> or
<code class="language-plaintext highlighter-rouge">git bisect good</code> (no sha). It’s a more manual process, but the result will be
the same!</p>

<h3 id="important">Important!</h3>

<p>It’s important that you run <code class="language-plaintext highlighter-rouge">git bisect reset</code> when you’re done, or you’ll find
yourself without a branch.</p>

<hr />]]></content><author><name></name></author><category term="Git" /><summary type="html"><![CDATA[TL;DR git bisect start git bisect bad &lt;bad-commit-sha&gt; git bisect good &lt;safe-commit-sha&gt; git bisect run &lt;command-proving-existence-of-bug&gt; ... git bisect reset Introduction git bisect can be used to find the commit that introduced a bug. It’s a multi-step process, and, like a lot of Git’s user interface, can appear intimidating. However, I think it’s actually pretty user-friendly, and hope that by the end of this walk-through that you’ll feel comfortable enough to add it to your debugging arsenal.]]></summary></entry><entry><title type="html">git track (aka git add -N)</title><link href="http://landongrindheim.com/2019/01/04/git-track-aka-git-add-N.html" rel="alternate" type="text/html" title="git track (aka git add -N)" /><published>2019-01-04T00:00:00+00:00</published><updated>2019-01-04T00:00:00+00:00</updated><id>http://landongrindheim.com/2019/01/04/git-track-aka-git-add-N</id><content type="html" xml:base="http://landongrindheim.com/2019/01/04/git-track-aka-git-add-N.html"><![CDATA[<h3 id="tracking-new-files">Tracking new files</h3>
<p>I learned a new bit of Git functionality this week while pairing with a
co-worker, namely the <code class="language-plaintext highlighter-rouge">-N</code> flag for <code class="language-plaintext highlighter-rouge">git add</code>. Whenever you create a new file in
a Git repository, it is considered “untracked” until you make Git aware of it.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Your branch is up to <span class="nb">date </span>with <span class="s1">'origin/master'</span><span class="nb">.</span>

Untracked files:
  <span class="o">(</span>use <span class="s2">"git add &lt;file&gt;..."</span> to include <span class="k">in </span>what will be committed<span class="o">)</span>

        file.ext
</code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">git add -N</code><a href="#from-the-git-add-man-page">¹</a> effectively tells Git to track the
file. After issuing the command, the contents of <code class="language-plaintext highlighter-rouge">file.txt</code> will be available
to Git as if they were introduced in a previous commit. You’ll be able to diff,
grep and mv <code class="language-plaintext highlighter-rouge">file.txt</code> (and more!) without actually having to stage the file.</p>

<h3 id="a-new-alias">A new alias</h3>
<p>To follow up on my last post, <a href="/2018/12/13/semantic-git-aliases.html">Semantic Git Aliases</a>,
I created an alias that I feel more aptly describes this operation, <code class="language-plaintext highlighter-rouge">git track</code>.
I’ve been using the alias for a couple of days now and have found it both useful
and intuitive. I hope you’ll agree.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="o">[</span><span class="nb">alias</span><span class="o">]</span>
  track <span class="o">=</span> add <span class="nt">-N</span>
</code></pre></div></div>

<hr />
<hr />
<h4 id="from-the-git-add-man-page">From the <code class="language-plaintext highlighter-rouge">git add</code> man page:</h4>
<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code> <span class="nt">-N</span>, <span class="nt">--intent-to-add</span>
   Record only the fact that the path will be added later. An entry
   <span class="k">for </span>the path is placed <span class="k">in </span>the index with no content. This is useful
   <span class="k">for</span>, among other things, showing the unstaged content of such files
   with git diff and committing them with git commit <span class="nt">-a</span><span class="nb">.</span>
</code></pre></div></div>]]></content><author><name></name></author><category term="Git" /><summary type="html"><![CDATA[Tracking new files I learned a new bit of Git functionality this week while pairing with a co-worker, namely the -N flag for git add. Whenever you create a new file in a Git repository, it is considered “untracked” until you make Git aware of it.]]></summary></entry><entry><title type="html">Semantic Git Aliases</title><link href="http://landongrindheim.com/2018/12/13/semantic-git-aliases.html" rel="alternate" type="text/html" title="Semantic Git Aliases" /><published>2018-12-13T00:00:00+00:00</published><updated>2018-12-13T00:00:00+00:00</updated><id>http://landongrindheim.com/2018/12/13/semantic-git-aliases</id><content type="html" xml:base="http://landongrindheim.com/2018/12/13/semantic-git-aliases.html"><![CDATA[<p>I’ve seen quite a few posts about setting up <code class="language-plaintext highlighter-rouge">.gitconfig</code> files with aliases
like <code class="language-plaintext highlighter-rouge">co = checkout</code>. I see the value in saving some keystrokes (and
misspellings), but I personally don’t use those aliases. Command length is
rarely the pain point I experience with Git. I do, however, use a handful of
aliases that I find very helpful. I like to classify them as semantic aliases.</p>

<h2 id="tldr">TL;DR</h2>
<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="o">[</span><span class="nb">alias</span><span class="o">]</span>
  uncommit <span class="o">=</span> reset <span class="nt">--soft</span> HEAD^
  unstage <span class="o">=</span> reset
  staged <span class="o">=</span> diff <span class="nt">--cached</span>
  ctags <span class="o">=</span> <span class="s2">"!.git/hooks/ctags"</span>
</code></pre></div></div>

<h3 id="uncommit">uncommit</h3>
<p>As of the time of writing, a question on StackOverflow named <a href="https://stackoverflow.com/questions/2845731/how-to-uncommit-my-last-commit-in-git">“How to uncommit
my last commit in Git”</a>
had been upvoted 666 times, and its accepted answer had been upvoted 1068 times.
The title alone suggests what users are <em>trying</em> to do. They’re just not sure
how to accomplish it. The answer is to use <code class="language-plaintext highlighter-rouge">git reset --soft HEAD^</code>, which, if
you spend some time thinking about it, makes sense. But <a href="https://en.wikipedia.org/wiki/Don't_Make_Me_Think">don’t make me think</a>.</p>

<p>Aliasing the command to <code class="language-plaintext highlighter-rouge">uncommit</code> has taken the mental overhead out of the
equation. And since I’m not searching for the correct syntax every time, it also
saves me time. It’s been all upside.</p>

<h3 id="unstage">unstage</h3>
<p>Here’s what I see every time I issue <code class="language-plaintext highlighter-rouge">git status</code>:</p>
<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Changes to be committed:
  <span class="o">(</span>use <span class="s2">"git reset HEAD &lt;file&gt;..."</span> to unstage<span class="o">)</span>
</code></pre></div></div>

<p>“Use … to <strong>unstage</strong>”. While I don’t need to open up my browser to look up
the syntax, I still have to translate the command and arguments to understand
its purpose. Aliasing to <code class="language-plaintext highlighter-rouge">unstage</code> ends up adding a keystroke, but I find it
reduces the mental energy spent on the task. Thanks to <a href="https://thoughtbot.com/upcase/videos/git-customizing#aliases">Thoughtbot</a>
for sharing and making my Git experience better!</p>

<h3 id="staged">staged</h3>
<p>I try to be very intentional about my commits, grouping alike changes to ensure
that the story I’m telling to the reviewer (and future maintainers) is coherent.
In the process of preparing a commit I often look at the current diff, as well
as what has already been <strong>staged</strong>. I used to have <code class="language-plaintext highlighter-rouge">git diff --cached</code>
memorized for this purpose, but aliasing the command has made it so much
more friendly to use.</p>

<p>While <code class="language-plaintext highlighter-rouge">uncommit</code> and <code class="language-plaintext highlighter-rouge">unstage</code> are used occasionally, I use <code class="language-plaintext highlighter-rouge">staged</code> all the
time.</p>

<h3 id="ctags">ctags</h3>
<p>This alias sheds less light on what Git itself is doing, but I find it useful
and hope others will as well. It relies on Tim Pope’s <a href="https://tbaggery.com/2011/08/08/effortless-ctags-with-git.html">Effortless Ctags with
Git</a> setup,
which I highly recommend if you’re a Vim user. With this alias, you can
re-index your codebase without relying on a Git hook.</p>

<p>I hope you find these aliases as helpful as I do, not for their ability to save
keystrokes, but for how accessible they make some of Git’s powerful features.</p>]]></content><author><name></name></author><category term="Git" /><summary type="html"><![CDATA[I’ve seen quite a few posts about setting up .gitconfig files with aliases like co = checkout. I see the value in saving some keystrokes (and misspellings), but I personally don’t use those aliases. Command length is rarely the pain point I experience with Git. I do, however, use a handful of aliases that I find very helpful. I like to classify them as semantic aliases.]]></summary></entry><entry><title type="html">The Perils of Class Instance Variables in Ruby</title><link href="http://landongrindheim.com/2018/12/04/the-perils-of-class-instance-variables-in-ruby.html" rel="alternate" type="text/html" title="The Perils of Class Instance Variables in Ruby" /><published>2018-12-04T00:00:00+00:00</published><updated>2018-12-04T00:00:00+00:00</updated><id>http://landongrindheim.com/2018/12/04/the-perils-of-class-instance-variables-in-ruby</id><content type="html" xml:base="http://landongrindheim.com/2018/12/04/the-perils-of-class-instance-variables-in-ruby.html"><![CDATA[<p>Recently someone at work asked about class instance variables. We had recently
been told about a catastrophic incident wherein data was being shared with the
wrong objects because a class method set an instance variable, then later used
that instance variable to do some important work.</p>

<p>If you’re familiar with variable ownership in Ruby, you can probably see where
this is going. Since each class is an instance of <code class="language-plaintext highlighter-rouge">Class</code>, an instance
variable in a class method belongs to the class. Each time that method is
called, the exact same instance variable is referenced.  In a multi-threaded
context, this can have some very undesirable side effects.</p>

<p>I’ll create a contrived scenario to illustrate. Say we’re a bank and we’ve got
customers who want their balance emailed to them each night. We assume customers
that carry no balance shouldn’t get emails. We’ve created <code class="language-plaintext highlighter-rouge">BalanceNotice</code> to
handle this.</p>

<div class="language-ruby highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">class</span> <span class="nc">BalanceNotice</span>
  <span class="k">def</span> <span class="nc">self</span><span class="o">.</span><span class="nf">mail</span><span class="p">(</span><span class="n">email</span><span class="p">,</span> <span class="n">balance</span><span class="p">)</span>
    <span class="vi">@balance</span> <span class="o">=</span> <span class="n">balance</span><span class="p">.</span><span class="nf">to_f</span>

    <span class="k">if</span> <span class="n">should_email?</span>
      <span class="no">BalanceMailer</span><span class="p">.</span><span class="nf">mail</span><span class="p">(</span><span class="ss">to: </span><span class="n">email</span><span class="p">,</span> <span class="ss">subject: </span><span class="s2">"Your balance is </span><span class="si">#{</span><span class="vi">@balance</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
    <span class="k">end</span>
  <span class="k">end</span>

  <span class="k">def</span> <span class="nf">should_email?</span>
    <span class="o">!</span><span class="vi">@balance</span><span class="p">.</span><span class="nf">zero?</span>
  <span class="k">end</span>
<span class="k">end</span>
</code></pre></div></div>

<p>Things are looking great: tests pass, the product team loves it, it looks great
in the staging environment. Time to ship! Then the first night it’s out in
its new multi-threaded production environment calls start coming in from frantic
customers. “Someone must have stolen my identity.” “Freeze my account, now!”
Something is wrong. They’re receiving emails with balances from other accounts.</p>

<p>Here’s how that could happen:</p>

<div class="language-ruby highlighter-rouge"><div class="highlight"><pre class="highlight"><code> <span class="no">BalanceNotice</span><span class="p">.</span><span class="nf">mail</span><span class="p">(</span><span class="s2">"joe@joe.com"</span><span class="p">,</span> <span class="mi">50</span><span class="p">)</span> <span class="o">|</span>
     <span class="vi">@balance</span> <span class="o">=</span> <span class="mf">50.0</span>                   <span class="o">|</span>
     <span class="n">should_email?</span> <span class="o">=&gt;</span> <span class="kp">true</span>             <span class="o">|</span>
                                       <span class="o">|</span> <span class="no">BalanceNotice</span><span class="p">.</span><span class="nf">mail</span><span class="p">(</span><span class="s2">"ann@ann.com"</span><span class="p">,</span> <span class="mi">9000</span><span class="p">)</span>
                                       <span class="o">|</span>     <span class="vi">@balance</span> <span class="o">=</span> <span class="mf">9000.0</span>
     <span class="no">BalanceMailer</span><span class="p">.</span><span class="nf">mail</span><span class="p">(</span>               <span class="o">|</span>
       <span class="s2">"joe@joe.com"</span><span class="p">,</span>                  <span class="o">|</span>
       <span class="s2">"Your balance is $9000.0"</span>       <span class="o">|</span>
     <span class="p">)</span>                                 <span class="o">|</span>
                                       <span class="o">|</span>     <span class="n">should_email?</span> <span class="o">=&gt;</span> <span class="kp">true</span>
                                       <span class="o">|</span>     <span class="no">BalanceMailer</span><span class="p">.</span><span class="nf">mail</span><span class="p">(</span>
                                       <span class="o">|</span>       <span class="s2">"ann@ann.com"</span><span class="p">,</span>
                                       <span class="o">|</span>       <span class="s2">"Your balance is $9000.0"</span>
                                       <span class="o">|</span>     <span class="p">)</span>
</code></pre></div></div>

<p>While Ann is happy with this new feature, Joe is ecstatic (for now).
<code class="language-plaintext highlighter-rouge">BalanceNotice.mail</code> was called with his balance as an argument, but before his
email was sent <code class="language-plaintext highlighter-rouge">@balance</code> was re-bound to Ann’s balance.</p>

<p>Unless you anticipate this behavior, this bug might be hard to find. However, it
is pretty simple to fix. By replacing the class instance variable (<code class="language-plaintext highlighter-rouge">@balance</code>)
with a local variable (<code class="language-plaintext highlighter-rouge">balance</code>), and passing that local variable to
<code class="language-plaintext highlighter-rouge">should_email?</code> as an argument, sanity is returned.</p>

<div class="language-ruby highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">class</span> <span class="nc">BalanceNotice</span>
  <span class="k">def</span> <span class="nc">self</span><span class="o">.</span><span class="nf">mail</span><span class="p">(</span><span class="n">email</span><span class="p">,</span> <span class="n">balance</span><span class="p">)</span>
    <span class="n">balance</span> <span class="o">=</span> <span class="n">balance</span><span class="p">.</span><span class="nf">to_f</span>

    <span class="k">if</span> <span class="n">should_email?</span><span class="p">(</span><span class="n">balance</span><span class="p">)</span>
      <span class="no">BalanceMailer</span><span class="p">.</span><span class="nf">mail</span><span class="p">(</span><span class="ss">to: </span><span class="n">email</span><span class="p">,</span> <span class="ss">subject: </span><span class="s2">"Your balance is </span><span class="si">#{</span><span class="n">balance</span><span class="si">}</span><span class="s2">"</span><span class="p">)</span>
    <span class="k">end</span>
  <span class="k">end</span>

  <span class="k">def</span> <span class="nf">should_email?</span><span class="p">(</span><span class="n">balance</span><span class="p">)</span>
    <span class="o">!</span><span class="n">balance</span><span class="p">.</span><span class="nf">zero?</span>
  <span class="k">end</span>
<span class="k">end</span>
</code></pre></div></div>

<p>Now each time <code class="language-plaintext highlighter-rouge">.mail</code> is called <code class="language-plaintext highlighter-rouge">balance</code> will be local to that call. Joe will
get Joe’s balance (with great disappointment) and Ann will continue to get Ann’s
balance.</p>]]></content><author><name></name></author><category term="Ruby" /><summary type="html"><![CDATA[Recently someone at work asked about class instance variables. We had recently been told about a catastrophic incident wherein data was being shared with the wrong objects because a class method set an instance variable, then later used that instance variable to do some important work.]]></summary></entry><entry><title type="html">Who owns what in Ruby</title><link href="http://landongrindheim.com/2018/12/01/self-in-ruby-by-example.html" rel="alternate" type="text/html" title="Who owns what in Ruby" /><published>2018-12-01T00:00:00+00:00</published><updated>2018-12-01T00:00:00+00:00</updated><id>http://landongrindheim.com/2018/12/01/self-in-ruby-by-example</id><content type="html" xml:base="http://landongrindheim.com/2018/12/01/self-in-ruby-by-example.html"><![CDATA[<div class="language-ruby highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">class</span> <span class="nc">Person</span>
  <span class="nb">self</span> <span class="c1">#=&gt; Person</span>
  <span class="nb">self</span><span class="p">.</span><span class="nf">class</span> <span class="c1">#=&gt; Class</span>

  <span class="vi">@class_instance_variable</span> <span class="o">=</span> <span class="s2">"Person's instance variable (not shared with subclasses)"</span>

  <span class="vc">@@class_variable</span> <span class="o">=</span> <span class="s2">"Person's class variable (shared with subclasses)"</span>

  <span class="k">def</span> <span class="nc">self</span><span class="o">.</span><span class="nf">persons_method</span> <span class="c1"># Person resonds to this</span>
    <span class="nb">self</span> <span class="c1">#=&gt; Person</span>
    <span class="nb">self</span><span class="p">.</span><span class="nf">class</span> <span class="c1">#=&gt; Class</span>
    <span class="vi">@class_instance_variable</span> <span class="o">=</span> <span class="s2">"Sets Person's instance variable. Not thread safe"</span>
    <span class="vc">@@class_variable</span> <span class="o">=</span> <span class="s2">"Sets Person's class variable. tsk tsk"</span>
  <span class="k">end</span>

  <span class="k">def</span> <span class="nf">bobs_method</span> <span class="c1"># instances of Person respond to this</span>
    <span class="nb">self</span> <span class="c1">#=&gt; #&lt;Person:0x00007f81b687a728&gt;</span>
    <span class="nb">self</span><span class="p">.</span><span class="nf">class</span> <span class="c1">#=&gt; Person</span>
    <span class="vi">@bobs_instance_variable</span> <span class="o">=</span> <span class="s2">"Bob owns this, no other Person will"</span>
  <span class="k">end</span>

  <span class="nb">attr_reader</span> <span class="ss">:bobs_instance_variable</span> <span class="c1"># reads @bobs_instance_variable</span>

  <span class="k">def</span> <span class="nf">set_all_the_things</span>
    <span class="vi">@bobs_instance_variable</span> <span class="o">=</span> <span class="s2">"Bob owns this. No other person will"</span>
    <span class="vc">@@class_variable</span> <span class="o">=</span> <span class="s2">"Person's class variable"</span>
  <span class="k">end</span>
<span class="k">end</span>
</code></pre></div></div>]]></content><author><name></name></author><category term="Ruby" /><summary type="html"><![CDATA[```ruby class Person self #=&gt; Person self.class #=&gt; Class]]></summary></entry></feed>