Exemple #1
0
class DisplayWebThing(Thing):
    # regarding capabilities refer https://iot.mozilla.org/schemas
    # there is also another schema registry http://iotschema.org/docs/full.html not used by webthing

    def __init__(self, name: str, description: str, lcd: BaseCharLCD):
        Thing.__init__(self, 'urn:dev:ops:lcddisplay-1',
                       'Display ' + name + ' Controller', ['Display'],
                       description)

        self.display = Display(lcd, self.__update_text)

        self.display_text = Value("")
        self.add_property(
            Property(self,
                     'displayed_text',
                     self.display_text,
                     metadata={
                         'title': 'Displayed text',
                         'type': 'string',
                         'description': 'Displayed text',
                         'readOnly': True,
                     }))

        self.upper_layer_text = Value(
            "",
            self.display.panel(Display.LAYER_UPPER).update_text)
        self.add_property(
            Property(self,
                     'upper_layer_text',
                     self.upper_layer_text,
                     metadata={
                         'title': 'Upper layer text',
                         'type': 'string',
                         'description': 'The text of the upper layer',
                         'readOnly': False,
                     }))

        self.upper_layer_text_ttl = Value(
            -1,
            self.display.panel(Display.LAYER_UPPER).update_ttl)
        self.add_property(
            Property(
                self,
                'upper_layer_text_ttl',
                self.upper_layer_text_ttl,
                metadata={
                    'title': 'Upper layer text (time-to-live)',
                    'type': 'integer',
                    'description':
                    'The time-to-live of the upper layer. Value -1 deactivates ttl',
                    'readOnly': False,
                }))

        self.middle_layer_text = Value(
            "",
            self.display.panel(Display.LAYER_MIDDLE).update_text)
        self.add_property(
            Property(self,
                     'middle_layer_text',
                     self.middle_layer_text,
                     metadata={
                         'title': 'Middle layer text',
                         'type': 'string',
                         'description': 'The text of the middle layer',
                         'readOnly': False,
                     }))

        self.middle_layer_text_ttl = Value(
            -1,
            self.display.panel(Display.LAYER_MIDDLE).update_ttl)
        self.add_property(
            Property(
                self,
                'middle_layer_text_ttl',
                self.middle_layer_text_ttl,
                metadata={
                    'title': 'Middle layer text (time-to-live)',
                    'type': 'integer',
                    'description':
                    'The time-to-live of the middle layer. Value -1 deactivates ttl',
                    'readOnly': False,
                }))

        self.lower_layer_text = Value(
            "",
            self.display.panel(Display.LAYER_LOWER).update_text)
        self.add_property(
            Property(self,
                     'lower_layer_text',
                     self.lower_layer_text,
                     metadata={
                         'title': 'Lower layer text',
                         'type': 'string',
                         'description': 'The text of the lower layer',
                         'readOnly': False,
                     }))

        self.lower_layer_text_ttl = Value(
            -1,
            self.display.panel(Display.LAYER_LOWER).update_ttl)
        self.add_property(
            Property(
                self,
                'lower_layer_text_ttl',
                self.lower_layer_text_ttl,
                metadata={
                    'title': 'Lower layer text (time-to-live)',
                    'type': 'integer',
                    'description':
                    'The time-to-live of the lower layer. Value -1 deactivates ttl',
                    'readOnly': False,
                }))

        self.ioloop = tornado.ioloop.IOLoop.current()

    def __update_text(self):
        self.ioloop.add_callback(self.__update_text_props)

    def __update_text_props(self):
        self.display_text.notify_of_external_update(self.display.text)
        self.upper_layer_text.notify_of_external_update(
            self.display.panel(Display.LAYER_UPPER).text)
        self.upper_layer_text_ttl.notify_of_external_update(
            self.display.panel(Display.LAYER_UPPER).ttl)
        self.middle_layer_text.notify_of_external_update(
            self.display.panel(Display.LAYER_MIDDLE).text)
        self.middle_layer_text_ttl.notify_of_external_update(
            self.display.panel(Display.LAYER_MIDDLE).ttl)
        self.lower_layer_text.notify_of_external_update(
            self.display.panel(Display.LAYER_LOWER).text)
        self.lower_layer_text_ttl.notify_of_external_update(
            self.display.panel(Display.LAYER_LOWER).ttl)
