Example #1
0
def create_asset_diffs(changeplan, target):
    changed_assets = Asset.objects.filter(version=changeplan).order_by('id')
    for changed_asset in changed_assets:
        try:
            live_asset = versioned_object(changed_asset, target, Asset.IDENTITY_FIELDS)
            if live_asset is None:
                live_asset = versioned_object(changed_asset, target, ['hostname'])
            AssetDiff.objects.create(
                changeplan=changeplan,
                live_asset=live_asset,
                changed_asset=changed_asset,
            )
        except Asset.DoesNotExist:
            AssetDiff.objects.create(
                changeplan=changeplan,
                changed_asset=changed_asset,
            )
    for child in changeplan.changeplan_set.all():
        asset = Asset.objects.filter(commissioned=None, version=child).first()
        if asset:
            old = newest_object(Asset, changeplan, asset_number=asset.asset_number, hostname=asset.hostname)
            AssetDiff.objects.create(
                changeplan=changeplan,
                live_asset=old,
                changed_asset=asset
            )
Example #2
0
def execute_networkports(changeplan):
    changed_networkports = NetworkPort.objects.filter(version=changeplan)
    for changed_networkport in changed_networkports:
        try:
            live = ChangePlan.objects.get(id=0)
            live_networkport = versioned_object(changed_networkport, live, NetworkPort.IDENTITY_FIELDS)

            if live_networkport is None:
                live_asset = add_asset(changed_networkport.asset, live)
                NetworkPort.objects.create(
                    asset=live_asset,
                    label=changed_networkport.label,
                    mac_address=changed_networkport.mac_address,
                    connection=add_network_conn(changed_networkport.connection, live),
                    version=live
                )
            else:
                live_networkport.label = changed_networkport.label
                live_networkport.mac_address = changed_networkport.mac_address
                if changed_networkport.connection:
                    live_networkport.connection = add_network_conn(changed_networkport.connection, live)
                else:
                    live_networkport.connection = None
                live_networkport.save()

        except Exception as e:
            pass
Example #3
0
def execute_assets(changeplan):
    changed_assets = Asset.objects.filter(version=changeplan).order_by('itmodel__type')
    for changed_asset in changed_assets:
        try:
            live = ChangePlan.objects.get(id=0)
            live_asset = versioned_object(changed_asset, live, Asset.IDENTITY_FIELDS)
            if live_asset is None:
                live_asset = versioned_object(changed_asset, live, ['hostname'])

            if live_asset is None:
                Asset.objects.create(
                    version=live,
                    hostname=changed_asset.hostname,
                    site=changed_asset.site,
                    rack=add_rack(changed_asset.rack, live) if not changed_asset.site.offline else None,
                    rack_position=changed_asset.rack_position if not changed_asset.site.offline and changed_asset.itmodel.type != ITModel.Type.BLADE else None,
                    itmodel=changed_asset.itmodel,
                    owner=changed_asset.owner,
                    comment=changed_asset.comment,
                    display_color=changed_asset.display_color if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None,
                    cpu=changed_asset.cpu if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None,
                    memory=changed_asset.memory if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None,
                    storage=changed_asset.storage if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None,
                    blade_chassis=add_asset(changed_asset.blade_chassis, live, Asset.IDENTITY_FIELDS)\
                    if changed_asset.itmodel.type == ITModel.Type.BLADE or changed_asset.itmodel.type == ITModel.Type.CHASSIS else None,
                    slot=changed_asset.slot if changed_asset.itmodel.type == ITModel.Type.CHASSIS else None
                )

            else:
                live_asset.asset_number = changed_asset.asset_number
                live_asset.hostname = changed_asset.hostname
                live_asset.site = changed_asset.site
                live_asset.rack = add_rack(changed_asset.rack, live) if not changed_asset.site.offline else None
                live_asset.rack_position = changed_asset.rack_position if not changed_asset.site.offline and changed_asset.itmodel.type != ITModel.Type.BLADE else None
                live_asset.itmodel = changed_asset.itmodel
                live_asset.owner = changed_asset.owner
                live_asset.comment = changed_asset.comment
                live_asset.display_color = changed_asset.display_color if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None
                live_asset.cpu = changed_asset.cpu if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None
                live_asset.memory = changed_asset.memory if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None
                live_asset.storage = changed_asset.storage if changed_asset.itmodel.type != ITModel.Type.CHASSIS else None
                live_asset.blade_chassis = add_asset(changed_asset.blade_chassis, live, Asset.IDENTITY_FIELDS)\
                    if changed_asset.itmodel.type == ITModel.Type.BLADE else None
                live_asset.slot = changed_asset.slot if changed_asset.itmodel.type == ITModel.Type.BLADE else None
                live_asset.save()
        except Exception as e:
            pass
