{"_id":"5a8fae0368264c001f20cc0c","category":{"_id":"5a8fae0268264c001f20cc02","version":"5a8fae0268264c001f20cc00","project":"5633ebff7e9e880d00af1a53","__v":0,"sync":{"url":"","isSync":false},"reference":false,"createdAt":"2015-12-23T20:06:16.013Z","from_sync":false,"order":4,"slug":"quickstart-guides-1","title":"Quickstart Guides"},"project":"5633ebff7e9e880d00af1a53","parentDoc":null,"user":"5633ec9b35355017003ca3f2","version":{"_id":"5a8fae0268264c001f20cc00","project":"5633ebff7e9e880d00af1a53","__v":4,"createdAt":"2018-02-23T06:00:34.961Z","releaseDate":"2018-02-23T06:00:34.961Z","categories":["5a8fae0268264c001f20cc01","5a8fae0268264c001f20cc02","5a8fae0368264c001f20cc03","5a8fae0368264c001f20cc04","5a8fae0368264c001f20cc05","5a8fae0368264c001f20cc06","5a8fae0368264c001f20cc07","5a8fae0368264c001f20cc08","5a8fae0368264c001f20cc09","5abaa7eb72d6dc0028a07bf3","5b8ee7842790f8000333f9ba","5b8ee8f244a21a00034b5cd9"],"is_deprecated":false,"is_hidden":false,"is_beta":false,"is_stable":true,"codename":"","version_clean":"2.0.0","version":"2.0"},"githubsync":"","__v":0,"updates":[],"next":{"pages":[],"description":""},"createdAt":"2015-12-30T05:54:28.154Z","link_external":false,"link_url":"","sync_unique":"","hidden":false,"api":{"results":{"codes":[]},"settings":"","auth":"required","params":[],"url":""},"isReference":false,"order":2,"body":"Creating an index on Elasticsearch is the first step towards leveraging the awesome power of Elasticsearch. While there is a wealth of resources online for creating an index on Elasticsearch, if you're new to Elasticsearch, make sure to check out the [definition of an index](doc:basic-glossary#index) in our docs. \n\nIf you're already familiar with the basics, we have a blog post / white paper on [The Ideal Elasticsearch Index](https://bonsai.io/blog/ideal-elasticsearch-cluster/), which has a ton of information and things to think about when creating an index.\n\nNote that many [Elasticsearch clients](doc:basic-glossary#elasticsearch-client) will take care of creating an index for you. You should review your client’s documentation for more information on its index usage conventions. If you don’t know how many indexes your application needs, we recommend creating one index per model or database table.\n[block:callout]\n{\n  \"type\": \"warning\",\n  \"title\": \"Important Note on Index Auto-Creation\",\n  \"body\": \"By default, Elasticsearch has a feature that will automatically create indices. Simply pushing data into a non-existing index will cause that index to be created with mappings inferred from the data. In accordance with Elasticsearch best practices for production applications, we've disabled this feature on Bonsai. \\n\\nHowever, some popular tools such as [Kibana](doc:using-kibana-with-bonsai) and  [Logstash](doc:using-logstash-with-bonsai) do not support explicit index creation, and rely on auto-creation being available. To accommodate these tools, we've whitelisted popular time-series index names such as `logstash*`, `requests*`, `events*`, `.kibana*` and `kibana-int*`.\"\n}\n[/block]\nFor the purposes of this discussion, we'll assume that you don't have an Elasticsearch client that can create the index for you. This guide will proceed with the manual steps for [creating an index](doc:creating-your-first-index#manually-creating-an-index), [changing settings](creating-your-first-index#updating-the-index-settings), [populating it with data](doc:creating-your-first-index#adding-data-to-your-index), and finally [destroying your index](doc:creating-your-first-index#destroying-your-index).\n[block:api-header]\n{\n  \"title\": \"Manually Creating an Index\"\n}\n[/block]\nThere are two main ways to manually create an index in your Bonsai cluster. The first is with a command line tool like `curl` or `httpie`. Curl is a standard tool that is bundled with many *nix-like operating systems. OSX and many Linux distributions should have it. It can even be installed on Windows. If you do not have curl, and don't have a package manager capable of installing it, you can [download it here](https://curl.haxx.se/download.html).\n\nThe second is through the Interactive Console. The Interactive Console is a feature provided by Bonsai and found in your cluster dashboard. You can find more information about the Interactive Console for your cluster by clicking the appropriate link below:\n\n* [Direct Signups](doc:managing-your-cluster#interactive-console) \n* [Heroku Users](doc:bonsai-elasticsearch-dashboard#interactive-console) \n* [Manifold Users](doc:managing-your-cluster-1#interactive-console) \n\nLet’s create an example index called `acme-production` from the command line with curl. \n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \" $ curl -X PUT http://user:password:::at:::redwood-12345.us-east-1.bonsai.io/acme-production\\n{\\\"acknowledged\\\":true}\",\n      \"language\": \"curl\",\n      \"name\": \"bash\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/1b9a4c7-creating-your-first-index-1.png\",\n        \"creating-your-first-index-1.png\",\n        1236,\n        418,\n        \"#dde4e2\"\n      ],\n      \"caption\": \"Creating the index via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\n\n[block:callout]\n{\n  \"type\": \"info\",\n  \"title\": \"Authentication required\",\n  \"body\": \"All Bonsai clusters have a randomly generated username and password. By default, these credentials need to be included with _all_ requests in order to be processed. If you're seeing something like:\\n\\n```\\nHTTP 401: Authorization required\\n```\\n\\nthen your credentials were not supplied. You can view the fully-qualified URL in your cluster dashboard. It will look like this: `http://user:password@redwood-12345.us-east-1.bonsai.io`\"\n}\n[/block]\n\n[block:api-header]\n{\n  \"title\": \"Updating the Index Settings\"\n}\n[/block]\nWe can inspect the index settings with a GET call to `/_cat/indices` like so:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XGET http://user:password@redwood-12345.us-east-1.bonsai.io/_cat/indices?v\\nhealth status index             pri rep docs.count docs.deleted store.size pri.store.size \\ngreen  open   acme-production   1   1          0            0        260b 130b\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/c28ce45-creating-your-first-index-2.png\",\n        \"creating-your-first-index-2.png\",\n        1352,\n        598,\n        \"#dcdddd\"\n      ],\n      \"caption\": \"Checking on the index via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nThe `?v` at the end of the URL tells Elasticsearch to return the headers of the data it's returning. It's not required, but it helps explain the data.\n\nIn the example above, Elasticsearch shows that the `acme-production` index was created with one primary shard and one replica shard. It doesn't have any documents yet, and is only a few bytes in size.\n\nLet's add a replica to the index:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XPUT http://user:password@redwood-12345.us-east-1.bonsai.io/acme-production/_settings -d '{\\\"index\\\":{\\\"number_of_replicas\\\":2}}'\\n{\\\"acknowledged\\\":true}\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/9938f2c-creating-your-first-index-3.png\",\n        \"creating-your-first-index-3.png\",\n        1200,\n        514,\n        \"#062c34\"\n      ],\n      \"caption\": \"Updating the index settings via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nNow, when we re-query the `/_cat/indices` endpoint, we can see that there are now two replicas, where before there was only one:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XGET http://user:password@redwood-12345.us-east-1.bonsai.io/_cat/indices?v\\nhealth status index             pri rep docs.count docs.deleted store.size pri.store.size \\ngreen  open   acme-production   1   2          0            0        390b 130b\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/00d9c02-creating-your-first-index-4.png\",\n        \"creating-your-first-index-4.png\",\n        1312,\n        636,\n        \"#dcdddd\"\n      ],\n      \"caption\": \"Checking on the index via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nSimilarly, if we wanted to remove all the replicas, we could simply modify the JSON payload like so:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XPUT http://user:password@redwood-12345.us-east-1.bonsai.io/acme-production/_settings -d '{\\\"index\\\":{\\\"number_of_replicas\\\":0}}'\\n{\\\"acknowledged\\\":true}\\n\\n$ curl -XGET http://user:password@redwood-12345.us-east-1.bonsai.io/_cat/indices?v\\nhealth status index             pri rep docs.count docs.deleted store.size pri.store.size \\ngreen  open   acme-production   1   0          0            0        318b 159b\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:api-header]\n{\n  \"type\": \"basic\",\n  \"title\": \"Adding Data to Your Index\"\n}\n[/block]\nLet’s insert a “Hello, world” test document to verify that your new index is available, and to highlight some basic Elasticsearch concepts.\n\nEvery document prior to Elasticsearch 7.x should specify a `type`, and preferably an `id`. You may specify these values with the `_id` and the `_type` keys, or Elasticsearch will infer them from the URL. If you don't explicitly provide an id, Elasticsearch will create a random one for you.\n\nIn the following example, we use POST to add a simple document to the index which specifies a `_type` of `test` and an `_id` of `1`. You should replace the sample URL in this document with your own index URL to follow along:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \" $ curl -XPOST http://user:password@redwood-12345/acme-production/test/1 -d '{\\\"title\\\":\\\"Hello world\\\"}'\\n{\\n  \\\"_index\\\" : \\\"acme-production\\\",\\n  \\\"_type\\\" : \\\"test\\\",\\n  \\\"_id\\\" : \\\"1\\\",\\n  \\\"_version\\\" : 1,\\n  \\\"_shards\\\" : {\\n    \\\"total\\\" : 3,\\n    \\\"successful\\\" : 3,\\n    \\\"failed\\\" : 0\\n  },\\n  \\\"created\\\" : true\\n}\",\n      \"language\": \"curl\",\n      \"name\": \"bash\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/5ad860b-creating-your-first-index-5.png\",\n        \"creating-your-first-index-5.png\",\n        1332,\n        598,\n        \"#052c34\"\n      ],\n      \"caption\": \"Creating a test document via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nBecause we haven't explicitly defined a mapping (schema) for the acme-production index, Elasticsearch will come up with one for us. It will inspect the contents of each field it receives and attempt to infer a data structure for the content. It will then use that for subsequent documents.\n[block:callout]\n{\n  \"type\": \"warning\",\n  \"title\": \"Dynamic Mapping Can Be Dangerous\",\n  \"body\": \"Elasticsearch's ability to generate mappings on the fly is a really nice feature, but it has some drawbacks. One is that the contents of the first field it sees determines how it will interpret the rest. \\n\\nFor example, there have been cases where users attempt to index geospatial data, and Elasticsearch interprets the field as being a float type. Certain documents then fail later in the indexing process with an HTTP 400 error. Or everything succeeds, but geospatial filtering is broken.\\n\\nIt's a best practice to explicitly create your mappings _before_ indexing into a new index, if you're planning to power a production application. Today, most clients and frameworks are pretty good about handling this automatically, but it's a subtle \\\"gotcha\\\" that has made its way into the support queues from time to time.\"\n}\n[/block]\nWe can see the mapping that Elasticsearch generated by using the `_mapping` API:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XGET http://user:password@redwood-12345/acme-production/_mapping\\n{\\\"acme-production\\\":{\\\"mappings\\\":{\\\"test\\\":{\\\"properties\\\":{\\\"title\\\":{\\\"type\\\":\\\"string\\\"}}}}}}\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/844e05f-creating-your-first-index-6.png\",\n        \"creating-your-first-index-6.png\",\n        1290,\n        642,\n        \"#dbdcdc\"\n      ],\n      \"caption\": \"Inspecting the index mappings via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nThe inspection of the index mapping shows that Elasticsearch has generated a schema from our sample JSON, and that it has decided that documents in the \"acme-production\" index of type \"test\" will have a string body in the \"title\" field. This is reasonable, so we'll leave it alone.\n\nNext, you may view this document by accessing it directly. In the example below, note the `?pretty` parameter at the end of the URL. This tells Elasticsearch to pretty print the results, making them more legible:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$curl -XGET 'http://user:password@redwood-12345/acme-production/test/1?pretty'\\n{\\n  \\\"_index\\\" : \\\"acme-production\\\",\\n  \\\"_type\\\" : \\\"test\\\",\\n  \\\"_id\\\" : \\\"1\\\",\\n  \\\"_version\\\" : 1,\\n  \\\"found\\\" : true,\\n  \\\"_source\\\" : {\\n    \\\"title\\\" : \\\"Hello world\\\"\\n  }\\n}\",\n      \"language\": \"curl\",\n      \"name\": \"bash\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/b22334c-creating-your-first-index-7.png\",\n        \"creating-your-first-index-7.png\",\n        1336,\n        556,\n        \"#dcdddd\"\n      ],\n      \"caption\": \"Inspecting the test document via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nAlternatively, you can see it in the search results with the `_search` endpoint:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$curl -XGET 'http://user:password@redwood-12345/acme-production/_search?pretty\\n{\\n  \\\"took\\\" : 1,\\n  \\\"timed_out\\\" : false,\\n  \\\"_shards\\\" : {\\n    \\\"total\\\" : 1,\\n    \\\"successful\\\" : 1,\\n    \\\"failed\\\" : 0\\n  },\\n  \\\"hits\\\" : {\\n    \\\"total\\\" : 3,\\n    \\\"max_score\\\" : 1.0,\\n    \\\"hits\\\" : [ {\\n      \\\"_index\\\" : \\\"acme-production\\\",\\n      \\\"_type\\\" : \\\"test\\\",\\n      \\\"_id\\\" : \\\"1\\\",\\n      \\\"_score\\\" : 1.0,\\n      \\\"_source\\\" : {\\n        \\\"title\\\" : \\\"Hello world\\\"\\n      }\\n    }\\n  }\\n}\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/049c715-creating-your-first-index-8.png\",\n        \"creating-your-first-index-8.png\",\n        1440,\n        984,\n        \"#dbdcdc\"\n      ],\n      \"caption\": \"Searching for the test document via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\n\n[block:callout]\n{\n  \"type\": \"info\",\n  \"body\": \"Note the `_source` key, which contains a copy of your original document. Elasticsearch makes an excellent general-purpose document store, although should never be used as a _primary store_. Use something [ACID-compliant](https://en.wikipedia.org/wiki/ACID) for that. \\n\\nThe _source field does also add some overhead. It can be disabled in the mappings. See the [Elasticsearch documentation](https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping-source-field.html) for more details.\",\n  \"title\": \"Check the _source\"\n}\n[/block]\nTo learn more about about the operations supported by your index, you should read the [Elasticsearch Index API documentation](http://www.elasticsearch.org/guide/reference/api/index_.html). Note that some operations mentioned in the documentation (such as “Automatic Index Creation”) are restricted on Bonsai for technical reasons.\n[block:api-header]\n{\n  \"title\": \"Destroying Your Index\"\n}\n[/block]\nWhen you have decided you no longer need the \"acme-production\" index, you can destroy it with a one liner:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XDELETE http://user:password@redwood-12345/acme-production\\n{\\\"acknowledged\\\":true}\",\n      \"language\": \"curl\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/ecc1f1d-creating-your-first-index-9.png\",\n        \"creating-your-first-index-9.png\",\n        1298,\n        368,\n        \"#dde4e2\"\n      ],\n      \"caption\": \"Destroying the index via the Interactive Console.\"\n    }\n  ]\n}\n[/block]\nThe `DELETE` verb will delete one or more indices in your cluster. If you have several indices to delete, you can still perform the action in one line by concatenating the indices with a comma, like so:\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"$ curl -XDELETE http://user:password@redwood-12345/acme-production-1,acme-production-2,acme-production-3\",\n      \"language\": \"text\"\n    }\n  ]\n}\n[/block]\n\n[block:callout]\n{\n  \"type\": \"danger\",\n  \"title\": \"There's No 'Undo' Button\",\n  \"body\": \"Destroying an index can not be undone, unless you restore it from a snapshot (if one exists). Do not delete indices without fully understanding the consequences. If there is a chance that your cluster is supporting a production application, be _very_ careful before taking this kind of action. Accidental deletes are a major reason Bonsai doesn't support `_all` or wildcard (*) destructive actions.\"\n}\n[/block]","excerpt":"","slug":"creating-your-first-index","type":"basic","title":"Creating Your First Index"}

Creating Your First Index


Creating an index on Elasticsearch is the first step towards leveraging the awesome power of Elasticsearch. While there is a wealth of resources online for creating an index on Elasticsearch, if you're new to Elasticsearch, make sure to check out the [definition of an index](doc:basic-glossary#index) in our docs. If you're already familiar with the basics, we have a blog post / white paper on [The Ideal Elasticsearch Index](https://bonsai.io/blog/ideal-elasticsearch-cluster/), which has a ton of information and things to think about when creating an index. Note that many [Elasticsearch clients](doc:basic-glossary#elasticsearch-client) will take care of creating an index for you. You should review your client’s documentation for more information on its index usage conventions. If you don’t know how many indexes your application needs, we recommend creating one index per model or database table. [block:callout] { "type": "warning", "title": "Important Note on Index Auto-Creation", "body": "By default, Elasticsearch has a feature that will automatically create indices. Simply pushing data into a non-existing index will cause that index to be created with mappings inferred from the data. In accordance with Elasticsearch best practices for production applications, we've disabled this feature on Bonsai. \n\nHowever, some popular tools such as [Kibana](doc:using-kibana-with-bonsai) and [Logstash](doc:using-logstash-with-bonsai) do not support explicit index creation, and rely on auto-creation being available. To accommodate these tools, we've whitelisted popular time-series index names such as `logstash*`, `requests*`, `events*`, `.kibana*` and `kibana-int*`." } [/block] For the purposes of this discussion, we'll assume that you don't have an Elasticsearch client that can create the index for you. This guide will proceed with the manual steps for [creating an index](doc:creating-your-first-index#manually-creating-an-index), [changing settings](creating-your-first-index#updating-the-index-settings), [populating it with data](doc:creating-your-first-index#adding-data-to-your-index), and finally [destroying your index](doc:creating-your-first-index#destroying-your-index). [block:api-header] { "title": "Manually Creating an Index" } [/block] There are two main ways to manually create an index in your Bonsai cluster. The first is with a command line tool like `curl` or `httpie`. Curl is a standard tool that is bundled with many *nix-like operating systems. OSX and many Linux distributions should have it. It can even be installed on Windows. If you do not have curl, and don't have a package manager capable of installing it, you can [download it here](https://curl.haxx.se/download.html). The second is through the Interactive Console. The Interactive Console is a feature provided by Bonsai and found in your cluster dashboard. You can find more information about the Interactive Console for your cluster by clicking the appropriate link below: * [Direct Signups](doc:managing-your-cluster#interactive-console) * [Heroku Users](doc:bonsai-elasticsearch-dashboard#interactive-console) * [Manifold Users](doc:managing-your-cluster-1#interactive-console) Let’s create an example index called `acme-production` from the command line with curl. [block:code] { "codes": [ { "code": " $ curl -X PUT http://user:password@redwood-12345.us-east-1.bonsai.io/acme-production\n{\"acknowledged\":true}", "language": "curl", "name": "bash" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/1b9a4c7-creating-your-first-index-1.png", "creating-your-first-index-1.png", 1236, 418, "#dde4e2" ], "caption": "Creating the index via the Interactive Console." } ] } [/block] [block:callout] { "type": "info", "title": "Authentication required", "body": "All Bonsai clusters have a randomly generated username and password. By default, these credentials need to be included with _all_ requests in order to be processed. If you're seeing something like:\n\n```\nHTTP 401: Authorization required\n```\n\nthen your credentials were not supplied. You can view the fully-qualified URL in your cluster dashboard. It will look like this: `http://user:password@redwood-12345.us-east-1.bonsai.io`" } [/block] [block:api-header] { "title": "Updating the Index Settings" } [/block] We can inspect the index settings with a GET call to `/_cat/indices` like so: [block:code] { "codes": [ { "code": "$ curl -XGET http://user:password@redwood-12345.us-east-1.bonsai.io/_cat/indices?v\nhealth status index pri rep docs.count docs.deleted store.size pri.store.size \ngreen open acme-production 1 1 0 0 260b 130b", "language": "curl" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/c28ce45-creating-your-first-index-2.png", "creating-your-first-index-2.png", 1352, 598, "#dcdddd" ], "caption": "Checking on the index via the Interactive Console." } ] } [/block] The `?v` at the end of the URL tells Elasticsearch to return the headers of the data it's returning. It's not required, but it helps explain the data. In the example above, Elasticsearch shows that the `acme-production` index was created with one primary shard and one replica shard. It doesn't have any documents yet, and is only a few bytes in size. Let's add a replica to the index: [block:code] { "codes": [ { "code": "$ curl -XPUT http://user:password@redwood-12345.us-east-1.bonsai.io/acme-production/_settings -d '{\"index\":{\"number_of_replicas\":2}}'\n{\"acknowledged\":true}", "language": "curl" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/9938f2c-creating-your-first-index-3.png", "creating-your-first-index-3.png", 1200, 514, "#062c34" ], "caption": "Updating the index settings via the Interactive Console." } ] } [/block] Now, when we re-query the `/_cat/indices` endpoint, we can see that there are now two replicas, where before there was only one: [block:code] { "codes": [ { "code": "$ curl -XGET http://user:password@redwood-12345.us-east-1.bonsai.io/_cat/indices?v\nhealth status index pri rep docs.count docs.deleted store.size pri.store.size \ngreen open acme-production 1 2 0 0 390b 130b", "language": "curl" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/00d9c02-creating-your-first-index-4.png", "creating-your-first-index-4.png", 1312, 636, "#dcdddd" ], "caption": "Checking on the index via the Interactive Console." } ] } [/block] Similarly, if we wanted to remove all the replicas, we could simply modify the JSON payload like so: [block:code] { "codes": [ { "code": "$ curl -XPUT http://user:password@redwood-12345.us-east-1.bonsai.io/acme-production/_settings -d '{\"index\":{\"number_of_replicas\":0}}'\n{\"acknowledged\":true}\n\n$ curl -XGET http://user:password@redwood-12345.us-east-1.bonsai.io/_cat/indices?v\nhealth status index pri rep docs.count docs.deleted store.size pri.store.size \ngreen open acme-production 1 0 0 0 318b 159b", "language": "curl" } ] } [/block] [block:api-header] { "type": "basic", "title": "Adding Data to Your Index" } [/block] Let’s insert a “Hello, world” test document to verify that your new index is available, and to highlight some basic Elasticsearch concepts. Every document prior to Elasticsearch 7.x should specify a `type`, and preferably an `id`. You may specify these values with the `_id` and the `_type` keys, or Elasticsearch will infer them from the URL. If you don't explicitly provide an id, Elasticsearch will create a random one for you. In the following example, we use POST to add a simple document to the index which specifies a `_type` of `test` and an `_id` of `1`. You should replace the sample URL in this document with your own index URL to follow along: [block:code] { "codes": [ { "code": " $ curl -XPOST http://user:password@redwood-12345/acme-production/test/1 -d '{\"title\":\"Hello world\"}'\n{\n \"_index\" : \"acme-production\",\n \"_type\" : \"test\",\n \"_id\" : \"1\",\n \"_version\" : 1,\n \"_shards\" : {\n \"total\" : 3,\n \"successful\" : 3,\n \"failed\" : 0\n },\n \"created\" : true\n}", "language": "curl", "name": "bash" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/5ad860b-creating-your-first-index-5.png", "creating-your-first-index-5.png", 1332, 598, "#052c34" ], "caption": "Creating a test document via the Interactive Console." } ] } [/block] Because we haven't explicitly defined a mapping (schema) for the acme-production index, Elasticsearch will come up with one for us. It will inspect the contents of each field it receives and attempt to infer a data structure for the content. It will then use that for subsequent documents. [block:callout] { "type": "warning", "title": "Dynamic Mapping Can Be Dangerous", "body": "Elasticsearch's ability to generate mappings on the fly is a really nice feature, but it has some drawbacks. One is that the contents of the first field it sees determines how it will interpret the rest. \n\nFor example, there have been cases where users attempt to index geospatial data, and Elasticsearch interprets the field as being a float type. Certain documents then fail later in the indexing process with an HTTP 400 error. Or everything succeeds, but geospatial filtering is broken.\n\nIt's a best practice to explicitly create your mappings _before_ indexing into a new index, if you're planning to power a production application. Today, most clients and frameworks are pretty good about handling this automatically, but it's a subtle \"gotcha\" that has made its way into the support queues from time to time." } [/block] We can see the mapping that Elasticsearch generated by using the `_mapping` API: [block:code] { "codes": [ { "code": "$ curl -XGET http://user:password@redwood-12345/acme-production/_mapping\n{\"acme-production\":{\"mappings\":{\"test\":{\"properties\":{\"title\":{\"type\":\"string\"}}}}}}", "language": "curl" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/844e05f-creating-your-first-index-6.png", "creating-your-first-index-6.png", 1290, 642, "#dbdcdc" ], "caption": "Inspecting the index mappings via the Interactive Console." } ] } [/block] The inspection of the index mapping shows that Elasticsearch has generated a schema from our sample JSON, and that it has decided that documents in the "acme-production" index of type "test" will have a string body in the "title" field. This is reasonable, so we'll leave it alone. Next, you may view this document by accessing it directly. In the example below, note the `?pretty` parameter at the end of the URL. This tells Elasticsearch to pretty print the results, making them more legible: [block:code] { "codes": [ { "code": "$curl -XGET 'http://user:password@redwood-12345/acme-production/test/1?pretty'\n{\n \"_index\" : \"acme-production\",\n \"_type\" : \"test\",\n \"_id\" : \"1\",\n \"_version\" : 1,\n \"found\" : true,\n \"_source\" : {\n \"title\" : \"Hello world\"\n }\n}", "language": "curl", "name": "bash" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/b22334c-creating-your-first-index-7.png", "creating-your-first-index-7.png", 1336, 556, "#dcdddd" ], "caption": "Inspecting the test document via the Interactive Console." } ] } [/block] Alternatively, you can see it in the search results with the `_search` endpoint: [block:code] { "codes": [ { "code": "$curl -XGET 'http://user:password@redwood-12345/acme-production/_search?pretty\n{\n \"took\" : 1,\n \"timed_out\" : false,\n \"_shards\" : {\n \"total\" : 1,\n \"successful\" : 1,\n \"failed\" : 0\n },\n \"hits\" : {\n \"total\" : 3,\n \"max_score\" : 1.0,\n \"hits\" : [ {\n \"_index\" : \"acme-production\",\n \"_type\" : \"test\",\n \"_id\" : \"1\",\n \"_score\" : 1.0,\n \"_source\" : {\n \"title\" : \"Hello world\"\n }\n }\n }\n}", "language": "curl" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/049c715-creating-your-first-index-8.png", "creating-your-first-index-8.png", 1440, 984, "#dbdcdc" ], "caption": "Searching for the test document via the Interactive Console." } ] } [/block] [block:callout] { "type": "info", "body": "Note the `_source` key, which contains a copy of your original document. Elasticsearch makes an excellent general-purpose document store, although should never be used as a _primary store_. Use something [ACID-compliant](https://en.wikipedia.org/wiki/ACID) for that. \n\nThe _source field does also add some overhead. It can be disabled in the mappings. See the [Elasticsearch documentation](https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping-source-field.html) for more details.", "title": "Check the _source" } [/block] To learn more about about the operations supported by your index, you should read the [Elasticsearch Index API documentation](http://www.elasticsearch.org/guide/reference/api/index_.html). Note that some operations mentioned in the documentation (such as “Automatic Index Creation”) are restricted on Bonsai for technical reasons. [block:api-header] { "title": "Destroying Your Index" } [/block] When you have decided you no longer need the "acme-production" index, you can destroy it with a one liner: [block:code] { "codes": [ { "code": "$ curl -XDELETE http://user:password@redwood-12345/acme-production\n{\"acknowledged\":true}", "language": "curl" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/ecc1f1d-creating-your-first-index-9.png", "creating-your-first-index-9.png", 1298, 368, "#dde4e2" ], "caption": "Destroying the index via the Interactive Console." } ] } [/block] The `DELETE` verb will delete one or more indices in your cluster. If you have several indices to delete, you can still perform the action in one line by concatenating the indices with a comma, like so: [block:code] { "codes": [ { "code": "$ curl -XDELETE http://user:password@redwood-12345/acme-production-1,acme-production-2,acme-production-3", "language": "text" } ] } [/block] [block:callout] { "type": "danger", "title": "There's No 'Undo' Button", "body": "Destroying an index can not be undone, unless you restore it from a snapshot (if one exists). Do not delete indices without fully understanding the consequences. If there is a chance that your cluster is supporting a production application, be _very_ careful before taking this kind of action. Accidental deletes are a major reason Bonsai doesn't support `_all` or wildcard (*) destructive actions." } [/block]