summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatthew Sackman <matthew@rabbitmq.com>2010-09-12 17:18:38 +0100
committerMatthew Sackman <matthew@rabbitmq.com>2010-09-12 17:18:38 +0100
commitc5126e4b19d2b5da1e8ad291fea29617c8b412ee (patch)
tree8e4c90af7107597f7b8d54e9df540af882bfe838
parent9ffaa55446fbe90d145dd23cf48ae640f360bf84 (diff)
downloadrabbitmq-server-c5126e4b19d2b5da1e8ad291fea29617c8b412ee.tar.gz
Avoid traversing lists multiple times
-rw-r--r--src/rabbit_exchange.erl29
-rw-r--r--src/rabbit_router.erl12
2 files changed, 18 insertions, 23 deletions
diff --git a/src/rabbit_exchange.erl b/src/rabbit_exchange.erl
index 9f85f4cc..14cd5cf4 100644
--- a/src/rabbit_exchange.erl
+++ b/src/rabbit_exchange.erl
@@ -233,14 +233,15 @@ publish(X = #exchange{name = XName}, Delivery) ->
find_qnames(Delivery, WorkList, SeenXs, QNames) ->
case queue:out(WorkList) of
{empty, _WorkList} ->
- lists:usort(lists:flatten(QNames));
+ lists:usort(QNames);
{{value, X = #exchange{type = Type}}, WorkList1} ->
- {NewQNames, NewXNames} =
+ DstNames =
process_alternate(
X, ((type_to_module(Type)):publish(X, Delivery))),
- {WorkList2, SeenXs1} =
+ {WorkList2, SeenXs1, QNames1} =
lists:foldl(
- fun (XName, {WorkListN, SeenXsN} = Acc) ->
+ fun (XName = #resource{kind = exchange},
+ {WorkListN, SeenXsN, QNamesN} = Acc) ->
case lists:member(XName, SeenXsN) of
true -> Acc;
false -> {case lookup(XName) of
@@ -248,19 +249,19 @@ find_qnames(Delivery, WorkList, SeenXs, QNames) ->
queue:in(X1, WorkListN);
{error, not_found} ->
WorkListN
- end, [XName | SeenXsN]}
- end
- end, {WorkList1, SeenXs}, NewXNames),
- find_qnames(Delivery, WorkList2, SeenXs1,
- [NewQNames | QNames])
+ end, [XName | SeenXsN], QNamesN}
+ end;
+ (QName = #resource{kind = queue},
+ {WorkListN, SeenXsN, QNamesN})->
+ {WorkListN, SeenXsN, [QName | QNamesN]}
+ end, {WorkList1, SeenXs, QNames}, DstNames),
+ find_qnames(Delivery, WorkList2, SeenXs1, QNames1)
end.
-process_alternate(#exchange{name = XName, arguments = Args}, {[], []}) ->
+process_alternate(#exchange{name = XName, arguments = Args}, []) ->
case rabbit_misc:r_arg(XName, exchange, Args, <<"alternate-exchange">>) of
- undefined ->
- {[], []};
- AName ->
- {[], [AName]}
+ undefined -> [];
+ AName -> [AName]
end;
process_alternate(_X, Results) ->
Results.
diff --git a/src/rabbit_router.erl b/src/rabbit_router.erl
index c5a1c440..0fccd61b 100644
--- a/src/rabbit_router.erl
+++ b/src/rabbit_router.erl
@@ -43,7 +43,7 @@
-type(routing_key() :: binary()).
-type(routing_result() :: 'routed' | 'unroutable' | 'not_delivered').
--type(match_result() :: {[rabbit_amqqueue:name()], [rabbit_exchange:name()]}).
+-type(match_result() :: [rabbit_amqqueue:name() | rabbit_exchange:name()]).
-spec(deliver/2 ::
([pid()], rabbit_types:delivery()) -> {routing_result(), [pid()]}).
@@ -91,20 +91,14 @@ match_bindings(SrcName, Match) ->
mnesia:table(rabbit_route),
SrcName == SrcName1,
Match(Binding)]),
- partition_destinations(mnesia:async_dirty(fun qlc:e/1, [Query])).
+ mnesia:async_dirty(fun qlc:e/1, [Query]).
match_routing_key(SrcName, RoutingKey) ->
MatchHead = #route{binding = #binding{source = SrcName,
destination = '$1',
key = RoutingKey,
_ = '_'}},
- partition_destinations(
- mnesia:dirty_select(rabbit_route, [{MatchHead, [], ['$1']}])).
-
-partition_destinations(Destinations) ->
- lists:partition(
- fun (DestinationName) -> DestinationName#resource.kind =:= queue end,
- Destinations).
+ mnesia:dirty_select(rabbit_route, [{MatchHead, [], ['$1']}]).
%%--------------------------------------------------------------------