<?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: Tahsin</title>
    <description>The latest articles on DEV Community by Tahsin (@tahsinature).</description>
    <link>https://dev.to/tahsinature</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%2F215848%2F70200c59-571b-4c6e-a4e4-b2b3025ab6f0.jpg</url>
      <title>DEV Community: Tahsin</title>
      <link>https://dev.to/tahsinature</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/tahsinature"/>
    <language>en</language>
    <item>
      <title>Easy Explanation of Coding Principles: Understand Key Concepts in Simple Terms</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Thu, 20 Apr 2023 12:08:01 +0000</pubDate>
      <link>https://dev.to/tahsinature/easy-explanation-of-coding-principles-understand-key-concepts-in-simple-terms-32h1</link>
      <guid>https://dev.to/tahsinature/easy-explanation-of-coding-principles-understand-key-concepts-in-simple-terms-32h1</guid>
      <description>&lt;p&gt;As a software developer, writing clean, maintainable, and efficient code is crucial for building robust and scalable applications. To achieve this, it’s essential to follow established software principles that provide guidelines for structuring and organizing code. In this article, we will explore a collection of widely used software principles that every developer should be familiar with. Whether you are a beginner or an experienced programmer, these principles can help you write high-quality code that is easier to understand, maintain, and extend.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5pbgfc2j87b3benx0hqw.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5pbgfc2j87b3benx0hqw.jpg" alt="Coding Principles" width="800" height="532"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I created &lt;a href="https://github.com/tahsinature/coding-principles" rel="noopener noreferrer"&gt;this&lt;/a&gt; GitHub repository with some examples of each principle in Python code. At the same time here are some easy explanations for each of those below:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Single Responsibility Principle (SRP):&lt;/strong&gt; Each part of the code should have only one job to do, just like you have one toy to play with at a time.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Open/Closed Principle (OCP):&lt;/strong&gt; We can add new features to our code without changing the old parts, just like we can add toppings to our pizza without changing the crust.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Liskov Substitution Principle (LSP):&lt;/strong&gt; We can use a new toy that looks like the old one, and it will work the same way, just like using a toy car or a toy truck on the same track.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Interface Segregation Principle (ISP):&lt;/strong&gt; Each toy should have only the buttons and parts that we need, and not extra ones, just like a toy phone should have buttons to call and hang up, but not unnecessary buttons for other functions.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Dependency Inversion Principle (DIP):&lt;/strong&gt; We should talk to our friends through a walkie-talkie, so we can use different walkie-talkies or even phones, as long as they work with the same frequency, just like our code should communicate with other parts through interfaces, so we can easily replace or upgrade those parts.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Don’t Repeat Yourself (DRY):&lt;/strong&gt; We should not say the same things over and over again, but just once, just like we should not write the same code in different places, but reuse it in one place.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Keep It Simple, Stupid (KISS):&lt;/strong&gt; We should not make things more complicated than they need to be, just like we should not use big words or difficult instructions when explaining something.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;You Ain’t Gonna Need It (YAGNI):&lt;/strong&gt; We should not worry about things that we don’t really need right now, just like we should not pack extra toys for a short trip, but only take what we really want to play with.&lt;/p&gt;

&lt;p&gt;In summary, understanding and applying the fundamentals of software can improve code quality and make your software more manageable, scalable, and efficient. You can improve your software development and design better by following these widely used principles.&lt;/p&gt;

&lt;p&gt;Whether you’re a newbie to software development or an experienced programmer looking to improve your skills, a simple understanding of this software principles is valuable.&lt;/p&gt;

&lt;p&gt;Happy coding!&lt;/p&gt;

