<?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: Colby Garland</title>
    <description>The latest articles on DEV Community by Colby Garland (@colbygarland).</description>
    <link>https://dev.to/colbygarland</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%2F266683%2F96dfd69e-3b01-4821-8b80-ff182da0b398.jpg</url>
      <title>DEV Community: Colby Garland</title>
      <link>https://dev.to/colbygarland</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/colbygarland"/>
    <language>en</language>
    <item>
      <title>How I Got Caller ID Working in Canada Using RingCentral, Twilio, and ElevenLabs</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Thu, 11 Dec 2025 18:18:35 +0000</pubDate>
      <link>https://dev.to/colbygarland/using-ringcentral-twilio-and-elevenlabs-in-canada-to-get-caller-id-d89</link>
      <guid>https://dev.to/colbygarland/using-ringcentral-twilio-and-elevenlabs-in-canada-to-get-caller-id-d89</guid>
      <description>&lt;h2&gt;
  
  
  Background
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://elevenlabs.io/" rel="noopener noreferrer"&gt;ElevenLabs&lt;/a&gt; is “the most realistic voice AI platform” (their words), and it really is fantastic. I have been using it to automatically call people, leave messages, and run outbound phone workflows. Since the business already had a Twilio number, I used &lt;a href="https://github.com/elevenlabs/elevenlabs-examples/tree/main/examples/conversational-ai/twilio/javascript" rel="noopener noreferrer"&gt;ElevenLabs' Twilio starter kit&lt;/a&gt; for outbound calling.&lt;/p&gt;

&lt;p&gt;The app worked beautifully, except for one big problem.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Problem
&lt;/h2&gt;

&lt;p&gt;Caller ID simply did not work.&lt;/p&gt;

&lt;p&gt;Even though the Twilio number had a name set, calls were coming through as just the phone number. And let’s be honest, nobody answers mystery numbers these days 😅.&lt;/p&gt;

&lt;p&gt;This was killing our answer rate because the agent was leaving tons of voicemails since people did not know who was calling.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Caller ID in Canada Is Weird
&lt;/h2&gt;

&lt;p&gt;In the United States, caller ID is driven by the CNAM database.&lt;/p&gt;

&lt;p&gt;Canada does not have this.&lt;/p&gt;

&lt;p&gt;Instead, Canadian carriers such as Telus, Bell, and Rogers control caller name lookup themselves. That means:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;CNAM registration in Twilio does nothing
&lt;/li&gt;
&lt;li&gt;Caller ID must originate from a number registered with a Canadian carrier
&lt;/li&gt;
&lt;li&gt;Twilio's Branded Calling pilot is mostly focused on the US (I applied and was rejected because our account was too small)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;So the Canadian telecom monopoly strikes again 😔.&lt;/p&gt;

&lt;h2&gt;
  
  
  Exploring Solutions (and Hitting Dead Ends)
&lt;/h2&gt;

&lt;h3&gt;
  
  
  1. Twilio Fix Attempts
&lt;/h3&gt;

&lt;p&gt;I tried everything:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Setting CNAM fields
&lt;/li&gt;
&lt;li&gt;Testing different API configurations
&lt;/li&gt;
&lt;li&gt;Applying for Branded Calling
&lt;/li&gt;
&lt;li&gt;Double checking every setting in the Twilio console
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Nothing worked.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. SIP Trunking: Initial Hope
&lt;/h3&gt;

&lt;p&gt;I started digging into SIP trunking.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;SIP trunking is an internet based replacement for traditional phone lines (PSTN or ISDN). It lets businesses make and receive calls over IP instead of physical lines.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;ElevenLabs supports SIP trunking, so this seemed promising.&lt;/p&gt;

&lt;p&gt;However, caller ID would still depend on having a Canadian registered number on the SIP provider. That meant SIP alone was not a solution.&lt;/p&gt;