Example #4
0
def create_asset_extra(asset, version, power_connections, net_ports):
    # Other objects
    if power_connections:
        order = 1
        for connection in power_connections:
            if order > asset.itmodel.power_ports:
                break
            if isinstance(connection['pdu_id'], int):
                connection['pdu_id'] = PDU.objects.get(id=connection['pdu_id'])
            new_pdu = versioned_object(connection['pdu_id'], version, PDU.IDENTITY_FIELDS)
            if new_pdu is None:
                add_rack(connection['pdu_id'].rack, version)
            Powered.objects.create(
                pdu=versioned_object(connection['pdu_id'], version, PDU.IDENTITY_FIELDS),
                plug_number=connection['plug'],
                version=version,
                asset=asset,
                order=order
            )
            order += 1

    if net_ports:
        i = 1
        for port in net_ports:
            if i > asset.itmodel.network_ports:
                break
            mac = port.get('mac_address')
            if mac and len(mac) == 0:
                mac = None

            if version.id != 0:
                if port['connection'] is not None:
                    versioned_conn = add_network_conn(port['connection'], version)
                    port['connection'] = versioned_conn

            NetworkPort.objects.create(
                asset=asset,
                label=NetworkPortLabel.objects.get(
                    itmodel=asset.itmodel,
                    name=port['label']
                ),
                mac_address=mac,
                connection=add_network_conn(port.get('connection'), version),
                version=version,
            )
            i += 1
Example #5
0
def execute_powereds(changeplan):
    changed_powereds = Powered.objects.filter(version=changeplan)
    for changed_powered in changed_powereds:
        try:
            live = ChangePlan.objects.get(id=0)
            live_powered = versioned_object(changed_powered, live, Powered.IDENTITY_FIELDS)

            live_powered.plug_number = changed_powered.plug_number
            live_powered.pdu = versioned_object(changed_powered.pdu, live, PDU.IDENTITY_FIELDS)
            new_asset = versioned_object(changed_powered.asset, live, Asset.IDENTITY_FIELDS)
            if new_asset is None:
                new_asset = versioned_object(changed_powered.asset, live, ['hostname'])
            live_powered.asset = new_asset
            live_powered.on = changed_powered.on
            live_powered.order = changed_powered.order
            live_powered.save()

        except:
            pass
Example #6
0
def create_powered_diffs(changeplan, target):
    for asset in Asset.objects.filter(version=changeplan).order_by('id'):
        live_asset = versioned_object(asset, target, Asset.IDENTITY_FIELDS)
        new_plugs = asset.powered_set.all()
        if live_asset:
            live_plugs = live_asset.powered_set.all()
            for plug in live_plugs:
                if versioned_object(plug, changeplan, Powered.IDENTITY_FIELDS) not in new_plugs:
                    PoweredDiff.objects.create(
                        changeplan=changeplan,
                        live_powered=plug,
                        changed_powered=None
                    )
        for plug in new_plugs:
            live_plug = versioned_object(plug, target, Powered.IDENTITY_FIELDS)
            PoweredDiff.objects.create(
                changeplan=changeplan,
                changed_powered=plug,
                live_powered=live_plug
            )
Example #7
0
def create_networkport_diffs(changeplan, target):
    for asset in Asset.objects.filter(version=changeplan).order_by('id'):
        live_asset = versioned_object(asset, target, ['hostname'])
        new_ports = asset.networkport_set.all()
        id_fields = ['asset__hostname', 'label__name']
        if live_asset:
            live_ports = live_asset.networkport_set.all()
            for port in live_ports:
                if versioned_object(port, changeplan, id_fields) not in new_ports:
                    NetworkPortDiff.objects.create(
                        changeplan=changeplan,
                        live_networkport=port,
                        changed_networkport=None
                    )
        for port in new_ports:
            live_port = versioned_object(port, target, id_fields)
            NetworkPortDiff.objects.create(
                changeplan=changeplan,
                changed_networkport=port,
                live_networkport=live_port
            )
