<?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: Abbas Ogaji</title>
    <description>The latest articles on DEV Community by Abbas Ogaji (@abbasogaji).</description>
    <link>https://dev.to/abbasogaji</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%2F290497%2F9c759d5a-1423-4c28-8219-aa426805d31c.png</url>
      <title>DEV Community: Abbas Ogaji</title>
      <link>https://dev.to/abbasogaji</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/abbasogaji"/>
    <language>en</language>
    <item>
      <title>How to dockerize your laravel app for heroku container registery</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Thu, 18 Nov 2021 07:27:46 +0000</pubDate>
      <link>https://dev.to/abbasogaji/how-to-dockerize-your-laravel-app-for-heroku-container-registery-23oa</link>
      <guid>https://dev.to/abbasogaji/how-to-dockerize-your-laravel-app-for-heroku-container-registery-23oa</guid>
      <description>&lt;p&gt;Its important to note that the build steps you will find right here is a basic starting point for dockerizing your laravel app in development environment. and this could be useful for teams that have a development environment hosted in heroku. &lt;em&gt;this is not a production setup&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;First let's outline the steps required for starting up a laravel project in development environment.&lt;/p&gt;

&lt;h6&gt;
  
  
  1- Installing PHP and Composer
&lt;/h6&gt;

&lt;p&gt;PHP is the language of the framework and composer is the dependency manager for the project,&lt;/p&gt;

&lt;h6&gt;
  
  
  2- Using Composer to install project dependencies
&lt;/h6&gt;

&lt;p&gt;The Laravel framework utilizes Composer for installation and dependency management.&lt;/p&gt;

&lt;h6&gt;
  
  
  3- Serving your Laravel project using the artisan cli tool
&lt;/h6&gt;

&lt;p&gt;When we want to run our laravel project we run the &lt;code&gt;php artisan serve&lt;/code&gt; command to serve our project at port 8000 by default &lt;/p&gt;

&lt;p&gt;Now lets Dockerize;&lt;br&gt;
The first step in writing our docker build steps is determing the base image for our docker container and the various dependencies that we would to install in our docker container to have our laravel project running confortably.&lt;/p&gt;

&lt;p&gt;Our base image will be a &lt;code&gt;php:8.0.5&lt;/code&gt; which is basically a linux image with php installed&lt;/p&gt;

&lt;p&gt;In the next step we will run the command below to update our package/dependency manager and dependences required for our laravel project&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;apt-get update &lt;span class="nt"&gt;-y&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; apt-get &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-y&lt;/span&gt; openssl zip unzip git
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Next is to install composer by running this command&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-sS&lt;/span&gt; https://getcomposer.org/installer | php &lt;span class="nt"&gt;--&lt;/span&gt; &lt;span class="nt"&gt;--install-dir&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;/usr/local/bin &lt;span class="nt"&gt;--filename&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;composer
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We might also like to install php extensions for mysql support and pdo for those using a mysql database in their project&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker-php-ext-install pdo_mysql
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then we install our laravel project dependency via composer&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;composer &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;--optimize-autoloader&lt;/span&gt; &lt;span class="nt"&gt;--no-dev&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now the tricky part is serving the application. Usually when serving our laravel application, port 8000 is allocated by default as the server port. but heroku platform doesnt respect ports defined by us, so we must make use of the PORT provided by heroku, luckly heroku defines an environment variable $PORT&lt;br&gt;
so therefore we will write the command to server the application this way 👇&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;php artisan serve &lt;span class="nt"&gt;--host&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;0.0.0.0 &lt;span class="nt"&gt;--port&lt;/span&gt; &lt;span class="nv"&gt;$PORT&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now putting all of this together in a Dockerfile at our root directory, we will have this👇&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight docker"&gt;&lt;code&gt;&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="s"&gt; php:8.0.5&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;apt-get update &lt;span class="nt"&gt;-y&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; apt-get &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-y&lt;/span&gt; openssl zip unzip git
&lt;span class="k"&gt;RUN &lt;/span&gt;curl &lt;span class="nt"&gt;-sS&lt;/span&gt; https://getcomposer.org/installer | php &lt;span class="nt"&gt;--&lt;/span&gt; &lt;span class="nt"&gt;--install-dir&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;/usr/local/bin &lt;span class="nt"&gt;--filename&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;composer
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; . /app&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;composer &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;--optimize-autoloader&lt;/span&gt; &lt;span class="nt"&gt;--no-dev&lt;/span&gt;
&lt;span class="k"&gt;CMD&lt;/span&gt;&lt;span class="s"&gt; php artisan serve --host=0.0.0.0 --port $PORT&lt;/span&gt;
&lt;span class="k"&gt;EXPOSE&lt;/span&gt;&lt;span class="s"&gt; $PORT&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And for laravel projects using mysql we will have this👇;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight docker"&gt;&lt;code&gt;&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="s"&gt; php:8.0.5&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;apt-get update &lt;span class="nt"&gt;-y&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; apt-get &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-y&lt;/span&gt; openssl zip unzip git
&lt;span class="k"&gt;RUN &lt;/span&gt;curl &lt;span class="nt"&gt;-sS&lt;/span&gt; https://getcomposer.org/installer | php &lt;span class="nt"&gt;--&lt;/span&gt; &lt;span class="nt"&gt;--install-dir&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;/usr/local/bin &lt;span class="nt"&gt;--filename&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;composer
&lt;span class="k"&gt;RUN &lt;/span&gt;docker-php-ext-install pdo_mysql
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; . /app&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;composer &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;--optimize-autoloader&lt;/span&gt; &lt;span class="nt"&gt;--no-dev&lt;/span&gt;
&lt;span class="k"&gt;CMD&lt;/span&gt;&lt;span class="s"&gt; php artisan serve --host=0.0.0.0 --port $PORT&lt;/span&gt;
&lt;span class="k"&gt;EXPOSE&lt;/span&gt;&lt;span class="s"&gt; $PORT&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



