diff options
author | Matthew Sackman <matthew@rabbitmq.com> | 2010-09-30 15:24:24 +0100 |
---|---|---|
committer | Matthew Sackman <matthew@rabbitmq.com> | 2010-09-30 15:24:24 +0100 |
commit | 68001e01905c771d4f6ebb712804e11be02a1c3a (patch) | |
tree | 10bba0f14a5a9c1ff1b1306e2e04739cf06c57a5 | |
parent | c4f5e27ff5fc0b2137fba393abb60999aa35bbb6 (diff) | |
download | rabbitmq-server-68001e01905c771d4f6ebb712804e11be02a1c3a.tar.gz |
Exchange auto-deletion works even with e2e. Diamond property works. Correct behaviour if explicitly deleted entity is queue or exchange
-rw-r--r-- | src/rabbit_binding.erl | 25 | ||||
-rw-r--r-- | src/rabbit_exchange.erl | 14 |
2 files changed, 21 insertions, 18 deletions
diff --git a/src/rabbit_binding.erl b/src/rabbit_binding.erl index 0199a354..a0389a52 100644 --- a/src/rabbit_binding.erl +++ b/src/rabbit_binding.erl @@ -167,12 +167,8 @@ remove(Binding, InnerFun) -> end) of {error, _} = Err -> Err; - {{IsDeleted, Src = #exchange{ type = Type }}, B} -> - Module = type_to_module(Type), - case IsDeleted of - auto_deleted -> ok = Module:delete(Src, [B]); - not_deleted -> ok = Module:remove_bindings(Src, [B]) - end, + {{IsDeleted, Src}, B} -> + ok = post_binding_removal(IsDeleted, Src, [B]), rabbit_event:notify(binding_deleted, info(B)), ok end. @@ -330,15 +326,20 @@ remove_for_destination(DstName, FwdDeleteFun) -> lists:keysort(#binding.source, DeletedBindings), []), fun () -> lists:foreach( - fun ({{IsDeleted, Src = #exchange{ type = Type }}, Bs}) -> - Module = type_to_module(Type), - case IsDeleted of - auto_deleted -> Module:delete(Src, Bs); - not_deleted -> Module:remove_bindings(Src, Bs) - end + fun ({{IsDeleted, Src}, Bs}) -> + ok = post_binding_removal(IsDeleted, Src, Bs) end, Grouped) end. +post_binding_removal(IsDeleted, Src = #exchange{ type = Type }, Bs) -> + Module = type_to_module(Type), + case IsDeleted of + {auto_deleted, Fun} -> ok = Module:delete(Src, Bs), + Fun(), + ok; + not_deleted -> ok = Module:remove_bindings(Src, Bs) + end. + %% Requires that its input binding list is sorted in exchange-name %% order, so that the grouping of bindings (for passing to %% group_bindings_and_auto_delete1) works properly. diff --git a/src/rabbit_exchange.erl b/src/rabbit_exchange.erl index 8497aa7b..e3ec1dcc 100644 --- a/src/rabbit_exchange.erl +++ b/src/rabbit_exchange.erl @@ -82,8 +82,9 @@ (name(), boolean())-> 'ok' | rabbit_types:error('not_found') | rabbit_types:error('in_use')). --spec(maybe_auto_delete/1:: (rabbit_types:exchange()) -> - 'not_deleted' | 'auto_deleted'). +-spec(maybe_auto_delete/1:: + (rabbit_types:exchange()) + -> 'not_deleted' | {'auto_deleted', fun (() -> any())}). -endif. @@ -289,8 +290,9 @@ delete(XName, IfUnused) -> false -> fun unconditional_delete/1 end, case call_with_exchange(XName, Fun) of - {deleted, X = #exchange{type = Type}, Bs} -> + {deleted, X = #exchange{type = Type}, Bs, Fun1} -> (type_to_module(Type)):delete(X, Bs), + Fun1(), ok; Error = {error, _InUseOrNotFound} -> Error @@ -300,8 +302,8 @@ maybe_auto_delete(#exchange{auto_delete = false}) -> not_deleted; maybe_auto_delete(#exchange{auto_delete = true} = X) -> case conditional_delete(X) of - {error, in_use} -> not_deleted; - {deleted, X, []} -> auto_deleted + {error, in_use} -> not_deleted; + {deleted, X, [], Fun} -> {auto_deleted, Fun} end. conditional_delete(X = #exchange{name = XName}) -> @@ -315,4 +317,4 @@ unconditional_delete(X = #exchange{name = XName}) -> ok = mnesia:delete({rabbit_durable_exchange, XName}), ok = mnesia:delete({rabbit_exchange, XName}), rabbit_event:notify(exchange_deleted, [{name, XName}]), - {deleted, X, Bindings}. + {deleted, X, Bindings, rabbit_binding:remove_for_destination(XName)}. |