Example #8
0
 def dehydrate_power_port_connection_2(self, asset):
     try:
         if asset.itmodel.power_ports >= 2:
             my_powered = Powered.objects.filter(asset=asset,
                                                 order=2).first()
             if self.version.id != 0 and my_powered is None:
                 my_powered = Powered.objects.filter(asset=versioned_object(
                     asset, ChangePlan.objects.get(id=0),
                     Asset.IDENTITY_FIELDS),
                                                     order=2).first()
             if my_powered:
                 return str(my_powered.pdu.position) + str(
                     my_powered.plug_number)
             else:
                 return ''
     except:
         return ''
Example #9
0
    def post(self, request, pk):
        try:
            # Get ChangePlan
            changeplan = ChangePlan.objects.get(id=pk)
            live = ChangePlan.objects.get(id=0)
            children = changeplan.changeplan_set.all()
            # Record diff for future reference
            create_asset_diffs(changeplan, live)
            create_powered_diffs(changeplan, live)
            create_networkport_diffs(changeplan, live)
            # Update Objects
            execute_assets(changeplan)
            execute_networkports(changeplan)
            execute_powereds(changeplan)
            changeplan.executed = True
            changeplan.executed_at = now()
            changeplan.save()
            for child in children:
                asset = Asset.objects.get(version=child,
                                          commissioned__isnull=True)
                live_asset = versioned_object(asset,
                                              ChangePlan.objects.get(id=0),
                                              Asset.IDENTITY_FIELDS)
                if live_asset:
                    decommission_asset(live_asset.id, DecommissionAsset(),
                                       request.user, live)
                    print('DECOMMISSIONED')

                for model in (Powered, NetworkPort, Asset, PDU, Rack):
                    if model == Asset:
                        model.objects.filter(
                            version=child,
                            itmodel__type=ITModel.Type.BLADE).delete()
                    model.objects.filter(version=child).delete()

                child.delete()
            return Response(ChangePlanDetailSerializer(changeplan).data,
                            status=HTTP_200_OK)
        except Exception as e:
            raise serializers.ValidationError("This ChangePlan is not valid.")
Example #10
0
 def after_save_instance(self, instance, using_transactions, dry_run):
     if self.version.parent:
         asset = versioned_object(instance.asset, self.version.parent,
                                  ['hostname'])
         for port in asset.networkport_set.all():
             add_network_conn(port, self.version)
Example #11
0
    def update(self, request, *args,
               **kwargs):  # todo the logic in this looks fishy..
        # Do you need to update data's id or is that done already? what about version?
        # Does the new asset get added to the new version? What about its network ports?
        # Make sure that network ports are not deleted in the offline case but connections are wiped
        version = ChangePlan.objects.get(id=get_version(request))
        asset = self.get_object()
        asset_ver = asset.version
        request.data['power_connections'] = request.data.get(
            'power_connections', [])
        request.data['network_ports'] = request.data.get('network_ports', [])
        request.data['power_connections'] = [
            entry for entry in request.data['power_connections'] if entry
        ]

        site = Site.objects.get(id=request.data['location']['site'])
        check_asset_perm(request.user.username, site.abbr)
        check_asset_perm(request.user.username, asset.site.abbr)

        if version != asset_ver:
            data = request.data
            if not site.offline:
                rack = versioned_object(asset.rack, version,
                                        Rack.IDENTITY_FIELDS)
                if not rack:
                    rack = add_rack(asset.rack, version)
                old_pdus = {
                    port['id']: port['position']
                    for port in asset.rack.pdu_set.order_by('position').values(
                        'id', 'position')
                }
                new_pdus = {
                    port['position']: port['id']
                    for port in rack.pdu_set.order_by('position').values(
                        'id', 'position')
                }
                data['location']['rack'] = rack.id
                for i, port in enumerate(request.data['power_connections']):
                    data['power_connections'][i]['pdu_id'] = new_pdus[old_pdus[
                        int(port['pdu_id'])]]

                for i, port in enumerate(request.data['network_ports']):
                    if port['connection'] is not None:
                        versioned_conn = add_network_conn(
                            NetworkPort.objects.get(id=port['connection']),
                            version)
                        data['network_ports'][i][
                            'connection'] = versioned_conn.id
            else:
                request.data['power_connections'] = []

            if request.data['location']['tag'] == 'chassis-mount':
                chassis = Asset.objects.get(
                    id=request.data['location']['asset'])
                request.data['location']['asset'] = add_asset(
                    chassis, version, Asset.IDENTITY_FIELDS).id
                pass

            serializer = AssetSerializer(data=data,
                                         context={
                                             'request': request,
                                             'version': version.id
                                         })
            serializer.is_valid(raise_exception=True)
            serializer.save()
            return Response(data=serializer.data, status=HTTP_200_OK)

        else:
            return super(AssetUpdate, self).update(request, *args, **kwargs)