</description>
      <category>laravel</category>
      <category>docker</category>
      <category>tutorial</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Learning Rust : Match Statements</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Sat, 06 Feb 2021 07:37:23 +0000</pubDate>
      <link>https://dev.to/abbasogaji/learning-rust-match-statements-220l</link>
      <guid>https://dev.to/abbasogaji/learning-rust-match-statements-220l</guid>
      <description>&lt;p&gt;Rust has an extremely powerful control flow operator called match that allows you to compare a value against a series of patterns and then execute code based on which pattern matches. Patterns can be made up of literal values, variable names, wildcards, and many other things; (&lt;a href="https://doc.rust-lang.org/book/ch06-02-match.html"&gt;source&lt;/a&gt;)&lt;/p&gt;

&lt;p&gt;Match statement are kind of similar to switch statements; below is an example of how to use a match statements in rust&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight rust"&gt;&lt;code&gt;    &lt;span class="k"&gt;let&lt;/span&gt; &lt;span class="n"&gt;country_code&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;234&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;let&lt;/span&gt; &lt;span class="n"&gt;country&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;match&lt;/span&gt; &lt;span class="n"&gt;country_code&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="mi"&gt;44&lt;/span&gt; &lt;span class="k"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s"&gt;"United Kingdom"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="mi"&gt;234&lt;/span&gt; &lt;span class="k"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s"&gt;"Nigeria"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="mi"&gt;7&lt;/span&gt; &lt;span class="k"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s"&gt;"Russia"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s"&gt;"USA"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="mi"&gt;_&lt;/span&gt; &lt;span class="k"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s"&gt;"Unknown"&lt;/span&gt;
    &lt;span class="p"&gt;};&lt;/span&gt;
    &lt;span class="nd"&gt;println!&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"the country with code {} is {}"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;country_code&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;country&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="go"&gt;OUTPUT: "the country with code 234 is Nigeria"
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The Breakdown;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;1) The match control flow operation begins with the &lt;a href="https://doc.rust-lang.org/std/keyword.match.html"&gt;match&lt;/a&gt; keyword followed by the value or variable used for comparison.&lt;/li&gt;
&lt;li&gt;2) After the keyword and variable is the expression. the match expressions are encapsulated within curly brackets.&lt;/li&gt;
&lt;li&gt;&lt;p&gt;3) In the expression, the left hand side is the pattern and the right hand side is the code executed when the pattern matches, here we are returning a string value. &lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Notice the &lt;code&gt;_&lt;/code&gt; pattern at the bottom?. The _ pattern is a special pattern that will match any value. By putting it after our other arms, the _ will match all the possible cases that aren’t specified before it.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>rust</category>
      <category>programming</category>
      <category>systems</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Advantages of a Decentralized Web Over Centralized Web (Content vs Location based addressing)</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Sun, 16 Aug 2020 12:02:56 +0000</pubDate>
      <link>https://dev.to/abbasogaji/tl-dr-advantages-of-a-decentralized-web-over-a-centralized-web-part-1-content-vs-location-based-addressing-3pfm</link>
      <guid>https://dev.to/abbasogaji/tl-dr-advantages-of-a-decentralized-web-over-a-centralized-web-part-1-content-vs-location-based-addressing-3pfm</guid>
      <description>&lt;h4&gt;
  
  
  Centralized Web
