Install and configure Tengine web server with SSL certificates and performance optimization

Beginner 45 min Apr 17, 2026 20 views
Ubuntu 24.04 Ubuntu 22.04 Debian 12 AlmaLinux 9 Rocky Linux 9 Fedora 41

Install Tengine web server from source and packages, configure virtual hosts with SSL certificates, and optimize performance with dynamic upstream health checks and security hardening.

Prerequisites

  • Root or sudo access
  • Domain name pointing to your server
  • At least 2GB RAM
  • Basic Linux command line knowledge

What this solves

Tengine is a high-performance web server based on Nginx that adds advanced features like dynamic upstream management, health checks, and enhanced performance monitoring. This tutorial shows you how to install Tengine, configure virtual hosts with SSL certificates, and optimize it for production use with security hardening and performance tuning.

Step-by-step installation

Update system packages

Start by updating your package manager to ensure you get the latest versions and security patches.

sudo apt update && sudo apt upgrade -y
sudo dnf update -y

Install build dependencies

Install the required packages for compiling Tengine from source, including development tools and libraries.

sudo apt install -y build-essential libpcre3-dev zlib1g-dev libssl-dev libgeoip-dev curl wget
sudo dnf groupinstall -y "Development Tools"
sudo dnf install -y pcre-devel zlib-devel openssl-devel GeoIP-devel curl wget

Create Tengine user

Create a dedicated system user for running Tengine with minimal privileges for security.

sudo useradd --system --home /var/cache/tengine --shell /sbin/nologin --comment "Tengine web server" --user-group tengine

Download and compile Tengine

Download the latest Tengine source code and compile it with essential modules including SSL support and dynamic upstream.

cd /tmp
wget http://tengine.taobao.org/download/tengine-3.1.0.tar.gz
tar -xzf tengine-3.1.0.tar.gz
cd tengine-3.1.0
./configure \
  --prefix=/etc/tengine \
  --sbin-path=/usr/sbin/tengine \
  --modules-path=/usr/lib/tengine/modules \
  --conf-path=/etc/tengine/tengine.conf \
  --error-log-path=/var/log/tengine/error.log \
  --http-log-path=/var/log/tengine/access.log \
  --pid-path=/var/run/tengine.pid \
  --lock-path=/var/run/tengine.lock \
  --http-client-body-temp-path=/var/cache/tengine/client_temp \
  --http-proxy-temp-path=/var/cache/tengine/proxy_temp \
  --http-fastcgi-temp-path=/var/cache/tengine/fastcgi_temp \
  --http-uwsgi-temp-path=/var/cache/tengine/uwsgi_temp \
  --http-scgi-temp-path=/var/cache/tengine/scgi_temp \
  --user=tengine \
  --group=tengine \
  --with-http_ssl_module \
  --with-http_realip_module \
  --with-http_addition_module \
  --with-http_sub_module \
  --with-http_dav_module \
  --with-http_flv_module \
  --with-http_mp4_module \
  --with-http_gunzip_module \
  --with-http_gzip_static_module \
  --with-http_random_index_module \
  --with-http_secure_link_module \
  --with-http_stub_status_module \
  --with-http_auth_request_module \
  --with-http_xslt_module \
  --with-http_image_filter_module \
  --with-http_geoip_module \
  --with-threads \
  --with-stream \
  --with-stream_ssl_module \
  --with-stream_ssl_preread_module \
  --with-stream_realip_module \
  --with-stream_geoip_module \
  --with-http_slice_module \
  --with-file-aio \
  --with-http_v2_module
make -j$(nproc)
sudo make install

Create directory structure

Set up the required directories with proper ownership and permissions for Tengine operation.

sudo mkdir -p /var/cache/tengine/{client_temp,proxy_temp,fastcgi_temp,uwsgi_temp,scgi_temp}
sudo mkdir -p /var/log/tengine
sudo mkdir -p /etc/tengine/conf.d
sudo mkdir -p /var/www/html
sudo chown -R tengine:tengine /var/cache/tengine
sudo chown -R tengine:tengine /var/log/tengine
sudo chown -R tengine:tengine /var/www/html
sudo chmod -R 755 /var/cache/tengine
sudo chmod -R 755 /var/log/tengine

Create main configuration file

Configure Tengine with optimized settings for performance, security, and dynamic upstream management.

user tengine;
worker_processes auto;
error_log /var/log/tengine/error.log warn;
pid /var/run/tengine.pid;

