Exemple #1
0
def assign_to_pool(zone_number, cluster_id):
  vms = []
  id_to_vm = {}
  selected_vm_ids = {}
  pools = None
  zone = None
  cluster = None
  memberships = {}
  try:
    Session()
    zone = Zone.query.get(zone_number)
    cluster = Cluster.query.filter_by(zone=zone, id=cluster_id).first()
    one_proxy = OneProxy(zone.xmlrpc_uri, zone.session_string, verify_certs=False)
    for membership in PoolMembership.query.join(VirtualMachinePool).filter_by(cluster=cluster).all():
      memberships[membership.vm_id] = membership
    for vm in one_proxy.get_vms():
      if vm.disk_cluster.id == cluster.id:
        vms.append(vm)
        id_to_vm[vm.id] = vm
    pools = VirtualMachinePool.get_all(cluster)
  except Exception as e:
    # raise e
    flash("Error fetching VMs in zone number {}: {}"
          .format(zone.number, e), category='danger')
  form = ActionForm()
  active_tab = 'create_new_pool'
  # Form submission handling begins
  if form.validate_on_submit():
    # Determine which tab needs to be active based on the action
    if request.form['action'] is not None:
      print('something')
      active_tab = {
        'create new pool': 'create_new_pool',
        'add to pool': 'add_to_existing_pool'}[request.form['action']]
    # Get a list of clusters of all selected VMs--pools cannot span clusters
    selected_clusters = {}
    for id in request.form.getlist('chk_vm_id'):
      selected_vm_ids[int(id)] = id
      selected_clusters[id_to_vm[int(id)].disk_cluster.id] = True
    # Error checking begins
    proceed = True
    if len(selected_vm_ids) == 0:
      flash("No virtual machines were selected!", category='danger')
      proceed = False
    elif len(selected_clusters) != 1:
      flash("Selected VMs must all be in the same cluster", category='danger')
      proceed = False
    # Handle the appropriate action if able to proceed
    if proceed and request.form['action'] == 'add to pool':
      if (request.form['pool_id']) is None or request.form['pool_id'] == '':
        flash('No pool selected', category='danger')
      else:
        pool = VirtualMachinePool.query.get(request.form['pool_id'])
        for vm_id in selected_vm_ids.keys():
          Session.add(PoolMembership(pool=pool, vm_name=id_to_vm[vm_id].name, vm_id=vm_id, date_added=datetime.utcnow()))
          Session.commit()
        flash(Markup('Successfully added {} members to pool <a href="{}">{}</a>'.format(
          len(selected_vm_ids),
          url_for('vpool_bp.view', pool_id=pool.id),
          pool.name, )), category='success')
        return redirect(url_for('vpool_bp.assign_to_pool', zone_number=zone.number, cluster_id=cluster.id))
    if proceed and request.form['action'] == 'create new pool':
      try:
        if request.form['new_pool_name'] is None or request.form['new_pool_name'] == '':
          raise Exception('Pool name cannot be blank')
        pool = VirtualMachinePool(
          name=request.form['new_pool_name'],
          cluster=cluster,
          zone_number=zone.number,
          cardinality=len(selected_vm_ids))
        Session.add(pool)
        Session.flush()
        for vm_id in selected_vm_ids.keys():
          membership = PoolMembership(pool=pool, vm_name=id_to_vm[vm_id].name, vm_id=vm_id, date_added=datetime.utcnow())
          memberships[vm_id] = membership
          Session.add(membership)
        Session.flush()
        Session.commit()
        flash(Markup('Successfully created <a href="{}">{}</a> with {} pool members'.format(
          url_for('vpool_bp.view', pool_id=pool.id),
          pool.name, len(selected_vm_ids))), category='success')
      except Exception as e:
        Session.rollback()
        flash('Error creating your new pool: {}'.format(e), category='danger')
  return render_template(
    'vpool/assign_to_pool.html',
    form=form,
    zone=zone,
    cluster=cluster,
    vms=vms,
    memberships=memberships,
    selected_vm_ids=selected_vm_ids,
    pools=pools,
    active_tab_name=active_tab
  )
