Merge pull request #214 from fronzbot/bugfix-motion

Fix motion detection getting stuck 'on'
This commit is contained in:
Kevin Fronczak
2020-04-09 15:05:44 -04:00
committed by GitHub
11 changed files with 77 additions and 22 deletions
+3 -3
View File
@@ -1,5 +1,5 @@
[run]
omit =
helpers/*
parallel = true
omit =
tests/*
setup.py
setup.py
+2
View File
@@ -0,0 +1,2 @@
[flake8]
ignore = BLK100
+4
View File
@@ -4,4 +4,8 @@ python:
ignored_directories:
- docs
flake8:
enabled: true
config_file: .flake8
fail_on_violations: true
+7 -2
View File
@@ -2,8 +2,9 @@ sudo: required
matrix:
fast_finish: true
include:
- python: "3.5.3"
- python: "3.7"
env: TOXENV=lint
dist: xenial
- python: "3.5.3"
env: TOXENV=py35
- python: "3.6"
@@ -13,11 +14,15 @@ matrix:
- python: "3.7"
env: TOXENV=py37
dist: xenial
- python: "3.8"
env: TOXENV=py38
- python: "3.8-dev"
env: TOXENV=py38
dist: xenial
install: pip install -U tox coveralls
install:
- pip install -U tox coveralls
- pip install coverage==4.5.4
language: python
script: tox
after_success: coveralls
+1 -1
View File
@@ -60,7 +60,7 @@ ONLINE = {'online': True, 'offline': False}
'''
OTHER
'''
TIMESTAMP_FORMAT = '%Y-%m-%dT%H:%M:%S%Z'
TIMESTAMP_FORMAT = '%Y-%m-%dT%H:%M:%S%z'
DEFAULT_MOTION_INTERVAL = 1
DEFAULT_REFRESH = 30
+13
View File
@@ -2,8 +2,10 @@
import logging
import time
from calendar import timegm
from functools import partial, wraps
from requests import Request, Session, exceptions
import dateutil.parser
from blinkpy.helpers.constants import BLINK_URL, TIMESTAMP_FORMAT
import blinkpy.helpers.errors as ERROR
@@ -11,6 +13,17 @@ import blinkpy.helpers.errors as ERROR
_LOGGER = logging.getLogger(__name__)
def time_to_seconds(timestamp):
"""Convert TIMESTAMP_FORMAT time to seconds."""
try:
dtime = dateutil.parser.isoparse(timestamp)
except ValueError:
_LOGGER.error("Incorrect timestamp format for conversion: %s.",
timestamp)
return False
return timegm(dtime.timetuple())
def get_time(time_to_convert=None):
"""Create blink-compatible timestamp."""
if time_to_convert is None:
+7 -2
View File
@@ -5,6 +5,7 @@ import logging
from requests.structures import CaseInsensitiveDict
from blinkpy import api
from blinkpy.camera import BlinkCamera
from blinkpy.helpers.util import time_to_seconds
from blinkpy.helpers.constants import ONLINE
_LOGGER = logging.getLogger(__name__)
@@ -163,7 +164,7 @@ class BlinkSyncModule():
def check_new_videos(self):
"""Check if new videos since last refresh."""
try:
interval = self.blink.last_refresh - self.motion_interval*60
interval = self.blink.last_refresh - self.motion_interval * 60
except TypeError:
# This is the first start, so refresh hasn't happened yet.
# No need to check for motion.
@@ -187,9 +188,13 @@ class BlinkSyncModule():
name = entry['device_name']
clip = entry['media']
timestamp = entry['created_at']
self.motion[name] = True
self.motion[name] = self.check_new_video_time(timestamp)
self.last_record[name] = {'clip': clip, 'time': timestamp}
except KeyError:
_LOGGER.debug("No new videos since last refresh.")
return True
def check_new_video_time(self, timestamp):
"""Check if video has timestamp since last refresh."""
return time_to_seconds(timestamp) > self.blink.last_refresh
+9 -8
View File
@@ -1,10 +1,11 @@
flake8==3.5.0
flake8-docstrings==1.3.0
pylint==2.3.0
pydocstyle==2.1.1
pytest==3.7.1
pytest-cov>=2.3.1
pytest-sugar>=0.9.0
pytest-timeout>=1.0.0
coverage==4.5.4
flake8==3.7.9
flake8-docstrings==1.5.0
pylint==2.4.4
pydocstyle==5.0.2
pytest==5.3.5
pytest-cov==2.8.1
pytest-sugar>=0.9.2
pytest-timeout>=1.3.3
restructuredtext-lint>=1.0.1
pygments>=2.2.0
+21 -3
View File
@@ -73,23 +73,41 @@ class TestBlinkSyncModule(unittest.TestCase):
'media': [{
'device_name': 'foo',
'media': '/foo/bar.mp4',
'created_at': '1970-01-01T00:00:00+0:00'
'created_at': '1990-01-01T00:00:00+00:00'
}]
}
sync_module = self.blink.sync['test']
sync_module.cameras = {'foo': None}
sync_module.blink.last_refresh = 0
self.assertEqual(sync_module.motion, {})
self.assertTrue(sync_module.check_new_videos())
self.assertEqual(sync_module.last_record['foo'],
{'clip': '/foo/bar.mp4',
'time': '1970-01-01T00:00:00+0:00'})
'time': '1990-01-01T00:00:00+00:00'})
self.assertEqual(sync_module.motion, {'foo': True})
mock_resp.return_value = {'media': []}
self.assertTrue(sync_module.check_new_videos())
self.assertEqual(sync_module.motion, {'foo': False})
self.assertEqual(sync_module.last_record['foo'],
{'clip': '/foo/bar.mp4',
'time': '1970-01-01T00:00:00+0:00'})
'time': '1990-01-01T00:00:00+00:00'})
def test_check_new_videos_old_date(self, mock_resp):
"""Test videos return response with old date."""
mock_resp.return_value = {
'media': [{
'device_name': 'foo',
'media': '/foo/bar.mp4',
'created_at': '1970-01-01T00:00:00+00:00'
}]
}
sync_module = self.blink.sync['test']
sync_module.cameras = {'foo': None}
sync_module.blink.last_refresh = 1000
self.assertTrue(sync_module.check_new_videos())
self.assertEqual(sync_module.motion, {'foo': False})
def test_check_new_videos_failed(self, mock_resp):
"""Test method when response is unexpected."""
+8 -1
View File
@@ -3,7 +3,7 @@
import unittest
from unittest import mock
import time
from blinkpy.helpers.util import Throttle, BlinkURLHandler
from blinkpy.helpers.util import Throttle, BlinkURLHandler, time_to_seconds
class TestUtil(unittest.TestCase):
@@ -105,3 +105,10 @@ class TestUtil(unittest.TestCase):
self.assertEqual(urls.subdomain, 'rest-test')
urls = BlinkURLHandler('test', legacy=True)
self.assertEqual(urls.subdomain, 'rest.test')
def test_time_to_seconds(self):
"""Test time to seconds conversion."""
correct_time = '1970-01-01T00:00:05+00:00'
wrong_time = '1/1/1970 00:00:03'
self.assertEqual(time_to_seconds(correct_time), 5)
self.assertFalse(time_to_seconds(wrong_time))
+2 -2
View File
@@ -8,11 +8,11 @@ setenv =
LANG=en_US.UTF-8
PYTHONPATH = {toxinidir}
commands =
py.test --timeout=30 --duration=10 --cov=blinkpy --cov-report term-missing {posargs}
pytest --timeout=9 --durations=10 --cov=blinkpy --cov-report term-missing {posargs}
deps =
-r{toxinidir}/requirements.txt
-r{toxinidir}/requirements_test.txt
[testenv:lint]
deps =
-r{toxinidir}/requirements.txt