diff --git a/djaosdb/caosdb_client.py b/djaosdb/caosdb_client.py index 8291ffd5ee145de0a20b7cce7e47aa2edf28b7cf..021ad7d2fbff2cc7a6c37391d0d149f99998b61a 100644 --- a/djaosdb/caosdb_client.py +++ b/djaosdb/caosdb_client.py @@ -121,6 +121,8 @@ class DefaultCaosDBClientDelegate: self._caosdb = caosdb self._caosdb.configure_connection(**kwargs) + self._query_cache = {} + self._etag = None def _get_reference_clause(self, type, p, v, negation, sub=None): result = (f" REFERENCES {v}" @@ -162,7 +164,22 @@ class DefaultCaosDBClientDelegate: return f' {n}{p}{o}"{v}"' raise NotImplementedError("_get_filter_clause(%s)", fil) - def _query(self, query): + def _cache_locally(self, etag, key, value): + if etag != self._etag: + self._query_cache = {} + if key is not None: + self._query_cache[key] = value + + def _query(self, query, key=None): + if key is not None and key in self.query_local_cache: + return self._query_cache[key] + + result = self._query_no_local_cache(query) + self._cache_locally(etag, key, result) + + return result + + def _query_no_local_cache(self, query): t1 = time.time() result = self._caosdb.execute_query(query) t2 = time.time() @@ -176,7 +193,7 @@ class DefaultCaosDBClientDelegate: filter_clause = " WITH " + self._get_filter_clause(fil) query = f'FIND RECORD "{record_type}"{filter_clause}' - return self._query(query) + return self._query(query, key=query) def _get_property_values(self, container, projection): if projection is None: @@ -335,10 +352,10 @@ class DefaultCaosDBClientDelegate: def _aggregate(self, record_type, sort=None, projection=None, limit=None, filter=None, count=False, skip=None): - query = self._generate_query(record_type, sort, projection, filter, + query, key = self._generate_query(record_type, sort, projection, filter, count) - res = self._query(query) + res = self._query(query, key=key) if count: return CountResult(res, count) rows = self._get_property_values(res, projection) @@ -354,7 +371,9 @@ class DefaultCaosDBClientDelegate: elif sort is not None: prefix = 'SELECT ' + ", ".join(list(projection) + list(sort.keys())) + " FROM" - return f'{prefix} RECORD "{record_type}"{filter_clause}' + query = f'{prefix} RECORD "{record_type}"{filter_clause}' + key = query if not count else None + return query, key def delete_many(self, record_type, filter): container = self._find(record_type, filter=filter) diff --git a/setup.py b/setup.py index 78db8ac1e5617f42cb894abbb7bf1e11b54c7914..a8a062f5db108195752e0632f3087f85da6c365e 100644 --- a/setup.py +++ b/setup.py @@ -82,7 +82,7 @@ def find_version(*file_paths): install_requires = [ 'sqlparse==0.2.4', - 'caosdb>=0.4.0', + 'caosdb>=0.5.1', 'django>=2.1', 'python-dateutil>=2.8.1', ]