Exemple #2
0
def plan_update(self, pool, update_members):
    task = crq = None
    try:
        pool = Session.merge(pool)
        start, end = jira.next_immediate_window_dates()
        logging = jira.instance.issue('SVC-1020')
        crq = jira.instance.create_issue(
            project=app.config['JIRA_CRQ_PROJECT'],
            issuetype={'name': 'Change Request'},
            assignee={'name': app.config['JIRA_USERNAME']},
            summary="[IMPLEMENT] {}".format(self.task.name),
            description=self.task.description,
            customfield_14530=start,
            customfield_14531=end,
            customfield_19031={'value': 'Maintenance'},
            customfield_15152=[{
                'value': 'Global'
            }],
            customfield_19430={'value': 'No conflict with any restrictions'},
            customfield_14135={
                'value': 'IPG',
                'child': {
                    'value': 'IPG Big Data'
                }
            },
            customfield_17679="Pool update required")
        self.log.msg("Created change request: {}".format(crq.key))
        jira.instance.transition_issue(
            crq, app.config['JIRA_TRANSITION_CRQ_PLANNING'])
        self.log.msg("Transitioned {} to planning".format(crq.key))
        jira.instance.create_issue_link('Relate', crq, logging)
        self.log.msg("Related {} to LOGGING service {}".format(
            crq.key, logging.key))
        batch_size = floor(
            len(update_members) / app.config['BATCH_SIZE_PERCENT'])
        batch_size = 1 if batch_size == 0 else batch_size
        num_batches = min(len(update_members),
                          app.config['BATCH_SIZE_PERCENT'])
        self.log.msg(
            "updating {} hosts in pool {} requires {} tasks with no more than {} hosts per task"
            .format(len(update_members), pool.name, num_batches, batch_size))
        batch_num = 0
        while len(update_members):
            batch_num += 1
            task = jira.instance.create_issue(
                issuetype={'name': 'MOP Task'},
                assignee={'name': app.config['JIRA_USERNAME']},
                project=app.config['JIRA_CRQ_PROJECT'],
                summary='[TASK {}/{} (Update {}%)] {}'.format(
                    batch_num, num_batches, app.config['BATCH_SIZE_PERCENT'],
                    self.task.name),
                parent={'key': crq.key},
                customfield_14135={
                    'value': 'IPG',
                    'child': {
                        'value': 'IPG Big Data'
                    }
                },
                customfield_15150={'value': 'No'})
            self.log.msg("Created task: {}".format(task.key))
            jira.instance.transition_issue(
                task, app.config['JIRA_TRANSITION_TASK_PLANNING'])
            self.log.msg("Transitioned {} to planning".format(task.key))
            env = Environment(loader=ObjectLoader())
            for num in range(0, min(len(update_members), batch_size)):
                m = update_members.pop()
                filename = '{}.{}.template'.format(m.pool.id, m.vm_id)
                attachment_content = io.StringIO(m.current_template())
                jira.instance.add_attachment(issue=task,
                                             filename=filename,
                                             attachment=attachment_content)
                self.log.msg("Attached template for {} to task {}".format(
                    filename, task.key))
            jira.instance.transition_issue(
                task, app.config['JIRA_TRANSITION_TASK_WRITTEN'])
            self.log.msg("Transitioned task {} to written".format(task.key))
            jira.approver_instance.transition_issue(
                task, app.config['JIRA_TRANSITION_TASK_APPROVED'])
            self.log.msg("Approved task {}".format(task.key))
        jira.instance.transition_issue(
            crq, app.config['JIRA_TRANSITION_CRQ_PLANNED_CHANGE'])
        self.log.msg("Transitioned change request {} to approved".format(
            task.key))
        jira.approver_instance.transition_issue(
            crq, app.config['JIRA_TRANSITION_CRQ_APPROVED'])
        self.log.msg("Transitioned change request {} to approved".format(
            crq.key))
        self.log.msg("Task ID {}".format(self.task.id))
        db_ticket = PoolTicket(pool=pool,
                               action_id=PoolTicketActions.update.value,
                               ticket_key=crq.key,
                               task=Session.merge(self.task))
        Session.add(db_ticket)
        Session.commit()
    except Exception as e:
        Session.rollback()
        if crq is not None:
            jira.cancel_crq_and_tasks(
                crq, comment="failure creating change tickets")
        raise e
