Exemple #1
0
def process_changelog(evt_key, classes):
    """Process the entries from changelog identifying previous events
    by evt_key, and using events and callback methods in classes
    """

    evt_id2call_back = {}
    for c in classes:
        for t in c.get_triggers():
            evt_id2call_back.setdefault(int(getattr(cl_const, t)), []).append(
                getattr(c, "notify_%s" % t))

    ei = CLHandler.CLHandler(Factory.get('Database')())
    for evt in ei.get_events(evt_key, evt_id2call_back.keys()):
        ok = []
        for call_back in evt_id2call_back[int(evt.fields.change_type_id)]:
            if evt['change_params']:
                params = pickle.loads(evt['change_params'])
            else:
                params = {}
            logger.debug2("Callback %i -> %s" % (evt['change_id'], call_back))
            ok.append(call_back(evt, params))
        # Only confirm if all call_backs returned true
        if not filter(lambda t: not t, ok):
            ei.confirm_event(evt)
    ei.commit_confirmations()
Exemple #2
0
def main():
    db = Factory.get('Database')()
    clco = Factory.get('CLConstants')(db)
    cl = CLHandler.CLHandler(db)

    parser = argparse.ArgumentParser(description=__doc__)
    parser.add_argument(
        '-t',
        '--changelog_tracker',
        dest='changelog_tracker',
        default=cereconf.PWD_WIPE_EVENT_HANDLER_KEY,
        help='Event handler key to monitor for changes. Default is {0}'.format(
            cereconf.PWD_WIPE_EVENT_HANDLER_KEY))
    parser.add_argument(
        '-m',
        '--max_changes',
        dest='max_changes',
        default=cereconf.PWD_MAX_WIPES,
        help='Maximum number of passwords to wipe. Default is {0}'.format(
            cereconf.PWD_MAX_WIPES))
    parser.add_argument(
        '-a',
        '-age_threshold',
        dest='age_threshold',
        default=cereconf.PWD_AGE_THRESHOLD,
        help='how old passwords need to be before they are wiped. ' +
        'Default is {0}'.format(cereconf.PWD_AGE_THRESHOLD))
    parser.add_argument('-c',
                        '--commit',
                        dest='commit',
                        action='store_true',
                        help='Write changes to database')

    Cerebrum.logutils.options.install_subparser(parser)
    args = parser.parse_args()
    Cerebrum.logutils.autoconf('cronjob', args)

    if not args.changelog_tracker:
        logger.error("Empty changelog tracker! This would go through the "
                     "entire change-log. No way! Quitting!")
        return

    changes = cl.get_events(args.changelog_tracker, (clco.account_password, ))
    num_changes = len(changes)

    if num_changes == 0:
        logger.info("No passwords to wipe!")
        return
    elif num_changes > args.max_changes:
        logger.error(
            "Too many changes (%s)! Check if changelog tracker "
            "(%s) is correct, or override limit in command-line "
            "or cereconf", num_changes, args.changelog_tracker)
        return

    logger.info("Starting to wipe %s password changes since last wipe",
                num_changes)
    pwd_wipe(db, cl, changes, args.age_threshold, args.commit)
    logger.info("Finished wiping passwords")
Exemple #3
0
def main():
    global cl, db, co, ac, logger, server

    db = Factory.get('Database')()
    co = Factory.get('Constants')(db)
    ac = Factory.get('Account')(db)
    logger = Factory.get_logger("cronjob")
    cl = CLHandler.CLHandler(db)

    delete_objects = False
    user_spread = None
    dry_run = False

    passwd = db._read_password(cereconf.AD_SERVER_HOST,
                               cereconf.AD_SERVER_UNAME)

    # Connect to AD-service at NMH
    #
    server = xmlrpclib.Server(
        "https://%s@%s:%i" %
        (passwd, cereconf.AD_SERVER_HOST, cereconf.AD_SERVER_PORT))

    try:
        opts, args = getopt.getopt(sys.argv[1:], 'hds:',
                                   ['user_spread=', 'help', 'dry_run'])
    except getopt.GetoptError:
        usage()

    for opt, val in opts:
        if opt == '--user_spread':
            user_spread = getattr(co, val)  # TODO: Need support in Util.py
        elif opt == '--help':
            usage()
        elif opt == '--dry_run':
            dry_run = True

    if not user_spread:
        usage()

    logger.info("Syncronizing passwords...")
    quick_sync(user_spread, dry_run)
    logger.info("All done.")
