diff --git a/lib/couchrest/core/model.rb b/lib/couchrest/core/model.rb
index 4e38674..b4ee0bf 100644
--- a/lib/couchrest/core/model.rb
+++ b/lib/couchrest/core/model.rb
@@ -247,7 +247,7 @@ module CouchRest
#
# To understand the capabilities of this view system more compeletly,
# it is recommended that you read the RSpec file at
- # spec/core/model.rb.
+ # spec/core/model_spec.rb.
def view_by *keys
opts = keys.pop if keys.last.is_a?(Hash)
opts ||= {}
@@ -386,6 +386,19 @@ module CouchRest
self['_rev']
end
+ # Takes a hash as argument, and applies the values by using writer methods
+ # for each key. Raises a NoMethodError if the corresponding methods are
+ # missing. In case of error, no attributes are changed.
+ def update_attributes hash
+ hash.each do |k, v|
+ raise NoMethodError, "#{k}= method not available, use key_accessor or key_writer :#{key}" unless self.respond_to?("#{k}=")
+ end
+ hash.each do |k, v|
+ self.send("#{k}=",v)
+ end
+ save
+ end
+
# returns true if the document has never been saved
def new_record?
!rev
diff --git a/spec/couchrest/core/model_spec.rb b/spec/couchrest/core/model_spec.rb
index 14d56a7..57c84c5 100644
--- a/spec/couchrest/core/model_spec.rb
+++ b/spec/couchrest/core/model_spec.rb
@@ -133,6 +133,41 @@ describe CouchRest::Model do
end
end
+ describe "update attributes" do
+ before(:each) do
+ a = Article.get "big-bad-danger" rescue nil
+ a.destroy if a
+ @art = Article.new(:title => "big bad danger")
+ @art.save
+ end
+ it "should work for attribute= methods" do
+ @art['title'].should == "big bad danger"
+ @art.update_attributes('date' => Time.now, :title => "super danger")
+ @art['title'].should == "super danger"
+ end
+
+ it "should flip out if an attribute= method is missing" do
+ lambda {
+ @art.update_attributes('slug' => "new-slug", :title => "super danger")
+ }.should raise_error
+ end
+
+ it "should not change other attributes if there is an error" do
+ lambda {
+ @art.update_attributes('slug' => "new-slug", :title => "super danger")
+ }.should raise_error
+ @art['title'].should == "big bad danger"
+ end
+
+ it "should save" do
+ @art['title'].should == "big bad danger"
+ @art.update_attributes('date' => Time.now, :title => "super danger")
+ loaded = Article.get @art.id
+ loaded['title'].should == "super danger"
+ end
+
+ end
+
describe "a model with template values" do
before(:all) do
@tmpl = WithTemplate.new
@@ -326,7 +361,9 @@ describe CouchRest::Model do
end
describe "a model with timestamps" do
- before(:all) do
+ before(:each) do
+ oldart = Article.get "saving-this" rescue nil
+ oldart.destroy if oldart
@art = Article.new(:title => "Saving this")
@art.save
end