<?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: Will Harris</title>
    <description>The latest articles on DEV Community by Will Harris (@will_devs).</description>
    <link>https://dev.to/will_devs</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%2F393911%2F161c6765-e200-4f04-ad08-26780951f711.jpeg</url>
      <title>DEV Community: Will Harris</title>
      <link>https://dev.to/will_devs</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/will_devs"/>
    <language>en</language>
    <item>
      <title>Why I Use Gatsby for My Website</title>
      <dc:creator>Will Harris</dc:creator>
      <pubDate>Wed, 29 Jul 2020 01:04:54 +0000</pubDate>
      <link>https://dev.to/will_devs/why-i-use-gatsby-for-my-website-mkf</link>
      <guid>https://dev.to/will_devs/why-i-use-gatsby-for-my-website-mkf</guid>
      <description>&lt;p&gt;&lt;em&gt;Originally posted on &lt;a href="https://www.willharris.dev/garden/why-i-use-gatsby-for-my-website"&gt;Will's blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;I built my personal website using &lt;a href="https://reactjs.org/"&gt;React&lt;/a&gt; and &lt;a href="https://www.gatsbyjs.org/"&gt;Gatsby&lt;/a&gt;. Partially this was to give me the opportunity both to learn a new tool (Gatsby) and to practice with GraphQL.&lt;/p&gt;

&lt;p&gt;Recently I stumbled across &lt;a href="https://beesbuzz.biz/blog/2934-Advice-to-young-web-developers"&gt;this blog post&lt;/a&gt; listing things the author would "like younger developers to think about."&lt;/p&gt;

&lt;p&gt;Many of the points in the article seem to bemoan the widespread use of front-end frameworks in web development. I can sympathize with this point; as the author says, "sometimes a website is just a website."&lt;/p&gt;

&lt;p&gt;However, I do think that there are good reasons for using React and Gatsby—or other static site generators—to create websites. I want to use this post to explore some of my reasons for embracing Gatsby.&lt;/p&gt;

&lt;p&gt;I also want to encourage anyone to challenge me on these reasons. I use Gatsby because I genuinely think it is the best tool for my use-case, but am always open to learning better ways of doing things.&lt;/p&gt;

&lt;h2&gt;
  
  
  Image optimization
&lt;/h2&gt;

&lt;p&gt;Images account for a significant portion of the size of most websites. Because of this, optimizing images can greatly improve a website's performance. The fewer bytes to download, the faster the browser can get to rendering content on the screen.&lt;/p&gt;

&lt;p&gt;Best practices for performance across a range of devices call for multiple image sizes and resolutions. We could manually create different versions of every image that we use on a website, but this adds a lot of duplicate work for every image that we include. Another downside of the manual approach is the added bookkeeping involved in ensuring that all of the images get optimized before they make it to production.&lt;/p&gt;

&lt;p&gt;Gatsby makes image optimization much easier, harnessing the power of build plugins and transformers to eliminate most of the manual work.&lt;/p&gt;

&lt;p&gt;Gatsby sources data using source plugins, which allow the developer to pull data from different sources. &lt;code&gt;gatsby-source-filesystem&lt;/code&gt; sources data into our application from the project's local filesystem, creating &lt;code&gt;File&lt;/code&gt; nodes in Gatsby's GraphQL API. Gatsby applies various transformer plugins to these &lt;code&gt;File&lt;/code&gt; nodes, turning them into various other types of nodes. For image processing, the &lt;code&gt;gatsby-transformer-sharp&lt;/code&gt; plugin takes supported image files and creates &lt;code&gt;ImageSharp&lt;/code&gt; nodes from them.&lt;/p&gt;

&lt;p&gt;These &lt;code&gt;ImageSharp&lt;/code&gt; nodes can then be manipulated by the &lt;a href="https://github.com/lovell/sharp"&gt;Sharp image processing Node.js library&lt;/a&gt; to help with image processing and optimization. We perform these manipulations with GraphQL queries in Gatsby, which allow Gatsby and Sharp to perform all of our required optimizations while building the final static site. This is where we save a ton of work compared to optimizing images manually. We only need to configure how we want our images optimized, and Gatsby handles the rest.&lt;/p&gt;

