<?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: Sriram Thiagarajan</title>
    <description>The latest articles on DEV Community by Sriram Thiagarajan (@tsriram).</description>
    <link>https://dev.to/tsriram</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%2F3540%2F450559.jpeg</url>
      <title>DEV Community: Sriram Thiagarajan</title>
      <link>https://dev.to/tsriram</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/tsriram"/>
    <language>en</language>
    <item>
      <title>Deconstructing Stripe's email verification flow</title>
      <dc:creator>Sriram Thiagarajan</dc:creator>
      <pubDate>Sun, 06 Mar 2022 15:53:36 +0000</pubDate>
      <link>https://dev.to/tsriram/deconstructing-stripes-email-verification-flow-3b29</link>
      <guid>https://dev.to/tsriram/deconstructing-stripes-email-verification-flow-3b29</guid>
      <description>&lt;p&gt;I came across this tweet from &lt;a href="https://twitter.com/championswimmer"&gt;@championswimmer&lt;/a&gt; and was intrigued about the feature &amp;amp; implementation.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://twitter.com/championswimmer/status/1489259915214405646"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--VmtW5QZc--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/5pv4cl8y33x3ltceobrl.png" alt="Screenshot of the linked tweet" width="880" height="438"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Let's dig deeper.&lt;/p&gt;

&lt;h3&gt;
  
  
  Stripe's signup flow
&lt;/h3&gt;

&lt;p&gt;When you sign up for a Stripe account, the app takes you to a dashboard page as soon as your account is created and shows a message asking you to verify your email address by clicking on the link sent to you email. Pretty standard right? Well, Stipe steps this UX up a notch by having a button on this landing page to open your email. And they take this to the next level by opening your email with a search query embedded to filter out only the emails sent by Stripe. This is an amazing UX.&lt;/p&gt;

&lt;p&gt;As you might think, this doesn't work for all email addresses obviously because it's hard to know the URL for ton of email providers and not all of them support a search query in the URL to filter emails.&lt;/p&gt;

&lt;p&gt;This flow works only for Gmail (both personal gmail.com accounts and other domains that have email hosted by Google Workspace). From my experiments, this button to open email works for Gmail &amp;amp; Outlook and the button clearly shows this with &lt;code&gt;Open Gmail&lt;/code&gt; &amp;amp; &lt;code&gt;Open Outlook&lt;/code&gt; labels respectively. I tried signing up with a &lt;a href="https://www.hey.com/"&gt;Hey&lt;/a&gt; email address and there was no button to open email. Only a message was displayed to&lt;/p&gt;

&lt;p&gt;Note: Both the email addresses shown below are not mine, Stripe one should've been obvious though :) Apologies to the owners of these emails. Sorry I had to test :P&lt;/p&gt;

&lt;p&gt;Here's how it looks for a Hey email address:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--DXDNubHd--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ouu7ymnrkvta3mac8ck0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--DXDNubHd--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ouu7ymnrkvta3mac8ck0.png" alt="Screenshot of Stripe's welcome message for a user with hey.com email" width="652" height="172"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And here's how it looks for a Gmail address (Stripe uses Gmail):&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--6zgd1kcs--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/p1npw9g4aapo660zvfxi.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--6zgd1kcs--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/p1npw9g4aapo660zvfxi.png" alt="Screenshot of Stripe's welcome message for a user with Gmail" width="651" height="172"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is the URL the &lt;code&gt;Open Gmail&lt;/code&gt; button opens:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;https://mail.google.com/mail/u/sriram@stripe.com/#search/from:support@stripe.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you can see in the above URL, it has the search query which filters emails from &lt;a href="mailto:support@stripe.com"&gt;support@stripe.com&lt;/a&gt; which is used to send out these verification emails.&lt;/p&gt;