&lt;h3&gt;
  
  
  3. RingCentral Plus Telus: Another Possible Path
&lt;/h3&gt;

&lt;p&gt;We did have a Telus registered number through RingCentral. Telus Business Connect is essentially RingCentral under the hood.&lt;/p&gt;

&lt;p&gt;RingCentral also has a great API and supports SIP trunking.&lt;/p&gt;

&lt;p&gt;I set up:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;SIP trunking in ElevenLabs
&lt;/li&gt;
&lt;li&gt;A SIP enabled extension in RingCentral
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Then I hit another blocker.&lt;br&gt;&lt;br&gt;
RingCentral only allows SIP connections through their internal network. They do not allow external services like ElevenLabs to connect.&lt;/p&gt;

&lt;p&gt;Another dead end.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Shower Thought
&lt;/h2&gt;

&lt;p&gt;While washing my hair, I suddenly thought:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;What if I place the call using RingCentral, which gives proper caller ID, and then transfer or bridge the call to Twilio or ElevenLabs afterward?&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;I tried it.&lt;/p&gt;

&lt;p&gt;I could place the call through RingCentral and the caller ID worked.&lt;/p&gt;

&lt;p&gt;But the audio routing did not cooperate.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;RingCentral greetings still played
&lt;/li&gt;
&lt;li&gt;The ElevenLabs audio did not come through
&lt;/li&gt;
&lt;li&gt;Conference or bridge attempts did not solve it
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Close, but still not usable.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Actual Solution
&lt;/h2&gt;

&lt;p&gt;The answer turned out to be much simpler than expected.&lt;/p&gt;

&lt;h3&gt;
  
  
  Let RingCentral call Twilio directly.
&lt;/h3&gt;

&lt;p&gt;Here is the flow:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Set the RingCentral (Telus) number to forward all calls to a Twilio number.&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
Caller ID stays intact because RingCentral is the origin of the call.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Configure the Twilio number to trigger a webhook on inbound calls.&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
The webhook points to your app with the ElevenLabs agent.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Handle the call in your app like any normal inbound Twilio call.&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
ElevenLabs takes over from there.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Why This Works
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;The call originates from a Canadian carrier, which preserves caller ID
&lt;/li&gt;
&lt;li&gt;Twilio only handles the call after it is already ringing, so CNAM is not needed
&lt;/li&gt;
&lt;li&gt;The ElevenLabs agent behaves exactly like a normal inbound Twilio call
&lt;/li&gt;
&lt;li&gt;No SIP trunking or bridging complexity is required
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The first time I answered my phone and saw the company name and heard the ElevenLabs voice agent start speaking, I was stunned. It finally worked.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Results
&lt;/h2&gt;

&lt;p&gt;You can see in this screenshot people are picking up more calls because of the caller ID! &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%2Fjcp67zfejcj4tdqmx5r2.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%2Fjcp67zfejcj4tdqmx5r2.png" alt=" " width="800" height="255"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  TL;DR
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Forward your RingCentral (Telus) number to your Twilio number
&lt;/li&gt;
&lt;li&gt;Configure Twilio to fire a webhook on inbound calls
&lt;/li&gt;
&lt;li&gt;Handle the call in your app using your ElevenLabs logic
&lt;/li&gt;
&lt;/ol&gt;

</description>
      <category>elevenlabs</category>
      <category>ringcentral</category>
      <category>twilio</category>
      <category>callerid</category>
    </item>
    <item>
      <title>Mocking function calls with Jest</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Wed, 04 Aug 2021 21:27:09 +0000</pubDate>
      <link>https://dev.to/colbygarland/mocking-function-calls-with-jest-1da4</link>
      <guid>https://dev.to/colbygarland/mocking-function-calls-with-jest-1da4</guid>
      <description>&lt;p&gt;Imagine you have an API class, that you use to make all of your api calls with.&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="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;API&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;login&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;username&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;password&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt; &lt;span class="cm"&gt;/* logic */&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="nx"&gt;logout&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt; &lt;span class="cm"&gt;/* logic */&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="nx"&gt;getCurrentUser&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt; &lt;span class="cm"&gt;/* logic */&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;When we write automated tests using Jest (&lt;a href="https://jestjs.io/"&gt;https://jestjs.io/&lt;/a&gt;) we want to "mock" these calls, since we don't want to be hitting the api each time we run our tests.&lt;/p&gt;

