63 lines
2.4 KiB
Python
63 lines
2.4 KiB
Python
from typing import List, Dict
|
|
|
|
from zope import component
|
|
|
|
from ..AbstractTransaction import AbstractTransaction
|
|
from ceo_common.interfaces import ILDAPService, IConfig
|
|
from ceo_common.errors import UserAlreadySubscribedError, UserNotSubscribedError
|
|
from ceo_common.logger_factory import logger_factory
|
|
|
|
logger = logger_factory(__name__)
|
|
|
|
class UpdateMemberPositionsTransaction(AbstractTransaction):
|
|
"""
|
|
Transaction to update member's positions, and remove positions for anyone that's not in the list,
|
|
then subscribe new execs to mailing list and unsubscribe old execs from it.
|
|
"""
|
|
|
|
# Positions is a dict where keys are member names and values are the list of positions they have
|
|
def __init__(self, positions: Dict[str, List[str]]):
|
|
super().__init__()
|
|
self.positions = positions
|
|
self.old_positions = {} # For rollback
|
|
self.ldap_srv = component.getUtility(ILDAPService)
|
|
|
|
def child_execute_iter(self):
|
|
cfg = component.getUtility(IConfig)
|
|
mailing_lists = cfg.get('auxiliary mailing lists_exec')
|
|
|
|
subscribe_status: Dict[IUser, bool] = {}
|
|
|
|
# Remove positions for old users
|
|
for user in self.ldap_srv.get_users_with_positions():
|
|
if user.uid not in self.positions:
|
|
self.positions[user.uid] = []
|
|
|
|
# Update positions via ldap
|
|
for username, positions in self.positions.items():
|
|
user = self.ldap_srv.get_user(username)
|
|
self.old_positions[username] = user.positions[:]
|
|
user.set_positions(positions)
|
|
subscribe_status[user] = len(positions) > 0
|
|
yield f'update_positions_{username}'
|
|
|
|
# Update mailing list subscription
|
|
for user, subscribe in subscribe_status.items():
|
|
for mailing_list in mailing_lists:
|
|
try:
|
|
if subscribe:
|
|
user.subscribe_to_mailing_list(mailing_list)
|
|
else:
|
|
user.unsubscribe_from_mailing_list(mailing_list)
|
|
except (UserAlreadySubscribedError, UserNotSubscribedError):
|
|
pass
|
|
except Exception as e:
|
|
logger.warning(f'Failed to update mailing list for {user.uid}')
|
|
|
|
self.finish(None)
|
|
|
|
def rollback(self):
|
|
for username, positions in self.old_positions.items():
|
|
user = self.ldap_srv.get_user(username)
|
|
user.set_positions(positions)
|