Improving documentation, VERSION increase
This commit is contained in:
parent
a78e3b74d6
commit
e8959883a9
121
README.md
121
README.md
|
@ -9,7 +9,7 @@ for validations and callbacks.
|
||||||
If your project is still running Rails 2.3, you'll have to continue using ExtendedDocument as
|
If your project is still running Rails 2.3, you'll have to continue using ExtendedDocument as
|
||||||
it is not possible to load ActiveModel into programs that do not use ActiveSupport 3.0.
|
it is not possible to load ActiveModel into programs that do not use ActiveSupport 3.0.
|
||||||
|
|
||||||
CouchRest Model is only tested on CouchDB 1.0.0 or newer.
|
CouchRest Model is only properly tested on CouchDB version 1.0 or newer.
|
||||||
|
|
||||||
## Install
|
## Install
|
||||||
|
|
||||||
|
@ -19,12 +19,11 @@ CouchRest Model is only tested on CouchDB 1.0.0 or newer.
|
||||||
|
|
||||||
### Bundler
|
### Bundler
|
||||||
|
|
||||||
If you're using bundler, just define a line similar to the following in your project's Gemfile:
|
If you're using bundler, define a line similar to the following in your project's Gemfile:
|
||||||
|
|
||||||
gem 'couchrest_model'
|
gem 'couchrest_model'
|
||||||
|
|
||||||
You might also consider using the latest git repository. All tests should pass in the master code branch
|
You might also consider using the latest git repository. We try to make sure the current version in git is stable and at the very least all tests should pass.
|
||||||
but no guarantees!
|
|
||||||
|
|
||||||
gem 'couchrest_model', :git => 'git://github.com/couchrest/couchrest_model.git'
|
gem 'couchrest_model', :git => 'git://github.com/couchrest/couchrest_model.git'
|
||||||
|
|
||||||
|
@ -100,7 +99,7 @@ be type casted and other options such as the default value. These replace your t
|
||||||
`add_column` methods found in relational database migrations.
|
`add_column` methods found in relational database migrations.
|
||||||
|
|
||||||
Attributes with a property definition will have setter and getter methods defined for them. Any other attibute
|
Attributes with a property definition will have setter and getter methods defined for them. Any other attibute
|
||||||
can be set in the same way you'd update a Hash, this funcionality is inherited from CouchRest Documents.
|
can be set as if the model were a Hash, this funcionality is inherited from CouchRest Documents.
|
||||||
|
|
||||||
Here are a few examples of the way properties are used:
|
Here are a few examples of the way properties are used:
|
||||||
|
|
||||||
|
@ -252,6 +251,118 @@ Anonymous classes will *only* create arrays of objects. If you're more of the tr
|
||||||
can be provided allowing you to use this variable before each method call inside the anonymous class. This is useful
|
can be provided allowing you to use this variable before each method call inside the anonymous class. This is useful
|
||||||
if you need to access variables outside of the block.
|
if you need to access variables outside of the block.
|
||||||
|
|
||||||
|
## Views
|
||||||
|
|
||||||
|
CouchDB views can be quite difficult to get grips with at first as they are quite different from what you'd expect with SQL queries in a normal Relational Database. Checkout some of the [CouchDB documentation on views](http://wiki.apache.org/couchdb/Introduction_to_CouchDB_views) to get to grips with the basics. The key is to remember that CouchDB will only generate indexes from which you can extract consecutive rows of data, filtering other than between two points in a data set is not possible.
|
||||||
|
|
||||||
|
CouchRest Model has great support for views, and since version 1.1.0 we added support for a View objects that make accessing your data even easier.
|
||||||
|
|
||||||
|
### The Old Way
|
||||||
|
|
||||||
|
Here's an example of adding a view to our Cat class:
|
||||||
|
|
||||||
|
class Cat < CouchRest::Model::Base
|
||||||
|
property :name, String
|
||||||
|
property :toys, [CatToy]
|
||||||
|
|
||||||
|
view_by :name
|
||||||
|
end
|
||||||
|
|
||||||
|
The `view_by` method will create a view in the Cat's design document called "by_name". This will allow searches to be made for the Cat's name attribute. Calling `Cat.by_name` will send a query of to the database and return an array of all the Cat objects available. Internally, a map function is generated automatically and stored in CouchDB's design document for the current model, it'll look something like the following:
|
||||||
|
|
||||||
|
function(doc) {
|
||||||
|
if (doc['couchrest-type'] == 'Cat' && doc['name']) {
|
||||||
|
emit(doc.name, null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
By default, a special view called `all` is created and added to all couchrest models that allows you access to all the documents in the database that match the model. By default, these will be ordered by each documents id field.
|
||||||
|
|
||||||
|
It is also possible to create views of multiple keys, for example:
|
||||||
|
|
||||||
|
view_by :birthday, :name
|
||||||
|
|
||||||
|
This will create an view of all the cats' birthdays and their names called `by_birthday_and_name`.
|
||||||
|
|
||||||
|
Sometimes the automatically generate map function might not be sufficient for more complicated queries. To customize, add the :map and :reduce functions when creating the view:
|
||||||
|
|
||||||
|
view_by :tags,
|
||||||
|
:map =>
|
||||||
|
"function(doc) {
|
||||||
|
if (doc['model'] == 'Post' && doc.tags) {
|
||||||
|
doc.tags.forEach(function(tag){
|
||||||
|
emit(doc.tag, 1);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}",
|
||||||
|
:reduce =>
|
||||||
|
"function(keys, values, rereduce) {
|
||||||
|
return sum(values);
|
||||||
|
}"
|
||||||
|
|
||||||
|
Calling a view will return document objects by default, to get access to the raw CouchDB result add the `:raw => true` option to get a hash instead. Custom views can also be queried with `:reduce => true` to return reduce results. The default is to query with `:reduce => false`.
|
||||||
|
|
||||||
|
Views are generated (on a per-model basis) lazily on first-access. This means that if you are deploying changes to a view, the views for
|
||||||
|
that model won't be available until generation is complete. This can take some time with large databases. Strategies are in the works.
|
||||||
|
|
||||||
|
### View Objects
|
||||||
|
|
||||||
|
Since CouchRest Model 1.1.0 it is now possible to create views that return objects chainable objects, similar to those you'd find in the Sequel Ruby library or Rails 3's Arel. Heres an example of creating a few views:
|
||||||
|
|
||||||
|
class Post < CouchRest::Model::Base
|
||||||
|
property :title
|
||||||
|
property :body
|
||||||
|
property :posted_at, DateTime
|
||||||
|
property :tags, [String]
|
||||||
|
|
||||||
|
design do
|
||||||
|
view :by_title
|
||||||
|
view :by_posted_at_and_title
|
||||||
|
view :tag_list,
|
||||||
|
:map =>
|
||||||
|
"function(doc) {
|
||||||
|
if (doc['model'] == 'Post' && doc.tags) {
|
||||||
|
doc.tags.forEach(function(tag){
|
||||||
|
emit(doc.tag, 1);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}",
|
||||||
|
:reduce =>
|
||||||
|
"function(keys, values, rereduce) {
|
||||||
|
return sum(values);
|
||||||
|
}"
|
||||||
|
end
|
||||||
|
|
||||||
|
You'll see that this new syntax requires all views to be defined inside a design block. Unlike the old version, the keys to be used in a query are determined from the name of the view, not the other way round. Acessing data is the fun part:
|
||||||
|
|
||||||
|
# Prepare a query:
|
||||||
|
view = Post.by_posted_at_and_title.skip(5).limit(10)
|
||||||
|
|
||||||
|
# Fetch the results:
|
||||||
|
view.each do |post|
|
||||||
|
puts "Title: #{post.title}"
|
||||||
|
end
|
||||||
|
|
||||||
|
# Grab the CouchDB result information with the same object:
|
||||||
|
view.total_rows => 10
|
||||||
|
view.offset => 5
|
||||||
|
|
||||||
|
# Re-use and add new filters
|
||||||
|
filter = view.startkey([1.month.ago]).endkey([Date.current, {}])
|
||||||
|
|
||||||
|
# Fetch row results without the documents:
|
||||||
|
filter.rows.each do |row|
|
||||||
|
puts "Row value: #{row.value} Doc ID: #{row.id}"
|
||||||
|
end
|
||||||
|
|
||||||
|
# Lazily load documents (take last row from previous example):
|
||||||
|
row.doc => Fetch last Post document from database
|
||||||
|
|
||||||
|
# Using reduced queries is also easy:
|
||||||
|
tag_usage = Post.tag_list.reduce.group_level(1)
|
||||||
|
tag_usage.rows.each do |row|
|
||||||
|
puts "Tag: #{row.key} Uses: #{row.value}"
|
||||||
|
end
|
||||||
|
|
||||||
## Assocations
|
## Assocations
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
Gem::Specification.new do |s|
|
Gem::Specification.new do |s|
|
||||||
s.name = %q{couchrest_model}
|
s.name = %q{couchrest_model}
|
||||||
s.version = "1.0.0"
|
s.version = `cat VERSION`.strip
|
||||||
|
|
||||||
s.required_rubygems_version = Gem::Requirement.new("> 1.3.1") if s.respond_to? :required_rubygems_version=
|
s.required_rubygems_version = Gem::Requirement.new("> 1.3.1") if s.respond_to? :required_rubygems_version=
|
||||||
s.authors = ["J. Chris Anderson", "Matt Aimonetti", "Marcos Tapajos", "Will Leinweber", "Sam Lown"]
|
s.authors = ["J. Chris Anderson", "Matt Aimonetti", "Marcos Tapajos", "Will Leinweber", "Sam Lown"]
|
||||||
|
|
|
@ -1,4 +1,8 @@
|
||||||
== 1.0.1
|
== 1.1.0.beta
|
||||||
|
|
||||||
|
* Epic enhancements:
|
||||||
|
* Added "View" object for dynamic view queries
|
||||||
|
* Added easy to use proxy_for and proxied_by class methods for proxying data
|
||||||
|
|
||||||
* Minor enhancements:
|
* Minor enhancements:
|
||||||
* A yield parameter in an anonymous casted model property block is no longer required (@samlown)
|
* A yield parameter in an anonymous casted model property block is no longer required (@samlown)
|
||||||
|
|
Loading…
Reference in a new issue