&lt;p&gt;Luckily, Jest has this functionality for us, built-in :) &lt;/p&gt;

&lt;p&gt;Let's create our mock function:&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="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;mockLogin&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
  &lt;span class="nx"&gt;jest&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;spyOn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;API&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;login&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;mockImplementation&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="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="na"&gt;success&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&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;Now in our test, we can mock this call before we make it:&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;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;user can login with correct username and password&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&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="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;mockLogin&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;api&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nx"&gt;API&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;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;api&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;login&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;colbygarland&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;hunter12&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="nx"&gt;expect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;success&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;toBe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&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;You can rinse and repeat this for any API functions you want to mock - you can decide what data to return back, as if the api was actually sending it back :) &lt;/p&gt;

</description>
      <category>javascript</category>
      <category>testing</category>
    </item>
    <item>
      <title>Try..catch..finally in JavaScript</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Wed, 28 Jul 2021 19:39:43 +0000</pubDate>
      <link>https://dev.to/colbygarland/try-catch-finally-in-javascript-1d2h</link>
      <guid>https://dev.to/colbygarland/try-catch-finally-in-javascript-1d2h</guid>
      <description>&lt;p&gt;Too often I find myself writing this type of code:&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="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;cleanup&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt; 
  &lt;span class="c1"&gt;// Doesn't matter what this does, it just needs &lt;/span&gt;
  &lt;span class="c1"&gt;// to be run after the function is done doing the thing&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;doTheThing&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
  &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// do something that could throw an error&lt;/span&gt;
    &lt;span class="nx"&gt;cleanup&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;results&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// handle the error&lt;/span&gt;
    &lt;span class="nx"&gt;cleanup&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;error&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;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;doTheThing&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Essentially, &lt;code&gt;cleanup()&lt;/code&gt; needs to be ran regardless if our function was successful or not. Luckily, JS provides a nice way to do that for us 🥳&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="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;cleanup&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt; 
  &lt;span class="c1"&gt;// Doesn't matter what this does, it just needs &lt;/span&gt;
  &lt;span class="c1"&gt;// to be run after the function is done doing the thing&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;doTheThing&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
  &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// do something that could throw an error&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;results&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// handle the error&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;finally&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// the finally block gets run regardless of &lt;/span&gt;
    &lt;span class="c1"&gt;// whether we had an error or not&lt;/span&gt;
    &lt;span class="nx"&gt;cleanup&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;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;doTheThing&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So using &lt;code&gt;finally&lt;/code&gt; can clean up our code quite a bit!&lt;/p&gt;

</description>
      <category>javascript</category>
    </item>
    <item>
      <title>Using TypeScript Interface in React Components</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Thu, 22 Jul 2021 22:15:24 +0000</pubDate>
      <link>https://dev.to/colbygarland/using-typescript-interface-in-react-components-227e</link>
      <guid>https://dev.to/colbygarland/using-typescript-interface-in-react-components-227e</guid>
      <description>&lt;p&gt;One of my favorite parts of writing React components with TypeScript is interfacing all of my components.&lt;/p&gt;

&lt;p&gt;Take a simple component:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;MyButton&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;props&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="k"&gt;return&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;button&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="kd"&gt;type&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&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="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So our component, &lt;code&gt;&amp;lt;MyButton /&amp;gt;&lt;/code&gt; takes a &lt;code&gt;type&lt;/code&gt;, an &lt;code&gt;id&lt;/code&gt;, and a &lt;code&gt;title&lt;/code&gt;. This is fine, however if I was importing this component into another file, how would my editor know what props this component takes?&lt;/p&gt;

