Envoy Proxy Installation and Configuration

Envoy is a Layer 7 proxy and communication bus designed for large modern service-oriented architectures. Originally developed at Lyft and now a CNCF project, Envoy provides advanced traffic management, security policies, and observability features. This guide covers installation, core concepts of listeners and clusters, routing configuration, health checking, and operational aspects.

Table of Contents

  1. Introduction to Envoy
  2. System Requirements
  3. Installation Methods
  4. Binary Installation
  5. Docker Installation
  6. Configuration Structure
  7. Listeners and Entrypoints
  8. Clusters and Upstream Services
  9. Routes and Virtual Hosts
  10. Filters and Extensions
  11. Health Checking
  12. Admin Interface
  13. Troubleshooting

Introduction to Envoy

Envoy is a self-contained process designed to run alongside each service. Unlike traditional reverse proxies handling traffic at infrastructure boundaries, Envoy operates at the service level, providing visibility and control over service-to-service communication. Key features include:

  • Advanced load balancing algorithms
  • Automatic retries and circuit breaking
  • Health checks and outlier detection
  • Comprehensive observability and metrics
  • Dynamic configuration via API
  • Protocol support: HTTP/1.1, HTTP/2, HTTP/3, gRPC, TCP

System Requirements

Ensure your system meets these requirements:

  • Linux kernel 3.10 or newer
  • 256 MB RAM minimum (512 MB recommended)
  • 50 MB disk space for binary
  • Network connectivity to upstream services
  • Root or sudo access for privileged ports

Envoy supports x86_64, ARM64, and other architectures.

Installation Methods

Envoy can be installed via package managers, Docker, or built from source.

Binary Installation

Download the latest Envoy release:

cd /tmp
wget https://github.com/envoyproxy/envoy/releases/download/v1.27.0/envoy-1.27.0-linux-x86_64
chmod +x envoy-1.27.0-linux-x86_64
sudo mv envoy-1.27.0-linux-x86_64 /usr/local/bin/envoy

Verify installation:

envoy --version

Create a dedicated user and directories:

sudo useradd -r -s /bin/false -d /var/lib/envoy envoy
sudo mkdir -p /etc/envoy
sudo mkdir -p /var/lib/envoy
sudo mkdir -p /var/log/envoy
sudo chown -R envoy:envoy /var/lib/envoy /var/log/envoy /etc/envoy

Create a systemd service file:

sudo tee /etc/systemd/system/envoy.service > /dev/null <<'EOF'
[Unit]
Description=Envoy Proxy
Documentation=https://www.envoyproxy.io/
After=network-online.target
Wants=network-online.target

[Service]
Type=simple
User=envoy
Group=envoy
ExecStart=/usr/local/bin/envoy -c /etc/envoy/envoy.yaml --log-level info
Restart=on-failure
RestartSec=5s
StandardOutput=journal
StandardError=journal
SyslogIdentifier=envoy

[Install]
WantedBy=multi-user.target
EOF

sudo systemctl daemon-reload
sudo systemctl enable envoy

Docker Installation

Deploy Envoy using Docker:

docker run -d \
  --name envoy \
  -p 80:10000 \
  -p 443:10001 \
  -p 8001:8001 \
  -v /etc/envoy/envoy.yaml:/etc/envoy/envoy.yaml:ro \
  -v /var/log/envoy:/var/log/envoy \
  envoyproxy/envoy:v1.27-latest \
  /usr/local/bin/envoy -c /etc/envoy/envoy.yaml

Use Docker Compose for multi-container deployments:

version: '3.8'

services:
  envoy:
    image: envoyproxy/envoy:v1.27-latest
    restart: always
    ports:
      - "80:10000"
      - "443:10001"
      - "8001:8001"
    volumes:
      - /etc/envoy/envoy.yaml:/etc/envoy/envoy.yaml:ro
      - /var/log/envoy:/var/log/envoy
    networks:
      - service_mesh
    command: /usr/local/bin/envoy -c /etc/envoy/envoy.yaml --log-level info