&lt;/h4&gt;

&lt;p&gt;On a centralized web we access data via URLs, these URLs provides information for locating and identifying a resources provided by a central authority &lt;/p&gt;

&lt;p&gt;so when we do;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight http"&gt;&lt;code&gt;&lt;span class="err"&gt;GET - https://cakes.com/blue-cake.png
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;...we are hereby requesting for &lt;code&gt;blue-cake.png&lt;/code&gt; located at &lt;code&gt;cakes.com&lt;/code&gt;, some of the few drawbacks of (getting a resource via location based addressing on a) centralized web is;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;We cannot verify the content of the resource&lt;/li&gt;
&lt;li&gt;We can have duplicates of this resource all across the internet&lt;/li&gt;
&lt;li&gt;We cannot truly verify the ownership of this particular resource&lt;/li&gt;
&lt;li&gt;We left to assume that the authority providing this resource is trustworthy&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  Decentralized Web
&lt;/h4&gt;

&lt;p&gt;But on a decentralized web, data stored are identified by a cryptographic hash (which serves as a fingerprint signature for a resource), since a hash value can uniquely identify a resource, all attempts to store duplicates of a resource across network can be evaded.&lt;/p&gt;

&lt;p&gt;therefore, when we do a&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight http"&gt;&lt;code&gt;&lt;span class="err"&gt;GET - https://decentralized.web/66FAC571933F185C3C4E4F03C01E76B66978DD13
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;we are hereby requesting for resource with the hash value &lt;code&gt;66FAC571933F185C3C4E4F03C01E76B66978DD13&lt;/code&gt; at &lt;code&gt;decentralized.web&lt;/code&gt; (with is a decentralized network of resource owning nodes, where the active node that owns this resource would provide it to the end user)&lt;/p&gt;

&lt;p&gt;So on a decentralized web;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;We can verify the content of the resource&lt;/li&gt;
&lt;li&gt;We can verify the owner of the resource&lt;/li&gt;
&lt;li&gt;We can avoid data redundancy and duplicate data all over the internet&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;For more info about decentralized web : &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://ipfs.io/#how"&gt;https://ipfs.io/#how&lt;/a&gt;
For more info about Cryptographic: &lt;/li&gt;
&lt;li&gt;&lt;a href="https://en.wikipedia.org/wiki/Cryptographic_hash_function"&gt;https://en.wikipedia.org/wiki/Cryptographic_hash_function&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://en.wikipedia.org/wiki/SHA-2"&gt;https://en.wikipedia.org/wiki/SHA-2&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>beginners</category>
      <category>webdev</category>
      <category>blockchain</category>
    </item>
    <item>
      <title>TL;DR:  DNS Cache Poisioning;</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Sun, 09 Aug 2020 11:48:21 +0000</pubDate>
      <link>https://dev.to/abbasogaji/tl-dr-dns-cache-poisioning-196o</link>
      <guid>https://dev.to/abbasogaji/tl-dr-dns-cache-poisioning-196o</guid>
      <description>&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Impersonating an Authoritative nameserver and forging a reply to the DNS server requesting for information, &lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Reply gets cached (meaning DNS server ends up caching wrong information)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;e.g DNS server ask for IP address of a Domain name Attackers forges a reply with the wrong IP and wrong IP gets cached&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Extras:
&lt;/h3&gt;

&lt;h4&gt;
  
  
  a) What is a DNS Server :
&lt;/h4&gt;

