def _getAcceptedOrgsList(self, description, params, filter, use_cache): """Returns a list with all accepted orgs. Args: description: the description of the list params: the params to use filter: the filter to use use_cache: whether or not to use the cache """ logic = params['logic'] order = ['name'] if not use_cache: fun = self._getData else: # only cache if all profiles are created fun = soc.cache.logic.cache(self._getData) entities = fun(logic.getModel(), filter, order, logic) result = dicts.rename(params, params['list_params']) result['action'] = (redirects.getHomeRedirect, params) result['description'] = description result['pagination'] = 'soc/list/no_pagination.html' result['data'] = entities return result
def _getOrgsWithProfilesList(self, program_entity, org_view, description, use_cache): """Returns a content of a list of all organizations that got accepted to the program and there is an Organization-like entity in datastore. Args: program_entity: program which list the organizations for org_view: a view for organization model description: the description of the list use_cache: whether or not to use the memcache """ ao_params = org_view.getParams().copy() org_logic = ao_params['logic'] filter = {'scope': program_entity, 'status': ['new', 'active']} order = ['name'] if not use_cache: entities = org_logic.getForFields(filter=filter, order=order) else: # only cache if all profiles are created fun = soc.cache.logic.cache(self._getData) entities = fun(org_logic.getModel(), filter, order, org_logic) # TODO(LIST) result = dicts.rename(ao_params, ao_params['list_params']) result['action'] = (redirects.getHomeRedirect, ao_params) result['description'] = description result['pagination'] = 'soc/list/no_pagination.html' result['data'] = entities return result
def viewResults(self, request, access_type, page_name=None, params=None, **kwargs): """View for SurveyRecord and SurveyRecordGroup. """ results_logic = params['logic'].getRecordLogic() user = user_logic.getForCurrentAccount() # TODO(ajaksu): use the named parameter link_id from the re if request.path == '/survey/show/user/' + user.link_id: records = tuple(user.surveys_taken.run()) context = responses.getUniversalContext(request) context['content'] = records[0].survey.survey_content responses.useJavaScript(context, params['js_uses_all']) context['page_name'] = u'Your survey records.' else: entity, context = self.getContextEntity(request, page_name, params, kwargs) if context is None: # user cannot see this page, return error response return entity context['content'] = entity.survey_content can_write = False rights = self._params['rights'] try: rights.checkIsSurveyWritable({'key_name': entity.key().name(), 'prefix': entity.prefix, 'scope_path': entity.scope_path, 'link_id': entity.link_id,}, 'key_name') can_write = True except out_of_band.AccessViolation: pass filter = self._params.get('filter') or {} # if user can edit the survey, show everyone's results if can_write: filter['survey'] = entity else: filter.update({'user': user, 'survey': entity}) limit = self._params.get('limit') or 1000 offset = self._params.get('offset') or 0 order = self._params.get('order') or [] idx = self._params.get('idx') or 0 records = results_logic.getForFields(filter=filter, limit=limit, offset=offset, order=order) updates = dicts.rename(params, params['list_params']) context.update(updates) context['results'] = records, records template = 'soc/survey/results_page.html' return responses.respond(request, template, context=context)
def render(self, survey, params, filter=filter, limit=1000, offset=0, order=[], idx=0, context={}): """ renders list of survey results params: survey: current survey params: dict of params for rendering list filter: filter for list results limit: limit for list results offset: offset for list results order: order for list results idx: index for list results context: context dict for template """ survey_logic = params['logic'] record_logic = survey_logic.getRecordLogic() filter = {'survey': survey} data = record_logic.getForFields(filter=filter, limit=limit, offset=offset, order=order) params['name'] = "Survey Results" content = { 'idx': idx, 'data': data, 'logic': record_logic, 'limit': limit, } updates = dicts.rename(params, params['list_params']) content.update(updates) contents = [content] if len(content) == 1: content = content[0] key_order = content.get('key_order') context['list'] = Lists(contents) # TODO(ajaksu) is this the best way to build the results list? for list_ in context['list']._contents: if len(list_['data']) < 1: return "<p>No Survey Results Have Been Submitted</p>" list_['row'] = 'soc/survey/list/results_row.html' list_['heading'] = 'soc/survey/list/results_heading.html' list_['description'] = 'Survey Results:' context['properties'] = survey.survey_content.orderedProperties() context['entity_type'] = "Survey Results" context['entity_type_plural'] = "Results" context['no_lists_msg'] = "No Survey Results" path = (survey.entity_type().lower(), survey.prefix, survey.scope_path, survey.link_id) context['grade_action'] = "/%s/grade/%s/%s/%s" % path markup = loader.render_to_string('soc/survey/results.html', dictionary=context).strip('\n') return markup
def _listStudentTasks(self, data, params): """Returns a list with all entities specified in data. """ result = dicts.rename(params, params['list_params']) result['action'] = (redirects.getPublicRedirect, params) result['data'] = data result['pagination'] = 'soc/list/no_pagination.html' # TODO(LIST) return result
def testRename(self): """Tests that keys in the target dict are renamed with value of the same key in another dict. """ target = {"wan": 1, "too": 2, "tree": 3} keys = {"wan": "one", "too": "two", "tree": "three"} expected_dict = {"one": 1, "two": 2, "three": 3} self.assertEqual(dicts.rename(target, keys), expected_dict) target = {} expected_dict = {} self.assertEqual(dicts.rename(target, keys), expected_dict) target = {"wan": 1, "too": 2, "tree": 3} keys = {} expected_dict = {} self.assertEqual(dicts.rename(target, keys), expected_dict) target = {"wan": 1, "too": 2, "tree": 3} keys = {"for": 4} expected_dict = {} self.assertEqual(dicts.rename(target, keys), expected_dict)
def testRename(self): """Tests that keys in the target dict are renamed with value of the same key in another dict. """ target = {'wan': 1, 'too': 2, 'tree': 3} keys = {'wan': 'one', 'too': 'two', 'tree': 'three'} expected_dict = {'one': 1, 'two': 2, 'three': 3} self.assertEqual(dicts.rename(target, keys), expected_dict) target = {} expected_dict = {} self.assertEqual(dicts.rename(target, keys), expected_dict) target = {'wan': 1, 'too': 2, 'tree': 3} keys = {} expected_dict = {} self.assertEqual(dicts.rename(target, keys), expected_dict) target = {'wan': 1, 'too': 2, 'tree': 3} keys = {'for': 4} expected_dict = {} self.assertEqual(dicts.rename(target, keys), expected_dict)
def getListGenerator(request, params, idx=0): """Returns a dict with fields used for rendering lists. Args: request: the Django HTTP request object params: a dict with params for the View this list belongs to idx: the index of this list """ content = { 'idx': idx, } updates = dicts.rename(params, params['list_params']) content.update(updates) return content
def render(self, this_survey, params, filter=filter, limit=1000, offset=0, order=[], idx=0, context={}): from soc.logic.models.survey import results_logic as results_logic logic = results_logic filter = { 'this_survey': this_survey } data = logic.getForFields(filter=filter, limit=limit, offset=offset, order=order) params['name'] = "Survey Results" content = { 'idx': idx, 'data': data, #'export': export_link, TODO - export to CVS 'logic': logic, 'limit': limit, } updates = dicts.rename(params, params['list_params']) content.update(updates) contents = [content] #content = [i for i in contents if i.get('idx') == export] if len(content) == 1: content = content[0] key_order = content.get('key_order') #if key_order: TODO - list order #data = [i.toDict(key_order) for i in content['data']] #filename = "export_%d" % export #return self.csv(request, data, filename, params, key_order) from soc.views import helper import soc.logic.lists context['list'] = soc.logic.lists.Lists(contents) for list in context['list']._contents: list['row'] = 'soc/survey/list/results_row.html' list['heading'] = 'soc/survey/list/results_heading.html' list['description'] = 'Survey Results:' context['properties'] = this_survey.this_survey.dynamic_properties() context['entity_type'] = "Survey Results" context['entity_type_plural'] = "Results" context['no_lists_msg'] = "No Survey Results" from django.template import loader markup = loader.render_to_string('soc/survey/results.html', dictionary=context).strip('\n') return markup
def acceptedProjects(self, request, access_type, page_name=None, params=None, filter=None, **kwargs): """See base.View.list. """ contents = [] logic = params['logic'] program_entity = logic.getFromKeyFieldsOr404(kwargs) filter = { 'status': 'accepted', 'program': program_entity } fmt = {'name': program_entity.name} description = self.DEF_ACCEPTED_PROJECTS_MSG_FMT % fmt from soc.views.models import student_project as sp_view ap_params = sp_view.view.getParams().copy() # accepted projects fun = soc.cache.logic.cache(self._getData) ap_logic = ap_params['logic'] entities = fun(logic.getModel(), filter, order=None, logic=ap_logic) ap_list = dicts.rename(ap_params, ap_params['list_params']) ap_list['action'] = (redirects.getPublicRedirect, ap_params) ap_list['description'] = description ap_list['pagination'] = 'soc/list/no_pagination.html' ap_list['heading'] = 'soc/student_project/list/heading_all.html' ap_list['row'] = 'soc/student_project/list/row_all.html' ap_list['data'] = entities contents.append(ap_list) params = params.copy() return self._list(request, params, contents, page_name)
def getListContent(request, params, filter=None, order=None, idx=0, need_content=False): """Returns a dict with fields used for rendering lists. TODO(dbentley): we need better terminology. List, in this context, can have one of two meanings. Meaning 1: the underlying list, which may be very large. Meaning 2: the returned list, which is at most 'limit' items. Args: request: the Django HTTP request object params: a dict with params for the View this list belongs to filter: a filter for this list order: the order which should be used for the list (in getForFields format) idx: the index of this list need_content: iff True will return None if there is no data Returns: A dictionary with the following values set: { 'data': list data to be displayed 'main': url to list main template 'pagination': url to list pagination template 'row': url to list row template 'heading': url to list heading template 'limit': max amount of items per page, 'newest': url to first page of the list 'prev': url to previous page 'next': url to next page 'first': offset of the first item in the list 'last': offset of the last item in the list } """ # TODO(dbentley): this appears to be unnecessary indirection, # as we only use this logic for getForFields, which is never overridden logic = params['logic'] limit_key = makeLimitKey(idx) # offset_key = makeOffsetKey(idx) # offset_linkid_key = makeOffsetLinkidKey(idx) # reverse_direction_key = makeReverseDirectionKey(idx) list_params = getListParameters(request, idx) limit, offset = list_params['limit'], list_params['offset'] offset_linkid = list_params['offset_linkid'] reverse_direction = list_params['reverse_direction'] pagination_form = makePaginationForm(request, list_params['limit'], limit_key) if offset_linkid: if filter is None: filter = {} if reverse_direction: filter['link_id <'] = offset_linkid else: filter['link_id >'] = offset_linkid if order is None: order = [] if reverse_direction: order.append('-link_id') else: order.append('link_id') # Fetch one more to see if there should be a 'next' link data = logic.getForFields(filter=filter, limit=limit+1, offset=offset, order=order) if need_content and not data: return None more = len(data) > limit if reverse_direction: data.reverse() if more: if reverse_direction: data = data[1:] else: data = data[:limit] should_have_next_link = True if not reverse_direction and not more: should_have_next_link = False # Calculating should_have_previous_link is tricky. It's possible we could # be creating a previous link to a page that would have 0 entities. # That would be suboptimal; what's a better way? should_have_previous_link = False if offset_linkid: should_have_previous_link = True if reverse_direction and not more: should_have_previous_link = False if data: first_displayed_item = data[0] last_displayed_item = data[-1] else: class Dummy(object): pass first_displayed_item = last_displayed_item = Dummy() first_displayed_item.link_id = None newest = next = prev = export_link = '' link_creator = LinkCreator(request, idx, limit) if params.get('list_key_order'): export_link = link_creator.create(export=True) if should_have_next_link: next = link_creator.create(offset_linkid=last_displayed_item.link_id) if should_have_previous_link: prev = link_creator.create(offset_linkid=first_displayed_item.link_id, reverse_direction=True) newest = link_creator.create(offset_linkid='') # TODO(dbentley): add a "last" link (which is now possible because we can # query with a reverse linkid sorting content = { 'idx': idx, 'data': data, 'export': export_link, 'first': first_displayed_item.link_id, 'last': last_displayed_item.link_id, 'logic': logic, 'limit': limit, 'newest': newest, 'next': next, 'pagination_form': pagination_form, 'prev': prev, } updates = dicts.rename(params, params['list_params']) content.update(updates) return content
def getListContent(request, params, filter=None, order=None, idx=0, need_content=False): """Returns a dict with fields used for rendering lists. TODO(dbentley): we need better terminology. List, in this context, can have one of two meanings. Meaning 1: the underlying list, which may be very large. Meaning 2: the returned list, which is at most 'limit' items. Args: request: the Django HTTP request object params: a dict with params for the View this list belongs to filter: a filter for this list order: the order which should be used for the list (in getForFields format) idx: the index of this list need_content: iff True will return None if there is no data Returns: A dictionary with the following values set: { 'data': list data to be displayed 'main': url to list main template 'pagination': url to list pagination template 'row': url to list row template 'heading': url to list heading template 'limit': max amount of items per page, 'newest': url to first page of the list 'prev': url to previous page 'next': url to next page 'first': offset of the first item in the list 'last': offset of the last item in the list } """ # TODO(dbentley): this appears to be unnecessary indirection, # as we only use this logic for getForFields, which is never overridden logic = params['logic'] limit_key, offset_key = makeLimitKey(idx), makeOffsetKey(idx) list_params = getListParameters(request, idx) limit, offset = list_params['limit'], list_params['offset'] pagination_form = makePaginationForm(request, list_params['limit'], limit_key) # Fetch one more to see if there should be a 'next' link data = logic.getForFields(filter=filter, limit=limit+1, offset=offset, order=order) if need_content and not data: return None more = len(data) > limit if more: del data[limit:] newest = next = prev = export_link = '' base_params = dict(i for i in request.GET.iteritems() if i[0].startswith('offset_') or i[0].startswith('limit_')) if params.get('list_key_order'): export_link = generateLinkForRequest(request, base_params, {'export': idx}) if more: # TODO(dbentley): here we need to implement a new field "last_key" next = generateLinkForRequest(request, base_params, {offset_key: offset + limit, limit_key: limit}) if offset > 0: # TODO(dbentley): here we need to implement previous in the good way. prev = generateLinkForRequest(request, base_params, {offset_key: max(0, offset-limit), limit_key: limit}) if offset > limit: # Having a link to the first doesn't make sense on the first page (we're on # it). It also doesn't make sense on the second page (because the first # page is the previous page). # NOTE(dbentley): I personally disagree that it's simpler to do that way, # because sometimes you want to go to the first page without having to # consider what page you're on now. newest = generateLinkForRequest(request, base_params, {offset_key: 0, limit_key: limit}) content = { 'idx': idx, 'data': data, 'export': export_link, 'first': offset+1, 'last': len(data) > 1 and offset+len(data) or None, 'logic': logic, 'limit': limit, 'newest': newest, 'next': next, 'pagination_form': pagination_form, 'prev': prev, } updates = dicts.rename(params, params['list_params']) content.update(updates) return content
def getListContentForData(request, params, data=None, idx=0, limit=DEF_DEFAULT_PAGINATION, offset=0, need_content=False): """Returns a dict with fields used for rendering lists. TODO(dbentley): we need better terminology. List, in this context, can have one of two meanings. Meaning 1: the underlying list, which may be very large. Meaning 2: the returned list, which is at most 'limit' items. Args: request: the Django HTTP request object params: a dict with params for the View this list belongs to data: list of entities to fill the list with idx: the index of this list limit: number of entities on a single list page offset: length of offset of the entities need_content: iff True will return None if there is no data Returns: See getListContent() for details. """ if need_content and not data: return None # TODO(dbentley): this appears to be unnecessary indirection, # as we only use this logic for getForFields, which is never overridden logic = params['logic'] limit_key, offset_key = makeLimitKey(idx), makeOffsetKey(idx) pagination_form = makePaginationForm(request, limit, limit_key) more = len(data) > limit if more: del data[limit:] newest = next = prev = export_link = '' base_params = dict( i for i in request.GET.iteritems() if i[0].startswith('offset_') or i[0].startswith('limit_')) if params.get('list_key_order'): export_link = generateLinkForRequest(request, base_params, {'export': idx}) if more: # TODO(dbentley): here we need to implement a new field "last_key" next = generateLinkForRequest(request, base_params, { offset_key: offset + limit, limit_key: limit }) if offset > 0: # TODO(dbentley): here we need to implement previous in the good way. prev = generateLinkForRequest(request, base_params, { offset_key: max(0, offset - limit), limit_key: limit }) if offset > limit: # Having a link to the first doesn't make sense on the first page (we're on # it). It also doesn't make sense on the second page (because the first # page is the previous page). # NOTE(dbentley): I personally disagree that it's simpler to do that way, # because sometimes you want to go to the first page without having to # consider what page you're on now. newest = generateLinkForRequest(request, base_params, { offset_key: 0, limit_key: limit }) content = { 'idx': idx, 'data': data, 'export': export_link, 'first': offset + 1, 'last': len(data) > 1 and offset + len(data) or None, 'logic': logic, 'limit': limit, 'newest': newest, 'next': next, 'pagination_form': pagination_form, 'prev': prev, } updates = dicts.rename(params, params['list_params']) content.update(updates) return content