&lt;p&gt;Another learning from this exercise is that Gmail can take the email address in URL instead of numbers (0/ 1/ 2) as route param and open the correct one if you've logged into multiple accounts in your browser. You might have seen URLs like these:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;mail.google.com/u/0&lt;/li&gt;
&lt;li&gt;mail.google.com/u/1&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;You can actually put &lt;code&gt;mail.google.com/u/&amp;lt;email&amp;gt;&lt;/code&gt; and it'll automatically redirect you to the correct account. It's brilliant that Gmail supports this and Stripe's team learnt &amp;amp; used it in their email verification flow to ensure that users don't land on their default Gmail account when they click on &lt;code&gt;Open Gmail&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  The How
&lt;/h3&gt;

&lt;p&gt;So we want to find if an email address belongs to Gmail. The implementation of this seems to be fairly straightforward. If I want to implement this, I'd probably follow these steps:&lt;/p&gt;

&lt;h4&gt;
  
  
  1. Get the domain name from email address
&lt;/h4&gt;

&lt;p&gt;This one's easy. Also check if the email is a valid one first. If the domain is &lt;code&gt;gmail.com&lt;/code&gt;, you don't have to anything else :)&lt;/p&gt;

&lt;h4&gt;
  
  
  2. Do a DNS lookup and get MX records
&lt;/h4&gt;

&lt;p&gt;If you're familiar with DNS records, you'd know that &lt;a href="https://www.cloudflare.com/en-in/learning/dns/dns-records/dns-mx-record/"&gt;MX records&lt;/a&gt; are used for routing emails. Since we want to find if an email is hosted by Gmail, we need to first get these records for the domain.&lt;/p&gt;

&lt;p&gt;This is quite easy with &lt;a href="https://en.wikipedia.org/wiki/DNS_over_HTTPS"&gt;DNS-over-HTTPS&lt;/a&gt; (DoH). You could use the service from &lt;a href="https://developers.google.com/speed/public-dns/docs/doh"&gt;Google&lt;/a&gt; or &lt;a href="https://developers.cloudflare.com/1.1.1.1/encrypted-dns/dns-over-https/dns-over-https-client"&gt;Cloudflare&lt;/a&gt;.&lt;/p&gt;

&lt;h4&gt;
  
  
  3. Verify if MX records belong to Gmail
&lt;/h4&gt;

&lt;p&gt;Google publishes MX records that one need to set if they want to get their domain configured for Google Workspace. You can find them here - &lt;a href="https://support.google.com/a/answer/140034"&gt;https://support.google.com/a/answer/140034&lt;/a&gt;. So once you have the MX records of the domain, it's simply verifying if the records match at least one of the records provided by Google for Gmail. If it does, you can be sure that the email is provided by Gmail.&lt;/p&gt;

&lt;p&gt;That's pretty much it. Once you know that the email is hosted on Gmail, you can use the same technique to add search query to the URL to filter out the mails sent by you.&lt;/p&gt;

&lt;p&gt;What do you think about this? Have a different solution in mind? Feel free to ping me on &lt;a href="https://twitter.com/tsriram"&gt;twitter&lt;/a&gt; :)&lt;/p&gt;

</description>
      <category>ux</category>
      <category>stripe</category>
    </item>
    <item>
      <title>Next.js' ISR vs Gatsby's DSG</title>
      <dc:creator>Sriram Thiagarajan</dc:creator>
      <pubDate>Sat, 09 Oct 2021 10:37:35 +0000</pubDate>
      <link>https://dev.to/tsriram/next-js-isr-vs-gatsby-s-dsg-3h66</link>
      <guid>https://dev.to/tsriram/next-js-isr-vs-gatsby-s-dsg-3h66</guid>
      <description>&lt;p&gt;When I heard about Gatsby adding a new rendering option called Deferred Static Generation in Gatsby 4, &lt;a href="https://twitter.com/tsriram/status/1438550978064633856"&gt;I thought&lt;/a&gt; it's similar to Next.js' Incremental Static Regeneration. Looking a bit deep into the DSG rendering option, it turns out there are quite a few differences. Hint: if you look closely at the names, you might be able to guess what the main difference is :) Let's see each of these options in detail.&lt;/p&gt;

