Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

easy way to make an elasticsearch server read-only

Tags:

It's really easy to just upload a bunch of json data to an elasticsearch server to have a basic query api, with lots of options

I'd just like to know if there's and easy way to publish it all preventing people from modifying it

From the default setting, the server is open ot receive a DELETE or PUT http message that would modify the data.

Is there some kind of setting to configure it to be read-only? Or shall I configure some kind of http proxy to achieve it?

(I'm an elasticsearch newbie)

like image 739
opensas Avatar asked Jan 02 '13 00:01

opensas


People also ask

How many writes per second can Elasticsearch handle?

Elasticsearch is one of the most widely used distributed systems out there; ranked #11 amongst all database systems and the #1 search engine.

How much RAM do I need for Elasticsearch?

As a Java application, Elasticsearch requires some logical memory (heap) allocation from the system's physical memory. This should be up to half of the physical RAM, capping at 32GB.


1 Answers

If you want to expose the Elasticsearch API as read-only, I think the best way is to put Nginx in front of it, and deny all requests except GET. An example configuration looks like this:

# Run me with:
#
#     $ nginx -c path/to/this/file
#
# All requests except GET are denied.

worker_processes  1;
pid               nginx.pid;

events {
    worker_connections  1024;
}

http {

  server {

    listen       8080;
    server_name  search.example.com;

    error_log   elasticsearch-errors.log;
    access_log  elasticsearch.log;

    location / {
      if ($request_method !~ "GET") {
        return 403;
        break;
      }

      proxy_pass http://localhost:9200;
      proxy_redirect off;

      proxy_set_header  X-Real-IP  $remote_addr;
      proxy_set_header  X-Forwarded-For $proxy_add_x_forwarded_for;
      proxy_set_header  Host $http_host;
    }

  }

}

Then:

curl -i -X GET http://localhost:8080/_search -d '{"query":{"match_all":{}}}'
HTTP/1.1 200 OK

curl -i -X POST http://localhost:8080/test/test/1 -d '{"foo":"bar"}'
HTTP/1.1 403 Forbidden

curl -i -X DELETE http://localhost:8080/test/
HTTP/1.1 403 Forbidden

Note, that a malicious user could still mess up your server, for instance sending incorrect script payloads, which would make Elasticsearch get stuck, but for most purposes, this approach would be fine.

If you would need more control about the proxying, you can either use more complex Nginx configuration, or write a dedicated proxy eg. in Ruby or Node.js.

See this example for a more complex Ruby-based proxy.

like image 82
karmi Avatar answered Oct 12 '22 21:10

karmi