Exemple #4
0
def main():
    global db, constants, logger, person, account
    global default_creator_id, default_expire_date

    db = Factory.get('Database')()
    db.cl_init(change_program='auto_create')
    acc = Factory.get('Account')(db)
    constants = Factory.get('Constants')(db)
    cl_handler = CLHandler.CLHandler(db)
    logger = Factory.get_logger('cronjob')
    person = Factory.get('Person')(db)
    account = Factory.get('Account')(db)

    acc.find_by_name(cereconf.INITIAL_ACCOUNTNAME)
    default_creator_id = acc.entity_id
    default_expire_date = None

    cl_events = []
    new_acc_id = None

    try:
        cl_events = cl_handler.get_events('auto_create',
                                          (constants.person_create, ))
        if cl_events == []:
            logger.info("Nothing to do.")
            sys.exit(0)

        for event in cl_events:
            if event['change_type_id'] == constants.person_create:
                new_acc_id = build_account(event['subject_entity'])
                if new_acc_id == None:
                    logger.error('Could not create an account for %s',
                                 event['subject_entity'])
                    continue
                cl_handler.confirm_event(event)
    except TypeError, e:
        logger.warn("No such event, %s" % e)
        return None
Exemple #5
0
def quicksync_roles_and_perms(client, selection_spread, config, commit):
    """Quick sync for roles and permissions.

    :type client: EphorteWS
    :param client: The client used to talk to ePhorte

    :type selection_spread: Spread
    :param selection_spread: A person must have this spread to be synced

    :type config: Config
    :param config: Configuration

    :type commit: bool
    :param commit: Commit confirmed events?
    """
    from Cerebrum.modules import CLHandler
    clh = CLHandler.CLHandler(db)
    pe = Factory.get('Person')(db)

    change_types_roles = (clconst.ephorte_role_add,
                          clconst.ephorte_role_rem,
                          clconst.ephorte_role_upd)
    change_types_perms = (clconst.ephorte_perm_add, clconst.ephorte_perm_rem)
    change_types = change_types_roles + change_types_perms

    event_selector = select_events_by_person(
        clh=clh,
        config=config,
        change_types=change_types,
        selection_spread=selection_spread)

    for person_id, events in event_selector:
        if not sanity_check_person(person_id=person_id,
                                   selection_spread=selection_spread):
            continue

        pe.clear()
        pe.find(person_id)

        if not update_person_info(pe, client):
            continue

        try:
            if update_person_roles(pe, client, remove_superfluous=True):
                for event in events:
                    if event['change_type_id'] in change_types_roles:
                        clh.confirm_event(event)
        except:
            logger.warn(
                'Failed to update roles for person_id:%s',
                person_id, exc_info=True)
        else:
            if commit:
                clh.commit_confirmations()

        try:
            if update_person_perms(pe, client, remove_superfluous=True):
                for event in events:
                    if event['change_type_id'] in change_types_perms:
                        clh.confirm_event(event)
        except:
            logger.warn(
                'Failed to update permissions for person_id:%s',
                person_id, exc_info=True)
        else:
            if commit:
                clh.commit_confirmations()

    if commit:
        clh.commit_confirmations()
