5 from os import listdir,system
 
   6 from os.path import isfile, join
 
   8 from pprint import pprint
 
  10 from termios import tcflush, TCIOFLUSH
 
  12 from time import sleep,time
 
  14 from uuid import getnode
 
  16 from hashlib import md5
 
  23 from urllib import urlencode
 
  24 from StringIO import StringIO
 
  26 searchpath = '/dev/serial/by-id/'
 
  31 external_submit_interval = 320
 
  32 owm_submit_interval = 320
 
  33 expire_interval = 1200
 
  35 submit_time_owm = time()
 
  46   files = listdir(searchpath)
 
  49       return join(searchpath,f)
 
  54   ser = serial.Serial(path,baud,timeout)
 
  56     tcflush(ser,TCIOFLUSH);
 
  64 def read_loop(ser,callback):
 
  72     except KeyboardInterrupt:
 
  81     system("logger -t weathermon \""+str+"\"")
 
  83 def submit_narodmon(queue):
 
  85   param = { 'ID':"{:X}".format(getnode())}
 
  90     value = submit_queue[sensor]['val']
 
  91     timestamp = submit_queue[sensor]['timestamp']
 
  92     digest = md5(sensor).hexdigest()[:18]
 
  93     param[digest] = value;
 
  97   url = "http://narodmon.ru/post.php"
 
 101     response_buffer = StringIO()
 
 104     curl.setopt(curl.URL, url)
 
 105     curl.setopt(curl.WRITEFUNCTION, response_buffer.write)   
 
 106     curl.setopt(curl.POST, 1)
 
 107     curl.setopt(curl.POSTFIELDS, urlencode(param))
 
 112     response_value = response_buffer.getvalue()
 
 114     print_log('Narodmon response: '+response_value)
 
 120     exc_type, exc_value, exc_traceback = sys.exc_info()
 
 121     traceback.print_tb(exc_traceback, limit=1, file=sys.stdout)
 
 122     traceback.print_exception(exc_type, exc_value, exc_traceback,
 
 123                               limit=2, file=sys.stdout)  
 
 126 def submit_owm(queue):
 
 128   url = "http://openweathermap.org/data/post"
 
 129   params = {'name':owm_station, 'lat':owm_lat, 'long':owm_lon}
 
 134       params['temp'] = queue[owm_temp]['val']
 
 135       params['pressure'] = queue[owm_pres]['val']
 
 136       params['humidity'] = queue[owm_humi]['val']
 
 140     response_buffer = StringIO()
 
 143     curl.setopt(curl.URL, url)
 
 144     curl.setopt(curl.USERPWD, '%s:%s' % (owmuser, owmpasswd))
 
 145     curl.setopt(curl.WRITEFUNCTION, response_buffer.write)
 
 146     curl.setopt(curl.POST, 1)
 
 147     curl.setopt(curl.POSTFIELDS, urlencode(params))
 
 152     response_value = response_buffer.getvalue()
 
 154     print_log('Openweathermap response: '+response_value)
 
 160     exc_type, exc_value, exc_traceback = sys.exc_info()
 
 161     traceback.print_tb(exc_traceback, limit=1, file=sys.stdout)
 
 162     traceback.print_exception(exc_type, exc_value, exc_traceback,
 
 163                                   limit=2, file=sys.stdout)
 
 169   for key in submit_queue:
 
 170     if submit_queue[key]['timestamp'] < time()-expire_interval:
 
 171       print_log("Expired value for "+key)
 
 176 def submit_data(sensor_type,sensor_id,sensor_param,param_value):
 
 178   global submit_time_owm
 
 179   global external_submit_interval
 
 180   global owm_submit_interval
 
 182   c = database.cursor()
 
 183   c.execute('CALL meteo.submit_value(%s,%s,%s,%s,NULL)', (sensor_type,sensor_id,sensor_param,param_value))
 
 185   submit_queue[sensor_type+'.'+sensor_id+'.'+sensor_param]={'val':param_value,'timestamp':time()}
 
 186   if time()>submit_time+external_submit_interval:
 
 187     submit_narodmon(submit_queue)
 
 189   if owmuser and time()>submit_time_owm+owm_submit_interval:
 
 190     submit_owm(submit_queue)
 
 191     submit_time_owm=time()
 
 195 def process_str(str):
 
 196   print_log("Received: "+str)
 
 198     msg_type, msg_body = str.split(':')
 
 202     if msg_type == 'STATUS':
 
 203       print_log('Status: '+msg_body)
 
 204     elif msg_type == 'ERROR':
 
 205       print_log('Error: '+ msg_body)
 
 206     elif msg_type == 'SENSOR':
 
 207       sens = msg_body.split(',')
 
 212         key,value = rec.split('=')
 
 226           print_log('Type = '+sensor_type+', ID = '+sensor_id+', Param = '+key+', Value = '+sensor[key])
 
 227           submit_data(sensor_type,sensor_id,key,sensor[key])
 
 229           print_log('Error: got empty parameter value for '+sensor_type+'.'+sensor_id+'.'+key)
 
 231     print_log('Exception processing...')
 
 232     exc_type, exc_value, exc_traceback = sys.exc_info()
 
 233     traceback.print_tb(exc_traceback, limit=1, file=sys.stdout)
 
 234     traceback.print_exception(exc_type, exc_value, exc_traceback,
 
 235                               limit=5, file=sys.stdout)  
 
 248   ser = open_port(path)
 
 249   read_loop(ser,process_str)
 
 260       database = MySQLdb.connect(host=dbhost,user=dbuser,passwd=dbpasswd,use_unicode=True,connect_timeout=10)
 
 261       database.set_character_set('utf8')
 
 262       c = database.cursor()
 
 263       c.execute('SET NAMES utf8;')
 
 264       print_log("Database connected...")
 
 269       print_log("Error connecting database")
 
 277   cfg = ConfigParser.RawConfigParser(allow_no_value=True)
 
 278   cfg.readfp(open('/etc/weathermon.conf'))
 
 279   dbhost = cfg.get("mysql","host")
 
 280   dbuser = cfg.get("mysql","user")
 
 281   dbpasswd = cfg.get("mysql","passwd")
 
 283     path = cfg.get("serial","port");
 
 287     serialnum = cfg.get("serial","id")
 
 291     logging = cfg.get("logging","enabled")
 
 294   owmuser = cfg.get("openweathermap","user")
 
 295   owmpasswd = cfg.get("openweathermap",'passwd')
 
 297     owm_temp = cfg.get("openweathermap",'temp')
 
 298     owm_pres = cfg.get("openweathermap",'pres')
 
 299     owm_humi = cfg.get("openweathermap",'humi')
 
 300     owm_lat = cfg.get("openweathermap",'lat')
 
 301     owm_lon = cfg.get("openweathermap",'lon')
 
 302     owm_station = cfg.get("openweathermap",'station')
 
 307   print_log("Cannot intialize system")
 
 310 if __name__ == "__main__":
 
 313   sys.setdefaultencoding('utf-8')