Monday, February 16, 2026

How To Deploy a React Application with apache on Ubuntu

 

To deploy a React application with Apache on Ubuntu, you need to
build your application for production, configure Apache to serve the static files, and ensure proper handling of client-side routing using an .htaccess file.
 
Prerequisites
  • An Ubuntu server with Apache installed.
  • Node.js and npm installed on your local machine or server.
  • A React application ready for deployment.
Step-by-Step Guide
 
 
1. Build the React Application
On your local machine, navigate to your project's root directory in the terminal and run the build command to generate production-ready static files:
bash
npm run build
This command creates an optimized build (or dist if using Vite) folder containing your static assets.
2. Prepare the Ubuntu Server and Upload Files
 
Connect to your Ubuntu server via SSH and prepare a directory to host your application.
  • Create a directory for your site (replace yourwebsite.com with your domain or desired folder name):
    bash
    sudo mkdir -p /var/www/yourwebsite.com
    
  • Set ownership of the directory:
    bash
    sudo chown -R $USER:$USER /var/www/yourwebsite.com
    
  • Upload the contents of the local build folder to the server's directory (e.g., /var/www/yourwebsite.com) using an FTP client like FileZilla or scp.
 
3. Configure Apache for React Routing
 
React applications use client-side routing, which means direct access to sub-routes (e.g., ://yourwebsite.com) will result in a 404 error without proper server configuration. Apache needs to be instructed to redirect all requests to the index.html file.
  • Enable the mod_rewrite module:
    bash
    sudo a2enmod rewrite
    
  • Create a .htaccess file: Inside your application's root directory on the server (e.g., /var/www/yourwebsite.com), create a file named .htaccess and add the following snippet:
    apache
    Options -MultiViews
    RewriteEngine On
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.html [QSA,L]
    
    This snippet tells Apache that if a requested file does not exist, it should load index.html.
  • Ensure AllowOverride All is set: You might need to edit your Apache configuration to allow .htaccess files to override settings.
    • Open your virtual host file or the main apache2.conf file (e.g., /etc/apache2/sites-available/000-default.conf or /etc/apache2/apache2.conf).
    • Find the <Directory /var/www/html> block (or your custom directory block) and ensure AllowOverride is set to All:
    apache
    <Directory /var/www/yourwebsite.com>
        Options Indexes FollowSymLinks
        AllowOverride All
        Require all granted
    </Directory>
    
4. Restart Apache
 
After making configuration changes, restart Apache for them to take effect:
bash
sudo systemctl restart apache2
Your React application should now be deployed and accessible via your server's IP address or domain name.

Python: virtual environments (venv) and environment variables (.env)

 

The venv module supports creating lightweight “virtual environments”, each with their own independent set of Python packages installed in their site ...
In Python, creating a "private environment" generally refers to two primary concepts:
 
- virtual environments for project isolation and managing dependencies, and 
- using environment variables and .env files for securely managing sensitive information (secrets).
1. Project Isolation with Virtual Environments (venv)
 
A virtual environment is a self-contained directory that contains a specific Python interpreter and its own isolated set of Python packages. This prevents conflicts between the dependencies of different projects and keeps your global Python installation clean.
Key Steps:
  • Creation: Navigate to your project directory in the terminal and run the following command to create a virtual environment named .venv (a common convention):
    bash
    python -m venv .venv
    
    This creates a directory containing the isolated Python installation.
  • Activation: Before working on your project, you must activate the environment:
    • macOS/Linux:
      bash
      source .venv/bin/activate
      
    • Windows:
      bash
      .venv\Scripts\activate
      
    Once activated, your terminal prompt will usually change to indicate the active environment (e.g., (.venv) YourName: ).
  • Deactivation: To leave the virtual environment, simply run:
    bash
    deactivate
    
  • Version Control: You should add the environment directory (e.g., .venv) to your .gitignore file to prevent accidentally committing it to source control. The environment is considered disposable and can be recreated from a requirements.txt file at any time.
  • Managing Python Versions: For managing multiple Python versions themselves on a single system (e.g., switching between Python 3.10 and 3.12), tools like pyenv can be used alongside venv.
 
2. Storing Secrets with .env Files
 
To keep sensitive information like API keys, passwords, and credentials out of your source code, you use environment variables loaded from a .env file.
Key Steps:
  • Create a .env file: In your project's root directory, create a file named .env. Inside this file, store key-value pairs (e.g., API_KEY=your_secret_key).
    • Crucial: Add the .env file to your .gitignore file immediately to prevent it from being committed to source control.
  • Install python-dotenv: Install the required package using pip within your activated virtual environment:
    bash
    pip install python-dotenv
    
    You can find the package on the official PyPI repository.
  • Load Variables in Python: In your Python code (e.g., app.py), use the load_dotenv function to read the variables, and access them using the standard os module.
    python
    import os
    from dotenv import load_dotenv
    
    # Load environment variables from .env file
    load_dotenv()
    
    # Access the variables
    api_key = os.getenv("API_KEY")
    database_url = os.getenv("DATABASE_URL")
    
    print(f"Key: {api_key}")
    
This ensures your sensitive data is kept private and can be easily managed across different deployment environments.

Ubuntu installation log

- sudo apt update
- sudo apt install vim
- sudo apt install build-essential
  This command will install G++, GCC, make, and other core development libraries.
  - gcc/g++ 15.2.0
    g++-15 -std=c++20 hello.cpp -o hello
  - perl 5, version 40, subversion 1 (v5.40.1)
- sudo apt install default-jdk
  This installs Java.
  - javac --version : javac 21.0.10
  - java --version  : openjdk version "21.0.10" 2026-01-20
- sudo apt install php
  This installs PHP.
  - PHP 8.4.11 (cli) (built: Jan  7 2026 08:44:00) (NTS)

- sudo apt install apache2
  apache2 is already the newest version (2.4.64-1ubuntu3.2)
  - sudo systemctl status apache2
  - server is running
  - conf: /etc/apache2/
  - /var/www/html/ 

- Python is pre-installed on all modern Ubuntu:
  - Python 3.13.7
- sudo apt install python3-pip
  This installs pip (Python package manager)
  - pip 25.1.1 from /usr/lib/python3/dist-packages/pip (python 3.13)

- sudo apt install python3-venv
  sudo apt install python3.14-venv
  Install venv (virtual environment module): This is crucial for creating isolated environments 
  for your projects to manage dependencies without affecting the system Python.
  - You also need to install for each python version

- sudo apt install software-properties-common
  This installs the add-apt-repository command in Ubuntu.
  - type add-apt-repository
    add-apt-repository is /usr/bin/add-apt-repository
  - You can now use the command to add a new repository, for example, a Personal Package Archive (PPA):
    sudo add-apt-repository ppa:some/ppa-name
- sudo add-apt-repository ppa:deadsnakes/ppa
  sudo apt update
  - This adds the deadsnakes PPA.

- sudo apt install python3.14
  - Installs Python 3.14
  - python3.14 --version
    3.14.0
  - python3 --version
    3.13.7

- make Python an alias of python3.14:
  - vi ~/.bash_aliases
  - add: alias python=python3.14
  - source ~/.bash_aliases

- mkdir wschat
  cd wschat
  python -m venv .myenv
  source .myenv/bin/activate
  - pip install autobahn[twisted]
  deactivate


Daemonize a process in python virtual environment

 

The most robust way to daemonize a Python process in a virtual environment on Ubuntu is by
using a systemd service unit file that explicitly points to the virtual environment's Python interpreter. This approach ensures proper isolation and reliable service management by the operating system.
Prerequisites
  • A Python script you want to run as a daemon (e.g., main.py).
  • A created virtual environment (e.g., in a .venv directory).
Steps
  1. For security, create a dedicated system user: sudo useradd --system --no-create-home --shell /usr/sbin/nologin appuser. Then, set ownership for your application directory: sudo chown -R appuser:appuser /path/to/your/app.
  2. Create a systemd service file (e.g., mydaemon.service) in /etc/systemd/system/: sudo nano /etc/systemd/system/mydaemon.service.
  3. Configure the service, ensuring the ExecStart line points to the Python interpreter within your virtual environment and the script:
    ini
    [Unit]
    Description=My Python Daemon Service
    After=network.target
    
    [Service]
    Type=simple
    User=appuser
    Group=appuser
    WorkingDirectory=/path/to/your/app
    ExecStart=/path/to/your/app/.venv/bin/python /path/to/your/app/main.py
    Restart=always
    RestartSec=10
    Environment=PYTHONUNBUFFERED=1
    
    Replace /path/to/your/app with your project's absolute path. Type=simple means systemd handles daemonization for your foreground script, and Environment=PYTHONUNBUFFERED=1 ensures immediate log writing.
  4. Reload systemd: sudo systemctl daemon-reload.
  5. Enable and start the service: sudo systemctl enable mydaemon.service and sudo systemctl start mydaemon.service.
  6. Check the status and logs: sudo systemctl status mydaemon.service and journalctl -xeu mydaemon.service.
Alternative Python Package
 
The python-daemon package offers a Python-only approach for creating daemons, though systemd is generally preferred on modern Linux systems. You can install it in your virtual environment and use its DaemonContext in your script. You can find more details in the referenced documents.

Install Python on Ubuntu

 

Python 3 is
pre-installed on all modern Ubuntu versions
. You should not remove or change the system's default Python version as it can break core system tools. For most use cases, you just need to install additional modules like pip and venv or a specific Python version alongside the system's default.
 
Using the Pre-installed Python 3
 
Open your terminal (Ctrl + Alt + T) and follow these steps:
  1. Update package lists:
    bash
    sudo apt update
    
  2. Verify Python 3 is installed:
    bash
    python3 --version
    
    This command will display the installed version (e.g., Python 3.12.x on Ubuntu 24.04).
  3. Install pip (Python package manager): This allows you to install other Python packages from the Python Package Index (PyPI).
    bash
    sudo apt install python3-pip
    
  4. Install venv (virtual environment module): This is crucial for creating isolated environments for your projects to manage dependencies without affecting the system Python.
    bash
    sudo apt install python3-venv
    
  5. Create and activate a virtual environment:
    • Create an environment in your project directory:
      bash
      python3 -m venv my_project_env
      
    • Activate the environment:
      bash
      source my_project_env/bin/activate
      
    Your terminal prompt will change to indicate you are in the virtual environment. You can now use python and pip commands within this environment (instead of python3 and pip3).
 
Installing a Specific or Newer Python Version
 
 If you need a different version not available in the default repositories, the recommended way is to use the deadsnakes PPA (Personal Package Archive).
  1. Add the deadsnakes PPA:
    bash
    sudo add-apt-repository ppa:deadsnakes/ppa
    sudo apt update
    
  2. Install the desired version (e.g., Python 3.14):
    bash
    sudo apt install python3.14
    
  3. Verify the installation:
    bash
    python3.14 --version
    
This version is installed alongside the system Python and can be accessed with its specific command (python3.14). Always use virtual environments when working with these separate installations.

Alma Linux, debian, centos or ubuntu

 

Choosing between AlmaLinux, Debian, CentOS, and Ubuntu depends on whether you prioritize enterprise stability (AlmaLinux/CentOS), extreme reliability (Debian), or modern, beginner-friendly, and well-supported ecosystems (Ubuntu). AlmaLinux is the preferred, free successor to CentOS for cPanel/RHEL compatibility
. Ubuntu is best for cloud, developers, and ease of use, while Debian is ideal for rock-solid, low-resource server stability.
 
Here is a breakdown of the four options:

Ubuntu: Best for beginners, cloud, and DevOps. It has the largest repository of software, frequent updates, and excellent documentation.
 
AlmaLinux: The top choice for replacing CentOS. It is an enterprise-grade, RHEL-compatible OS, perfect for long-term stability and web hosting (e.g., cPanel).
Debian: Known for extreme stability, making it ideal for production servers that require minimal changes. It is highly reliable but has a steeper learning curve and older software packages.

CentOS: Historically, the standard for servers; however, with CentOS Linux 7/8 reaching end-of-life, most users are transitioning to AlmaLinux or Rocky Linux.
Key Decision Factors
  • For Ease of Use/Cloud: Ubuntu.
  • For Enterprise/RHEL/cPanel: AlmaLinux.
  • For Maximum Stability: Debian.
  • For Older Hardware: Debian.
Note: CentOS Stream is the only active official CentOS version, which acts as an upstream for RHEL and is generally less suitable for stable production environments than AlmaLinux.

Sunday, December 7, 2025

Display CJK fonts in matplotlib

Error: Glyph 21518 (\N{CJK UNIFIED IDEOGRAPH-540E}) missing from font(s) DejaVu Sans 

使用matplotlib绘图中文字符显示问题:UserWarning: missing from current font

Code added:

from pylab import mpl
mpl.rcParams["font.sans-serif"] = ["SimSong"]

# all_rcParams_keys = mpl.rcParams.keys()
# You can then iterate through them or convert to a list
# for key in all_rcParams_keys:
#    print(key)

 

Blog Archive

Followers