</description>
      <category>coding</category>
      <category>programming</category>
    </item>
    <item>
      <title>Tired of circular dependency in Typescript/Node.js?</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Mon, 07 Mar 2022 14:22:41 +0000</pubDate>
      <link>https://dev.to/tahsinature/tired-of-circular-dependency-in-typescriptnodejs-4i0a</link>
      <guid>https://dev.to/tahsinature/tired-of-circular-dependency-in-typescriptnodejs-4i0a</guid>
      <description>&lt;p&gt;First of all, let’s see what is a &lt;a href="https://en.wikipedia.org/wiki/Circular_dependency" rel="noopener noreferrer"&gt;circular dependency&lt;/a&gt;. According to this Wikipedia:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;In software engineering, a circular dependency is a relation between two or more modules which either directly or indirectly depend on each other to function properly. Such modules are also known as mutually recursive.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fuo316hsdbilzq9jfjfks.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fuo316hsdbilzq9jfjfks.png" alt="Circular dependency demonstration" width="216" height="199"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Alright, what does it mean? Well, to understand it properly let’s clone this &lt;a href="https://github.com/tahsinature/circular-dependency-typescript" rel="noopener noreferrer"&gt;repository&lt;/a&gt; and cd into &lt;code&gt;src/good&lt;/code&gt; dir &amp;amp; inspect the files.&lt;/p&gt;

&lt;p&gt;What we can see there is, &lt;code&gt;a.ts&lt;/code&gt; is importing a variable from &lt;code&gt;b.ts&lt;/code&gt; &amp;amp; in the &lt;code&gt;main.ts&lt;/code&gt; we are importing &amp;amp; printing the variable from &lt;code&gt;a.ts&lt;/code&gt;. So the flow looks like this:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fil15caryznh11249sotx.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fil15caryznh11249sotx.png" alt="Circular depndency possibilities" width="261" height="32"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When we execute main.ts by npx ts-node main.ts here is the output:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjjghn1bvxfcz09xzaoyy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjjghn1bvxfcz09xzaoyy.png" alt="Working fine without circular depndency" width="184" height="47"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;So far so good. Now let’s cd into src/problem dir &amp;amp; inspect what's going on. Here we can see a.ts importing a variable from b.ts and so does b.ts the opposite. And in main.ts it’s importing a variable from a.ts &amp;amp; b.ts and printing them. In this case, the flow looks like this:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2aitneex6a13flcx7cof.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2aitneex6a13flcx7cof.png" alt="Circular depndency" width="161" height="111"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When we execute main.ts by npx ts-node main.ts here is the output:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fe5mkqzuylxfh8nbjapq6.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fe5mkqzuylxfh8nbjapq6.png" alt="Module not loaded correct because of circular dep" width="281" height="123"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;What is going on? In the last line instead of John, we are seeing &lt;code&gt;undefined&lt;/code&gt;. Didn’t we import the variable correctly? Yes, we did. But it is happening because of the circular dependency problem. Look at the problem dir flow above. File &lt;code&gt;a.ts&lt;/code&gt; is dependent on &lt;code&gt;b.ts&lt;/code&gt; &amp;amp; &lt;code&gt;b.ts&lt;/code&gt; dependent on &lt;code&gt;a.ts&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;How it’s happening let’s talk about it another time, but before that let’s see how we can detect it.&lt;/p&gt;

&lt;p&gt;In a small program like this, it’s not a big problem to detect circular dependency. But in a large codebase, once we depend on a wrong module accidentally, then it’s tough to detect this later on. So today we are gonna use a tool call madge. Let’s see how we are gonna use it.&lt;/p&gt;

&lt;p&gt;cd into &lt;code&gt;src/good&lt;/code&gt; dir &amp;amp; execute &lt;code&gt;npx madge --extensions js,ts --circular .&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;What do you see? No problems found. Right? Yeah. Because there is no circular dependency problem.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fb9toa6519e05ct8lesx7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fb9toa6519e05ct8lesx7.png" alt="No circular dependency" width="355" height="83"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Now cd into &lt;code&gt;src/problem&lt;/code&gt; dir &amp;amp; execute &lt;code&gt;npx madge --extensions js,ts --circular .&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;What do you see? It’s awesome, right? The way it shows which files are circularly depending on what files, in a large codebase, it saves a lot of time.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fvj2hewqwm3tbpdhadwwz.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fvj2hewqwm3tbpdhadwwz.png" alt="Circular dependency detected" width="359" height="121"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Oiya, before we forget, of course in a large codebase we use tsconfig.json. If we have module aliases or something like that, we have to point to that tsconfig.json. So in that case we can add another flag like this:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frx4e3tyvn5nlfqoheb7l.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frx4e3tyvn5nlfqoheb7l.png" alt="Command with TypeScript" width="800" height="226"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If we do not use typescript, we don’t have to use &lt;code&gt;--ts-config&lt;/code&gt; flag as well as &lt;code&gt;ts&lt;/code&gt; in the &lt;code&gt;--extensions&lt;/code&gt; flag.&lt;/p&gt;

