]> git.immae.eu Git - perso/Immae/Projets/Cryptomonnaies/Cryptoportfolio/Trader.git/commitdiff
Store last cryptoportfolio repartition to redis
authorIsmaël Bouya <ismael.bouya@normalesup.org>
Tue, 1 May 2018 23:50:46 +0000 (01:50 +0200)
committerIsmaël Bouya <ismael.bouya@normalesup.org>
Tue, 1 May 2018 23:50:46 +0000 (01:50 +0200)
store.py
tests/test_store.py

index cd0bf7babe2e7240588f4605571365f98096305b..81828f0ae3df4a1c60ea5a287a7b4fe531cacf90 100644 (file)
--- a/store.py
+++ b/store.py
@@ -7,6 +7,7 @@ import datetime
 import inspect
 from json import JSONDecodeError
 from simplejson.errors import JSONDecodeError as SimpleJSONDecodeError
+import dbs
 
 __all__ = ["Portfolio", "BalanceStore", "ReportStore", "TradeStore"]
 
@@ -530,11 +531,24 @@ class Portfolio:
         try:
             cls.data.set(r.json(parse_int=D, parse_float=D))
             cls.parse_cryptoportfolio()
+            cls.store_cryptoportfolio()
         except (JSONDecodeError, SimpleJSONDecodeError):
             cls.data.set(None)
             cls.last_date.set(None)
             cls.liquidities.set({})
 
+    @classmethod
+    def store_cryptoportfolio(cls):
+        if dbs.redis_connected():
+            hash_ = {}
+            for liquidity, repartitions in cls.liquidities.items():
+                hash_[liquidity] = repartitions[cls.last_date.get()]
+            dump = json.dumps(hash_)
+            key = "/cryptoportfolio/repartition/latest"
+            dbs.redis.set(key, dump)
+            key = "/cryptoportfolio/repartition/date"
+            dbs.redis.set(key, cls.last_date.date().isoformat())
+
     @classmethod
     def parse_cryptoportfolio(cls):
         def filter_weights(weight_hash):
index 12999d36e1b7e9bd64f0d7eda8ad002dd14b8411..d0f7755c10cd73285861a004acda2f27a3b37c6f 100644 (file)
@@ -1101,7 +1101,8 @@ class PortfolioTest(WebMockTestCase):
         self.wm.get(market.Portfolio.URL, text=self.json_response)
 
     @mock.patch.object(market.Portfolio, "parse_cryptoportfolio")
-    def test_get_cryptoportfolio(self, parse_cryptoportfolio):
+    @mock.patch.object(market.Portfolio, "store_cryptoportfolio")
+    def test_get_cryptoportfolio(self, store_cryptoportfolio, parse_cryptoportfolio):
         with self.subTest(parallel=False):
             self.wm.get(market.Portfolio.URL, [
                 {"text":'{ "foo": "bar" }', "status_code": 200},
@@ -1116,23 +1117,28 @@ class PortfolioTest(WebMockTestCase):
             market.Portfolio.report.log_error.assert_not_called()
             market.Portfolio.report.log_http_request.assert_called_once()
             parse_cryptoportfolio.assert_called_once_with()
+            store_cryptoportfolio.assert_called_once_with()
             market.Portfolio.report.log_http_request.reset_mock()
             parse_cryptoportfolio.reset_mock()
+            store_cryptoportfolio.reset_mock()
             market.Portfolio.data = store.LockedVar(None)
 
             market.Portfolio.get_cryptoportfolio()
             self.assertIsNone(market.Portfolio.data.get())
             self.assertEqual(2, self.wm.call_count)
             parse_cryptoportfolio.assert_not_called()
+            store_cryptoportfolio.assert_not_called()
             market.Portfolio.report.log_error.assert_not_called()
             market.Portfolio.report.log_http_request.assert_called_once()
             market.Portfolio.report.log_http_request.reset_mock()
             parse_cryptoportfolio.reset_mock()
+            store_cryptoportfolio.reset_mock()
 
             market.Portfolio.data = store.LockedVar("Foo")
             market.Portfolio.get_cryptoportfolio()
             self.assertEqual(2, self.wm.call_count)
             parse_cryptoportfolio.assert_not_called()
+            store_cryptoportfolio.assert_not_called()
 
             market.Portfolio.get_cryptoportfolio(refetch=True)
             self.assertEqual("Foo", market.Portfolio.data.get())
@@ -1153,6 +1159,7 @@ class PortfolioTest(WebMockTestCase):
                     market.Portfolio.get_cryptoportfolio()
                     self.assertIn("foo", market.Portfolio.data.get())
                 parse_cryptoportfolio.reset_mock()
+                store_cryptoportfolio.reset_mock()
                 with self.subTest(worker=False):
                     market.Portfolio.data = store.LockedVar(None)
                     market.Portfolio.worker = mock.Mock()
@@ -1160,6 +1167,7 @@ class PortfolioTest(WebMockTestCase):
                     market.Portfolio.get_cryptoportfolio()
                     notify.assert_called_once_with()
                     parse_cryptoportfolio.assert_not_called()
+                    store_cryptoportfolio.assert_not_called()
 
     def test_parse_cryptoportfolio(self):
         with self.subTest(description="Normal case"):
@@ -1223,6 +1231,33 @@ class PortfolioTest(WebMockTestCase):
             self.assertEqual({}, market.Portfolio.liquidities.get("high"))
             self.assertEqual(datetime.datetime(1,1,1), market.Portfolio.last_date.get())
 
+    @mock.patch.object(store.dbs, "redis_connected")
+    @mock.patch.object(store.dbs, "redis")
+    def test_store_cryptoportfolio(self, redis, redis_connected):
+        store.Portfolio.liquidities = store.LockedVar({
+                "medium": {
+                    datetime.datetime(2018,3,1): "medium_2018-03-01",
+                    datetime.datetime(2018,3,8): "medium_2018-03-08",
+                    },
+                "high": {
+                    datetime.datetime(2018,3,1): "high_2018-03-01",
+                    datetime.datetime(2018,3,8): "high_2018-03-08",
+                    }
+                })
+        store.Portfolio.last_date = store.LockedVar(datetime.datetime(2018,3,8))
+
+        with self.subTest(redis_connected=False):
+            redis_connected.return_value = False
+            store.Portfolio.store_cryptoportfolio()
+            redis.set.assert_not_called()
+
+        with self.subTest(redis_connected=True):
+            redis_connected.return_value = True
+            store.Portfolio.store_cryptoportfolio()
+            redis.set.assert_has_calls([
+                mock.call("/cryptoportfolio/repartition/latest", '{"medium": "medium_2018-03-08", "high": "high_2018-03-08"}'),
+                mock.call("/cryptoportfolio/repartition/date", "2018-03-08"),
+                ])
 
     @mock.patch.object(market.Portfolio, "get_cryptoportfolio")
     def test_repartition(self, get_cryptoportfolio):