&lt;p&gt;Gatsby also ships an &lt;a href="https://www.gatsbyjs.org/packages/gatsby-image/"&gt;image component&lt;/a&gt; that is designed to work well with Gatsby's GraphQL queries. It is optimized specifically for fixed width/height images and images that stretch to fit full-width containers.&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;gatsby-image&lt;/code&gt; component automatically helps with image optimization in several ways. It:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Loads the optimal image size for a given screen size, using the &lt;code&gt;srcset&lt;/code&gt; property on a &lt;a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/picture"&gt;&lt;code&gt;picture&lt;/code&gt; element&lt;/a&gt; to load the correct image size for the current viewport.&lt;/li&gt;
&lt;li&gt;Holds the image's position in the document with a placeholder so that the page doesn't jump around as images load.&lt;/li&gt;
&lt;li&gt;Uses either a "blur-up" effect or a "traced-placeholder" SVG to show a visual placeholder while the full image loads.&lt;/li&gt;
&lt;li&gt;Lazy loads images, reducing bandwidth and load time.&lt;/li&gt;
&lt;li&gt;Can convert images to the &lt;a href="https://developers.google.com/speed/webp/"&gt;WebP format&lt;/a&gt; if it is supported by the browser.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;All of these features are "batteries-included" with the &lt;code&gt;gatsby-image&lt;/code&gt; component, saving the developer a ton of manual image optimization work.&lt;/p&gt;

&lt;h2&gt;
  
  
  No Backend / Moving Parts
&lt;/h2&gt;

&lt;p&gt;Setting up a "traditional" website is a fairly complex process. From provisioning VMs to run instances of a server-side app, to configuring &lt;a href="https://www.docker.com/"&gt;Docker&lt;/a&gt; images to ensure a consistent environment, to configuring auto-scaling solutions like &lt;a href="https://kubernetes.io/"&gt;Kubernetes&lt;/a&gt;. There are a lot of moving pieces to keep track of.&lt;/p&gt;

&lt;p&gt;And if we want to deploy any changes to our site with this structure, it involves deploying a completely new version of the site. We'd have to spin down existing versions of the service, spin up the new version, and deal with any issues that might pop up during the process.&lt;/p&gt;

&lt;p&gt;Gatsby simplifies this process by building websites as static HTML files which can be hosted on a &lt;a href="https://developer.mozilla.org/en-US/docs/Glossary/CDN"&gt;CDN&lt;/a&gt;, getting our content as close as possible to our users. We can then configure a continuous integration (CI) system to rapidly build and deploy code updates to the CDN.&lt;/p&gt;

&lt;p&gt;My site is hosted on &lt;a href="https://www.netlify.com/"&gt;Netlify&lt;/a&gt;, which allows me to use a GitHub repository as my CI system. If I want to publish a new version of the site, all I need to do is merge a pull request into my main branch. Netlify is constantly listening for pushes to that branch—as soon as changes are noticed, a new version of the site is built with Gatsby and pushed to the CDN. Typical deploys for me right now take about one minute.&lt;/p&gt;

&lt;p&gt;Both approaches can result in robust, performant websites. However, deploying and hosting static content via CDN has far fewer moving pieces and completely removes the server management aspect of developing a website.&lt;/p&gt;

&lt;h2&gt;
  
  
  Build Optimizations
&lt;/h2&gt;

&lt;p&gt;Gatsby sites are built in React and then built into static HTML files by Node.js processes. The process of converting pages and content on the server into HTML is called server-side rendering (SSR), and it's nothing new.&lt;/p&gt;

&lt;p&gt;Developers have been rendering HTML pages on servers for many years. Previously, however, sites would use languages like PHP on the server to fetch data from databases, in response to user requests, and compile it into an HTML document to send to the user.&lt;/p&gt;

&lt;p&gt;With Gatsby, &lt;strong&gt;all of the SSR magic occurs during the build process&lt;/strong&gt;. This build process has quite a few steps, but as a quick summary:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Gatsby checks for data sources defined in the &lt;code&gt;gatsby-config.js&lt;/code&gt; and &lt;code&gt;gatsby-node.js&lt;/code&gt; files. It then creates &lt;code&gt;Node&lt;/code&gt; objects from the data it finds in these sources.&lt;/li&gt;
&lt;li&gt;Gatsby infers a GraphQL schema from the &lt;code&gt;Node&lt;/code&gt; objects created in the previous step. This is where Gatsby forms the data layer for our application, making all of the data brought in from our sources available in a GraphQL API.&lt;/li&gt;
&lt;li&gt;Gatsby creates pages from the React components in our site.&lt;/li&gt;
&lt;li&gt;GraphQL queries from our React components are extracted from our components and run against the GraphQL layer, providing data for all of the HTML pages.&lt;/li&gt;
&lt;li&gt;Static files are created for all of our pages, with all data bundled alongside our views in the &lt;code&gt;public&lt;/code&gt; directory.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The resulting HTML files created by Gatsby also use modern browser APIs to maximize performance, resulting in &lt;em&gt;crazy fast&lt;/em&gt; websites.&lt;/p&gt;