Exemple #3
0
def plan_expansion(self, pool, expansion_names):
    task = crq = None
    try:
        pool = Session.merge(pool)
        start, end = jira.next_immediate_window_dates()
        logging = jira.instance.issue('SVC-1020')
        crq = jira.instance.create_issue(
            project=app.config['JIRA_CRQ_PROJECT'],
            issuetype={'name': 'Change Request'},
            assignee={'name': app.config['JIRA_USERNAME']},
            summary='[TEST IMPLEMENT] {}'.format(self.task.name),
            description=self.task.description,
            customfield_14530=start,
            customfield_14531=end,
            customfield_19031={'value': 'Maintenance'},
            customfield_15152=[{
                'value': 'Global'
            }],
            customfield_19430={'value': 'No conflict with any restrictions'},
            customfield_14135={
                'value': 'IPG',
                'child': {
                    'value': 'IPG Big Data'
                }
            },
            customfield_17679="Pool expansion required")
        self.log.msg("Created change request: {}".format(crq.key))
        jira.instance.transition_issue(
            crq, app.config['JIRA_TRANSITION_CRQ_PLANNING'])
        self.log.msg("Transitioned {} to planning".format(crq.key))
        jira.instance.create_issue_link('Relate', crq, logging)
        self.log.msg("Related {} to LOGGING service {}".format(
            crq.key, logging.key))
        task = jira.instance.create_issue(
            issuetype={'name': 'MOP Task'},
            assignee={'name': app.config['JIRA_USERNAME']},
            project=app.config['JIRA_CRQ_PROJECT'],
            description=
            "Instanitate the attached templates in the zone associated "
            "to the pool identified in the filename <pool_id>.<hostname>",
            summary='[TEST IMPLEMENTATION TASK] {}'.format(self.task.name),
            parent={'key': crq.key},
            customfield_14135={
                'value': 'IPG',
                'child': {
                    'value': 'IPG Big Data'
                }
            },
            customfield_15150={'value': 'No'})
        self.log.msg("Created task: {}".format(task.key))
        jira.instance.transition_issue(
            task, app.config['JIRA_TRANSITION_TASK_PLANNING'])
        self.log.msg("Transitioned {} to planning".format(task.key))
        env = Environment(loader=ObjectLoader())
        for hostname in expansion_names:
            vars = VarParser.parse_kv_strings_to_dict(
                pool.cluster.zone.vars, pool.cluster.vars, pool.vars,
                'hostname={}'.format(hostname))
            vm_template = env.from_string(pool.template).render(pool=pool,
                                                                vars=vars)
            attachment_content = io.StringIO(vm_template)
            jira.instance.add_attachment(issue=task,
                                         filename='{}.{}.template'.format(
                                             pool.id, hostname),
                                         attachment=attachment_content)
            self.log.msg("Attached template for {} to task {}".format(
                hostname, task.key))
        jira.instance.transition_issue(
            task, app.config['JIRA_TRANSITION_TASK_WRITTEN'])
        self.log.msg("Transitioned task {} to written".format(task.key))
        jira.approver_instance.transition_issue(
            task, app.config['JIRA_TRANSITION_TASK_APPROVED'])
        self.log.msg("Approved task {}".format(task.key))
        jira.instance.transition_issue(
            crq, app.config['JIRA_TRANSITION_CRQ_PLANNED_CHANGE'])
        self.log.msg("Transitioned task {} to approved".format(task.key))
        jira.approver_instance.transition_issue(
            crq, app.config['JIRA_TRANSITION_CRQ_APPROVED'])
        self.log.msg("Transitioned change request {} to approved".format(
            crq.key))
        self.log.msg("Task ID {}".format(self.task.id))
        db_ticket = PoolTicket(pool=Session.merge(pool),
                               action_id=PoolTicketActions.expand.value,
                               ticket_key=crq.key,
                               task=Session.merge(self.task))
        Session.add(db_ticket)
        Session.commit()
    except Exception as e:
        Session.rollback()
        if crq is not None:
            jira.cancel_crq_and_tasks(
                crq, comment="failure creating change tickets")
        raise e