&lt;p&gt;Alright, enough for today. Next, hopefully, we will talk about how circular-dependency gets created underneath. Thank You.&lt;/p&gt;

&lt;p&gt;Happy Coding 💻&lt;/p&gt;

</description>
      <category>typescript</category>
      <category>javascript</category>
      <category>node</category>
      <category>npm</category>
    </item>
    <item>
      <title>The impact of sharing sessions in an engineering team</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Mon, 07 Mar 2022 13:37:14 +0000</pubDate>
      <link>https://dev.to/tahsinature/the-impact-of-sharing-sessions-in-an-engineering-team-5f3g</link>
      <guid>https://dev.to/tahsinature/the-impact-of-sharing-sessions-in-an-engineering-team-5f3g</guid>
      <description>&lt;p&gt;&lt;strong&gt;D&lt;/strong&gt;id you know? Throughout the course of one year, an average person receives an impressive amount of data. According to &lt;a href="https://www.forbes.com/sites/lisaquast/2012/08/20/why-knowledge-management-is-important-to-the-success-of-your-company/#29245be53681" rel="noopener noreferrer"&gt;David Derbyshire&lt;/a&gt;, scientists have even figured out the exact amount we’re talking about: the equivalent of every person in the world reading 174 newspapers every single day. This overload of data people are dealing with, increases the importance of knowledge sharing within a team.&lt;/p&gt;

&lt;p&gt;In my opinion, the impact of having sharing sessions regularly as a part of the team culture is massive. Let me explain how. Have you heard of this following term?&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;The best way to learn something is: teaching that.&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Whether or not you’re a developer, you’re most likely learning something new every single day. It can be a productivity tool, a concept, a hack, a new technology. No matter what is it, as long as your team can relate to the knowledge, just arrange a session and share it. So the question is: why? What’s the outcome?&lt;/p&gt;

&lt;h2&gt;
  
  
  Creates an ideal environment for syncing up ideas
&lt;/h2&gt;

&lt;p&gt;Very often we come up with new ideas. Sometimes good, sometimes maybe not so good. Or, maybe a solution to a critical problem. So if we have an easy-going sharing session, it enables the possibility to sync up that idea within the team very easily. If the team gets used to it, they will feel it easier to do thing and tend to share more often. It enables an educative environment that makes you/me feel like: “&lt;strong&gt;&lt;em&gt;I am having growth here with my team.&lt;/em&gt;&lt;/strong&gt;”&lt;/p&gt;

&lt;h2&gt;
  
  
  Motivates others
&lt;/h2&gt;

&lt;p&gt;Sometimes you see, your colleague (A) is facing an issue of which you or other teammates have easy &amp;amp; quick solutions. But your colleague (A) will not ask about it. Rather he/she will try to figure it out alone. I noticed this type of thing happens when we do not have an open culture.&lt;/p&gt;

&lt;p&gt;Or maybe the other way around. Your colleague (B) has very good knowledge about a problem that your team facing. But due to the fact that your colleague (B) is very shy/afraid about sharing that knowledge in front of a group of people, we all are about to be deprived of gaining that good knowledge.&lt;/p&gt;

&lt;p&gt;But things wouldn’t be the case if we could make the environment like: it’s very easy to share things/knowledge/idea, no matter how good or bad it is. We should welcome it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Increases team chemistry/bonding
&lt;/h2&gt;