Exemple #2
0
class ExtEnvironSensor(Thing):
    """An external environment sensor which updates every few seconds."""
    global h

    def __init__(self, tbsense):
        Thing.__init__(
            self, 'urn:dev:ops:my-tb-thing-1234',
            'My Thunderboard Sense Thing', [
                'TemperatureSensor', 'MultiLevelSensor', 'MultiLevelSensor',
                'MultiLevelSensor', 'MultiLevelSensor', 'MultiLevelSensor',
                'MultiLevelSensor'
            ], 'A web connected environment sensor')

        self.tbsense = tbsense

        #temperature sensor
        self.temp = Value(0.0)
        self.add_property(
            Property(self,
                     'temperature',
                     self.temp,
                     metadata={
                         '@type': 'TemperatureProperty',
                         'title': 'Temperature',
                         'type': 'number',
                         'description': 'The ambient temperature in C',
                         'minimum': -40.0,
                         'maximum': 100.0,
                         'unit': 'Celsius',
                         'readOnly': True,
                         'multipleOf': 0.1,
                     }))
        #humidity sensor
        self.humidity = Value(0.0)
        self.add_property(
            Property(self,
                     'humidity',
                     self.humidity,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Humidity',
                         'type': 'number',
                         'description': 'The level of rel. humidity',
                         'minimum': 0,
                         'maximum': 100,
                         'unit': '%',
                         'readOnly': True,
                         'multipleOf': 0.1,
                     }))
        #ambient light sensor
        # self.amb_light = Value(0.0)
        # self.add_property(
        #     Property(self, 'ambient light', self.amb_light,
        #             metadata={
        #                       '@type': 'LevelProperty',
        #                       'title': 'Ambient Light',
        #                       'type': 'number',
        #                       'description': 'The level of ambient light',
        #                       'minimum': 0,
        #                       'maximum': 100000,
        #                       'unit': 'lux',
        #                       'readOnly': True,
        #                     }))
        #UV index
        # self.uv_index = Value(0.0)
        # self.add_property(
        #     Property(self, 'UV index', self.uv_index,
        #             metadata={
        #                       '@type': 'LevelProperty',
        #                       'title': 'UV index',
        #                       'type': 'number',
        #                       'description': 'The level of UV index',
        #                       'minimum': 0,
        #                       'maximum': 50,
        #                       'readOnly': True,
        #                     }))
        #barometric pressure
        self.pressure = Value(0.0)
        self.add_property(
            Property(self,
                     'pressure',
                     self.pressure,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Barometric pressure',
                         'type': 'number',
                         'description': 'The level of barometric pressure',
                         'minimum': 0,
                         'maximum': 1.2,
                         'unit': 'atm',
                         'readOnly': True,
                         'multipleOf': 0.01,
                     }))
        #CO2 level
        self.co2 = Value(0)
        self.add_property(
            Property(self,
                     'co2',
                     self.co2,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'CO2 level',
                         'type': 'number',
                         'description': 'The level of CO2',
                         'minimum': 0,
                         'maximum': 5000,
                         'unit': 'ppm',
                         'readOnly': True,
                     }))
        #VOC level
        self.voc = Value(0)
        self.add_property(
            Property(self,
                     'voc',
                     self.voc,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'VOC content',
                         'type': 'number',
                         'description': 'VOC content of air',
                         'minimum': 0,
                         'maximum': 5000,
                         'unit': 'ppb',
                         'readOnly': True,
                     }))
        #Connection state
        self.connctd = Value(False)
        self.add_property(
            Property(self,
                     'connctd',
                     self.connctd,
                     metadata={
                         '@type': 'OnOffProperty',
                         'title': 'Connection',
                         'type': 'boolean',
                         'description': 'Conection status to Thunderboard',
                         'readOnly': True,
                     }))

        syslog.syslog('Starting the sensor update looping task')
        self.enviro_task = get_event_loop().create_task(self.update_TbSense())

    async def update_TbSense(self):
        while True:
            try:
                if self.tbsense.getConnState() == 'conn':
                    temp = self.tbsense.readTemperature() - 6.0
                    self.temp.notify_of_external_update(temp)
                    self.humidity.notify_of_external_update(
                        self.tbsense.readHumidity())
                    # self.amb_light.notify_of_external_update(self.tbsense.readAmbientLight())
                    # self.uv_index.notify_of_external_update(self.tbsense.readUvIndex())
                    self.co2.notify_of_external_update(self.tbsense.readCo2())
                    self.voc.notify_of_external_update(self.tbsense.readVoc())
                    self.pressure.notify_of_external_update(
                        round(self.tbsense.readPressure() / 1000, 2))
                    self.connctd.notify_of_external_update(True)
                    await sleep(h)
                else:
                    self.connctd.notify_of_external_update(False)
                    raise BTLEDisconnectError("Connection lost!")
            except (BTLEDisconnectError, BTLEInternalError):
                syslog.syslog('Trying to reconnect...')
                while True:
                    try:
                        #try to reconnect same device
                        await sleep(1)
                        self.tbsense.peri.connect(self.tbsense.dev.addr,
                                                  self.tbsense.dev.addrType)
                        self.tbsense.storeCharacteristics()
                    except:
                        continue
                    else:
                        syslog.syslog('Reconnected!')
                        self.connctd.notify_of_external_update(True)
                        break
            except CancelledError:
                break

    def cancel_tasks(self):
        self.enviro_task.cancel()
        get_event_loop().run_until_complete(self.enviro_task)