&lt;p&gt;Gatsby harnesses the &lt;a href="https://developer.mozilla.org/en-US/docs/Web/API/Intersection_Observer_API"&gt;&lt;code&gt;IntersectionObserver&lt;/code&gt; API&lt;/a&gt;, which conditionally performs actions when elements enter the browser's viewport.&lt;/p&gt;

&lt;p&gt;Specifically, in Gatsby &lt;code&gt;IntersectionObserver&lt;/code&gt; is implemented in the &lt;code&gt;Link&lt;/code&gt; component for routes internal to the site. The behavior has two parts:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;An &lt;code&gt;IntersectionObserver&lt;/code&gt; is registered for all &lt;code&gt;Link&lt;/code&gt; components. This registers an &lt;a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Link_prefetching_FAQ"&gt;idle prefetch&lt;/a&gt; request for each &lt;code&gt;Link&lt;/code&gt;'s resources, allowing the browser to automatically start loading those resources as soon as the browser is in an idle state.&lt;/li&gt;
&lt;li&gt;On a &lt;code&gt;mouseenter&lt;/code&gt; event for any &lt;code&gt;Link&lt;/code&gt; component, a &lt;code&gt;fetch&lt;/code&gt; request is fired with a non-idle request for the &lt;code&gt;Link&lt;/code&gt;'s resources.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In combination, these two techniques almost guarantee that internal page data will be prefetched, which makes page loads on our site feel instantaneous.&lt;/p&gt;

&lt;h2&gt;
  
  
  Plain Text
&lt;/h2&gt;

&lt;p&gt;One additional benefit I've found in using a system like Gatsby for my writing is the ability to keep all of my data in plain text markdown files.&lt;/p&gt;

&lt;p&gt;As Dave Thomas and Andy Hunt write in &lt;em&gt;The Pragmatic Programmer&lt;/em&gt;:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;The problem with most binary formats is that the context necessary to understand the data is separate from the data itself. You are artificially divorcing the data from its meaning. The data may as well be encrypted: it is absolutely meaningless without the application logic to parse it. With plain text, however, you can achieve a self-describing data stream that is independent of the application that created it.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;By keeping all of my writing in markdown files, I guarantee that I'll never be dependent on a specific piece of software to use my content. I also can harness the inherent semantics of markdown to generate HTML elements from my writing.&lt;/p&gt;

&lt;p&gt;Gatsby uses the &lt;code&gt;gatsby-transformer-remark&lt;/code&gt; plugin to make the contents of my markdown files available in GraphQL, allowing me to inject the generated HTML into my blog posts at build time.&lt;/p&gt;




&lt;p&gt;This is by no means a complete list of reasons for choosing static site generators like Gatsby for building modern websites, but I hope it can at least be helpful for anyone who hasn't yet jumped into the Gatsby ecosystem. It can be intimidating at first, but the time spent learning the system is well worth it for the speed of the final site. The developer experience building and maintaining a Gatsby site is also excellent.&lt;/p&gt;

&lt;p&gt;Do you have other static site generators or other approaches to building websites that you're crazy about? Tweet me &lt;a href="https://twitter.com/will__tweets"&gt;@will__tweets&lt;/a&gt; and let me know, I'd love to hear about it!&lt;/p&gt;

</description>
      <category>gatsby</category>
      <category>react</category>
      <category>javascript</category>
      <category>webdev</category>
    </item>
    <item>
      <title>React JSX Basics</title>
      <dc:creator>Will Harris</dc:creator>
      <pubDate>Tue, 14 Jul 2020 17:21:32 +0000</pubDate>
      <link>https://dev.to/will_devs/react-jsx-basics-2b27</link>
      <guid>https://dev.to/will_devs/react-jsx-basics-2b27</guid>
      <description>&lt;p&gt;&lt;em&gt;Originally posted on &lt;a href="//willharris.dev"&gt;Will's blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;Over the last year I've been on a mission to learn modern JavaScript. Much of the language has changed and improved since my initial exposure to it, and I've found no shortage of things to explore. I've also landed on React as my front-end framework of choice and have been enjoying working with it immensely.&lt;/p&gt;