&lt;p&gt;Sharing is caring. We all know the fact. When we have a weekly or, bi-weekly sharing session, it allows us to have a group discussion together. And as we know, any group project/discussion increases the chemistry which helps every individual to be more productive. In other words, it also enables more interaction among the team altogether.&lt;/p&gt;

&lt;p&gt;And don’t forget about your remote workers! It’s often challenging for them to learn from their colleagues outside of the face-to-face environment, and perhaps more difficult to ask the right questions. When you’re remote, there’s the worry that you’re pestering people. Well, when people can search for shared knowledge, that really kills those two birds with one stone.&lt;/p&gt;

&lt;h2&gt;
  
  
  The feel-good factor
&lt;/h2&gt;

&lt;p&gt;Let’s end on the most positive note of all! Sometimes, sharing knowledge isn’t even about the knowledge, the biggest benefit can come from everybody feeling like their voice is being heard. That’s a real shot of motivation for most people because they feel like a valued part of the team, and their experience is genuinely helping others to grow. At the same time, they’re giving somebody else that same feeling and that can go a long way to helping your business progress.&lt;/p&gt;

&lt;h2&gt;
  
  
  Let’s Wrap Up
&lt;/h2&gt;

&lt;p&gt;It was tough to cover everything here. But this was a brief overview from my little experience of how a &lt;strong&gt;Regular Sharing Session&lt;/strong&gt; in a team makes a significant impact. If you have any other thoughts, please do let me know.&lt;/p&gt;

&lt;p&gt;Happy Knowledge Sharing!&lt;br&gt;
Thank you, and take care!&lt;/p&gt;

</description>
      <category>sharing</category>
      <category>knowledge</category>
    </item>
    <item>
      <title>Concurrency is not Parallelism - A deeper look at their key difference</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Mon, 07 Mar 2022 03:02:27 +0000</pubDate>
      <link>https://dev.to/tahsinature/concurrency-is-not-parallelism-a-deeper-look-at-their-key-difference-3amb</link>
      <guid>https://dev.to/tahsinature/concurrency-is-not-parallelism-a-deeper-look-at-their-key-difference-3amb</guid>
      <description>&lt;p&gt;Today, in this article, we'll analyze two common processing techniques used by the operating system (OS). &lt;strong&gt;Concurrency&lt;/strong&gt; &amp;amp; &lt;strong&gt;Parallelism&lt;/strong&gt;. When we have more than one process waiting to be executed, these 2 concepts come into the picture. Before we jump into the brief explanation about each, let's have a quick look at how CPU works underneath the hood.&lt;/p&gt;

&lt;p&gt;Generally, the processor cores are meant to process 1 instruction at a time. So let’s say, you’re playing a video somewhere on a single-core machine. Does it mean you will not get any notification from your mail app that is running in the background? No, your background processes are doing their job nicely. But why is that? Didn’t I tell you that a single core can run one instruction at a time? How is it possible? Ah well, that’s the main job of an Operating System (OS). This job is known as &lt;a href="https://en.wikipedia.org/wiki/Context_switch" rel="noopener noreferrer"&gt;Context Switching&lt;/a&gt;. All these processes happening not necessarily at the same time but in a scheduled manner. Operating system schedules processes for execution. Let’s say for simplicity's sake, we have 3 processes happening.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1mmeue8uj6ygczy037ii.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1mmeue8uj6ygczy037ii.png" alt="Round-Robin scheduling" width="576" height="359"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If the &lt;a href="https://en.wikipedia.org/wiki/Scheduling_%28computing%29" rel="noopener noreferrer"&gt;Scheduler&lt;/a&gt; schedules the processes like the figure above, the CPU will execute &lt;strong&gt;Process 1.&lt;/strong&gt; Then after a certain amount of time, move to &lt;strong&gt;Process 2&lt;/strong&gt;, then &lt;strong&gt;3&lt;/strong&gt;, then again &lt;strong&gt;1&lt;/strong&gt;. You get the idea. So when OS moves from one process to another, that act of switching is called &lt;a href="https://en.wikipedia.org/wiki/Context_switch" rel="noopener noreferrer"&gt;Context Switching&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdp14xivrve324ahbsrcf.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdp14xivrve324ahbsrcf.png" alt="OS context switching" width="800" height="430"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the figure above, we see Process A and B, two processes are scheduled. CPU processing &lt;strong&gt;Process A&lt;/strong&gt;. While it’s not finished, OS  stopped that task and make the CPU process: &lt;strong&gt;Process B&lt;/strong&gt;. Whether or not &lt;strong&gt;Process B&lt;/strong&gt; is finished, it moved back to &lt;strong&gt;Process A&lt;/strong&gt; again. That’s the operating system, doing its main job. But all these activities happening so fast, from the user's perspective, it feels at the same time. The user has the impression of parallelism. It gives the illusion of parallel execution even though it’s not.&lt;/p&gt;

