Jump to content

[Python] neuerdings Fehler bei Definition einer Callback-Funktion


Recommended Posts

Hallo,

 

hatte vor ein paar Tagen die Firmware meiner Bricks und Bricklets sowie die Bindings erneuert. Läuft auf Banana Pi. Bis dahin alles bestens.

Hatte heute einen Neustart des Pi, danach bricht das script bei Aufruf der Callback-Definitionen (set_<bricklet>_callback_period) ab.

 

Fehlermeldung jeweils:

 

Did not receive response for function 3 in time (-1)
2015-11-10 19:35:38,390 INFO     Time: 1447180538.39
2015-11-10 19:35:41,590 ERROR    Traceback (most recent call last):
2015-11-10 19:35:41,590 ERROR      File "tf_collectdata.py", line 227, in <module>
2015-11-10 19:35:41,591 ERROR    t2.set_temperature_callback_period(step * 1000)
2015-11-10 19:35:41,592 ERROR      File "build/bdist.linux-armv7l/egg/tinkerforge/bricklet_temperature.py", line 105, in set_temperature_callback_period
2015-11-10 19:35:41,593 ERROR      File "build/bdist.linux-armv7l/egg/tinkerforge/ip_connection.py", line 948, in send_request
2015-11-10 19:35:41,593 ERROR    tinkerforge.ip_connection

 

Die Verbindung zum Brick scheint noch zu funktionieren, da die Status-LED aus geht.

 

Mein Script sieht folgendermaßen aus:

 

#!/usr/bin/env python
# -*- coding: utf-8 -*-

__author__ = 'fs'


import logging
import logging.handlers
import argparse
import sys
import time
import mysql.connector
from tinkerforge.ip_connection import IPConnection
from tinkerforge.brick_master import Master
import tinkerforge.bricklet_temperature
import tinkerforge.bricklet_humidity
import tinkerforge.bricklet_barometer


# Deafults
LOG_FILENAME = "/var/log/tf/tf_collectdata.log"
LOG_LEVEL = logging.DEBUG # Could be e.g. "DEBUG" or "WARNING"

# Define and parse command line arguments
parser = argparse.ArgumentParser(description="service for collecting tinkerforge bricklet data")
parser.add_argument("-l", "--log", help="file to write log to (default '" + LOG_FILENAME + "')")

# If the log file is specified on the command line then override the default
args = parser.parse_args()
if args.log:
    LOG_FILENAME = args.log

# Configure logging to log to a file, making a new file at midnight and keeping the last 3 day's data
# Give the logger a unique name (good practice)
logger = logging.getLogger(__name__)
# Set the log level to LOG_LEVEL
logger.setLevel(LOG_LEVEL)
# Make a handler that writes to a file, making a new file at midnight and keeping 3 backups
handler = logging.handlers.TimedRotatingFileHandler(LOG_FILENAME, when="midnight", backupCount=3)
# Format each log message like this
formatter = logging.Formatter('%(asctime)s %(levelname)-8s %(message)s')
# Attach the formatter to the handler
handler.setFormatter(formatter)
# Attach the handler to the logger
logger.addHandler(handler)


# Messdaten alle 1min updaten
step = 60

hour = 60 * 60
day = 24 * hour
week = 7 * day
month = day * 30
quarter = month * 3
half = 365 * day / 2
year = 365 * day
times = [(3*hour,60), (12*hour,60), (day,60), (3*day,300)]

# Hoehe ueber NN fuer LE:
altitude_loc = 114
tg = 0.0065


tfbrick01_opts = {
    'host': "192.168.x.1",
    'port': 4223,
    'uid_master': "x",
    'uid_tempbricklet': "x",
    'uid_humbricklet': "x",
    'uid_pressbricklet': "x"
}

tfbrick02_opts = {
    'host': "192.168.x.2",
    'port': 4223,
    'uid_master': "y",
    'uid_tempbricklet': "y",
    'uid_humbricklet': "y"
}


mysql_opts = {
    'host': "192.168.x.6",
    'user': "user",
    'pass': "pass",
    'db': "tinkerforge"
    }



######

# Make a class we can use to capture stdout and sterr in the log
class MyLogger(object):
    def __init__(self, logger, level):
        """Needs a logger and a logger level."""
        self.logger = logger
        self.level = level

    def write(self, message):
        # Only log if there is a message (not just a new line)
        if message.rstrip() != "":
            self.logger.log(self.level, message.rstrip())

# Replace stdout with logging to file at INFO level
sys.stdout = MyLogger(logger, logging.INFO)
# Replace stderr with logging to file at ERROR level
sys.stderr = MyLogger(logger, logging.ERROR)


print("Time: " + str(time.time()))


#db = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
#dbcursor = db.cursor()

# Callback for temperature
def cbt1(temperature):
    print('temp1: ' + str(temperature/100.0) + ' °C.')
    value = temperature/100.0
    db = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
    dbcursor = db.cursor()
    dbcursor.execute("insert into rawvalues (dsid, rawvalue) values (1, %s)", (value, ))
    db.commit()
    dbcursor.close()
    db.close

def cbt2(temperature):
    print('temp2: ' + str(temperature/100.0) + ' °C.')
    value = temperature/100.0
    db = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
    dbcursor = db.cursor()
    dbcursor.execute("insert into rawvalues (dsid, rawvalue) values (3, %s)", (value, ))
    db.commit()
    dbcursor.close()
    db.close


# Callback for humidity
def cbh1(humidity):
    print('hum1:  ' + str(humidity/10.0) + ' %.')
    value = humidity/10.0
    db = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
    dbcursor = db.cursor()
    dbcursor.execute("insert into rawvalues (dsid, rawvalue) values (2, %s)", (value, ))
    db.commit()
    dbcursor.close()
    db.close