&lt;p&gt;For some time I've wanted to sit down and think through the different basic building blocks of React, so this will be the first of a series of posts covering React fundamentals as I understand them.&lt;/p&gt;

&lt;p&gt;Today let's talk about JSX.&lt;/p&gt;

&lt;h2&gt;
  
  
  What is JSX?
&lt;/h2&gt;

&lt;p&gt;JSX, or JavaScript XML, was introduced as React's syntax extension to JavaScript. React embraces the idea that rendering logic should be coupled with other UI logic -- things like how events are handled, how data flows through the application, and how to deal with changes to application state over time.&lt;/p&gt;

&lt;p&gt;It's worth noting that JSX is not a requirement for using React: you can do everything without JSX that can be done with JSX. However, many people find JSX to be a useful tool for working with UI elements inside React's .jsx files. It also helps React produce more useful error and warning messages.&lt;/p&gt;

&lt;p&gt;Let's look at a basic example of JSX:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;greeting&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"greeting"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Hello, world!&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;If we run this code in a normal JavaScript file it will immediately throw a &lt;code&gt;SyntaxError&lt;/code&gt; at the &lt;code&gt;&amp;lt;&lt;/code&gt; because it isn't valid JavaScript syntax.&lt;/p&gt;

&lt;p&gt;We're able to mix what looks like HTML with JavaScript here because under the hood it gets 'translated' into valid JavaScript at runtime with a tool called &lt;a href="https://babeljs.io/docs/en/"&gt;Babel&lt;/a&gt;.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;An explanation of Babel is beyond the scope of this post. &lt;a href="https://babeljs.io/docs/en/"&gt;Their documentation&lt;/a&gt; is excellent if you'd like to learn more!&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The output from Babel will look like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;greeting&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;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;h1&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="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;greeting&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="s2"&gt;Hello, world!&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Note that because React does all the heavy lifting of turning our JSX into &lt;code&gt;React.createElement&lt;/code&gt; calls, React must always be in scope in our JSX files.&lt;/p&gt;

&lt;h2&gt;
  
  
  Embed Expressions with JSX
&lt;/h2&gt;

&lt;p&gt;We can use any valid JavaScript &lt;a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Expressions_and_Operators"&gt;expression&lt;/a&gt; (but not &lt;a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements"&gt;statements&lt;/a&gt;) inside curly braces in our JSX.&lt;/p&gt;

&lt;p&gt;I like to think of curly braces in JSX as indicating that we are stepping out of HTML-land and into JavaScript-land.&lt;/p&gt;

&lt;p&gt;As an example, imagine that we have an element of an application that displays a random number between 0 and 100 every time a user visits the website. Using JSX we can do something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight jsx"&gt;&lt;code&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="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;randomNumber&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;floor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;random&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="mi"&gt;100&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;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Your random number is: &lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;randomNumber&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&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;We can wrap JavaScript expressions in curly braces inline in our JSX and they will be translated into whatever value the expressions evaluate to at runtime.&lt;/p&gt;

&lt;h2&gt;
  
  
  Use JSX to Set HTML Attributes
&lt;/h2&gt;

&lt;p&gt;We can also use JSX to set HTML attributes, allowing us to use dynamic values as attributes on HTML elements. Let's look at an example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;img&lt;/span&gt; &lt;span class="na"&gt;src&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;userImage&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt; &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;When we use this element, we can render different images depending on the &lt;code&gt;useImage&lt;/code&gt; value passed into the &lt;code&gt;src&lt;/code&gt; attribute. This allows us to &lt;em&gt;reuse the same element with different values&lt;/em&gt;, providing flexibility and reusability in our code. The useImage value could come from anywhere in our application -- an HTTP request, user input, etc. Our JSX is the same, it is only concerned with rendering the final value.&lt;/p&gt;

&lt;h2&gt;
  
  
  Children in JSX
&lt;/h2&gt;