&lt;h2&gt;
  
  
  Concurrent
&lt;/h2&gt;

&lt;p&gt;So first thing first, when we talk about concurrency, concurrent execution is not necessarily executing tasks at the same time. Like the discussion above with a single-core CPU. When we have 2 tasks scheduled, at a given point in time we can say that, either task 1, or task 2 getting executed. Not both. OS scheduler &amp;amp; context-switcher decides how the CPU will finish both tasks.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fagnqhi3effspynglx500.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fagnqhi3effspynglx500.png" alt="At a given point in time, only one task gets processed." width="469" height="302"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;From the figure above, we can see that, while Task 1 is not finished, Task 2 is getting processed. That's the key difference with Parallel execution which we will talk about in a sec. Yes, Task 2 is running while Task 1 is not finished yet, but at that time, Task 1 stopped. The state (code, memory, registry, unique values, etc) of Task 1 is frozen and saved somewhere by Context Switcher for later use when it will go back to Task 1.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;Concurrency means executing multiple tasks at the same time but not necessarily simultaneously.&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Parallel
&lt;/h2&gt;

&lt;p&gt;The key point of how parallel is different from concurrent is: &lt;strong&gt;for Parallel, we need different hardware&lt;/strong&gt;. It can be a different core or an entirely different machine. From above, if we bring the same example for parallel we can see the execution like the figure below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F265t3yvvamequyopoi2x.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F265t3yvvamequyopoi2x.png" alt="At a given point in time, multiple tasks get processed." width="435" height="302"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;While Task 1 is getting processed, at a certain point Task 2 started &lt;strong&gt;without&lt;/strong&gt; Task 1 getting stopped. They both running at the same time. Even, parallelism does not require two tasks to exist. It literally physically run parts of tasks or, multiple tasks, at the same time using the multi-core infrastructure of CPU, by assigning one core to each task or sub-task.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;Parallelism is a specific kind of concurrency where tasks are really executed simultaneously.&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  Summary
&lt;/h2&gt;

&lt;p&gt;Even though concurrent &amp;amp; parallel both will finish the tasks significantly faster, when it goes to parallel, it will finish a bit faster than concurrent (depending on amount &amp;amp; types of tasks).&lt;/p&gt;

&lt;p&gt;But now you might think, why concurrent then? While it's not running multiple tasks at the same time. Isn't it better if we run tasks just sequentially and forget about concurrency? Well, there are some benefits to concurrency. I will talk about those some other time.&lt;/p&gt;

&lt;p&gt;So for today, that's all about Concurrency &amp;amp; Parallelism, a very important concept. Hope you will get it simpler now when either of these is in the conversation.&lt;/p&gt;

&lt;p&gt;Happy Learning !!!&lt;/p&gt;

</description>
      <category>concurrency</category>
      <category>parallelism</category>
      <category>os</category>
    </item>
    <item>
      <title>Get productive with docker using: lazydocker</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Sun, 20 Feb 2022 05:38:52 +0000</pubDate>
      <link>https://dev.to/tahsinature/get-productive-with-docker-using-lazydocker-4on2</link>
      <guid>https://dev.to/tahsinature/get-productive-with-docker-using-lazydocker-4on2</guid>
      <description>&lt;p&gt;When you manage docker containers on a server, you typically have two choices:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Install &amp;amp; deploy a web-based GUI&lt;/li&gt;