&lt;p&gt;Enter &lt;code&gt;interface&lt;/code&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kr"&gt;interface&lt;/span&gt; &lt;span class="nx"&gt;MyButtonProps&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;number&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;MyButton&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;MyButtonProps&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="k"&gt;return&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;button&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="kd"&gt;type&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&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="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, when we import this component into another file, VS Code will know what props this component has. 🎉&lt;/p&gt;

</description>
      <category>reactnative</category>
      <category>react</category>
      <category>typescript</category>
    </item>
    <item>
      <title>Using VS Code to git rebase</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Tue, 20 Jul 2021 15:23:40 +0000</pubDate>
      <link>https://dev.to/colbygarland/using-vs-code-to-git-rebase-1lc</link>
      <guid>https://dev.to/colbygarland/using-vs-code-to-git-rebase-1lc</guid>
      <description>&lt;p&gt;Git rebase is a powerful, albeit confusing tool. I primarily use rebase to squash my commits before I PR my branch into &lt;code&gt;main&lt;/code&gt;. This tutorial will show you how to use VS Code to visually do this process.&lt;/p&gt;

&lt;h2&gt;
  
  
  Prerequisites
&lt;/h2&gt;

&lt;p&gt;You will need to install this VS Code extension: &lt;a href="https://marketplace.visualstudio.com/items?itemName=eamodio.gitlens" rel="noopener noreferrer"&gt;https://marketplace.visualstudio.com/items?itemName=eamodio.gitlens&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;You will also need to enable "force push":&lt;/p&gt;

&lt;p&gt;In settings, search for "git allow force push" and check the box&lt;/p&gt;

&lt;p&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%2Fpya9bvebfkbt48v8q8hl.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%2Fpya9bvebfkbt48v8q8hl.png" alt="image" width="800" height="138"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Optional but recommended&lt;/strong&gt;: set VS Code as your git editor:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;git config --global core.editor "code --wait"&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Let's Begin!
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Ensure your local branch you are rebasing onto (in our case, &lt;code&gt;main&lt;/code&gt;) is up to date.&lt;/li&gt;
&lt;li&gt;Switch to your feature branch (the branch you have been working on)&lt;/li&gt;
&lt;li&gt;Type in &lt;code&gt;git rebase -i main&lt;/code&gt;, where &lt;code&gt;main&lt;/code&gt; is the branch you are rebasing onto&lt;/li&gt;
&lt;li&gt;You will then see the codelens rebase screen, where you can choose what to do with each commit. We are going to &lt;code&gt;squash&lt;/code&gt; every commit, and &lt;code&gt;reword&lt;/code&gt; the last one into a good commit message.&lt;/li&gt;
&lt;li&gt;Once you have your commits ready, we can click the &lt;code&gt;Start Rebase&lt;/code&gt; button.&lt;/li&gt;
&lt;li&gt;You will then be presented with a screen in VS Code to reword your commit message. Write your new message, and save and close the file to continue.&lt;/li&gt;
&lt;li&gt;After this, our rebase is complete. However, now we must force push to remote. In your version control panel, click on the kebab menu (3 dots) and under the &lt;code&gt;Pull, Push&lt;/code&gt; menu, choose &lt;code&gt;Push (Force)&lt;/code&gt;. Use this with caution, especially when working with other developers, as force push is destructive.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;And we are done! A very easy way to rebase and squash all your commits using VS Code.&lt;/p&gt;

