<?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>Forem: Nikkhiel Seath</title>
    <description>The latest articles on Forem by Nikkhiel Seath (@snikhill).</description>
    <link>https://forem.com/snikhill</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%2F299093%2F3c9c11b7-995f-4007-a96e-e333519708bb.jpg</url>
      <title>Forem: Nikkhiel Seath</title>
      <link>https://forem.com/snikhill</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/snikhill"/>
    <language>en</language>
    <item>
      <title>Serial and Parallel JS Promises</title>
      <dc:creator>Nikkhiel Seath</dc:creator>
      <pubDate>Tue, 28 Jun 2022 00:00:00 +0000</pubDate>
      <link>https://forem.com/snikhill/serial-and-parallel-js-promises-440n</link>
      <guid>https://forem.com/snikhill/serial-and-parallel-js-promises-440n</guid>
      <description>&lt;p&gt;A week ago, I was looking at a bug. Some operations were being performed that resulted in the change of state of the IndexedDB storage.&lt;/p&gt;

&lt;p&gt;(I can't share all the details so please, bear with me)&lt;/p&gt;

&lt;p&gt;For one of the operations, a piece of data was being calculated again and this should not have been happening as this data was already calculated as a part of another operation and any &lt;em&gt;following&lt;/em&gt; operations should have referred to this pre-calculated data.&lt;/p&gt;

&lt;p&gt;The way these operations were being performed was not exactly apparent and clear as a list of these operations was basically being passed on to another method which was using some deep-nested logic to execute them.&lt;/p&gt;

&lt;p&gt;Turns out that &lt;code&gt;Promise.all&lt;/code&gt; was being used to resolve the results from all the operations in the list.&lt;/p&gt;

&lt;h2&gt;
  
  
  Difference between Serial and Parallel
&lt;/h2&gt;

&lt;p&gt;In my mind, I had formed a general model of the process: Operation 1 is performed and then Operation 2 is performed and so on.&lt;br&gt;
This model where operations happen in a sequence is called &lt;code&gt;Serial&lt;/code&gt; and if I am being honest, this is how I usually think that things are done.&lt;/p&gt;

&lt;p&gt;Turns out that there is another model: Operation 1 is being performed and simultaneously, Operation 2 is being performed. There is no exact order/relation between the end of Operation 1 and start of Operation 2.&lt;br&gt;
This model is called &lt;code&gt;Parallel&lt;/code&gt; and this was one of the reasons behind the bug I was looking into.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does Promise.all do?
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;bakeCake&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;():&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;CakeDetails&lt;/span&gt;&lt;span class="o"&gt;&amp;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="c1"&gt;// something};&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;eatCake&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;():&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;EatenCakeDetails&lt;/span&gt;&lt;span class="o"&gt;&amp;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="c1"&gt;// something};&lt;/span&gt;


&lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;all&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="nx"&gt;bakeCake&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="nx"&gt;eatCake&lt;/span&gt;&lt;span class="p"&gt;()]).&lt;/span&gt;&lt;span class="nx"&gt;then&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;result&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;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;warn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Result&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;result&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;In life, you first bake the cake and then eat it.&lt;/p&gt;