&lt;li&gt;Manage your containers from command line&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Wouldn't it be nice if there was something in between? If we could manage the containers &amp;amp; images right from the terminal in a better and faster way? That's when &lt;a href="https://github.com/jesseduffield/lazydocker" rel="noopener noreferrer"&gt;lazydocker&lt;/a&gt; comes into the rescue.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/jesseduffield/lazydocker" rel="noopener noreferrer"&gt;lazydocker&lt;/a&gt; is a simple, open-source, terminal based UI for both docker and docker-compose written in &lt;a href="https://golang.org/" rel="noopener noreferrer"&gt;Go&lt;/a&gt;. It makes managing your containers &amp;amp; images from your command line really simple.&lt;/p&gt;

&lt;p&gt;To install &lt;a href="https://github.com/jesseduffield/lazydocker" rel="noopener noreferrer"&gt;lazydocker&lt;/a&gt;, just follow the instruction from official repository. Right after that optionally, you can create an alias to start &lt;a href="https://github.com/jesseduffield/lazydocker" rel="noopener noreferrer"&gt;lazydocker&lt;/a&gt; easily. In my case it's like this:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpbwbg2r682agubzal8ru.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpbwbg2r682agubzal8ru.png" alt="alias-preview" width="296" height="239"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The highlighting features from &lt;a href="https://github.com/jesseduffield/lazydocker.git" rel="noopener noreferrer"&gt;lazydocker&lt;/a&gt; are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;viewing the state of your docker or docker-compose container environment at a glance&lt;/li&gt;
&lt;li&gt;viewing logs for a container/service&lt;/li&gt;
&lt;li&gt;viewing ascii graphs of your containers' metrics so that you can not only feel but also look like a developer&lt;/li&gt;
&lt;li&gt;customizing those graphs to measure nearly any metric you want&lt;/li&gt;
&lt;li&gt;attaching to a container/service&lt;/li&gt;
&lt;li&gt;restarting/removing/rebuilding containers/services&lt;/li&gt;
&lt;li&gt;viewing the ancestor layers of a given image&lt;/li&gt;
&lt;li&gt;pruning containers, images, or volumes that are hogging up disk space&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fgithub.com%2Ftahsinature%2Flazydocker%2Fblob%2Fmaster%2Fdocs%2Fresources%2Fdemo3.gif%3Fraw%3Dtrue" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fgithub.com%2Ftahsinature%2Flazydocker%2Fblob%2Fmaster%2Fdocs%2Fresources%2Fdemo3.gif%3Fraw%3Dtrue" alt="lazydocker-demo" width="800" height="400"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;And the fact that, all of these you can do with some fantastic keyboard shortcuts in a matter of seconds, is just awesome.&lt;/p&gt;

&lt;p&gt;So, if you don't want to deal with the complications of the standard CLI commands of docker, &lt;a href="//git@github.com:tahsinature/lazydocker.git"&gt;lazydocker&lt;/a&gt; is a great handy little tool for you.&lt;/p&gt;

&lt;p&gt;And finally, don't think: you're being lazy by using this tool. You're being productive and efficient. So what are you waiting for more? Go, give it a shot.&lt;/p&gt;

&lt;p&gt;Happy productive hours!&lt;br&gt;
Thanks &amp;amp; take care!&lt;/p&gt;

</description>
      <category>docker</category>
      <category>cli</category>
      <category>productivity</category>
      <category>terminal</category>
    </item>
    <item>
      <title>Secure your traefik dashboard with HTTPS and Basic Auth</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Fri, 10 Dec 2021 01:25:57 +0000</pubDate>
      <link>https://dev.to/tahsinature/secure-your-traefik-dashboard-with-https-and-basic-auth-nkh</link>
      <guid>https://dev.to/tahsinature/secure-your-traefik-dashboard-with-https-and-basic-auth-nkh</guid>
      <description>&lt;h3&gt;
  
  
  Intro