</description>
      <category>vscode</category>
      <category>git</category>
    </item>
    <item>
      <title>Logging Exceptions via Slack in Laravel</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Tue, 20 Jul 2021 15:02:23 +0000</pubDate>
      <link>https://dev.to/colbygarland/logging-exceptions-via-slack-in-laravel-33b7</link>
      <guid>https://dev.to/colbygarland/logging-exceptions-via-slack-in-laravel-33b7</guid>
      <description>&lt;p&gt;Logging can be a powerful tool that people tend to gloss over. Most developers still view logging as an archaic way of dealing with bugs and user issues. Laravel has a very easy and eloquent way of dealing with the logging problem.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Problem
&lt;/h2&gt;

&lt;p&gt;Logging is usually done by creating a log file on your server, and telling your backend to send all errors to that file. While this is a good temporary solution, this system tends to fill up fast, and is a pain to search and find certain things.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Solution (one of many)
&lt;/h2&gt;

&lt;p&gt;Using Laravel’s built-in logging system, you can log to many different “channels”, including our old tried and true, file logging on the server. But that isn’t why you are reading this post, is it?&lt;/p&gt;

&lt;h2&gt;
  
  
  Slack it to me
&lt;/h2&gt;

&lt;p&gt;If you have ever used Slack, you’ve grown to love the instant messaging capabilities, and the searching function. Search is great on Slack. And one of our problems with logging was search, wasn’t it? Wouldn’t it be great if we could log all our errors to Slack? Good news!&lt;/p&gt;

&lt;h2&gt;
  
  
  How to log exceptions to Slack
&lt;/h2&gt;

&lt;p&gt;Logging is relatively easy in Laravel (&lt;a href="https://laravel.com/docs/6.x/logging"&gt;see this page for how-to setup Slack logging&lt;/a&gt;). What we want is to nicely log all our exceptions.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;This post is written assuming you have a Laravel project already set up.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Open your &lt;code&gt;app/Exceptions/Handler.php&lt;/code&gt; handler file. This is where Laravel gives you the option to send exceptions to Sentry, Bugsnag, or any other bug reporters you want to set up. This is also where we will be logging to our Slack channel.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight php"&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="n"&gt;report&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;Exception&lt;/span&gt; &lt;span class="nv"&gt;$exception&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;parent&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="nf"&gt;report&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;$exception&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 are going to change this function to do a few things.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Log to Slack (that is why you are here!)&lt;/li&gt;
&lt;li&gt;Format the exception nicely.&lt;/li&gt;
&lt;li&gt;We will do an optional filter to filter out any vendor code.&lt;/li&gt;
&lt;li&gt;Remove the &lt;code&gt;parent::report($exception)&lt;/code&gt; as we are going to be doing this ourselves.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Our function will now look like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight php"&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="n"&gt;report&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;Exception&lt;/span&gt; &lt;span class="nv"&gt;$exception&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// You can specify which exceptions not to report here&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;$this&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="nf"&gt;shouldntReport&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;$exception&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="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="c1"&gt;// We are getting the directory so we can filter out any vendor code,&lt;/span&gt;
    &lt;span class="c1"&gt;// along with the directory, so it looks better for the developer.&lt;/span&gt;
    &lt;span class="nv"&gt;$dir&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;substr&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;__DIR__&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="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;14&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="nv"&gt;$backtrace&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;  &lt;span class="nv"&gt;$exception&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="nf"&gt;getTraceAsString&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="nv"&gt;$backtrace&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;str_replace&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="nv"&gt;$dir&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="s2"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;$backtrace&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="nv"&gt;$backtrace&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;preg_replace&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'^(.*vendor.*)\n^'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;''&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nv"&gt;$backtrace&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="c1"&gt;// And finally, we log the exception! &lt;/span&gt;
    &lt;span class="nc"&gt;Log&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="nf"&gt;channel&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'slack'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="nf"&gt;error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'@here'&lt;/span&gt;&lt;span class="mf"&gt;.&lt;/span&gt;&lt;span class="kc"&gt;PHP_EOL&lt;/span&gt;&lt;span class="mf"&gt;.&lt;/span&gt;&lt;span class="s1"&gt;' . PHP_EOL . '&lt;/span&gt;&lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="nc"&gt;Error&lt;/span&gt;&lt;span class="o"&gt;:**&lt;/span&gt; &lt;span class="s1"&gt;'.$exception-&amp;gt;getMessage() . PHP_EOL. '&lt;/span&gt;&lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="nc"&gt;Line&lt;/span&gt;&lt;span class="o"&gt;:**&lt;/span&gt; &lt;span class="s1"&gt;' . $exception-&amp;gt;getLine() . PHP_EOL. '&lt;/span&gt;&lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="nc"&gt;File&lt;/span&gt;&lt;span class="o"&gt;:**&lt;/span&gt; &lt;span class="s1"&gt;'. $exception-&amp;gt;getFile() . PHP_EOL . '&lt;/span&gt;&lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="nc"&gt;Trace&lt;/span&gt;&lt;span class="o"&gt;:**&lt;/span&gt;&lt;span class="err"&gt;'&lt;/span&gt;&lt;span class="mf"&gt;.&lt;/span&gt;&lt;span class="kc"&gt;PHP_EOL&lt;/span&gt;&lt;span class="mf"&gt;.&lt;/span&gt; &lt;span class="nv"&gt;$backtrace&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 that’s it! It is very easy to nicely log your exceptions using Laravel’s built-in logging system.&lt;/p&gt;

