Beispiel #1
0
def move_to_commited(log_action, *args, **kwargs):
    sl = data.SL()
    item = next((i for i in sl if i.log_action == log_action), None)
    if item:
        resource_obj = resource.load(item.resource)
        commited = CommitedResource.get_or_create(item.resource)
        updated = resource_obj.db_obj.updated
        if item.action == CHANGES.remove.name:

            resource_obj.delete()
            commited.state = resource.RESOURCE_STATE.removed.name
        else:
            resource_obj.set_operational()
            commited.state = resource.RESOURCE_STATE.operational.name
            commited.base_path = item.base_path
            updated = resource_obj.db_obj.updated
            # required to update `updated` field
            resource_obj.db_obj.save()
        commited.inputs = patch(item.diff, commited.inputs)
        # TODO fix TagsWrp to return list
        # commited.tags = resource_obj.tags
        sorted_connections = sorted(commited.connections)
        commited.connections = patch(item.connections_diff, sorted_connections)
        commited.save()
        item.log = 'history'
        item.state = 'success'
        item.updated = updated
        item.save()
Beispiel #2
0
def test_revert_removal():
    res = orm.DBResource(id='test1', name='test1', base_path='x')
    res.save()
    res.add_input('a', 'str', '9')
    res.add_input('location_id', 'str', '1')
    res.add_input('transports_id', 'str', '1')

    commited = orm.DBCommitedState.get_or_create('test1')
    commited.inputs = {'a': '9', 'location_id': '1', 'transports_id': '1'}
    commited.save()

    logitem =change.create_logitem(
        res.name, 'remove', change.create_diff({}, {'a': '9'}), [],
        base_path=res.base_path)
    log = data.SL()
    log.append(logitem)
    resource_obj = resource.load(res.name)
    resource_obj.remove()
    operations.move_to_commited(logitem.log_action)

    resources = orm.DBResource.load_all()

    assert resources == []
    assert logitem.diff == [('remove', '', [('a', '9')])]

    with mock.patch.object(resource, 'read_meta') as mread:
        mread.return_value = {'input': {'a': {'schema': 'str!'}}, 'id': 'mocked'}
        change.revert(logitem.uid)
    resource_obj = resource.load('test1')
    assert resource_obj.args == {'a': '9', 'location_id': '1', 'transports_id': '1'}
Beispiel #3
0
def test_revert_update():
    commit = {'a': '10'}
    previous = {'a': '9'}
    res = DBResource.from_dict('test1',
                               {'name': 'test1',
                                'base_path': 'x',
                                'meta_inputs': {'a': {'value': None,
                                                      'schema': 'str'}}})
    res.save()
    action = 'update'
    res.inputs['a'] = '9'
    resource_obj = resource.load(res.name)

    assert resource_obj.args == previous

    log = data.SL()
    logitem = change.create_logitem(res.name,
                                    action,
                                    change.create_diff(commit, previous),
                                    [],
                                    base_path=res.base_path)
    log.append(logitem)
    resource_obj.update(commit)
    operations.move_to_commited(logitem.log_action)

    assert logitem.diff == [('change', 'a', ('9', '10'))]
    assert resource_obj.args == commit

    change.revert(logitem.uid)
    assert resource_obj.args == previous
Beispiel #4
0
def test_revert_update():
    commit = {'a': '10'}
    previous = {'a': '9'}
    res = orm.DBResource(id='test1', name='test1', base_path='x')
    res.save()
    res.add_input('a', 'str', '9')
    action = 'update'

    resource_obj = resource.load(res.name)

    assert resource_obj.args == previous

    log = data.SL()
    logitem =change.create_logitem(
        res.name, action, change.create_diff(commit, previous), [],
        base_path=res.base_path)
    log.append(logitem)
    resource_obj.update(commit)
    operations.move_to_commited(logitem.log_action)

    assert logitem.diff == [('change', 'a', ('9', '10'))]
    assert resource_obj.args == commit

    change.revert(logitem.uid)
    assert resource_obj.args == previous
Beispiel #5
0
def staged_item(log_action):
    item = data.SL().get(log_action)
    if not item:
        click.echo('No staged changes for {}'.format(log_action))
    else:
        click.echo(item)
        for line in item.details:
            click.echo(' '*4+line)
Beispiel #6
0
def set_error(log_action, *args, **kwargs):
    sl = data.SL()
    item = next((i for i in sl if i.log_action == log_action), None)
    if item:
        resource_obj = resource.load(item.res)
        resource_obj.set_error()
        item.state = data.STATES.error
        sl.update(item)
Beispiel #7
0
def set_error(log_action, *args, **kwargs):
    sl = data.SL()
    item = next((i for i in sl if i.log_action == log_action), None)
    if item:
        resource_obj = resource.load(item.resource)
        resource_obj.set_error()
        item.state = 'error'
        item.delete()
Beispiel #8
0
def stage_changes():
    for li in data.SL():
        li.delete()

    last = LogItem.history_last()
    since = StrInt.greater(last.updated) if last else None
    staged_log = utils.solar_map(make_single_stage_item,
                                 resource.load_updated(since), concurrency=10)
    staged_log = filter(None, staged_log)
    return staged_log