Exemple #3
0
class LedStrip(Thing):
    """A LED-Strip in the entry of my upper Level"""
    def __init__(self, _location, _main_loop):
        self.location = _location
        self.main_loop = _main_loop
        self.id = f'urn:dev:ops:{self.location}-vorraum-led'
        self.name = f'{self.location}-LED_Strip'
        Thing.__init__(self, self.id, self.name, ['OnOffSwitch', 'Light'],
                       'A web connected LED-Strip')
        # GPIO18 (P26) pwm on Linkit Smart 7688
        self.pwm = mraa.Pwm(26)
        self.pwm.period_us(20000)  # 20ms period ==> 50Hz
        self.pwm.enable(True)  # Start sending PWM signal

        # relay2 (P18) on Linkit Smart 7688
        self.relay2 = mraa.Gpio(18)
        # relay1 (P19) on Linkit Smart 7688
        self.relay1 = mraa.Gpio(19)
        self.relay2.dir(mraa.DIR_OUT)  # set as OUTPUT pin
        # set as INPUT pin, its a pullup, so its High when the switch is open.
        self.relay1.dir(mraa.DIR_IN)
        self.relay1_read()  # get initial Value of Relay1
        self.r1_previous = False

        self.main_loop_time = None
        self.async_timeout = None

        self.locality = LocationInfo('Zürich', 'Switzerland', 'Europe/Zurich',
                                     47.39, 8.07)
        logging.info(
            f'Information for {self.locality.name}/{self.locality.region}, '
            f'Timezone: {self.locality.timezone}, '
            f'Latitude: {self.locality.latitude:.02f}; '
            f'Longitude: {self.locality.longitude:.02f}')
        self.day_time_start = sun.sunrise(
            self.locality.observer,
            date=datetime.now(),
            tzinfo=self.locality.timezone) - timedelta(minutes=30)
        logging.debug(f'LedStrip: day_time_start:{self.day_time_start}')
        self.day_time_stop = sun.sunset(
            self.locality.observer,
            date=datetime.now(),
            tzinfo=self.locality.timezone) + timedelta(minutes=30)
        logging.debug(f'LedStrip: day_time_stop:{self.day_time_stop}')

        self.state = Value(self.get_state(), self.toggle_digitalswitch)
        self.add_property(
            Property(self,
                     'digitalswitch',
                     self.state,
                     metadata={
                         '@type': 'OnOffProperty',
                         'title': f'{self.name}-digitalswitch',
                         'type': 'boolean',
                         'description': 'Whether the Strip is turned on',
                     }))

        self.brightness = Value(self.get_brightness(), self.set_brightness)
        self.add_property(
            Property(self,
                     'brightness',
                     self.brightness,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Helligkeit',
                         'type': 'integer',
                         'description': 'The level of light from 0-100%',
                         'minimum': 0,
                         'maximum': 100,
                         'unit': 'percent',
                     }))

        self.add_available_action(
            'fade', {
                'title': 'Helligkeitswert über eine Zeitdauer einstellen',
                'description': 'Fade the lamp to a given level',
                'input': {
                    'type': 'object',
                    'required': [
                        'brightness',
                        'duration',
                    ],
                    'properties': {
                        'brightness': {
                            'type': 'integer',
                            'minimum': 0,
                            'maximum': 100,
                            'unit': 'percent',
                        },
                        'duration': {
                            'type': 'integer',
                            'minimum': 1,
                            'unit': 'milliseconds',
                        },
                    },
                },
            }, FadeLedStrip)

        self.motion_detection_delay = Value(self.get_motion_detection_delay(),
                                            self.set_motion_detection_delay)
        self.add_property(
            Property(self,
                     'motion_detection_delay',
                     self.motion_detection_delay,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Verzögertes Aus bei Bewegung (in Minuten)',
                         'type': 'integer',
                         'description': 'The delay in minutes',
                         'minimum': 0,
                         'maximum': 20,
                         'unit': 'minutes',
                     }))

        self.motion_detection_active = Value(
            self.get_motion_detection_active(),
            self.set_motion_detection_active)
        self.add_property(
            Property(self,
                     'motion_detection_active',
                     self.motion_detection_active,
                     metadata={
                         '@type': 'BooleanProperty',
                         'title': 'Auf Bewegung reagieren?',
                         'type': 'boolean',
                         'description': 'Set Motion detection active or not',
                     }))

        self.motion_detection_follower = Value(self.get_motion(),
                                               self.set_motion)
        self.add_property(
            Property(self,
                     'motion_detection_follower',
                     self.motion_detection_follower,
                     metadata={
                         '@type': 'MotionProperty',
                         'title': 'Bewegungs Sensor',
                         'type': 'boolean',
                         'description': 'motion=true, nomotion=false',
                     }))

        self.timer = tornado.ioloop.PeriodicCallback(self.get_r1, 1000)
        self.timer.start()

    def get_brightness(self):
        """get the level from mraa.pwm"""
        brightness = round(self.pwm.read() * 100)
        logging.debug(f'LedStrip: get_brightness is set to: {brightness}')
        return brightness

    def set_brightness(self, brightness):
        """set the level with mraa"""
        self.pwm.write(round((brightness / 100), 2))
        led_on = self.get_property('digitalswitch')
        if brightness < 1 and led_on is True:
            self.set_property('digitalswitch', False)
        elif brightness >= 1 and led_on is False:
            self.set_property('digitalswitch', True)
        logging.info(f'LedStrip: Set Brightness to {brightness}')
        return brightness

    def relay1_read(self):
        relay1 = bool(self.relay1.read())
        if relay1 is True:
            relay1 = False
        elif relay1 is False:
            relay1 = True
        return relay1

    def get_r1(self):
        """ only if footswitch changes """
        r1 = self.relay1_read()
        if r1 != self.r1_previous:
            state = self.get_state()
            # if state:
            #     self.fade_brightness_up(self.get_property('brightness'), 4000, 80)
            # else:
            #     self.fade_brightness_down(self.get_property('brightness'), 4000, 0)
            self.state.notify_of_external_update(state)
        self.r1_previous = r1

    def get_state(self):
        """
        The manual switch is connected to a multiway switch made of two Relays
        with 3-ways.
        https://en.wikipedia.org/wiki/Multiway_switching#Traveler_system
        """
        footswitch = bool(self.relay1_read())
        digitalswitch = bool(self.relay2.read())
        state = footswitch ^ digitalswitch
        logging.info(f'LedStrip: get_state: is set to {state}')
        return state

    def toggle_digitalswitch(self, state):
        """
        switch to turn on/off LedStrip.
        """
        s = self.relay2.read()
        self.relay2.write(not s)
        logging.info('LedStrip: toggle_digitalswitch called '
                     f'with state:{state} set to {s}')

    def motion(self):
        """ MOTION SENSOR calls this when ever it triggers """
        logging.debug('LedStrip: motion: starts')
        date_time_now = datetime.now().time()
        logging.debug('LedStrip: motion: called self.date_time_now:'
                      f'{date_time_now}')
        day_start = self.day_time_start.time()
        logging.debug(f'LedStrip: motion: called day_start:{day_start}')
        day_end = self.day_time_stop.time()
        logging.debug(f'LedStrip: motion: called day_end:{day_end}')
        if date_time_now > day_start and date_time_now < day_end:
            self.day_time = True
            logging.debug('LedStrip: motion: called during the Day')
        else:
            self.day_time = False
            logging.debug('LedStrip: motion: called in the Night')
        if not self.day_time:
            motion_active = self.get_property('motion_detection_active')
            logging.debug('LedStrip: motion: called while motion_active:'
                          f'{motion_active}')
            if motion_active:
                logging.debug('LedStrip: motion: called on not day_time '
                              'and Motion was activated, future add_callback '
                              'awaits interrupt_call_back now')
                self.main_loop.add_callback(self.interrupt_call_back)
            else:
                logging.debug('LedStrip: motion: Motion is not activated')
        logging.debug('LedStrip: motion: end')

    def interrupt_call_back(self):
        logging.info('LedStrip: interrupt_call_back: starts, '
                     f'async_timeout:{self.async_timeout}')
        if self.async_timeout:
            self.main_loop.remove_timeout(self.async_timeout)
            logging.debug('LedStrip: interrupt_call_back: timeout was removed,'
                          f' async_timeout:{self.async_timeout}')
        digitalswitch = self.get_property('digitalswitch')
        if digitalswitch:
            logging.debug(f'LedStrip: interrupt_call_back: '
                          f'digitalswitch is {digitalswitch} '
                          'light is already ON')
        else:
            logging.debug(f'LedStrip: interrupt_call_back: '
                          f'digitalswitch is {digitalswitch} '
                          'light now turns ON')
            #self.set_brightness(self, 1)
            self.set_property('digitalswitch', True)
        delay_seconds = self.get_delay_seconds()
        timeout_delta = self.main_loop.time() + delay_seconds
        timeout_delta_human = time.strftime('%H:%M:%S',
                                            time.gmtime(timeout_delta))
        logging.debug(f'LedStrip: interrupt_call_back:'
                      f'Light will stay on for {delay_seconds}s '
                      f'and turns OFF at:{timeout_delta_human}')
        self.async_timeout = self.main_loop.add_timeout(
            timeout_delta, self.interrupt_call_timeout)
        logging.debug('LedStrip: interrupt_call_back: end')

    def interrupt_call_timeout(self):
        logging.info('LedStrip: interrupt_call_timeout: called')
        digitalswitch = self.get_property('digitalswitch')
        footswitch = self.relay1_read()
        if (digitalswitch) and (not footswitch):
            self.set_property('digitalswitch', False)
        logging.debug('LedStrip: interrupt_call_timeout: '
                      f'async_timeout: {self.async_timeout}')
        self.main_loop.remove_timeout(self.async_timeout)
        logging.debug('LedStrip: interrupt_call_timeout '
                      f'async_timeout removed: {self.async_timeout}')
        self.async_timeout = False

    def fade_brightness_up(self, brightness_now, duration, brightness_after):
        steps = brightness_after - brightness_now
        if steps < 1:
            steps = 1
        if steps > 100:
            steps = 100
        delay_ms = duration / steps
        while brightness_after > self.get_property('brightness'):
            self.set_property('brightness',
                              self.get_property('brightness') + 1)
            time.sleep(delay_ms / 1000)

    def fade_brightness_down(self, brightness_now, duration, brightness_after):
        steps = brightness_now - brightness_after
        if steps < 1:
            steps = 1
        if steps > 100:
            steps = 100
        delay_ms = duration / steps
        while brightness_after < self.get_property('brightness'):
            self.set_property('brightness',
                              self.get_property('brightness') - 1)
            time.sleep(delay_ms / 1000)

    def get_delay_seconds(self):
        delay_minutes = self.get_property('motion_detection_delay')
        delay_seconds = delay_minutes * 60
        logging.debug(f'LedStrip: get_delay_seconds is {delay_seconds}')
        return delay_seconds

    def get_motion(self):
        logging.debug('LedStrip: get_motion: get_motion_follower')
        value = self.get_property('motion_detection_follower')
        if value is None:
            logging.debug(f'LedStrip: get_motion: '
                          f'get_motion_detection_follower is {value}')
            self.set_property('motion_detection_follower', False)
        value = self.get_property('motion_detection_follower')
        logging.debug(
            f'LedStrip: get_motion: get_motion_detection_follower is {value}')
        return value

    def set_motion(self, value):
        if value:
            logging.debug('LedStrip: set_motion before set_motion_follower '
                          f'(LedStrip): {value}')
            self.motion()
            logging.debug('LedStrip: set_motion after set_motion_follower '
                          f'(LedStrip): {value}')
        else:
            logging.debug('LedStrip: set_motion is False we do nothing more '
                          f'(LedStrip) set_motion: {value}')

    def get_motion_detection_active(self):
        value = self.get_property('motion_detection_active')
        if value is None:
            logging.info(f'LedStrip: get_motion_detection_active: '
                         f'setting: True because {value}')
            return True
        return value

    def set_motion_detection_active(self, value):
        logging.info(f'LedStrip: set_motion_detection_active to {value}')

    def get_motion_detection_delay(self):
        value = self.get_property('motion_detection_delay')
        if value is None:
            logging.info(
                f'get_motion_detection_delay setting to 2 because {value}')
            return 2
        return value

    def set_motion_detection_delay(self, value):
        logging.info(f'LedStrip: set_motion_detection_delay to {value}')

    """ END OF LED STRIP THING """

    def cancel_led_strip_async_tasks(self):
        logging.info('LedStrip: stopping the status update loop task')
        self.timer.stop()
