Exporting env files to shell.

How to Read a .env File in Bash

Sometimes you need to read a .env file in a bash script to access the environment variables defined in it. There are two(2) basic ways of achieving this namely

1. Sourcing the .env file

source .env

2. Exporting the variables in the .env file

export $(cat .env | xargs)

The two techniques achieve the same thing. The second choice using xargs is more flexible. It lets you manipulate the variables as much as you want before exporting them into the shell.

Quick introduction to the a2query Command

The a2query command is a very simple and niffty tool that is used to retrieve information from the configuration of a local Apache 2 HTTP Server.

Lets see a few examples of how to use a2query.

How to list all enabled apache modules

$ a2query -m
access_compat (enabled by maintainer script)
alias (enabled by maintainer script)
auth_basic (enabled by maintainer script)
authn_core (enabled by maintainer script)
authn_file (enabled by maintainer script)
authz_core (enabled by maintainer script)
authz_host (enabled by maintainer script)
authz_user (enabled by maintainer script)
autoindex (enabled by maintainer script)
deflate (enabled by maintainer script)
dir (enabled by maintainer script)
env (enabled by maintainer script)
filter (enabled by maintainer script)
mime (enabled by maintainer script)
mpm_event (enabled by maintainer script)
negotiation (enabled by maintainer script)
reqtimeout (enabled by maintainer script)
setenvif (enabled by maintainer script)
status (enabled by maintainer script)

    How to list all virtual hosts

    $a2query -s
    000-default (enabled by site administrator)
    

    How to check if a module is enabled?

    $a2query -m status
    status (enabled by maintainer script)
    

    How to check the enabled Apache MPM (Multi Processing Module)

    $a2query -M       
    event
    

    How to display the current Apache2 version

    $ a2query -v
    2.4.38
    

    Note: For every successful command, a2query returns a zero (0) exit code and non-zero exit code for every unsuccessful operation.

    How To Concatenate & Interpolate Strings In Twig

    Twig is arguably the most powerful, modern and easy to use templating engine in PHP.

    When using twig, sooner or later, you will run into the situation where you need to join two strings (concatenation) or evaluate an expression in strings (interpolation). Please consider the following

    Concatenate Strings In Twig

    To join two strings in Twig, you can use the tilde ~ operator as follows

    {{ "Welcome Mr " ~ name }}
    

    This will give the output Welcome Mr JohnDoe if the value of the name variable is JohnDoe.

    You can play with this exact example on the twig playground.

    Interpolating Strings In Twig

    Sometimes you will desire to evaluate an expression and embed the result in a string, this is called interpolation, consider the example below where we will like to display the total sales of two months and display it.

    {{ "Jan & Feb Sales = #{jan_sales + feb_sales}"}}
    

    This will give the output “Jan & Feb Sales = 51” if the values of jan_sales and feb_sales are 28 & 23 respectively.

    You can play with this exact example on the twig playground.

    ANAME vs CNAME

    When it comes to managing DNS records, CNAME is a very popular DNS record type, however its close cousin ANAME is largely unknown, hopefully at the end of this short article, you will be able to tell the two apart and also understand when they are used.

    Either of a CNAME and ANAME can be used to map domain names to other domains with the following differences.

    A CNAME (also called Canonical NAME) is used to map a domain or subdomain to another domain name, effectively creating a shortcut or an alias. Therefore if a domain http://www.234.com is a CNAME for http://www.github.com, then it means http://www.234.com will resolve to http://www.github.com. Note, this DNS record type cannot be used at the root level of a domain i.e (234.com cannot CNAME to http://www.github.com) but http://www.234.com can.

    Lastly, an ANAME record also called the Alias NAME record is very similar to the CNAME record discussed above with the exception that the ANAME record resolves directly to the IP address behind the dns domain name being aliased to. This subtle difference makes it possible for an ANAME record to be used at the apex of a domain i.e. the root domain.

    i.e 234.com ALIAS http://www.github.com will resolve to the IP address behind http://www.github.com.

    It is also worthy of note that ALIAS (ANAME) isnt a standard DNS record type, hence the implementation may differ from provider to provider.

    In summary, to help you visualise the difference between CNAME and ANAME, consider the following

    1. CNAME is equivalent to an address card that points to another address card
    2. ANAME is the equivalent of an address card that point to an actual house (i.e the house number contained in the address card being passed around).

    How to split string and print over multiple lines in bash

    Sometimes, you get some cli outputs seperated/delimited by a character but you want it printed over multiple lines or used in a loop or pipe each item to another command. Lets solve that easily

    $ echo "1,2,3,4,5"
                        
    1,2,3,4,5
    
    # Now lets print this over multiple lines as follows
    $ echo "1,2,3,4,5" | sed -e 's/,/\n/g'
    
    1
    2
    3
    4
    5
    

    Lets consider a more practical example, lets get all all IPs of a machine using the hostname command.

    $ hostname -I
    
    192.168.1.179 172.17.0.1 172.18.0.1
    
    # Now, lets print this over multiple lines
    $ hostname -I | sed -e  's/ /\n/g'
    
    192.168.1.179
    172.17.0.1
    172.18.0.1
    

    We can parse this output to other commands

    $ hostname -I | sed -e  's/ /\n/g' | xargs -I {} echo "IP = {}"
    
    IP = 192.168.1.179
    IP = 172.17.0.1
    IP = 172.18.0.1
    

    How to Use Minikube on ARM Mac (m1/m2)

    I use a Mac M1 as my day to day machine and I found that setting up the minikube for use on the machine was a bit problematic, so I am writing this to help someone out there.

    There are many drivers (ways of running) for minikube including the following Docker, KVM2, VirtualBox, QEMU etc, however on Mac m1 and m2, the QEMU is reputed to be least stressful or problematic way to run minikube, so in this tutorial we will be going through how to set it up for use.

    Installing Minikube & Starting It On Mac Arm

    Step 1: Install Minikube

    This is a straighforward step, you can use one of two methods Direct Binary Download or by using Homebrew as follows

    curl -LO https://storage.googleapis.com/minikube/releases/latest/minikube-darwin-amd64
    sudo install minikube-darwin-amd64 /usr/local/bin/minikube
    

    or by using Homebrew

    $ brew install minikube
    

    then validate minikube is installed by running the following

    $ minikube update-check
    CurrentVersion: v1.33.1
    LatestVersion: v1.33.1 
    

    Step 2: Install Qemu

    You need to install the qemu emulator & virtualizer that uses https://www.qemu.org/ underneath for VM creation.

    $ brew install qemu
    

    Step 3: Install socket_vvmnet for networking

    brew install socket_vmnet
    brew tap homebrew/services
    HOMEBREW=$(which brew) && sudo ${HOMEBREW} services start socket_vmnet
    

    Step 4: Startup minikube using qemu as the specified driver and socket_vmnet for networking

    Step 5: Confirm that minikube is running

    Step 6: Add a workload to kubernetes

    Step 7: Test the exposed url

    Visit the retuned url in the brower

    In conclusion, we no have minikube running and we have a workload exposed in it, running successfully. If you run into any problems recreating this, you can troubleshoot it by following the steps listed on the minikube website or the issues page on github

    What Is Kubernetes (k8s) Ingress? An Explainer

    Kubernetes also known as the popular moniker (K8s) is an opensource tool developed by Google that has established itself as the industry defacto standard tool for container orchestration. Kubernetes can run virtually any kind of workload, especially those that needs to be made publicly accessible over the internet or a network.

    By default, applications running on kubernetes are not publicly accessible outside the cluster, it then begs the question, how do you expose a kubernetes application to the wild over the internet. There are a couple of ways, listed below

    • Ingress
    • External Load Balancer

    In this tutorial, we will go through the use of Kubernetes Ingresses.

    What is a Kubernetes Ingress?

    A K8s Ingress is a kubernetes API object that helps in managing traffic and external access to services running in a kubernetes cluster. An Ingress achieves this by exposing HTTP(80) and HTTPS(443) traffic from outside the cluster into services in the cluster. Think of it as proxy that directs traffic from port (80) and (443) to different services grouped by hostnames and paths etc.

    A Kubernetes ingress has two components, namely

    • Kubernetes Ingress Controller
    • Kubernetes Ingress Object

    Kubernetes Ingress Controller: This is a K8s component that manages the implementation of the ingress objects, it is in charge of defining the rules that implements the ingress specification. Think of this as a type of webserver flavour (i.e same way Nginx is different from Apache and Caddy) but they all implement the HTTP protocol in the same way although through different syntaxes. Same way, there are various types of K8s Ingress controllers but they all implement the Ingress rules and specifications.

    Some of the most popular controllers are

    Kubernetes Ingress Object: This is the bread and butter of the K8s ingress resources, this is the actual k8s resource that defines the rules for routing (based on hostnames or URI path) and mapping the external traffic to k8s services. It also handles TLS termination (i.e it decodes https traffic)

    An example of K8s ingress manifest defined in YAML is given below

    apiVersion: networking.k8s.io/v1
    kind: Ingress
    metadata:
      name: sample-ingress
    spec:
      rules:
      - host: www.example.com
        http:
          paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: website-service
                port:
                  number: 443
      - host: cdn.example.com
        http:
          - path: /images
            pathType: Prefix
            backend:
              service:
                name: cdn-images-service
                port:
                  number: 80
      tls:
        - hosts:
          - www.example.com
          - cdn.example.com
          secretName: example-com-tls-secret
    

    The above defined manifest defines the routing of traffic based on two (hostnames http://www.example.com and cdn.example.com) and the paths

    • hostname(www.example.com) and path prefixed by (/) is routed to the website-service on port 443
    • hostname(cdn.example.com) and path prefixed by (/images) is routed to the cdn-images-service on port 80.

    Finally, K8s Ingress is a powerful and exciting resource for managing and routing external access to services in a Kubernetes cluster. It is highly scalable and very flexible for use in your kubernetes cluster, making it an invaluable assets in the toolset of a seasoned kubernetes developer or administrator. As part of this series, we will be exploring more features of the kubernetes ingress.

    How To Validate The Presence Of A Module In Perl From The Linux Shell

    Perl is a very versatile programming language and it allows for sharing and use of modules. The question occasionally arises, how do I check if a module is present in perl, lets solve that.

    To test if the XML::Parser module is present , just execute a simple perl script as follows

    $ perl -e "use XML::Parser"
    $ echo $?
    0
    

    By returning zero (0) as the exit code, this confirms that the module exists in perl.

    To check a module that is not present, lets do the following

    $ perl -e "use Not::PresentModule"
    
    Can't locate Not/PresentModule.pm in @INC (you may need to install the Not::PresentModule module) (@INC contains: /Library/Perl/5.34/darwin-thread-multi-2level /Library/Perl/5.34 /Network/Library/Perl/5.34/darwin-thread-multi-2level /Network/Library/Perl/5.34 /Library/Perl/Updates/5.34.1 /System/Library/Perl/5.34/darwin-thread-multi-2level /System/Library/Perl/5.34 /System/Library/Perl/Extras/5.34/darwin-thread-multi-2level /System/Library/Perl/Extras/5.34) at -e line 1.
    BEGIN failed--compilation aborted at -e line 1.
    
    $ echo $?                                                                                                                                                       2
    

    As you can see, this returns an error, this shows that the module is not present. Hopefully, this saves you some time.

    How To Generate Random String On Linux

    A quick way to generate random strings on linux is by using the ever versatile openssl application.

    The synopsis of the openssl command is as follow

    openssl rand [-help] [-out file] [-rand file…] [-writerand file] [-base64] [-hexnum

    The openssl command will generate num number of random bytes

    e.g To create 32 bytes random string, you can do

    $ openssl rand -base64 32
    hQwaQTd5WFRIPcfto129nfdX1dBPUOBQraqnSyD56hA=
    
    
    # to check the number of bytes, you can do
    $ openssl rand 32 | wc -c
          32
    

    How To Schedule Tasks on Linux Using the at Command

    The at command is a very useful and powerful tool in Linux that allows users to schedule single tasks to run at a specific time or date. It is an alternative to the cron command, which is used for managing recurring tasks, however the at command is is designed for one-time jobs.

    How to Install and enable the at Command

    The at command usually comes already installed on most modern Linux distributions. However, to check if the at command is installed, you can use the following command:

    $ at -V
    

    If the at command is not installed, you can install it on ubuntu or debian using apt as follows, on other distributions you can just use the package manager on the distribution.

    $ apt install -y at
    
    # then you can enable the daemon service atd as follows
    
    $ sudo systemctl enable --now atd
    

    Basic Syntax of the at Command

    The basic syntax of the at command is as follows:

    $ at [-q queue] [-f file] [-mldv] TIME
    
    • -q queue: Specifies the job queue (default is “a”).
    • -f file: Reads the job from the specified file.
    • -m: Sends an email to the user after the job has been executed.
    • -l: Lists the user’s pending jobs.
    • -d: Deletes a pending job.
    • -v: Displays the time of job execution.
    • TIME: Specifies the time when the job should be executed.

    Examples of how to use the at Command

    1: Scheduling a Command to Run at a Specific Time

    To schedule a command to run at 11:00 PM, you can use the following command:

    $ at 11:00 PM
    at> echo "Welcome to my world" > /tmp/hello.txt
    at> Ctrl+D
    

    This will schedule the echo command to write “Welcome to my world” to the specified file at 11:00 PM.

    2: Using a File to Specify Commands

    You can also use a script file to specify commands. For example, to schedule a script to run at 10:00 PM:

    $ echo "whoami" > /path/to/script.sh
    $ at 11:00 PM -f /path/to/script.sh
    
    warning: commands will be executed using /bin/sh
    job 2 at Wed Aug  7 11:10:00 2024
    

    This will schedule the whoami command to run at 11:00 PM.

    3: System Shutdown at a Specific Date

    To schedule a system shutdown at 11:45 PM on July 31:

    $ at 15:35 PM June 30
    at> shutdown now
    at> Ctrl+D
    

    This will schedule the shutdown of the machine at 15:35 PM on June 30.

    Viewing and Managing Scheduled Jobs

    To view the scheduled jobs, you can use the atq command:

    You can view all the jobs already scheduled for various times by using the atq command

    $ atq
    

    You can remove a specific job from the queue by using the job-id as follows

    $ atrm <job-id>