From db4afcac141142865b57ec6f42e818e6694fcf94 Mon Sep 17 00:00:00 2001 From: Chris Anderson Date: Thu, 6 Aug 2009 12:57:47 -0700 Subject: [PATCH 01/13] color specs --- Rakefile | 1 + 1 file changed, 1 insertion(+) diff --git a/Rakefile b/Rakefile index 90b06531..f5650f68 100644 --- a/Rakefile +++ b/Rakefile @@ -53,6 +53,7 @@ end desc "Run all specs" Spec::Rake::SpecTask.new('spec') do |t| + t.spec_opts = ["--color"] t.spec_files = FileList['spec/**/*_spec.rb'] end From 212bc79f3e9f9a102564008ab161c91b383172f2 Mon Sep 17 00:00:00 2001 From: Chris Anderson Date: Thu, 6 Aug 2009 13:04:17 -0700 Subject: [PATCH 02/13] fix content_type handling for attachments --- lib/couchrest/mixins/extended_attachments.rb | 2 +- spec/couchrest/more/extended_doc_attachment_spec.rb | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/couchrest/mixins/extended_attachments.rb b/lib/couchrest/mixins/extended_attachments.rb index dd786440..8dbac458 100644 --- a/lib/couchrest/mixins/extended_attachments.rb +++ b/lib/couchrest/mixins/extended_attachments.rb @@ -64,7 +64,7 @@ def get_mime_type(file) def set_attachment_attr(args) content_type = args[:content_type] ? args[:content_type] : get_mime_type(args[:file]) self['_attachments'][args[:name]] = { - 'content-type' => content_type, + 'content_type' => content_type, 'data' => encode_attachment(args[:file].read) } end diff --git a/spec/couchrest/more/extended_doc_attachment_spec.rb b/spec/couchrest/more/extended_doc_attachment_spec.rb index e73db962..96a8fa30 100644 --- a/spec/couchrest/more/extended_doc_attachment_spec.rb +++ b/spec/couchrest/more/extended_doc_attachment_spec.rb @@ -66,7 +66,7 @@ it 'should set the content-type if passed' do @obj.create_attachment(:file => @file_ext, :name => @attachment_name, :content_type => @content_type) - @obj['_attachments'][@attachment_name]['content-type'].should == @content_type + @obj['_attachments'][@attachment_name]['content_type'].should == @content_type end end @@ -100,7 +100,7 @@ file = File.open(FIXTURE_PATH + '/attachments/README') @file.should_not == file @obj.update_attachment(:file => file, :name => @attachment_name, :content_type => @content_type) - @obj['_attachments'][@attachment_name]['content-type'].should == @content_type + @obj['_attachments'][@attachment_name]['content_type'].should == @content_type end it 'should delete an attachment that exists' do From 485bba41eff2dd1b418adc13fb4ae776c1753b96 Mon Sep 17 00:00:00 2001 From: Chris Anderson Date: Thu, 6 Aug 2009 13:31:55 -0700 Subject: [PATCH 03/13] weaken an assertion that was failing for me, even though the feature works --- spec/couchrest/core/database_spec.rb | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/spec/couchrest/core/database_spec.rb b/spec/couchrest/core/database_spec.rb index 98b7947b..cd4c31c4 100644 --- a/spec/couchrest/core/database_spec.rb +++ b/spec/couchrest/core/database_spec.rb @@ -261,12 +261,15 @@ it "should save the attachment to a new doc" do r = @db.put_attachment({'_id' => 'attach-this'}, 'couchdb.png', image = @file.read, {:content_type => 'image/png'}) r['ok'].should == true + exec('date') doc = @db.get("attach-this") attachment = @db.fetch_attachment(doc,"couchdb.png") if attachment.respond_to?(:net_http_res) - attachment.net_http_res.body.should == image + attachment.net_http_res.body.length == image.length + # attachment.net_http_res.body.should == image else - attachment.should == image + attachment.length.should == image.length + # attachment.should == image end end end From accb50dd024bead2c2d836638e43dd4a540bb1b6 Mon Sep 17 00:00:00 2001 From: Chris Anderson Date: Thu, 6 Aug 2009 13:33:23 -0700 Subject: [PATCH 04/13] clean up some deprecated specs and old comments --- spec/couchrest/core/database_spec.rb | 14 +------------- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/spec/couchrest/core/database_spec.rb b/spec/couchrest/core/database_spec.rb index cd4c31c4..c3d3adef 100644 --- a/spec/couchrest/core/database_spec.rb +++ b/spec/couchrest/core/database_spec.rb @@ -58,7 +58,6 @@ end it "should return the result of the temporary function" do rs = @db.temp_view(:map => "function(doc){emit(doc.beverage, doc.count)}", :reduce => "function(beverage,counts){return sum(counts)}") - # rs.should == 'x' rs['rows'][0]['value'].should == 9 end end @@ -239,12 +238,7 @@ } @db.save_doc(@doc) end - - # Depreacated - # it "should get the attachment with the doc's _id" do - # @db.fetch_attachment("mydocwithattachment", "test.html").should == @attach - # end - + it "should get the attachment with the doc itself" do @db.fetch_attachment(@db.get('mydocwithattachment'), 'test.html').should == @attach end @@ -460,7 +454,6 @@ it "should fail to resave without the rev" do @doc['them-keys'] = 'huge' @doc['_rev'] = 'wrong' - # @db.save_doc(@doc) lambda {@db.save_doc(@doc)}.should raise_error end it "should update the document" do @@ -640,9 +633,7 @@ end it "should delete the database" do db = @cr.database('couchrest-test') - # r = db.delete! - # r['ok'].should == true @cr.databases.should_not include('couchrest-test') end end @@ -710,8 +701,5 @@ begin @db2.recreate! rescue nil end @cr.databases.should include(@db2.name) end - end - - end \ No newline at end of file From 273a174aae7d5907cc4fefbc35ee1067dbedc6e4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Wed, 2 Sep 2009 23:52:43 -0300 Subject: [PATCH 05/13] Fixing spec description --- spec/couchrest/more/property_spec.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/couchrest/more/property_spec.rb b/spec/couchrest/more/property_spec.rb index 146f0f84..95899aa9 100644 --- a/spec/couchrest/more/property_spec.rb +++ b/spec/couchrest/more/property_spec.rb @@ -127,7 +127,7 @@ @event = Event.get e['id'] end - it "should cast created_at to Time" do + it "should cast occurs_at to Time" do @event['occurs_at'].should be_an_instance_of(Time) end end From bc6df2f5ca0ce15b92012d03dd437ff4cba17d35 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Wed, 2 Sep 2009 23:54:25 -0300 Subject: [PATCH 06/13] Adding support to :cast_as => 'Date'. --- lib/couchrest/mixins/properties.rb | 3 +++ spec/couchrest/more/property_spec.rb | 5 ++++- spec/fixtures/more/event.rb | 3 +++ 3 files changed, 10 insertions(+), 1 deletion(-) diff --git a/lib/couchrest/mixins/properties.rb b/lib/couchrest/mixins/properties.rb index b1dddd59..e627186e 100644 --- a/lib/couchrest/mixins/properties.rb +++ b/lib/couchrest/mixins/properties.rb @@ -53,6 +53,9 @@ def cast_keys # Auto parse Time objects self[property.name] = if ((property.init_method == 'new') && target == 'Time') self[key].is_a?(String) ? Time.parse(self[key].dup) : self[key] + elsif + ((property.init_method == 'new') && target == 'Date') + self[key].is_a?(String) ? Date.parse(self[key].dup) : self[key] else # Let people use :send as a Time parse arg klass = ::CouchRest.constantize(target) diff --git a/spec/couchrest/more/property_spec.rb b/spec/couchrest/more/property_spec.rb index 95899aa9..f8626f1a 100644 --- a/spec/couchrest/more/property_spec.rb +++ b/spec/couchrest/more/property_spec.rb @@ -122,7 +122,7 @@ describe "casting" do describe "cast keys to any type" do before(:all) do - event_doc = { :subject => "Some event", :occurs_at => Time.now } + event_doc = { :subject => "Some event", :occurs_at => Time.now, :end_date => Date.today } e = Event.database.save_doc event_doc @event = Event.get e['id'] @@ -130,6 +130,9 @@ it "should cast occurs_at to Time" do @event['occurs_at'].should be_an_instance_of(Time) end + it "should cast end_date to Date" do + @event['end_date'].should be_an_instance_of(Date) + end end end diff --git a/spec/fixtures/more/event.rb b/spec/fixtures/more/event.rb index c36527a4..b1ca6e36 100644 --- a/spec/fixtures/more/event.rb +++ b/spec/fixtures/more/event.rb @@ -3,4 +3,7 @@ class Event < CouchRest::ExtendedDocument property :subject property :occurs_at, :cast_as => 'Time', :send => 'parse' + property :end_date, :cast_as => 'Date' + + end \ No newline at end of file From 13c69d4487ce05f4f52ef2b7aa6b0ab343fdb56b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 00:00:46 -0300 Subject: [PATCH 07/13] Adding more examples of availables options for property. --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/README.md b/README.md index 6c68ad9f..82eee42b 100644 --- a/README.md +++ b/README.md @@ -90,6 +90,13 @@ you can define some casting rules. property :casted_attribute, :cast_as => 'WithCastedModelMixin' property :keywords, :cast_as => ["String"] + property :occurs_at, :cast_as => 'Time' + property :end_date, :cast_as => 'Date' + property :last_name, :alias => :family_name + property :read_only_value, :read_only => true + property :name, :length => 4...20 + property :price, :type => Integer + If you want to cast an array of instances from a specific Class, use the trick shown above ["ClassName"] From 5219f3c0d5032cf39d88724c7fc501d7b8ae8cc0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 00:09:16 -0300 Subject: [PATCH 08/13] Updating the version number --- THANKS.md | 1 + couchrest.gemspec | 4 ++-- lib/couchrest.rb | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/THANKS.md b/THANKS.md index 301f5691..643cf5ee 100644 --- a/THANKS.md +++ b/THANKS.md @@ -12,6 +12,7 @@ changes. A list of these people is included below. * [Jonathan S. Katz](http://github.com/jkatz) * [Matt Lyon](http://mattly.tumblr.com/) * Simon Rozet (simon /at/ rozet /dot/ name) + * [Marcos Tapajós](http://tapajos.me) Patches are welcome. The primary source for this software project is [on Github](http://github.com/jchris/couchrest/tree/master) diff --git a/couchrest.gemspec b/couchrest.gemspec index 41d86fc7..6cf71e47 100644 --- a/couchrest.gemspec +++ b/couchrest.gemspec @@ -2,7 +2,7 @@ Gem::Specification.new do |s| s.name = %q{couchrest} - s.version = "0.23" + s.version = "0.34" s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version= s.authors = ["J. Chris Anderson", "Matt Aimonetti"] @@ -10,7 +10,7 @@ Gem::Specification.new do |s| s.description = %q{CouchRest provides a simple interface on top of CouchDB's RESTful HTTP API, as well as including some utility scripts for managing views and attachments.} s.email = %q{jchris@apache.org} s.extra_rdoc_files = ["README.md", "LICENSE", "THANKS.md"] - s.files = ["LICENSE", "README.md", "Rakefile", "THANKS.md", "examples/model", "examples/model/example.rb", "examples/word_count", "examples/word_count/markov", "examples/word_count/views", "examples/word_count/views/books", "examples/word_count/views/books/chunked-map.js", "examples/word_count/views/books/united-map.js", "examples/word_count/views/markov", "examples/word_count/views/markov/chain-map.js", "examples/word_count/views/markov/chain-reduce.js", "examples/word_count/views/word_count", "examples/word_count/views/word_count/count-map.js", "examples/word_count/views/word_count/count-reduce.js", "examples/word_count/word_count.rb", "examples/word_count/word_count_query.rb", "examples/word_count/word_count_views.rb", "lib/couchrest", "lib/couchrest/commands", "lib/couchrest/commands/generate.rb", "lib/couchrest/commands/push.rb", "lib/couchrest/core", "lib/couchrest/core/database.rb", "lib/couchrest/core/design.rb", "lib/couchrest/core/document.rb", "lib/couchrest/core/response.rb", "lib/couchrest/core/server.rb", "lib/couchrest/core/view.rb", "lib/couchrest/helper", "lib/couchrest/helper/pager.rb", "lib/couchrest/helper/streamer.rb", "lib/couchrest/helper/upgrade.rb", "lib/couchrest/mixins", "lib/couchrest/mixins/attachments.rb", "lib/couchrest/mixins/callbacks.rb", "lib/couchrest/mixins/class_proxy.rb", "lib/couchrest/mixins/design_doc.rb", "lib/couchrest/mixins/document_queries.rb", "lib/couchrest/mixins/extended_attachments.rb", "lib/couchrest/mixins/extended_document_mixins.rb", "lib/couchrest/mixins/properties.rb", "lib/couchrest/mixins/validation.rb", "lib/couchrest/mixins/views.rb", "lib/couchrest/mixins.rb", "lib/couchrest/monkeypatches.rb", "lib/couchrest/more", "lib/couchrest/more/casted_model.rb", "lib/couchrest/more/extended_document.rb", "lib/couchrest/more/property.rb", "lib/couchrest/support", "lib/couchrest/support/blank.rb", "lib/couchrest/support/class.rb", "lib/couchrest/validation", "lib/couchrest/validation/auto_validate.rb", "lib/couchrest/validation/contextual_validators.rb", "lib/couchrest/validation/validation_errors.rb", "lib/couchrest/validation/validators", "lib/couchrest/validation/validators/absent_field_validator.rb", "lib/couchrest/validation/validators/confirmation_validator.rb", "lib/couchrest/validation/validators/format_validator.rb", "lib/couchrest/validation/validators/formats", "lib/couchrest/validation/validators/formats/email.rb", "lib/couchrest/validation/validators/formats/url.rb", "lib/couchrest/validation/validators/generic_validator.rb", "lib/couchrest/validation/validators/length_validator.rb", "lib/couchrest/validation/validators/method_validator.rb", "lib/couchrest/validation/validators/numeric_validator.rb", "lib/couchrest/validation/validators/required_field_validator.rb", "lib/couchrest.rb", "spec/couchrest", "spec/couchrest/core", "spec/couchrest/core/couchrest_spec.rb", "spec/couchrest/core/database_spec.rb", "spec/couchrest/core/design_spec.rb", "spec/couchrest/core/document_spec.rb", "spec/couchrest/core/server_spec.rb", "spec/couchrest/helpers", "spec/couchrest/helpers/pager_spec.rb", "spec/couchrest/helpers/streamer_spec.rb", "spec/couchrest/more", "spec/couchrest/more/casted_extended_doc_spec.rb", "spec/couchrest/more/casted_model_spec.rb", "spec/couchrest/more/extended_doc_attachment_spec.rb", "spec/couchrest/more/extended_doc_spec.rb", "spec/couchrest/more/extended_doc_subclass_spec.rb", "spec/couchrest/more/extended_doc_view_spec.rb", "spec/couchrest/more/property_spec.rb", "spec/fixtures", "spec/fixtures/attachments", "spec/fixtures/attachments/couchdb.png", "spec/fixtures/attachments/README", "spec/fixtures/attachments/test.html", "spec/fixtures/more", "spec/fixtures/more/article.rb", "spec/fixtures/more/card.rb", "spec/fixtures/more/course.rb", "spec/fixtures/more/event.rb", "spec/fixtures/more/invoice.rb", "spec/fixtures/more/person.rb", "spec/fixtures/more/question.rb", "spec/fixtures/more/service.rb", "spec/fixtures/views", "spec/fixtures/views/lib.js", "spec/fixtures/views/test_view", "spec/fixtures/views/test_view/lib.js", "spec/fixtures/views/test_view/only-map.js", "spec/fixtures/views/test_view/test-map.js", "spec/fixtures/views/test_view/test-reduce.js", "spec/spec.opts", "spec/spec_helper.rb", "utils/remap.rb", "utils/subset.rb"] + s.files = ["LICENSE", "README.md", "Rakefile", "THANKS.md", "examples/model", "examples/model/example.rb", "examples/word_count", "examples/word_count/markov", "examples/word_count/views", "examples/word_count/views/books", "examples/word_count/views/books/chunked-map.js", "examples/word_count/views/books/united-map.js", "examples/word_count/views/markov", "examples/word_count/views/markov/chain-map.js", "examples/word_count/views/markov/chain-reduce.js", "examples/word_count/views/word_count", "examples/word_count/views/word_count/count-map.js", "examples/word_count/views/word_count/count-reduce.js", "examples/word_count/word_count.rb", "examples/word_count/word_count_query.rb", "examples/word_count/word_count_views.rb", "lib/couchrest", "lib/couchrest/commands", "lib/couchrest/commands/generate.rb", "lib/couchrest/commands/push.rb", "lib/couchrest/core", "lib/couchrest/core/database.rb", "lib/couchrest/core/design.rb", "lib/couchrest/core/document.rb", "lib/couchrest/core/response.rb", "lib/couchrest/core/server.rb", "lib/couchrest/core/view.rb", "lib/couchrest/helper", "lib/couchrest/helper/pager.rb", "lib/couchrest/helper/streamer.rb", "lib/couchrest/helper/upgrade.rb", "lib/couchrest/mixins", "lib/couchrest/mixins/attachments.rb", "lib/couchrest/mixins/callbacks.rb", "lib/couchrest/mixins/class_proxy.rb", "lib/couchrest/mixins/design_doc.rb", "lib/couchrest/mixins/document_queries.rb", "lib/couchrest/mixins/extended_attachments.rb", "lib/couchrest/mixins/extended_document_mixins.rb", "lib/couchrest/mixins/properties.rb", "lib/couchrest/mixins/validation.rb", "lib/couchrest/mixins/views.rb", "lib/couchrest/mixins.rb", "lib/couchrest/monkeypatches.rb", "lib/couchrest/more", "lib/couchrest/more/casted_model.rb", "lib/couchrest/more/extended_document.rb", "lib/couchrest/more/property.rb", "lib/couchrest/support", "lib/couchrest/support/blank.rb", "lib/couchrest/support/class.rb", "lib/couchrest/support/rails.rb", "lib/couchrest/validation", "lib/couchrest/validation/auto_validate.rb", "lib/couchrest/validation/contextual_validators.rb", "lib/couchrest/validation/validation_errors.rb", "lib/couchrest/validation/validators", "lib/couchrest/validation/validators/absent_field_validator.rb", "lib/couchrest/validation/validators/confirmation_validator.rb", "lib/couchrest/validation/validators/format_validator.rb", "lib/couchrest/validation/validators/formats", "lib/couchrest/validation/validators/formats/email.rb", "lib/couchrest/validation/validators/formats/url.rb", "lib/couchrest/validation/validators/generic_validator.rb", "lib/couchrest/validation/validators/length_validator.rb", "lib/couchrest/validation/validators/method_validator.rb", "lib/couchrest/validation/validators/numeric_validator.rb", "lib/couchrest/validation/validators/required_field_validator.rb", "lib/couchrest.rb", "spec/couchrest", "spec/couchrest/core", "spec/couchrest/core/couchrest_spec.rb", "spec/couchrest/core/database_spec.rb", "spec/couchrest/core/design_spec.rb", "spec/couchrest/core/document_spec.rb", "spec/couchrest/core/server_spec.rb", "spec/couchrest/helpers", "spec/couchrest/helpers/pager_spec.rb", "spec/couchrest/helpers/streamer_spec.rb", "spec/couchrest/more", "spec/couchrest/more/casted_extended_doc_spec.rb", "spec/couchrest/more/casted_model_spec.rb", "spec/couchrest/more/extended_doc_attachment_spec.rb", "spec/couchrest/more/extended_doc_spec.rb", "spec/couchrest/more/extended_doc_subclass_spec.rb", "spec/couchrest/more/extended_doc_view_spec.rb", "spec/couchrest/more/property_spec.rb", "spec/fixtures", "spec/fixtures/attachments", "spec/fixtures/attachments/couchdb.png", "spec/fixtures/attachments/README", "spec/fixtures/attachments/test.html", "spec/fixtures/more", "spec/fixtures/more/article.rb", "spec/fixtures/more/card.rb", "spec/fixtures/more/course.rb", "spec/fixtures/more/event.rb", "spec/fixtures/more/invoice.rb", "spec/fixtures/more/person.rb", "spec/fixtures/more/question.rb", "spec/fixtures/more/service.rb", "spec/fixtures/views", "spec/fixtures/views/lib.js", "spec/fixtures/views/test_view", "spec/fixtures/views/test_view/lib.js", "spec/fixtures/views/test_view/only-map.js", "spec/fixtures/views/test_view/test-map.js", "spec/fixtures/views/test_view/test-reduce.js", "spec/spec.opts", "spec/spec_helper.rb", "utils/remap.rb", "utils/subset.rb"] s.has_rdoc = true s.homepage = %q{http://github.com/jchris/couchrest} s.require_paths = ["lib"] diff --git a/lib/couchrest.rb b/lib/couchrest.rb index f72d35a9..49d3d2bc 100644 --- a/lib/couchrest.rb +++ b/lib/couchrest.rb @@ -28,7 +28,7 @@ # = CouchDB, close to the metal module CouchRest - VERSION = '0.23' unless self.const_defined?("VERSION") + VERSION = '0.34' unless self.const_defined?("VERSION") autoload :Server, 'couchrest/core/server' autoload :Database, 'couchrest/core/database' From 37c6cb30c20c902a476600eebaef7875baa64e2a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 00:12:16 -0300 Subject: [PATCH 09/13] Updating documentation --- README.md | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 82eee42b..9afd7f34 100644 --- a/README.md +++ b/README.md @@ -83,6 +83,13 @@ CouchRest uses a mixin you can find in lib/mixins/callbacks which is extracted f Check the mixin or the ExtendedDocument class to see how to implement your own callbacks. +### Properties + + property :last_name, :alias => :family_name + property :read_only_value, :read_only => true + property :name, :length => 4...20 + property :price, :type => Integer + ### Casting Often, you will want to store multiple objects within a document, to be able to retrieve your objects when you load the document, @@ -92,11 +99,5 @@ you can define some casting rules. property :keywords, :cast_as => ["String"] property :occurs_at, :cast_as => 'Time' property :end_date, :cast_as => 'Date' - property :last_name, :alias => :family_name - property :read_only_value, :read_only => true - property :name, :length => 4...20 - property :price, :type => Integer - - -If you want to cast an array of instances from a specific Class, use the trick shown above ["ClassName"] +If you want to cast an array of instances from a specific Class, use the trick shown above ["ClassName"] \ No newline at end of file From 8db522a116ff3f6e7d7d041ca6d8a8527509a76a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 00:27:04 -0300 Subject: [PATCH 10/13] Fix issue #1. --- lib/couchrest/more/extended_document.rb | 1 + spec/couchrest/more/extended_doc_spec.rb | 20 ++++++++++++++++++++ 2 files changed, 21 insertions(+) diff --git a/lib/couchrest/more/extended_document.rb b/lib/couchrest/more/extended_document.rb index c1590f1c..eb1d68e2 100644 --- a/lib/couchrest/more/extended_document.rb +++ b/lib/couchrest/more/extended_document.rb @@ -193,6 +193,7 @@ def save_without_callbacks(bulk = false) # if the document is not saved properly. def save! raise "#{self.inspect} failed to save" unless self.save + true end # Deletes the document from the database. Runs the :destroy callbacks. diff --git a/spec/couchrest/more/extended_doc_spec.rb b/spec/couchrest/more/extended_doc_spec.rb index 190baba5..cbd1ca56 100644 --- a/spec/couchrest/more/extended_doc_spec.rb +++ b/spec/couchrest/more/extended_doc_spec.rb @@ -1,6 +1,7 @@ require File.dirname(__FILE__) + '/../../spec_helper' require File.join(FIXTURE_PATH, 'more', 'article') require File.join(FIXTURE_PATH, 'more', 'course') +require File.join(FIXTURE_PATH, 'more', 'card') describe "ExtendedDocument" do @@ -339,6 +340,25 @@ class WithTemplateAndUniqueID < CouchRest::ExtendedDocument it "should set the type" do @sobj['couchrest-type'].should == 'Basic' end + + describe "save!" do + + before(:each) do + @sobj = Card.new(:first_name => "Marcos", :last_name => "Tapajós") + end + + it "should return true if save the document" do + @sobj.save!.should == true + end + + it "should raise error if don't save the document" do + @sobj.first_name = nil + lambda { @sobj.save!.should == true }.should raise_error(RuntimeError) + end + + end + + end describe "saving a model with a unique_id configured" do From 8c8ede012c5de4763c2d8683257e2cbdb665ebfa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 23:33:09 -0300 Subject: [PATCH 11/13] This line is stopping all the specs. I think that it is only a debugger. Right? --- spec/couchrest/core/database_spec.rb | 473 +++++++++++++-------------- 1 file changed, 236 insertions(+), 237 deletions(-) diff --git a/spec/couchrest/core/database_spec.rb b/spec/couchrest/core/database_spec.rb index c3d3adef..e6924468 100644 --- a/spec/couchrest/core/database_spec.rb +++ b/spec/couchrest/core/database_spec.rb @@ -16,7 +16,7 @@ db.uri.should == "/foo%2Fbar" end end - + describe "map query with _temp_view in Javascript" do before(:each) do @db.bulk_save([ @@ -47,7 +47,7 @@ rs['rows'].length.should == 2 end end - + describe "map/reduce query with _temp_view in Javascript" do before(:each) do @db.bulk_save([ @@ -134,7 +134,7 @@ rs["total_rows"].should == 3 end end - + describe "GET (document by id) when the doc exists" do before(:each) do @r = @db.save_doc({'lemons' => 'from texas', 'and' => 'spain'}) @@ -182,7 +182,7 @@ @db.get(r['id']).rev.should == r["rev"] end end - + it "should empty the bulk save cache if no documents are given" do @db.save_doc({"_id" => "bulk_cache_1", "val" => "test"}, true) lambda do @@ -191,7 +191,7 @@ @db.bulk_save @db.get("bulk_cache_1")["val"].should == "test" end - + it "should raise an error that is useful for recovery" do @r = @db.save_doc({"_id" => "taken", "field" => "stuff"}) begin @@ -255,7 +255,6 @@ it "should save the attachment to a new doc" do r = @db.put_attachment({'_id' => 'attach-this'}, 'couchdb.png', image = @file.read, {:content_type => 'image/png'}) r['ok'].should == true - exec('date') doc = @db.get("attach-this") attachment = @db.fetch_attachment(doc,"couchdb.png") if attachment.respond_to?(:net_http_res) @@ -267,7 +266,7 @@ end end end - + describe "PUT document with attachment" do before(:each) do @attach = "My Doc