Exemple #4
0
class VorraumNode(Thing):
    """A node in the entry of my upper Level"""
    def __init__(self, _location, _w1_device_id_list):
        self.location = _location
        self.id = f'urn:dev:ops:{self.location}-vorraum-node'
        self.name = f'{self.location}-node_functions'
        self.w1_device_id_list = _w1_device_id_list
        Thing.__init__(self, self.id, self.name, ['EnergyMonitor'],
                       'A web connected node')
        self.ina219 = ina219.INA219(busnum=0, address=0x40)
        self.power = Value(0.0)
        self.add_property(
            Property(self,
                     f'{self.name}-power',
                     self.power,
                     metadata={
                         '@type': 'InstantaneousPowerProperty',
                         'title': f'{self.name}-Power',
                         'type': 'float',
                         'multipleOf': 0.01,
                         'description': 'the power used by this node',
                     }))
        self.volt = Value(0.0)
        self.add_property(
            Property(self,
                     f'{self.name}-voltage',
                     self.volt,
                     metadata={
                         '@type': 'VoltageProperty',
                         'title': f'{self.name}-Voltage',
                         'type': 'float',
                         'multipleOf': 0.01,
                         'description': 'the voltage used by this node',
                     }))
        self.current = Value(0.0)
        self.add_property(
            Property(self,
                     f'{self.name}-current',
                     self.current,
                     metadata={
                         '@type': 'CurrentProperty',
                         'title': f'{self.name}-Current',
                         'type': 'float',
                         'multipleOf': 0.01,
                         'description': 'the current used by this node',
                     }))
        self.temperature = Value(0.0)
        self.add_property(
            Property(self,
                     f'{self.name}-Temperature',
                     self.temperature,
                     metadata={
                         '@type': 'TemperatureProperty',
                         'title': f'{self.name}-Temperature',
                         'type': 'float',
                         'multipleOf': 0.01,
                         'description': 'the temperature in the case',
                     }))
        self.timer = tornado.ioloop.PeriodicCallback(self.get_sensors, 300000)
        self.timer.start()

    def get_sensors(self):
        self.get_power()
        self.get_temperature()

    def get_power(self):
        logging.info("get_power")
        try:
            bus_voltage = self.ina219.get_bus_voltage_mV()
            self.volt.notify_of_external_update(bus_voltage / 1000)
            curent = self.ina219.get_current_mA()
            self.current.notify_of_external_update(curent / 1000)
            milliwats = self.ina219.get_power_mW()
            self.power.notify_of_external_update(milliwats / 1000)
        except AssertionError as e:
            logging.error(repr(e))

    def get_temperature(self):
        logging.info('get_temperature')
        number_of_device_ids = len(self.w1_device_id_list)
        if number_of_device_ids < 1:
            logging.error('get_temperature:no w1 device detected')
            return
        for device in self.w1_device_id_list:
            logging.info(f'get_temperature:reading w1 device {device}. '
                         f'{number_of_device_ids} to been read')
            temperature = self.get_temperature_read_one(device)
            self.temperature.notify_of_external_update(temperature)

    def get_temperature_read_one(self, temp_sensor_id):
        try:
            logging.info(f'get_temperature_read_one of {temp_sensor_id}')
            # read 1-wire slave file from a specific device
            file_name = "/sys/bus/w1/devices/" + temp_sensor_id + "/w1_slave"
            file = open(file_name)
            filecontent = file.read()
            file.close()
            # read temperature values and convert to readable float
            stringvalue = filecontent.split("\n")[1].split(" ")[9]
            sensorvalue = float(stringvalue[2:]) / 1000
            temperature = '%6.2f' % sensorvalue
            return temperature
        except Exception:
            logging.warn('get_temperature_read_one: '
                         f'not able to read from: {temp_sensor_id}')

    def cancel_node_async_tasks(self):
        logging.info('stopping the node update loop task')
        self.timer.stop()
