CMDB项目中遇到的问题

客户端


类的调用

class Response(object):
    def __init__(self):
        self.status = True
        self.msg = None
        self.data = None

    @property
    def dict(self):
        return self.__dict__


response = Response()




class Disk(object):
    def __init__(self):
        self.response = response

    @property
    def info(self):
        self.response.status = 100
        self.response.msg = '魏新雨咋软'
        self.response.data = {'1':{'capatablities': '100GB', 'model': 'hp2344'}}

        return self.response.dict



class Memory(object):
    def __init__(self):
        self.response = response

    @property
    def info(self):
        self.response.status = 100
        self.response.msg = '陈骏啊, 萨宁啊'
        self.response.data = {'#DISM1':{'capatablities': '8GB', 'model': 'kingstong222'}}
        return self.response.dict


disk = Disk().info
memory = Memory().info


print(disk)  # {'status': 100, 'msg': '陈骏啊, 萨宁啊', 'data': {'#DISM1': {'capatablities': '8GB', 'model': 'kingstong222'}}}
print(memory)  # {'status': 100, 'msg': '陈骏啊, 萨宁啊', 'data': {'#DISM1': {'capatablities': '8GB', 'model': 'kingstong222'}}}

最后2者的输出结果是一样的, 因为无论是Disk对象还是Memory对象, 他们的属性self.response 指向的都是response这个对象, 所以最后的值是由最后一次赋值的结果


TypeError: Object of type 'Response' is not JSON serializable


原因: 返回的对象无法用json进行实例化(json.dumps(ret)), 最后返回的是个对象, 而不是字典


lib.response.py

class Response(object):
    def __init__(self):
        self.status = None
        self.msg = None
        self.data = None

    @property
    def dict(self):
        return self.__dict__

src.plugins.disk.py

from .base import BasePlugin
import os
import traceback
from lib.response import Response



class Disk(BasePlugin):
    def __init__(self, handler):
        super().__init__(handler)
        self.disk_path = os.path.join(self.filepath, 'disk.out')
        # self.response = response_obj
        self.error = traceback.format_exc()
        self.response = Response()

    def Windows(self):
        return 'windows'

    def Linux(self, handler):
        # print('disk', response)
        if not self.debug:
            data = handler.cmd('sudo MegaCli -PDList -aALL')
        else:
            try:
                data = open(self.disk_path, 'r', encoding='utf-8').read().split('Enclosure Device ID: 32')[1:]
                disk_dict = self.LinuxParse(data)

                self.response.status = 1000
                self.response.msg = '采集磁盘成功'
                self.response.data = disk_dict

            except Exception:
                self.response.status = 4000
                self.response.msg = self.error

        return  self.response


    def LinuxParse(self, data):
        key_map = {
            'PD Type': 'iface',
            'Slot Number': 'slot',
            'Inquiry Data': 'model',
            'Raw Size': 'capacity',
        }
        disk_dict = {}
        for item in data:
            res = item.strip().split('\n')
            info = {}
            for row in res:
                if len(row.strip().split(':')) == 2:
                    key, value = row.strip().split(':')
                    if key in key_map:
                        info[key_map[key]] = value.strip()

            disk_dict[info['slot']] = info

            return disk_dict

报错信息的处理

from .base import BasePlugin
import os
import traceback
from lib.response import Response




class Disk(BasePlugin):
    def __init__(self, handler):
        super().__init__(handler)
        self.disk_path = os.path.join(self.filepath, 'disk.out')
        self.response = Response()
        self.error = traceback.format_exc()

    def Windows(self):
        return 'windows'

    def Linux(self, handler):
        # print('disk', response)
        if not self.debug:
            data = handler.cmd('sudo MegaCli -PDList -aALL')
        else:
            try:
                data = open(self.disk_path, 'r', encoding='utf-8').read().split('Enclosure Device ID: 32')[1:]
                disk_dict = self.LinuxParse(data)

                self.response.status = 1000
                self.response.msg = '采集磁盘成功'
                self.response.data = disk_dict

            except Exception:
                self.response.status = 4000
                self.response.msg = self.error
                self.logger.error(self.error)

        return  self.response.dict


    def LinuxParse(self, data):
        key_map = {
            'PD Type': 'iface',
            'Slot Number': 'slot',
            'Inquiry Data': 'model',
            'Raw Size': 'capacity',
        }
        disk_dict = {}
        for item in data:
            res = item.strip().split('\n')
            info = {}
            for row in res:
                if len(row.strip().split(':')) == 2:
                    key, value = row.strip().split(':')
                    if key in key_map:
                        info[key_map[key]] = value.strip()

            disk_dict[info['slot']] = info

            return disk_dict

问题

在初始化方法中定义了 self.error = traceback.format_exc(), 这就导致了无论出现什么样的异常, 最后的报错信息都是NoneType: None

所以正确的逻辑是在出现异常的时候进行补货

from .base import BasePlugin
import os
import traceback
from lib.response import Response

class Disk(BasePlugin):
    def __init__(self, handler):
        super().__init__(handler)
        self.disk_path = os.path.join(self.filepath, 'disk.out')
        self.response = Response()

    def Windows(self):
        return 'windows'

    def Linux(self, handler):
        # print('disk', response)
        if not self.debug:
            data = handler.cmd('sudo MegaCli -PDList -aALL')
        else:
            try:
                data = open(self.disk_path, 'r', encoding='utf-8').read().split('Enclosure Device ID: 32')[1:]
                disk_dict = self.LinuxParse(data)

                self.response.status = 1000
                self.response.msg = '采集磁盘成功'
                self.response.data = disk_dict

            except Exception:
                error_msg = traceback.format_exc()
                self.response.status = 4000
                self.response.msg = error_msg
                self.logger.error(error_msg)

        return  self.response.dict


    def LinuxParse(self, data):
        key_map = {
            'PD Type': 'iface',
            'Slot Number': 'slot',
            'Inquiry Data': 'model',
            'Raw Size': 'capacity',
        }
        disk_dict = {}
        for item in data:
            res = item.strip().split('\n')
            info = {}
            for row in res:
                if len(row.strip().split(':')) == 2:
                    key, value = row.strip().split(':')
                    if key in key_map:
                        info[key_map[key]] = value.strip()

            disk_dict[info['slot']] = info

            return disk_dict

API


TypeError: init() missing 1 required positional argument: 'app_module'



原因: 将app注册到MIDDLEWARE的列表中


posted @ 2019-11-13 00:39  cjw1219  阅读(492)  评论(0编辑  收藏  举报