Python 串口编程 AT指令控制短信猫

本文展示了如何使用Python进行串口编程,通过AT指令与短信猫交互,接收和发送短信。首先,文章定义了神秘函数解码PDU格式的短信,然后获取并设置消息索引文件,接着执行消息处理,包括判断是否为可信用户并发送回复短信。最后,程序进入循环,不断检查新消息并处理。

#-*- encoding: gbk -*-
import time
import sys
import os
import locale
import string
import traceback
import datetime
import serial

reload(sys);
sys.setdefaultencoding('gbk');


def mysterious(ust):
    s="";
    for i in range(len(ust)/4):
        us=ust[i*4:i*4+4];
        s=s+unichr(int(us,16));
    #end for
    return s
#end 


def decodePDU(pdu):
    phonelen=int(pdu[20:22],16);
    b=pdu[24:25+phonelen];#38
    phone="";
    for i in range(1,phonelen+1,2):
        if(i!=phonelen):
            phone=phone+b[i]+b[i-1];
        else:
            phone=phone+b[i];
        #end if
    #end for
    afterphone=25+phonelen+4;
    c=pdu[afterphone:afterphone+12];
    mytime= c[1]+c[0]+'-'+c[3]+c[2]+'-'+c[5]+c[4]+' '+c[7]+c[6]+':'+c[9]+c[8]+':'+c[11]+c[10];
    #15-04-12 14:32:35
    datalength=int(pdu[afterphone+12+2:afterphone+12+4],16)*2;
    mydata=mysterious(pdu[afterphone+12+4:afterphone+12+4+datalength]);
    return (phone,mydata,mytime);
#end def


def getMailIndex():
    file = open('messageindex.txt',"r");
    lines = file.readlines();
    file.close();
    return time.strptime(lines[0], "%y-%m-%d %H:%M:%S");
#    


def setMailIndex(timestr):
    f = open('messageindex.txt', 'w');
    f.write(timestr);
    f.close();
#    


def _queryQuick(cu,sql,tuple):
    try:
        cu.execute(sql,tuple);
        rows = []
        for row in cu:
            rows.append(row)
        #
        return rows
    except:
        print(traceback.format_exc())
    #end 
#
#获取信息
def _queryRows(cu,sql):
    try:
        cu.execute(sql)
        rows = []
        for row in cu:
            rows.append(row)
        #
        return rows
    except:
        print(traceback.format_exc())
    #end 
#


def executeMessage(messagelist):
    for messagetuple in messagelist:
        article=messagetuple[1];
        origin=messagetuple[0];
        
        conn.commit();
        #判断用户是否是信任列表里的用户
        users=_queryQuick(cur,"select username from trusted_users where username=%s",(origin,));
        if(len(users)<1):
            print('the user %s is not trusted user,ignore the message: %s,continue search the message...'%(origin,article));
            time.sleep(5)
            continue;
        #end if
        #start send message'已收到短信');
        print 'start send message'
        ser.write("AT+CMGS=47\r");
        pdus3="";
        while(pdus3.find('> ')<0):
            mydata3=ser.read(12);
            pdus3=pdus3+mydata3;
            time.sleep(0.1);
        #end while
        PDUmsg='0891683108200005F011000D91683166607056F70008AA205DF26536523077ED4FE1FF0C4E2D697757FA91D1611F8C224E0E60A854084F5C';
        myphone=origin[1]+origin[0]+origin[3]+origin[2]+origin[5]+origin[4]+origin[7]+origin[6]+origin[9]+origin[8]+origin[11]+origin[10]+'F'+origin[12];
        PDUmsgAll=PDUmsg[0:26]+myphone+PDUmsg[40:];
        ser.write(PDUmsgAll+"\x1a");
        time.sleep(1);
        pdus4="";
        while(pdus4.find('OK\r\n')<0):
            mydata4=ser.read(65536);
            pdus4=pdus4+mydata4;
            time.sleep(0.1);
        #end while
        print 'end send message'
#end def


#全局已读的邮件数量
globalMailReaded=getMailIndex();
hasNewMail=True;
ser = serial.Serial('COM3', 9600);
print 'get new Message...'
while True:
    if(hasNewMail):
        globalMailReaded=getMailIndex();
    #end if
    ser.write("AT+CMGL=4\r");
    pdus="";
    hasMessage=True;
    while(pdus.find('\r\nOK\r\n')<=0):
        mydata2=ser.read(65536);
        pdus=pdus+mydata2;
        if(len(pdus)==6 and pdus=='\r\nOK\r\n'):
            hasMessage=False;
            break;
        #end if  
        time.sleep(1);
    #end while
    if(hasMessage==False):
        hasNewMail=False;
        time.sleep(5);
        continue;
    #end if
    while(pdus.find('\r\n\r\nOK\r\n')<0):
        mydata=ser.read(65536);
        pdus=pdus+mydata;
        time.sleep(1);
    #end while
    strlist=pdus.split('+CMGL:');
    messagelist=[];
    pduCount=0;
    for str in strlist:
        index = str.find('0891');
        pduStr=str[index-1:].replace("\n", "");
        if(len(pduStr)>30):
            print pduStr;
            pduCount=pduCount+1;
            (phone2,mydata2,mytime2)=decodePDU(pduStr);
            Sms_Time=time.strptime(mytime2, "%y-%m-%d %H:%M:%S");
            if(Sms_Time>globalMailReaded):
                messagelist.append((phone2,mydata2));
                setMailIndex(mytime2);
                hasNewMail=True;
            #end if
        #end if
    #end for
    #删除旧短信
    print messagelist;
    print 'delete old message'
    time.sleep(1);
    if(pduCount>0):
        for j in range(25,0,-1):
            ATStr="AT+CMGD=%d\r"%(j);
            ser.write(ATStr);
            ATReturn="";
            while(ATReturn.find('OK')<0):
                mydata=ser.read(65536);
                ATReturn=ATReturn+mydata;
                time.sleep(0.05);
            #end while
        #end for
        print('has deleted all messages');
    #end if    
    if(len(messagelist)>0):
        executeMessage(messagelist);
    else:
        hasNewMail=False;
    #end if
    time.sleep(1);
#end while

评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值