&lt;p&gt;JSX tags can also contain children, just like HTML elements:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;This is a nested heading!&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;We can nest as many children as needed!&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;ul&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Turtles&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;All&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;The&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Way&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Down!&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;li&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;ul&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;We wrap this JSX in parentheses to avoid issues with &lt;a href="https://stackoverflow.com/questions/2846283/what-are-the-rules-for-javascripts-automatic-semicolon-insertion-asi"&gt;automatic semicolon insertion (ASI)&lt;/a&gt;)&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;We can also use JavaScript anywhere in this hierarchy of children, just like with any other JSX element.&lt;/p&gt;

&lt;p&gt;That wraps up our brief look at what JSX is and how it works. Remember that JSX is just syntactic sugar on top of normal JavaScript.&lt;/p&gt;

</description>
      <category>react</category>
      <category>javascript</category>
      <category>webdev</category>
    </item>
    <item>
      <title>JavaScript: How to Remove Duplicate Values from Arrays</title>
      <dc:creator>Will Harris</dc:creator>
      <pubDate>Fri, 03 Jul 2020 18:15:06 +0000</pubDate>
      <link>https://dev.to/will_devs/javascript-how-to-remove-duplicate-values-from-arrays-lf0</link>
      <guid>https://dev.to/will_devs/javascript-how-to-remove-duplicate-values-from-arrays-lf0</guid>
      <description>&lt;p&gt;&lt;em&gt;Originally posted on &lt;a href="https://www.willharris.dev/garden/remove-array-duplicates"&gt;Will's blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;In a &lt;a href="https://bikesandbytes.net/check-for-array-duplicates"&gt;previous post&lt;/a&gt; we saw how to determine whether a JavaScript array contains duplicate values. Today, I want to show a few different methods I've found for removing duplicate values from an array.&lt;/p&gt;

&lt;h2&gt;
  
  
  Using the &lt;code&gt;Array.prototype.filter()&lt;/code&gt; &amp;amp; &lt;code&gt;Array.prototype.indexOf()&lt;/code&gt; methods
&lt;/h2&gt;



&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;originalArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;

&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;uniqueArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;originalArray&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;filter&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;array&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="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;indexOf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;

&lt;span class="c1"&gt;// uniqueArray === [1, 2, 3, 4]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;The basic strategy here is to iterate through &lt;code&gt;originalArray&lt;/code&gt; and check to see if the index of the item we are currently examining is the same as the index of the item in the &lt;code&gt;originalArray&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Because &lt;code&gt;indexOf&lt;/code&gt; returns the first index that it finds for a given value, if it isn't a duplicate value then the index for that item must be the same!&lt;/p&gt;

&lt;p&gt;Note that this method is not the most efficient: it executes in quadratic time. So if the arrays you're checking are very large in size, you may want to use a different method.&lt;/p&gt;

&lt;p&gt;Another thing worth nothing is that we can use the same method to return only the duplicate values by inverting the comparison:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;duplicateArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;originalArray&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;filter&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;array&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="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;indexOf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;!==&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;h2&gt;
  
  
  Using &lt;code&gt;Array.prototype.reduce()&lt;/code&gt; &amp;amp; &lt;code&gt;Array.prototype.includes()&lt;/code&gt;
&lt;/h2&gt;



&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;originalArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;

