def sync_icus(self): self.prepare() icus_df = self._shdb.get_icus() icus_df.rename(columns={'icu_name': 'name'}, inplace=True) for _, icu in icus_df.iterrows(): icu_dict = icu.to_dict() icu_name = icu_dict["name"] region = icu_dict.pop('region', None) db_icu = self._icus.get(icu_name, None) # Maybe create region first. if region is not None: if region not in self._regions: region_id = self._store.add_region( self._default_admin, store.Region(name=region)) self._regions[region] = region_id logging.info("Adding Region {}".format(region)) icu_dict['region_id'] = self._regions[region] # Update icu now if db_icu is not None: manager = self._managers.get(db_icu.icu_id, self._default_admin) self._store.update_icu(manager, db_icu.icu_id, icu_dict) logging.info("Updating ICU {}".format(icu_name)) else: new_icu = store.ICU(**icu_dict) icu_id = self._store.add_icu(self._default_admin, new_icu) self._store.assign_user_as_icu_manager( self._default_admin, self._default_admin, icu_id) logging.info("Adding ICU {}".format(icu_name))
async def test_process_update(self): with open(UPDATES_FILE, 'r') as fp: data = json.load(fp) example_update = data['result'][0] # This should lead to a unknown user. await self.processor.process_update(example_update) self.assertGreater(len(self.processor.bot.client.requests), 0) msg_json = self.processor.bot.client.requests[-1].body self.assertIn('Cannot identify', msg_json.decode()) # Now makes a real user and pass a token along admin_id = self.db.add_default_admin() icu_id = self.db.add_icu(admin_id, store.ICU(name='icu')) icu = self.db.get_icu(icu_id) user_id = self.db.add_user_to_icu( admin_id, icu_id, store.User(name='patrick') ) user = self.db.get_user(user_id) # TODO(olivier): use authenticator here when available. token_encoder = token.TokenEncoder(self.config) jwt = token_encoder.encode_data(user, icu) example_update['message']['text'] = f'/start {jwt}' await self.processor.process_update(example_update) self.assertGreater(len(self.processor.bot.client.requests), 0) msg_json = self.processor.bot.client.requests[-1].body self.assertIn('registered', msg_json.decode())
def test_user_not_in_icu(self): other_icu_id = self.db.add_icu(self.admin_id, store.ICU(name='other')) token = self.db.add_token( self.admin_id, store.UserICUToken(user_id=self.user_id, icu_id=other_icu_id)) self.assertIsNotNone(self.authenticator.decode(token)) self.assertIsNone(self.authenticator.authenticate(token))
def post(self): values = self.parse_from_body(store.ICU) values["is_active"] = values.get("is_active", "off") == 'on' values['region_id'] = int(values.get('region_id', -1)) id_key = 'icu_id' icu_id = values.pop(id_key, '') try: if not icu_id: icu_id = self.db.add_icu(self.user.user_id, store.ICU(**values)) else: self.db.update_icu(self.user.user_id, icu_id, values) except Exception as e: logging.error(f'Cannot save ICU: {e}') values[id_key] = icu_id return self.do_render(store.ICU(**values), error=True) return self.redirect(ListICUsHandler.ROUTE)
def populate_db(self): self.admin_id = self.db.add_default_admin() r1 = self.db.add_region(self.admin_id, store.Region(name='IDF')) r2 = self.db.add_region(self.admin_id, store.Region(name='PACA')) self.db.add_icu( self.admin_id, store.ICU(name='icu1', region_id=r1, dept='75', city='Paris', telephone='+65123')) self.db.add_icu( self.admin_id, store.ICU(name='icu2', region_id=r1, dept='75', city='Paris')) self.db.add_icu( self.admin_id, store.ICU(name='icu3', region_id=r1, dept='92', city='Clamart')) self.db.add_icu( self.admin_id, store.ICU(name='icu4', region_id=r1, dept='93', city='Bobigny')) self.db.add_icu( self.admin_id, store.ICU(name='icu5', region_id=r1, dept='93', city='Saint-Denis')) self.db.add_icu( self.admin_id, store.ICU(name='icu6', region_id=r1, dept='94', city='Vitry')) self.db.add_icu( self.admin_id, store.ICU(name='icu7', region_id=r1, dept='94', city='Creteil')) self.db.add_icu( self.admin_id, store.ICU(name='icu8', region_id=r1, dept='94', city='Creteil')) self.db.add_icu( self.admin_id, store.ICU(name='icu9', region_id=r2, dept='13', city='Marseille')) self.icus = self.db.get_icus() self.regions = self.db.get_regions() self.insert_time = datetime.datetime(2020, 4, 8, 11, 13) # Adding bedcounts: here we cheat a bit since we insert zeros counts # to have those bedcounts on the map and simplify the maths. for icu in self.icus: count = store.BedCount(icu_id=icu.icu_id, create_date=self.insert_time) self.db.update_bed_count_for_icu(self.admin_id, count)
def test_schedule_message(self): msg = message.Message(self.icu, self.user, url='url') self.assertEqual(len(self.scheduler.timeouts), 0) delay = 100 success = self.scheduler.schedule_message(msg, delay=delay) self.assertTrue(success) self.assertEqual(len(self.scheduler.timeouts), 1) key = self.user.user_id, self.icu.icu_id timeout = self.scheduler.timeouts.get(key, None) self.assertIsNotNone(timeout) self.assertTrue(timeout.when, fake_now + delay) # another message with longer delay: not in offset = 100 success = self.scheduler.schedule_message(msg, delay=delay + offset) self.assertFalse(success) # another message with smaller delay: in offset = -2 success = self.scheduler.schedule_message(msg, delay=delay + offset) self.assertTrue(success) timeout = self.scheduler.timeouts.get(key, None) self.assertIsNotNone(timeout) self.assertTrue(timeout.when, fake_now + delay + offset) # Another user same icu: another entry user = store.User(name='jacqueline', telephone='12333') userid = self.db.add_user_to_icu(self.admin, self.icu.icu_id, user) user = self.db.get_user(userid) offset = 100 msg2 = message.Message(self.icu, user, url='url') success = self.scheduler.schedule_message(msg2, delay=delay + offset) self.assertEqual(len(self.scheduler.timeouts), 2) # Same user new icu: new entry icu = store.ICU(name='anothericu') icuid = self.db.add_icu(self.admin, store.ICU(name='my_icu')) self.db.assign_user_to_icu(self.admin, self.user.user_id, icuid) msg3 = message.Message(icu, self.user, url='url') success = self.scheduler.schedule_message(msg3, delay=delay + offset) self.assertEqual(len(self.scheduler.timeouts), 3)
def setUp(self): super().setUp() self.config = config.Config('resources/test.toml') self.db = store.create_store_factory_for_sqlite_db( self.config).create() self.formatter = message_formatter.MessageFormatter() self.admin_id = self.db.add_default_admin() self.icu_id = self.db.add_icu(self.admin_id, store.ICU(name='rea')) self.icu = self.db.get_icu(self.icu_id) self.user_id = self.db.add_user_to_icu(self.admin_id, self.icu_id, store.User(name='user')) self.user = self.db.get_user(self.user_id)
def setUp(self): self.config = config.Config(self.TEST_CONFIG) self.server = server.AnalyticsServer(self.config, port=8866) self.db = self.server.db_factory.create() self.admin_id = self.db.add_default_admin() self.icu_id = self.db.add_icu(self.admin_id, store.ICU(name='icu')) self.user_id = self.db.add_user_to_icu( self.admin_id, self.icu_id, store.User(name='user', consent=True, is_active=True)) self.user = self.db.get_user(self.user_id) self.icu = self.db.get_icu(self.icu_id) super().setUp()
def setUp(self): super().setUp() self.config = config.Config('resources/test.toml') self.db = store.create_store_factory_for_sqlite_db(self.config).create() self.queue = tornado.queues.Queue() self.admin = self.db.add_default_admin() icu_id = self.db.add_icu(self.admin, store.ICU(name='icu1')) self.icu = self.db.get_icu(icu_id) self.bot = mock_bot.MockTelegramBot(self.config) self.sender = sender.Sender( self.config, self.db, self.queue, tg_bot=self.bot )
def setUp(self): super().setUp() self.config = config.Config('resources/test.toml') factory = store.create_store_factory_for_sqlite_db(self.config) self.db = factory.create() self.admin_id = self.db.add_default_admin() self.icu_id = self.db.add_icu(self.admin_id, store.ICU(name='hospital')) self.icu = self.db.get_icu(self.icu_id) self.user_id = self.db.add_user_to_icu(self.admin_id, self.icu_id, store.User(name='michel')) self.user = self.db.get_user(self.user_id) self.authenticator = authenticator.Authenticator(self.config, self.db)
def do_render(self, icu, error=False): if self.user.is_admin: regions = self.db.get_regions() if not self.user.is_admin: regions = [e.region for e in self.user.managed_icus] regions.sort(key=lambda r: r.name) icu = icu if icu is not None else store.ICU() if icu.is_active is None: icu.is_active = True return self.render("icu.html", icu=icu, regions=regions, error=error, list_route=ListICUsHandler.ROUTE)
def setUp(self): super().setUp() self.config = config.Config('resources/test.toml') self.db = store.create_store_for_sqlite_db(self.config) self.queue = MockQueue() self.scheduler = scheduler.MessageScheduler(self.config, self.db, self.queue) self.admin = self.db.add_default_admin() icuid = self.db.add_icu(self.admin, store.ICU(name='my_icu')) self.icu = self.db.get_icu(icuid) user = store.User(name='michel', telephone='1234') userid = self.db.add_user_to_icu(self.admin, icuid, user) self.user = self.db.get_user(userid)
def setUp(self): super().setUp() self.config = config.Config('resources/test.toml') self.server = server.BackOfficeServer(self.config, port=8889) self.app = self.server.make_app() self.request = tornado.httpserver.HTTPRequest( method='GET', uri=bedcounts.ListBedCountsHandler.ROUTE, headers=None, body=None) self.request.connection = MockConnection() self.handler = bedcounts.ListBedCountsHandler(self.app, self.request) self.handler.initialize() self.admin_id = self.handler.db.add_default_admin() rid = self.handler.db.add_region(self.admin_id, store.Region(name='myregion')) self.icuid = self.handler.db.add_icu( self.admin_id, store.ICU(name='iuc1', region_id=rid))
def do_render(self, icu, error=False): if self.current_user.is_admin: regions = self.db.get_regions() if not self.current_user.is_admin: regions = [e.region for e in self.current_user.managed_icus] regions.sort(key=lambda r: r.name) icus = self.db.get_managed_icus(self.current_user.user_id) depts = sorted(set([i.dept for i in icus])) cities = sorted(set([i.city for i in icus])) icu = icu if icu is not None else store.ICU() if icu.is_active is None: icu.is_active = True return self.render("icu.html", icu=icu, depts=json.dumps(depts), cities=json.dumps(cities), regions=regions, error=error, list_route=ListICUsHandler.ROUTE)
def test_schedule(self): self.assertEqual(len(self.scheduler.timeouts), 0) delay = 200 success = self.scheduler.schedule(self.user, self.icu, delay=delay) self.assertTrue(success) self.assertEqual(len(self.scheduler.timeouts), 1) # New user, in icu user1 = store.User(name='jacqueline', telephone='12333') userid1 = self.db.add_user_to_icu(self.admin, self.icu_id, user1) user1 = self.db.get_user(userid1) success = self.scheduler.schedule(user1, self.icu, delay=delay) self.assertTrue(success) self.assertEqual(len(self.scheduler.timeouts), 2) # New user, not in icu user2 = store.User(name='armand', telephone='127313') userid2 = self.db.add_user(user2) user2 = self.db.get_user(userid2) success = self.scheduler.schedule(user2, self.icu, delay=delay) self.assertFalse(success) self.assertEqual(len(self.scheduler.timeouts), 2) # New user, in icu but not active user3 = store.User(name='armande', telephone='15313', is_active=False) userid3 = self.db.add_user_to_icu(self.admin, self.icu_id, user3) user3 = self.db.get_user(userid3) success = self.scheduler.schedule(user3, self.icu, delay=delay) self.assertFalse(success) self.assertEqual(len(self.scheduler.timeouts), 2) # New user, in new but inactive icu inactive_icu_id = self.db.add_icu( self.admin, store.ICU(name='inactive_icu', is_active=False)) inactive_icu = self.db.get_icu(inactive_icu_id) user4 = store.User(name='armande', telephone='15313', is_active=True) userid4 = self.db.add_user_to_icu(self.admin, inactive_icu_id, user4) user4 = self.db.get_user(userid4) success = self.scheduler.schedule(user4, inactive_icu, delay=delay) self.assertFalse(success) self.assertEqual(len(self.scheduler.timeouts), 2)
def sync_icus(self, icus_df, force_update=False): self.prepare() # pandas sometimes maps missing values (for example in CSV files) to NA # but NA values are rejected by our SQL layer, so we replace them with None icus_df = icus_df.replace({pd.NA: None}) for _, icu in icus_df.iterrows(): icu_dict = icu.to_dict() icu_name = icu_dict["name"] region = icu_dict.pop('region', None) db_icu = self.db.get_icu_by_name(icu_name) if db_icu is not None and not force_update: continue # Maybe create region first. if region is not None: regions = {x.name: x.region_id for x in self.db.get_regions()} if region not in regions: self.db.add_region(self._default_admin, store.Region(name=region)) logging.info("Adding Region {}".format(region)) icu_dict['region_id'] = self.db.get_region_by_name( region).region_id # If an ICU exists with the same name, update: if db_icu is not None: manager = self._managers.get(db_icu.icu_id, [ self._default_admin, ])[0] logging.info(manager) self.db.update_icu(manager, db_icu.icu_id, icu_dict) logging.info("Updating ICU {}".format(icu_name)) # Or insert new ICU: else: new_icu = store.ICU(**icu_dict) icu_id = self.db.add_icu(self._default_admin, new_icu) self.db.assign_user_as_icu_manager(self._default_admin, self._default_admin, icu_id) logging.info("Adding ICU {}".format(icu_name))
def sync_icus(self, icus_df, force_update=False): self.prepare() for _, icu in icus_df.iterrows(): icu_dict = icu.to_dict() icu_name = icu_dict["name"] region = icu_dict.pop('region', None) db_icu = self._store.get_icu_by_name(icu_name) if db_icu is not None and not force_update: continue # Maybe create region first. if region is not None: regions = { x.name: x.region_id for x in self._store.get_regions() } if region not in regions: region_id = self._store.add_region( self._default_admin, store.Region(name=region)) logging.info("Adding Region {}".format(region)) icu_dict['region_id'] = self._store.get_region_by_name( region).region_id # If an ICU exists with the same name, update: if db_icu is not None: manager = self._managers.get(db_icu.icu_id, self._default_admin)[0] logging.info(manager) self._store.update_icu(manager, db_icu.icu_id, icu_dict) logging.info("Updating ICU {}".format(icu_name)) # Or insert new ICU: else: new_icu = store.ICU(**icu_dict) icu_id = self._store.add_icu(self._default_admin, new_icu) self._store.assign_user_as_icu_manager(self._default_admin, self._default_admin, icu_id) logging.info("Adding ICU {}".format(icu_name))
def migrate_icus(self): icus_df = self.old_db.get_icus() logging.info('migrating {} icus'.format(icus_df.shape[0])) regions = dict() for _, icu_row in icus_df.iterrows(): icu_dict = icu_row.to_dict() # We cannot set the id old_icu_id = icu_dict.pop('icu_id') # TODO(olivier): remove this! region_name = icu_dict.pop('region', 'Grand-Est') if region_name is not None and region_name not in regions: region = store.Region(name=region_name) region_id = self.new_db.add_region(self.admin_id, region) regions[region_name] = region_id region_id = regions.get(region_name, None) if region_id is not None: icu_dict['region_id'] = region_id else: logging.error(f"Unknown region {region_name}.") name = icu_dict.pop('icu_name', '-') icu_dict['name'] = name self.new_db.add_icu(self.admin_id, store.ICU(**icu_dict)) logging.info(f'adding icus {name}')
def add_icu(self, name="icu", region_id=None, is_active=True): return self.db.add_icu( self.sync._default_admin, store.ICU(name=name, region_id=region_id, is_active=is_active))