Class: ChillDB::Design
- Inherits:
-
Object
- Object
- ChillDB::Design
- Defined in:
- lib/chill.rb
Overview
Representing a named design in the Couch database, Design is used to setup views. Views index all of the documents in your database, creating ChillDB::List’s for each emitted document. Your views can choose to emit as many entries as you like for each document, or none at all. Views can be as simple as listing all of a certain kind of document, or more complex schemes like extracting every word in a document and generating an index of words in documents for a simple but powerful search engine.
For more information on designs and views, CouchDB: The Definitive Guide is a great resource. guide.couchdb.org/draft/design.html
Example:
KittensApp.design(:lists).views(
# lists all cats with a softness rating of two or more
soft_cats: 'function(doc) {
if (doc.kind == "cat" && doc.softness > 1) emit(doc._id, null);
}'
).commit!
Note that views default to being javascript functions, as this is what couch ships with support for. It is possible to
Instance Attribute Summary collapse
-
#name ⇒ Object
Returns the value of attribute name.
Instance Method Summary collapse
-
#add_views(collection) ⇒ Object
Add more views to an existing design.
-
#commit! ⇒ Object
Commit this design document to the server and start the server’s process of updating the view’s contents.
-
#document ⇒ Object
lazy load document - referencing this causes load from database.
-
#initialize(database, name) ⇒ Design
constructor
A new instance of Design.
-
#language(set = nil) ⇒ Object
get’s the current language of this design document.
-
#query(view, options = {}) ⇒ Object
Query a named view.
-
#views(collection) ⇒ Object
Set the views in this design.
Constructor Details
#initialize(database, name) ⇒ Design
Returns a new instance of Design.
764 765 766 767 |
# File 'lib/chill.rb', line 764 def initialize database, name @database = database @name = name.to_s end |
Instance Attribute Details
#name ⇒ Object
Returns the value of attribute name.
762 763 764 |
# File 'lib/chill.rb', line 762 def name @name end |
Instance Method Details
#add_views(collection) ⇒ Object
Add more views to an existing design. See also #views
778 779 780 781 |
# File 'lib/chill.rb', line 778 def add_views collection document['views'].merge! views_preprocess(collection) return self end |
#commit! ⇒ Object
Commit this design document to the server and start the server’s process of updating the view’s contents. Note that querying the view immediately after a commit may be slow, while the server finishes initially processing it’s contents. The more documents you have, the more time this can take.
850 851 852 853 |
# File 'lib/chill.rb', line 850 def commit! document['_id'] = "_design/#{@name}" document.commit! end |
#document ⇒ Object
lazy load document - referencing this causes load from database
770 771 772 773 774 775 |
# File 'lib/chill.rb', line 770 def document @document ||= ChillDB::Document::load @database, "_design/#{@name}" @document['language'] ||= 'javascript' @document['views'] ||= {} return @document end |
#language(set = nil) ⇒ Object
get’s the current language of this design document. Usually this would be “javascript”. If called with an argument, set’s the language property and returns self.
Example:
KittensApp.design(:lists).language #=> "javascript"
KittensApp.design(:lists).language(:ruby) #=> KittensApp.design(:lists)
KittensApp.design(:lists).language #=> "ruby"
# chain it together with views for extra nyan:
KittensApp.design(:lists).language(:ruby).views(
soft_cats: %q{ proc do |doc|
emit doc['_id'], doc['softness'] if doc['softness'] > 1
end }
)
ChillDB doesn’t currently include a ruby view server, and it needs to be specifically configured and installed before you can use one. More info in an implementation is at theexciter.com/articles/couchdb-views-in-ruby-instead-of-javascript.html
837 838 839 840 841 842 843 844 |
# File 'lib/chill.rb', line 837 def language set = nil if set @document['language'] = set.to_s self else @document['language'] end end |
#query(view, options = {}) ⇒ Object
Query a named view. Returns a ChillDB::List, which works like a Hash or an Array containing each result. Optionally pass in arguments. Check out wiki.apache.org/couchdb/HTTP_view_API#Querying_Options for the definitive list. Some really useful options:
Options:
include_docs: (true or false) load documents which emitted each entry?
key: only return items emitted with this exact key
keys: (Array) only return items emitted with a key in this Array
range: (Range) shortcut for startkey, endkey, and inclusive_end
startkey: return items starting with this key
endkey: return items ending with this key
startkey_docid: (String) return items starting with this document id
endkey_docid: (String) return items ending with this document id
inclusive_end: (true or false) defaults true, endkey included in result?
limit: (Number) of documents to load before stopping
stale: (String) 'ok' or 'update_after' - view need not be up to date.
descending: (true or false) direction of search?
skip: (Number) skip the first few documents - slow - not recomended!
group: (true or false) should reduce grouping by exact identical key?
group_level: (Number) first x items in key Array are used to group rows
reduce: (true or false) should the reduce function be used?
update_seq: (true or false) response includes sequence id of database?
878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 |
# File 'lib/chill.rb', line 878 def query view, = {} if [:range] range = .delete[:range] [:startkey], [:endkey] = range.first, range.last [:startkey], [:endkey] = [:endkey], [:startkey] if [:descending] [:inclusive_end] = !range.exclude_end? end # these options need to be json encoded [:key, :startkey, :endkey, :keys, :descending, :limit, :skip, :group, :group_level, :reduce, :include_docs, :inclusive_end, :update_seq ].each do |name| [name] = [name].to_json if .has_key? name end opts = .map { |key, value| "#{URI.escape(key.to_s)}=#{URI.escape(value.to_s)}" }.join('&') url = "_design/#{URI.escape @name}/_view/#{URI.escape view.to_s}?#{opts}" response = @database.http(url).get() # put the results in to a QueryResults object - a glorified array return ChillDB::List.load(JSON.parse(response.body), database: @database) end |
#views(collection) ⇒ Object
Set the views in this design. Argument is a Hash containing String’s for each javascript (by default) view function. Reduce functions can also be included optionally.
Example:
KittensApp.design(:lists).views(
# just a map function
adults: 'function(doc) {
if (doc.kind == "cat" && doc.age > 4) emit(doc._id, null);
}',
# a map and a reduce - lookup the overall softness of our kitten database
# when queried returns just one value: the number output of the reduce
# function.
softness: {
map: 'function(doc) {
if (doc.kind == "cat") emit(doc._id, doc.softness);
}',
reduce: 'function(key, values, rereduce) {
return sum(values); // add them all together
}'
}
).commit!
KittensApp.design(:lists).query(:adults) #=> <ChillDB::List> [a, b, c...]
KittensApp.design(:lists).query(:softness) #=> 19
Check out wiki.apache.org/couchdb/Introduction_to_CouchDB_views for a great introduction to CouchDB view design.
812 813 814 815 816 |
# File 'lib/chill.rb', line 812 def views collection document['views'] = {} add_views collection return self end |