<?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: Olivia Mattiazzo</title>
    <description>The latest articles on DEV Community by Olivia Mattiazzo (@oliviamattiazzo).</description>
    <link>https://dev.to/oliviamattiazzo</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%2F542114%2F6694fb5c-1d1a-4642-ba7c-ba2ca8629666.png</url>
      <title>DEV Community: Olivia Mattiazzo</title>
      <link>https://dev.to/oliviamattiazzo</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/oliviamattiazzo"/>
    <language>en</language>
    <item>
      <title>Understanding Kubernetes Components – Volumes</title>
      <dc:creator>Olivia Mattiazzo</dc:creator>
      <pubDate>Wed, 25 Sep 2024 11:00:00 +0000</pubDate>
      <link>https://dev.to/oliviamattiazzo/understanding-kubernetes-components-volumes-1ij7</link>
      <guid>https://dev.to/oliviamattiazzo/understanding-kubernetes-components-volumes-1ij7</guid>
      <description>&lt;p&gt;Having studied Docker last year, initially through &lt;a href="https://www.alura.com.br/curso-online-docker-e-docker-compose" rel="noopener noreferrer"&gt;a course on Alura&lt;/a&gt;, was the starting point for my interest in DevOps culture to flourish. Eventually, in 2021, I was awarded the &lt;a href="https://www.youtube.com/watch?v=0WVADNxcm3w&amp;amp;ab_channel=LINUXtips" rel="noopener noreferrer"&gt;#ChamaAsMinas&lt;/a&gt; program, promoted by the &lt;a href="https://www.linuxtips.io/" rel="noopener noreferrer"&gt;LinuxTips&lt;/a&gt; school, and received the &lt;a href="https://www.linuxtips.io/certifica%C3%A7%C3%B5es" rel="noopener noreferrer"&gt;Containers Expert&lt;/a&gt; training completely free of charge. Besides solidifying my knowledge of Docker, I began learning about Kubernetes and, wow... &lt;strong&gt;it’s a lot&lt;/strong&gt;. In one of the classes, we were introduced to several different concepts, and I’m writing this series of posts because I felt the need to dive deeper into them. So, I'm inviting you all to join me in my next mission: &lt;strong&gt;understanding Kubernetes components – Volumes!&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2jeqfj0tsy8cle3ce8av.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2jeqfj0tsy8cle3ce8av.gif" alt="A cat typing on a laptop"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  What components will this series of posts cover?
&lt;/h2&gt;

&lt;p&gt;If you, like me, are taking the Descomplicating Kubernetes training: today is (almost) your lucky day. I've summarized some of the components explained on Day 4 of the course. For each component, my goal is to describe:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Its definition&lt;/li&gt;
&lt;li&gt;Examples of usage&lt;/li&gt;
&lt;li&gt;Possible related commands&lt;/li&gt;
&lt;li&gt;A snippet of the corresponding creation YAML and/or related YAML&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;As I start writing this post, I’ve just finished studying this part of the course and, honestly, I’m a bit nervous about the final quiz. 😅 Personally, &lt;strong&gt;I find Kubernetes much harder to understand than Docker&lt;/strong&gt;, but onward we go!&lt;/p&gt;

&lt;p&gt;However, if you're not taking this course, here are the components I plan to cover:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Volumes &lt;strong&gt;(in this very post!)&lt;/strong&gt;

&lt;ul&gt;
&lt;li&gt;EmptyDir&lt;/li&gt;
&lt;li&gt;Persistent Volume&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Cronjobs &amp;amp; Secrets (in the next one)&lt;/li&gt;

&lt;/ul&gt;




&lt;h2&gt;
  
  
  Volumes in Kubernetes
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Definition
&lt;/h3&gt;

&lt;p&gt;First and foremost, to put it simply, &lt;strong&gt;a volume is nothing more than a directory accessed by the containers of a Pod, which contains data&lt;/strong&gt;. If you're a developer and need a rough analogy, we can say that your Pod and its containers are like an application, and the volume would be its database.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The main utility of a volume is to make your containers less ephemeral&lt;/strong&gt;. For example, you have your cluster with its pods, and one of the existing containers restarts due to some issue. If there is no volume associated with this container, it will come back “clean,” just as it was initially created. Therefore, &lt;strong&gt;volumes are used to store any type of information that can help you avoid losing work if something goes wrong&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Docker already has the concept of volumes, but within Kubernetes, this is expanded: &lt;strong&gt;there are many different types of volumes tailored to various uses, and pods can use as many volumes as needed simultaneously&lt;/strong&gt;. Primarily, Kubernetes volumes can be divided into two categories: &lt;strong&gt;ephemeral&lt;/strong&gt; volumes, whose existence is tied to the pod’s existence; and &lt;strong&gt;persistent&lt;/strong&gt; volumes, which continue to exist regardless of whether the pod is still running or has been deleted. &lt;strong&gt;However, no matter the volume type, the data will always be preserved even if the containers within that pod are restarted&lt;/strong&gt;, as they are tied to the pod, not to the containers associated with it.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://i.giphy.com/media/Rh4UZDcPrxF5vhKfaD/giphy.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://i.giphy.com/media/Rh4UZDcPrxF5vhKfaD/giphy.gif"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  EmptyDir
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Definition
&lt;/h3&gt;

&lt;p&gt;As explained earlier, EmptyDir is a type of Kubernetes volume and falls under the group of &lt;strong&gt;ephemeral volumes&lt;/strong&gt;, as it doesn’t handle data persistence. So be careful: &lt;strong&gt;when you delete your pod, everything saved in this volume will be lost&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;This volume is created as soon as we assign a pod to an existing node. It always starts empty, and &lt;strong&gt;anything stored here can be accessed by all containers within the pod&lt;/strong&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Usage Example
&lt;/h3&gt;