Example #12
0
def assetdiff_message(sender, instance, *args, **kwargs):
    messages = []
    conflicts = []
    if instance.live_asset:
        if instance.changed_asset.asset_number != instance.live_asset.asset_number:
            messages.append('OLD ASSET NUMBER: ' +
                            str(instance.live_asset.asset_number) + ' | ' +
                            'NEW ASSET NUMBER: ' +
                            str(instance.changed_asset.asset_number))
        if instance.changed_asset.hostname != instance.live_asset.hostname:
            messages.append('OLD HOSTNAME: ' +
                            str(instance.live_asset.hostname) + ' | ' +
                            'NEW HOSTNAME: ' +
                            str(instance.changed_asset.hostname))

        if instance.changed_asset.site != instance.live_asset.site:
            messages.append('OLD SITE: ' + instance.live_asset.site.name +
                            ' | ' + 'NEW SITE: ' +
                            instance.changed_asset.site.name)

        if instance.live_asset.commissioned == Asset.Decommissioned.COMMISSIONED \
                and instance.changed_asset.commissioned is None:
            messages.append('DECOMMISSION ASSET' +
                            (': ' + instance.live_asset.hostname) if instance.
                            live_asset.hostname else '')

        if not instance.changed_asset.site.offline:
            if not instance.live_asset.site.offline:
                if not versioned_equal(instance.changed_asset.rack,
                                       instance.live_asset.rack,
                                       Rack.IDENTITY_FIELDS):
                    messages.append(
                        'OLD RACK: ' + str(instance.live_asset.rack.rack) +
                        ' | '
                        +  # todo test if new rack create in change plan breaks this
                        'NEW RACK: ' + str(instance.changed_asset.rack.rack))
            else:
                messages.append('NEW RACK: ' +
                                str(instance.changed_asset.rack.rack))

        if not instance.changed_asset.site.offline and instance.changed_asset.itmodel.type != 'blade':
            if not instance.live_asset.site.offline and instance.live_asset.itmodel.type != 'blade':
                if instance.changed_asset.rack_position != instance.live_asset.rack_position:
                    messages.append('OLD RACK POSITION: ' +
                                    str(instance.live_asset.rack_position) +
                                    ' | ' + 'NEW RACK POSITION: ' +
                                    str(instance.changed_asset.rack_position))
            else:
                messages.append('NEW RACK POSITION: ' +
                                str(instance.changed_asset.rack_position))

        if instance.changed_asset.itmodel != instance.live_asset.itmodel:
            messages.append('OLD ITMODEL: ' +
                            str(instance.live_asset.itmodel) + ' | ' +
                            'NEW ITMODEL: ' +
                            str(instance.changed_asset.itmodel))
        if instance.changed_asset.owner != instance.live_asset.owner:
            messages.append(('OLD OWNER: ' +
                             ((str(instance.live_asset.owner.username)
                               ) if instance.live_asset.owner else 'None')) +
                            ' | ' +
                            ('NEW OWNER: ' +
                             (str(instance.changed_asset.owner.username)
                              if instance.changed_asset.owner else 'None')))

        # display_color, cpu, memory, storage
        def get_upgrades(attr):
            if getattr(instance.live_asset, attr) is not None:
                old_val = getattr(instance.live_asset, attr)
            else:
                old_val = getattr(instance.live_asset.itmodel, attr)
            if getattr(instance.changed_asset, attr) is not None:
                new_val = getattr(instance.changed_asset, attr)
            else:
                new_val = getattr(instance.changed_asset.itmodel, attr)

            return old_val, new_val

        old_display_color, new_display_color = get_upgrades('display_color')
        if old_display_color != new_display_color:
            messages.append('OLD DISPLAY COLOR: ' + str(old_display_color) +
                            ' | ' + 'NEW DISPLAY COLOR: ' +
                            str(new_display_color))
        old_cpu, new_cpu = get_upgrades('cpu')
        if old_cpu != new_cpu:
            messages.append('OLD CPU: ' + (str(old_cpu) or 'None') + ' | ' +
                            'NEW CPU: ' + (str(new_cpu) or 'None'))
        old_storage, new_storage = get_upgrades('storage')
        if old_storage != new_storage:
            messages.append('OLD STORAGE: ' + (str(old_storage) or 'None') +
                            ' | ' + 'NEW STORAGE: ' +
                            (str(new_storage) or 'None'))
        old_memory, new_memory = get_upgrades('memory')
        if old_memory != new_memory:
            messages.append('OLD MEMORY: ' + str(old_memory) + ' | ' +
                            'NEW MEMORY: ' + str(new_memory))

        if instance.live_asset.commissioned is None and instance.changed_asset.commissioned is not None:
            conflicts.append({
                "field": "decommissioned",
                "message": 'Live asset is decommissioned.'
            })

        # blade_chassis
        if instance.changed_asset.itmodel.type == 'blade':
            if not versioned_equal(instance.changed_asset.blade_chassis,
                                   instance.live_asset.blade_chassis,
                                   Asset.IDENTITY_FIELDS):
                messages.append('OLD BLADE CHASSIS: ' +
                                str(instance.live_asset.blade_chassis) +
                                ' | ' + 'NEW BLADE CHASSIS: ' +
                                str(instance.changed_asset.blade_chassis))
            # slot
            if instance.changed_asset.slot != instance.live_asset.slot:
                messages.append('OLD SLOT: ' + str(instance.live_asset.slot) +
                                ' | ' + 'NEW SLOT: ' +
                                str(instance.changed_asset.slot))

    else:
        changed = instance.changed_asset
        messages.append('CREATE ASSET: {} in {}{}'.format(
            str(changed) if str(changed) != '' and str(changed) != 'None' else
            str(changed.itmodel), changed.site.name + ' ' + changed.rack.rack
            if changed.rack is not None else changed.site.name,
            'U' + str(changed.rack_position)
            if changed.rack_position is not None else ''))

    asset = instance.changed_asset
    if asset.rack_position is not None and asset.commissioned == Asset.Decommissioned.COMMISSIONED:
        blocked = Asset.objects.filter(
            rack=asset.rack,
            rack_position__range=(asset.rack_position, asset.rack_position +
                                  asset.itmodel.height - 1),
            site=asset.site,
            version_id=0)
        if len(blocked) > 0:
            conflicts.append({
                "field":
                "rack_position",
                "message":
                'There is already an asset in this area of the specified rack.'
            })
        i = asset.rack_position - 1
        while i > 0:
            live_rack = versioned_object(asset.rack,
                                         ChangePlan.objects.get(id=0),
                                         Rack.IDENTITY_FIELDS)
            under = Asset.objects.filter(rack=live_rack,
                                         rack_position=i,
                                         site=asset.site,
                                         version_id=0)
            if asset.asset_number is not None:
                under = under.exclude(asset_number=asset.asset_number)
            if len(under) > 0:
                other = under.values_list('rack_position',
                                          'itmodel__height')[0]
                if other[0] + other[1] > asset.rack_position:
                    conflicts.append({
                        "field":
                        "rack_position",
                        "message":
                        'There is already an asset in this area of the specified rack.'
                    })
            i -= 1
    instance.messages = messages
    instance.conflicts = conflicts