document attachments now supported

This commit is contained in:
Chris Anderson 2008-06-07 08:32:51 -07:00
parent b2765a5309
commit bf1acd8355
5 changed files with 86 additions and 15 deletions

View file

@ -7,7 +7,7 @@ require File.dirname(__FILE__) + '/database'
class CouchRest class CouchRest
attr_accessor :uri attr_accessor :uri
def initialize server def initialize server = 'http://localhost:5984'
@uri = server @uri = server
end end
@ -38,7 +38,7 @@ class CouchRest
end end
def get uri def get uri
JSON.parse(RestClient.get(uri)) JSON.parse(RestClient.get(uri), :max_nesting => false)
end end
def post uri, doc = nil def post uri, doc = nil

View file

@ -1,4 +1,5 @@
require 'cgi' require 'cgi'
require "base64"
class CouchRest class CouchRest
class Database class Database
@ -25,12 +26,21 @@ class CouchRest
end end
def get id def get id
slug = CGI.escape(id) slug = CGI.escape(id)
CouchRest.get "#{@root}/#{slug}" CouchRest.get "#{@root}/#{slug}"
end end
# PUT or POST depending on precense of _id attribute def fetch_attachment doc, name
doc = CGI.escape(doc)
name = CGI.escape(name)
RestClient.get "#{@root}/#{doc}/#{name}"
end
# PUT or POST depending on presence of _id attribute
def save doc def save doc
if doc['_attachments']
doc['_attachments'] = encode_attachments(doc['_attachments'])
end
if doc['_id'] if doc['_id']
slug = CGI.escape(doc['_id']) slug = CGI.escape(doc['_id'])
CouchRest.put "#{@root}/#{slug}", doc CouchRest.put "#{@root}/#{slug}", doc
@ -51,5 +61,19 @@ class CouchRest
def delete! def delete!
CouchRest.delete @root CouchRest.delete @root
end end
private
def encode_attachments attachments
result = {}
attachments.each do |k,v|
result[k] = {
"type" => "base64",
"data" => base64(v)
}
end
result
end
def base64 data
Base64.encode64(data).gsub(/\s/,'')
end
end end
end end

View file

@ -98,26 +98,30 @@ when "push" # files to views
end end
designs = all.group_by{|f|f[0]} designs = all.group_by{|f|f[0]}
designs.each do |design,parts| designs.each do |design,parts|
puts "design #{design}" # puts "replace _design/#{design}? (enter to proceed, 'n' to skip)"
# rep = $stdin.gets.chomp
# next if rep == 'n'
dviews = {} dviews = {}
parts.group_by{|p|p[1]}.each do |view,fs| parts.group_by{|p|p[1]}.each do |view,fs|
fs.each do |f| fs.each do |f|
dviews["#{view}-reduce"] ||= {} dviews["#{view}-reduce"] ||= {}
dviews["#{view}-reduce"][f[2]] = readjs(f.last,libs) dviews["#{view}-reduce"][f[2]] = readjs(f.last,libs)
end end
dviews["#{view}-map"] = {:map => dviews["#{view}-reduce"]['map']} dviews["#{view}-map"] = {'map' => dviews["#{view}-reduce"]['map']}
dviews.delete("#{view}-reduce") unless dviews["#{view}-reduce"]["reduce"] dviews.delete("#{view}-reduce") unless dviews["#{view}-reduce"]["reduce"]
end end
# save them to the db # save them to the db
begin view = db.get("_design/#{design}") rescue nil
view = db.get("_design/#{design}") if (view && view['views'] == dviews)
db.delete(view) puts "no change to _design/#{design}. skipping..."
rescue else
puts "replacing _design/#{design}"
db.delete(view) rescue nil
db.save({
"_id" => "_design/#{design}",
:views => dviews
})
end end
db.save({
"_id" => "_design/#{design}",
:views => dviews
})
end end
when "pull" # views to files when "pull" # views to files

View file

@ -23,7 +23,7 @@ describe CouchRest do
v = @cr.info["version"] v = @cr.info["version"]
vi = v.split(/a/).pop.to_i vi = v.split(/a/).pop.to_i
vi.should be >= 661484 # versions older than this will likely fail many specs vi.should be >= 661484 # versions older than this will likely fail many specs
vi.should be <= 661484 # versions newer than this haven't been tried vi.should be <= 663797 # versions newer than this haven't been tried
end end
end end

View file

@ -183,6 +183,49 @@ describe CouchRest::Database do
end end
end end
describe "PUT document with attachment" do
before(:each) do
@attach = "<html><head><title>My Doc</title></head><body><p>Has words.</p></body></html>"
@doc = {
"_id" => "mydocwithattachment",
"field" => ["some value"],
"_attachments" => {
"test.html" => @attach
}
}
@db.save(@doc)
end
it "should save and be indicated" do
doc = @db.get("mydocwithattachment")
doc['_attachments']['test.html']['length'].should == @attach.length
end
it "should be there" do
attachment = @db.fetch_attachment("mydocwithattachment","test.html")
attachment.should == @attach
end
end
describe "POST document with attachment (with funky name)" do
before(:each) do
@attach = "<html><head><title>My Funky Doc</title></head><body><p>Has words.</p></body></html>"
@doc = {
"field" => ["some other value"],
"_attachments" => {
"http://example.com/stuff.cgi?things=and%20stuff" => @attach
}
}
@docid = @db.save(@doc)['id']
end
it "should save and be indicated" do
doc = @db.get(@docid)
doc['_attachments']['http://example.com/stuff.cgi?things=and%20stuff']['length'].should == @attach.length
end
it "should be there" do
attachment = @db.fetch_attachment(@docid,"http://example.com/stuff.cgi?things=and%20stuff")
attachment.should == @attach
end
end
describe "PUT (new document with url id)" do describe "PUT (new document with url id)" do
it "should create the document" do it "should create the document" do
@docid = "http://example.com/stuff.cgi?things=and%20stuff" @docid = "http://example.com/stuff.cgi?things=and%20stuff"