Exemple #5
0
class WeatherstationBME680(Thing):
    def __init__(self):
        Thing.__init__(self, 'Indoor Weatherstation',
                       ['MultiLevelSensor', 'TemperatureSensor'],
                       'A web connected weatherstation')

        self.level = Value(0.0)
        self.add_property(
            Property(self,
                     'level',
                     self.level,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Air Quality',
                         'type': 'number',
                         'description': 'The current air quality',
                         'minimum': 0,
                         'maximum': 100,
                         'unit': 'percent',
                         'readOnly': True,
                     }))

        self.humidity = Value(0.0)
        self.add_property(
            Property(self,
                     'humidity',
                     self.humidity,
                     metadata={
                         'title': 'Humidity',
                         'type': 'number',
                         'description': 'Humidity in %',
                         'minimum': 0,
                         'maximum': 100,
                         'unit': 'percent',
                         'readOnly': True,
                     }))

        self.temperature = Value(0.0)
        self.add_property(
            Property(self,
                     'temperature',
                     self.temperature,
                     metadata={
                         '@type': 'TemperatureProperty',
                         'title': 'Temperature',
                         'type': 'number',
                         'description': 'The current temperature',
                         'minimum': -20,
                         'maximum': 80,
                         'unit': 'degree celsius',
                         'readOnly': True,
                     }))

        self.pressure = Value(0.0)
        self.add_property(
            Property(self,
                     'pressure',
                     self.pressure,
                     metadata={
                         'title': 'Air Pressure',
                         'type': 'number',
                         'description': 'The current air pressure',
                         'minimum': 600,
                         'maximum': 1200,
                         'unit': 'hPa',
                         'readOnly': True,
                     }))

        logging.debug('starting the sensor update looping task')
        self.timer = tornado.ioloop.PeriodicCallback(self.update_levels, 3000)
        self.timer.start()

    def update_levels(self):
        if sensorBME680.sensor.get_sensor_data():
            new_level = sensorBME680.update_air_quality()
            logging.debug('setting new air quality: %s', new_level)
            self.level.notify_of_external_update(new_level)

            new_humidity = sensorBME680.update_humidity()
            logging.debug('setting new humidity: %s', new_humidity)
            self.humidity.notify_of_external_update(new_humidity)

            new_temperature = sensorBME680.update_temperature()
            logging.debug('setting new temperature: %s', new_temperature)
            self.temperature.notify_of_external_update(new_temperature)

            new_pressure = sensorBME680.update_pressure()
            logging.debug('setting new air pressure: %s', new_pressure)
            self.pressure.notify_of_external_update(new_pressure)

    def cancel_update_level_task(self):
        self.timer.stop()
