Secure Access to Kibana on AWS Elasticsearch Service

With Amazon Web Services offering of Elasticsearch you can secure your search domain using resource-based, IP-Based, and IAM user and role-based access policies.

However, these do not apply for Kibana. You can secure your endpoint using IP-Based access policies, and with no VPC support, in order to look into a workaround, you can implement a EC2 Instance that serves as a reverse proxy to your search domain endpoint.

In this post, we will use an EC2 instance, using NGINX as a reverse proxy and using Basic HTTP auth to authenticate clients for Kibana.

Note: ES5 with Kibana Config has been added at the bottom page

Installing Nginx:

$ sudo yum update -y
$ sudo yum install nginx httpd-tools -y

Nginx Configuration:

We will configure the following configuration files on Nginx:

  • /etc/nginx/nginx.conf
  • /etc/nginx/conf.d/kibana.conf

You will need to replace the values of:

  • server_name
  • proxy_pass, proxy_redirect
# Config: /etc/nginx/nginx.conf
worker_processes 1;
error_log /var/log/nginx/error.log;
pid /var/run/nginx.pid;

include /usr/share/nginx/modules/*.conf;

events {

    worker_connections 1024;
}

http {

    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/nginx/access.log  main;
    server_names_hash_bucket_size 128;
    sendfile            on;
    tcp_nopush          on;
    tcp_nodelay         on;
    keepalive_timeout   65;
    types_hash_max_size 2048;

    include             /etc/nginx/mime.types;
    default_type        application/octet-stream;

    include /etc/nginx/conf.d/*.conf;
    index   index.html index.htm;

    server {
        listen       8080 default_server;
        listen       [::]:8080 default_server;
        server_name  localhost;
        root         /usr/share/nginx/html;

        include /etc/nginx/default.d/*.conf;

        location / {
        }

        error_page 404 /404.html;
            location = /40x.html {
        }

        error_page 500 502 503 504 /50x.html;
            location = /50x.html {
        }

    }

}

# Config: /etc/nginx/conf.d/kibana.conf

server {
    listen 80;
    server_name myproxy.mydomain.com;

    location / {
        proxy_pass http://search-domain.eu-west-1.es.amazonaws.com/;
        proxy_redirect http://search-domain.eu-west-1.es.amazonaws.com/ /;
        proxy_http_version 1.1;

        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header Authorization "";
        proxy_hide_header Authorization;
        auth_basic "Username and Password are required";
        auth_basic_user_file /etc/nginx/.htpasswd;
    }
}

With the above configuration, your Nginx server will listen on port 80 for your reverse proxy, and port 8080 for your normal web server.

Elasticsearch Service Access Policy:

Below is a example policy, that will allow access to the Elasticsearch Domain from 1 IP Address:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "",
      "Effect": "Allow",
      "Principal": {
        "AWS": "*"
      },
      "Action": "es:*",
      "Resource": "arn:aws:es:eu-west-1:123456789012:domain/search-domain/*",
      "Condition": {
        "IpAddress": {
          "aws:SourceIp": [
            "196.10.12.13"
          ]
        }
      }
    }
  ]
}

Once you saved the policy, allow the service about 15 minutes to make the changes before its in service.

Adding Users to Authenticate:

$ sudo htpasswd -c /etc/nginx/.htpasswd admin

Start Nginx:

$ /etc/init.d/nginx restart
$ chkconfig nginx on

Once the Nginx service has started, when accessing your proxy on: http://<myproxy>.<mydomain>.com/_plugin/kibana/ you should be prompted for credentials, and after successful login, you should be presented with your Kibana UI.

Update:

Example Nginx Config of Elasticsearch 5 with Kibana can be found on my Nginx Config Repo