&lt;h3&gt;
  
  
  Deferred Static Generation
&lt;/h3&gt;

&lt;p&gt;From the &lt;a href="https://v4.gatsbyjs.com/docs/conceptual/rendering-options/#deferred-static-generation-dsg"&gt;docs&lt;/a&gt; - Deferred Static Generation is developers can choose to defer building certain pages until the first time a user requests it. This essentially means we're delaying the generation of the page until the first request. Once the page is generated, all subsequent users will see the same page from cache.&lt;/p&gt;

&lt;h3&gt;
  
  
  Incremental Static Regeneration
&lt;/h3&gt;

&lt;p&gt;From the &lt;a href="https://nextjs.org/docs/basic-features/data-fetching#incremental-static-regeneration"&gt;docs&lt;/a&gt; - Next.js allows you to create or update static pages after you’ve built your site. Incremental Static Regeneration (ISR) enables you to use static-generation on a per-page basis, without needing to rebuild the entire site. With ISR, you can retain the benefits of static while scaling to millions of pages. The key to note here is "create or update". Next.js ISR will be able delay the generation of a page until first request, and also be able to regenerate the page after a specific time has elapsed. &lt;/p&gt;

&lt;h3&gt;
  
  
  ISR vs DSG
&lt;/h3&gt;

&lt;p&gt;As you would have seen from the above details, the main difference between ISR and DSG is that ISR will be able regenerate your page on a given interval. Once a page is generated, it'll be served from cache till the time it is regenerated and the regeneration happens in the background. This is really powerful as the page regeneration will be able to fetch updated data from your data source.&lt;/p&gt;

&lt;p&gt;In contrast, DSG is just delaying the generation of static pages. Once a page is generated (upon first request), it's just static. If you update the content for the page after it's generated, you've to run the build once again to invalidate the cached page.&lt;/p&gt;

&lt;p&gt;The problems that ISR &amp;amp; DSG solve are also different. DSG solves the problem of having a longer build times. This has been a problem with Gatsby for a while. More the number of pages, more the build time. And DSG is a pretty good option to solve this as you can build the logic yourself whether you want to generate a page at build time or not.&lt;/p&gt;

&lt;p&gt;ISR, to me, seems like a superset of DSG - you can still do deferred generation of static pages, and also regenerate those pages automatically when the given time elapses. For example, if you have page with some data source that gets updated on a daily basis, you can set Next.js to regenerate the page every day. So your users will still be accessing static page from CDN &amp;amp; you get all the speed benefits, and at the same time you don't have to run the build process everyday.&lt;/p&gt;

&lt;p&gt;Furthermore, pages generated by ISR are persisted across deployments (at least on Vercel) i.e. your users will see the cached version of the page even if you deploy a new version of your code. The page will only be regenerated based on &lt;a href="https://nextjs.org/docs/basic-features/data-fetching#incremental-static-regeneration"&gt;&lt;code&gt;revalidate&lt;/code&gt;&lt;/a&gt; option in your code. For more details, look at Vercel's &lt;a href="https://vercel.com/docs/next.js/incremental-static-regeneration#isr:-not-just-caching"&gt;documentation&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Okay, this is my understanding of these two and if you find something is wrong, please &lt;a href="https://twitter.com/tsriram"&gt;let me know on twitter&lt;/a&gt;. Feel free to tweet / DM if you want to talk about this in more detail or just wanna say hi :)&lt;/p&gt;

&lt;p&gt;PS: I'm quite sure something like ISR will be coming to Gatsby in near future&lt;/p&gt;

</description>
      <category>nextjs</category>
      <category>gatsby</category>
      <category>react</category>
    </item>
  </channel>
</rss>