If sendmail is enabled, events will be confirmed in CLHandler, and emails
will be sent instead of outputted to the logger instance.
"""

import pickle
import cereconf
import cerebrum_path
from Cerebrum import Errors
from Cerebrum import Utils
from Cerebrum.Utils import Factory
from Cerebrum.modules import CLHandler

db = Factory.get('Database')()
co = Factory.get('Constants')(db)
ac = Factory.get('Account')(db)
cl = CLHandler.CLHandler(db)


def check_changelog_for_quarantine_triggers(logger, sendmail):
    """
    Scans the changelog for changes related to the quarantines defined in
    cereconf.QUARANTINE_NOTIFY_DATA. This dict also contains which actions
    should trigger an email notification for specific quarantines, as well as
    the email sender/recipient and a quarantine-specific CLHandler-key.
    If sendmail is enabled, events will be confirmed in CLHandler, and emails
    will be sent instead of outputted to the logger instance.

    :param logger: Factory-generated logger-instance
    :param sendmail: Turns on event confirming to CLHandler and email sending
    :type: bool
    """
Exemple #7
0
def main():
    global logger
    global EVENT_KEY
    logger = Factory.get_logger('cronjob')
    parser = argparse.ArgumentParser(description=__doc__)
    parser.add_argument('-c', '--commit', action='store_true',
                        default=False, help="Commit changes")
    parser.add_argument('-s', '--skip-events', action='store_true',
                        default=False, help="Skip past events (good for initial"
                        "run)")
    args = parser.parse_args()

    db = Factory.get('Database')(client_encoding='UTF-8')
    db.cl_init(change_program="update-ougroups")
    co = Factory.get('Constants')(db)
    clco = Factory.get('CLConstants')(db)
    clh = CLHandler.CLHandler(db)
    data = make_data()

    types = {}

    def make_handler(tp, function, const):
        if tp == 'person':
            filler = fill_person
        elif tp == 'account':
            filler = fill_account
        elif tp == 'both':
            filler = fill_account
            tp = 'person'
        else:
            def handler(event):
                function(event, db, co, data)
            return handler

        def handler(event):
            args = event['change_params']
            if args is not None:
                args = pickle.loads(args)
            logger.debug('Handler(%s) called for %s', tp, args)
            eid = int(event['subject_entity'])
            datum = data[tp].get(eid)
            try:
                if datum is None:
                    datum = filler(eid, db, co, data)
                function(event, db, co, datum, args)
            except NotFoundError:
                pass
        return handler

    for tp in (('person',
                (clco.person_aff_src_add, handle_person_aff_add),
                (clco.person_aff_src_mod, handle_person_aff_mod),
                (clco.person_aff_src_del, handle_person_aff_del)),
               ('account',
                (clco.account_type_add, handle_account_type_add),
                (clco.account_type_mod, handle_account_type_mod),
                (clco.account_type_del, handle_account_type_del)),
               ('group',
                (clco.group_add, handle_group_add),
                (clco.group_rem, handle_group_rem))):
        t, changes = tp[0], tp[1:]
        for const, adder in changes:
            logger.debug5("Setting up handler %s -> %s", const, adder)
            types[int(const)] = make_handler(t, adder, const)

    events = clh.get_events(EVENT_KEY, types.keys())
    if args.skip_events:
        logger.info('Skipping events')
        for event in events:
            clh.confirm_event(event)
        logger.info('Done')
    else:
        logger.info('Starting event traversing')
        for event in reversed(events):
            logger.debug('Handling event %s', event)
            types.get(int(event['change_type_id']), lambda x: None)(event)
            clh.confirm_event(event)
        logger.info('Done event traversing, calculating changes')
        calculate_changes(db, data, co)
        logger.info('Done')

    if args.commit:
        logger.info('Committing')
        clh.commit_confirmations()
        db.commit()
    else:
        logger.info('Doing rollback')
        db.rollback()
Exemple #8
0
 def __init__(self, *args, **kwargs):
     super(ADquiSync, self).__init__(*args, **kwargs)
     self.cl = CLHandler.CLHandler(db)
Exemple #9
0
def main():

    parser = argparse.ArgumentParser(description=__doc__)
    parser.add_argument('-d',
                        '--dryrun',
                        dest='dryrun',
                        action='store_true',
                        default=False,
                        help="Do not commit the changes to db")
    parser.add_argument(
        '--list-handlers',
        action='store_true',
        help="List defined change handlers from the db and quit")
    parser.add_argument('--print-handlers',
                        action='store_true',
                        help="Print all change handler data and quit")
    parser.add_argument('-k',
                        '--key',
                        help="Set what change handler key you want to work on")
    parser.add_argument(
        '--force-last-id',
        type=int,
        default=0,
        help="""Force last_id to the given number. The key argument must be
        specified. If the change handler key doesn't exist, it gets created.
        Note: This forces the last_id and removes all gaps in the range before
        this, setting every change to "completed". Use with care!""")
    args = parser.parse_args()

    db = Factory.get('Database')(client_encoding='UTF-8')
    db.cl_init(change_program="change-handler-manipulator")
    co = Factory.get('Constants')(db)
    clh = CLHandler.CLHandler(db)

    logger.info("change_handler_manipulate.py started")

    if args.dryrun:
        # Force rollback to be sure, since CLHandler forces commits itself
        db.commit = db.rollback

    if args.list_handlers:
        handlers = {}
        for row in clh.list_handler_data():
            handlers.setdefault(row['evthdlr_key'], []).append(row)

        for key in sorted(handlers):
            first = None
            last = None

            ids = handlers[key]
            for i in ids:
                if first is None or i['first_id'] < first:
                    first = i['first_id']
                if last is None or i['last_id'] > last:
                    last = i['last_id']

            print "'%s' (%d handlers):" % (key, len(handlers[key]))
            print "  First first_id: %20d" % first
            print "  Last last_id:   %20d" % last
            print
    elif args.print_handlers:
        handlers = {}
        for row in clh.list_handler_data():
            handlers.setdefault(row['evthdlr_key'], []).append(row)
        print "%20s %10s %10s" % ('Key', 'first_id', 'last_id')
        for key in sorted(handlers):
            for r in handlers[key]:
                print "%20s %10d %10d" % (key, r['first_id'], r['last_id'])
    elif args.force_last_id > 0:
        if not args.key:
            raise Exception("Missing --key argument")
        logger.info("Forcing change handler key '%s' to last_id = %d",
                    args.key, args.force_last_id)
        clh._update_ranges(args.key, [
            [-1, args.force_last_id],
        ])
    else:
        print "No action given. Quits"

    if args.dryrun:
        logger.info("Rolled back changes")
        db.rollback()
    else:
        logger.info("Commiting changes")
        db.commit()
    logger.info("change_handler_manipulate.py finished")