远程访问传感器获取数据并传入数据库----Three

上次实验已经成功连接数据库...

这次实验就是将数据传入数据库,因为数据库中存温湿度的 表是cdsjb,与其关联的表有cdb和bcxmb,所以需要对三个表都做处理才能正常传入数据。

程序如下:

 
 
#!/usr/bin/env python3
# -*- coding:utf-8 -*-
u'''
Created on 2018年5月22日

@author: RJ
'''
__author__ = 'RJ <[email protected]>'
__version__ = '1.0.0'
__company__ = u'重庆交大'
__updated__ = '2018-05-22 16:43'

import socket  
import codecs  
import time  
import pymysql
import datetime  
import struct    
      
"""  
client  
connect()  
recv()  
send()  
sendall()  
      
"""  

# 以字典形式创建数据库配置信息,方便修改  
PY_MYSQL_CONN_DICT = {                  
        "host": '10.1.161.209',
        "port": 3306,
        "user": 'bridge',
        "passwd": '123456',
        "db": 'bridge',
        "charset": 'utf8'  
    }    


class dbConnect:  

        def __init__(self):  
            self.conn = None  
            self.cursor = None  
            self.__conn_dict = PY_MYSQL_CONN_DICT  
      
        def connect(self, cursor=pymysql.cursors.DictCursor):  
            try:  
                self.conn = pymysql.connect(**self.__conn_dict)  
                self.cursor = self.conn.cursor(cursor=cursor)  # 数据库连接成功并返回游标  
                return self.cursor  
            except Exception as e:  
                print("连接失败:%s" % e)  
      
        def close(self):  
            self.conn.commit()  
            self.cursor.close()  
            self.conn.close()  


# crc16校验
def crc16(x):  
    u'''  
    @summary: 计算CRC16值  
    @param x: bytes  
    @return: 返回2字节值,类似:b'\x7B\x2A'。  
    '''  
    if not isinstance(x, bytes):  
        raise ValueError('Parameter must be a bytes type')  
    b = 0xA001  
    a = 0xFFFF  
    for byte in x:  
        a = a ^ byte  
        for _ in range(8):  
            last = a % 2  
            a = a >> 1  
            if last == 1:  
                a = a ^ b  
    aa = '0' * (6 - len(hex(a))) + hex(a)[2:]  
    ll, hh = int(aa[:2], 16), int(aa[2:], 16)  
    rtn = '%x' % (hh * 256 + ll & 0xffff)  
    while len(rtn) < 4:  
        rtn = '0' + rtn  
    rtn = hextobytes(rtn)  
    return rtn  


def hextobytes(x): 
    u'''
    16进制转字节流
    ''' 
    if not isinstance(x, str):  
        x = str(x, 'ascii')  
    return bytes.fromhex(x)  


def bytestohex(x): 
    u'''
    字节流转16进制
    ''' 
    if not isinstance(x, bytes):  
        x = bytes(x, 'ascii')  
    return ''.join(["%02x" % i for i in x]).strip() 


def fetchone():  
    conn = dbConnect()  
    cousor = conn.connect()  
    sql = """SELECT  gcxmbm cdbm, cdmc, cgqbm, jldw, sfqy, sjlx, sflb, lbfs, lbcs, bz FROM cdb WHERE 1 """  
    cousor.execute(sql)  
    result = cousor.fetchone()  # 获取第一一条数据并返回结果  
    conn.close()  
    return result  

  
def insertone(**kwargs):  
    conn = dbConnect()  
    cursor = conn.connect()  
    sql = """insert into cdb(%s) values(%s)"""  
    key_list = []  
    value_list = []  
    for k, v in kwargs.items():  
        key_list.append(k)  
        value_list.append('%%(%s)s' % k)  
    sql = sql % (','.join(key_list), ','.join(value_list))  
    cursor.execute(sql, kwargs)  
    conn.close()


def fetchtwo():  
    conn = dbConnect()  
    cursor = conn.connect()  
    cursor.execute("select * from cdsjb")  
    result = cursor.fetchall()  
    conn.close()  
    print("success")  
    return result  


def inserttwo(**kwargs):  
    conn = dbConnect()  
    cursor = conn.connect()  
    sql = """insert into cdsjb(%s) values(%s)"""  
    key_list = []  
    value_list = []  
    for k, v in kwargs.items():  
        key_list.append(k)  
        value_list.append('%%(%s)s' % k)  
    sql = sql % (','.join(key_list), ','.join(value_list))  
    cursor.execute(sql, kwargs)  
    conn.close()

 
def insertthree(gcxmbm, gcxmmc):  
    conn = dbConnect()  
    cursor = conn.connect()  
    sql = """insert into gcxmb(gcxmbm,gcxmmc) values(%s,%s)"""  
    cursor.execute(sql, (gcxmbm, gcxmmc))  
    conn.close()  

  
def fetchthree():  
    conn = dbConnect()  
    cursor = conn.connect()  
    sql = """ select * from gcxmb """  
    cursor.execute(sql)  
    result = cursor.fetchone()  
    conn.close()  
    return result 

    
