diff --git a/ChangeLog b/ChangeLog index 666270236..e5a9f1ea0 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2009-01-11 Christophe Romain + + * src/mod_pubsub/mod_pubsub.erl: fix owners cache and fix unsubscribe + permissions (thanks to Andy Skelton)(EJAB-840) + * src/mod_pubsub/node_default.erl: Likewise + 2009-01-10 Pablo Polvorin * src/mod_vcard_odbc.erl: Fix bug in user search. diff --git a/src/mod_pubsub/mod_pubsub.erl b/src/mod_pubsub/mod_pubsub.erl index af4a57257..0ab6b7053 100644 --- a/src/mod_pubsub/mod_pubsub.erl +++ b/src/mod_pubsub/mod_pubsub.erl @@ -2031,15 +2031,33 @@ set_subscriptions(Host, Node, From, EntitiesEls) -> {error, 'bad-request'}; _ -> Action = fun(#pubsub_node{type = Type, owners = Owners}) -> - case lists:member(Owner, Owners) of - true -> - lists:foreach(fun({JID, Subscription}) -> - node_call(Type, set_subscription, [Host, Node, JID, Subscription]) - end, Entities), - {result, []}; - _ -> - {error, 'forbidden'} - end + case lists:member(Owner, Owners) of + true -> + lists:foreach( + fun({JID, Affiliation}) -> + node_call(Type, set_affiliation, [Host, Node, JID, Affiliation]), + case Affiliation of + owner -> + NewOwner = jlib:short_prepd_bare_jid(JID), + NewOwners = [NewOwner|Owners], + tree_call(Host, set_node, [N#pubsub_node{owners = NewOwners}]); + none -> + NewOwner = jlib:short_prepd_bare_jid(JID), + case lists:member(OldOwner, Owners) of + true -> + NewOwners = Owners--[OldOwner], + tree_call(Host, set_node, [N#pubsub_node{owners = NewOwners}]); + _ -> + ok + end; + _ -> + ok + end + end, Entities), + {result, []}; + _ -> + {error, 'forbidden'} + end end, transaction(Host, Node, Action, sync_dirty) end. diff --git a/src/mod_pubsub/node_default.erl b/src/mod_pubsub/node_default.erl index ebb92e112..afc305f86 100644 --- a/src/mod_pubsub/node_default.erl +++ b/src/mod_pubsub/node_default.erl @@ -288,7 +288,6 @@ subscribe_node(Host, Node, Sender, Subscriber, AccessModel, _ -> get_state(Host, Node, SubKey) end, Affiliation = GenState#pubsub_state.affiliation, - Subscription = SubState#pubsub_state.subscription, Whitelisted = lists:member(Affiliation, [member, publisher, owner]), if not Authorized -> @@ -297,7 +296,7 @@ subscribe_node(Host, Node, Sender, Subscriber, AccessModel, Affiliation == outcast -> %% Requesting entity is blocked {error, 'forbidden'}; - Subscription == pending -> + SubState#pubsub_state.subscription == pending -> %% Requesting entity has pending subscription {error, ?ERR_EXTENDED('not-authorized', "pending-subscription")}; (AccessModel == presence) and (not PresenceSubscription) -> @@ -358,8 +357,6 @@ unsubscribe_node(Host, Node, Sender, Subscriber, _SubId) -> GenKey -> GenState; _ -> get_state(Host, Node, SubKey) end, - Affiliation = GenState#pubsub_state.affiliation, - Subscription = SubState#pubsub_state.subscription, if %% Entity did not specify SubID %%SubID == "", ?? -> @@ -368,10 +365,10 @@ unsubscribe_node(Host, Node, Sender, Subscriber, _SubId) -> %%InvalidSubID -> %% {error, ?ERR_EXTENDED('not-acceptable', "invalid-subid")}; %% Requesting entity is not a subscriber - Subscription == none -> + SubState#pubsub_state.subscription == none -> {error, ?ERR_EXTENDED('unexpected-request', "not-subscribed")}; %% Requesting entity is prohibited from unsubscribing entity - (not Authorized) and (Affiliation =/= owner) -> + not Authorized -> {error, 'forbidden'}; %% Was just subscriber, remove the record SubState#pubsub_state.affiliation == none -> @@ -577,7 +574,12 @@ get_affiliation(Host, Node, Owner) -> set_affiliation(Host, Node, Owner, Affiliation) -> GenKey = jlib:short_prepd_bare_jid(Owner), GenState = get_state(Host, Node, GenKey), - set_state(GenState#pubsub_state{affiliation = Affiliation}), + case {Affiliation, GenState#pubsub_state.subscription} of + {none, none} -> + del_state(GenState#pubsub_state.stateid); + _ -> + set_state(GenState#pubsub_state{affiliation = Affiliation}) + end, ok. %% @spec (Host, Owner) -> [{Node,Subscription}] @@ -614,14 +616,19 @@ get_node_subscriptions(Host, Node) -> {result, lists:map(Tr, States)}. get_subscription(Host, Node, Owner) -> - GenKey = jlib:short_prepd_bare_jid(Owner), - GenState = get_state(Host, Node, GenKey), - {result, GenState#pubsub_state.subscription}. + SubKey = jlib:short_prepd_jid(Owner), + SubState = get_state(Host, Node, SubKey), + {result, SubState#pubsub_state.subscription}. set_subscription(Host, Node, Owner, Subscription) -> - GenKey = jlib:short_prepd_bare_jid(Owner), - GenState = get_state(Host, Node, GenKey), - set_state(GenState#pubsub_state{subscription = Subscription}), + SubKey = jlib:short_prepd_jid(Owner), + SubState = get_state(Host, Node, SubKey), + case {Subscription, SubState#pubsub_state.affiliation} of + {none, none} -> + del_state(SubState#pubsub_state.stateid); + _ -> + set_state(SubState#pubsub_state{subscription = Subscription}) + end, ok. %% @spec (Host, Node) -> [States] | []