Exemplo n.º 1
0
def get_device_status():
    errors = {}
    tenant = request.args.get('tenant')
    try:
        limit = abs(int(request.args.get('limit', 0)))
    except Exception:
        errors['limit'] = 'limit must be a valid integer'

    try:
        start_date = validate_datetime(request.args.get('startDate'))
    except Exception:
        errors['startDate'] = 'This query param is required.' \
                              'Please provide a valid ISO formatted datetime string (%Y-%m-%dT%H:%M:%S.%fZ)'

    try:
        end_date = validate_datetime(request.args.get('endDate'))
    except Exception:
        errors['endDate'] = 'This query param is required.' \
                              'Please provide a valid ISO formatted datetime string (%Y-%m-%dT%H:%M:%S.%fZ)'

    if errors:
        return jsonify({
            'message': 'Some errors occurred while processing this request',
            'errors': errors
        }), 400

    model = DeviceStatus(tenant)
    documents = model.get_device_status(start_date, end_date, limit)
    converted_documents = convert_model_ids(documents)

    response = dict(message="devices status query successful", data=converted_documents)
    return jsonify(response), 200
Exemplo n.º 2
0
 def turn_off(self, token: str, status: DeviceStatus) -> DeviceStatus:
     if status.is_off():
         logger.info('Coffee Machine is already off.')
         return status
     logger.info('Coffee Machine Runtime State: OFF')
     CM_API.toggle_power()
     return CM_API.status
Exemplo n.º 3
0
class DeviceStatusResource(Resource):
    def __init__(self):
        self.controller = DeviceStatusController()

    @token_required()
    @swag_from('/resources/device/description/device_status_get.yml')
    @marshal_with(DeviceStatus.get_fields())
    def get(self, token: str) -> DeviceStatus:
        return self.controller.get_status(token)

    @token_required()
    @swag_from('/resources/device/description/device_status_put.yml')
    @marshal_with(DeviceStatus.get_fields())
    def put(self, token: str) -> DeviceStatus:
        data = request.get_json()
        new_status = EditDeviceStatus(**data)
        return self.controller.set_status(token, new_status)
Exemplo n.º 4
0
    def post(self):
        request_data = json.loads(self.request.body)
        response = []
        for status in request_data:
            uuid = _create_uuid()
            d = DeviceStatus(id=uuid)
            d.raw_data = status
            #d.put()
            response.append({'_id': uuid})

        most_recent_status = sorted(request_data,
                                    key=lambda k: k['created_at'])[-1]
        api_secret = self.request.headers.get('api-secret')
        if not api_secret is None:
            device = LoopDevice.get_by_id(api_secret)
            if not device is None:
                device.raw_data = most_recent_status
                device.put()

        logging.info(json.dumps(request_data, indent=4))
        self.response.headers['Content-Type'] = 'application/json'
        self.response.out.write(json.dumps(response))
    def update_db_device_status(self):
        """Override this to change database storage behavior"""
        device_status = DeviceStatus(self.node)
        device_status = DeviceSchema().dump(device_status)

        _logger.debug(device_status)
        db_id = device_status["_id"]

        # Update local DB
        with get_local_db() as db:
            if db_id in db:
                # Update item if it exists
                local_db_doc = db[db_id]

                # Don't do any database updates if the value has not changed
                if local_db_doc["value"] != device_status["value"]:
                    local_db_doc.update(device_status)
                    local_db_doc.save()

            else:
                # Create item if it doesn't exist
                local_db_doc = db.create_document(device_status)

        # Update AWS DB
        aws_table = get_aws_table()
        try:
            # Update item if it exists
            current_doc = aws_table.get(db_id)
            if current_doc.value != device_status["value"]:
                actions = [
                    # name should never change
                    # aws_table.name.set(device_status["name"]),
                    aws_table.value.set(device_status["value"]),
                    aws_table.year.set(device_status["year"]),
                    aws_table.month.set(device_status["month"]),
                    aws_table.day.set(device_status["day"]),
                    aws_table.hour.set(device_status["hour"]),
                    aws_table.minute.set(device_status["minute"]),
                    aws_table.microsecond.set(device_status["microsecond"])
                ]
                current_doc.update(actions=actions)
        except aws_table.DoesNotExist:
            # Create item if it doesn't exist
            new_doc = dict(**device_status)
            new_doc.pop("_id")
            item = aws_table(db_id, **new_doc)
            item.save()

        return local_db_doc
Exemplo n.º 6
0
 def read_status(self):
     self._status = DeviceStatus()
     logger.warning(
         'Should read status of coffee machine here and set it to self._status'
     )