&lt;p&gt;DNS translates domain names to IP addresses so browsers can load Internet resources. the DNS Server handles this task of finding the right IP address for the domain name entered&lt;/p&gt;

&lt;h4&gt;
  
  
  b) What is a Nameserver:
&lt;/h4&gt;

&lt;p&gt;They hold information about domain names and their associated ip addresses&lt;/p&gt;

</description>
      <category>security</category>
      <category>computerscience</category>
      <category>beginners</category>
    </item>
    <item>
      <title>TL;DR : RFC 6238, TOTP (Time based one time password)</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Sun, 19 Jul 2020 09:53:35 +0000</pubDate>
      <link>https://dev.to/abbasogaji/tl-dr-rfc-6238-totp-time-based-one-time-password-amc</link>
      <guid>https://dev.to/abbasogaji/tl-dr-rfc-6238-totp-time-based-one-time-password-amc</guid>
      <description>&lt;p&gt;Used in: &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Google Authenticator.&lt;/li&gt;
&lt;li&gt;Twillio Authy e.t.c
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;
&lt;span class="c1"&gt;// n digits &lt;/span&gt;
&lt;span class="nx"&gt;TOTP&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;TRUCATE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;HMAC&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;secret_key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;counter&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="o"&gt;^&lt;/span&gt;&lt;span class="nx"&gt;n&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Where;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;secret_key  = shared between client and server&lt;/li&gt;
&lt;li&gt;counter = floor(unix-time/time step)&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Hash will be truncated, converted to decimal divided by 10^n (where n is the number of otp digits), the result of the remainder will give you an n length integer, which is our OTP code&lt;/p&gt;

</description>
      <category>tutorial</category>
      <category>security</category>
    </item>
    <item>
      <title>How to write a custom *ngIf directive to display only authorized views</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Wed, 05 Feb 2020 10:10:14 +0000</pubDate>
      <link>https://dev.to/abbasogaji/how-to-write-a-custom-ngif-directive-to-display-only-authorized-views-2jm7</link>
      <guid>https://dev.to/abbasogaji/how-to-write-a-custom-ngif-directive-to-display-only-authorized-views-2jm7</guid>
      <description>&lt;p&gt;Imagine a scenario where you have a page or form that should only display certain sections or fields based on a user role or authority in an application. For this, you would probably need conditional statements that would drive your display. Traditional *ngIf directive could be used, but for this use-case, we will write a custom derivate with more features;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;So let's go:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;For our use-case, a user is provided with an array of viewable sections based on role/level/authority, so that a section of a page will only be displayed if it's included in the array.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;userViewableSections&lt;/span&gt; &lt;span class="o"&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;bio-section&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;friends-section&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;posts-section&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;ul&gt;
&lt;li&gt;Our custom directive name would be &lt;strong&gt;"isAuthorized"&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;we would add an asterisk(*) to our directive name *isAuthorized to make use of Angular's &lt;a href="https://angular.io/guide/structural-directives#microsyntax"&gt;microsyntax&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Our directive will be written like this;
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Directive&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;TemplateRef&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nx"&gt;ViewContainerRef&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;OnInit&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;OnChanges&lt;/span&gt;  &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@angular/core&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="nd"&gt;Directive&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;selector&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;[isAuthorized]&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IsAuthorizedDirective&lt;/span&gt; &lt;span class="k"&gt;implements&lt;/span&gt; &lt;span class="nx"&gt;OnInit&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;OnChanges&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="nx"&gt;isAuthorizedIn&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;
  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="nx"&gt;isAuthorized&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;
  &lt;span class="k"&gt;private&lt;/span&gt; &lt;span class="nx"&gt;hasView&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="kd"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt; &lt;span class="nx"&gt;templateRef&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;TemplateRef&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="kr"&gt;any&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;private&lt;/span&gt; &lt;span class="nx"&gt;vcr&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;ViewContainerRef&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nx"&gt;ngOnInit&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;configureView&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nx"&gt;ngOnChanges&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
    &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;configureView&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nx"&gt;configureView&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;isAuthorized&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;isAuthorizedIn&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;some&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;gt;&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;isAuthorized&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;isAuthorized&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;vcr&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;createEmbeddedView&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;templateRef&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;isAuthorized&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;vcr&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;clear&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;false&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="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Directive Breakdown:&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;strong&gt;TemplateRef&lt;/strong&gt; and &lt;strong&gt;ViewContainerRef&lt;/strong&gt;:
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;TemplateRef&lt;/strong&gt; represents an embedded template that can be used to instantiate embedded views, so the HTML snippet that houses our directive becomes a &lt;em&gt;templateRef&lt;/em&gt; which is then instantiated by the ViewContainerRef.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;strong&gt;Microsyntax&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Angular's microsyntax features provides us options to pass parameters with the format below;&lt;/p&gt;

