<?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: Mouhamadou Tidiane Seck</title>
    <description>The latest articles on DEV Community by Mouhamadou Tidiane Seck (@moha528).</description>
    <link>https://dev.to/moha528</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.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F1092350%2F02cd7d7e-ceec-4e9d-a24b-8fa01aae581d.jpg</url>
      <title>DEV Community: Mouhamadou Tidiane Seck</title>
      <link>https://dev.to/moha528</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/moha528"/>
    <language>en</language>
    <item>
      <title>How to Obtain a Let's Encrypt SSL Certificate for Nginx on Ubuntu 22.04</title>
      <dc:creator>Mouhamadou Tidiane Seck</dc:creator>
      <pubDate>Tue, 20 Aug 2024 00:00:54 +0000</pubDate>
      <link>https://dev.to/moha528/how-to-create-a-self-signed-ssl-certificate-for-nginx-on-ubuntu-2204-165j</link>
      <guid>https://dev.to/moha528/how-to-create-a-self-signed-ssl-certificate-for-nginx-on-ubuntu-2204-165j</guid>
      <description>&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;Securing your web server with SSL is a crucial step in protecting your users' data and ensuring the integrity of your web application. &lt;strong&gt;Let’s Encrypt&lt;/strong&gt; is a popular service that offers free SSL certificates via an automated API, with &lt;strong&gt;Certbot&lt;/strong&gt; as the most commonly used client. In this guide, we'll walk through the process of obtaining a Let’s Encrypt SSL certificate for Nginx on Ubuntu 22.04 using Certbot.&lt;/p&gt;

&lt;p&gt;We won't delve deeply into SSL configuration, but by the end of this tutorial, you'll have a valid certificate that renews automatically. Plus, you'll know how to automate the reloading of your service to account for the renewed certificate.&lt;/p&gt;

&lt;h2&gt;
  
  
  Prerequisites
&lt;/h2&gt;

&lt;p&gt;Before starting, ensure you have the following:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;An Ubuntu 22.04 server with a non-root user configured with sudo privileges and a basic firewall.&lt;/li&gt;
&lt;li&gt;Nginx installed, with a server block for your domain.&lt;/li&gt;
&lt;li&gt;A domain name pointing to your server (replace &lt;code&gt;your_domain&lt;/code&gt; in the tutorial with your actual domain).&lt;/li&gt;
&lt;li&gt;Port 80 must be reachable from the internet. In standalone mode, Certbot runs its own temporary web server on this port, so Nginx has to be stopped while a certificate is issued or renewed (Step 2 automates this with hooks). If you prefer to keep Nginx running, consider using Certbot's webroot mode instead.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Step 1 — Installing Certbot
&lt;/h2&gt;

&lt;p&gt;Certbot recommends using their snap package for installation. Snaps are supported on most Linux distributions, but you'll need &lt;code&gt;snapd&lt;/code&gt; installed to manage snap packages. Ubuntu 22.04 supports snaps by default, so start by ensuring your snapd core is up to date:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;snap &lt;span class="nb"&gt;install &lt;/span&gt;core&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="nb"&gt;sudo &lt;/span&gt;snap refresh core
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you have an older version of Certbot installed, remove it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;apt remove certbot
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, install the Certbot package:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;snap &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;--classic&lt;/span&gt; certbot
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Finally, link the Certbot command to your path:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo ln&lt;/span&gt; &lt;span class="nt"&gt;-s&lt;/span&gt; /snap/bin/certbot /usr/bin/certbot
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Certbot is now installed, and we can proceed to obtain our SSL certificate.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 2 — Running Certbot
&lt;/h2&gt;