networks:
  service_mesh:
    driver: bridge

Configuration Structure

Envoy configuration is YAML-based with four main sections:

Create /etc/envoy/envoy.yaml:

static_resources:
  listeners:
    - name: listener_0
      address:
        socket_address:
          protocol: TCP
          address: 0.0.0.0
          port_value: 10000
      filter_chains:
        - filters:
            - name: envoy.filters.network.http_connection_manager
              typed_config:
                "@type": type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager
                stat_prefix: ingress_http
                route_config:
                  name: local_route
                  virtual_hosts:
                    - name: backend
                      domains: ["*"]
                      routes:
                        - match:
                            prefix: "/"
                          route:
                            cluster: backend_service
                http_filters:
                  - name: envoy.filters.http.router
                    typed_config:
                      "@type": type.googleapis.com/envoy.extensions.filters.http.router.v3.Router

  clusters:
    - name: backend_service
      connect_timeout: 1s
      type: STRICT_DNS
      lb_policy: ROUND_ROBIN
      load_assignment:
        cluster_name: backend_service
        endpoints:
          - lb_endpoints:
              - endpoint:
                  address:
                    socket_address:
                      address: 192.168.1.100
                      port_value: 8080

admin:
  address:
    socket_address:
      protocol: TCP
      address: 127.0.0.1
      port_value: 9001

Start Envoy:

sudo systemctl start envoy

Listeners and Entrypoints

Listeners define where Envoy accepts incoming connections:

static_resources:
  listeners:
    - name: http_listener
      address:
        socket_address:
          protocol: TCP
          address: 0.0.0.0
          port_value: 80
      filter_chains:
        - filters:
            - name: envoy.filters.network.http_connection_manager
              typed_config:
                "@type": type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager
                stat_prefix: ingress_http
                
    - name: https_listener
      address:
        socket_address:
          protocol: TCP
          address: 0.0.0.0
          port_value: 443
      filter_chains:
        - transport_socket:
            name: envoy.transport_sockets.tls
            typed_config:
              "@type": type.googleapis.com/envoy.extensions.transport_sockets.tls.v3.DownstreamTlsContext
              common_tls_context:
                tls_certificates:
                  - certificate_chain:
                      filename: /etc/envoy/certs/example.crt
                    private_key:
                      filename: /etc/envoy/certs/example.key
          filters:
            - name: envoy.filters.network.http_connection_manager
              typed_config:
                "@type": type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager
                stat_prefix: ingress_https

Clusters and Upstream Services

Clusters define groups of upstream services:

clusters:
  - name: backend_service
    connect_timeout: 1s
    type: STRICT_DNS
    lb_policy: ROUND_ROBIN
    load_assignment:
      cluster_name: backend_service
      endpoints:
        - lb_endpoints:
            - endpoint:
                address:
                  socket_address:
                    address: 192.168.1.100
                    port_value: 8080
                weight: 3
            - endpoint:
                address:
                  socket_address:
                    address: 192.168.1.101
                    port_value: 8080
                weight: 1

  - name: api_service
    connect_timeout: 2s
    type: STRICT_DNS
    lb_policy: LEAST_REQUEST
    load_assignment:
      cluster_name: api_service
      endpoints:
        - lb_endpoints:
            - endpoint:
                address:
                  socket_address:
                    address: 192.168.1.110
                    port_value: 8000
            - endpoint:
                address:
                  socket_address:
                    address: 192.168.1.111
                    port_value: 8000
    circuit_breakers:
      thresholds:
        - max_connections: 1000
          max_pending_requests: 100
          max_requests: 1000
          max_retries: 3

Routes and Virtual Hosts

Define routing rules for different domains and paths:

route_config:
  name: local_route
  virtual_hosts:
    - name: example_com
      domains: ["example.com", "www.example.com"]
      routes:
        - name: api_route
          match:
            prefix: "/api/v1"
          route:
            cluster: api_service
            timeout: 5s
            retry_policy:
              retry_on: "5xx"
              num_retries: 3
              per_try_timeout: 2s
        
        - name: static_route
          match:
            prefix: "/static"
          route:
            cluster: static_service
            timeout: 10s
        
        - name: default_route
          match:
            prefix: "/"
          route:
            cluster: backend_service
            timeout: 30s

    - name: api_example_com
      domains: ["api.example.com"]
      routes:
        - match:
            prefix: "/"
          route:
            cluster: api_service
            prefix_rewrite: "/"

Filters and Extensions

Filters provide traffic processing capabilities:

http_filters:
  - name: envoy.filters.http.authentication
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.ext_authz.v3.ExtAuthz
      transport_api_version: V3
      grpc_service:
        envoy_grpc:
          cluster_name: auth_service
        timeout: 2s
  
  - name: envoy.filters.http.rate_limit
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
      stat_prefix: http_local_rate_limiter
      token_bucket:
        max_tokens: 100
        tokens_per_fill: 10
        fill_interval: 1s
      filter_enabled:
        runtime_key: local_rate_limit_enabled
        default_value:
          numerator: 100
          denominator: HUNDRED
      filter_enforced:
        runtime_key: local_rate_limit_enforced
        default_value:
          numerator: 100
          denominator: HUNDRED
  
  - name: envoy.filters.http.router
    typed_config:
      "@type": type.googleapis.com/envoy.extensions.filters.http.router.v3.Router

Health Checking

Configure active health checking:

clusters:
  - name: backend_service
    connect_timeout: 1s
    type: STRICT_DNS
    lb_policy: ROUND_ROBIN
    load_assignment:
      cluster_name: backend_service
      endpoints:
        - lb_endpoints:
            - endpoint:
                address:
                  socket_address:
                    address: 192.168.1.100
                    port_value: 8080
            - endpoint:
                address:
                  socket_address:
                    address: 192.168.1.101
                    port_value: 8080
    
    health_checks:
      - timeout: 1s
        interval: 10s
        unhealthy_threshold: 3
        healthy_threshold: 2
        http_health_check:
          path: "/health"
          expected_statuses:
            - start: 200
              end: 299
    
    outlier_detection:
      consecutive_5xx: 5
      interval: 30s
      base_ejection_time: 30s
      max_ejection_percent: 50
      split_external_local_origin_errors: true

Admin Interface

Access the Envoy admin interface for monitoring:

admin:
  address:
    socket_address:
      protocol: TCP
      address: 127.0.0.1
      port_value: 9001

Access admin endpoints:

# Get admin help
curl http://localhost:9001/

# View configuration
curl http://localhost:9001/config_dump

# View statistics
curl http://localhost:9001/stats

# View runtime settings
curl http://localhost:9001/runtime

# View clusters
curl http://localhost:9001/clusters

# Get listener information
curl http://localhost:9001/listeners

Troubleshooting

Check Envoy service status:

sudo systemctl status envoy
sudo journalctl -u envoy -f

Validate configuration:

envoy -c /etc/envoy/envoy.yaml --mode validate

Test configuration with dry run:

envoy -c /etc/envoy/envoy.yaml --mode init_only

Check listening ports:

sudo netstat -tlnp | grep envoy

Query admin interface:

curl -s http://localhost:9001/stats | grep -i error
curl -s http://localhost:9001/clusters | grep -i status

Test backend connectivity:

curl -v http://localhost:10000/

Enable debug logging:

sudo systemctl stop envoy
sudo /usr/local/bin/envoy -c /etc/envoy/envoy.yaml --log-level debug

Conclusion

Envoy provides a sophisticated proxy platform for modern microservices architectures. Its flexible configuration model, advanced load balancing capabilities, health checking, circuit breaking, and comprehensive observability make it ideal for complex service-to-service communication patterns. Whether operating as an edge proxy, API gateway, or service mesh proxy, Envoy delivers the control and visibility required for reliable distributed systems.