&lt;p&gt;*isAuthorized="'bio-section'; in : userViewableSections"&lt;/p&gt;

&lt;p&gt;the string &lt;em&gt;'bio-section'&lt;/em&gt; is mapped to &lt;em&gt;@Input()&lt;/em&gt; isAuthorized and &lt;em&gt;"...; in : userViewableSections"&lt;/em&gt; maps the &lt;em&gt;userViewableSections&lt;/em&gt; array to &lt;em&gt;@Input() isAuthorizedIn;&lt;/em&gt; the microsytax will resolve the &lt;em&gt;"in"&lt;/em&gt; to recognize a &lt;em&gt;@Input()&lt;/em&gt; variable with &lt;strong&gt;"in"&lt;/strong&gt; appended to the parent directive &lt;em&gt;@Input&lt;/em&gt; in camel case format (i.e isAuthorized + In = &lt;em&gt;@Input()&lt;/em&gt; isAuthorizedIn)&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;strong&gt;Summary&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;In summary, the directive displays our template if the string passed into &lt;em&gt;@Input() isAuthorized&lt;/em&gt;, exists in array passed into &lt;em&gt;@Input() isAuthorizedIn&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;See Screenshots below;&lt;/p&gt;

&lt;p&gt;PAGE :&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--LzKDtDPN--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73829652-a3e4bd00-4803-11ea-9d54-3df6e832005c.PNG" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--LzKDtDPN--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73829652-a3e4bd00-4803-11ea-9d54-3df6e832005c.PNG" alt="custom-dir-html-page"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;COMPONENT HTML&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--sSPMlb_S--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73830251-a267c480-4804-11ea-9dbe-c5786ae1b16f.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--sSPMlb_S--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73830251-a267c480-4804-11ea-9dbe-c5786ae1b16f.png" alt="angular-html-ngIf"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Check out the complete project on GitHub; &lt;a href="https://github.com/abbasogaji/custom-ngIf-directive"&gt;Project Link&lt;/a&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>typescript</category>
      <category>tutorial</category>
      <category>javascript</category>
    </item>
    <item>
      <title>How to write a custom structural directive to display only authorized sections of a page in Angular</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Wed, 05 Feb 2020 09:55:09 +0000</pubDate>
      <link>https://dev.to/abbasogaji/how-to-use-custom-structural-derivates-to-display-authorized-sections-of-a-page-or-form-in-angular-3c90</link>
      <guid>https://dev.to/abbasogaji/how-to-use-custom-structural-derivates-to-display-authorized-sections-of-a-page-or-form-in-angular-3c90</guid>
      <description>&lt;p&gt;Imagine a scenario where you have a page or form that should only display certain sections or fields based on a user role or authority in an application. For this, you would probably need conditional statements that would drive your display. Traditional *ngIf directive could be used, but for this use-case, we will write a custom derivate with more features;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;So let's go:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;For our use-case, a user is provided with an array of viewable sections based on role/level/authority, so that a section of a page will only be displayed if it's included in the array.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;userViewableSections&lt;/span&gt; &lt;span class="o"&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;bio-section&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;friends-section&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;posts-section&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;ul&gt;
