Skip to content

Commit

Permalink
Merge pull request #815 from sabeechen/dev
Browse files Browse the repository at this point in the history
Release 0.110.3
  • Loading branch information
sabeechen committed Mar 24, 2023
2 parents dc294c7 + 7fca5b3 commit 0561762
Show file tree
Hide file tree
Showing 7 changed files with 111 additions and 8 deletions.
4 changes: 4 additions & 0 deletions hassio-google-drive-backup/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
## v0.110.3 [2023-03-24]
- Fix an error causing "Days Between Backups" to be ignored when "Time of Day" for a backup is set.
- Fix a bug causing some timezones to make the addon to fail to start.

## v0.110.2 [2023-03-24]
- Fix a potential cause of SSL errors when communicating with Google Drive
- Fix a bug causing backups to be requested indefinitely if scheduled during DST transitions.
Expand Down
2 changes: 1 addition & 1 deletion hassio-google-drive-backup/backup/model/model.py
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,7 @@ def _nextBackup(self, now: datetime, last_backup: Optional[datetime]) -> Optiona
next = self.time.toUtc(time_that_day_local)
else:
# return the next backup after the delta
next_date = date.fromordinal(date(newest_local.year, newest_local.month, newest_local.day).toordinal() + 1)
next_date = date.fromordinal(int(date(newest_local.year, newest_local.month, newest_local.day).toordinal() + self.config.get(Setting.DAYS_BETWEEN_BACKUPS)))
next_datetime_local = self.time.localize(datetime(next_date.year, next_date.month, next_date.day, timeofDay[0], timeofDay[1]))
next = self.time.toUtc(next_datetime_local)

Expand Down
54 changes: 52 additions & 2 deletions hassio-google-drive-backup/backup/time.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,17 +7,67 @@
from dateutil.parser import parse
from .logger import getLogger
import pytz
import os
from pytz import timezone, utc
from tzlocal import get_localzone_name
from tzlocal import get_localzone_name, get_localzone
from dateutil.tz import tzlocal


logger = getLogger(__name__)


def get_local_tz():
methods = [
_infer_timezone_from_env,
_infer_timezone_from_system,
_infer_timezone_from_name,
_infer_timezone_from_offset
]
for method in methods:
try:
tz = method()
if tz is not None:
return tz
except Exception:
pass
return utc


def _infer_timezone_from_offset():
now = datetime.now()
desired_offset = tzlocal().utcoffset(now)
for tz_name in pytz.all_timezones:
tz = pytz.timezone(tz_name)
if desired_offset == tz.utcoffset(now):
return tz
return None


def _infer_timezone_from_name():
name = get_localzone_name()
if name is not None:
return timezone(name)
return None


def _infer_timezone_from_system():
tz = get_localzone()
if tz is not None:
return tz
return None


def _infer_timezone_from_env():
if "TZ" in os.environ:
tz = timezone(os.environ["TZ"])
if tz is not None:
return tz
return None

@singleton
class Time(object):
@inject
def __init__(self, local_tz=timezone(get_localzone_name())):
def __init__(self, local_tz=get_local_tz()):
self.local_tz = local_tz
self._offset = timedelta(seconds=0)

Expand Down
2 changes: 1 addition & 1 deletion hassio-google-drive-backup/config.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "Home Assistant Google Drive Backup",
"version": "0.110.2",
"version": "0.110.3",
"slug": "hassio_google_drive_backup",
"description": "Automatically manage backups between Home Assistant and Google Drive",
"arch": ["armhf", "armv7", "aarch64", "amd64", "i386"],
Expand Down
7 changes: 5 additions & 2 deletions hassio-google-drive-backup/tests/faketime.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,11 @@ def __init__(self, now: datetime = None):
datetime(1985, 12, 6, 0, 0, 0, tzinfo=timezone('EST')))
self.sleeps = []

def setTimeZone(self, name):
self.local_tz = timezone(name)
def setTimeZone(self, tz):
if isinstance(tz, str):
self.local_tz = timezone(tz)
else:
self.local_tz = tz

def setNow(self, now: datetime):
self._now = now
Expand Down
17 changes: 17 additions & 0 deletions hassio-google-drive-backup/tests/test_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -1330,3 +1330,20 @@ async def test_generational_delete_dst_end_rome_3_00(time: FakeTime, model: Mode
for x in range(0, 24 * 15):
time.advance(minutes=15)
assert model.nextBackup(time.now()) == time.local(2023, 10, 30, 3)


def test_next_time_over_a_day(estimator, data_cache):
time: FakeTime = FakeTime()
now: datetime = time.localize(datetime(1985, 12, 6))
time.setNow(now)
info = GlobalInfo(time)

config: Config = createConfig()
config.override(Setting.BACKUP_TIME_OF_DAY, "00:00")
config.override(Setting.DAYS_BETWEEN_BACKUPS, 2.0)
model: Model = Model(config, time, default_source,
default_source, info, estimator, data_cache)
assert model._nextBackup(
now=now, last_backup=None) == now
assert model._nextBackup(
now=now, last_backup=now) == now + timedelta(days=2)
33 changes: 31 additions & 2 deletions hassio-google-drive-backup/tests/test_timezone.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import datetime

from backup.time import Time
import os
from backup.time import Time, _infer_timezone_from_env, _infer_timezone_from_name, _infer_timezone_from_offset, _infer_timezone_from_system
from .faketime import FakeTime


def test_parse() -> None:
Expand Down Expand Up @@ -28,3 +29,31 @@ def assertOffset(time, hours):

def assertUtc(time):
assertOffset(time, 0)


def test_common_timezones(time: FakeTime):
assert _infer_timezone_from_system() is not None
assert _infer_timezone_from_name() is not None
assert _infer_timezone_from_offset() is not None
assert _infer_timezone_from_env() is None

os.environ["TZ"] = "America/Denver"
assert _infer_timezone_from_env() is not None

os.environ["TZ"] = "Australia/Brisbane"

assert _infer_timezone_from_env() is not None

tzs = [_infer_timezone_from_system(),
_infer_timezone_from_env(),
_infer_timezone_from_offset(),
_infer_timezone_from_name()]

for tz in tzs:
time.setTimeZone(tz)
time.now()
time.nowLocal()
time.localize(datetime.datetime(1985, 12, 6))
time.local(1985, 12, 6)
time.toLocal(time.now())
time.toUtc(time.nowLocal())

0 comments on commit 0561762

Please sign in to comment.