&lt;p&gt;Certbot needs to respond to a cryptographic challenge issued by the &lt;strong&gt;Let’s Encrypt&lt;/strong&gt; API to prove that you control your domain. In standalone mode, it uses port 80 (HTTP) for this purpose. Open port 80 for the challenge and port 443 for the HTTPS traffic Nginx will serve:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;ufw allow 80
&lt;span class="nb"&gt;sudo &lt;/span&gt;ufw allow 443
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Run Certbot to obtain your certificate, using the &lt;code&gt;--standalone&lt;/code&gt; option to let Certbot handle the challenge with its built-in web server. Since Nginx already listens on port 80, the &lt;code&gt;--pre-hook&lt;/code&gt; and &lt;code&gt;--post-hook&lt;/code&gt; options stop Nginx before the challenge and start it again afterwards. Certbot saves these hooks and reuses them for every renewal:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;certbot certonly &lt;span class="nt"&gt;--standalone&lt;/span&gt; &lt;span class="nt"&gt;-d&lt;/span&gt; your_domain &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--pre-hook&lt;/span&gt; &lt;span class="s2"&gt;"systemctl stop nginx"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--post-hook&lt;/span&gt; &lt;span class="s2"&gt;"systemctl start nginx"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You’ll need to enter an email address and accept the terms of service. If successful, Certbot will inform you where the certificates are stored.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 3 — Configuring Your Application
&lt;/h2&gt;

&lt;p&gt;Configuring your application for SSL varies depending on the software you use, but let’s explore what Certbot has downloaded. List the directory containing your keys and certificates:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo ls&lt;/span&gt; /etc/letsencrypt/live/your_domain
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The most commonly needed files are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;privkey.pem&lt;/strong&gt;: This is the private key for your certificate. Keep this file secure and private.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;fullchain.pem&lt;/strong&gt;: This is your certificate bundled with any intermediate certificates. Most configurations refer to this file as the actual certificate.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;For more details on the other files, check the Certbot documentation.&lt;/p&gt;

&lt;p&gt;For Nginx, reference these two files in the server block of your site (for example &lt;code&gt;/etc/nginx/sites-available/your_domain&lt;/code&gt;):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight nginx"&gt;&lt;code&gt;&lt;span class="k"&gt;server&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kn"&gt;listen&lt;/span&gt; &lt;span class="mi"&gt;443&lt;/span&gt; &lt;span class="s"&gt;ssl&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="kn"&gt;listen&lt;/span&gt; &lt;span class="s"&gt;[::]:443&lt;/span&gt; &lt;span class="s"&gt;ssl&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="kn"&gt;server_name&lt;/span&gt; &lt;span class="s"&gt;your_domain&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="kn"&gt;ssl_certificate&lt;/span&gt; &lt;span class="n"&gt;/etc/letsencrypt/live/your_domain/fullchain.pem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="kn"&gt;ssl_certificate_key&lt;/span&gt; &lt;span class="n"&gt;/etc/letsencrypt/live/your_domain/privkey.pem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="c1"&gt;# your existing location blocks&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then test the configuration and reload Nginx:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;nginx &lt;span class="nt"&gt;-t&lt;/span&gt;
&lt;span class="nb"&gt;sudo &lt;/span&gt;systemctl reload nginx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Step 4 — Managing Automatic Renewals with Certbot
&lt;/h2&gt;

&lt;p&gt;Let’s Encrypt certificates are valid for 90 days, encouraging users to automate the renewal process. The Certbot snap package handles this with a systemd timer, which runs twice daily and renews any certificate that is close to expiration. You can check the timer with:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;systemctl list-timers | &lt;span class="nb"&gt;grep &lt;/span&gt;certbot
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The hooks passed in Step 2 are stored in &lt;code&gt;/etc/letsencrypt/renewal/your_domain.conf&lt;/code&gt;, so each renewal stops Nginx, renews the certificate, and starts Nginx again with the new certificate. You can confirm they were saved:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo cat&lt;/span&gt; /etc/letsencrypt/renewal/your_domain.conf
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If another service uses the same certificate, place an executable script in &lt;code&gt;/etc/letsencrypt/renewal-hooks/deploy/&lt;/code&gt; to reload it after each renewal. Then perform a dry run to check for errors (this briefly stops and restarts Nginx):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;certbot renew &lt;span class="nt"&gt;--dry-run&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If there are no errors, you're all set. Certbot will now automatically renew your certificate and execute the necessary commands.&lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;In this tutorial, we installed the &lt;strong&gt;Let’s Encrypt&lt;/strong&gt; Certbot client, obtained an SSL certificate using the standalone mode, configured Nginx to use it, and set up automatic renewals with custom hooks. This process provides a solid foundation for using Let’s Encrypt certificates with various services beyond the typical web server.&lt;/p&gt;

&lt;h2&gt;
  
  
  Notes
&lt;/h2&gt;