&lt;li&gt;Our custom directive name would be &lt;strong&gt;"isAuthorized"&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;we would add an asterisk(*) to our directive name *isAuthorized to make use of Angular's &lt;a href="https://angular.io/guide/structural-directives#microsyntax"&gt;microsyntax&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Our directive will be written like this;
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Directive&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;TemplateRef&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nx"&gt;ViewContainerRef&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;OnInit&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;OnChanges&lt;/span&gt;  &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@angular/core&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="nd"&gt;Directive&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;selector&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;[isAuthorized]&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IsAuthorizedDirective&lt;/span&gt; &lt;span class="k"&gt;implements&lt;/span&gt; &lt;span class="nx"&gt;OnInit&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;OnChanges&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="nx"&gt;isAuthorizedIn&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;
  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="nx"&gt;isAuthorized&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;
  &lt;span class="k"&gt;private&lt;/span&gt; &lt;span class="nx"&gt;hasView&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="kd"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt; &lt;span class="nx"&gt;templateRef&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;TemplateRef&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="kr"&gt;any&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;private&lt;/span&gt; &lt;span class="nx"&gt;vcr&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;ViewContainerRef&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nx"&gt;ngOnInit&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;configureView&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nx"&gt;ngOnChanges&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
    &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;configureView&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nx"&gt;configureView&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;isAuthorized&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;isAuthorizedIn&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;some&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;gt;&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;isAuthorized&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;isAuthorized&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;vcr&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;createEmbeddedView&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;templateRef&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;isAuthorized&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;vcr&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;clear&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;hasView&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;false&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="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Directive Breakdown:&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;strong&gt;TemplateRef&lt;/strong&gt; and &lt;strong&gt;ViewContainerRef&lt;/strong&gt;:
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;TemplateRef&lt;/strong&gt; represents an embedded template that can be used to instantiate embedded views, so the HTML snippet that houses our directive becomes a &lt;em&gt;templateRef&lt;/em&gt; which is then instantiated by the ViewContainerRef.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;strong&gt;Microsyntax&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Angular's microsyntax features provides us options to pass parameters with the format below;&lt;/p&gt;

&lt;p&gt;*isAuthorized="'bio-section'; in : userViewableSections"&lt;/p&gt;

&lt;p&gt;the string &lt;em&gt;'bio-section'&lt;/em&gt; is mapped to &lt;em&gt;@Input()&lt;/em&gt; isAuthorized and &lt;em&gt;"...; in : userViewableSections"&lt;/em&gt; maps the &lt;em&gt;userViewableSections&lt;/em&gt; array to &lt;em&gt;@Input() isAuthorizedIn;&lt;/em&gt; the microsytax will resolve the &lt;em&gt;"in"&lt;/em&gt; to recognize a &lt;em&gt;@Input()&lt;/em&gt; variable with &lt;strong&gt;"in"&lt;/strong&gt; appended to the parent directive &lt;em&gt;@Input&lt;/em&gt; in camel case format (i.e isAuthorized + In = &lt;em&gt;@Input()&lt;/em&gt; isAuthorizedIn)&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;strong&gt;Summary&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;In summary, the directive displays our template if the string passed into &lt;em&gt;@Input() isAuthorized&lt;/em&gt;, exists in array passed into &lt;em&gt;@Input() isAuthorizedIn&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;See Screenshots below;&lt;/p&gt;

&lt;p&gt;PAGE :&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--LzKDtDPN--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73829652-a3e4bd00-4803-11ea-9d54-3df6e832005c.PNG" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--LzKDtDPN--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73829652-a3e4bd00-4803-11ea-9d54-3df6e832005c.PNG" alt="custom-dir-html-page"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;COMPONENT HTML&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--sSPMlb_S--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73830251-a267c480-4804-11ea-9dbe-c5786ae1b16f.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--sSPMlb_S--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://user-images.githubusercontent.com/34817010/73830251-a267c480-4804-11ea-9dbe-c5786ae1b16f.png" alt="angular-html-ngIf"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Check out the complete project on GitHub; &lt;a href="https://github.com/abbasogaji/custom-ngIf-directive"&gt;Project Link&lt;/a&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>typescript</category>
      <category>tutorial</category>
      <category>javascript</category>
    </item>
    <item>
      <title>How to Dockerize your NestJS App for production</title>
      <dc:creator>Abbas Ogaji</dc:creator>
      <pubDate>Sat, 28 Dec 2019 13:41:00 +0000</pubDate>
      <link>https://dev.to/abbasogaji/how-to-dockerize-your-nestjs-app-for-production-2lmf</link>
      <guid>https://dev.to/abbasogaji/how-to-dockerize-your-nestjs-app-for-production-2lmf</guid>
      <description>&lt;p&gt;As we all know Docker is not just another buzzword, but one of the best containerization tool for software engineers. With the ability to ship any application regardless of its environmental requirements docker has solved problems in development and production stage like; inconsistencies when running your application with the phrase popularly known as &lt;strong&gt;&lt;em&gt;"urghh..but it worked on my PC!"&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This tutorial shows how to Dockerize a Nestjs app, built with the Nestjs CLI and Docker.&lt;/p&gt;