&lt;p&gt;image credits: &lt;a href="https://unsplash.com/photos/gNoqNvYAsBg"&gt;https://unsplash.com/photos/gNoqNvYAsBg&lt;/a&gt;&lt;/p&gt;

</description>
      <category>laravel</category>
      <category>php</category>
    </item>
    <item>
      <title>Create a useStore hook for mobx-state-tree</title>
      <dc:creator>Colby Garland</dc:creator>
      <pubDate>Mon, 19 Jul 2021 20:53:56 +0000</pubDate>
      <link>https://dev.to/colbygarland/create-a-usestore-hook-for-mobx-state-tree-1la9</link>
      <guid>https://dev.to/colbygarland/create-a-usestore-hook-for-mobx-state-tree-1la9</guid>
      <description>&lt;h2&gt;
  
  
  Mobx-state-tree?
&lt;/h2&gt;

&lt;p&gt;From the mobx-state-tree docs:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;MobX is a state management "engine", and MobX-State-Tree gives it structure and common tools you need for your app.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;This post will help you to create a &lt;code&gt;useStore&lt;/code&gt; hook to use MST in functional components in a React project.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Note: this post will be written in TypeScript.&lt;/em&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Let's Get Hooked
&lt;/h2&gt;

&lt;p&gt;First things first, let's create our "root store" (this will be our store that will hold our of other stores - more on that later)&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;/// src/stores/rootStore.ts&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mobx-state-tree&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;rootStore&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt;
  &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;model&lt;/span&gt;&lt;span class="p"&gt;({})&lt;/span&gt;
  &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;create&lt;/span&gt;&lt;span class="p"&gt;({});&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Explanation
&lt;/h3&gt;

&lt;p&gt;From MST, we import the &lt;code&gt;types&lt;/code&gt;. This allows us to create a "model", which will hold our data, as well as computed data, and actions to update our data.&lt;/p&gt;

&lt;h2&gt;
  
  
  Context is Key
&lt;/h2&gt;

&lt;p&gt;To use our hook in our React app, let's utilize React's Context API to help us do that.&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;/// src/stores/rootStore.ts&lt;/span&gt;

&lt;span class="c1"&gt;// Add `Instance` to our import from MST&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;type&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Instance&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mobx-state-tree&lt;/span&gt;&lt;span class="dl"&gt;'&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;RootStoreContext&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;createContext&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="nx"&gt;Instance&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;typeof&lt;/span&gt; &lt;span class="nx"&gt;rootStore&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;StoreProvider&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;RootStoreContext&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;Provider&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 javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;/// src/app.tsx&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;StoreProvider&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;rootStore&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./stores/rootStore&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;App&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;StoreProvider&lt;/span&gt; &lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;rootStore&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="cm"&gt;/** rest of your app here */&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/StoreProvider&lt;/span&gt;&lt;span class="err"&gt;&amp;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;
  
  
  Explanation