events {
    worker_connections 2048;
    use epoll;
    multi_accept on;
}

http {
    include /etc/tengine/mime.types;
    default_type application/octet-stream;

    # Logging format
    log_format main '$remote_addr - $remote_user [$time_local] "$request" '
                   '$status $body_bytes_sent "$http_referer" '
                   '"$http_user_agent" "$http_x_forwarded_for"';

    access_log /var/log/tengine/access.log main;

    # Performance optimizations
    sendfile on;
    tcp_nopush on;
    tcp_nodelay on;
    keepalive_timeout 65;
    types_hash_max_size 2048;
    client_max_body_size 64M;
    server_tokens off;

    # Gzip compression
    gzip on;
    gzip_vary on;
    gzip_proxied any;
    gzip_comp_level 6;
    gzip_types
        text/plain
        text/css
        text/xml
        text/javascript
        application/json
        application/javascript
        application/xml+rss
        application/atom+xml
        image/svg+xml;

    # Security headers
    add_header X-Frame-Options DENY;
    add_header X-Content-Type-Options nosniff;
    add_header X-XSS-Protection "1; mode=block";
    add_header Referrer-Policy "strict-origin-when-cross-origin";

    # Rate limiting
    limit_req_zone $binary_remote_addr zone=login:10m rate=10r/m;
    limit_req_zone $binary_remote_addr zone=global:10m rate=100r/s;

    # Include virtual host configurations
    include /etc/tengine/conf.d/*.conf;

    # Default server block
    server {
        listen 80 default_server;
        listen [::]:80 default_server;
        server_name _;
        root /var/www/html;
        index index.html;

        location / {
            try_files $uri $uri/ =404;
        }

        # Security location blocks
        location ~ /\. {
            deny all;
        }

        location ~* \.(log|conf)$ {
            deny all;
        }
    }
}

Create MIME types configuration

Set up proper MIME type mappings for different file extensions to ensure correct content serving.

types {
    text/html                                        html htm shtml;
    text/css                                         css;
    text/xml                                         xml;
    image/gif                                        gif;
    image/jpeg                                       jpeg jpg;
    image/png                                        png;
    image/svg+xml                                    svg svgz;
    image/webp                                       webp;
    application/javascript                           js;
    application/json                                 json;
    application/pdf                                  pdf;
    application/zip                                  zip;
    font/woff                                        woff;
    font/woff2                                       woff2;
}

Create systemd service

Set up a systemd service file for managing Tengine with automatic startup and proper service management.

[Unit]
Description=Tengine HTTP server
Documentation=http://tengine.taobao.org/
After=network.target remote-fs.target nss-lookup.target

[Service]
Type=forking
PIDFile=/var/run/tengine.pid
ExecStartPre=/usr/sbin/tengine -t
ExecStart=/usr/sbin/tengine
ExecReload=/bin/kill -s HUP $MAINPID
KillMode=mixed
KillSignal=SIGQUIT
TimeoutStopSec=5
PrivateTmp=true
LimitNOFILE=65536

[Install]
WantedBy=multi-user.target

Create default index page

Create a simple test page to verify Tengine installation and basic functionality.




    
    
    Tengine Server
    


    

Welcome to Tengine!

Tengine web server is successfully installed and running.

Server: example.com

Enable and start Tengine

Enable the Tengine service to start automatically on boot and start it immediately.

sudo systemctl daemon-reload
sudo systemctl enable tengine
sudo systemctl start tengine

Configure SSL certificates and virtual hosts

Install Certbot for SSL certificates

Install Certbot to automatically obtain and manage SSL certificates from Let's Encrypt.

sudo apt install -y certbot python3-certbot-nginx
sudo dnf install -y certbot python3-certbot-nginx

Create virtual host configuration

Configure a virtual host with SSL support and security headers for your domain.

server {
    listen 80;
    listen [::]:80;
    server_name example.com www.example.com;
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name example.com www.example.com;
    root /var/www/example.com;
    index index.html index.php;

    # SSL Configuration
    ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
    ssl_session_timeout 1d;
    ssl_session_cache shared:MozTLS:10m;
    ssl_session_tickets off;

    # SSL Security
    ssl_protocols TLSv1.2 TLSv1.3;
    ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
    ssl_prefer_server_ciphers off;

    # HSTS
    add_header Strict-Transport-Security "max-age=63072000" always;

    # Security headers
    add_header X-Frame-Options DENY;
    add_header X-Content-Type-Options nosniff;
    add_header X-XSS-Protection "1; mode=block";
    add_header Referrer-Policy "strict-origin-when-cross-origin";

    # Rate limiting
    limit_req zone=global burst=20 nodelay;

    location / {
        try_files $uri $uri/ =404;
    }

    # Static file caching
    location ~* \.(jpg|jpeg|png|gif|ico|css|js|woff|woff2)$ {
        expires 1y;
        add_header Cache-Control "public, immutable";
        access_log off;
    }

    # Security location blocks
    location ~ /\. {
        deny all;
    }

    location ~* \.(log|conf|bak)$ {
        deny all;
    }

    # Health check endpoint
    location /health {
        access_log off;
        return 200 "healthy\n";
        add_header Content-Type text/plain;
    }
}

Create website directory

Create the directory structure for your website with proper ownership and permissions.

sudo mkdir -p /var/www/example.com
sudo chown -R tengine:tengine /var/www/example.com
sudo chmod -R 755 /var/www/example.com

Obtain SSL certificate

Use Certbot to obtain an SSL certificate for your domain. Replace example.com with your actual domain.

sudo certbot certonly --webroot -w /var/www/html -d example.com -d www.example.com --email admin@example.com --agree-tos --no-eff-email

Configure dynamic upstream and health checks

Configure upstream backend servers

Set up dynamic upstream configuration with health checks for load balancing and high availability.

upstream backend_servers {
    # Dynamic upstream with health checks
    server 203.0.113.10:8080 max_fails=3 fail_timeout=30s;
    server 203.0.113.11:8080 max_fails=3 fail_timeout=30s backup;
    
    # Load balancing method
    least_conn;
    
    # Health check configuration
    check interval=3000 rise=2 fall=3 timeout=1000 type=http;
    check_http_send "GET /health HTTP/1.0\r\n\r\n";
    check_http_expect_alive http_2xx http_3xx;
}

Upstream status page

server { listen 8080; server_name localhost; location /upstream_status { check_status; access_log off; allow 127.0.0.1; allow 203.0.113.0/24; deny all; } }

Configure load balancer virtual host

Create a virtual host configuration that uses the upstream servers with advanced features.

server {
    listen 80;
    listen [::]:80;
    server_name api.example.com;
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name api.example.com;

    # SSL Configuration
    ssl_certificate /etc/letsencrypt/live/api.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/api.example.com/privkey.pem;
    ssl_session_timeout 1d;
    ssl_session_cache shared:MozTLS:10m;
    ssl_session_tickets off;

    # Real IP configuration
    real_ip_header X-Forwarded-For;
    set_real_ip_from 203.0.113.0/24;

    location / {
        proxy_pass http://backend_servers;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_cache_bypass $http_upgrade;
        
        # Timeouts
        proxy_connect_timeout 30s;
        proxy_send_timeout 30s;
        proxy_read_timeout 30s;
        
        # Buffer settings
        proxy_buffering on;
        proxy_buffer_size 4k;
        proxy_buffers 8 4k;
    }

    # Health check endpoint
    location /lb-health {
        access_log off;
        return 200 "load balancer healthy\n";
        add_header Content-Type text/plain;
    }
}

Test configuration and reload

Test the Tengine configuration for syntax errors and reload to apply changes.

sudo tengine -t
sudo systemctl reload tengine

Performance optimization

Configure worker process optimization

Optimize worker processes and connections based on your server's CPU cores and expected load. Learn more about Linux process monitoring in our process monitoring guide.

# Check CPU cores
nproc

Check current limits

ulimit -n
# Update these values in the main configuration
worker_processes auto;  # or number of CPU cores
worker_rlimit_nofile 65535;

events {
    worker_connections 4096;  # Increase based on ulimit
    use epoll;
    multi_accept on;
    accept_mutex off;
}

Configure caching and compression

Set up advanced caching and compression for better performance.

# Add to http block in main config or include this file

Browser cache

location ~* \.(css|js|png|jpg|jpeg|gif|ico|svg|woff|woff2|ttf|eot)$ { expires 1y; add_header Cache-Control "public, no-transform"; add_header Vary Accept-Encoding; access_log off; }

Gzip compression settings

gzip on; gzip_vary on; gzip_min_length 1024; gzip_proxied any; gzip_comp_level 6; gzip_types text/plain text/css text/xml text/javascript text/x-component application/javascript application/json application/xml application/rss+xml application/atom+xml font/truetype font/opentype application/vnd.ms-fontobject image/svg+xml;

File handle cache

open_file_cache max=200000 inactive=20s; open_file_cache_valid 30s; open_file_cache_min_uses 2; open_file_cache_errors on;

Configure system-level optimizations

Optimize system limits for high-performance web serving. For more system optimization, check our kernel parameters guide.

# Add these lines to increase file descriptor limits
tengine soft nofile 65535
tengine hard nofile 65535
www-data soft nofile 65535
www-data hard nofile 65535
# Network performance optimizations
net.core.somaxconn = 65535
net.core.netdev_max_backlog = 5000
net.core.rmem_default = 262144
net.core.rmem_max = 16777216
net.core.wmem_default = 262144
net.core.wmem_max = 16777216
net.ipv4.tcp_rmem = 4096 65536 16777216
net.ipv4.tcp_wmem = 4096 65536 16777216
net.ipv4.tcp_max_syn_backlog = 30000
net.ipv4.tcp_max_tw_buckets = 400000
net.ipv4.tcp_no_metrics_save = 1
net.ipv4.tcp_tw_reuse = 1
net.ipv4.tcp_fin_timeout = 15
net.ipv4.tcp_keepalive_time = 300
net.ipv4.tcp_keepalive_probes = 5
net.ipv4.tcp_keepalive_intvl = 15
sudo sysctl -p /etc/sysctl.d/99-tengine.conf

Security hardening

Configure firewall rules

Set up firewall rules to allow only necessary traffic and protect your Tengine server.

sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow ssh
sudo ufw allow 'Nginx Full'
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw --force enable

Configure security headers and rate limiting

Implement additional security measures including rate limiting and security headers.

# Rate limiting zones
limit_req_zone $binary_remote_addr zone=login:10m rate=5r/m;
limit_req_zone $binary_remote_addr zone=api:10m rate=100r/s;
limit_req_zone $binary_remote_addr zone=global:10m rate=10r/s;
limit_conn_zone $binary_remote_addr zone=conn_limit_per_ip:10m;

Security configuration to include in server blocks

Rate limiting

limit_req zone=global burst=20 nodelay; limit_conn conn_limit_per_ip 20;

Security headers

add_header X-Frame-Options DENY always; add_header X-Content-Type-Options nosniff always; add_header X-XSS-Protection "1; mode=block" always; add_header Referrer-Policy "strict-origin-when-cross-origin" always; add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always;

Hide server information

server_tokens off; more_set_headers "Server: Web Server";

Deny access to sensitive files

location ~ /\.(ht|git|svn) { deny all; return 404; } location ~* \.(log|conf|sql|bak|backup|old)$ { deny all; return 404; }

Set up automated certificate renewal

Configure automatic SSL certificate renewal to maintain security without manual intervention.

sudo systemctl enable certbot.timer
sudo systemctl start certbot.timer
sudo systemctl status certbot.timer
#!/bin/bash
/bin/systemctl reload tengine
sudo chmod +x /etc/letsencrypt/renewal-hooks/deploy/tengine-reload.sh

Verify your setup

# Check Tengine status
sudo systemctl status tengine

Verify configuration

sudo tengine -t

Check version and modules

tengine -V

Test HTTP and HTTPS

curl -I http://localhost curl -I https://example.com

Check upstream status (if configured)

curl http://localhost:8080/upstream_status

Verify SSL certificate

openssl s_client -connect example.com:443 -servername example.com < /dev/null

Check listening ports

sudo netstat -tlnp | grep tengine

Common issues

SymptomCauseFix
Tengine fails to startConfiguration syntax errorsudo tengine -t to check syntax
Permission denied errorsIncorrect file ownershipsudo chown -R tengine:tengine /var/www/
SSL certificate errorsInvalid certificate pathCheck paths in /etc/letsencrypt/live/
502 Bad GatewayUpstream servers downCheck upstream status and backend servers
High memory usageWorker process misconfigurationAdjust worker_connections and buffer sizes
Cannot bind to port 80/443Port already in usesudo netstat -tlnp | grep :80 to find process
Compilation failsMissing dependenciesInstall build-essential and development libraries

Next steps

Running this in production?

Want this handled for you? Setting up Tengine once is straightforward. Keeping it patched, monitored, backed up and tuned across environments is the harder part. See how we run infrastructure like this for European SaaS and e-commerce teams.

Automated install script

Run this to automate the entire setup

Need help?

Don't want to manage this yourself?

We handle managed cloud infrastructure for businesses that depend on uptime. From initial setup to ongoing operations.