&lt;p&gt;Requirements&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Docker installed&lt;/li&gt;
&lt;li&gt;A NestJs app&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;1. Docker Installation&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;a) For the installion guide on windows visit &lt;a href="https://docs.docker.com/docker-for-windows/install/" rel="noopener noreferrer"&gt;https://docs.docker.com/docker-for-windows/install/&lt;/a&gt;  &lt;/p&gt;

&lt;p&gt;b) For the installation guide on Linux visit &lt;br&gt;
 &lt;a href="https://docs.docker.com/install/linux/docker-ce/ubuntu/" rel="noopener noreferrer"&gt;https://docs.docker.com/install/linux/docker-ce/ubuntu/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;c) For the installation guide on macOs visit &lt;a href="https://docs.docker.com/docker-for-mac/" rel="noopener noreferrer"&gt;https://docs.docker.com/docker-for-mac/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. NestJs Application&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Create and develop your NestJs application or use the sample project provided below for the demo:&lt;br&gt;
&lt;a href="https://github.com/abbasogaji/dockerized-nestjs-production-app" rel="noopener noreferrer"&gt;https://github.com/abbasogaji/dockerized-nestjs-production-app&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Your nestJs application project structure usually would look like this:&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%2Fuser-images.githubusercontent.com%2F34817010%2F71542915-ae8e7580-296c-11ea-87d9-e22298afbf0e.jpg" 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%2Fuser-images.githubusercontent.com%2F34817010%2F71542915-ae8e7580-296c-11ea-87d9-e22298afbf0e.jpg" alt="Nestjs project structure"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And its associated npm commands for running, testing and building your nestJs project are found in your package.json's scripts object (property);&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%2Fuser-images.githubusercontent.com%2F34817010%2F71543032-712ae780-296e-11ea-9940-e893bc6d5fd4.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%2Fuser-images.githubusercontent.com%2F34817010%2F71543032-712ae780-296e-11ea-9940-e893bc6d5fd4.png" alt="package.json scripts"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Some of these commands will be used when we dockerize our application. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;NOW WE WRITE OUR Dockerfile&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight docker"&gt;&lt;code&gt;&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;node:10&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;AS&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;builder&lt;/span&gt;
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; ./package.json ./&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; . .&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;npm run build


&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="s"&gt; node:10-alpine&lt;/span&gt;
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; --from=builder /app ./&lt;/span&gt;
&lt;span class="k"&gt;CMD&lt;/span&gt;&lt;span class="s"&gt; ["npm", "run", "start:prod"]&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Breakdown&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;The build process is divided into two steps (multi-step build);&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The First step uses node:10 as base image, installs dependencies and transpiles Typescript files to Javascript. Full node image is used for this process since it contains all the necessarity build tools required for dependencies with native build (node-gyp, python, gcc, g++, make)&lt;/li&gt;
&lt;li&gt;The Second step uses node:10-alpine (lightweight version), copies file-system from the first step's (intermediate) container, sets command for running the application. A multi step build process was setup to efficiently install our dependencies at first step and to run a lightweight container from image the of our final step.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;

&lt;p&gt;In First step; &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;We will set our application directory to "/app", so our application is bundled into "/app" in our docker image file-system&lt;/li&gt;
&lt;li&gt;We will COPY our &lt;em&gt;"package.json"&lt;/em&gt; then run &lt;em&gt;"npm install"&lt;/em&gt; before we copy the remaining project files because that will prevent unnecessary installs anytime we re-build our image and make use of cached installs.&lt;/li&gt;
&lt;li&gt;We will run "npm run build" to generate production files at &lt;em&gt;"dist/main"&lt;/em&gt; directory which is required by our "run" command in production context i.e (npm run start:prod)&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;