&lt;p&gt;EmptyDir is the ideal volume to use in situations such as:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;When you need a &lt;strong&gt;“scratch space” for your algorithm&lt;/strong&gt; (e.g., sorting algorithms)&lt;/li&gt;
&lt;li&gt;When you need a place to store &lt;strong&gt;recovery points for the containers&lt;/strong&gt; within your pod&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Setting Up a Pod with an EmptyDir Volume
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;v1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Pod&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;test-pd&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;containers&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;image&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;k8s.gcr.io/test-webserver&lt;/span&gt;
    &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;test-container&lt;/span&gt;
    &lt;span class="na"&gt;volumeMounts&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;mountPath&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;/cache&lt;/span&gt;
      &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;cache-volume&lt;/span&gt;
  &lt;span class="na"&gt;volumes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;cache-volume&lt;/span&gt;
   &lt;span class="na"&gt;emptyDir&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  ⚠ Reminder!
&lt;/h4&gt;

&lt;p&gt;To create any type of Kubernetes component from a YAML file, just run the following command:&lt;br&gt;
&lt;code&gt;kubectl create -f filename.yaml&lt;/code&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Persistent Volume
&lt;/h2&gt;

&lt;p&gt;First of all, it's important to clarify that there are &lt;strong&gt;"two concepts" associated with this single name, Persistent Volume&lt;/strong&gt;. The first is more general and defines the Persistent Volume component as a type of volume and what it provides. Within the Persistent Volume component, there is also a "subcomponent" called Persistent Volume.&lt;/p&gt;

&lt;p&gt;Confusing, right? Let me explain it a bit better:&lt;/p&gt;


  &lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2021%2F08%2Fgif_pv.gif"&gt;

&lt;h3&gt;
  
  
  Definition
&lt;/h3&gt;

&lt;p&gt;Anyway, there is a subsystem within Kubernetes called Persistent Volume, which &lt;strong&gt;provides an API for users and administrators that abstracts the details of how volumes are provisioned and consumed&lt;/strong&gt;. Within this Persistent Volumes subsystem, there are two main components that handle this process: Persistent Volume and Persistent Volume Claim.&lt;/p&gt;
&lt;h3&gt;
  
  
  Usage Example
&lt;/h3&gt;

&lt;p&gt;Given that applications are increasingly cloud-based, when someone wants to consume data from an API, for example, it’s necessary to integrate with a specific storage system (Amazon, Azure, etc.). &lt;strong&gt;Kubernetes, through Persistent Volume, aims to change this by providing an abstraction&lt;/strong&gt;. This allows for connecting to a variety of cloud systems without needing explicit dependencies for each system.&lt;/p&gt;

&lt;p&gt;Thus, with Persistent Volume, &lt;strong&gt;consuming data from a cloud system becomes more straightforward and robust&lt;/strong&gt;, significantly reducing related costs. It also makes it easier to migrate between cloud systems and/or adopt strategies involving multiple cloud systems.&lt;/p&gt;

&lt;p&gt;⚠ &lt;strong&gt;Note!&lt;/strong&gt; Given the more detailed definition, let’s agree on this: &lt;strong&gt;when I’m referring to the Persistent Volume subsystem, I’ll use the full name. When referring to the component within the subsystem, I’ll use the acronym PV&lt;/strong&gt;. Got it?&lt;/p&gt;
&lt;h2&gt;
  
  
  Persistent Volume (the subcomponent)
&lt;/h2&gt;
&lt;h3&gt;
  
  
  Definition
&lt;/h3&gt;

&lt;p&gt;This component, within the subsystem we mentioned, &lt;strong&gt;is responsible for providing the actual storage for the volumes we want to create&lt;/strong&gt;. It is part of the cluster just like any other resource; just as a node is a resource, a PV is too. Unlike EmptyDir, &lt;strong&gt;a PV is a persistent volume&lt;/strong&gt; (obviously), meaning its content is not tied to the lifecycle of a pod; after deleting the pod that uses the volume, the content remains. The PV is also the API object responsible for capturing the details of the storage implementation (such as NFS, iSCSI, or a cloud provider).&lt;/p&gt;
&lt;h3&gt;
  
  
  Configuring a PV with NFS
&lt;/h3&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;v1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;PersistentVolume&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;primeiro-pv&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;capacity&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;storage&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;1Gi&lt;/span&gt;
  &lt;span class="na"&gt;accessModes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;ReadWriteMany&lt;/span&gt;
  &lt;span class="na"&gt;persistentVolumeReclaimPolicy&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Retain&lt;/span&gt;
  &lt;span class="na"&gt;nfs&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;/opt/dados&lt;/span&gt;
    &lt;span class="na"&gt;server&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;10.138.0.2&lt;/span&gt;
    &lt;span class="na"&gt;readOnly&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;⚠ &lt;strong&gt;Note!&lt;/strong&gt; To configure the PV with NFS, it’s also necessary to set up NFS itself. You can find the complete &lt;a href="https://github.com/badtuxx/DescomplicandoKubernetes/blob/main/day-4/DescomplicandoKubernetes-Day4.md#persistent-volume" rel="noopener noreferrer"&gt;step-by-step guide&lt;/a&gt; for creating this component in the &lt;em&gt;Descomplicando Kubernetes&lt;/em&gt; repository.&lt;/p&gt;
&lt;h3&gt;
  
  
  Related Commands
&lt;/h3&gt;

&lt;p&gt;Unlike EmptyDir, with PVs we can use some &lt;code&gt;kubectl&lt;/code&gt; commands for viewing and managing them. Here are a few useful commands:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;kubectl get pv
kubectl describe pv [your-pv-name]
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Persistent Volume Claim
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Definition
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;The PVC is the component that actually binds a PV to a pod.&lt;/strong&gt; As the name suggests, &lt;strong&gt;it’s through the PVC that you can “claim” access to a PV&lt;/strong&gt;. Just as a pod consumes resources from a node, the PVC will consume resources from a PV. Similarly, just as a pod can request specific levels of resources like CPU and memory, the PVC can specify the size and access mode it needs from the volume.&lt;/p&gt;

&lt;h4&gt;
  
  
  Access Modes
&lt;/h4&gt;