Exemple #6
0
class MotionSensor(Thing):

    # regarding capabilities refer https://iot.mozilla.org/schemas
    # there is also another schema registry http://iotschema.org/docs/full.html not used by webthing

    def __init__(self, gpio_number, name, description):
        Thing.__init__(self, 'urn:dev:ops:motionSensor-1',
                       'Motion ' + name + ' Sensor', ['MotionSensor'],
                       description)

        self.gpio_number = gpio_number
        GPIO.setmode(GPIO.BCM)
        GPIO.setup(self.gpio_number, GPIO.IN)
        GPIO.add_event_detect(self.gpio_number,
                              GPIO.BOTH,
                              callback=self.__update,
                              bouncetime=5)
        self.is_motion = False

        self.motion = Value(False)
        self.add_property(
            Property(self,
                     'motion',
                     self.motion,
                     metadata={
                         '@type': 'MotionProperty',
                         'title': 'Motion detected',
                         "type": "boolean",
                         'description':
                         'Whether ' + name + ' motion is detected',
                         'readOnly': True,
                     }))

        self.last_motion = Value(datetime.now().isoformat())
        self.add_property(
            Property(self,
                     'motion_last_seen',
                     self.last_motion,
                     metadata={
                         'title': 'Motion last seen',
                         "type": "string",
                         'unit': 'datetime',
                         'description':
                         'The ISO 8601 date time of last movement',
                         'readOnly': True,
                     }))
        self.ioloop = tornado.ioloop.IOLoop.current()

    def __update(self, channel):
        if GPIO.input(self.gpio_number):
            logging.info("motion detected")
            self.ioloop.add_callback(self.__update_motion_prop, True)
        else:
            self.ioloop.add_callback(self.__update_motion_prop, False)

    def __update_motion_prop(self, is_motion):
        if is_motion:
            self.motion.notify_of_external_update(True)
            self.last_motion.notify_of_external_update(
                datetime.now().isoformat())
        else:
            self.motion.notify_of_external_update(False)
