14 Commits

Author SHA1 Message Date
Civlo85 13fbd1ba78 Merge pull request #5 from ThinkTransit/master
Update gsmHat.py
Some Waveshare devices return more than 21 data items for GPS data
2024-05-27 07:21:23 +02:00
Civlo85 d4d2878e5e Update README.md 2024-04-04 23:49:04 +02:00
Patrick Joy 1c63208d2b Update gsmHat.py
Some Waveshare devices return more than 21 data items for GPS data
2021-04-17 15:48:04 +10:00
Civlo85 f8e4bf75f2 Update README.md
Update of the pip command
2020-10-22 11:50:09 +02:00
Tarek 94558e35fc Correction of some minor errors 2020-10-21 00:57:29 +02:00
Tarek cb2c254b28 Internet functionality added 2020-10-21 00:38:28 +02:00
Tarek 29d4f54d52 Assuming, that the wrong logging package is included 2020-10-15 11:29:12 +02:00
Tarek 2ffb53977c Assuming, that the wrong logging package is included 2020-10-15 11:25:36 +02:00
Tarek c5ecfc538e Update README 2020-09-03 20:55:02 +02:00
Tarek 5a09095cda Call and GPS functionality added 2020-09-03 20:41:10 +02:00
Tarek 4d495905cd README updated 2020-09-03 20:36:59 +02:00
Tarek 76387c74c7 Call and GPS functionality added 2020-09-03 17:06:40 +02:00
Tarek 7c3a6ad886 Call and GPS functionality added 2020-09-03 17:04:39 +02:00
Tarek 32ba0c839f add setup files for PyPi 2020-09-02 12:23:56 +02:00
5 changed files with 633 additions and 41 deletions
+96 -8
View File
@@ -1,11 +1,20 @@
# Update on Thu Apr 4th, 2024
Unfortunately, there is no time (and equipment anymore) to maintain this repository. I hope that someone else will find the time to continue with that.
# gsmHat - Waveshare GSM/GPRS/GNSS HAT for Raspberry Pi with Python # gsmHat - Waveshare GSM/GPRS/GNSS HAT for Raspberry Pi with Python
With gsmHat, you can easily use the functionality of the Waveshare GSM/GPRS/GNSS HAT for Raspberry Pi ([Link to HAT](https://www.waveshare.com/gsm-gprs-gnss-hat.htm)). On this module a SIM868 Controller is doing the job too connect your Raspberry Pi with the world just by using a sim card. With gsmHat, you can easily use the functionality of the Waveshare GSM/GPRS/GNSS HAT for Raspberry Pi ([Link to HAT](https://www.waveshare.com/gsm-gprs-gnss-hat.htm)). On this module a SIM868 Controller is doing the job to connect your Raspberry Pi with the world just by using a sim card.
## Update on Wed Oct 21st, 2020
:point_right: Internet functionality added!
## Overview ## Overview
gsmHat was written for Python 3. It provides the following features gsmHat was written for Python 3. It provides the following features
- Non-blocking receiving and sending SMS in background - Non-blocking receiving and sending SMS in background
- Non-blocking calling
- Non-blocking refreshing of actual gps position
- Non-blocking URL Call and receiving of response
## Usage ## Usage
@@ -13,15 +22,14 @@ In the following paragraphs, I am going to describe how you can get and use gsmH
### Getting it ### Getting it
To download scrapeasy, either fork this github repo or simply use Pypi via pip. To download gsmHat, either fork this github repo or simply use Pypi via pip.
```sh ```sh
$ pip3 install gsmHat $ python3 -m pip install -U gsmHat
``` ```
### Prepare ### Prepare
* Install your sim card in your module, connect the GSM antenna and mount the module on the pin headers of your Raspberry Pi * Install your sim card in your module, connect the GSM and the GPS antennas and mount the module on the pin headers of your Raspberry Pi. Make sure, that you **do not** need to enter Pin Code to use your card. Pin Codes are not supported yet.
Make sure, that you **do not** need to enter Pin Code to use your card
* Enable the Uart Interface in your Raspberry Pi * Enable the Uart Interface in your Raspberry Pi
@@ -37,7 +45,7 @@ $ pip3 install gsmHat
1. Import gsmHat to your project 1. Import gsmHat to your project
```Python ```Python
from gsmHat import GSMHat, SMS from gsmHat import GSMHat, SMS, GPS
``` ```
2. Init gsmHat 2. Init gsmHat
@@ -76,10 +84,90 @@ Message = 'Hello mobile world'
# Send SMS # Send SMS
gsm.SMS_write(Number, Message) gsm.SMS_write(Number, Message)
``` ```
6. Or you can call a number
```Python
Number = '+491601234567'
gsm.Call(Number) # This call hangs up automatically after 15 seconds
time.sleep(10) # Wait 10 seconds ...
gsm.HangUp() # Or you can HangUp by yourself earlier
gsm.Call(Number, 60) # Or lets change the timeout to 60 seconds. This call hangs up automatically after 60 seconds
```
7. Lets see, where your Raspberry Pi (in a car or on a motocycle or on a cat?) is positioned on earth
```Python
# Get actual GPS position
GPSObj = gsm.GetActualGPS()
# Lets print some values
print('GNSS_status: %s' % str(GPSObj.GNSS_status))
print('Fix_status: %s' % str(GPSObj.Fix_status))
print('UTC: %s' % str(GPSObj.UTC))
print('Latitude: %s' % str(GPSObj.Latitude))
print('Longitude: %s' % str(GPSObj.Longitude))
print('Altitude: %s' % str(GPSObj.Altitude))
print('Speed: %s' % str(GPSObj.Speed))
print('Course: %s' % str(GPSObj.Course))
print('HDOP: %s' % str(GPSObj.HDOP))
print('PDOP: %s' % str(GPSObj.PDOP))
print('VDOP: %s' % str(GPSObj.VDOP))
print('GPS_satellites: %s' % str(GPSObj.GPS_satellites))
print('GNSS_satellites: %s' % str(GPSObj.GNSS_satellites))
print('Signal: %s' % str(GPSObj.Signal))
```
8. Calculate the distance between two Points on earth
```Python
GPSObj1 = GPS() # You can also use gsm.GetActualGPS() to get an GPS object
GPSObj1.Latitude = 52.266949 # Location of Braunschweig, Germany
GPSObj1.Longitude = 10.524822
GPSObj2 = GPS()
GPSObj2.Latitude = 36.720005 # Location of Manavgat, Turkey
GPSObj2.Longitude = 31.546094
print('Distance from Braunschweig to Manavgat in metres:')
print(GPS.CalculateDeltaP(GPSObj1, GPSObj2)) # this will print 2384660.7 metres
```
9. Call URL to send some data
```Python
# Init gsmHat
gsm = GSMHat('/dev/ttyS0', 115200)
# Set the APN Connection data. You will get this from your provider
# e.g. German Provider 'Congstar'
gsm.SetGPRSconnection('internet.telekom', 'congstar', 'cs')
# Get actual GPS position
GPSObj = gsm.GetActualGPS()
# Build url string with data
url = 'www.someserver.de/myscript.php'
url += '?time='+str(int(GPSObj.UTC.timestamp()))
url += '&lat='+str(GPSObj.Latitude)
url += '&lon='+str(GPSObj.Longitude)
url += '&alt='+str(GPSObj.Altitude)
gsm.CallUrl(url) # Send actual position to a webserver
```
10. Get the Response from a previous URL call
```Python
# Check, if new Response Data is available
if gsm.UrlResponse_available() > 0:
# Read the Response
newResponse = gsm.UrlResponse_read()
# Do something with it
```
## What will come in the future? ## What will come in the future?
* Outgoing and Incoming Calls
* GPS functionality
* More options to configure the module (e.g. using sim cards with pin code) * More options to configure the module (e.g. using sim cards with pin code)
## On which platform was gsmHat developed and tested? ## On which platform was gsmHat developed and tested?
+1 -1
View File
@@ -1 +1 @@
from gsmHat.gsmHat import GSMHat, SMS from gsmHat.gsmHat import GSMHat, SMS, GPS
+500 -32
View File
@@ -4,6 +4,7 @@ import logging
import serial import serial
import threading import threading
import time import time
import math
import re import re
from datetime import datetime from datetime import datetime
import RPi.GPIO as GPIO import RPi.GPIO as GPIO
@@ -15,20 +16,56 @@ class SMS:
self.Receiver = '' self.Receiver = ''
self.Date = '' self.Date = ''
class GPS:
EarthRadius = 6371e3 # meters
@staticmethod
def CalculateDeltaP(Position1, Position2):
phi1 = Position1.Latitude * math.pi / 180.0
phi2 = Position2.Latitude * math.pi / 180.0
deltaPhi = (Position2.Latitude - Position1.Latitude) * math.pi / 180.0
deltaLambda = (Position2.Longitude - Position1.Longitude) * math.pi / 180.0
a = math.sin(deltaPhi / 2) * math.sin(deltaPhi / 2) + math.cos(phi1) * math.cos(phi2) * math.sin(deltaLambda / 2) * math.sin(deltaLambda / 2)
c = 2 * math.atan2(math.sqrt(a), math.sqrt(1 - a))
d = GPS.EarthRadius * c # in meters
return d
def __init__(self):
self.GNSS_status = 0
self.Fix_status = 0
self.UTC = '' # yyyyMMddhhmmss.sss
self.Latitude = 0.0 # ±dd.dddddd [-90.000000,90.000000]
self.Longitude = 0.0 # ±ddd.dddddd [-180.000000,180.000000]
self.Altitude = 0.0 # in meters
self.Speed = 0.0 # km/h [0,999.99]
self.Course = 0.0 # degrees [0,360.00]
self.HDOP = 0.0 # [0,99.9]
self.PDOP = 0.0 # [0,99.9]
self.VDOP = 0.0 # [0,99.9]
self.GPS_satellites = 0 # [0,99]
self.GNSS_satellites = 0 # [0,99]
self.Signal = 0.0 # % max = 55 dBHz
class GSMHat: class GSMHat:
"""GSM Hat Backend with SMS Functionality (for now)""" """GSM Hat Backend with SMS Functionality (for now)"""
regexGetSingleValue = r'([+][a-zA-Z\ ]+(:\ ))([\d]+)' regexGetSingleValue = r'([+][a-zA-Z\ ]+(:\ ))([\d]+)'
regexGetAllValues = r'([+][a-zA-Z:\s]+)([\w\",\s+\/:]+)' regexGetAllValues = r'([+][a-zA-Z:\s]+)([\w\",\s+-\/:.]+)'
timeoutSerial = 5 timeoutSerial = 5
timeoutGPSActive = 1
timeoutGPSInactive = 2000
cSMSwaittime = 2500 # milliseconds
cGPRSstatusWaittime = 5000 # milliseconds
def __init__(self, SerialPort, Baudrate): def __init__(self, SerialPort, Baudrate, Logpath='gmsHat.log'):
self.__baudrate = Baudrate self.__baudrate = Baudrate
self.__port = SerialPort self.__port = SerialPort
self.__logger = logging.getLogger(__name__) self.__logger = logging.getLogger(__name__)
self.__logger.setLevel(logging.DEBUG) self.__logger.setLevel(logging.DEBUG)
self.__loggerFileHandle = logging.FileHandler('gsmHat.log') self.__loggerFileHandle = logging.FileHandler(Logpath)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s') formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
self.__loggerFileHandle.setFormatter(formatter) self.__loggerFileHandle.setFormatter(formatter)
self.__loggerFileHandle.setLevel(logging.DEBUG) self.__loggerFileHandle.setLevel(logging.DEBUG)
@@ -50,12 +87,36 @@ class GSMHat:
def __startWorking(self): def __startWorking(self):
self.__working = True self.__working = True
self.__state = 1 self.__state = 1
self.__nextState = 0
self.__smsToRead = 0 self.__smsToRead = 0
self.__retryAfterTimeout = False
self.__retryAfterTimeoutCount = 0
self.__init = False self.__init = False
self.__readRAW = False self.__lastCommandSentString = ''
self.__readRAW = 0
self.__smsToBuild = None self.__smsToBuild = None
self.__smsList = [] self.__smsList = []
self.__smsSendList = [] self.__smsSendList = []
self.__SMSwaittime = 0
self.__numberToCall = ''
self.__sendHangUp = False
self.__startGPS = False
self.__GPRSwaittimeStatus = 0
self.__GPRSIPaddress = ''
self.__GPRSready = False
self.__GPRSuserAPN = None
self.__GPRSuserUSER = None
self.__GPRSuserPWD = None
self.__GPRScallUrlList = []
self.__GPRSdataReceived = []
self.__GPRSwaitForData = False
self.__GPSstarted = False
self.__GPSstartSending = False
self.__GPSstopSending = False
self.__GPScollectData = False
self.__GPSactualData = GPS()
self.__GPStimeout = self.timeoutGPSInactive
self.__GPSwaittime = 0
self.__workerThread = threading.Thread(target=self.__workerThread, daemon=True) self.__workerThread = threading.Thread(target=self.__workerThread, daemon=True)
self.__workerThread.start() self.__workerThread.start()
@@ -65,7 +126,7 @@ class GSMHat:
def __sendToHat(self, string): def __sendToHat(self, string):
if self.__writeLock == False: if self.__writeLock == False:
self.__lastCommand = string self.__lastCommandSentString = string
string = string + '\n' string = string + '\n'
self.__ser.write(string.encode('iso-8859-1')) self.__ser.write(string.encode('iso-8859-1'))
self.__writeLock = True self.__writeLock = True
@@ -73,7 +134,7 @@ class GSMHat:
self.__logger.debug('Sent to hat: %s' % string) self.__logger.debug('Sent to hat: %s' % string)
return True return True
else: else:
self.__logger.debug('Wait for Lock...') self.__logger.debug('Wait for Lock... state: ' + str(self.__state) + ' senddata: ' + string)
time.sleep(1) time.sleep(1)
return False return False
@@ -105,6 +166,58 @@ class GSMHat:
newSMS.Message = Message newSMS.Message = Message
self.__smsSendList.append(newSMS) self.__smsSendList.append(newSMS)
def Call(self, Number, Timeout = 15):
if self.__numberToCall == '':
self.__numberToCall = str(Number)
self.__callTimeout = Timeout
return True
return False
def HangUp(self):
self.__sendHangUp = True
def GetActualGPS(self):
return self.__GPSactualData
def UrlResponse_available(self):
return len(self.__GPRSdataReceived)
def UrlResponse_read(self):
if self.UrlResponse_available() > 0:
retResponse = self.__GPRSdataReceived[0]
del self.__GPRSdataReceived[0]
return retResponse
return None
def CallUrl(self, url):
self.__GPRScallUrlList.append(url)
self.__logger.debug('Got new URL call')
def PendingUrlCalls(self):
return len(self.__GPRScallUrlList)
def SetGPRSconnection(self, APN, Username, Password):
self.__GPRSuserAPN = APN
self.__GPRSuserUSER = Username
self.__GPRSuserPWD = Password
def __startGPSUnit(self):
self.__startGPS = True
def __startGPSsending(self):
self.__GPSstartSending = True
def __stopGPSsending(self):
self.__GPSstopSending = True
def __collectGPSData(self):
self.__GPScollectData = True
def ColData(self):
self.__collectGPSData()
def close(self): def close(self):
self.__disconnect() self.__disconnect()
self.__logger.info('Serial connection to '+self.__port+' closed') self.__logger.info('Serial connection to '+self.__port+' closed')
@@ -112,22 +225,40 @@ class GSMHat:
def __processData(self): def __processData(self):
if self.__serData != '': if self.__serData != '':
if self.__readRAW: if self.__readRAW > 0:
self.__logger.debug('Received Raw Data: %s' % self.__serData) self.__logger.debug('Received Raw Data: %s' % self.__serData)
if self.__serData == 'OK\r\n': if self.__readRAW == 1:
self.__smsToBuild.Message = self.__smsToBuild.Message.rstrip('\r\n') # Handle SMS
self.__smsList.append(self.__smsToBuild) if self.__serData == 'OK\r\n':
self.__readRAW = False self.__smsToBuild.Message = self.__smsToBuild.Message.rstrip('\r\n')
self.__writeLock = False self.__smsList.append(self.__smsToBuild)
else: self.__readRAW = 0
#self.__smsToBuild.Message = bytearray.fromhex(self.__serData).decode() self.__writeLock = False
self.__smsToBuild.Message = self.__smsToBuild.Message + self.__serData else:
self.__smsToBuild.Message = self.__smsToBuild.Message + self.__serData
elif self.__readRAW == 2:
# Handle HTTP Response
if self.__serData == 'OK\r\n':
self.__readRAW = 0
self.__writeLock = False
self.__GPRSdataToBuild = self.__GPRSdataToBuild.rstrip('\r\n')
self.__GPRSdataReceived.append(self.__GPRSdataToBuild)
else:
self.__GPRSdataToBuild = self.__GPRSdataToBuild + self.__serData
else: else:
self.__logger.debug('Received Data: %s' % self.__serData) self.__logger.debug('Received Data: %s' % self.__serData)
if 'OK' in self.__serData: if 'OK' in self.__serData:
self.__writeLock = False self.__writeLock = False
self.__logger.debug('Lock Off') self.__logger.debug('Lock Off')
if 'ERROR' in self.__serData:
# ERROR Handling here
if self.__state == 71:
# Error after sending AT+HTTPINIT
# Lets terminate request before starting new one
self.__logger.info('Error after starting new HTTP Request.')
self.__writeLock = False
self.__state = 75
elif '+CME ERROR:' in self.__serData: elif '+CME ERROR:' in self.__serData:
self.__writeLock = False self.__writeLock = False
@@ -154,7 +285,7 @@ class GSMHat:
# read SMS content # read SMS content
match = re.findall(self.regexGetAllValues, self.__serData) match = re.findall(self.regexGetAllValues, self.__serData)
rawData = match[0][1].split('","') rawData = match[0][1].split('","')
self.__readRAW = True self.__readRAW = 1
self.__smsToBuild = SMS() self.__smsToBuild = SMS()
#self.__smsToBuild.Sender = bytearray.fromhex(rawData[1]).decode() #self.__smsToBuild.Sender = bytearray.fromhex(rawData[1]).decode()
self.__smsToBuild.Sender = rawData[1] self.__smsToBuild.Sender = rawData[1]
@@ -162,6 +293,42 @@ class GSMHat:
self.__smsToBuild.Date = datetime.strptime(rawData[3].replace('"', '')[:-3], '%y/%m/%d,%H:%M:%S') self.__smsToBuild.Date = datetime.strptime(rawData[3].replace('"', '')[:-3], '%y/%m/%d,%H:%M:%S')
self.__smsToBuild.Message = '' self.__smsToBuild.Message = ''
elif '+SAPBR:' in self.__serData:
# check if IP is valid
# Return value looks like: +SAPBR: 1,3,"0.0.0.0"
match = re.findall(self.regexGetAllValues, self.__serData)
rawData = match[0][1].split(',')
self.__GPRSIPaddress = rawData[2].replace('"', '')
if self.__GPRSIPaddress != '0.0.0.0':
self.__GPRSready = True
else:
self.__GPRSready = False
elif '+HTTPREAD:' in self.__serData:
# read HTTP content
self.__GPRSdataToBuild = ''
self.__readRAW = 2
elif '+HTTPACTION:' in self.__serData:
# Return value looks like: +HTTPACTION: 0,200,0
match = re.findall(self.regexGetAllValues, self.__serData)
rawData = match[0][1].split(',')
self.__GPRSgotHttpResponse = True
if len(rawData) == 3:
requestMethod = int(rawData[0])
httpStatus = int(rawData[1])
recvDataLength = int(rawData[2])
if httpStatus == 200: # Successful request
self.__GPRSnewDataReceived = True
elif httpStatus == 601: # Successful request
self.__logger.info('HTTPACTION Network Error ' + str(httpStatus))
else:
self.__logger.info('HTTPACTION Unhandled Error ' + str(httpStatus))
else:
self.__logger.info('HTTPACTION return value is not expected: ' + match[0][1])
# unannounced data reception below (e.g. new SMS oder phone call) # unannounced data reception below (e.g. new SMS oder phone call)
elif '+CMTI:' in self.__serData: elif '+CMTI:' in self.__serData:
self.__logger.info('Received new SMS') self.__logger.info('Received new SMS')
@@ -171,25 +338,143 @@ class GSMHat:
numSMS = int(rawData[1]) numSMS = int(rawData[1])
self.__logger.debug('New SMS in memory ' + storage + ' at position ' + str(numSMS)) self.__logger.debug('New SMS in memory ' + storage + ' at position ' + str(numSMS))
self.__smsToRead = numSMS self.__smsToRead = numSMS
# GPS Data coming here
elif '+CGNSINF:' in self.__serData:
self.__logger.debug('New GPS Data:')
match = re.findall(self.regexGetAllValues, self.__serData)
rawData = match[0][1].split(',')
if len(rawData) >= 21:
newGPS = GPS()
goodPosition = True
try:
newGPS.GNSS_status = int(rawData[0])
except:
self.__logger.debug('GNSS_status: Could not convert ' + rawData[0] + ' to int.')
try:
# Fix_status: GPS connection
newGPS.Fix_status = int(rawData[1])
if newGPS.Fix_status == 0:
goodPosition = False
except:
self.__logger.debug('Fix_status: Could not convert ' + rawData[1] + ' to int.')
try:
newGPS.UTC = datetime.strptime(rawData[2][:-4], '%Y%m%d%H%M%S')
except:
self.__logger.debug('UTC: Could not convert ' + rawData[2][:-4] + ' to int.')
try:
newGPS.Latitude = float(rawData[3])
if newGPS.Latitude == 0.0:
goodPosition = False
except:
self.__logger.debug('Latitude: Could not convert ' + rawData[3] + ' to float.')
try:
newGPS.Longitude = float(rawData[4])
if newGPS.Longitude == 0.0:
goodPosition = False
except:
self.__logger.debug('Longitude: Could not convert ' + rawData[4] + ' to float.')
try:
newGPS.Altitude = float(rawData[5])
if newGPS.Altitude == 0.0:
goodPosition = False
except:
self.__logger.debug('Altitude: Could not convert ' + rawData[5] + ' to float.')
try:
newGPS.Speed = float(rawData[6])
except:
self.__logger.debug('Speed: Could not convert ' + rawData[6] + ' to float.')
try:
newGPS.Course = float(rawData[7])
except:
self.__logger.debug('Course: Could not convert ' + rawData[7] + ' to float.')
try:
newGPS.HDOP = float(rawData[10])
except:
self.__logger.debug('HDOP: Could not convert ' + rawData[10] + ' to float.')
try:
newGPS.PDOP = float(rawData[11])
if newGPS.PDOP == 0.0:
goodPosition = False
except:
self.__logger.debug('PDOP: Could not convert ' + rawData[11] + ' to float.')
try:
newGPS.VDOP = float(rawData[12])
except:
self.__logger.debug('VDOP: Could not convert ' + rawData[12] + ' to float.')
try:
newGPS.GPS_satellites = int(rawData[14])
except:
self.__logger.debug('GPS_satellites: Could not convert ' + rawData[14] + ' to int.')
try:
newGPS.GNSS_satellites = int(rawData[15])
except:
self.__logger.debug('GNSS_satellites: Could not convert ' + rawData[15] + ' to int.')
try:
newGPS.Signal = float(rawData[18])/55.0
except:
self.__logger.debug('Signal: Could not convert ' + rawData[18] + ' to float.')
if goodPosition:
self.__GPSactualData = newGPS
self.__serData = '' self.__serData = ''
def __restartProcedure(self):
self.__logger.error('Try to restart gsm module')
self.__pressPowerKey()
self.__state = 1
self.__writeLock = False
self.__retryAfterTimeout = False
self.__sentTimeout = 0
def __waitForUnlock(self): def __waitForUnlock(self):
actTime = int(round(time.time())) actTime = int(round(time.time()))
if self.__sentTimeout > 0 and actTime > self.__sentTimeout: if self.__sentTimeout > 0 and actTime > self.__sentTimeout:
# Timeout # Timeout
self.__logger.error('Timeout during data reception') self.__logger.error('Timeout during data reception')
self.__logger.info('Command sent: ' + self.__lastCommandSentString)
self.__logger.info('Actual state of programme: ' + str(self.__state))
if self.__state == 2: if self.__state == 2 or self.__state == 97:
# It might be that the gsm module is not powered on # It might be that the gsm module is not powered on
# So let's try # So let's try to restart
self.__logger.error('Try to restart gsm module') self.__restartProcedure()
self.__pressPowerKey() return False
self.__state = 1 elif self.__state == 3:
# Tried to check for new SMS
# Retry 3 times
if self.__retryAfterTimeout:
if self.__retryAfterTimeoutCount > 0:
self.__retryAfterTimeoutCount -= 1
else:
self.__restartProcedure()
return False
else:
self.__retryAfterTimeout = True
self.__retryAfterTimeoutCount = 3
self.__state = 2
self.__writeLock = False self.__writeLock = False
self.__sentTimeout = 0 self.__sentTimeout = 0
return False return False
else: else:
self.__logger.critical('Exception: Unhandled timeout during data reception')
raise 'Unhandled timeout during data reception' raise 'Unhandled timeout during data reception'
if self.__writeLock: if self.__writeLock:
@@ -208,12 +493,12 @@ class GSMHat:
newChar = self.__ser.read().decode('iso-8859-1') newChar = self.__ser.read().decode('iso-8859-1')
if newChar == '\n': if newChar == '\n':
if self.__readRAW == True: if self.__readRAW > 0:
self.__serData += newChar self.__serData += newChar
self.__processData() self.__processData()
else: else:
if newChar == '\r': if newChar == '\r':
if self.__readRAW == True: if self.__readRAW > 0:
self.__serData += newChar self.__serData += newChar
else: else:
self.__serData += newChar self.__serData += newChar
@@ -222,6 +507,8 @@ class GSMHat:
actTime = int(round(time.time() * 1000)) actTime = int(round(time.time() * 1000))
if self.__state == 1: if self.__state == 1:
if self.__sendToHat('AT+CMGF=1'): if self.__sendToHat('AT+CMGF=1'):
self.__startGPSUnit()
self.__stopGPSsending()
self.__state = 2 self.__state = 2
elif self.__state == 2: elif self.__state == 2:
if self.__waitForUnlock(): if self.__waitForUnlock():
@@ -230,8 +517,6 @@ class GSMHat:
elif self.__state == 3: elif self.__state == 3:
if self.__waitForUnlock(): if self.__waitForUnlock():
self.__state = 97 self.__state = 97
self.__nextState = 2
self.__waitTime = actTime + 5000
elif self.__state == 20: elif self.__state == 20:
# Read SMS # Read SMS
if self.__sendToHat('AT+CMGR='+str(self.__smsToRead)): if self.__sendToHat('AT+CMGR='+str(self.__smsToRead)):
@@ -243,7 +528,8 @@ class GSMHat:
pass pass
else: else:
# Es gab eine neue SMS # Es gab eine neue SMS
self.__smsToBuild = None self.__logger.info('New Message from ' + self.__smsToBuild.Sender + ' was received')
self.__smsToBuild = None
# Lösche die behandelte SMS an der Stelle # Lösche die behandelte SMS an der Stelle
if self.__sendToHat('AT+CMGD='+str(self.__smsToRead)): if self.__sendToHat('AT+CMGD='+str(self.__smsToRead)):
@@ -257,8 +543,6 @@ class GSMHat:
self.__smsToRead = self.__smsToRead + 1 self.__smsToRead = self.__smsToRead + 1
self.__state = 97 self.__state = 97
self.__nextState = 2
self.__waitTime = actTime + 5000
elif self.__state == 30: elif self.__state == 30:
# SMS versenden # SMS versenden
@@ -276,21 +560,205 @@ class GSMHat:
self.timeoutSerial = 5 self.timeoutSerial = 5
self.__state = 97 self.__state = 97
self.__nextState = 2
self.__waitTime = actTime + 5000 elif self.__state == 40:
if self.__sendToHat('ATD' + self.__numberToCall + ';'):
self.__state = 41
elif self.__state == 41:
if self.__waitForUnlock():
self.__waitTime = actTime + self.__callTimeout * 1000
self.__state = 42
elif self.__state == 42:
# Wait x Seconds
if actTime > self.__waitTime or self.__sendHangUp == True:
self.__numberToCall = ''
self.__sendHangUp = True
self.__state = 97
elif self.__state == 43:
if self.__sendToHat('AT+CHUP'):
self.__state = 44
elif self.__state == 44:
if self.__waitForUnlock():
self.__sendHangUp = False
self.__state = 97
elif self.__state == 50:
if self.__sendToHat('AT+CGNSPWR=1'):
self.__state = 51
elif self.__state == 51:
if self.__waitForUnlock():
self.__logger.debug('GPS powered on')
self.__startGPS = False
self.__state = 97
elif self.__state == 52:
if self.__sendToHat('AT+CGNSTST=1'):
self.__state = 55
self.__logger.debug('GPS start sending')
self.__GPSstartSending = False
elif self.__state == 53:
if self.__sendToHat('AT+CGNSTST=0'):
self.__state = 55
self.__GPSstopSending = False
elif self.__state == 54:
if self.__sendToHat('AT+CGNSINF'):
self.__state = 55
self.__GPScollectData = False
elif self.__state == 55:
if self.__waitForUnlock():
self.__state = 97
elif self.__state == 60:
if self.__sendToHat('AT+SAPBR=2,1'):
self.__state = 61
elif self.__state == 61:
if self.__waitForUnlock():
tempState = 97
if self.__GPRSready == True:
pass
else:
if self.__GPRSuserAPN != None and self.__GPRSuserUSER != None and self.__GPRSuserPWD != None:
# try to connect
tempState = 62
self.__state = tempState
elif self.__state == 62:
if self.__sendToHat('AT+SAPBR=3,1,"Contype","GPRS"'):
self.__state = self.__state + 1
elif self.__state == 63:
if self.__waitForUnlock():
if self.__sendToHat('AT+SAPBR=3,1,"APN","' + self.__GPRSuserAPN + '"'):
self.__state = self.__state + 1
elif self.__state == 64:
if self.__waitForUnlock():
if self.__sendToHat('AT+SAPBR=3,1,"USER","' + self.__GPRSuserUSER + '"'):
self.__state = self.__state + 1
elif self.__state == 65:
if self.__waitForUnlock():
if self.__sendToHat('AT+SAPBR=3,1,"PWD","' + self.__GPRSuserPWD + '"'):
self.__state = self.__state + 1
elif self.__state == 66:
if self.__waitForUnlock():
if self.__sendToHat('AT+SAPBR=1,1'):
self.__state = self.__state + 1
elif self.__state == 67:
if self.__waitForUnlock():
self.__state = 97
elif self.__state == 70:
# Call the first URL in List
if self.__sendToHat('AT+HTTPINIT'):
self.__state = self.__state + 1
elif self.__state == 71:
if self.__waitForUnlock():
if self.__sendToHat('AT+HTTPPARA="CID",1'):
self.__state = self.__state + 1
elif self.__state == 72:
if self.__waitForUnlock():
getUrl = self.__GPRScallUrlList[0]
if self.__sendToHat('AT+HTTPPARA="URL","' + getUrl + '"'):
del self.__GPRScallUrlList[0]
self.__GPRSwaitForData = True
self.__GPRSnewDataReceived = False
self.__GPRSgotHttpResponse = False
self.__state = self.__state + 1
elif self.__state == 73:
if self.__waitForUnlock():
if self.__sendToHat('AT+HTTPACTION=0'):
self.__state = 97
#self.__state = self.__state + 1
elif self.__state == 74:
if self.__waitForUnlock():
if self.__sendToHat('AT+HTTPREAD'):
self.__state = self.__state + 1
elif self.__state == 75:
# Close HTTP Request
if self.__waitForUnlock():
if self.__sendToHat('AT+HTTPTERM'):
self.__state = 97
self.__GPRSwaitForData = False
self.__GPRSnewDataReceived = False
elif self.__state == 97: elif self.__state == 97:
# Check if new SMS to send is there # Check if new SMS to send is there
if len(self.__smsSendList) > 0: if len(self.__smsSendList) > 0:
self.__state = 30 self.__state = 30
# Check if we have to Call somebody
elif self.__numberToCall != '':
self.__state = 40
# Should I Hang Up ?
elif self.__sendHangUp:
self.__state = 43
# Check if new SMS is there # Check if new SMS is there
elif self.__smsToRead > 0: elif self.__smsToRead > 0:
self.__state = 20 self.__state = 20
# Check if we should call some Urls
elif len(self.__GPRScallUrlList) > 0 and self.__GPRSready and self.__GPRSwaitForData == False:
self.__state = 70
elif self.__GPRSwaitForData and self.__GPRSgotHttpResponse:
if self.__GPRSnewDataReceived:
self.__state = 74
else:
self.__state = 75
# Check if GPS Unit should start
elif self.__startGPS:
self.__state = 50
# Check if GPS Unit should start send
elif self.__GPSstartSending:
self.__state = 52
# Check if GPS Unit should stop send
elif self.__GPSstopSending:
self.__state = 53
# Check if Single GPS Data should be collected
elif self.__GPScollectData:
self.__state = 54
elif actTime > self.__GPSwaittime:
self.__GPScollectData = True
self.__GPSwaittime = actTime + self.__GPStimeout
elif actTime > self.__SMSwaittime:
self.__state = 2
self.__SMSwaittime = actTime + self.cSMSwaittime
elif actTime > self.__GPRSwaittimeStatus:
self.__state = 60
self.__GPRSwaittimeStatus = actTime + self.cGPRSstatusWaittime
# Wait x Seconds # Wait x Seconds
elif actTime > self.__waitTime: elif actTime > self.__waitTime:
self.__state = self.__nextState if self.__nextState > 0:
self.__state = self.__nextState
self.__nextState = 0
elif self.__state == 98: elif self.__state == 98:
#Check if alive #Check if alive
self.__logger.debug('Check if alive 98') self.__logger.debug('Check if alive 98')
@@ -305,4 +773,4 @@ class GSMHat:
# Let other Threads also do their job # Let other Threads also do their job
time.sleep(0.1) time.sleep(0.1)
self.__logger.info('Worker ended') self.__logger.info('Worker ended')
Executable
+2
View File
@@ -0,0 +1,2 @@
[metadata]
description-file = README.md
Executable
+34
View File
@@ -0,0 +1,34 @@
from setuptools import setup
with open('README.md') as f:
long_description = f.read()
setup(
name = 'gsmHat',
packages = ['gsmHat'],
version = '0.4.2',
license='MIT',
description = 'Using the Waveshare GSM/GPRS/GNSS Hat for Raspberry Pi with Python',
long_description = long_description,
long_description_content_type="text/markdown",
author = 'Tarek Tounsi',
author_email = 'software@tounsi.de',
url = 'https://github.com/Civlo85/gsmHat',
download_url = 'https://github.com/Civlo85/gsmHat/archive/v_04.tar.gz',
keywords = ['Waveshare', 'GSM', 'GPS', 'Raspberry', 'Pi'],
install_requires=[
'serial',
'datetime'
],
classifiers=[
'Development Status :: 3 - Alpha', # Chose either "3 - Alpha", "4 - Beta" or "5 - Production/Stable" as the current state of your package
'Intended Audience :: Developers',
'Topic :: Software Development :: Build Tools',
'License :: OSI Approved :: MIT License',
'Programming Language :: Python :: 3',
'Programming Language :: Python :: 3.4',
'Programming Language :: Python :: 3.5',
'Programming Language :: Python :: 3.6',
'Programming Language :: Python :: 3.7',
],
)