&lt;/h3&gt;

&lt;p&gt;When I created my first droplet at &lt;a href="https://www.digitalocean.com/" rel="noopener noreferrer"&gt;DigitalOcean&lt;/a&gt;, I needed a service discovery. At that time I had no idea how to deal with it. Eventually I went for &lt;a href="https://www.nginx.com/" rel="noopener noreferrer"&gt;nginx&lt;/a&gt;. But not knowing the concept, syntax, workaround I was having difficult time. Then I discovered &lt;a href="https://github.com/nginx-proxy/nginx-proxy" rel="noopener noreferrer"&gt;nginx-proxy&lt;/a&gt; which made the process a bit easier as there was few app/services on my droplet running in docker. &lt;a href="https://github.com/nginx-proxy/nginx-proxy" rel="noopener noreferrer"&gt;nginx-proxy&lt;/a&gt; adjusts the configuration automatically based on environment variable.&lt;/p&gt;

&lt;p&gt;But, when I discovered &lt;a href="https://traefik.io/" rel="noopener noreferrer"&gt;traefik&lt;/a&gt;, everything changed. As it has yaml supported configuration, easy to start-with behavior and fully docker support: it became my favorite service discovery tool.&lt;/p&gt;




&lt;h3&gt;
  
  
  Dashboard
&lt;/h3&gt;

&lt;p&gt;Traefik provides a nice looking dashboard to manage and observe configuration to routers and services. It's relatively easy to setup TLS with &lt;a href="https://letsencrypt.org/" rel="noopener noreferrer"&gt;Let's Encrypt&lt;/a&gt; to a router by configuring traefik. However, it was a bit tricky for me to setup TLS for the dashboard itself.&lt;/p&gt;




&lt;h3&gt;
  
  
  Add TLS
&lt;/h3&gt;

&lt;p&gt;Here is the configuration for docker-compose labels:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;labels:
  traefik.enable: true
  traefik.http.routers.traefik_https.rule: Host(`traefik.example.com`)
  traefik.http.routers.traefik_https.entrypoints: websecure
  traefik.http.routers.traefik_https.tls: true
  traefik.http.routers.traefik_https.tls.certResolver: myresolver
  traefik.http.routers.traefik_https.service: api@internal
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After putting the above labels in your docker-compose for traefik container, just execute &lt;code&gt;docker-compose up&lt;/code&gt;. As there are changes in the compose file, it will restart the container. As soon as you do this, you will see a new route protected with TLS in your dashboard like below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwirm4jde4flrhb4w0cgp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwirm4jde4flrhb4w0cgp.png" alt="dashboard with new route" width="800" height="504"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;For me the tricky part was naming the service: &lt;code&gt;api@internal&lt;/code&gt;&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h3&gt;
  
  
  Add basic auth
&lt;/h3&gt;

&lt;p&gt;Of course you don't want to keep this dashboard open. In my case I just added basic auth to keep it protected. So add these labels additionally to your docker-compose file for traefik container.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;traefik.http.routers.traefik_https.middlewares: basic-auth-global
traefik.http.middlewares.basic-auth-global.basicauth.users: &amp;lt;username&amp;gt;:&amp;lt;encoded-password&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;I thought it would read the middleware from traefik configuration which is: &lt;code&gt;traefik.yml&lt;/code&gt;. But that was not the case. I had to create the middleware on docker-compose file with label.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h3&gt;
  
  
  Disable insecure mode
&lt;/h3&gt;

&lt;p&gt;Finally, you want to disable insecure mode to prevent access with http. To do so make your trafik api configuration in &lt;code&gt;traefik.yml&lt;/code&gt; like below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;api:
  insecure: false
  dashboard: true
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h3&gt;
  
  
  Conclusion
&lt;/h3&gt;