Beispiel #9
0
def discard_uids(uids):
    staged_log = data.SL()
    check_uids_present(staged_log, uids)
    for uid in uids:
        item = staged_log.get(uid)
        if item.action == CHANGES.update.name:
            _discard_update(item)
        elif item.action == CHANGES.remove.name:
            _discard_remove(item)
        elif item.action == CHANGES.run.name:
            _discard_run(item)
        else:
            log.debug('Action %s for resource %s is a side'
                      ' effect of another action', item.action, item.res)
        staged_log.pop(uid)
Beispiel #10
0
def send_to_orchestration():
    dg = nx.MultiDiGraph()
    events = {}
    changed_nodes = []

    for logitem in data.SL():
        events[logitem.res] = evapi.all_events(logitem.res)
        changed_nodes.append(logitem.res)

        state_change = evapi.StateChange(logitem.res, logitem.action)
        state_change.insert(changed_nodes, dg)

    evapi.build_edges(dg, events)

    # what `name` should be?
    dg.graph['name'] = 'system_log'
    return graph.create_plan_from_graph(dg)
Beispiel #11
0
def send_to_orchestration(tags=None):
    dg = nx.MultiDiGraph()
    events = {}
    changed_nodes = []

    if tags:
        staged_log = LogItem.log_items_by_tags(tags)
    else:
        staged_log = data.SL()
    for logitem in staged_log:
        events[logitem.resource] = evapi.all_events(logitem.resource)
        changed_nodes.append(logitem.resource)

        state_change = StateChange(logitem.resource, logitem.action)
        state_change.insert(changed_nodes, dg)

    evapi.build_edges(dg, events)

    # what `name` should be?
    dg.graph['name'] = 'system_log'
    return graph.create_plan_from_graph(dg)
Beispiel #12
0
def staged_log(populate_with_changes=True):
    """Staging procedure takes manually created log items, populate them
    with diff and connections diff

    Current implementation prevents from several things to occur:
    - same log_action (resource.action pair) cannot not be staged multiple
      times
    - child will be staged only if diff or connections_diff is changed,
      and we can execute *run* action to apply that diff - in all other cases
      child should be staged explicitly
    """
    log_actions = set()
    resources_names = set()
    staged_log = data.SL()
    without_duplicates = []
    for log_item in staged_log:
        if log_item.log_action in log_actions:
            log_item.delete()
            continue
        resources_names.add(log_item.resource)
        log_actions.add(log_item.log_action)
        without_duplicates.append(log_item)

    utils.solar_map(lambda li: populate_log_item(li),
                    without_duplicates,
                    concurrency=10)
    # this is backward compatible change, there might better way
    # to "guess" child actions
    childs = filter(lambda child: child.name not in resources_names,
                    resource.load_childs(list(resources_names)))
    child_log_items = filter(
        lambda li: li.diff or li.connections_diff,
        utils.solar_map(create_run, [c.name for c in childs], concurrency=10))
    for log_item in child_log_items + without_duplicates:
        log_item.save_lazy()
    return without_duplicates + child_log_items
Beispiel #13
0
def move_to_commited(log_action, *args, **kwargs):
    sl = data.SL()
    item = next((i for i in sl if i.log_action == log_action), None)
    if item:
        sl.pop(item.uid)
        resource_obj = resource.load(item.res)
        commited = orm.DBCommitedState.get_or_create(item.res)

        if item.action == CHANGES.remove.name:
            resource_obj.delete()
            commited.state = resource.RESOURCE_STATE.removed.name
        else:
            resource_obj.set_operational()
            commited.state = resource.RESOURCE_STATE.operational.name
            commited.inputs = patch(item.diff, commited.inputs)
            commited.tags = resource_obj.tags
            sorted_connections = sorted(commited.connections)
            commited.connections = patch(item.signals_diff, sorted_connections)
            commited.base_path = item.base_path

        commited.save()
        cl = data.CL()
        item.state = data.STATES.success
        cl.append(item)
Beispiel #14
0
def stage_changes():
    log = data.SL()
    log.clean()

    for resouce_obj in resource.load_all():
        commited = resouce_obj.load_commited()
        base_path = resouce_obj.base_path
        if resouce_obj.to_be_removed():
            resource_args = {}
            resource_connections = []
        else:
            resource_args = resouce_obj.args
            resource_connections = resouce_obj.connections

        if commited.state == RESOURCE_STATE.removed.name:
            commited_args = {}
            commited_connections = []
        else:
            commited_args = commited.inputs
            commited_connections = commited.connections

        inputs_diff = create_diff(resource_args, commited_args)
        connections_diff = create_sorted_diff(
            resource_connections, commited_connections)

        # if new connection created it will be reflected in inputs
        # but using inputs to reverse connections is not possible
        if inputs_diff:
            log_item = create_logitem(
                resouce_obj.name,
                guess_action(commited_args, resource_args),
                inputs_diff,
                connections_diff,
                base_path=base_path)
            log.append(log_item)
    return log
Beispiel #15
0
def commit_all():
    """Helper mainly for ease of testing"""
    from solar.system_log.operations import move_to_commited
    for item in data.SL():
        move_to_commited(item.log_action)
Beispiel #16
0
def discard_all():
    staged_log = data.SL()
    return discard_uids([l.key for l in staged_log])
Beispiel #17
0
def move_to_commited(log_action, *args, **kwargs):
    sl = data.SL()
    item = next((i for i in sl if i.log_action == log_action), None)
    if item:
        commit_log_item(item)