Exemplo n.º 1
0
 def connDb(self):
     '''
     连接数据库
     '''
     try:
         self.dbObj = ClassDb()
         self.dbObj.connect(host=dbHost,port=dbPort,user=dbUser,passwd=dbPass,db=dbName,charset="utf8")
     finally:
         pass
Exemplo n.º 2
0
class RunCmd():
    '''
    定义 执行命令行 类, 传入一个队列对象
    '''
    def __init__(self, iq):
        self.sqlRes = iq
        self.sOption = " -i /root/.ssh/id_rsa -o StrictHostKeyChecking=no -o ConnectTimeout=30 "

    def connDb(self):
        '''
        连接数据库
        '''
        try:
            self.dbObj = ClassDb()
            self.dbObj.connect(host=dbHost,port=dbPort,user=dbUser,passwd=dbPass,db=dbName,charset="utf8")
        finally:
            pass

    def upStatus(self, id, status):
        '''
        更新已执行状态,需要传入2个参数
        1: 数据库记录编号
        2: 需要更新的状态值
        '''
        try:
            ## 更新状态SQL
            sql = "update dbtx_cmd_execute set iStatus=%s,dExecuteTime = now() where iId=%s" % (str(status), str(id))
            self.dbObj.execute(sql)
        finally:
            pass

    def upReturnContents(self, id, status, returnContens):
        '''
        更新命令执行的状态,需要传入3个参数
        1: 数据库记录编号
        2: 状态
        3: 执行命令的返回值
        '''
        try:
            ## 更新数据库SQL
            sql = "update dbtx_cmd_execute set iStatus=%s,sReturnContents='%s',dExecutedTime=now() where iId = %s" % (str(status), addslashes(str(returnContens)),str(id))
            self.dbObj.execute(sql)
        finally:
            pass

    def getDependPidStatus(self, dependID):
        ## 获取依赖任务的执行状态
        if not dependID:   ## 如果dependID为空, 表示没有依赖任务, 命令可直接运行, 返回True
            return True
        try:
            ## 查询依赖任务状态的SQL
            sql = "select iStatus from dbtx_cmd_execute where iId = %s" % str(self.dependID)
            self.dbObj.execute(sql)
            result = self.dbObj.fetchall()
            iStatus = result[0]['iStatus']
            if iStatus == 3:    ## 状态为3, 表示依赖任务已完成, 返回True
                return True
            elif iStatus == '':
                return True
            elif iStatus is None:
                return True
            else:
                return False
        finally:
            pass

    def doWork(self):
        '''
        传入一个SQL语句队列对象
        参数说明
        self.id: 数据库记录编号,用于回填执行结果
        self.cmd: 命令
        self.type: 命令类型
        self.ip: 需要执行该命令的IP地址
        self.dependID: 依赖的PID, 即需要等该PID执行完以后才开始运行
        '''
        self.id = self.sqlRes['iId']
        self.cmd = str(self.sqlRes['sCmd'])
        self.type = self.sqlRes['eType']
        self.dependID = self.sqlRes['iDependID']
        self.ip = self.sqlRes['sIP']
        self.sshPort = self.sqlRes['sSSHport']

        self.connDb()     ## 连接数据库
        
        if self.dependID:
            if not self.getDependPidStatus(self.dependID):
                return
        ## 执行待执行的命令
        ## 定义ssh连接参数
        ## 按类型执行命令
        if self.type == 'local':
            ## 即为 本地命令,在中央服本地运行
            fullCmd = self.cmd
        elif self.type == 'remote':
            ## 即为 远程命令
            fullCmd = 'ssh -p%s %s root@%s "%s"' % (self.sshPort,self.sOption,self.ip,self.cmd)
        elif self.type == 'scp':
            ## SCP推送文件/目录
            tmpCmd = self.cmd.split()
            srcFile = tmpCmd[0]
            dstFile = tmpCmd[1]
            fullCmd = 'scp -r -P%s %s%s root@%s:%s' % (self.sshPort,self.sOption,srcFile,self.ip,dstFile)
        elif self.type == 'scp_back':
            ## 从远程服务器拉取文件/目录
            tmpCmd = self.cmd.split()
            srcFile = tmpCmd[0]
            dstFile = tmpCmd[1]
            fullCmd = 'scp -r -P%s %s root@%s:%s %s' % (self.sshPort,self.sOption,self.ip,srcFile,dstFile)
        elif self.type == 'rsync':
            ## rsync推送文件/目录到远程服务器
            tmpCmd = self.cmd.split()
            srcFile = tmpCmd[0]
            dstFile = tmpCmd[1]
            fullCmd = 'rsync -az -e "ssh -p%s %s" %s root@%s:%s' % (self.sshPort,self.sOption,srcFile,self.ip,dstFile)
        else:
            ## 否则为不支持的命令类型
            saveLog("你输入的命令:%s 不在本机支持的命令类型范围内,请重新输入." % (fullCmd))
            print "你输入的命令:%s 不在本机支持的命令类型范围内,请重新输入." % (fullCmd)
            return

        ## 开始执行命令
        saveLog("%s 开始执行." % fullCmd)
        self.upStatus(self.id, 2)      ## 状态置为2, 即正在运行...

        try:
            ssh_master(self.ip)
        except Exception, err:
            saveLog("创建 ssh socket 失败: %s" % str(err))

        try:
            p = subprocess.Popen(fullCmd,shell=True,stdout=subprocess.PIPE,stderr=subprocess.PIPE)
            out, errInfo = p.communicate()    ## 返回一个元组,元组第一个元素为标准输出,第二个元素为标准错误输出
            if p.returncode != 0:     ## 如果stderr不为空,表示命令运行有误,状态置为4
                stat = 4
            else:
                stat = 3       ## 运行成功,状态置为3
        except Exception, err:
            saveLog("执行命令,等待命令返回值发生未知错误. %s --- %s" % (str(err), type(self.cmd)))