Exemplo n.º 7
0
    def read_status(self):
        gpio_numbers = list(GPIO_IN_PINS.values())
        session = self._session
        reads = read_gpio_list(gpio_numbers=gpio_numbers,
                               sample_rate=SAMPLE_RATE,
                               check_cycles=CHECK_CYCLES,
                               session=session)
        status = DeviceStatus()

        # Check water LED
        water_gpio = GPIO_IN_PINS['WATER']
        water_led = self._read_single_status(gpio_reads=reads,
                                             gpio_number=water_gpio,
                                             fallback=True,
                                             status_name='Water LED')

        # Check coffee grounds LED
        coffee_grounds_gpio = GPIO_IN_PINS['COFFEE_GROUNDS_CONTAINER']
        coffee_grounds_led = self._read_single_status(
            gpio_reads=reads,
            gpio_number=coffee_grounds_gpio,
            fallback=True,
            status_name='Coffee Grounds Container LED')

        # Check one dose LED
        one_dose_gpio = GPIO_IN_PINS['ONE_DOSE']
        one_dose_led = self._read_single_status(gpio_reads=reads,
                                                gpio_number=one_dose_gpio,
                                                fallback=False,
                                                status_name='One Dose LED')

        # Check two doses LED
        two_doses_gpio = GPIO_IN_PINS['TWO_DOSES']
        two_doses_led = self._read_single_status(gpio_reads=reads,
                                                 gpio_number=two_doses_gpio,
                                                 fallback=False,
                                                 status_name='Two Doses LED')

        # Check warning LED
        warning_gpio = GPIO_IN_PINS['WARNING']
        warning_led = self._read_single_status(gpio_reads=reads,
                                               gpio_number=warning_gpio,
                                               fallback=True,
                                               status_name='Warning LED')

        # Steam LED
        steam_gpio = GPIO_IN_PINS['STEAM']
        steam_led = self._read_single_status(gpio_reads=reads,
                                             gpio_number=steam_gpio,
                                             fallback=False,
                                             status_name='Steam LED')

        # Check maintenance LED
        maintenance_gpio = GPIO_IN_PINS['MAINTENANCE']
        maintenance_led = self._read_single_status(
            gpio_reads=reads,
            gpio_number=maintenance_gpio,
            fallback=True,
            status_name='Maintenance LED')

        # Check eco LED
        eco_gpio = GPIO_IN_PINS['ECO']
        eco_led = self._read_single_status(gpio_reads=reads,
                                           gpio_number=eco_gpio,
                                           fallback=False,
                                           status_name='Eco LED')

        # Set status
        status.water_tank_ready = water_led is False
        status.coffee_grounds_container_ready = coffee_grounds_led is False
        status.device_eco_mode = eco_led
        status.device_maintenance = maintenance_led
        status.device_steam = steam_led

        is_on = one_dose_led and two_doses_led
        runtime_state = DeviceRuntimeState.ON if is_on else DeviceRuntimeState.OFF
        status.coffee_machine_runtime_state = runtime_state.state_id

        is_ready = status.water_tank_ready and status.coffee_grounds_container_ready and is_on
        status.device_ready = is_ready

        self._status = status
Exemplo n.º 8
0
def compute_device_channel_status(tenant):
    devices = get_all_devices(tenant)
    count_of_online_devices = 0
    online_devices = []
    offline_devices = []
    count_of_offline_devices = 0
    count_of_solar_devices = 0
    count_of_alternator_devices = 0
    count_of_mains = 0
    count_due_maintenance = 0
    count_overdue_maintenance = 0
    count_unspecified_maintenance = 0

    futures = []
    executor = ThreadPoolExecutor()

    for device in devices:
        futures.append(executor.submit(get_device_status, device))

    for future in futures:
        try:
            device_status = future.result()
        except Exception as ex:
            print("Cannot process channel", ex)
            continue
        device = device_status.device

        try:
            last_maintained_duration = (
                datetime.utcnow() -
                device.get("nextMaintenance")).total_seconds()

            if last_maintained_duration <= 0:
                if abs(last_maintained_duration
                       ) <= configuration.DUE_FOR_MAINTENANCE_DURATION:
                    device["maintenance_status"] = "due"
                    count_due_maintenance += 1
                else:
                    device["maintenance_status"] = "good"
            else:
                device["maintenance_status"] = "overdue"
                count_overdue_maintenance += 1

        except Exception:
            device["nextMaintenance"] = None
            device["maintenance_status"] = -1
            count_unspecified_maintenance += 1

        def check_power_type(power):
            return (device.get("powerType") or device.get("power")
                    or "").lower() == power

        if check_power_type("solar"):
            count_of_solar_devices += 1
        elif check_power_type("mains"):
            count_of_mains += 1
        elif check_power_type("alternator") or check_power_type("battery"):
            count_of_alternator_devices += 1

        device['elapsed_time'] = device_status.elapsed_time

        if device_status.is_online:
            count_of_online_devices += 1
            online_devices.append(device)
        else:
            count_of_offline_devices += 1
            offline_devices.append(device)

        print("Done processing channel", device.get("device_number"))

    device_status_results = []

    created_at = datetime.utcnow()
    record = {
        "created_at": created_at,
        "total_active_device_count": len(devices),
        "count_of_online_devices": count_of_online_devices,
        "count_of_offline_devices": count_of_offline_devices,
        "count_of_mains": count_of_mains,
        "count_of_solar_devices": count_of_solar_devices,
        "count_of_alternator_devices": count_of_alternator_devices,
        "count_due_maintenance": count_due_maintenance,
        "count_overdue_maintenance": count_overdue_maintenance,
        "count_unspecified_maintenance": count_unspecified_maintenance,
        "online_devices": online_devices,
        "offline_devices": offline_devices
    }

    device_status_results.append(record)

    device_status_model = DeviceStatusModel(tenant)
    device_status_model.save_device_status(device_status_results)