&lt;/h3&gt;

&lt;p&gt;We will wrap our app with this &lt;code&gt;StoreProvider&lt;/code&gt; and pass as its value, our &lt;code&gt;rootStore&lt;/code&gt; from above.&lt;/p&gt;

&lt;h2&gt;
  
  
  Now to create the hook
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;/// src/stores/rootStore.ts&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;useStore&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;store&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;React&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;useContext&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;RootStoreContext&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;store&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;
    &lt;span class="k"&gt;throw&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nb"&gt;Error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Store cannot be null, please add a context provider&lt;/span&gt;&lt;span class="dl"&gt;'&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="nx"&gt;store&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;h2&gt;
  
  
  Add some models
&lt;/h2&gt;

&lt;p&gt;Now we can use this, but first, let us add a store into our &lt;code&gt;rootStore&lt;/code&gt; so we can utilize this.&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;/// src/stores/userStore.ts&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mobx-state-tree&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;// example store, replace this with your actual stores&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;UserStore&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt;
  &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;model&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;UserStore&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;string&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;span class="nx"&gt;actions&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nb"&gt;self&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="na"&gt;setName&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;string&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="nb"&gt;self&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;name&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;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;UserStoreInitialState&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;''&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&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;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;/// src/stores/rootStore.ts&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;UserStore&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;UserStoreInitialState&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./userStore&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;rootStore&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;types&lt;/span&gt;
  &lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;model&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;userStore&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;UserStore&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;span class="nx"&gt;create&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;userStore&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;UserStoreInitialState&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;h2&gt;
  
  
  Using our new hook
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;/// src/components/user.ts&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;useStore&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;../stores/rootStore&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;User&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;userStore&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;useStore&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;h1&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;userStore&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/h1&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;button&lt;/span&gt; &lt;span class="nx"&gt;onPress&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="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;userStore&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;setName&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Colby&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&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="nx"&gt;Update&lt;/span&gt; &lt;span class="nx"&gt;Name&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;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;h2&gt;
  
  
  What about re-rendering?
&lt;/h2&gt;

&lt;p&gt;If you want your component to automatically re-render when state changes, use the &lt;code&gt;mobx-react-lite&lt;/code&gt; package.&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;/// src/components/user.ts&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;useStore&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;../stores/rootStore&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;observer&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mobx-react-lite&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;User&lt;/span&gt; &lt;span class="nx"&gt;observer&lt;/span&gt;&lt;span class="p"&gt;((){&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;userStore&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;useStore&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;h1&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;userStore&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/h1&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;button&lt;/span&gt; &lt;span class="nx"&gt;onPress&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="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;userStore&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;setName&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Colby&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&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="nx"&gt;Update&lt;/span&gt; &lt;span class="nx"&gt;Name&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;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;Wrapping any component that "observers" an MST model's state will automatically re-render when that state changes.&lt;/p&gt;

&lt;h2&gt;
  
  
  All done!
&lt;/h2&gt;

&lt;p&gt;And that's it! Mobx-state-tree (combined with mobx-react-lite for re-rendering) are amazing tools to keep in your tool belt, and a nice alternative to Redux (a lot less code to write to achieve what you want).&lt;/p&gt;

&lt;p&gt;image credit: &lt;a href="https://unsplash.com/photos/c9FQyqIECds"&gt;https://unsplash.com/photos/c9FQyqIECds&lt;/a&gt;&lt;/p&gt;

</description>
      <category>typescript</category>
      <category>react</category>
    </item>
  </channel>
</rss>
