使用Enfora GSM调制解调器发送和接收短信
sms的Python项目详细描述
短信包为Enfora GSM调制解调器提供短信功能,以及 可能是其他人。
sms包提供调制解调器和消息类,用于发送和 正在接收短信。
sms.server模块提供了两个服务器,允许您分派 收到短信。sms.echo模块是一个可以工作的示例 使用sms.server.subprocess_服务器。
用法
创建一个传递串行设备ID的调制解调器对象。 就像是“com1”。下面的示例适用于Mac和 Linux:
>>> import sms >>> m = sms.Modem('/dev/ttyS0')
如果有更多的调制解调器对象,可以同时使用多个调制解调器对象 多个调制解调器连接到不同的串行端口。
为了测试的目的我们要替换真正的连续剧 在调制解调器上连接一个虚拟调制解调器,这样测试就不会 实际上是发短信。
>>> m.conn = DummyConnection()
虚拟连接将简单地保存发送的at命令的列表 而不是直接发送到调制解调器。
要发送短信,请调用send方法,传递电话号码 字符串和消息字符串。
>>> m.send('14161234567', 'This is a message')
让我们看看发送了什么at命令。
>>> m.conn.sent() 'AT+CMGS="14161234567"\r\nThis is a message\x1a'
发送了at+cmgs命令,然后终止了sms消息 使用ctrl-z。
让我们模拟一个发送错误,通过硬编码连接到 返回错误字符串。
>>> m.conn.response = ['ERROR']
现在我们试着发一条消息。
>>> m.send('14161234567', 'This is a message') Traceback (most recent call last): ... ModemError: ['ERROR']
出现modemerror并显示错误消息。
让我们恢复正常的连接响应。
>>> m.conn.response = []
可以使用messages()方法接收短消息。它重新播放 已接收的所有邮件的列表。
>>> m.messages() []
到目前为止还没有收到任何消息。让我们看看调制解调器的要求 对于消息。
>>> m.conn.reset() >>> m.messages() [] >>> m.conn.sent() 'AT+CMGL="ALL"\r\n'
AT+CMGL消息告诉调制解调器列出存储的消息。让我们 模拟对此命令的典型响应。
>>> m.conn.response = ['\r\n', '+CMGL: 1,"REC UNREAD","+16476186676",,"08/07/11,11:02:11+00"\r\n', 'Activation code 63966 Go 2 www.ipipi.com and signin with your username and pwd, enter 63966 to activate your mobile/account\r\n', '\r\n', '\r\n', 'Welcome 2 ipipi.com\r\n', 'OK\r\n']
现在我们再试一次。
>>> msgs = m.messages() >>> msgs [<sms.Message object at 0x...>]
消息对象有两个属性:数字、日期和文本。
>>> msgs[0].number '+16476186676'>>> msgs[0].date datetime.datetime(2008, 7, 11, 11, 2, 11)>>> msgs[0].text 'Activation code 63966 Go 2 www.ipipi.com and signin with your username and pwd, enter 63966 to activate your mobile/account\n\nWelcome 2 ipipi.com'
让我们做一个更复杂的例子来确保我们可以处理 不同类型的消息。
>>> m.conn.response = ['\r\n', '+CMGL: 1,"REC READ","+16476186676",,"08/07/11,11:02:11+00"\r\n', 'Activation code 63966 Go 2 www.ipipi.com and signin with your username and pwd, enter 63966 to activate your mobile/account\r\n', '\r\n', '\r\n', 'Welcome 2 ipipi.com\r\n', '+CMGL: 2,"STO UNSENT","14166243508",,\r\n', 'Out over the fields,\r\n', '\n', 'attached to nothing,\r\n', '\n', 'a skylark sings\r\n', '\r\n', '+CMGL: 3,"REC READ","+14161234567","Example Name","08/07/11,13:02:11+00"\r\n', 'Test message\r\n','OK\r\n']>>> msgs = m.messages() >>> len(msgs) 3 >>> msgs[0].number '+16476186676' >>> msgs[0].date datetime.datetime(2008, 7, 11, 11, 2, 11) >>> msgs[0].text 'Activation code 63966 Go 2 www.ipipi.com and signin with your username and pwd, enter 63966 to activate your mobile/account\n\nWelcome 2 ipipi.com' >>> msgs[2].number '+14161234567' >>> msgs[2].date datetime.datetime(2008, 7, 11, 13, 2, 11) >>> msgs[2].text 'Test message'
收到邮件后,您将希望从SIM卡中删除它们 卡片。这是通过调用消息的delete方法来完成的。
>>> msgs[0].delete()
让我们通过查看发送到调制解调器的at命令来测试这一点 当邮件被删除时。
>>> m.conn.reset() >>> msgs[0].delete() >>> m.conn.sent() 'AT+CMGD=1\r\n'>>> m.conn.reset() >>> msgs[1].delete() >>> m.conn.sent() 'AT+CMGD=2\r\n'
您可以调用wait()而不是轮询调制解调器来查找消息 方法,在收到消息之前阻塞。等待方法 接受可选的超时参数。
在这个测试中,而不是实际上阻塞 连接将打印它将阻塞的时间。
>>> m.wait(1) reading with 1 timeout>>> m.wait() reading with no timeout
等待消息不返回任何内容。你应该打电话给 方法返回以接收消息。请注意 有可能在 wait方法返回。
消息解码
大多数情况下,您可以将短消息视为ascii字符串。然而 它们应该是gms 03.387bit编码。我从没见过这个 在实践中。
我看到过Unicode消息。它们被编码为一系列十六进制 这样的数字:
>>> text = "004500200074006500730074002000E800E9002000C800C90020006100200074006500730074002000C000C1002000E000E1"
有一个函数可以解码这些消息。
>>> import sms.encoding >>> sms.encoding.decode_unicode(text) u'E test \xe8\xe9 \xc8\xc9 a test \xc0\xc1 \xe0\xe1'
如果您尝试为它提供看起来不是Unicode消息的文本,它将失败。
>>> sms.encoding.decode_unicode('not a unicode message') Traceback (most recent call last): ... ValueError: Message is not unicode
我还观察到了与ascii混合的重音字符。 角色。重音字符的值大于127。我不知道 它们是什么编码的,但我已经逆向工程过了 为了我.
下面是一个示例:
>>> text = "Montr\x82al"
decode_accents函数将这些消息解码为Unicode 最好的办法。
>>> sms.encoding.decode_accents(text) u'Montr\xe9al'
解码口音功能不会因未知字符而失败。它 将简单地用unicode替换字符替换它们。
>>> sms.encoding.decode_accents('what is this \xff') u'what is this \ufffd'
还有一个公司利用ascii函数将unicode转换为 ASCII码。它使用了弗雷德里克·伦德的不在场剧本。
>>> sms.encoding.to_ascii(u'Montr\xe9al') 'Montreal'
无法轻松转换为ascii的字符将更改为?.
>>> sms.encoding.to_ascii(u'\ufffd') '?'