&lt;p&gt;Written for Ubuntu 22.04 LTS with Nginx 1.18.0 from the Ubuntu repositories and Certbot from the snap store.&lt;/p&gt;

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

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://nginx.org/en/docs/http/configuring_https_servers.html" rel="noopener noreferrer"&gt;Nginx documentation: Configuring HTTPS servers&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://nginx.org/en/docs/http/ngx_http_ssl_module.html" rel="noopener noreferrer"&gt;Nginx documentation: Module ngx_http_ssl_module&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://eff-certbot.readthedocs.io/en/stable/using.html" rel="noopener noreferrer"&gt;Certbot documentation: User Guide&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://letsencrypt.org/docs/challenge-types/" rel="noopener noreferrer"&gt;Let’s Encrypt documentation: Challenge Types&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>nginx</category>
      <category>linux</category>
      <category>devops</category>
      <category>security</category>
    </item>
    <item>
      <title>Configuring Nginx as a Reverse Proxy on Ubuntu 22.04</title>
      <dc:creator>Mouhamadou Tidiane Seck</dc:creator>
      <pubDate>Mon, 19 Aug 2024 23:58:16 +0000</pubDate>
      <link>https://dev.to/moha528/configuring-nginx-as-a-reverse-proxy-on-ubuntu-2204-1na3</link>
      <guid>https://dev.to/moha528/configuring-nginx-as-a-reverse-proxy-on-ubuntu-2204-1na3</guid>
      <description>&lt;p&gt;A &lt;strong&gt;reverse proxy&lt;/strong&gt; is a server that sits between client devices and backend servers, forwarding client requests to the appropriate server. &lt;strong&gt;Nginx&lt;/strong&gt; is commonly used as a reverse proxy due to its stability, simple configuration, and low resource consumption. In this guide, we'll walk through how to configure Nginx as a reverse proxy.&lt;/p&gt;

&lt;h2&gt;
  
  
  Network Architecture
&lt;/h2&gt;

&lt;p&gt;A reverse proxy is often deployed between two networks, sometimes with a dedicated network interface for each:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;External Interface&lt;/strong&gt;: This interface is exposed to the internet and handles requests from external users.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Internal Interface&lt;/strong&gt;: This interface communicates with the backend web servers that hold the requested information.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Here’s a diagram illustrating the basic flow:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;External Users -&amp;gt; Reverse Proxy (Nginx) -&amp;gt; Internal Web Servers
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Roles and Benefits of a Reverse Proxy
&lt;/h2&gt;

&lt;p&gt;Using a reverse proxy like Nginx offers several advantages:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Load Balancing&lt;/strong&gt;: Distributes incoming traffic across multiple web servers, improving performance and availability.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Traffic Management&lt;/strong&gt;: Allows you to manage server maintenance or migrations without downtime.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Centralized Configuration&lt;/strong&gt;: Manages access and configuration for multiple sites and web servers from a single location.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Traffic Optimization&lt;/strong&gt;: Uses caching and compression to improve response times.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Enhanced Security&lt;/strong&gt;: Handles SSL encryption and filters requests/URLs to increase security.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Configuring Nginx as a Reverse Proxy
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Step 1 — Installing Nginx
&lt;/h3&gt;

&lt;p&gt;Start by installing Nginx on your server:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Update the package index:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;apt update
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Install Nginx:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;apt &lt;span class="nb"&gt;install &lt;/span&gt;nginx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Ensure Nginx is running:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  systemctl status nginx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 2 — Configuring the Firewall (Optional)
&lt;/h3&gt;

&lt;p&gt;If your server’s firewall is active, you'll need to allow HTTP traffic:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Allow HTTP traffic:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;ufw allow &lt;span class="s1"&gt;'Nginx HTTP'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 3 — Creating a Configuration File
&lt;/h3&gt;

&lt;p&gt;Create a configuration file for your site:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Use a text editor like &lt;code&gt;nano&lt;/code&gt; to create a new configuration file in the &lt;code&gt;/etc/nginx/sites-available/&lt;/code&gt; directory:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;nano /etc/nginx/sites-available/your_domain
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 4 — Configuring the Server Block
&lt;/h3&gt;