Exemple #4
0
def assign_to_pool(zone_number, cluster_id):
    vms = []
    id_to_vm = {}
    selected_vm_ids = {}
    pools = None
    zone = None
    cluster = None
    memberships = {}
    try:
        Session()
        zone = Zone.query.get(zone_number)
        cluster = Cluster.query.filter_by(zone=zone, id=cluster_id).first()
        one_proxy = OneProxy(zone.xmlrpc_uri,
                             zone.session_string,
                             verify_certs=False)
        for membership in PoolMembership.query.join(
                VirtualMachinePool).filter_by(cluster=cluster).all():
            memberships[membership.vm_id] = membership
        for vm in one_proxy.get_vms():
            if vm.disk_cluster.id == cluster.id:
                vms.append(vm)
                id_to_vm[vm.id] = vm
        pools = VirtualMachinePool.get_all(cluster)
    except Exception as e:
        # raise e
        flash("Error fetching VMs in zone number {}: {}".format(
            zone.number, e),
              category='danger')
    form = ActionForm()
    active_tab = 'create_new_pool'
    # Form submission handling begins
    if form.validate_on_submit():
        # Determine which tab needs to be active based on the action
        if request.form['action'] is not None:
            print('something')
            active_tab = {
                'create new pool': 'create_new_pool',
                'add to pool': 'add_to_existing_pool'
            }[request.form['action']]
        # Get a list of clusters of all selected VMs--pools cannot span clusters
        selected_clusters = {}
        for id in request.form.getlist('chk_vm_id'):
            selected_vm_ids[int(id)] = id
            selected_clusters[id_to_vm[int(id)].disk_cluster.id] = True
        # Error checking begins
        proceed = True
        if len(selected_vm_ids) == 0:
            flash("No virtual machines were selected!", category='danger')
            proceed = False
        elif len(selected_clusters) != 1:
            flash("Selected VMs must all be in the same cluster",
                  category='danger')
            proceed = False
        # Handle the appropriate action if able to proceed
        if proceed and request.form['action'] == 'add to pool':
            if (request.form['pool_id']
                ) is None or request.form['pool_id'] == '':
                flash('No pool selected', category='danger')
            else:
                pool = VirtualMachinePool.query.get(request.form['pool_id'])
                for vm_id in selected_vm_ids.keys():
                    Session.add(
                        PoolMembership(pool=pool,
                                       vm_name=id_to_vm[vm_id].name,
                                       vm_id=vm_id,
                                       date_added=datetime.utcnow()))
                    Session.commit()
                flash(Markup(
                    'Successfully added {} members to pool <a href="{}">{}</a>'
                    .format(
                        len(selected_vm_ids),
                        url_for('vpool_bp.view', pool_id=pool.id),
                        pool.name,
                    )),
                      category='success')
                return redirect(
                    url_for('vpool_bp.assign_to_pool',
                            zone_number=zone.number,
                            cluster_id=cluster.id))
        if proceed and request.form['action'] == 'create new pool':
            try:
                if request.form['new_pool_name'] is None or request.form[
                        'new_pool_name'] == '':
                    raise Exception('Pool name cannot be blank')
                pool = VirtualMachinePool(name=request.form['new_pool_name'],
                                          cluster=cluster,
                                          zone_number=zone.number,
                                          cardinality=len(selected_vm_ids))
                Session.add(pool)
                Session.flush()
                for vm_id in selected_vm_ids.keys():
                    membership = PoolMembership(pool=pool,
                                                vm_name=id_to_vm[vm_id].name,
                                                vm_id=vm_id,
                                                date_added=datetime.utcnow())
                    memberships[vm_id] = membership
                    Session.add(membership)
                Session.flush()
                Session.commit()
                flash(Markup(
                    'Successfully created <a href="{}">{}</a> with {} pool members'
                    .format(url_for('vpool_bp.view', pool_id=pool.id),
                            pool.name, len(selected_vm_ids))),
                      category='success')
            except Exception as e:
                Session.rollback()
                flash('Error creating your new pool: {}'.format(e),
                      category='danger')
    return render_template('vpool/assign_to_pool.html',
                           form=form,
                           zone=zone,
                           cluster=cluster,
                           vms=vms,
                           memberships=memberships,
                           selected_vm_ids=selected_vm_ids,
                           pools=pools,
                           active_tab_name=active_tab)