&lt;p&gt;After doing these works, you will see that your traefik dashboard can't be accessed through http anymore, rather https. And you need to enter username and password for the first time in a browser.&lt;/p&gt;

</description>
      <category>traefik</category>
      <category>https</category>
      <category>tls</category>
      <category>ssl</category>
    </item>
    <item>
      <title>Get lazy with lazygit</title>
      <dc:creator>Tahsin</dc:creator>
      <pubDate>Tue, 23 Nov 2021 14:32:04 +0000</pubDate>
      <link>https://dev.to/tahsinature/get-lazy-with-lazygit-4h37</link>
      <guid>https://dev.to/tahsinature/get-lazy-with-lazygit-4h37</guid>
      <description>&lt;p&gt;As a developer, my assumption is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;You are working with Git literally every hour.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But I wonder, how many times you felt the necessity of a tool that makes the repetitive commands/steps a bit more convenient for the things like:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Seeing the diff&lt;/li&gt;
&lt;li&gt;Quickly stage/unstage files&lt;/li&gt;
&lt;li&gt;Seeing the logs&lt;/li&gt;
&lt;li&gt;A tool to quickly open PR regardless of your SCM&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Well, that's when &lt;a href="https://github.com/jesseduffield/lazygit" rel="noopener noreferrer"&gt;lazygit&lt;/a&gt; comes to the rescue. It's a terminal UI for git commands written in &lt;a href="https://go.dev/" rel="noopener noreferrer"&gt;Go&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Just install it following the instruction from the official repository. Then optionally you can set an alias in your shell configuration to quickly open lazygit. In my case, it's &lt;code&gt;lg&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frnw0yb2e96g4ahbn3mf9.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frnw0yb2e96g4ahbn3mf9.png" alt="alias preview" width="296" height="239"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Here are the features I use most of the time from this tool.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Stage/unstage like bullet&lt;/li&gt;
&lt;li&gt;Open a PR with a single keypress&lt;/li&gt;
&lt;li&gt;Search through commits&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  Stage/unstage like bullet
&lt;/h3&gt;

&lt;p&gt;Every time performing these type of commands is really a bit painful when a tool like lazygit exists:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;code&gt;git add foo.go&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;git add bar.js&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;git logs&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;git diff foo.go&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;With &lt;a href="https://github.com/jesseduffield/lazygit" rel="noopener noreferrer"&gt;lazygit&lt;/a&gt; you can quickly see through the changed files and stage/unstage them accordingly. As well as, you can see the changes on each file very easily.&lt;/p&gt;

&lt;h3&gt;
  
  
  Open a PR with a single keypress
&lt;/h3&gt;

&lt;p&gt;This is my favorite feature of this tool. Because every time I commit something and want to create PR/MR, I have to do a bunch of repetitive clicks here and there. On top of that, sometimes I have to work with GitHub, sometimes GitLab. So even if I wanna use the GitHub CLI tool &lt;a href="https://github.com/github/hub" rel="noopener noreferrer"&gt;&lt;code&gt;hub&lt;/code&gt;&lt;/a&gt; or GitLab CLI tool &lt;a href="https://glab.readthedocs.io/en/latest/" rel="noopener noreferrer"&gt;&lt;code&gt;glab&lt;/code&gt;&lt;/a&gt;, I am ending up using two different tools. So it's nice when I can open PR/MR just by a shortcut within a second or two regardless of what SCM I am on.&lt;/p&gt;

&lt;h3&gt;
  
  
  Search through commits
&lt;/h3&gt;

&lt;p&gt;When I have to search through a bunch of commits, lazygit comes very handy. Altho there are other tools that exist as well. But I end up utilizing this tool a lot in this case it's I don't have to open another tool or even VS Code for this.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/jesseduffield/lazygit" rel="noopener noreferrer"&gt;lazygit&lt;/a&gt; is open-source. And easy to download and install, so definitely give it a go!&lt;/p&gt;

</description>
      <category>git</category>
      <category>productivity</category>
      <category>terminal</category>
      <category>cli</category>
    </item>
  </channel>
</rss>