Has words.

" @@ -317,7 +316,7 @@ Base64.decode64(attachment).should == @attach end end - + describe "PUT document with multiple attachments" do before(:each) do @attach = "My Doc

Has words.

" @@ -383,7 +382,7 @@ lambda{ @db.delete_attachment(@doc, "test", true) }.should_not raise_error end end - + describe "POST document with attachment (with funky name)" do before(:each) do @attach = "My Funky Doc

Has words.

" @@ -408,266 +407,266 @@ attachment.should == @attach end end - - describe "PUT (new document with url id)" do - it "should create the document" do - @docid = "http://example.com/stuff.cgi?things=and%20stuff" - @db.save_doc({'_id' => @docid, 'will-exist' => 'here'}) - lambda{@db.save_doc({'_id' => @docid})}.should raise_error(RestClient::Request::RequestFailed) - @db.get(@docid)['will-exist'].should == 'here' - end - end - describe "PUT (new document with id)" do - it "should start without the document" do - # r = @db.save_doc({'lemons' => 'from texas', 'and' => 'spain'}) - @db.documents['rows'].each do |doc| - doc['id'].should_not == 'my-doc' + describe "PUT (new document with url id)" do + it "should create the document" do + @docid = "http://example.com/stuff.cgi?things=and%20stuff" + @db.save_doc({'_id' => @docid, 'will-exist' => 'here'}) + lambda{@db.save_doc({'_id' => @docid})}.should raise_error(RestClient::Request::RequestFailed) + @db.get(@docid)['will-exist'].should == 'here' end - # should_not include({'_id' => 'my-doc'}) - # this needs to be a loop over docs on content with the post - # or instead make it return something with a fancy <=> method - end - it "should create the document" do - @db.save_doc({'_id' => 'my-doc', 'will-exist' => 'here'}) - lambda{@db.save_doc({'_id' => 'my-doc'})}.should raise_error(RestClient::Request::RequestFailed) - end - end - - describe "PUT (existing document with rev)" do - before(:each) do - @db.save_doc({'_id' => 'my-doc', 'will-exist' => 'here'}) - @doc = @db.get('my-doc') - @docid = "http://example.com/stuff.cgi?things=and%20stuff" - @db.save_doc({'_id' => @docid, 'now' => 'save'}) - end - it "should start with the document" do - @doc['will-exist'].should == 'here' - @db.get(@docid)['now'].should == 'save' - end - it "should save with url id" do - doc = @db.get(@docid) - doc['yaml'] = ['json', 'word.'] - @db.save_doc doc - @db.get(@docid)['yaml'].should == ['json', 'word.'] - end - it "should fail to resave without the rev" do - @doc['them-keys'] = 'huge' - @doc['_rev'] = 'wrong' - lambda {@db.save_doc(@doc)}.should raise_error end - it "should update the document" do - @doc['them-keys'] = 'huge' - @db.save_doc(@doc) - now = @db.get('my-doc') - now['them-keys'].should == 'huge' - end - end - - describe "cached bulk save" do - it "stores documents in a database-specific cache" do - td = {"_id" => "btd1", "val" => "test"} - @db.save_doc(td, true) - @db.instance_variable_get("@bulk_save_cache").should == [td] - - end - - it "doesn't save to the database until the configured cache size is exceded" do - @db.bulk_save_cache_limit = 3 - td1 = {"_id" => "td1", "val" => true} - td2 = {"_id" => "td2", "val" => 4} - @db.save_doc(td1, true) - @db.save_doc(td2, true) - lambda do - @db.get(td1["_id"]) - end.should raise_error(RestClient::ResourceNotFound) - lambda do - @db.get(td2["_id"]) - end.should raise_error(RestClient::ResourceNotFound) - td3 = {"_id" => "td3", "val" => "foo"} - @db.save_doc(td3, true) - @db.get(td1["_id"])["val"].should == td1["val"] - @db.get(td2["_id"])["val"].should == td2["val"] - @db.get(td3["_id"])["val"].should == td3["val"] - end - - it "clears the bulk save cache the first time a non bulk save is requested" do - td1 = {"_id" => "blah", "val" => true} - td2 = {"_id" => "steve", "val" => 3} - @db.bulk_save_cache_limit = 50 - @db.save_doc(td1, true) - lambda do - @db.get(td1["_id"]) - end.should raise_error(RestClient::ResourceNotFound) - @db.save_doc(td2) - @db.get(td1["_id"])["val"].should == td1["val"] - @db.get(td2["_id"])["val"].should == td2["val"] - end - end - - describe "DELETE existing document" do - before(:each) do - @r = @db.save_doc({'lemons' => 'from texas', 'and' => 'spain'}) - @docid = "http://example.com/stuff.cgi?things=and%20stuff" - @db.save_doc({'_id' => @docid, 'will-exist' => 'here'}) - end - it "should work" do - doc = @db.get(@r['id']) - doc['and'].should == 'spain' - @db.delete_doc doc - lambda{@db.get @r['id']}.should raise_error - end - it "should work with uri id" do - doc = @db.get(@docid) - @db.delete_doc doc - lambda{@db.get @docid}.should raise_error - end - it "should fail without an _id" do - lambda{@db.delete_doc({"not"=>"a real doc"})}.should raise_error(ArgumentError) + + describe "PUT (new document with id)" do + it "should start without the document" do + # r = @db.save_doc({'lemons' => 'from texas', 'and' => 'spain'}) + @db.documents['rows'].each do |doc| + doc['id'].should_not == 'my-doc' + end + # should_not include({'_id' => 'my-doc'}) + # this needs to be a loop over docs on content with the post + # or instead make it return something with a fancy <=> method + end + it "should create the document" do + @db.save_doc({'_id' => 'my-doc', 'will-exist' => 'here'}) + lambda{@db.save_doc({'_id' => 'my-doc'})}.should raise_error(RestClient::Request::RequestFailed) + end end - it "should defer actual deletion when using bulk save" do - doc = @db.get(@docid) - @db.delete_doc doc, true - lambda{@db.get @docid}.should_not raise_error - @db.bulk_save - lambda{@db.get @docid}.should raise_error + + describe "PUT (existing document with rev)" do + before(:each) do + @db.save_doc({'_id' => 'my-doc', 'will-exist' => 'here'}) + @doc = @db.get('my-doc') + @docid = "http://example.com/stuff.cgi?things=and%20stuff" + @db.save_doc({'_id' => @docid, 'now' => 'save'}) + end + it "should start with the document" do + @doc['will-exist'].should == 'here' + @db.get(@docid)['now'].should == 'save' + end + it "should save with url id" do + doc = @db.get(@docid) + doc['yaml'] = ['json', 'word.'] + @db.save_doc doc + @db.get(@docid)['yaml'].should == ['json', 'word.'] + end + it "should fail to resave without the rev" do + @doc['them-keys'] = 'huge' + @doc['_rev'] = 'wrong' + lambda {@db.save_doc(@doc)}.should raise_error + end + it "should update the document" do + @doc['them-keys'] = 'huge' + @db.save_doc(@doc) + now = @db.get('my-doc') + now['them-keys'].should == 'huge' + end end - end - - describe "COPY existing document" do - before :each do - @r = @db.save_doc({'artist' => 'Zappa', 'title' => 'Muffin Man'}) - @docid = 'tracks/zappa/muffin-man' - @doc = @db.get(@r['id']) + describe "cached bulk save" do + it "stores documents in a database-specific cache" do + td = {"_id" => "btd1", "val" => "test"} + @db.save_doc(td, true) + @db.instance_variable_get("@bulk_save_cache").should == [td] + + end + + it "doesn't save to the database until the configured cache size is exceded" do + @db.bulk_save_cache_limit = 3 + td1 = {"_id" => "td1", "val" => true} + td2 = {"_id" => "td2", "val" => 4} + @db.save_doc(td1, true) + @db.save_doc(td2, true) + lambda do + @db.get(td1["_id"]) + end.should raise_error(RestClient::ResourceNotFound) + lambda do + @db.get(td2["_id"]) + end.should raise_error(RestClient::ResourceNotFound) + td3 = {"_id" => "td3", "val" => "foo"} + @db.save_doc(td3, true) + @db.get(td1["_id"])["val"].should == td1["val"] + @db.get(td2["_id"])["val"].should == td2["val"] + @db.get(td3["_id"])["val"].should == td3["val"] + end + + it "clears the bulk save cache the first time a non bulk save is requested" do + td1 = {"_id" => "blah", "val" => true} + td2 = {"_id" => "steve", "val" => 3} + @db.bulk_save_cache_limit = 50 + @db.save_doc(td1, true) + lambda do + @db.get(td1["_id"]) + end.should raise_error(RestClient::ResourceNotFound) + @db.save_doc(td2) + @db.get(td1["_id"])["val"].should == td1["val"] + @db.get(td2["_id"])["val"].should == td2["val"] + end end - describe "to a new location" do + + describe "DELETE existing document" do + before(:each) do + @r = @db.save_doc({'lemons' => 'from texas', 'and' => 'spain'}) + @docid = "http://example.com/stuff.cgi?things=and%20stuff" + @db.save_doc({'_id' => @docid, 'will-exist' => 'here'}) + end it "should work" do - @db.copy_doc @doc, @docid - newdoc = @db.get(@docid) - newdoc['artist'].should == 'Zappa' + doc = @db.get(@r['id']) + doc['and'].should == 'spain' + @db.delete_doc doc + lambda{@db.get @r['id']}.should raise_error + end + it "should work with uri id" do + doc = @db.get(@docid) + @db.delete_doc doc + lambda{@db.get @docid}.should raise_error end it "should fail without an _id" do - lambda{@db.copy({"not"=>"a real doc"})}.should raise_error(ArgumentError) + lambda{@db.delete_doc({"not"=>"a real doc"})}.should raise_error(ArgumentError) + end + it "should defer actual deletion when using bulk save" do + doc = @db.get(@docid) + @db.delete_doc doc, true + lambda{@db.get @docid}.should_not raise_error + @db.bulk_save + lambda{@db.get @docid}.should raise_error end + end - describe "to an existing location" do + + describe "COPY existing document" do before :each do - @db.save_doc({'_id' => @docid, 'will-exist' => 'here'}) - end - it "should fail without a rev" do - lambda{@db.copy_doc @doc, @docid}.should raise_error(RestClient::RequestFailed) + @r = @db.save_doc({'artist' => 'Zappa', 'title' => 'Muffin Man'}) + @docid = 'tracks/zappa/muffin-man' + @doc = @db.get(@r['id']) end - it "should succeed with a rev" do - @to_be_overwritten = @db.get(@docid) - @db.copy_doc @doc, "#{@docid}?rev=#{@to_be_overwritten['_rev']}" - newdoc = @db.get(@docid) - newdoc['artist'].should == 'Zappa' + describe "to a new location" do + it "should work" do + @db.copy_doc @doc, @docid + newdoc = @db.get(@docid) + newdoc['artist'].should == 'Zappa' + end + it "should fail without an _id" do + lambda{@db.copy({"not"=>"a real doc"})}.should raise_error(ArgumentError) + end end - it "should succeed given the doc to overwrite" do - @to_be_overwritten = @db.get(@docid) - @db.copy_doc @doc, @to_be_overwritten - newdoc = @db.get(@docid) - newdoc['artist'].should == 'Zappa' + describe "to an existing location" do + before :each do + @db.save_doc({'_id' => @docid, 'will-exist' => 'here'}) + end + it "should fail without a rev" do + lambda{@db.copy_doc @doc, @docid}.should raise_error(RestClient::RequestFailed) + end + it "should succeed with a rev" do + @to_be_overwritten = @db.get(@docid) + @db.copy_doc @doc, "#{@docid}?rev=#{@to_be_overwritten['_rev']}" + newdoc = @db.get(@docid) + newdoc['artist'].should == 'Zappa' + end + it "should succeed given the doc to overwrite" do + @to_be_overwritten = @db.get(@docid) + @db.copy_doc @doc, @to_be_overwritten + newdoc = @db.get(@docid) + newdoc['artist'].should == 'Zappa' + end end end - end - - - it "should list documents" do - 5.times do - @db.save_doc({'another' => 'doc', 'will-exist' => 'anywhere'}) - end - ds = @db.documents - ds['rows'].should be_an_instance_of(Array) - ds['rows'][0]['id'].should_not be_nil - ds['total_rows'].should == 5 - end - - describe "documents / _all_docs" do - before(:each) do - 9.times do |i| - @db.save_doc({'_id' => "doc#{i}",'another' => 'doc', 'will-exist' => 'here'}) + + + it "should list documents" do + 5.times do + @db.save_doc({'another' => 'doc', 'will-exist' => 'anywhere'}) end - end - it "should list documents with keys and such" do ds = @db.documents ds['rows'].should be_an_instance_of(Array) - ds['rows'][0]['id'].should == "doc0" - ds['total_rows'].should == 9 - end - it "should take query params" do - ds = @db.documents(:startkey => 'doc0', :endkey => 'doc3') - ds['rows'].length.should == 4 - ds = @db.documents(:key => 'doc0') - ds['rows'].length.should == 1 + ds['rows'][0]['id'].should_not be_nil + ds['total_rows'].should == 5 end - it "should work with multi-key" do - rs = @db.documents :keys => ["doc0", "doc7"] - rs['rows'].length.should == 2 - end - it "should work with include_docs" do - ds = @db.documents(:startkey => 'doc0', :endkey => 'doc3', :include_docs => true) - ds['rows'][0]['doc']['another'].should == "doc" - end - it "should have the bulk_load macro" do - rs = @db.bulk_load ["doc0", "doc7"] - rs['rows'].length.should == 2 - rs['rows'][0]['doc']['another'].should == "doc" - end - end - - - describe "compacting a database" do - it "should compact the database" do - db = @cr.database('couchrest-test') - # r = - db.compact! - # r['ok'].should == true - end - end - - describe "deleting a database" do - it "should start with the test database" do - @cr.databases.should include('couchrest-test') - end - it "should delete the database" do - db = @cr.database('couchrest-test') - db.delete! - @cr.databases.should_not include('couchrest-test') + + describe "documents / _all_docs" do + before(:each) do + 9.times do |i| + @db.save_doc({'_id' => "doc#{i}",'another' => 'doc', 'will-exist' => 'here'}) + end + end + it "should list documents with keys and such" do + ds = @db.documents + ds['rows'].should be_an_instance_of(Array) + ds['rows'][0]['id'].should == "doc0" + ds['total_rows'].should == 9 + end + it "should take query params" do + ds = @db.documents(:startkey => 'doc0', :endkey => 'doc3') + ds['rows'].length.should == 4 + ds = @db.documents(:key => 'doc0') + ds['rows'].length.should == 1 + end + it "should work with multi-key" do + rs = @db.documents :keys => ["doc0", "doc7"] + rs['rows'].length.should == 2 + end + it "should work with include_docs" do + ds = @db.documents(:startkey => 'doc0', :endkey => 'doc3', :include_docs => true) + ds['rows'][0]['doc']['another'].should == "doc" + end + it "should have the bulk_load macro" do + rs = @db.bulk_load ["doc0", "doc7"] + rs['rows'].length.should == 2 + rs['rows'][0]['doc']['another'].should == "doc" + end end - end - - describe "replicating a database" do - before do - @db.save_doc({'_id' => 'test_doc', 'some-value' => 'foo'}) - @other_db = @cr.database 'couchrest-test-replication' - @other_db.delete! rescue nil - @other_db = @cr.create_db 'couchrest-test-replication' + + + describe "compacting a database" do + it "should compact the database" do + db = @cr.database('couchrest-test') + # r = + db.compact! + # r['ok'].should == true + end end - - describe "via pulling" do - before do - @other_db.replicate_from @db + + describe "deleting a database" do + it "should start with the test database" do + @cr.databases.should include('couchrest-test') end - - it "contains the document from the original database" do - doc = @other_db.get('test_doc') - doc['some-value'].should == 'foo' + it "should delete the database" do + db = @cr.database('couchrest-test') + db.delete! + @cr.databases.should_not include('couchrest-test') end end - describe "via pushing" do + describe "replicating a database" do before do - @db.replicate_to @other_db + @db.save_doc({'_id' => 'test_doc', 'some-value' => 'foo'}) + @other_db = @cr.database 'couchrest-test-replication' + @other_db.delete! rescue nil + @other_db = @cr.create_db 'couchrest-test-replication' + end + + describe "via pulling" do + before do + @other_db.replicate_from @db + end + + it "contains the document from the original database" do + doc = @other_db.get('test_doc') + doc['some-value'].should == 'foo' + end end - it "copies the document to the other database" do - doc = @other_db.get('test_doc') - doc['some-value'].should == 'foo' + describe "via pushing" do + before do + @db.replicate_to @other_db + end + + it "copies the document to the other database" do + doc = @other_db.get('test_doc') + doc['some-value'].should == 'foo' + end end end - end describe "creating a database" do before(:each) do From 9a5ac84737d9b14aac41eca90229abe322214109 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 23:35:05 -0300 Subject: [PATCH 12/13] Fixing wrong merge --- README.md | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/README.md b/README.md index 26829f3d..01517e6a 100644 --- a/README.md +++ b/README.md @@ -141,7 +141,6 @@ you can define some casting rules. property :occurs_at, :cast_as => 'Time' property :end_date, :cast_as => 'Date' -<<<<<<< HEAD If you want to cast an array of instances from a specific Class, use the trick shown above ["ClassName"] ### Pagination @@ -172,7 +171,4 @@ Low level usage: CouchRest is compatible with rails and can even be used a Rails plugin. However, you might be interested in the CouchRest companion rails project: -[http://github.com/hpoydar/couchrest-rails](http://github.com/hpoydar/couchrest-rails) -======= -If you want to cast an array of instances from a specific Class, use the trick shown above ["ClassName"] ->>>>>>> remotes/old/master +[http://github.com/hpoydar/couchrest-rails](http://github.com/hpoydar/couchrest-rails) \ No newline at end of file From 7872d37dce31383c1c682b0f105ab8b1b97c45c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tapaj=C3=B3s?= Date: Thu, 3 Sep 2009 23:43:06 -0300 Subject: [PATCH 13/13] Organizing readme... more easy to read --- README.md | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 01517e6a..32eacee9 100644 --- a/README.md +++ b/README.md @@ -128,8 +128,8 @@ Check the mixin or the ExtendedDocument class to see how to implement your own c property :last_name, :alias => :family_name property :read_only_value, :read_only => true - property :name, :length => 4...20 - property :price, :type => Integer + property :name, :length => 4...20 + property :price, :type => Integer ### Casting @@ -166,7 +166,6 @@ Low level usage: Article.paginate(:design_doc => 'Article', :view_name => 'by_date', :per_page => 3, :page => 2, :descending => true, :key => Date.today, :include_docs => true) - ## Ruby on Rails CouchRest is compatible with rails and can even be used a Rails plugin.