def cbh2(humidity):
    print('hum2:  ' + str(humidity/10.0) + ' %.')
    value = humidity/10.0
    db = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
    dbcursor = db.cursor()
    dbcursor.execute("insert into rawvalues (dsid, rawvalue) values (4, %s)", (value, ))
    db.commit()
    dbcursor.close()
    db.close


# Callback for air pressure
def cbp1(air_pressure):
    print('press1:  ' + str(air_pressure/1000.0) + ' mbar (raw).')
    
    # letzte Aussentemperatur holen (elv, also aus DB)
    dbx = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
    curx = dbx.cursor(buffered=True)
    #temps = curx.execute("select rawvalue from  rawvalues where dsid=5 order by timestamp desc limit 1")
    curx.execute("select rawvalue from  rawvalues where dsid=5 order by timestamp desc limit 1")
    row = curx.fetchone()
    if row is not None:
temp_location = float(row[0])
print('temp_loc:  ' + str(temp_location) + ' °C')
    #print('anz: ' + str(temps))
    #if temps > 0:
    #for tr in curx.fetchall():
    #temp_location = float(tr[0])
    curx.close()
    dbx.close()

    temp_nn = temp_location + tg * altitude_loc
#    value = air_pressure/1000.0/(1-tg * altitude_loc/temp_nn)**(0.03416/tg)
    value = air_pressure/1000.0/(1 - tg * altitude_loc / (273.15 + temp_location + tg * altitude_loc)) ** (0.034163 / tg)
    value = round(value,1)
    
    print('press1:  ' + str(value) + ' mbar (QFF).')
    db = mysql.connector.connect(host=mysql_opts['host'], user=mysql_opts['user'], password=mysql_opts['pass'], database=mysql_opts['db'])
    dbcursor = db.cursor()
    dbcursor.execute("insert into rawvalues (dsid, rawvalue) values (7, %s)", (value, ))
    db.commit()
    dbcursor.close()
    db.close


ipconb1 = IPConnection() # Create IP connection
ipconb2 = IPConnection() # Create IP connection

# Create device object
m1 = Master(tfbrick01_opts['uid_master'],ipconb1)
t1 = tinkerforge.bricklet_temperature.Temperature(tfbrick01_opts['uid_tempbricklet'], ipconb1)
h1 = tinkerforge.bricklet_humidity.Humidity(tfbrick01_opts['uid_humbricklet'], ipconb1)
p1 = tinkerforge.bricklet_barometer.Barometer(tfbrick01_opts['uid_pressbricklet'], ipconb1)

m2 = Master(tfbrick02_opts['uid_master'],ipconb2)
t2 = tinkerforge.bricklet_temperature.Temperature(tfbrick02_opts['uid_tempbricklet'], ipconb2)
h2 = tinkerforge.bricklet_humidity.Humidity(tfbrick02_opts['uid_humbricklet'], ipconb2)


ipconb1.connect(tfbrick01_opts['host'], tfbrick01_opts['port']) # Connect to brickd
ipconb2.connect(tfbrick02_opts['host'], tfbrick02_opts['port']) # Connect to brickd


# Don't use device before ipcon is connected

# set wifi power-mode to low
m1.set_wifi_power_mode(1)
m1.disable_status_led()
# Get callbacks with a period time of 60 seconds (1min)
t1.set_temperature_callback_period(step * 1000)     # <-- ab hier Fehler
h1.set_humidity_callback_period(step * 1000)
p1.set_air_pressure_callback_period(60 *1000)

m2.set_wifi_power_mode(1)
m2.disable_status_led()
# Get callbacks with a period time of 60 seconds (1min)
t2.set_temperature_callback_period(step * 1000)
h2.set_humidity_callback_period(step * 1000)


# Register threshold reached callback to function cb_reached
t1.register_callback(t1.CALLBACK_TEMPERATURE,cbt1)
h1.register_callback(h1.CALLBACK_HUMIDITY,cbh1)
p1.register_callback(p1.CALLBACK_AIR_PRESSURE,cbp1)

t2.register_callback(t2.CALLBACK_TEMPERATURE,cbt2)
h2.register_callback(h2.CALLBACK_HUMIDITY,cbh2)


next_call_time = time.time()
while True:
    next_call_time += 1
    time.sleep(next_call_time - time.time())


    #raw_input('Press key to exit\n') # Use input() in Python 3


#db.commit()
#dbcursor.close()
#db.close()
ipconb1.disconnect()
ipconb2.disconnect()

 

Hat da evtl jemand 'ne Idee?

 

Danke Euch.

Frank.

Link zu diesem Kommentar
Share on other sites

Hi,

 

zur Sicherheit habe ich das nochmal geprüft. Aber im Viewer ist alles ok.

 

Es ist ja nicht nur das eine Bricklet, welches Fehler wirft. Es sind alle "set_<bricklet>_callback_period" Aufrufe mit identischer Fehlermeldung. Ich habe die Fehlerausgabe nur ein wenig gekürzt (im Text stand's, war aber vlcht. nicht deutlich genug, sorry).

 

Und wie gesagt, das tauchte bei unveränderter Hardware nach einem Neustart des Banana auf. Vorher die tinkerforge Python Bindings geupdatet.

Link zu diesem Kommentar
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Gast
Reply to this topic...

×   Du hast formatierten Text eingefügt.   Formatierung jetzt entfernen

  Only 75 emoji are allowed.

×   Dein Link wurde automatisch eingebettet.   Einbetten rückgängig machen und als Link darstellen

×   Dein vorheriger Inhalt wurde wiederhergestellt.   Clear editor

×   Du kannst Bilder nicht direkt einfügen. Lade Bilder hoch oder lade sie von einer URL.

×
×
  • Neu erstellen...