&lt;p&gt;But, using the above code example you can bake and eat the cake simultaneously (assuming that the eatCake fallbacks to baking a cake in case one doesn't already exists).&lt;/p&gt;

&lt;h3&gt;
  
  
  What is it good for?
&lt;/h3&gt;

&lt;p&gt;It is basically a way to perform &lt;strong&gt;concurrent&lt;/strong&gt; operations in JS.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;It should only be used to perform independent asynchronous operations.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Based on the above statement, the &lt;code&gt;cake&lt;/code&gt; example is an incorrect usage of Promise.all and a similar mistake was the reason behind the bug I was looking at.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is it a way to perform operations parallelly?
&lt;/h3&gt;

&lt;p&gt;No. It is not.&lt;br&gt;
It may look like that the operations are being performed parallelly but, they are not. Instead, the right term for this behavior is &lt;em&gt;Concurrent&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;The &lt;em&gt;thing&lt;/em&gt; responsible for executing a piece of JS is single-threaded and therefore, only a single operation can occupy it at a time.&lt;/p&gt;

&lt;p&gt;And in the case of &lt;code&gt;Promise.all&lt;/code&gt;, this &lt;em&gt;thing&lt;/em&gt; is actually bouncing between multiple operations by starting an operation, suspending it and then, starting of another one, suspending it, resuming the previous one and so on.&lt;br&gt;
Therefore, we can't call it &lt;code&gt;parallel&lt;/code&gt; because, at a give time only single operation is being &lt;em&gt;worked on&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;(NB: I am using simplified names to prevent confusion caused by terminology)&lt;/p&gt;

&lt;h3&gt;
  
  
  Does it have a performance impact?
&lt;/h3&gt;

&lt;p&gt;Is Promise.all faster then waiting for every promise to be resolved before proceeding on to the next one?&lt;br&gt;
I am not so sure. I am yet to find a definitive answer and I shall share my thoughts on the same later.&lt;/p&gt;

&lt;h2&gt;
  
  
  References
&lt;/h2&gt;

&lt;p&gt;This post is based on what I have learnt after taking care of that bug and reading other articles on the internet.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://codeburst.io/is-javascript-single-threaded-youre-kidding-me-80b11d74f4e5"&gt;Javascript is single-threaded? You’re kidding
me&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://bytearcher.com/articles/parallel-vs-concurrent/"&gt;Parallel vs
Concurrent&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.logrocket.com/javascript-promises-race-all-allsettled-then/"&gt;Promise: race, all,
allSettled&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>javascript</category>
      <category>programming</category>
      <category>typescript</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Symbols in package.json</title>
      <dc:creator>Nikkhiel Seath</dc:creator>
      <pubDate>Mon, 06 Jun 2022 20:52:50 +0000</pubDate>
      <link>https://forem.com/snikhill/symbols-in-packagejson-47io</link>
      <guid>https://forem.com/snikhill/symbols-in-packagejson-47io</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;Recently, I came across a dependency error. Basically, a package being used by a&lt;br&gt;
project didn't have the correct version of a dependency listed as a peer.&lt;br&gt;
&lt;/p&gt;
&lt;/blockquote&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;package&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;had&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;issue&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"peerDependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"package-a"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"^6.5.7"&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;

&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;project&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;used&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;said&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;package&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"dependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"package-a"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~6.6.7"&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In this post I shall try to explain what symbols like &lt;code&gt;~ ^&lt;/code&gt; and those numbers&lt;br&gt;
mean?&lt;/p&gt;

&lt;h2&gt;
  
  
  Talking about the numbers first
&lt;/h2&gt;

&lt;p&gt;I intially found it a bit weird that there are two decimals in this version&lt;br&gt;
string. But, now, I know better.&lt;br&gt;
Each of those digits represents a change in the version. Depending upon the&lt;br&gt;
position of the digit that was incremented, the change can be divided into:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Major&lt;/strong&gt; - A Breaking Change or a New feature&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Minor&lt;/strong&gt; - A change that maintains backwards compatiblity&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Patch&lt;/strong&gt; - A minor bug/error fix&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Turns out that there is a whole set of rules defining what these digits are and&lt;br&gt;
under what circumstances should and which digit be incremented. This rule set is&lt;br&gt;
referred to as &lt;a href="https://semver.org/"&gt;Semantic Versioning&lt;/a&gt;.&lt;br&gt;
So, for a package with version string &lt;code&gt;8.5.4&lt;/code&gt;:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;8 =&amp;gt; Major Version&lt;/li&gt;
&lt;li&gt;5 =&amp;gt; Minor Version. Like: 5th revision of version 8&lt;/li&gt;
&lt;li&gt;4 =&amp;gt; Patch Version. Like: 4th revision of the 5th revision (of version 8)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;And now if a typo was fixed then, the digit representing "patch" would be&lt;br&gt;
incremented making the new version string &lt;code&gt;8.5.(4 + 1)&lt;/code&gt; = &lt;code&gt;8.5.5&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;In a proper production level released package, the minimum "major" is 1 and&lt;br&gt;
minor, patch range from 0 to 9. (The first release is usually &lt;code&gt;1.0.0&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;On the other hand, for a package that is released for development purposes,&lt;br&gt;
usually has the "major" as 0 (and possibly no limit on range of major and&lt;br&gt;
minor).&lt;/p&gt;

&lt;h2&gt;
  
  
  Talking about the symbols
&lt;/h2&gt;

&lt;p&gt;Before I jump on symbols, I shall like to give a brief on what package.json&lt;br&gt;
stores.&lt;/p&gt;

&lt;h3&gt;
  
  
  What exactly does package.json store?
&lt;/h3&gt;

&lt;p&gt;A &lt;code&gt;package.json&lt;/code&gt; file basically lists all the "pieces of code" (aka dependencies)&lt;br&gt;
that the current project (which itself is a piece of code) may be dependent&lt;br&gt;
upon.&lt;br&gt;
Along with this, it stores what version of these "pieces of code" should&lt;br&gt;
actually be used.&lt;/p&gt;

&lt;p&gt;This version requirement can be:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;strict: &lt;em&gt;Only v1 of &lt;code&gt;package-a&lt;/code&gt;&lt;/em&gt;
&lt;/li&gt;
&lt;li&gt;a little less strict: &lt;em&gt;Either v2.3 or v3.1 of &lt;code&gt;package-a&lt;/code&gt;&lt;/em&gt;
&lt;/li&gt;
&lt;li&gt;flexible: &lt;em&gt;Anything after v3 of &lt;code&gt;package-a&lt;/code&gt; will do fine&lt;/em&gt;.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  How do symbols help?
&lt;/h3&gt;

&lt;p&gt;Symbols like: &lt;code&gt;~, ^, &amp;lt;, ||&lt;/code&gt; basically represents the above requirement in a&lt;br&gt;
compact manner.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;&amp;lt;&lt;/code&gt; &lt;em&gt;aka&lt;/em&gt; less-than&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Corresponds to &lt;strong&gt;major, minor, patch&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;&amp;lt;4.3.0&lt;/code&gt; means any major or minor or patch update less than &lt;code&gt;4.3.0&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;4.2.9&lt;/code&gt; or &lt;code&gt;3.1.7&lt;/code&gt; would work&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;
&lt;li&gt;

&lt;p&gt;&lt;code&gt;&amp;gt;&lt;/code&gt; &lt;em&gt;aka&lt;/em&gt; greater-than&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Corresponds to &lt;strong&gt;major, minor, patch&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;&amp;gt;4.3.0&lt;/code&gt; means any major or minor or patch update greater than &lt;code&gt;4.3.0&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;5.1.6&lt;/code&gt; would work but &lt;code&gt;4.2.9&lt;/code&gt; won't&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  This is where it gets slightly tricky
&lt;/h4&gt;

&lt;p&gt;The following symbols can allow updates to &lt;code&gt;major&lt;/code&gt;, &lt;code&gt;minor&lt;/code&gt; or &lt;code&gt;patch&lt;/code&gt; depending upon which of them is defined.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;~4.3.5&lt;/code&gt; means a totally different thing than &lt;code&gt;~4&lt;/code&gt;&lt;br&gt;
and &lt;code&gt;^7.8.6&lt;/code&gt; is different from &lt;code&gt;^7.0.6&lt;/code&gt;.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;~&lt;/code&gt; &lt;em&gt;aka&lt;/em&gt; tilde&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Allows patch update if a minor version is defined or a minor
update if no patch version is defined&lt;/li&gt;
&lt;li&gt;For &lt;code&gt;~4.3.5&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Only patch updates would be allowed&lt;/li&gt;
&lt;li&gt;Greater than or equal to &lt;code&gt;4.3.5&lt;/code&gt; but, less than &lt;code&gt;4.4.0&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;~4.3.6&lt;/code&gt; would work but, &lt;code&gt;~4.4.1&lt;/code&gt; won't work&lt;/li&gt;
&lt;li&gt;For &lt;code&gt;~4&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Only minor and patch updates would be allowed&lt;/li&gt;
&lt;li&gt;Greater than or equal to &lt;code&gt;4.0.0&lt;/code&gt; but, less than &lt;code&gt;5.0.0&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;4.4.2&lt;/code&gt; would work but, &lt;code&gt;5.0.0&lt;/code&gt; won't work&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;
&lt;li&gt;

&lt;p&gt;&lt;code&gt;^&lt;/code&gt; &lt;em&gt;aka&lt;/em&gt; carret&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Allows updates less than the left most non-zero digit&lt;/li&gt;
&lt;li&gt;If major is zero and minor is a non-zero number then, only patch updates would be allowed&lt;/li&gt;
&lt;li&gt;If major is non zero and minor is zero then both minor and patch updates would be allowed&lt;/li&gt;
&lt;li&gt;For &lt;code&gt;^0.3.5&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Greater than or equal to &lt;code&gt;0.3.5&lt;/code&gt; but, less than &lt;code&gt;0.4.0&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;0.3.6&lt;/code&gt; or &lt;code&gt;0.3.9&lt;/code&gt; would work but, &lt;code&gt;0.4.x&lt;/code&gt; won't work&lt;/li&gt;
&lt;li&gt;For &lt;code&gt;^4.0.5&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Greater than or equal to &lt;code&gt;4.0.5&lt;/code&gt; but, less than &lt;code&gt;5.0.0&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;4.1.5&lt;/code&gt; would work but, &lt;code&gt;5.x.y&lt;/code&gt; won't work&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Wrapping Up
&lt;/h2&gt;

&lt;p&gt;This post obviously doesn't contain explanation for all the combantions possible&lt;br&gt;
with all the relevant symbols. Instead, it is just an attempt to better explain&lt;br&gt;
the concepts that confused me.&lt;/p&gt;

&lt;p&gt;In a later post, I shall be sharing some actual examples using&lt;br&gt;
&lt;a href="https://github.com/npm/node-semver"&gt;&lt;em&gt;node-semver&lt;/em&gt;&lt;/a&gt;, which is &lt;strong&gt;the tool that npm&lt;br&gt;
uses&lt;/strong&gt; to parse these Semantic Versioning Complaint dependencies version.&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>packages</category>
      <category>programming</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Managing vim plugins using pathogen</title>
      <dc:creator>Nikkhiel Seath</dc:creator>
      <pubDate>Sun, 10 Apr 2022 11:32:06 +0000</pubDate>
      <link>https://forem.com/snikhill/managing-vim-plugins-using-pathogen-55g9</link>
      <guid>https://forem.com/snikhill/managing-vim-plugins-using-pathogen-55g9</guid>
      <description>&lt;p&gt;I have been using &lt;a href="https://github.com/tpope/vim-pathogen#pathogenvim"&gt;pathogen&lt;/a&gt; as a plugin manager for my &lt;code&gt;neovim&lt;/code&gt;.&lt;br&gt;
It is a very simple tool that requires no special commands to install a plugin.&lt;br&gt;
Just clone the plugin repository to a specified folder (&lt;code&gt;bundle&lt;/code&gt; by default) and pathogen will add the plugin to the runtime-path(*) on next restart.&lt;/p&gt;

&lt;p&gt;It works fine but, the thing is, what if you end up migrating your system or for some reason, you had to recover your vim config. There is no way to keep a record of the plugins you had installed previously.&lt;br&gt;
&lt;em&gt;Zum Beispiel&lt;/em&gt;:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/junegunn/vim-plug"&gt;vim-plug&lt;/a&gt; stores the plugins installed in the &lt;code&gt;vimrc&lt;/code&gt; between &lt;code&gt;call plug#begin()&lt;/code&gt; and &lt;code&gt;call plug#end()&lt;/code&gt;.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I wanted something quick and similar to &lt;code&gt;vim-plug&lt;/code&gt;'s solution.&lt;br&gt;
So, I wrote a mini bash script.&lt;/p&gt;

&lt;p&gt;It is just a combination of a &lt;a href="https://github.com/SNikhill/dotfiles/blob/master/nvim/plugins.sh"&gt;PLUGINS[]&lt;/a&gt; meant to hold the url(s) for all the plugins used and a &lt;a href="https://github.com/SNikhill/dotfiles/blob/master/nvim/plug_install.sh"&gt;for-loop&lt;/a&gt; that clones them to the &lt;code&gt;bundle&lt;/code&gt; directory.&lt;/p&gt;

&lt;h2&gt;
  
  
  Here is the code
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/SNikhill/dotfiles/blob/master/nvim/plugins.sh"&gt;plugins.sh&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;#!/bin/bash&lt;/span&gt;
&lt;span class="c"&gt;# I STORE THE plugins LIST IN A SEPARATE shell file&lt;/span&gt;
&lt;span class="nb"&gt;export &lt;/span&gt;&lt;span class="nv"&gt;plugins&lt;/span&gt;&lt;span class="o"&gt;=(&lt;/span&gt;
&lt;span class="s2"&gt;"https://github.com/flazz/vim-colorschemes.git colorschemes"&lt;/span&gt;
&lt;span class="c"&gt;# ...OtherPlugins&lt;/span&gt;
&lt;span class="o"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://github.com/SNikhill/dotfiles/blob/master/nvim/plug_install.sh"&gt;plug_install.sh&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;#!/bin/bash&lt;/span&gt;

&lt;span class="c"&gt;# THE FILE THAT CONTAINS THE plugins LIST&lt;/span&gt;
&lt;span class="nb"&gt;source &lt;/span&gt;plugins.sh

&lt;span class="nb"&gt;cd&lt;/span&gt; ./bundle
&lt;span class="k"&gt;for &lt;/span&gt;plugin &lt;span class="k"&gt;in&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="k"&gt;${&lt;/span&gt;&lt;span class="nv"&gt;plugins&lt;/span&gt;&lt;span class="p"&gt;[@]&lt;/span&gt;&lt;span class="k"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="k"&gt;do
    &lt;/span&gt;git clone &lt;span class="nt"&gt;-q&lt;/span&gt; &lt;span class="nv"&gt;$plugin&lt;/span&gt;
&lt;span class="k"&gt;done&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Sure, there may be some more sophisticated tools for the same out-there but, till now, this script works for me.&lt;/p&gt;

&lt;h2&gt;
  
  
  Caveats
&lt;/h2&gt;

&lt;p&gt;Yes, there are some caveats like:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;There is no check if a plugin already exists and this may be a problem for people who install new plugins frequently.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;(NB: I may update the script to address these caveats)&lt;/p&gt;

&lt;h2&gt;
  
  
  Custom Cloned Directory Name?
&lt;/h2&gt;

&lt;p&gt;Yes, you can still specify a custom-directory name for the plugin so that it is registered under the runtime-path appropriately. And all you need to do is add the &lt;code&gt;directory name&lt;/code&gt; after the git url.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;"https://SOME_GIT_URL.git CUSTOM_DIRECTORY_NAME"&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--bEN3-nUA--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/l33vlzcd4lzru7p460f1.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--bEN3-nUA--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/l33vlzcd4lzru7p460f1.png" alt="custome_directory-name" width="704" height="107"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;For example in the above image, I have specified &lt;code&gt;colorschemes&lt;/code&gt; as the custom-directory-name and hence, git will clone the &lt;code&gt;vim-colorschemes&lt;/code&gt; plugin to &lt;code&gt;colorschemes&lt;/code&gt; directory and not &lt;code&gt;vim-colorschemes&lt;/code&gt; directory.&lt;/p&gt;

&lt;h2&gt;
  
  
  Using it
&lt;/h2&gt;

&lt;p&gt;(I have presumed that you are using the same file/variable names as my dotfiles)&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Add the new plugin's git repository url to &lt;code&gt;plugins&lt;/code&gt; list specified in &lt;code&gt;plugins.sh&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Run the &lt;code&gt;plug_install.sh&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Start your &lt;code&gt;vim&lt;/code&gt; instance and run &lt;code&gt;:CheckHealth&lt;/code&gt; to see if the installed plugin is setup correctly&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;You can see this setup in action in my &lt;a href="https://github.com/SNikhill/dotfiles/tree/master/nvim"&gt;dotfiles repository.&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;NB: Let me know if you have any questions. :)&lt;/em&gt;&lt;/p&gt;

</description>
      <category>vim</category>
      <category>bash</category>
      <category>linux</category>
    </item>
    <item>
      <title>optimus-manager on arch linux</title>
      <dc:creator>Nikkhiel Seath</dc:creator>
      <pubDate>Mon, 04 Apr 2022 16:45:42 +0000</pubDate>
      <link>https://forem.com/snikhill/optimus-manager-on-arch-linux-1589</link>
      <guid>https://forem.com/snikhill/optimus-manager-on-arch-linux-1589</guid>
      <description>&lt;p&gt;In this post I am sharing how to use &lt;a href="https://github.com/Askannz/optimus-manager#optimus-manager" rel="noopener noreferrer"&gt;optimus-manager&lt;/a&gt; to shift between Integrated and NVIDIA GPU on Arch Linux with i3 as the tiling windows manager and no display manager.&lt;br&gt;
(That is you start your Xserver using the &lt;code&gt;startx&lt;/code&gt; command).&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%2Fjdls1nxxslxhr3q1yy63.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%2Fjdls1nxxslxhr3q1yy63.png" alt="startx in my .bash_profile"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://github.com/Askannz/optimus-manager/wiki/FAQ,-common-issues,-troubleshooting#i-do-not-use-a-display-manager-i-use-startx-or-xinit" rel="noopener noreferrer"&gt;official documentation&lt;/a&gt; just mentions that &lt;code&gt;prime-offload&lt;/code&gt; and &lt;code&gt;prime-switch&lt;/code&gt; need to be run at start and end of the Xserver (respectively) but, it fails to mention to how to do this setup.&lt;/p&gt;

&lt;p&gt;Without wasting any further time, lets get started.&lt;/p&gt;
&lt;h2&gt;
  
  
  Steps
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Open up your &lt;code&gt;.xinitrc&lt;/code&gt; located under &lt;code&gt;$HOME&lt;/code&gt; or &lt;code&gt;~&lt;/code&gt;. If it doesn't exist &lt;a href="https://wiki.archlinux.org/title/Xinit#Configuration" rel="noopener noreferrer"&gt;then, create one&lt;/a&gt;.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Look at the following code-block:&lt;br&gt;
&lt;/p&gt;

&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# MENTION HERE COMMAND THAT IS RUN AT THE START OF XServer&lt;/span&gt;
&lt;span class="c"&gt;# and before starting up `i3` (#a)&lt;/span&gt;

nitrogen &lt;span class="nt"&gt;--restore&lt;/span&gt; &amp;amp;
picom &amp;amp;
i3

&lt;span class="c"&gt;# MENTION HERE COMMAND THAT IS RUN AT THE END OF XServer&lt;/span&gt;
&lt;span class="c"&gt;# and after exiting `i3` (#b)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;




&lt;/li&gt;

&lt;li&gt;

&lt;p&gt;Place the command to run &lt;code&gt;prime-offload&lt;/code&gt; at #a:&lt;br&gt;
&lt;/p&gt;

&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;[[&lt;/span&gt; &lt;span class="nt"&gt;-f&lt;/span&gt; /usr/bin/prime-offload &lt;span class="o"&gt;]]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="k"&gt;then&lt;/span&gt;
    /usr/bin/prime-offload
&lt;span class="k"&gt;fi

&lt;/span&gt;nitrogen &lt;span class="nt"&gt;--restore&lt;/span&gt; &amp;amp;
picom &amp;amp;
i3
&lt;/code&gt;&lt;/pre&gt;




&lt;/li&gt;

&lt;li&gt;

&lt;p&gt;Place the command to run &lt;code&gt;prime-switch&lt;/code&gt; at #b:&lt;br&gt;
&lt;/p&gt;

&lt;pre class="highlight shell"&gt;&lt;code&gt;nitrogen &lt;span class="nt"&gt;--restore&lt;/span&gt; &amp;amp;
picom &amp;amp;
i3

&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;[[&lt;/span&gt; &lt;span class="nt"&gt;-f&lt;/span&gt; /usr/bin/prime-switch &lt;span class="o"&gt;]]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="k"&gt;then
    &lt;/span&gt;&lt;span class="nb"&gt;sudo&lt;/span&gt; /usr/bin/prime-switch
&lt;span class="k"&gt;fi&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;




&lt;/li&gt;

&lt;/ol&gt;

&lt;h2&gt;
  
  
  Verify
&lt;/h2&gt;

&lt;p&gt;Your final &lt;code&gt;.xinitrc&lt;/code&gt; should be like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;[[&lt;/span&gt; &lt;span class="nt"&gt;-f&lt;/span&gt; /usr/bin/prime-offload &lt;span class="o"&gt;]]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="k"&gt;then&lt;/span&gt;
    /usr/bin/prime-offload
&lt;span class="k"&gt;fi

&lt;/span&gt;nitrogen &lt;span class="nt"&gt;--restore&lt;/span&gt; &amp;amp;
picom &amp;amp;
i3

&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;[[&lt;/span&gt; &lt;span class="nt"&gt;-f&lt;/span&gt; /usr/bin/prime-switch &lt;span class="o"&gt;]]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="k"&gt;then
    &lt;/span&gt;&lt;span class="nb"&gt;sudo&lt;/span&gt; /usr/bin/prime-switch
&lt;span class="k"&gt;fi&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Basically, we are checking if &lt;code&gt;prime-offload&lt;/code&gt; exists then, run it at the start of XServer. Technically, not exactly at start but, before we run our compositor and &lt;code&gt;i3&lt;/code&gt; instance.&lt;br&gt;
And then, we are checking if &lt;code&gt;prime-switch&lt;/code&gt; exists then, run it after the &lt;code&gt;i3&lt;/code&gt; instance has ended.&lt;/p&gt;

&lt;p&gt;You can read more about &lt;code&gt;.xinitrc&lt;/code&gt; &lt;a href="https://wiki.archlinux.org/title/Xinit#Configuration" rel="noopener noreferrer"&gt;here&lt;/a&gt;&lt;/p&gt;

</description>
      <category>linux</category>
      <category>archlinux</category>
      <category>nvidia</category>
      <category>bash</category>
    </item>
    <item>
      <title>Setting up project-level gitconfig</title>
      <dc:creator>Nikkhiel Seath</dc:creator>
      <pubDate>Sun, 03 Apr 2022 08:57:09 +0000</pubDate>
      <link>https://forem.com/snikhill/project-level-git-config-5cam</link>
      <guid>https://forem.com/snikhill/project-level-git-config-5cam</guid>
      <description>&lt;p&gt;Last week, I completely shifted my system to Arch Linux and during this process, I lost some config(s), settings, etc.&lt;/p&gt;

&lt;p&gt;git config was one of them. I used to have a separate config like username, email, ssh key to use based on which project I was working on.&lt;br&gt;
For example, my work projects require a different set of credentials (username, email, ssh-key) than the credentials I use on my personal projects.&lt;/p&gt;

&lt;p&gt;I have done this before too but, after a while, I just tend to forget how to do it. This time, I am writing it in a post so that I can refer to it when required.&lt;/p&gt;
&lt;h2&gt;
  
  
  Steps
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Go to the directory where you store the projects and create a &lt;code&gt;.project.gitconfig&lt;/code&gt; with the desired credentials:
&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;[user]
    name = work-username
    email = username@work-domain.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;ol&gt;
&lt;li&gt;Edit the user level &lt;code&gt;.gitconfig&lt;/code&gt; present under &lt;code&gt;$HOME/.gitconfig&lt;/code&gt; to include the following condition:
&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;[includeIf "gitdir:ABSOLUTE_PROJECT_DIRECTORY_PATH"]
    path = "ABSOLUTE_PROJECT_DIRECTORY_PATH/.project.gitconfig"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Basically, we are telling &lt;code&gt;git&lt;/code&gt;:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;"If you find a &lt;code&gt;.git&lt;/code&gt; directory nested under this path then, use these set of credentials."&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2&gt;
  
  
  Verify
&lt;/h2&gt;

&lt;p&gt;Now, go to a project inside the work/project-root directory and verify that the correct credentials is being used:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--list&lt;/span&gt; | &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="nt"&gt;-P&lt;/span&gt; &lt;span class="s2"&gt;"user|email"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Note (or Gotcha)
&lt;/h2&gt;

&lt;p&gt;Keep in mind that this config will only be used by &lt;code&gt;git&lt;/code&gt; if it finds &lt;code&gt;.git&lt;/code&gt; directory at that path or a parent &lt;code&gt;.git&lt;/code&gt; directory.&lt;br&gt;
For example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;work/
|- .work.gitconfig
|- project-a/
   |- .git/
|- project-b/
   |- .git/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, my &lt;code&gt;.work.gitconfig&lt;/code&gt; will be used when I am inside &lt;code&gt;project-a&lt;/code&gt; or &lt;code&gt;project-b&lt;/code&gt; but, not inside &lt;code&gt;work&lt;/code&gt;.&lt;/p&gt;

</description>
      <category>git</category>
      <category>posts</category>
      <category>bash</category>
      <category>config</category>
    </item>
    <item>
      <title>One doesn't simply exit VIM</title>
      <dc:creator>Nikkhiel Seath</dc:creator>
      <pubDate>Tue, 01 Jun 2021 15:27:19 +0000</pubDate>
      <link>https://forem.com/snikhill/one-doesn-t-simply-exit-vim-jmo</link>
      <guid>https://forem.com/snikhill/one-doesn-t-simply-exit-vim-jmo</guid>
      <description>&lt;p&gt;Around four years ago, I introduced myself to VIM. I had joined a Discord Community composed of Sophisticated Developers, Linux Users. And among these were VIM users. They had a certain vibe to them that made me desire their company. That is how my journey to a better path began.&lt;/p&gt;

&lt;p&gt;No, this path was not better because it involved VIM. It was better as it made me acquire an attitude that most never aim for but should.&lt;/p&gt;

&lt;p&gt;The attitude was to KEEP EXPLORING FOREVER.&lt;/p&gt;

&lt;p&gt;My journey began with writing that first letter on VIM after learning how to enter Insert Mode and then exiting the same to navigate the document.&lt;br&gt;
VIM showed me the beauty that simplicity could hold and the complexity that minimalism could contain.&lt;br&gt;
It enabled me to explore solutions for even the most basic features that other text editors contain.&lt;/p&gt;

&lt;p&gt;During this journey that began from VIM and shall continue forever, I encountered a MEME similar to this one&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--TcYv6j9o--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://149351115.v2.pressablecdn.com/wp-content/uploads/2017/05/meme.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--TcYv6j9o--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://149351115.v2.pressablecdn.com/wp-content/uploads/2017/05/meme.jpeg" alt="VIM MEME"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And it made me realise the great significance VIM holds for me. It enabled me to keep learning and exploring to find solutions and inspired me to apply the same to other aspects of my life.&lt;/p&gt;

&lt;p&gt;I shall now like to end this brief to encourage the reader to always seek learning in every endeavour that you undertake. Yes, you will fail and fall but, soon, you will learn how to pick yourself up.&lt;/p&gt;

</description>
      <category>bash</category>
      <category>vim</category>
      <category>git</category>
      <category>linux</category>
    </item>
  </channel>
</rss>