&lt;p&gt;Edit the server block configuration with your domain and application server address:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Insert the following configuration into your new file, replacing &lt;code&gt;your_domain&lt;/code&gt; and &lt;code&gt;app_server_address&lt;/code&gt; with your actual domain and the address of your application server (for example &lt;code&gt;127.0.0.1:8000&lt;/code&gt;):
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight nginx"&gt;&lt;code&gt;  &lt;span class="k"&gt;server&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="kn"&gt;listen&lt;/span&gt; &lt;span class="mi"&gt;80&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
      &lt;span class="kn"&gt;listen&lt;/span&gt; &lt;span class="s"&gt;[::]:80&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

      &lt;span class="kn"&gt;server_name&lt;/span&gt; &lt;span class="s"&gt;your_domain&lt;/span&gt; &lt;span class="s"&gt;www.your_domain&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

      &lt;span class="kn"&gt;location&lt;/span&gt; &lt;span class="n"&gt;/&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
          &lt;span class="kn"&gt;proxy_pass&lt;/span&gt; &lt;span class="s"&gt;http://app_server_address&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
          &lt;span class="kn"&gt;include&lt;/span&gt; &lt;span class="s"&gt;proxy_params&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 5 — Activating the Configuration
&lt;/h3&gt;

&lt;p&gt;Activate the new configuration file:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Create a symbolic link from the configuration file to the directory that Nginx reads from at startup:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo ln&lt;/span&gt; &lt;span class="nt"&gt;-s&lt;/span&gt; /etc/nginx/sites-available/your_domain /etc/nginx/sites-enabled/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Step 6 — Testing the Configuration
&lt;/h3&gt;

&lt;p&gt;Test the Nginx configuration for syntax errors and then restart Nginx:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Verify the configuration:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;nginx &lt;span class="nt"&gt;-t&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Restart Nginx to apply the changes:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;systemctl restart nginx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Optional: Using Gunicorn
&lt;/h3&gt;

&lt;p&gt;If you need to run a Python web application, you can use Gunicorn as an application server:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Install Gunicorn:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  &lt;span class="nb"&gt;sudo &lt;/span&gt;apt &lt;span class="nb"&gt;install &lt;/span&gt;gunicorn
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Create a test application that returns "Hello World!" in an HTTP response to verify Gunicorn is working correctly, for example in &lt;code&gt;~/wsgi.py&lt;/code&gt;:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;app&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;start_response&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
      &lt;span class="nf"&gt;start_response&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;200 OK&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;[(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Content-Type&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;text/plain&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)])&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sa"&gt;b&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Hello World!&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Start Gunicorn on the loopback interface, port 8000:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  gunicorn &lt;span class="nt"&gt;--chdir&lt;/span&gt; ~ &lt;span class="nt"&gt;--bind&lt;/span&gt; 127.0.0.1:8000 wsgi:app
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Set &lt;code&gt;proxy_pass http://127.0.0.1:8000;&lt;/code&gt; in your server block, reload Nginx with &lt;code&gt;sudo systemctl reload nginx&lt;/code&gt;, then open &lt;code&gt;http://your_domain&lt;/code&gt;: the response should be "Hello World!".&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;You have successfully configured Nginx as a reverse proxy for your websites. This setup not only optimizes traffic management but also enhances the security and scalability of your web infrastructure. Feel free to explore more Nginx features to further improve your deployment!&lt;/p&gt;

&lt;h2&gt;
  
  
  Notes
&lt;/h2&gt;

&lt;p&gt;Written for Ubuntu 22.04 LTS with Nginx 1.18.0 and Gunicorn from the Ubuntu repositories.&lt;/p&gt;

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

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://nginx.org/en/docs/http/ngx_http_proxy_module.html" rel="noopener noreferrer"&gt;Nginx documentation: Module ngx_http_proxy_module&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://nginx.org/en/docs/http/load_balancing.html" rel="noopener noreferrer"&gt;Nginx documentation: Using nginx as HTTP load balancer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://nginx.org/en/docs/beginners_guide.html" rel="noopener noreferrer"&gt;Nginx documentation: Beginner's Guide&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://gunicorn.org/deploy/" rel="noopener noreferrer"&gt;Gunicorn documentation: Deploy&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>nginx</category>
      <category>linux</category>
      <category>devops</category>
      <category>security</category>
    </item>
  </channel>
</rss>
