Couchdb
Couchdb is a Document database designed for very large scale.
- data stores as JSON objects
- views are pre-made/indexed queries written in javascript
- queries are made via HTTP, filters on views applied with URL params.
Documentation
Tutorials
view intro http://guide.couchdb.org/draft/cookbook.html couchdb queries http://sitr.us/2009/06/30/database-queries-the-couchdb-way.html couchdb best practices https://github.com/eHealthAfrica/couchdb-best-practices
Locations
/etc/couchdb/local.ini
Ports
5984
Install
Archlinux
sudo pacman -S couchdb sudo systemctl enable couchdb.service sudo systemctl start couchdb.service
Usage
cdbcli
An interactive shell for couchdb.
See cdbcli.HTTP
GET # retrieve a file/query POST # update a file PUT # create a file DELETE # delete a filecurl http://127.0.0.1:5984 # test access to database curl -X GET http://127.0.0.1:5984/test_database/document # get a file curl -X PUT http://127.0.0.1:5984/test_database # create a database curl -X DELETE http://127.0.0.1:5984/test_database # delete a database/document curl -X POST http://127.0.0.1:5984/test_database/document \ -H 'Content-Type: application/json' \ -d @/path/to/file.json # update a filespecial things
curl -X GET http://127.0.0.1:5984/_all_dbs # get list of all databases curl -X GET http://127.0.0.1:5984/test_database/_all_docs # get list of all documents/revisions from a database curl -X GET http://127.0.0.1:5984/_uuids # request a uuid from the server
cdbcli
cdbcli lets you treat your couchdb installation like it is a filesystem... kind of... I find that the lack of vi-mode, and aliases makes me struggle more than just simply using curl. but it did help me quickly understand couchdb's concepts, and that is really worth something.
cdbcli -h 127.0.0.1 mkdir test_database cd test_database touch first_doc vim first_doc touch _design/some_related_views
Concepts
Documents
couchdb stores it's information in documents. These are just ordinary json files, the only special part about them is that they require 2x fields (that will be created automatically if not present):
_id
_rev
When POSTing new json files, you do not need to worry about these fields. ex:
{ //"_id": "your_filename", //"_rev": "a long uuid", "name": "will", "age": 30, "shoesize": 13 }# create database and document curl -X PUT http://127.0.0.1:5984/database curl -X PUT http://127.0.0.1:5984/database/document # add above json file curl -X POST http://127.0.0.1:5984/database/document -t 'Content-Type application/json' -d @file.json
Views
summary
This is where couch is much different from other databases. Instead of using SQL, and running queries on the fly, couchdb prefers that you create queries in advance (in javascript). The return is in the form of a key (which the results will be sorted by), and a JSON payload (nested dict, key, list, ...).
The returned documents, and their fields are determined primarily by the map function. This set of results can be further isolated using a filter function.
curl -X GET https://localhost:8601/blog/_design/docs/_view/by_date?startkey="2010/01/01 00:00:00"&endkey="2010/02/00 00:00:00"
- designs can comprise of several views
- each view builds a document
- view-documents can be filtered by the values of their queried keys
designsDesign documents define views.
{ "_id" : "my_database/_design/group_of_queries", // path to design-doc "_rev" : "1-8fc484a77d9d4c348ef9566b669af239", "views": { "all_docs" : { "map" : "function(doc) { emit( doc.id, doc.shoesize ); }" }, "docs_with_shoesizes" : { "map" : "function(doc) { if (doc.shoesize){ emit( doc.id, doc.shoesize ); } }" } } }views
Views are written inside design documents. When queried, they have a subpath
_view/my_view_name
. Views are written in javascript. Views are composed of a map function, and an optional reduce function. They are both written in javascript.my_database/_design/my_design_doc/_view/my_view_name ## path to query a specific view from.map
The map function determines the results that get returned. Every map function returns 2x results (but they can both comprise of other datatypes if you need more info).
- The first returned item is the key. The results are sorted by this alphabetically.
- The second returned item is any data you would like passed along.
- All results are returned with their _id value.
function(doc) { emit( doc.date, [ doc.name, doc.desc ] ); }## curl -X GET http://localhost:8601/db/_design/mydesign/_view/myview { "total_rows": 3, "offset": 0, "rows": [ { "key": "2009/01/15 15:52:20", "id": "hello-world", "value": ["example", "a simple example"] }, { "key": "2009/01/30 18:04:11", "id": "biking", "value": ["sport", "a sport performed on 2x wheels"] }, { "key": "2009/02/17 21:13:39", "id": "bought-a-cat", "value": ["activity", "obtained a pet"] } ] }reduce
The reduce function operates on the results returned by map.
Query Parameters
If you want to retrieve a maximum-of N entries, or you want to restrict your entries to a specific date-range you can add additional information to the URL used in the query.
The query parameters are passed after the _view is named. Start your parameters with a ?. Afterwards, they are separated by &.
key
# Only return results whose key matches this string exactly # searches view 'last' for all entries whose key == 'pittman' curl -X GET http://localhost:5984/testdb/_design/by_name/_view/last?key=pittmanstartkey & endkey
# Only return results between startkey/endkey (alphabetically). /blog/_design/docs/_view/by_date?startkey="2010/01/01 00:00:00"&endkey="2010/02/00 00:00:00"descending=1
# Order is inversed. (Order is normally alphabetical by key). /blog/_design/docs/_view/by_date?descending=1limit=1
# get a single document (the last alphabetical) curl -X GET http:/localhost:5984/testdb/_all_docs?descending=1&limit=1
Query Examples
couchdb example: basics couchdb example: list as key
Designs Quirks
This is a list of things you should probably be aware of before getting too deeply involved in setting up your datastructures:
- Nothing is ever deleted. If you create a key, then delete it, it will remain. Existing keys can be updated.
- all users are 'root' in couchdb until configured otherwise.
- databases are created at the root. There is no other hierarchy (
_design/<design_name>
is actually treated as a document name)
Best Practices
- databases are created to represent a group of like documents. (business cards is the example they refer to in documentation)
- http://sitr.us/2009/06/30/database-queries-the-couchdb-way.html
- https://github.com/eHealthAfrica/couchdb-best-practices
Management
Users
Backup
Replication