def delete(self, tile_id): if self.redis.exists(getRedisPrefix(tile_id=tile_id)): self.redis.delete(getRedisPrefix(tile_id=tile_id)) return True if LOG: print(f'{getTimeStr()}(-) tile: {tile_id} not found in redis', flush=True) return False
def push(request, unsecured=False): """ Update the content of a tile(widget) """ if request.method == "POST": if not checkAccessToken( method="POST", request=request, unsecured=unsecured): return HttpResponse("API KEY incorrect", status=401) try: tile_id = request.POST.get("key", None) data = request.POST.get("data", None) tile_template = request.POST.get("tile", None) if not tile_id or not data or not tile_template: return HttpResponseBadRequest(f"Missing data") tilePrefix = getRedisPrefix(tile_id) if not redis.exists(tilePrefix): if LOG: print( f"{getTimeStr()}: (+) {tile_id} not found in cache, creating tile {tile_template}", flush=True) if cache.createTile(tile_id=tile_id, value=data, tile_template=tile_template): return HttpResponse( f"{tile_id} data created successfully.") else: return HttpResponse( f"Internal Error {tile_id} was not created") cachedTile = json.loads(redis.get(tilePrefix)) cachedTile['data'] = json.loads(data) cachedTile['modified'] = getIsoTime() cachedTile['tile_template'] = tile_template cache.set(tilePrefix, json.dumps(cachedTile)) return HttpResponse(f"{tile_id} data updated successfully.") except IOError as e: return HttpResponseServerError(e) raise Http404
def meta(request, tile_key, unsecured=False): """ Update the meta(config) of a tile(widget) """ if request.method == "POST": if not checkAccessToken( method="POST", request=request, unsecured=unsecured): return HttpResponse("API KEY incorrect", status=401) try: value = request.POST.get("value", None) if value is None: return HttpResponseBadRequest("Missing data") try: value = json.loads(value) except: return HttpResponseBadRequest("Invalid Json data") if "big_value_color" not in value or "fading_background" not in value: return HttpResponseBadRequest("Bad data") tilePrefix = getRedisPrefix(tile_key) if not redis.exists(tilePrefix): if LOG: print( f"{getTimeStr()}: (+) {tile_key} is not present in cache", flush=True) return HttpResponseBadRequest( f"{tile_key} is not present in cache") cachedTile = json.loads(redis.get(tilePrefix)) cachedTile['meta']['big_value_color'] = value['big_value_color'] cachedTile['meta']['fading_background'] = value[ 'fading_background'] cache.set(tilePrefix, json.dumps(cachedTile)) return HttpResponse(f"{tile_key} data updated successfully.") except Exception as e: return HttpResponseServerError(e) raise Http404
def update_meta_if_present(tile_id, meta): """ Update the meta(config) of a tile(widget) """ cachedTile = json.loads(MyCache().redis.get(getRedisPrefix(tile_id))) metaTile = cachedTile['meta']['options'] if 'options' in cachedTile[ 'meta'] else cachedTile['meta'] cachedTile['meta'] = update_tile_data_from_redis(metaTile, json.loads(meta), None) return cachedTile['meta']
def get_tile(request, tile_key): """ Return Json from redis for tile_key """ if not checkAccessToken(method='GET', request=request, unsecured=True): return HttpResponse('API KEY incorrect', status=401) redis = MyCache().redis if redis.exists(getRedisPrefix(tile_key)): return HttpResponse(redis.get(tile_key)) return HttpResponseBadRequest(f'{tile_key} key does not exist.')
def test_0012_cache_permissionTest(self): """ Test redis cache Handle when GET / SET """ tilePrefix = getRedisPrefix('test') self.assertTrue( self.cache.set(tile_fullid=tilePrefix, dumped_value=json.dumps({'testValue': True}))) self.assertTrue( json.loads(self.cache.redis.get(tilePrefix))['testValue'])
def delete_tile(request, tile_key): """ Delete in redis """ if not checkAccessToken(method='DELETE', request=request, unsecured=True): return HttpResponse('API KEY incorrect', status=401) redis = MyCache().redis if redis.exists(getRedisPrefix(tile_key)): redis.delete(tile_key) return HttpResponse('Tile\'s data deleted.') return HttpResponseBadRequest(f'{tile_key} key does not exist.')
def update_tile_receive(self, tile_id, template_name=None): """ Create or update the tile with value and send to the client with websocket """ tileData = MyCache().get(tile_id=getRedisPrefix(tile_id)) if tileData is None: print( f'[DEBUG] Building fake data for {tile_id}. with template {template_name}', flush=True) tileData = buildFakeDataFromTemplate(tile_id, template_name, MyCache()) self.send(text_data=tileData)
def buildFakeDataFromTemplate(tile_id, template_name, cache): print(f'Building fake data for {tile_id} as template: {template_name}') data = dict() ptrToFake = buildSwicthPythonFfso_o() if template_name in ptrToFake: if template_name in ptrToFake: data = ptrToFake[template_name](tile_id, template_name) if cache is not None: cache.redis.set(name=getRedisPrefix(tile_id), value=json.dumps(data)) return data
def save_tile_ToRedis(tile_id, tile_template, data): # pragma: no cover cache = getCache() tilePrefix = getRedisPrefix(tile_id) if not cache.redis.exists(tilePrefix) and DEBUG: # if tile don't exist, create it with template, DEBUG mode only buildFakeDataFromTemplate(tile_id, tile_template, cache) cachedTile = json.loads(cache.redis.get(tilePrefix)) cachedTile['data'] = update_tile_data_from_redis(cachedTile['data'], json.loads(data), tile_template) cachedTile['modified'] = getIsoTime() cachedTile['tile_template'] = tile_template cache.set(tilePrefix, json.dumps(cachedTile)) return HttpResponse(f'{tile_id} data updated successfully.')
def meta_api(request, tile_key, unsecured=False): # pragma: no cover """ Update the meta(config) of a tile(widget) """ if request.method == 'POST': if not checkAccessToken( method='POST', request=request, unsecured=unsecured): return HttpResponse('API KEY incorrect', status=401) tilePrefix = getRedisPrefix(tile_key) if not getCache().redis.exists(tilePrefix): return HttpResponseBadRequest( f'{tile_key} is not present in cache') return update_tile_meta(request, tilePrefix, tile_key) raise Http404
def createTile(self, tile_id, value, tile_template): try: if self.isRedisConnected: cache.set(getRedisPrefix(tile_id), json.dumps(dict( id=tile_id, tile_template=tile_template, data=json.loads(value), meta={}, modified=getIsoTime(), ))) return True, None except Exception as e: return False, e
def update_tile(self, data): # pragma: no cover """ send to client a single tile config """ tile_id = getRedisPrefix(data['tile_id']) tileData = cache.get(tile_id=tile_id) if tileData is None: if LOG: print(f'{getTimeStr()} (-) No data in key {tile_id} on Redis.', flush=True) return data = json.loads(tileData) if isinstance(data, str): data = json.loads(data) self.send(text_data=json.dumps(data))
def buildFakeDataFromTemplate(tile_id, template_name, cache): ptrToFuncUpdateTile = buildSwicthPythonFfso_o() if template_name in ptrToFuncUpdateTile: functionTileUpdate = ptrToFuncUpdateTile[template_name] tileData = add_template_and_id(functionTileUpdate(), tile_id, template_name) if cache is not None: tileData = json.dumps(tileData) cache.redis.set(name=getRedisPrefix(tile_id), value=tileData) return tileData print(f'[ERROR] with tile:{template_name}', flush=True) else: print(f'[ERROR] Error no update function for tile: {template_name}', flush=True) return None
def update_tile(self, data): tile_id = getRedisPrefix(data['tile_id']) tileData = cache.get(tile_id=tile_id) if tileData is None: if LOG: print(f'{getTimeStr()} (-) No data in key {tile_id} on Redis.', flush=True) return data = json.loads(tileData) if type(data) is str: data = json.loads(data) data['tipboard'] = tipboard_helpers self.send(text_data=json.dumps(data))
def check_sanity_request(request): """ Test token, and presence of all data required """ HttpData = request.POST tilePrefix = getRedisPrefix(HttpData.get('tile_id', None)) cache = MyCache() fg = not HttpData.get('tile_id', None) or not HttpData.get( 'tile_template', None) or not HttpData.get('data', None) if request.method != 'POST' or \ fg or request.GET.get('API_KEY', 'NO_API_KEY_FOUND') != API_KEY and DEBUG is False or \ HttpData.get('tile_template', None) not in ALLOWED_TILES or \ not cache.redis.exists(tilePrefix) and not DEBUG: return False return True
def is_meta_present_in_request(meta, tile_id): # pragma: no cover """ Update the meta(config) of a tile(widget) """ if meta is not None: tilePrefix = getRedisPrefix(tile_id) if getCache().redis.exists(tilePrefix) is not None: cachedTile = json.loads(getCache().redis.get(tilePrefix)) metaTile = cachedTile['meta']['options'] if 'options' in cachedTile['meta'] else cachedTile['meta'] update_tile_data_from_redis(metaTile, json.loads(meta), None) getCache().set(tilePrefix, json.dumps(cachedTile), sendToWS=False) print(f"(+) Meta of tile {tilePrefix} has been updated") return True print(f"(+) Meta of tile not present") return False
def get_tile(request, tile_key): httpMessage = '' httpStatus_code = 200 redis = MyCache().redis if redis.exists(getRedisPrefix(tile_key)): if request.method == 'DELETE': redis.delete(tile_key) httpMessage = 'Tile\'s data deleted.' if request.method == 'GET': httpMessage = redis.get(tile_key) else: httpMessage = f'{tile_key} key does not exist.' httpStatus_code = 400 return httpMessage, httpStatus_code
def createTile(self, tile_id, value, tile_template): try: dumped_value = json.dumps( dict( id=tile_id, tile_template=tile_template, data=json.loads(value), meta={}, modified=getIsoTime(), )) cache.set(getRedisPrefix(tile_id), dumped_value) return True except: return False
def test_0015_cache_buildFakeData(self): """ Test fake_data generation: integrity of data + save in redis """ for tile in self.ALLOWED_TILES: if tile != 'empty': tileData = buildFakeDataFromTemplate(tile_id=f'test_{tile}', template_name=tile, cache=self.cache) self.assertTrue(tileData is not None) self.assertTrue('data' in tileData) self.assertTrue('id' in tileData) self.assertTrue('tile_template' in tileData) isIdCorrect = json.loads(self.cache.redis.get(getRedisPrefix(f'test_{tile}')))['id'] == f'test_{tile}' self.assertTrue(isIdCorrect) testWithoutCache = buildFakeDataFromTemplate(tile_id='faketest', template_name='Fake_tile', cache=None) testWithCache = buildFakeDataFromTemplate(tile_id='faketest', template_name='Fake_tile', cache=self.cache) self.assertTrue(testWithoutCache is None and testWithCache is None)
def test_1026_test_sensors(self): tilePrefix = getRedisPrefix('test_simple_percentage') lm = MyCache().get(tilePrefix) beforeUpdate = json.loads(lm) test_sensors(tester=self) scheduler = BackgroundScheduler() nbrSensors = scheduleYourSensors(scheduler=scheduler, tester=self) self.assertTrue(nbrSensors >= 21) time.sleep(5) scheduler.shutdown() time.sleep(3) afterUpdate = json.loads(MyCache().get(tilePrefix))['data']['big_value'] isDiff = beforeUpdate != afterUpdate self.assertTrue(isDiff)
def sanity_push_api(request, unsecured): """ Test token, all data present, correct tile_template and tile_id present in cache """ if not checkAccessToken(method='POST', request=request, unsecured=unsecured): return False, HttpResponse('API KEY incorrect', status=401) HttpData = request.POST if not HttpData.get('tile_id', None) or not HttpData.get('tile_template', None) or \ not HttpData.get('data', None): return False, HttpResponseBadRequest('Missing data') if HttpData.get('tile_template', None) not in ALLOWED_TILES: tile_template = HttpData.get('tile_template', None) return False, HttpResponseBadRequest(f'tile_template: {tile_template} is unknow') cache = getCache() tilePrefix = getRedisPrefix(HttpData.get('tile_id', None)) if not cache.redis.exists(tilePrefix) and not DEBUG: return False, HttpResponseBadRequest(f'tile_id: {tilePrefix} is unknow') return True, HttpData
def save_tile(tile_id, template, data, meta): redis_cache = MyCache() tilePrefix = getRedisPrefix(tile_id) if not redis_cache.redis.exists(tilePrefix) and DEBUG: buildFakeDataFromTemplate( tile_id, template, redis_cache) # Build fake data and save it on redis cachedTile = json.loads(redis_cache.redis.get(tilePrefix)) cachedTile['tile_template'] = template cachedTile['data'] = update_tile_data_from_redis(cachedTile['data'], json.loads(data), template) if meta is not None: cachedTile['meta'] = update_meta_if_present(tile_id, meta) redis_cache.set(tilePrefix, json.dumps(cachedTile)) return True
def update_tile_receive(self, tile_id, template_name=None): # pragma: no cover """ Create or update the tile with value send """ tileData = cache.get(tile_id=getRedisPrefix(tile_id)) if tileData is None: if LOG: print(f'{getTimeStr()} (-) No data in key {tile_id} on Redis.', flush=True) print( f'{getTimeStr()} (-) Generating fake data for {tile_id}.', flush=True) data = buildFakeDataFromTemplate(tile_id, template_name, cache) else: data = json.loads(tileData) if isinstance(data, str): data = json.loads(data) self.send(text_data=json.dumps(data))
def testTileUpdate(tester=None, tileId='test_pie_chart', sonde=None, isChartJS=True): """ 1 - Get a tile from the redis cache, store this in tile_txt_data_before 2 - execute the sensors to update the data of the tile 3 - Again, get a tile from the redis cache store this in tile_txt_data_after 4 - Compare the data of tile_txt_data_before vs tile_txt_data_after 5 - If there are the same, update tile data is broken :) """ tilePrefix = getRedisPrefix(tileId) beforeUpdate = json.loads(MyCache().redis.get(tilePrefix)) if tileId == 'test_vbar_chart': sonde(tester=tester, tile_id=tileId, isHorizontal=True) sonde(tester=tester, tile_id=tileId) afterUpdate = json.loads(MyCache().redis.get(tilePrefix)) if isChartJS: isDiff = beforeUpdate['data']['datasets'][0]['data'] != afterUpdate['data']['datasets'][0]['data'] else: isDiff = beforeUpdate['data'] != afterUpdate['data'] tester.assertTrue(isDiff)
def handleHttpError(request): output = 'error' if request.method != 'POST': output = 'Only accept Post request' if request.GET.get('API_KEY', 'NO_API_KEY_FOUND') != API_KEY and DEBUG is False: return HttpResponse('API KEY incorrect', status=401) cache = MyCache() HttpData = request.POST tile_id = HttpData.get('tile_id', None) tile_template = HttpData.get('tile_template', None) data = HttpData.get('data', None) tilePrefix = getRedisPrefix(tile_id) if output == 'error' and (not tile_id or not tile_template or not data): output = 'Missing data' elif output == 'error' and (tile_template not in ALLOWED_TILES): output = f'tile_template: {tile_template} is unknow' elif output == 'error' and (not cache.redis.exists(tilePrefix) and not DEBUG): output = f'tile_id: {tilePrefix} is unknow' return HttpResponseBadRequest(output)
def delete(self, tile_id): if self.redis.exists(getRedisPrefix(tile_id=tile_id)): self.redis.delete(getRedisPrefix(tile_id=tile_id)) return True return False
def update_tile(self, data): """ send to client a single tile config """ self.send(text_data=MyCache().get( tile_id=getRedisPrefix(data['tile_id'])))
def listOfTilesCached(self): listOfTiles = list() for key in self.redis.keys(getRedisPrefix()): listOfTiles.append(key) return listOfTiles
def listOfTilesCached(self): return [key for key in self.redis.keys(getRedisPrefix()) ] if self.isRedisConnected else list()