def info_for(self, ids, related=True): """ Return {id: {'location': location, entities_keys: entities_data}}. If related is True, return list of entities data, otherwise - only ids. """ cache_prefix = self.model.cache_prefix cached_locations = cache.get_many([cache_prefix+str(id) for id in ids]) cached_ids = [] res = {} for key, entity in cached_locations.iteritems(): id = int(key[len(cache_prefix):]) cached_ids.append(id) res[id] = entity other_ids = set(ids) - set(cached_ids) if len(other_ids) > 0: other_res = dict((id, {}) for id in other_ids) comments_data = FEATURES_MODELS['comments'].objects.get_for(Location, other_ids) ct_id = ContentType.objects.get_for_model(self.model).id locations = self.filter(id__in=other_ids).select_related() participants_ids = [] for loc in locations: # TODO: instance is a dict in all entities other_res[loc.id] = {'instance': loc, 'ct': ct_id} # TODO: do we need tools data here? for name, model in ENTITIES_MODELS.iteritems(): if name == 'participants': continue other_res[loc.id][name] = loc.get_entities(name)( limit=settings.LIST_COUNT['tools']) # Get participants participants_data = loc.get_entities('participants')(limit=settings.LIST_COUNT['participants']) participants_ids += participants_data['ids'] other_res[loc.id]['participants'] = { 'count': participants_data['count'], 'entities': [{'id': id} for id in participants_data['ids']], } # Comments other_res[loc.id]['comments'] = comments_data[loc.id] profiles_by_id = ENTITIES_MODELS['participants'].objects.only('id', 'first_name', 'last_name', 'intro', 'rating') \ .in_bulk(set(participants_ids)) for loc in locations: for entity in other_res[loc.id]['participants']['entities']: entity.update(profiles_by_id[entity['id']].display_info()) res.update(other_res) cache_res = dict((cache_prefix+str(id), other_res[id]) for id in other_res) cache.set_many(cache_res, 60) # TODO: specify time outside of this method if related: for name, model in ENTITIES_MODELS.iteritems(): if name == 'participants': continue e_ids = set(e_id for id in ids for e_id in res[id][name]['ids']) e_info = model.objects.info_for(e_ids, related=False) for id in ids: res[id][name]['entities'] = [e_info[e_id] for e_id in res[id][name]['ids'] if e_id in e_info] return res
def handle(self, *args, **options): from elements.models import ENTITIES_MODELS for model in ENTITIES_MODELS.values(): for instance in model.objects.all(): instance.update_rating()