&lt;p&gt;In Final step;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;We will set our application directory to "/app", so our application is bundled into "/app" in our docker image file-system&lt;/li&gt;
&lt;li&gt;We will copy the file-system of the previous step.&lt;/li&gt;
&lt;li&gt;We will set command for running our application &lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;ol&gt;
&lt;li&gt;Create .dockerignore to avoid copying node_modules; so in your &lt;em&gt;.dockerignore&lt;/em&gt; you type in &lt;em&gt;"node_modules"&lt;/em&gt; and now you have your &lt;em&gt;Dockerfile&lt;/em&gt; and &lt;em&gt;.dockerignore&lt;/em&gt; file at your base directory of your project as shown below;&lt;/li&gt;
&lt;/ol&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%2Fuser-images.githubusercontent.com%2F34817010%2F71544162-d802cd80-297b-11ea-8e00-f04ba8a7ffed.JPG" 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%2Fuser-images.githubusercontent.com%2F34817010%2F71544162-d802cd80-297b-11ea-8e00-f04ba8a7ffed.JPG" alt="final project"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Now we build our image,  assign a tag with the format "docker-username/project-name" then push to docker hub by running:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; docker build -t exampleuser/dockerized-nest-project .

 docker push exampleuser/dockerized-nest-project

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Question&lt;/strong&gt;: Now we are done; but wait a minute? EXPOSE port command was omitted?. &lt;br&gt;
&lt;strong&gt;Answer&lt;/strong&gt;: because EXPOSE command is not respected by some Paas (Platform as service) providers e.g (Heroku).&lt;/p&gt;

&lt;p&gt;but if you deploy your docker image to a cloud provider that requires EXPOSE command which maps your docker network ports to your host port. then you should add "EXPOSE 3000" IN Dockerfile before the last CMD command;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight docker"&gt;&lt;code&gt;&lt;span class="c"&gt;# Using Node:10 Image Since it contains all &lt;/span&gt;
&lt;span class="c"&gt;# the necessary build tools required for dependencies with native build (node-gyp, python, gcc, g++, make)&lt;/span&gt;
&lt;span class="c"&gt;# First Stage : to install and build dependences&lt;/span&gt;

&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;node:10&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;AS&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;builder&lt;/span&gt;
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; ./package.json ./&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; . .&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;npm run build


&lt;span class="c"&gt;# Second Stage : Setup command to run your app using lightweight node image&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="s"&gt; node:10-alpine&lt;/span&gt;
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; --from=builder /app ./&lt;/span&gt;
&lt;span class="k"&gt;EXPOSE&lt;/span&gt;&lt;span class="s"&gt; 3000&lt;/span&gt;
&lt;span class="k"&gt;CMD&lt;/span&gt;&lt;span class="s"&gt; ["npm", "run", "start:prod"]&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt; : Using Multi-Step build process to dockerize our nestjs application isn't a necessity and was only used because we would like our image to be lightweight. for a single step build process we will write the following;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight docker"&gt;&lt;code&gt;&lt;span class="c"&gt;# Using Node:10 Image Since it contains all &lt;/span&gt;
&lt;span class="c"&gt;# the necessary build tools required for dependencies with native build (node-gyp, python, gcc, g++, make)&lt;/span&gt;

&lt;span class="k"&gt;FROM&lt;/span&gt;&lt;span class="s"&gt; node:10&lt;/span&gt;
&lt;span class="k"&gt;WORKDIR&lt;/span&gt;&lt;span class="s"&gt; /app&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; ./package.json ./&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt;
&lt;span class="k"&gt;COPY&lt;/span&gt;&lt;span class="s"&gt; . .&lt;/span&gt;
&lt;span class="k"&gt;RUN &lt;/span&gt;npm run build
&lt;span class="c"&gt;# EXPOSE 3000&lt;/span&gt;
&lt;span class="k"&gt;CMD&lt;/span&gt;&lt;span class="s"&gt; ["npm", "run", "start:prod"]&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then finally we will have to &lt;strong&gt;rebuild&lt;/strong&gt;, &lt;strong&gt;deply&lt;/strong&gt; and &lt;strong&gt;run&lt;/strong&gt; the image&lt;/p&gt;

</description>
      <category>docker</category>
      <category>nestjs</category>
      <category>npm</category>
      <category>devops</category>
    </item>
  </channel>
</rss>
