Skip to content

Commit ce16af2

Browse files
authored
Merge pull request #14 from soloam/dev
Fix big list pulls Fixes #4
2 parents e1a64cc + f1539ac commit ce16af2

File tree

2 files changed

+63
-13
lines changed

2 files changed

+63
-13
lines changed

custom_components/fireflyiii_integration/integrations/fireflyiii.py

Lines changed: 61 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
import logging
55
from copy import deepcopy
66
from datetime import datetime, timedelta
7+
from hashlib import md5
78
from typing import Any, Dict, List, Optional
89

910
import aiohttp
@@ -49,6 +50,17 @@ def __init__(
4950
self._about: FireflyiiiAbout = FireflyiiiAbout()
5051
self._preferences: FireflyiiiPreferences = FireflyiiiPreferences()
5152
self._timerange: Optional[DateTimeRange] = timerange
53+
self._default_currency: Optional[FireflyiiiCurrency] = None
54+
self.clear_cache()
55+
56+
def clear_cache(self):
57+
"""Clears cache"""
58+
self._api_cache = {}
59+
60+
def _set_max_limit(self, params: dict):
61+
"""Sets max limits to avoid paging"""
62+
if "limit" not in params:
63+
params["limit"] = 9999999999
5264

5365
@property
5466
async def version(self) -> str:
@@ -83,6 +95,10 @@ def host_api(self) -> str:
8395
@property
8496
async def default_currency(self) -> FireflyiiiCurrency:
8597
"""Get FireflyIII Default Currency"""
98+
99+
if self._default_currency:
100+
return self._default_currency
101+
86102
default_currency = await self._request_api("GET", "/currencies/default")
87103
if not "data" in default_currency:
88104
_LOGGER.error(
@@ -110,7 +126,7 @@ async def default_currency(self) -> FireflyiiiCurrency:
110126
enabled=attributes.get("enabled", True),
111127
decimal_places=attributes.get("decimal_places", 2),
112128
)
113-
129+
self._default_currency = default_currency
114130
return default_currency
115131

116132
@property
@@ -216,7 +232,10 @@ async def accounts(
216232

217233
account_list = FireflyiiiObjectBaseList(type=FireflyiiiObjectType.ACCOUNTS)
218234

219-
accounts = await self._request_api("GET", "/accounts")
235+
params: dict = {}
236+
self._set_max_limit(params)
237+
238+
accounts = await self._request_api("GET", "/accounts", params)
220239
if not "data" in accounts:
221240
_LOGGER.error(
222241
"Invalid response from server on accounts, "
@@ -353,7 +372,10 @@ async def categories(self, ids=None, currency=None) -> FireflyiiiObjectBaseList:
353372
"""Get FireflyIII categories"""
354373
_LOGGER.debug("Updating FireflyIII categories")
355374

356-
categories = await self._request_api("GET", "/categories")
375+
params: dict = {}
376+
self._set_max_limit(params)
377+
378+
categories = await self._request_api("GET", "/categories", params)
357379
if not "data" in categories:
358380
_LOGGER.error(
359381
"Invalid response from server on categories, "
@@ -498,7 +520,10 @@ async def piggy_banks(self, ids=None) -> FireflyiiiObjectBaseList:
498520
type=FireflyiiiObjectType.PIGGY_BANKS
499521
)
500522

501-
piggy_banks = await self._request_api("GET", "/piggy-banks")
523+
params: dict = {}
524+
self._set_max_limit(params)
525+
526+
piggy_banks = await self._request_api("GET", "/piggy-banks", params)
502527
if not "data" in piggy_banks:
503528
_LOGGER.error(
504529
"Invalid response from server on piggy banks, "
@@ -555,18 +580,19 @@ async def budgets(self, ids=None, currency=None) -> FireflyiiiObjectBaseList:
555580

556581
budgets_list = FireflyiiiObjectBaseList(type=FireflyiiiObjectType.BUDGETS)
557582

558-
date_range = {}
583+
params = {}
559584
if (
560585
self._timerange
561586
and self._timerange.start_datetime
562587
and self._timerange.end_datetime
563588
):
564-
date_range = {
589+
params = {
565590
"start": self._timerange.start_datetime.strftime("%Y-%m-%d"),
566591
"end": self._timerange.end_datetime.strftime("%Y-%m-%d"),
567592
}
568593

569-
budgets = await self._request_api("GET", "/budgets", date_range)
594+
self._set_max_limit(params)
595+
budgets = await self._request_api("GET", "/budgets", params)
570596
if not "data" in budgets:
571597
_LOGGER.error(
572598
"Invalid response from server on budgets, "
@@ -588,7 +614,7 @@ async def budgets(self, ids=None, currency=None) -> FireflyiiiObjectBaseList:
588614
continue
589615

590616
budget_limits = await self._request_api(
591-
"GET", f"/budgets/{budget_id}/limits", date_range
617+
"GET", f"/budgets/{budget_id}/limits", params
592618
)
593619
if not "data" in budget_limits or len(budget_limits["data"]) < 1:
594620
budget_limits = None
@@ -656,20 +682,22 @@ async def bills(
656682
)
657683
get_timerange.set_end_datetime(end_date)
658684

659-
date_range = {}
685+
params = {}
660686
if (
661687
get_timerange
662688
and get_timerange.start_datetime
663689
and get_timerange.end_datetime
664690
):
665-
date_range = {
691+
params = {
666692
"start": get_timerange.start_datetime.strftime("%Y-%m-%d"),
667693
"end": get_timerange.end_datetime.strftime("%Y-%m-%d"),
668694
}
669695

670696
bill_list = FireflyiiiObjectBaseList(type=FireflyiiiObjectType.BILLS)
671697

672-
bills = await self._request_api("GET", "/bills", date_range)
698+
self._set_max_limit(params)
699+
700+
bills = await self._request_api("GET", "/bills", params)
673701
if not "data" in bills:
674702
_LOGGER.error(
675703
"Invalid response from server on bills, "
@@ -897,6 +925,16 @@ def _set_headers(self, header=None):
897925
header["Content-Type"] = "application/json"
898926
header["Accept"] = "application/json"
899927

928+
def _request_hash(self, path: str, params: Optional[dict] = None):
929+
hash_key = md5(
930+
(
931+
md5(path.encode("utf-8")).hexdigest()
932+
+ md5(json.dumps(params).encode("utf-8")).hexdigest()
933+
).encode("utf-8")
934+
).hexdigest()
935+
936+
return hash_key
937+
900938
async def _request_api(
901939
self,
902940
method="GET",
@@ -906,6 +944,15 @@ async def _request_api(
906944
timeout=10,
907945
):
908946
"""Request FireflyIII API"""
947+
hash_key = None
948+
949+
if method.upper() == "GET":
950+
hash_key = self._request_hash(path, params)
951+
if hash_key in self._api_cache:
952+
_LOGGER.debug("FireflyIII api response from cache for '%s' ok", path)
953+
return self._api_cache[hash_key]
954+
955+
_LOGGER.debug("Requesting FireflyIII api '%s'", path)
909956

910957
url = f"{self.host_api}{path}"
911958

@@ -918,8 +965,6 @@ async def _request_api(
918965

919966
message = None
920967

921-
_LOGGER.debug("Requesting FireflyIII api '%s'", path)
922-
923968
async with aiohttp.ClientSession() as session:
924969
http_method = getattr(session, method)
925970

@@ -958,6 +1003,9 @@ async def _request_api(
9581003
await session.close()
9591004

9601005
_LOGGER.debug("FireflyIII api response for '%s' ok", path)
1006+
if hash_key:
1007+
self._api_cache[hash_key] = message
1008+
9611009
return message
9621010
except (TimeoutError, ServerTimeoutError):
9631011
_LOGGER.error("Error in server api call, timeout")

custom_components/fireflyiii_integration/integrations/fireflyiii_coordinator.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,8 @@ async def _async_update_data(self):
226226
_LOGGER.warning("Skiping FireflyIII update, disconnected")
227227
return False
228228

229+
self.api.clear_cache()
230+
229231
_LOGGER.debug("Updating FireflyIII sensors")
230232

231233
data_list = FireflyiiiObjectBaseList()

0 commit comments

Comments
 (0)