&lt;p&gt;Each volume can and should be mounted using &lt;strong&gt;only one&lt;/strong&gt; access mode, even though it may support multiple modes. The available access modes are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;ReadWriteOnce&lt;/code&gt; – Only a single node can perform read and write operations.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;ReadOnlyMany&lt;/code&gt; – The volume will be read-only for all nodes.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;ReadWriteMany&lt;/code&gt; – All nodes can perform read and write operations.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Configuring a PVC
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;v1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;PersistentVolumeClaim&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;primeiro-pvc&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;accessModes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;ReadWriteMany&lt;/span&gt;
  &lt;span class="na"&gt;resources&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;requests&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="na"&gt;storage&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;800Mi&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Related Commands
&lt;/h3&gt;

&lt;p&gt;Just like with PVs, we can use some &lt;code&gt;kubectl&lt;/code&gt; commands to view and manage PVCs.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;kubectl get pvc&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  A diagram to simplify the process
&lt;/h2&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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2021%2F08%2Fdiagrama_pv.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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2021%2F08%2Fdiagrama_pv.png"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  ✔ Links consulted
&lt;/h2&gt;

&lt;p&gt;📕 &lt;a href="https://kubernetes.io/docs/concepts/storage/volumes/" rel="noopener noreferrer"&gt;Documentação do Kubernetes – Volumes&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📘 &lt;a href="https://github.com/badtuxx/DescomplicandoKubernetes/blob/main/day-4/DescomplicandoKubernetes-Day4.md" rel="noopener noreferrer"&gt;Repositório do treinamento Descomplicando Kubernetes&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📗 &lt;a href="https://community.suse.com/posts/stupid-simple-kubernetes-persistent-volumes-explained" rel="noopener noreferrer"&gt;Stupid Simple Kubernetes — Persistent Volumes Explained&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  📩 A Last Message
&lt;/h2&gt;

&lt;p&gt;Did you like the text? Do you have anything to add? Any constructive criticism? Feedback? Suggestions? Requests? Feel free to contact me via email (&lt;a href="mailto:oli.pmatt@gmail.com"&gt;oli.pmatt@gmail.com&lt;/a&gt;), LinkedIn (&lt;a href="https://www.linkedin.com/in/oliviamattiazzo/" rel="noopener noreferrer"&gt;/in/oliviamattiazzo&lt;/a&gt;) or through the comments section below! I’d be delighted to chat with you! ✨&lt;/p&gt;

&lt;p&gt;You can also check the &lt;a href="https://oliviamattiazzo.dev/2021/08/16/entendendo-componentes-kubernetes-volumes/" rel="noopener noreferrer"&gt;original post (in PT-BR)&lt;/a&gt; at my blog: &lt;a href="https://oliviamattiazzo.dev/" rel="noopener noreferrer"&gt;oliviamattiazzo.dev&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://ko-fi.com/Q5Q4I8JOP" rel="noopener noreferrer"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fko-fi.com%2Fimg%2Fgithubbutton_sm.svg" alt="ko-fi"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  ⏰ Other posts
&lt;/h2&gt;

&lt;p&gt;💎 &lt;a href=""&gt;A Study on Git Rebase&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;💎 &lt;a href="https://dev.to/oliviamattiazzo/super-helpful-gem-syntaxsuggest-1a2p"&gt;Super-helpful gem: syntax_suggest&lt;/a&gt;&lt;/p&gt;




</description>
      <category>kubernetes</category>
      <category>devops</category>
      <category>beginners</category>
    </item>
    <item>
      <title>A Study on Git Rebase</title>
      <dc:creator>Olivia Mattiazzo</dc:creator>
      <pubDate>Wed, 18 Sep 2024 11:00:00 +0000</pubDate>
      <link>https://dev.to/oliviamattiazzo/a-study-on-git-rebase-3384</link>
      <guid>https://dev.to/oliviamattiazzo/a-study-on-git-rebase-3384</guid>
      <description>&lt;p&gt;It's been a while since I wanted to research and write about the difference between &lt;code&gt;git push --force&lt;/code&gt; and &lt;code&gt;git push --force-with-lease&lt;/code&gt;. Today, I started looking into these two commands and also thought: hmm, why not include an introduction to &lt;code&gt;git rebase&lt;/code&gt; as well? After all, it's such a feared tool, surrounded by so many myths, and personally, I didn't know much about it—just that I need to use it. So, I decided to combine my curiosity with the opportunity to create a study on &lt;code&gt;git rebase&lt;/code&gt; and share it here with everyone!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://i.giphy.com/media/zQOmyYc8TXzSBfrTFb/giphy.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://i.giphy.com/media/zQOmyYc8TXzSBfrTFb/giphy.gif" alt="Merge, Squash or Rebase?"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Conceptually, what is Git Rebase?
&lt;/h2&gt;

