<?xml version="1.0" encoding="UTF-8"?>
<commit>
  <added type="array"/>
  <modified type="array">
    <modified>
      <diff>@@ -17,31 +17,23 @@ module CouchRest
       else
         doc_keys = keys.collect{|k|&quot;doc['#{k}']&quot;} # this is where :require =&gt; 'doc.x == true' would show up
         key_emit = doc_keys.length == 1 ? &quot;#{doc_keys.first}&quot; : &quot;[#{doc_keys.join(', ')}]&quot;
-        guards = doc_keys
+        guards = opts.delete(:guards) || []
+        guards.concat doc_keys
         map_function = &lt;&lt;-JAVASCRIPT
-        function(doc) {
-          if (#{guards.join(' &amp;&amp; ')}) {
-            emit(#{key_emit}, null);
-          }
-        }
-        JAVASCRIPT
+function(doc) {
+  if (#{guards.join(' &amp;&amp; ')}) {
+    emit(#{key_emit}, null);
+  }
+}
+JAVASCRIPT
         self['views'][method_name] = {
           'map' =&gt; map_function
         }
-        self['views'][method_name]['couchrest-defaults'] = opts
-        method_name
       end
+      self['views'][method_name]['couchrest-defaults'] = opts unless opts.empty?
+      method_name
     end
-
-    # def method_missing m, *args
-    #   if opts = has_view?(m)
-    #     query = args.shift || {}
-    #     view(m, opts.merge(query), *args)
-    #   else
-    #     super
-    #   end
-    # end
-
+    
     # Dispatches to any named view.
     def view view_name, query={}, &amp;block
       view_name = view_name.to_s</diff>
      <filename>lib/couchrest/core/design.rb</filename>
    </modified>
    <modified>
      <diff>@@ -1,7 +1,7 @@
 require 'rubygems'
 require 'extlib'
 require 'digest/md5'
-
+require File.dirname(__FILE__) + '/document'
 # = CouchRest::Model - ORM, the CouchDB way
 module CouchRest
   # = CouchRest::Model - ORM, the CouchDB way
@@ -111,15 +111,16 @@ module CouchRest
       # Load all documents that have the &quot;couchrest-type&quot; field equal to the
       # name of the current class. Take thes the standard set of
       # CouchRest::Database#view options.
-      # def all opts = {}
-      #   self.generated_design_doc ||= default_design_doc
-      #   unless design_doc_fresh
-      #     refresh_design_doc
-      #   end
-      #   view_name = &quot;#{design_doc_slug}/all&quot;
-      #   raw = opts.delete(:raw)
-      #   fetch_view_with_docs(view_name, opts, raw)
-      # end
+      def all opts = {}, &amp;block
+        self.design_doc ||= Design.new(default_design_doc)
+        unless design_doc_fresh
+          refresh_design_doc
+        end
+        # view_name = &quot;#{design_doc_slug}/all&quot;
+        # raw = opts.delete(:raw)
+        # fetch_view_with_docs(view_name, opts, raw)
+        view :all, opts, &amp;block
+      end
       
       # Cast a field as another class. The class must be happy to have the
       # field's primitive type as the argument to it's constucture. Classes
@@ -266,7 +267,14 @@ module CouchRest
 
       def view_by *keys
         self.design_doc ||= Design.new(default_design_doc)
+        opts = keys.pop if keys.last.is_a?(Hash)
+        opts ||= {}
+        ducktype = opts.delete(:ducktype)
+        # if ducktype
+        # end
+        keys.push opts
         self.design_doc.view_by(*keys)
+        self.design_doc_fresh = false
       end
 
       # def view_by *keys
@@ -319,7 +327,7 @@ module CouchRest
       # returns stored defaults if the there is a view named this in the design doc
       def has_view?(view)
         view = view.to_s
-        design_doc['views'][view]
+        design_doc &amp;&amp; design_doc['views'] &amp;&amp; design_doc['views'][view]
       end
 
       # # Fetch the generated design doc. Could raise an error if the generated
@@ -397,21 +405,22 @@ module CouchRest
         }
       end
 
-      # def refresh_design_doc
-      #   did = &quot;_design/#{design_doc_slug}&quot;
-      #   saved = database.get(did) rescue nil
-      #   if saved
-      #     design_doc['views'].each do |name, view|
-      #       saved['views'][name] = view
-      #     end
-      #     database.save(saved)
-      #   else
-      #     design_doc['_id'] = did
-      #     design_doc.database = database
-      #     design_doc.save
-      #   end
-      #   self.design_doc_fresh = true
-      # end
+      def refresh_design_doc
+        did = &quot;_design/#{design_doc_slug}&quot;
+        saved = database.get(did) rescue nil
+        if saved
+          design_doc['views'].each do |name, view|
+            saved['views'][name] = view
+          end
+          database.save(saved)
+        else
+          design_doc['_id'] = did
+          design_doc.delete('_rev')
+          design_doc.database = database
+          design_doc.save
+        end
+        self.design_doc_fresh = true
+      end
 
     end # class &lt;&lt; self
 
@@ -433,6 +442,34 @@ module CouchRest
       save
     end
 
+    # for compatibility with old-school frameworks
+    alias :new_record? :new_document? 
+
+    # We override this to create the create and update callback opportunities.
+    # I think we should drop those and just have save. If you care, in your callback, 
+    # check new_document?
+    def save actually=false
+      if actually
+        super()
+      else
+        if new_document?
+          create
+        else
+          update
+        end
+      end     
+    end
+    
+    def update
+      save :actually
+    end
+
+    def create
+      # can we use the callbacks for this?
+      set_unique_id if self.respond_to?(:set_unique_id)
+      save :actually
+    end
+
     private
 
     def apply_defaults
@@ -461,6 +498,8 @@ module CouchRest
     end
 
     include ::Extlib::Hook
+    # todo: drop create and update hooks... 
+    # (use new_record? in callbacks if you care)
     register_instance_hooks :save, :create, :update, :destroy
 
   end # class Model</diff>
      <filename>lib/couchrest/core/model.rb</filename>
    </modified>
    <modified>
      <diff>@@ -119,7 +119,8 @@ describe CouchRest::Design do
       method = @des.view_by :name, :age
       @des.database = @db
       @des.save
-      @db.bulk_save([{&quot;name&quot; =&gt; &quot;a&quot;, &quot;age&quot; =&gt; 2},{&quot;name&quot; =&gt; &quot;a&quot;, &quot;age&quot; =&gt; 4},{&quot;name&quot; =&gt; &quot;z&quot;, &quot;age&quot; =&gt; 9}])
+      @db.bulk_save([{&quot;name&quot; =&gt; &quot;a&quot;, &quot;age&quot; =&gt; 2},
+        {&quot;name&quot; =&gt; &quot;a&quot;, &quot;age&quot; =&gt; 4},{&quot;name&quot; =&gt; &quot;z&quot;, &quot;age&quot; =&gt; 9}])
     end
     it &quot;should work&quot; do
       res = @des.view :by_name_and_age</diff>
      <filename>spec/couchrest/core/design_spec.rb</filename>
    </modified>
    <modified>
      <diff>@@ -1,5 +1,5 @@
 require File.dirname(__FILE__) + '/../../spec_helper'
-__END__
+
 class Basic &lt; CouchRest::Model
 end
 
@@ -34,8 +34,6 @@ class Course &lt; CouchRest::Model
   view_by :dept, :ducktype =&gt; true
 end
 
-
-
 class Article &lt; CouchRest::Model
   use_database CouchRest.database!('http://localhost:5984/couchrest-model-test')
   unique_id :slug
@@ -216,24 +214,24 @@ describe CouchRest::Model do
       @course[&quot;questions&quot;][0].a[0].should == &quot;beast&quot;
     end
   end
-  # 
-  # describe &quot;finding all instances of a model&quot; do
-  #   before(:all) do
-  #     WithTemplate.new('important-field' =&gt; '1').save
-  #     WithTemplate.new('important-field' =&gt; '2').save
-  #     WithTemplate.new('important-field' =&gt; '3').save
-  #     WithTemplate.new('important-field' =&gt; '4').save
-  #   end
-  #   it &quot;should make the design doc&quot; do
-  #     WithTemplate.all
-  #     d = WithTemplate.design_doc
-  #     d['views']['all']['map'].should include('WithTemplate')
-  #   end
-  #   it &quot;should find all&quot; do
-  #     rs = WithTemplate.all 
-  #     rs.length.should == 4
-  #   end
-  # end
+  
+  describe &quot;finding all instances of a model&quot; do
+    before(:all) do
+      WithTemplate.new('important-field' =&gt; '1').save
+      WithTemplate.new('important-field' =&gt; '2').save
+      WithTemplate.new('important-field' =&gt; '3').save
+      WithTemplate.new('important-field' =&gt; '4').save
+    end
+    it &quot;should make the design doc&quot; do
+      WithTemplate.all
+      d = WithTemplate.design_doc
+      d['views']['all']['map'].should include('WithTemplate')
+    end
+    it &quot;should find all&quot; do
+      rs = WithTemplate.all 
+      rs.length.should == 4
+    end
+  end
 
   describe &quot;getting a model with a subobject field&quot; do
     before(:all) do
@@ -288,6 +286,11 @@ describe CouchRest::Model do
       Article.database.delete(@old) if @old
     end
     
+    it &quot;should be a new document&quot; do
+      @art.should be_a_new_document
+      @art.title.should be_nil
+    end
+    
     it &quot;should require the title&quot; do
       lambda{@art.save}.should raise_error
       @art.title = 'This is the title'
@@ -409,10 +412,10 @@ describe CouchRest::Model do
       view['rows'].length.should == 4
     end
     
-    # it &quot;should return the matching objects (with default argument :descending =&gt; true)&quot; do
-    #   articles = Article.by_date
-    #   articles.collect{|a|a.title}.should == @titles.reverse
-    # end
+    it &quot;should return the matching objects (with default argument :descending =&gt; true)&quot; do
+      articles = Article.by_date
+      articles.collect{|a|a.title}.should == @titles.reverse
+    end
     
     it &quot;should allow you to override default args&quot; do
       articles = Article.by_date :descending =&gt; false
@@ -433,25 +436,25 @@ describe CouchRest::Model do
       doc = Course.design_doc
       doc['views']['all']['map'].should include('Course')
     end
-    # it &quot;should can query via view&quot; do
-    #   # register methods with method-missing, for local dispatch. method
-    #   # missing lookup table, no heuristics.
-    #   view = Course.view :by_title
-    #   designed = Course.by_title
-    #   view.should == designed
-    # end
-    # it &quot;should get them&quot; do
-    #   rs = Course.by_title 
-    #   rs.length.should == 4
-    # end
-    # it &quot;should yield&quot; do
-    #   courses = []
-    #   rs = Course.by_title # remove me
-    #   Course.view(:by_title) do |course|
-    #     courses &lt;&lt; course
-    #   end
-    #   courses[0][&quot;doc&quot;][&quot;title&quot;].should =='aaa'
-    # end
+    it &quot;should can query via view&quot; do
+      # register methods with method-missing, for local dispatch. method
+      # missing lookup table, no heuristics.
+      view = Course.view :by_title
+      designed = Course.by_title
+      view.should == designed
+    end
+    it &quot;should get them&quot; do
+      rs = Course.by_title 
+      rs.length.should == 4
+    end
+    it &quot;should yield&quot; do
+      courses = []
+      rs = Course.by_title # remove me
+      Course.view(:by_title) do |course|
+        courses &lt;&lt; course
+      end
+      courses[0][&quot;doc&quot;][&quot;title&quot;].should =='aaa'
+    end
   end
 
   
@@ -473,9 +476,6 @@ describe CouchRest::Model do
       @as[0]['_id'].should == @id
     end
   end
-
-end
-__END__
   
   describe &quot;a model with a compound key view&quot; do
     before(:all) do
@@ -553,6 +553,8 @@ __END__
       Article.by_updated_at
       newdocs = Article.database.documents :startkey =&gt; &quot;_design/&quot;, 
         :endkey =&gt; &quot;_design/\u9999&quot;
+      # puts @design_docs.inspect
+      # puts newdocs.inspect
       newdocs[&quot;rows&quot;].length.should == @design_docs[&quot;rows&quot;].length + 1
     end
   end</diff>
      <filename>spec/couchrest/core/model_spec.rb</filename>
    </modified>
  </modified>
  <removed type="array"/>
  <parents type="array">
    <parent>
      <id>19a70ffd7dd4a4439144e673921c7e7a34852458</id>
    </parent>
  </parents>
  <author>
    <name>Chris Anderson</name>
    <email>jchris@grabb.it</email>
  </author>
  <url>http://github.com/jchris/couchrest/commit/78534f8ec921e8eef853f6e53377a1863ce550ca</url>
  <id>78534f8ec921e8eef853f6e53377a1863ce550ca</id>
  <committed-date>2008-11-22T14:15:07-08:00</committed-date>
  <authored-date>2008-11-22T14:15:07-08:00</authored-date>
  <message>I seem to have all the CR::Model specs passing</message>
  <tree>32d8d52c26ac338ffb45f42a66a6a7784f7f4ce3</tree>
  <committer>
    <name>Chris Anderson</name>
    <email>jchris@grabb.it</email>
  </committer>
</commit>