Exemple #7
0
class AnwingWebThing(Thing):

    # regarding capabilities refer https://iot.mozilla.org/schemas
    # there is also another schema registry http://iotschema.org/docs/full.html not used by webthing

    def __init__(self, description: str, awning: Awning):
        Thing.__init__(self, 'urn:dev:ops:anwing-TB6612FNG',
                       'Awning ' + awning.name + " Controller",
                       ['MultiLevelSensor'], description)
        self.awning = awning
        self.awning.register_listener(WebThingAwningPropertyListener(self))

        self.target_position = Value(0, self.__target_position)
        self.add_property(
            Property(self,
                     'target_position',
                     self.target_position,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Awning target position',
                         "type": "integer",
                         "minimum": 0,
                         "maximum": 100,
                         "unit": "percent",
                         'description': 'awning target position'
                     }))

        self.current_position = Value(0)
        self.add_property(
            Property(self,
                     'current_position',
                     self.current_position,
                     metadata={
                         '@type': 'LevelProperty',
                         'title': 'Awning current position',
                         "type": "integer",
                         'minimum': 0,
                         'maximum': 100,
                         "unit": "percent",
                         'readOnly': True,
                         'description': 'awning current position'
                     }))

        self.retracting = Value(0)
        self.add_property(
            Property(self,
                     'retracting',
                     self.retracting,
                     metadata={
                         '@type': 'BooleanProperty',
                         'title': 'Awning is retracting',
                         "type": "boolean",
                         'readOnly': True,
                         'description': 'Awning is retracting'
                     }))

        self.extending = Value(0)
        self.add_property(
            Property(self,
                     'extending',
                     self.extending,
                     metadata={
                         '@type': 'BooleanProperty',
                         'title': 'Awning is extending',
                         "type": "boolean",
                         'readOnly': True,
                         'description': 'Awning is extending'
                     }))

        self.ioloop = tornado.ioloop.IOLoop.current()

    def __target_position(self, new_postion):
        self.awning.set_target_position(new_postion)

    def set_current_position(self, value):
        self.current_position.notify_of_external_update(value)
        logging.debug(self.awning.name + " position " + str(value) +
                      " reached (target=" + str(self.target_position.get()) +
                      ")")

    def set_retracting(self, value):
        self.retracting.notify_of_external_update(value)

    def set_extending(self, value):
        self.extending.notify_of_external_update(value)