&lt;p&gt;First, let me clarify that &lt;code&gt;rebase&lt;/code&gt; is one of the methods available in Git for updating branches, along with &lt;code&gt;merge&lt;/code&gt; (if there are others, let me know, because I can't remember 😅). When you create a feature branch—this special place where you'll start developing a new feature for a system—you do so from the latest commit of a main branch. The characteristic of &lt;code&gt;rebase&lt;/code&gt;, unlike &lt;code&gt;merge&lt;/code&gt;, is that &lt;strong&gt;it changes the base of your branch from one commit to another&lt;/strong&gt;, making it appear as though you created your feature branch from a different, more recent starting point than the one where you initially started your work.&lt;/p&gt;

&lt;p&gt;A bit confusing, right? Hold on, I'll try to clarify with a diagram.&lt;/p&gt;

&lt;h3&gt;
  
  
  A Git Rebase in 3 Acts
&lt;/h3&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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2022%2F10%2F1-1024x1024.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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2022%2F10%2F1-1024x1024.png" alt="Act I - New Branch"&gt;&lt;/a&gt;&lt;br&gt;Act I - New Branch
  &lt;/p&gt;

&lt;p&gt;The person speaking here went ahead and created a new branch from the main branch of a project. The initial commit of my branch, which we’ll call &lt;code&gt;branch-oli&lt;/code&gt;, is commit &lt;code&gt;wap662&lt;/code&gt;, which includes everything from the main branch up to that point.&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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2022%2F10%2F2-1024x1024.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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2022%2F10%2F2-1024x1024.png" alt="Act II - Updated branch"&gt;&lt;/a&gt;&lt;br&gt;Act II - Updated branch
  &lt;/p&gt;

&lt;p&gt;The next day, a colleague merged their feature branch, &lt;code&gt;branch-do-colega&lt;/code&gt;, into the main branch. As a result, the main branch was updated, and its latest commit, &lt;strong&gt;which will serve as the base for any new feature branches&lt;/strong&gt;, is now commit &lt;code&gt;sus0sz&lt;/code&gt;. However, my branch, &lt;code&gt;branch-oli&lt;/code&gt;, became outdated and needs to be updated with the latest changes from the main branch. I can do this in two ways: using &lt;code&gt;git merge&lt;/code&gt; or &lt;code&gt;git rebase&lt;/code&gt;. Today, I'll use rebase: &lt;strong&gt;in other words, I'll make &lt;code&gt;branch-oli&lt;/code&gt; have &lt;code&gt;sus0sz&lt;/code&gt; as its base commit.&lt;/strong&gt;&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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2022%2F10%2F3-1024x1024.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%2Foliviamattiazzo.dev%2Fwp-content%2Fuploads%2F2022%2F10%2F3-1024x1024.png" alt="Act III - Rebase done"&gt;&lt;/a&gt;&lt;br&gt;Act III - Rebase done
  &lt;/p&gt;

&lt;p&gt;Awesome! Our code is now fully updated.&lt;/p&gt;

&lt;h2&gt;
  
  
  So, what are the advantages of Git Rebase?
&lt;/h2&gt;

&lt;p&gt;The most practical advantage of rebase is that &lt;strong&gt;it results in a cleaner merge of your feature branch into the main branch&lt;/strong&gt;. The poetic advantage is this: the commits in the main branch are largely composed of merges from other branches. When these merges come with descriptive titles and are done with care, the commits in the main branch start telling the story of a system. &lt;strong&gt;Rebase helps make this story more linear, making it more coherent and easier to follow.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;When it comes to tracking down which feature branch introduced a bug into the production codebase, having a tidy and organized commit history makes it much easier to find the culprit.&lt;/p&gt;

&lt;h3&gt;
  
  
  How is this done?
&lt;/h3&gt;

&lt;p&gt;Git organizes this “story” by creating new commits from the existing ones and applying them to the base (which, in this case, is your feature branch). Although the branch may appear unchanged to us, it actually consists of &lt;strong&gt;completely new and different commits&lt;/strong&gt; after the rebase.&lt;/p&gt;

&lt;h2&gt;
  
  
  Types of Git Rebase
&lt;/h2&gt;

&lt;p&gt;There are two types of Git Rebase available for use, each with its own advantages and disadvantages.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Standard Git Rebase:&lt;/strong&gt; When you run the rebase command without any additional flags, it will simply take all the new commits created in a branch and automatically add them in front of the new base commit of your feature branch. This process is straightforward and doesn’t require much thought or concern.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Interactive Git Rebase:&lt;/strong&gt; This occurs when you include the &lt;code&gt;-i&lt;/code&gt; flag with the rebase command in the console/terminal. Interactive rebase allows you &lt;strong&gt;to modify commits made during development&lt;/strong&gt;, including splitting, removing, or reordering them.&lt;/p&gt;

&lt;p&gt;With interactive rebase, you can focus on developing your feature without worrying about the commit messages or their order. You can make necessary changes as you go, and before merging into the main branch, you can tidy up the commit history using the &lt;code&gt;-i&lt;/code&gt; flag.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://i.giphy.com/media/1ziYAKJRHZ4zymDXpS/giphy.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://i.giphy.com/media/1ziYAKJRHZ4zymDXpS/giphy.gif" alt="I wanna break free videoclip"&gt;&lt;/a&gt;&lt;br&gt;Leave the Cleanup for Later!
  &lt;/p&gt;

&lt;h2&gt;
  
  
  Main Differences Between Git Merge and Git Rebase
&lt;/h2&gt;

&lt;p&gt;First and foremost, it’s important to note that both commands address the same issue: &lt;strong&gt;integrating code changes between branches&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;The primary difference is that &lt;strong&gt;Git Merge brings in the new code independently and integrates it through a single commit&lt;/strong&gt; into your feature branch. It is a &lt;strong&gt;non-destructive operation&lt;/strong&gt;, meaning there's little risk of making unwanted changes to the branch you're working on.&lt;/p&gt;

&lt;p&gt;However, &lt;strong&gt;Merge can also introduce extra commits beyond those you've created&lt;/strong&gt;. If the main branch is very active and you need to perform multiple merges throughout the development of your feature, these extra commits can clutter the “history” of your branch.&lt;/p&gt;

&lt;p&gt;On the other hand, &lt;strong&gt;Git Rebase rewrites the history of your project&lt;/strong&gt;, as explained earlier. This is beneficial for clarity and a clean history but can have a downside: &lt;strong&gt;it becomes less clear when new changes were added to the feature branch&lt;/strong&gt;, leading to less context compared to using Git Merge.&lt;/p&gt;

&lt;h2&gt;
  
  
  About Force Pushes During Git Rebase
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Why do we need --force push during a rebase?
&lt;/h3&gt;

&lt;p&gt;Git has a rule called the &lt;strong&gt;Fast-Forward Rule&lt;/strong&gt;: essentially, it will reject any commit if the remote branch is not an "ancestor" of what's on your local branch. &lt;strong&gt;Rebase breaks this rule&lt;/strong&gt; because it creates new commits and changes the base of the local branch, which is why we need to use force push to bypass it. The &lt;code&gt;--force&lt;/code&gt; flag will completely ignore the existing history of the feature branch and replace it with what’s on your machine.&lt;/p&gt;

&lt;h3&gt;
  
  
  Difference Between --force and --force-with-lease
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;--force&lt;/code&gt; is a blunt instrument. If someone has made commits while you were doing the Git rebase locally, those changes will be lost forever. However, this can be circumvented with &lt;code&gt;--force-with-lease&lt;/code&gt;, which I translate loosely as &lt;em&gt;forceful with care&lt;/em&gt;: &lt;strong&gt;Git will refuse to update the branch if its state differs from what is expected&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://i.giphy.com/media/MrjMIWrGZFsTS/giphy.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://i.giphy.com/media/MrjMIWrGZFsTS/giphy.gif" alt="A man playing with a cat"&gt;&lt;/a&gt;&lt;br&gt;Force into the force push!
  &lt;/p&gt;

&lt;p&gt;In other words, when using &lt;code&gt;--force-with-lease&lt;/code&gt;, Git will first &lt;strong&gt;check if the remote version of your feature branch is the same as the one you rebased or if there are any changes beyond the “re-created” commits&lt;/strong&gt;. If there are additional changes, such as commits made by another developer, the push will be rejected. If there are no additional changes, you can bypass the Fast-Forward Rule without major issues.&lt;/p&gt;

&lt;h2&gt;
  
  
  Main Commands Related to Git Rebase
&lt;/h2&gt;

&lt;p&gt;To perform a rebase:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;git rebase [-i] branch-name
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; The &lt;code&gt;-i&lt;/code&gt; flag is optional and is used for interactive rebases, as explained in the definition above.&lt;/p&gt;

&lt;p&gt;To continue with the changes made:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;git rebase --skip
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Force pushes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;git push --force
git push --force-with-lease
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  ✔ Links consulted
&lt;/h2&gt;

&lt;p&gt;📗&lt;a href="https://www.atlassian.com/git/tutorials/rewriting-history/git-rebase" rel="noopener noreferrer"&gt;git rebase – Atlassian Git Tutorial&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📘&lt;a href="https://jtemporal.com/atualizando-um-branch-com-git-rebase/" rel="noopener noreferrer"&gt;Atualizando um branch com git rebase – Jessica Temporal&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📙&lt;a href="https://blog.betrybe.com/git/git-rebase/#1" rel="noopener noreferrer"&gt;Git rebase: integrando alterações de uma branch em outra, por Daniela Araújo – BeTrybe Blog&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📕&lt;a href="https://www.atlassian.com/git/tutorials/merging-vs-rebasing" rel="noopener noreferrer"&gt;Merging vs. Rebasing – Atlassian Git Tutorial&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📗&lt;a href="https://itnext.io/git-force-vs-force-with-lease-9d0e753e8c41" rel="noopener noreferrer"&gt;Git Force vs Force with Lease, por Mohammad-Ali A’Râbi&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;📘&lt;a href="https://stackoverflow.com/a/52823955" rel="noopener noreferrer"&gt;Essa resposta no Stack Overflow&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  📩 A Last Message
&lt;/h2&gt;

&lt;p&gt;Did you like the text? Do you have anything to add? Any constructive criticism? Feedback? Suggestions? Requests? Feel free to contact me via email (&lt;a href="mailto:oli.pmatt@gmail.com"&gt;oli.pmatt@gmail.com&lt;/a&gt;), LinkedIn (&lt;a href="https://www.linkedin.com/in/oliviamattiazzo/" rel="noopener noreferrer"&gt;/in/oliviamattiazzo&lt;/a&gt;) or through the comments section below! I’d be delighted to chat with you! ✨&lt;/p&gt;

&lt;p&gt;You can also check the &lt;a href="https://oliviamattiazzo.dev/2022/11/13/estudo-sobre-git-rebase/" rel="noopener noreferrer"&gt;original post (in PT-BR)&lt;/a&gt; at my blog: &lt;a href="https://oliviamattiazzo.dev/" rel="noopener noreferrer"&gt;oliviamattiazzo.dev&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://ko-fi.com/Q5Q4I8JOP" rel="noopener noreferrer"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fko-fi.com%2Fimg%2Fgithubbutton_sm.svg" alt="ko-fi"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  ⏰ Other posts
&lt;/h2&gt;

&lt;p&gt;💎 &lt;a href="https://dev.to/oliviamattiazzo/rails-helpers-what-are-they-and-what-are-they-used-for-l38"&gt;Rails Helpers – what are they and what are they used for?&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;💎 &lt;a href="https://dev.to/oliviamattiazzo/super-helpful-gem-syntaxsuggest-1a2p"&gt;Super-helpful gem: syntax_suggest&lt;/a&gt;&lt;/p&gt;

</description>
      <category>git</category>
      <category>rebase</category>
    </item>
    <item>
      <title>Super-helpful gem: syntax_suggest</title>
      <dc:creator>Olivia Mattiazzo</dc:creator>
      <pubDate>Thu, 12 Sep 2024 11:00:00 +0000</pubDate>
      <link>https://dev.to/oliviamattiazzo/super-helpful-gem-syntaxsuggest-1a2p</link>
      <guid>https://dev.to/oliviamattiazzo/super-helpful-gem-syntaxsuggest-1a2p</guid>
      <description>&lt;p&gt;One day at work, Code Climate flagged an error in one of my commits. Honestly, I don't remember exactly what it was, but it was something related to a missing closing parenthesis or brace, something along those lines. The problem was: &lt;strong&gt;I went back to my code and, at first glance, couldn't find exactly where the issue was&lt;/strong&gt;, and there were no additional details anywhere to help. So, I started looking for a solution to better visualize potential syntax errors and &lt;strong&gt;stumbled upon a real gem: &lt;code&gt;syntax_suggest&lt;/code&gt;!&lt;/strong&gt; I thought it would be interesting to write a quick post about it here to document this solution for myself, in case I need to use it again in the future!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwhgimbazvgzk9zxnfqvj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwhgimbazvgzk9zxnfqvj.png" alt="A red gem"&gt;&lt;/a&gt;&lt;br&gt;That method to give you a little help.
  &lt;/p&gt;




&lt;p&gt;First of all, I need to clarify that &lt;strong&gt;I used this gem in a very specific situation&lt;/strong&gt;, more to find a problem than to actually fix it. So, &lt;strong&gt;what I'll present here is the most basic way to use&lt;/strong&gt; this little gem. Finally, you can always find more about it on its &lt;a href="https://github.com/ruby/syntax_suggest" rel="noopener noreferrer"&gt;GitHub repository&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Installation in your Ruby project
&lt;/h2&gt;

&lt;p&gt;Open a console in your Ruby project's folder and install the gem as follows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;gem install syntax_suggest
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Checking the syntax of a file
&lt;/h2&gt;

&lt;p&gt;I already knew which file had the issue thanks to Code Climate, so I went straight to the point with the following command (in the application console):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;syntax_suggest [file-path]

#Example:
syntax_suggest app/services/file_xpto.rb
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;An example of how the response is returned:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Unmatched keyword, missing `end' ?

&amp;gt; 1 class Dog
&amp;gt; 2 def bark
&amp;gt; 4 end
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you need help within the console itself, you can always access the gem's &lt;code&gt;help&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;syntax_suggest --help
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And that's it! A simple and short post, but it was also a quick and easy solution to fix a problem I was facing. I hope it helps you as well!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://i.giphy.com/media/UjCXeFnYcI2R2/giphy.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://i.giphy.com/media/UjCXeFnYcI2R2/giphy.gif"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  ✔ Links consulted
&lt;/h2&gt;

&lt;p&gt;📀 &lt;a href="https://github.com/ruby/syntax_suggest" rel="noopener noreferrer"&gt;&lt;code&gt;syntax_suggest&lt;/code&gt; repository on GitHub&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  📩 A Last Message
&lt;/h2&gt;

&lt;p&gt;Did you like the text? Do you have anything to add? Any constructive criticism? Feedback? Suggestions? Requests? Feel free to contact me via email (&lt;a href="mailto:oli.pmatt@gmail.com"&gt;oli.pmatt@gmail.com&lt;/a&gt;), LinkedIn (&lt;a href="https://www.linkedin.com/in/oliviamattiazzo/" rel="noopener noreferrer"&gt;/in/oliviamattiazzo&lt;/a&gt;) or through the comments section below! I’d be delighted to chat with you! ✨&lt;/p&gt;

&lt;p&gt;You can also check the &lt;a href="https://oliviamattiazzo.dev/2022/12/23/uma-gem-na-roda-syntax-suggest/" rel="noopener noreferrer"&gt;original post (in PT-BR)&lt;/a&gt; at my blog: &lt;a href="https://oliviamattiazzo.dev/" rel="noopener noreferrer"&gt;oliviamattiazzo.dev&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://ko-fi.com/Q5Q4I8JOP" rel="noopener noreferrer"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fko-fi.com%2Fimg%2Fgithubbutton_sm.svg" alt="ko-fi"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  ⏰ Other posts
&lt;/h2&gt;

&lt;p&gt;💎 &lt;a href="https://dev.to/oliviamattiazzo/rails-helpers-what-are-they-and-what-are-they-used-for-l38"&gt;Rails Helpers – what are they and what are they used for?&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  🪪 Credits
&lt;/h2&gt;

&lt;p&gt;The icons used to illustrate this post came from the following IconFinder users:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.iconfinder.com/PixelBuddha" rel="noopener noreferrer"&gt;https://www.iconfinder.com/PixelBuddha&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>rails</category>
      <category>ruby</category>
    </item>
    <item>
      <title>Rails Helpers – what are they and what are they used for?</title>
      <dc:creator>Olivia Mattiazzo</dc:creator>
      <pubDate>Wed, 04 Sep 2024 11:22:28 +0000</pubDate>
      <link>https://dev.to/oliviamattiazzo/rails-helpers-what-are-they-and-what-are-they-used-for-l38</link>
      <guid>https://dev.to/oliviamattiazzo/rails-helpers-what-are-they-and-what-are-they-used-for-l38</guid>
      <description>&lt;p&gt;Has it ever happened to you that you use a concept in your preferred programming language without really understanding why you’re using it? Or what exactly it does? This recently happened to me when I was tasked with refactoring someone else’s code: I didn’t quite understand what Rails &lt;code&gt;modules&lt;/code&gt; were or what &lt;code&gt;Helpers&lt;/code&gt; were for. So, I took some time to study this and prepared this summary on &lt;strong&gt;what Rails Helpers are and what they are used for!&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F01e29s5lqo27ytbu7cc1.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F01e29s5lqo27ytbu7cc1.png" alt="A small elf helper" width="128" height="128"&gt;&lt;/a&gt;&lt;br&gt;That method to give you a little help.
  &lt;/p&gt;




&lt;h2&gt;
  
  
  Organizing the party
&lt;/h2&gt;

&lt;p&gt;In this post, I intend to cover, in the following order:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;A &lt;strong&gt;general explanation of what Rails Helper methods are&lt;/strong&gt; and the best practices associated with them&lt;/li&gt;
&lt;li&gt;Delve into &lt;strong&gt;more details about Ruby Modules&lt;/strong&gt; and their importance within the language&lt;/li&gt;
&lt;li&gt;Touch on the topic of &lt;strong&gt;Composition vs. Inheritance&lt;/strong&gt;, which is always good to keep fresh in mind&lt;/li&gt;
&lt;/ol&gt;




&lt;h2&gt;
  
  
  What are Helpers in Rails?
&lt;/h2&gt;

&lt;p&gt;Helpers are methods primarily used to &lt;strong&gt;share reusable code between the views in your project&lt;/strong&gt;. It's important to note that Helpers don't necessarily need to be created by developers: &lt;strong&gt;there are already some native methods provided by Rails&lt;/strong&gt; to make our lives easier.&lt;/p&gt;

&lt;p&gt;Examples of native Rails Helpers:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="n"&gt;time_ago_in_words&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="no"&gt;Time&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="c1"&gt;# "less than a minute"&lt;/span&gt;

&lt;span class="n"&gt;number_to_human&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;10_000&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="c1"&gt;# "10 Thousand"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Helper methods are also very important when created by programmers themselves, as they help apply the &lt;a href="https://web.archive.org/web/20131204221336/http://programmer.97things.oreilly.com/wiki/index.php/Don't_Repeat_Yourself" rel="noopener noreferrer"&gt;DRY principle&lt;/a&gt; within the project's code. By doing so, &lt;strong&gt;you condense a portion of the logic into a single place&lt;/strong&gt; instead of having it scattered across various parts of the code.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fw93vf863foolt4b1a2ae.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fw93vf863foolt4b1a2ae.png" alt="Clothes hanging on a line" width="128" height="128"&gt;&lt;/a&gt;&lt;br&gt;DRY – Don’t Repeat Yourself
  &lt;/p&gt;

&lt;h2&gt;
  
  
  Writing Your Own Helpers
&lt;/h2&gt;

&lt;p&gt;There is a specific directory for creating your own Helpers in Rails, which is the &lt;code&gt;app/helpers&lt;/code&gt; directory. Inside this folder, you need to create a new file and, within a &lt;code&gt;module&lt;/code&gt;, develop what you need. Everything inside it automatically becomes visible to the &lt;code&gt;views&lt;/code&gt; in your project.&lt;/p&gt;

&lt;p&gt;For example: we went to &lt;code&gt;app/helpers&lt;/code&gt; and created the file &lt;code&gt;user_helper.rb&lt;/code&gt;, which will contain all our user-related helpers. Inside it, we will build the following &lt;code&gt;module&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="k"&gt;module&lt;/span&gt; &lt;span class="nn"&gt;UserHelper&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;format_name&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;user&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;gender&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="s2"&gt;"M"&lt;/span&gt;
      &lt;span class="s2"&gt;"Mr. &lt;/span&gt;&lt;span class="si"&gt;#{&lt;/span&gt;&lt;span class="n"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;name&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;
    &lt;span class="k"&gt;else&lt;/span&gt;
      &lt;span class="s2"&gt;"Mrs. &lt;/span&gt;&lt;span class="si"&gt;#{&lt;/span&gt;&lt;span class="n"&gt;user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;name&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There is also a generic option, useful if your application is small and you need only a few Helpers, for example, which is to put everything inside the &lt;code&gt;ApplicationHelper&lt;/code&gt;. This is a base module in Rails, ready to receive any future helpers you develop.&lt;/p&gt;

&lt;h2&gt;
  
  
  Best Practices for Using Helpers
&lt;/h2&gt;

&lt;h3&gt;
  
  
  When should you use and/or create a helper?
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Whenever you have reusable logic that produces HTML code.&lt;/strong&gt; Most of the time, this involves code related to string formatting or &lt;code&gt;view&lt;/code&gt; elements that are conditional. It's a good idea to encapsulate this logic within a helper to avoid having it scattered and repeated throughout your application.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh237t5wig723336bm43y.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh237t5wig723336bm43y.png" alt="A line messed up" width="128" height="128"&gt;&lt;/a&gt;&lt;br&gt;Organize your stuff
  &lt;/p&gt;

&lt;h3&gt;
  
  
  Use and abuse of parameters
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;It's a way to clearly specify from the beginning what your method needs&lt;/strong&gt;, reducing the risk of encountering errors related to &lt;em&gt;missing variables&lt;/em&gt; while working with information within your helper.&lt;/p&gt;

&lt;h3&gt;
  
  
  Try not to use helpers in Controllers
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://damely-tineo.medium.com/helper-methods-9143cc1826b5" rel="noopener noreferrer"&gt;Some developers believe in the concept of Controller Helpers&lt;/a&gt;, which are helpers more focused on logic rather than presentation. It's also possible to use view helpers directly in controllers by invoking them with the &lt;code&gt;helpers&lt;/code&gt; object. For example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;UsersController&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;index&lt;/span&gt;
    &lt;span class="n"&gt;helpers&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;time_ago_in_words&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="no"&gt;Time&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://www.rubyguides.com/2020/01/rails-helpers/" rel="noopener noreferrer"&gt;RubyGuides&lt;/a&gt; advises caution when doing this, as it can be considered a design problem, suggesting the use of a Ruby object instead, although it doesn't provide further details on why. I also think it's worth noting this warning, and when in doubt, &lt;strong&gt;keep helpers confined to views&lt;/strong&gt;, OK?&lt;/p&gt;

&lt;h2&gt;
  
  
  What are Ruby Modules?
&lt;/h2&gt;

&lt;p&gt;Throughout this article, I've talked a lot about Ruby modules and how important they are when writing helpers. Then I realized that &lt;strong&gt;I didn't know what the heck a Ruby module was&lt;/strong&gt;. So, I did some research and am sharing this important extra bit on what it is and what this useful little keyword is for.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;A module is a Ruby container used to store methods, variables, and constants. It's similar to a class, but unlike a class, a module cannot be instantiated.&lt;/strong&gt; It's somewhat similar to the concept of static in .NET.&lt;/p&gt;

&lt;p&gt;Modules have &lt;strong&gt;two main purposes&lt;/strong&gt; in Ruby:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Creating a namespace&lt;/strong&gt;, that is, grouping logically related objects together, which also helps avoid name conflicts
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Facilitating composition&lt;/strong&gt; within your application&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Ruby, as a programming language, does not support multiple inheritance.&lt;/strong&gt; Therefore, to keep the code scalable and maintainable in the long run, it is necessary to apply the principle of Composition Over Inheritance. Fortunately, Ruby makes composition easier by offering what is called the &lt;strong&gt;&lt;em&gt;Mixing Facility&lt;/em&gt;&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpgb7ftrlpa3gse3t5mci.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpgb7ftrlpa3gse3t5mci.png" alt="Happy dance" width="128" height="128"&gt;&lt;/a&gt;&lt;br&gt;Happy dance!
  &lt;/p&gt;

&lt;p&gt;The Mixing Facility is simply a module being included by another module, or even by another class, using keywords like &lt;code&gt;include&lt;/code&gt;, &lt;code&gt;prepend&lt;/code&gt;, or &lt;code&gt;extend&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Composition vs. Inheritance
&lt;/h2&gt;

&lt;p&gt;Ah, the age-old dilemma for those who program in object-oriented languages &lt;del&gt;and for a paycheck&lt;/del&gt;. &lt;strong&gt;This debate is present from the earliest stages of learning to the most seasoned seniors.&lt;/strong&gt; Precisely because it’s so prevalent in our daily work, I think it’s important to revisit the definitions of these two concepts, especially since it’s already explained above why one is more important for Rails. I’m also leaving &lt;a href="https://www.devmedia.com.br/heranca-versus-composicao-qual-utilizar/26145" rel="noopener noreferrer"&gt;a link to a well-detailed DevMedia article (in PT-BR)&lt;/a&gt; that explains the importance of each and when to use them (spoiler: most of the time, it’s not Inheritance).&lt;/p&gt;

&lt;h3&gt;
  
  
  Inheritance
&lt;/h3&gt;

&lt;p&gt;Inheritance in programming &lt;strong&gt;is defined by the existence of a parent class (also known as a base class or superclass) and a child class (or subclass)&lt;/strong&gt;, and it is considered a fundamental tool for extending and reusing functionalities. In this principle, we focus heavily on the &lt;strong&gt;generalization&lt;/strong&gt; of concepts: similarities between classes are placed in the parent class, while all specific business logic is placed in the child class.&lt;/p&gt;

&lt;p&gt;In this concept, &lt;strong&gt;there is a strong coupling between classes&lt;/strong&gt;, as one class depends on the other throughout the system.&lt;/p&gt;

&lt;h3&gt;
  
  
  Composition
&lt;/h3&gt;

&lt;p&gt;In Composition, we define small behaviors that will exist between classes, which are standardized. As our classes are created and evolve, &lt;strong&gt;we compose more complex behaviors using these small units of behavior that have already been designed and tested&lt;/strong&gt;. Here, &lt;strong&gt;the emphasis is on encapsulating logic&lt;/strong&gt;, which is always a good practice.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5rab770kky8ft608563p.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5rab770kky8ft608563p.png" alt="Some Legos" width="128" height="128"&gt;&lt;/a&gt;&lt;br&gt;Encapsulate your stuff, bro.
  &lt;/p&gt;




&lt;p&gt;🪡 &lt;strong&gt;Revisions and Corrections&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
&lt;strong&gt;May 30, 2023&lt;/strong&gt; – I corrected some parts of the text that mistakenly stated that &lt;code&gt;modules&lt;/code&gt; belong to Rails, when &lt;strong&gt;they actually belong to Ruby itself&lt;/strong&gt;. Thanks to Sérgio Ribeiro for the heads up! 😀&lt;/p&gt;




&lt;h2&gt;
  
  
  ✔ Links consulted
&lt;/h2&gt;

&lt;p&gt;♥ &lt;a href="https://www.rubyguides.com/2020/01/rails-helpers/" rel="noopener noreferrer"&gt;RubyGuides: How to Use Rails Helpers (Complete Guide)&lt;/a&gt; – by Jesus Castello&lt;/p&gt;

&lt;p&gt;★ &lt;a href="https://damely-tineo.medium.com/helper-methods-9143cc1826b5" rel="noopener noreferrer"&gt;Helper Methods&lt;/a&gt; – by Damely Tineo&lt;/p&gt;

&lt;p&gt;♥ &lt;a href="https://medium.com/rubycademy/modules-in-ruby-part-i-a2cdfaccdb6e" rel="noopener noreferrer"&gt;Modules in Ruby: Part I&lt;/a&gt; – by RubyCademy&lt;/p&gt;

&lt;p&gt;★ &lt;a href="https://www.devmedia.com.br/heranca-versus-composicao-qual-utilizar/26145" rel="noopener noreferrer"&gt;DevMedia: Herança versus Composição: qual utilizar?&lt;/a&gt; – by Higor&lt;/p&gt;

&lt;p&gt;Last accessed on April 2, 2023.&lt;/p&gt;




&lt;h2&gt;
  
  
  📩 A Last Message
&lt;/h2&gt;

&lt;p&gt;Did you like the text? Do you have anything to add? Any constructive criticism? Feedback? Suggestions? Requests? Feel free to contact me via email (&lt;a href="mailto:oli.pmatt@gmail.com"&gt;oli.pmatt@gmail.com&lt;/a&gt;), LinkedIn (&lt;a href="https://www.linkedin.com/in/oliviamattiazzo/" rel="noopener noreferrer"&gt;/in/oliviamattiazzo&lt;/a&gt;) or through the comments section below! I’d be delighted to chat with you! ✨&lt;/p&gt;

&lt;p&gt;You can also check the &lt;a href="https://oliviamattiazzo.dev/2023/04/02/rails-helpers/" rel="noopener noreferrer"&gt;original post (in PT-BR)&lt;/a&gt; at my blog: &lt;a href="https://oliviamattiazzo.dev/" rel="noopener noreferrer"&gt;oliviamattiazzo.dev&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://ko-fi.com/Q5Q4I8JOP" rel="noopener noreferrer"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--mLqxWhiG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://ko-fi.com/img/githubbutton_sm.svg" alt="ko-fi" width="223" height="30"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  🪪 Credits
&lt;/h2&gt;

&lt;p&gt;The icons used to illustrate this post came from the following IconFinder users:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.iconfinder.com/Puckung" rel="noopener noreferrer"&gt;https://www.iconfinder.com/Puckung&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.iconfinder.com/SItchko" rel="noopener noreferrer"&gt;https://www.iconfinder.com/SItchko&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.iconfinder.com/dooder" rel="noopener noreferrer"&gt;https://www.iconfinder.com/dooder&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>rails</category>
      <category>ruby</category>
      <category>learning</category>
    </item>
  </channel>
</rss>