&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;uniqueArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;originalArray&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;reduce&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;unique&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;item&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;unique&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;includes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;?&lt;/span&gt; &lt;span class="nx"&gt;unique&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[...&lt;/span&gt;&lt;span class="nx"&gt;unique&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;item&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="c1"&gt;// uniqueArray === [1, 2, 3, 4]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Here the strategy is to keep a running list of the unique items in our reducer function's 'accumulator' (&lt;code&gt;unique&lt;/code&gt;). For each item in &lt;code&gt;originalArray&lt;/code&gt; we check to see if the accumulator includes the item under consideration.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;If it does contain the item, return the accumulator without making any changes, in effect 'skipping over' that item.&lt;/li&gt;
&lt;li&gt;If it does not contain the item, spread the values in the accumulator into a new array, and add the item under consideration.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;code&gt;Array.prototype.includes&lt;/code&gt; returns a boolean value -- &lt;code&gt;true&lt;/code&gt; if the value is found in the array, &lt;code&gt;false&lt;/code&gt; if not. This boolean value drives our conditional, determining what to do with each value.&lt;/p&gt;

&lt;p&gt;I find this approach less intuitive and harder to read, but it works.&lt;/p&gt;

&lt;p&gt;Also note that the empty array that is passed in after the reducer function is the starting value for the accumulator, so the first pass through the &lt;code&gt;reduce&lt;/code&gt;, &lt;code&gt;unique&lt;/code&gt; is an empty array.&lt;/p&gt;

&lt;h2&gt;
  
  
  ⚡ Using the ES6 &lt;code&gt;Set&lt;/code&gt; object ⚡
&lt;/h2&gt;



&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;originalArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;

&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;uniqueArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;array&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;new&lt;/span&gt; &lt;span class="nb"&gt;Set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;

&lt;span class="c1"&gt;// or&lt;/span&gt;

&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;uniqueArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Array&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nb"&gt;Set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;originalArray&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;

&lt;span class="c1"&gt;// uniqueArray = [1, 2, 3, 4]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This approach harnesses the power of the &lt;code&gt;Set&lt;/code&gt; object, introduced in ES6.&lt;/p&gt;

&lt;p&gt;Sets are guaranteed to preserve the order of the inserted items, and to only contain unique values. Therefore it is by definition impossible for a set to contain duplicates!&lt;/p&gt;

&lt;p&gt;Here we call the &lt;code&gt;Set&lt;/code&gt; object's constructor, passing it the array we'd like to construct a &lt;code&gt;Set&lt;/code&gt; from. Then, once we've trimmed out all the duplicates and stored the remaining values in our &lt;code&gt;Set&lt;/code&gt;, we convert back to an array and return the result.&lt;/p&gt;

&lt;p&gt;I've seen some discussion of this approach being a bit less performant if the array under consideration is very large and contains many duplicate values. However, the same discussion found that this approach is very efficient in a scenario where the data has very few duplicates.&lt;/p&gt;

&lt;p&gt;Personally I think the conciseness of this last approach is enough of a benefit to warrant using the &lt;code&gt;Set&lt;/code&gt; object approach, unless there's a compelling performance reason not to.&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>webdev</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Shell: Keyboard Shortcuts Pt. 1</title>
      <dc:creator>Will Harris</dc:creator>
      <pubDate>Mon, 01 Jun 2020 19:05:59 +0000</pubDate>
      <link>https://dev.to/will_devs/shell-keyboard-shortcuts-pt-1-31e</link>
      <guid>https://dev.to/will_devs/shell-keyboard-shortcuts-pt-1-31e</guid>
      <description>&lt;p&gt;&lt;em&gt;Originally published on &lt;a href="https://www.willharris.dev/garden/shell-keyboard-shortcuts-01"&gt;Will's blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;As developers, we spend a great deal of time in our text editors and terminals. Any boost in efficiency with these tools has a direct impact on our productivity. Small gains with these tools add up over time and get us closer to feeling like our computers can respond immediately to our thoughts.&lt;/p&gt;

&lt;p&gt;This series of posts is primarily a way for me to store and reference some of the shell tricks and tips I've come across that I can never remember. I hope that they can be of some use to you as well.&lt;/p&gt;

&lt;p&gt;I should also note: my understanding is that all of these commands will work with both &lt;code&gt;bash&lt;/code&gt; and &lt;code&gt;zsh&lt;/code&gt; default shell configurations, but if I'm mistaken in this please reach out to correct me!&lt;/p&gt;

&lt;h2&gt;
  
  
  Navigating the current line
&lt;/h2&gt;

&lt;p&gt;Moving around the current line in your terminal with the ← and → keys is slow - it's no way to live your life. The following table shows some shortcuts for navigating the current command quickly.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Navigation&lt;/th&gt;
&lt;th&gt;Shortcut&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Go to beginning of line&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + A&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Go to end of line&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + E&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Go to next word&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Alt + F&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Go to previous word&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Alt + B&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Toggle cursor between current position and beginning of line&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + X + X&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;




&lt;h2&gt;
  
  
  Editing and deleting text
&lt;/h2&gt;

&lt;p&gt;These commands help quickly edit and delete items in the current command.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Edits&lt;/th&gt;
&lt;th&gt;Shortcut&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Delete previous word (via cutting)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + W&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Delete next word (via cutting)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Alt + D&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Edit current command in default terminal text editor&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + X - Ctrl + E&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Clear command line&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + U&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;




&lt;h2&gt;
  
  
  Cutting and pasting text
&lt;/h2&gt;

&lt;p&gt;The shell has some built-in commands that can help you quickly cut and paste text without using the mouse.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Action&lt;/th&gt;
&lt;th&gt;Shortcut&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Cut previous word&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + W&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cut next word&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Alt + D&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cut from cursor to end of line&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + K&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cut from cursor to beginning of line&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + U&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Paste the cut contents at current cursor position&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + Y&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;There is a little bit of nuance here.&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;Ctrl + W&lt;/code&gt; and &lt;code&gt;Alt + D&lt;/code&gt; commands build up the cut buffer sequentially from within the current command. This can be useful if you want to cut the first/last three words in a command, for example, but not the entire line. This behavior, as far as I can tell, does not allow you to bounce around different parts of the command, but only from any given word forward/backward. As soon as you start navigating around other parts of the command and making cuts, it seems the cut buffer is overwritten.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;(If my understanding of this is flawed, please let me know.)&lt;/strong&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Controlling the terminal
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Action&lt;/th&gt;
&lt;th&gt;Shortcut&lt;/th&gt;
&lt;th&gt;Command&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Clear terminal screen&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + L&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;clear&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Close terminal screen / tab&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + D&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;exit&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Stop current job&lt;/td&gt;
&lt;td&gt;&lt;code&gt;Ctrl + K&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Restart stopped job and send to foreground&lt;/td&gt;
&lt;td&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;fg&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Restart stopped job and send to background&lt;/td&gt;
&lt;td&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;bg&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;List running and stopped jobs&lt;/td&gt;
&lt;td&gt;&lt;/td&gt;
&lt;td&gt;`jobs&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;One nice shortcut for starting a program and immediately sending it to the background is the bitwise &lt;code&gt;&amp;amp;&lt;/code&gt; operator. For example, the following command would start firefox and send the job to the background of the current terminal instance.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;firefox &amp;amp;&lt;/code&gt;&lt;/p&gt;




&lt;p&gt;This list is just a taste of the things we can do with our terminals. Mastering these shortcuts will greatly increase how quickly and efficiently you can navigate and control your command-line environment.&lt;/p&gt;

&lt;p&gt;If you have any other keyboard shortcuts that you feel should be included in this list, please reach out and let me know.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>JavaScript: How to Check if an Array has Duplicate Values</title>
      <dc:creator>Will Harris</dc:creator>
      <pubDate>Tue, 26 May 2020 03:27:31 +0000</pubDate>
      <link>https://dev.to/will_devs/javascript-how-to-check-if-an-array-has-duplicate-values-cha</link>
      <guid>https://dev.to/will_devs/javascript-how-to-check-if-an-array-has-duplicate-values-cha</guid>
      <description>&lt;p&gt;&lt;em&gt;Originally posted on &lt;a href="https://www.willharris.dev/garden/check-for-array-duplicates"&gt;Will's blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;When dealing with arrays of values in JavaScript we sometimes want to determine if the array contains any duplicate values. Unfortunately, JavaScript arrays do not expose any built-in methods that can do this for us -- we have to write the implementation ourselves.&lt;/p&gt;

&lt;p&gt;One approach to this problem might look like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="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;checkForDuplicates&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;valuesAlreadySeen&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;

  &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&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;let&lt;/span&gt; &lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;i&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;valuesAlreadySeen&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;indexOf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;!==&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="nx"&gt;valuesAlreadySeen&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;value&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="kc"&gt;false&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This works, but in the worst-case scenario where the only duplicate value occurs at the end of the array, this is not a very performant approach. We would have to iterate through the entire array (which could be huge!) only to realize at the last element that there is actually a non-unique value in the array.&lt;/p&gt;

&lt;p&gt;Another approach that I recently learned harnesses the power of ES6 Sets.&lt;/p&gt;

&lt;p&gt;In case you aren't familiar with Sets in JavaScript (I wasn't until recently!), &lt;a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Set"&gt;here is the MDN definition&lt;/a&gt;:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;code&gt;Set&lt;/code&gt; objects are collections of values. You can iterate through the elements of a set in insertion order. A value in the &lt;code&gt;Set&lt;/code&gt; may only occur once; it is unique in the &lt;code&gt;Set&lt;/code&gt;'s collection.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Read that last line one more time, as that is our secret sauce here. 'A value in the &lt;code&gt;Set&lt;/code&gt; may only occur once; it is unique in the &lt;code&gt;Set&lt;/code&gt;'s collection.'&lt;/p&gt;

&lt;p&gt;This fact means that we can convert our original array into a &lt;code&gt;Set&lt;/code&gt; and then be confident that it only contains unique values. Once we've extracted all of the unique values from the array and stored them in our &lt;code&gt;Set&lt;/code&gt;, we can compare the lengths of the array and the Set. If the lengths are not the same, it must follow that the array contained duplicate values!&lt;/p&gt;

&lt;p&gt;Here's what that approach looks like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="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;checkForDuplicates&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;array&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="k"&gt;new&lt;/span&gt; &lt;span class="nb"&gt;Set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;size&lt;/span&gt; &lt;span class="o"&gt;!==&lt;/span&gt; &lt;span class="nx"&gt;array&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;If the length of the &lt;code&gt;Set&lt;/code&gt; and the array are not the same this function will return &lt;code&gt;true&lt;/code&gt;, indicating that the array did contain duplicates. Otherwise, if the array and the &lt;code&gt;Set&lt;/code&gt; are the same length the function will return &lt;code&gt;false&lt;/code&gt; and we can be certain that the original array contained no duplicate values!&lt;/p&gt;

&lt;p&gt;I really like this second approach for how concise and expressive it is, but &lt;a href="https://caniuse.com/#feat=mdn-javascript_builtins_set_set_null_allowed"&gt;you might run into browser support issues if you need to target older browsers&lt;/a&gt; so take that into consideration!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>JavaScript: Double Not Operator?</title>
      <dc:creator>Will Harris</dc:creator>
      <pubDate>Sun, 24 May 2020 02:37:59 +0000</pubDate>
      <link>https://dev.to/will_devs/javascript-double-not-operator-3ocn</link>
      <guid>https://dev.to/will_devs/javascript-double-not-operator-3ocn</guid>
      <description>&lt;p&gt;&lt;em&gt;Article originally published on &lt;a href="https://www.willharris.dev/garden/javascript-double-not-operator"&gt;Will’s personal blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;




&lt;p&gt;Here's a little JavaScript tidbit I learned about recently.&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;!&lt;/code&gt; operator is a familiar face in the JavaScript landscape, showing up when we need to negate a value.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;thing&lt;/span&gt;
&lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;// true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Here we take a Boolean value (&lt;code&gt;true&lt;/code&gt;) and invert it to the opposite value (&lt;code&gt;false&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;This also works with non-Boolean values as well, since all values in JavaScript are either &lt;a href="https://developer.mozilla.org/en-US/docs/Glossary/Truthy"&gt;truthy&lt;/a&gt; or &lt;a href="https://developer.mozilla.org/en-US/docs/Glossary/Falsy"&gt;falsy&lt;/a&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;This string is truthy!&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
&lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;thing&lt;/span&gt;
&lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;// true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Here we can see how the &lt;code&gt;!&lt;/code&gt; operator casts the value from a string value (truthy) to it's opposite Boolean value &lt;code&gt;false&lt;/code&gt;. The same conversion happens when we use the &lt;code&gt;!&lt;/code&gt; operator on any value in JavaScript. If the value is already truthy it is cast to &lt;code&gt;false&lt;/code&gt;, and vice versa.&lt;/p&gt;

&lt;p&gt;It follows then that &lt;code&gt;!!&lt;/code&gt; just performs this inversion twice.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;This string is truthy!&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
&lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt;&lt;span class="nx"&gt;thing&lt;/span&gt;
&lt;span class="nx"&gt;thing&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;// true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This is really just a shorter way to cast a value to it's Boolean counterpart. If a value is already falsy, using &lt;code&gt;!!&lt;/code&gt; will result in the value being cast to &lt;code&gt;false&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;We could just as well do this for the same result:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;let thing = Boolean("This string is truthy!")
thing === true // true
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;What's the difference? As far as I can tell, there is none!&lt;/p&gt;

&lt;p&gt;Although &lt;code&gt;!!&lt;/code&gt; is more succinct, the argument could be made that it is more confusing syntactically than &lt;code&gt;Boolean(value)&lt;/code&gt;.&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>webdev</category>
      <category>todayilearned</category>
    </item>
  </channel>
</rss>