Exemple #8
0
class DhtSensor(Thing):

    # regarding capabilities refer https://iot.mozilla.org/schemas
    # there is also another schema registry http://iotschema.org/docs/full.html not used by webthing

    def __init__(self, gpio_number: int, description: str):
        Thing.__init__(self, 'urn:dev:ops:dhtSensor-1',
                       'Humidity and Temperature Sensor',
                       ['TemperatureSensor', 'HumiditySensor'], description)

        self.sensor = Adafruit_DHT.DHT22
        self.gpio_number = gpio_number
        self.humidity = Value(0.0)
        self.add_property(
            Property(self,
                     'humidity',
                     self.humidity,
                     metadata={
                         '@type': 'HumidityProperty',
                         'title': 'Humidity',
                         'type': 'number',
                         'description': 'The current humidity from 0%-100%',
                         'minimum': 0,
                         'maximum': 100,
                         'unit': 'percent',
                         'readOnly': True,
                     }))

        self.temperature = Value(0)
        self.add_property(
            Property(self,
                     'temperature',
                     self.temperature,
                     metadata={
                         '@type': 'TemperatureProperty',
                         'title': 'Temperature',
                         'type': 'number',
                         'description': 'The current temperature',
                         'unit': 'degree celsius',
                         'readOnly': True,
                     }))

        self.timer = tornado.ioloop.PeriodicCallback(self.__measure,
                                                     (60 * 1000))  # 1 min
        self.timer.start()

    def __measure(self):
        try:
            humidity, temperature = Adafruit_DHT.read_retry(
                self.sensor, self.gpio_number)
            if humidity is not None:
                self.humidity.notify_of_external_update(round(humidity, 1))
                logging.debug('humidity ' + str(humidity))
            if temperature is not None:
                self.temperature.notify_of_external_update(
                    round(temperature, 1))
                logging.debug('temperature ' + str(temperature))
        except Exception as e:
            logging.error(e)

    def cancel_measure_task(self):
        self.timer.stop()
class SenseHatThingSensor(Thing):
    """A Thing controlling Sensors of SenseHat"""
    def __init__(self):
        Thing.__init__(self, 'urn:dev:ops:my-sense-hat-sensor-1234',
                       'SenseHat Sensor', [], 'A web connected sense hat')
        controller.set_imu_config(True, True, True)

        self.pitch = Value(0.0)
        self.add_property(
            Property(self,
                     'pitch',
                     self.pitch,
                     metadata={
                         'title': 'Pitch',
                         'type': 'number',
                         'description': 'Angle pitch',
                         'unit': 'd',
                         'minimum': 0,
                         'maximum': 360,
                         'readOnly': True,
                     }))

        self.roll = Value(0.0)
        self.add_property(
            Property(self,
                     'roll',
                     self.roll,
                     metadata={
                         'title': 'Roll',
                         'type': 'number',
                         'description': 'Angle',
                         'unit': 'd',
                         'minimum': 0,
                         'maximum': 360,
                         'readOnly': True,
                     }))

        self.yaw = Value(0.0)
        self.add_property(
            Property(self,
                     'yaw',
                     self.yaw,
                     metadata={
                         'title': 'Yaw',
                         'type': 'number',
                         'description': 'Angle',
                         'unit': 'd',
                         'minimum': 0,
                         'maximum': 360,
                         'readOnly': True,
                     }))

        logging.debug('info: starting the sensor update looping task')
        self.timer = tornado.ioloop.PeriodicCallback(self.update_properties,
                                                     1000)
        self.timer.start()

    def update_properties(self):
        orientation = controller.get_orientation()
        self.pitch.notify_of_external_update(orientation['pitch'])
        self.roll.notify_of_external_update(orientation['roll'])
        self.yaw.notify_of_external_update(orientation['yaw'])

    def cancel_update_properties_task(self):
        self.timer.stop()