def main():  
        sk = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)  
        print(sk)  
        address = ('10.1.156.82', 8001)  
        sk.connect(address)  
        inp = '030300000002c5e9'    
        gcxmbm, gcxmmc = "631507030233冉杰", "温湿度处理"  # 这个为自己设定的工程项目编码和名称,用于后面对gcxmb表的操作  
      
        # 提前定义工程编码和名称,因为需要对温度和湿度进行操作,所以定义两个,也是用于后面对cdb表的操作  
        cdbm1, cdbm2 = "shidu", "wendu"  
        cdmc1, cdmc2 = "湿度", "温度"  
      
        while True:  
            list_wendu = []  
            list_shidu = []  
            global inst_wendu  # 瞬时温度  
            global inst_shidu  # 瞬时湿度   
            n = 0  
            begin_time = time.time()  # 开始读取是的时间戳  
            while True:  
                sk.send(codecs.decode(inp, 'hex'))  
                try:  
                    result = sk.recv(1024)  
                except socket.timeout:  
                    print('timeout')  
                crc = crc16(result[:-2])  # 进行CRC16-2校验  
                if crc == result[-2:]:  
                    print('CRC16成功')  
                shidu, wendu = struct.unpack('>hh', result[3:7])  # 用struct方法解析湿度和温度 
                shidu /= 100  
                wendu /= 100  
                # 比较上一次的温湿度的波动  
                with open("last_data", 'r') as r:  
                    last_data = r.read()  
                if not last_data:  # 如果last_data.txt中没有数据,就把当前温室度作为上一次温湿度进行比较  
                    last_data = str(wendu) + '%' + str(shidu)  # 字符串拼接  
                last_wendu, last_shidu = last_data.split("%")  # 字符串以%拆分,得到温湿度  
                last_wendu, last_shidu = float(last_wendu), float(last_shidu)  # 转化为float型数值  
              if(abs(shidu - last_shidu) > 5 or abs(wendu - last_wendu > 5)): # 比较当前温湿度与上一次温湿度差异,波动大于5就过滤掉  
                    print(abs(shidu - last_shidu), abs(wendu - last_wendu))  
                    print("数字波动太大,未记录")  
                    continue  
                else:  
                    # 将当前温度湿度写入文档作为记录  
                    data = str(wendu) + "%" + str(shidu)  
                    with open("last_data", 'w') as f:  
                        f.write(data)  
                    n += 1  
                    list_shidu.append(shidu)      
                    list_wendu.append(wendu)     
                    end_time = time.time()  # 获取结束时的时间戳  
                    if(end_time - begin_time > 5):  # 如果如果两次间隔大于五秒,停止读取数据,开始对数据进行处理  
                        inst_wendu = list_wendu[-1]  # 数组最后一个就是当时的瞬时值  
                        inst_shidu = list_shidu[-1]  
                        time.sleep(0.1)  
                        break  
                    else:  # 时间没有大于五秒则继续读取数据  
                        continue  
            cur_time = datetime.datetime.now()  # 记录处理完成的时间  
            print("瞬时温度%s" % (inst_wendu), cur_time)  
            print("瞬时湿度%s" % (inst_shidu), cur_time)  
            print("开始向数据库传入数据...")  
            gcxmb_data = fetchthree()  # 先对gcxmb表进行查询,如果存在数据,则进行下一步,如果不存在就插入数据  
            if not gcxmb_data:  
                try:  
                    insertthree(gcxmbm, gcxmmc)  
                except Exception:  
                    print("工程项目表插入失败")  
            cdb_data = fetchone()  # 对cdb表进行查询,存在数据则跳过,不存在则插入数据  
            if not cdb_data:  
                try:  
                    insertone(gcxmbm=gcxmbm, cdbm=cdbm1, cdmc=cdmc1, cgqbm="03", jldw="RH", sflb=1)  
                    insertone(gcxmbm=gcxmbm, cdbm=cdbm2, cdmc=cdmc2, cgqbm="03", jldw="摄氏度", sflb=1)  
                except Exception:  
                    print("测点表插入失败 ")  
            try:  # 插入处理后的数据  
                inserttwo(gcxmbm=gcxmbm, cdbm=cdbm1, clsj=cur_time, inst=inst_shidu)  
                inserttwo(gcxmbm=gcxmbm, cdbm=cdbm2, clsj=cur_time, inst=inst_wendu)  
                print("传入成功")  
            except:  
                print("测点数据表插入失败")  
        sk.close()  
main()

运行之前记得连接校网,打开虚拟机,ifconfig查询ip,修改程序。

运行结果:


插入后打开数据库查看数据:

cdb表:

cdsjb表:

gcxmb表:

这次实验这里只是将获得的数据做简单的处理传进去,

并没有获取平均值,最大值,最小值一同传进去。

下次实验是对数据做处理......

猜你喜欢

转载自blog.csdn.net/weixin_42134141/article/details/80408361