summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorAdam Kocoloski <adam@cloudant.com>2010-05-28 14:26:07 -0400
committerAdam Kocoloski <adam@cloudant.com>2010-05-28 14:26:07 -0400
commit12318c9384bd8f8d82b0c1501e3e8ab0fea34095 (patch)
treea9aacd1853f5f8367666cea947aec3b5d6e86769 /src
parent450bc69ea891d9ad03c26c31c181c28ee5cbe8f9 (diff)
open_revs for fabric, BugzID 10216
Diffstat (limited to 'src')
-rw-r--r--src/fabric_doc.erl25
-rw-r--r--src/fabric_rpc.erl12
2 files changed, 26 insertions, 11 deletions
diff --git a/src/fabric_doc.erl b/src/fabric_doc.erl
index 97e7cfb6..e641d286 100644
--- a/src/fabric_doc.erl
+++ b/src/fabric_doc.erl
@@ -22,7 +22,12 @@ open_revs(DbName, Id, Revs, Options) ->
Workers = fabric_util:submit_jobs(partitions:for_key(DbName,Id), open_revs,
[Id, Revs, Options]),
Acc0 = {length(Workers), couch_util:get_value(r, Options, 1), []},
- fabric_util:recv(Workers, #shard.ref, fun handle_open_revs/3, Acc0).
+ case fabric_util:recv(Workers, #shard.ref, fun handle_open_revs/3, Acc0) of
+ {ok, {ok, Reply}} ->
+ {ok, Reply};
+ Else ->
+ Else
+ end.
get_missing_revs(DbName, AllIdsRevs) ->
Workers = lists:map(fun({#shard{name=Name, node=Node} = Shard, IdsRevs}) ->
@@ -69,8 +74,18 @@ handle_open_revs(_Worker, {rexi_DOWN, _, _, _}, Acc0) ->
skip_message(Acc0);
handle_open_revs(_Worker, {rexi_EXIT, _}, Acc0) ->
skip_message(Acc0);
-handle_open_revs(_Worker, _Reply, {_WaitingCount, _R, _Replies}) ->
- {stop, not_implemented}.
+handle_open_revs(_Worker, Reply, {WaitingCount, R, Replies}) ->
+ case merge_read_reply(make_key(Reply), Reply, Replies) of
+ {_, KeyCount} when KeyCount =:= R ->
+ {stop, Reply};
+ {NewReplies, KeyCount} when KeyCount < R ->
+ if WaitingCount =:= 1 ->
+ % last message arrived, but still no quorum
+ repair_read_quorum_failure(NewReplies);
+ true ->
+ {ok, {WaitingCount-1, R, NewReplies}}
+ end
+ end.
handle_missing_revs(_Worker, {rexi_DOWN, _, _, _}, Acc0) ->
skip_message(Acc0);
@@ -200,8 +215,8 @@ append_update_replies([Doc|Rest1], [Reply|Rest2], Dict0) ->
make_key({ok, #doc{id=Id, revs=Revs}}) ->
{Id, Revs};
-make_key({not_found, missing}) ->
- {not_found, missing}.
+make_key(Else) ->
+ Else.
repair_read_quorum_failure(Replies) ->
case [Doc || {_Key, {ok, Doc}, _Count} <- Replies] of
diff --git a/src/fabric_rpc.erl b/src/fabric_rpc.erl
index 75ce5e90..90ee8627 100644
--- a/src/fabric_rpc.erl
+++ b/src/fabric_rpc.erl
@@ -1,7 +1,7 @@
-module(fabric_rpc).
--export([open_doc/3, open_doc/4, get_db_info/1, update_docs/3,
- get_missing_revs/2]).
+-export([get_db_info/1]).
+-export([open_doc/3, open_revs/4, get_missing_revs/2, update_docs/3]).
-include("../../couch/src/couch_db.hrl").
-include_lib("eunit/include/eunit.hrl").
@@ -25,13 +25,13 @@ get_missing_revs(DbName, IdRevsList) ->
Error ->
Error
end).
-
+
+open_revs(DbName, Id, Revs, Options) ->
+ with_db(DbName, {couch_db, open_doc_revs, [Id, Revs, Options]}).
+
%% rpc endpoints
%% call to with_db will supply your M:F with a #db{} and then remaining args
-open_doc(DbName, DocId, Revs, Options) ->
- with_db(DbName, {couch_api, open_doc, [DocId, Revs, Options]}).
-
get_db_info(DbName) ->
with_db(DbName, {couch_db, get_db_info, []}).