def reopen(self, request, pk): obj = self.get_object() closed_logs = obj.logs.filter( code__in=["COMPLAINT_CLOSED", "COMPLAINT_VOID"]) # complaint void if not closed_logs.exists(): return DRFResponse( "Cannot reopen a complaint that is not closed or void", status=status.HTTP_400_BAD_REQUEST) last_closed = closed_logs.order_by("-created").first() notes = u"Complaint reopened.\nOriginally {action_name} {closed_date} by {closed_by}.".format( action_name="voided" if last_closed.code == "COMPLAINT_VOID" else "closed", closed_date=last_closed.created.strftime("%d/%m/%Y %H:%M"), closed_by=last_closed.created_by.username, ) notes += u"\n\n" + last_closed.notes event = event_registry.get_event("complaint")() event.process(obj.eod.case, created_by=request.user, notes=notes.strip(), complaint=obj, code="COMPLAINT_REOPENED") obj.resolved = None obj.save() obj.eod.case.complaint_flag = True obj.eod.case.save() closed_logs.delete() return DRFResponse(status=status.HTTP_204_NO_CONTENT)
def search_for_personal_details(self, request, reference=None, **kwargs): """ You can only call this endpoint if the case doesn't have any personal_details record attached. This is by design as it feels slighly more secure than allowing clients to use a dedicated endpoint that they can call whenever they want. If things change in the future, feel free to add a dedicated endpoint for this though. Should return just ('reference', 'full_name', 'postcode', 'dob') and should NOT include vulnerable users. """ obj = self.get_object() if obj.personal_details: return DRFResponse( {'error': 'This case is already linked to a Person'}, status=status.HTTP_400_BAD_REQUEST ) person_q = request.QUERY_PARAMS.get('person_q', '') or '' if len(person_q) >= 3: users = PersonalDetails.objects.filter( full_name__icontains=person_q ).exclude(vulnerable_user=True) else: users = [] data = [BarePersonalDetailsSerializer(user).data for user in users] return DRFResponse(data)
def get(self, *args, **kwargs): try: qs = self.get_queryset() except Http404: return DRFResponse(status=status.HTTP_404_NOT_FOUND) data = self.serializer_class(qs).data return DRFResponse(data)
def list_by_event_key(self, request, event_key, *args, **kwargs): try: event = event_registry.get_event(event_key) except ValueError: return DRFResponse({"detail": "Not found"}, status=status.HTTP_404_NOT_FOUND) response_data = self.format_codes(event.get_ordered_codes()) return DRFResponse(response_data, status=status.HTTP_200_OK)
def add_event(self, request, pk): obj = self.get_object() form = ComplaintLogForm(complaint=obj, data=request.DATA) if form.is_valid(): form.save(request.user) return DRFResponse(status=status.HTTP_204_NO_CONTENT) return DRFResponse(dict(form.errors), status=status.HTTP_400_BAD_REQUEST)
def get(self, request, *args, **kwargs): timer = get_timer(request.user) if not timer: return DRFResponse({"detail": "Not found"}, status=status.HTTP_404_NOT_FOUND) data = self.get_serializer(timer) return DRFResponse(data)
def defer_assignment(self, request, **kwargs): obj = self.get_object() form = DeferAssignmentCaseForm(case=obj, data=request.DATA) if form.is_valid(): form.save(request.user) return DRFResponse(status=status.HTTP_204_NO_CONTENT) return DRFResponse( dict(form.errors), status=status.HTTP_400_BAD_REQUEST )
def delete(self, request, *args, **kwargs): timer = get_timer(request.user) if not timer: return DRFResponse({"detail": "Not found"}, status=status.HTTP_404_NOT_FOUND) timer.stop(cancelled=True) return DRFResponse(status=status.HTTP_204_NO_CONTENT)
def get_or_create(self, request, *args, **kwargs): try: timer, created = get_or_create_timer(request.user) except ValueError as e: return DRFResponse({"detail": str(e)}, status=status.HTTP_400_BAD_REQUEST) data = self.get_serializer(timer) resp_status = status.HTTP_201_CREATED if created else status.HTTP_200_OK return DRFResponse(data, resp_status)
def delete(self, request, *args, **kwargs): timer = get_timer(request.user) statsd.incr('timer.cancel') statsd.incr('timer.cancel.user.%s' % request.user.pk) if not timer: return DRFResponse( {'detail': 'Not found'}, status=status.HTTP_404_NOT_FOUND ) timer.stop(cancelled=True) return DRFResponse(status=status.HTTP_204_NO_CONTENT)
def assign_suggest(self, request, reference=None, **kwargs): """ @return: dict - 'suggested_provider' (single item) ; 'suitable_providers' all possible providers for this category. """ as_of = None if 'as_of' in request.GET and (settings.DEBUG or settings.TEST_MODE): as_of = parser.parse(request.GET.get('as_of')) as_of = as_of.replace(tzinfo=timezone.get_current_timezone()) obj = self.get_object() helper = ProviderAllocationHelper(as_of=as_of) if hasattr(obj, 'eligibility_check') and obj.eligibility_check != None and obj.eligibility_check.category: category = obj.eligibility_check.category suggested = helper.get_suggested_provider(category) if suggested: suggested_provider = ProviderSerializer(suggested).data else: suggested_provider = None else: category = None suggested_provider = None suitable_providers = [ ProviderSerializer(p).data for p in helper.get_qualifying_providers(category)] suggestions = {'suggested_provider': suggested_provider, 'suitable_providers': suitable_providers, 'as_of': helper.as_of } return DRFResponse(suggestions)
def post(self, request, *args, **kwargs): to = request.data["to"] message = request.data["message"] message = self._send_message(to, message, Message.WHATSAPP) data, status_code = self._handle_response(message) return DRFResponse(data, status=status_code)
def reset_lockout(self, request, *args, **kwargs): logged_in_user_model = self.get_logged_in_user_model() if not logged_in_user_model.is_manager: raise PermissionDenied() user = self.get_object().user AccessAttempt.objects.delete_for_username(user.username) return DRFResponse(status=status.HTTP_204_NO_CONTENT)
def create(self, request): imgstr = request.POST['payload'] payload = ContentFile(base64.b64decode(imgstr), name='{}.jpg'.format(uuid4())) serializer = self.serializer_class(data={ 'request': request.POST['request'], 'payload': { 'image': payload } }) if serializer.is_valid(): serializer.save() resp_data = serializer.data return DRFResponse(resp_data) else: return DRFResponse(serializer.errors)
def _form_action(self, request, Form, no_body=True, form_kwargs={}): obj = self.get_object() _form_kwargs = form_kwargs.copy() _form_kwargs["data"] = request.DATA _form_kwargs[self.FORM_ACTION_OBJ_PARAM] = obj form = Form(**_form_kwargs) if form.is_valid(): form.save(request.user) if no_body: return DRFResponse(status=status.HTTP_204_NO_CONTENT) else: serializer = self.get_serializer(obj) return DRFResponse(serializer.data, status=status.HTTP_200_OK) return DRFResponse(dict(form.errors), status=status.HTTP_400_BAD_REQUEST)
def options(self, request): """ CORS requests begin with an OPTIONS request, which must not require authentication and must have CORS headers in the response. """ return DRFResponse(self.metadata(request), content_type='application/json', status=200, headers={'Access-Control-Allow-Origin': '*'})
def password_reset(self, request, *args, **kwargs): user = self.get_object().user try: return self._form_action(request, PasswordResetForm, no_body=True, form_kwargs={ "action_user": request.user, "reset_user": user }) except PermissionDenied as pd: return DRFResponse(pd.detail, status=status.HTTP_403_FORBIDDEN)
def assign(self, request, reference=None, **kwargs): """ Assigns the case to a provider """ obj = self.get_object() helper = ProviderAllocationHelper() category = obj.eligibility_check.category if obj.eligibility_check else None suitable_providers = helper.get_qualifying_providers(category) # find given provider in suitable - avoid extra lookup and ensures # valid provider for sp in suitable_providers: if sp.id == int(request.DATA['provider_id']): p = sp break else: raise ValueError("Provider not found") # if we're inside office hours then: # Randomly assign to provider who offers this category of service # else it should be the on duty provider data = request.DATA.copy() data['provider'] = p.pk form = ProviderAllocationForm(case=obj, data=data, providers=suitable_providers) if form.is_valid(): provider = form.save(request.user) notify_case_assigned(provider, form.case) provider_serialised = ProviderSerializer(provider) return DRFResponse(data=provider_serialised.data) return DRFResponse( dict(form.errors), status=status.HTTP_400_BAD_REQUEST )
def get(self, *args, **kwargs): return DRFResponse({ "justified": self.make_bool_choices("Justified", "Unjustified"), "resolved": self.make_bool_choices("Resolved", "Unresolved"), "levels": self.get_field_choices("level"), "sources": self.get_field_choices("source"), "actions": [{ "value": event_code, "description": event_details["description"] } for event_code, event_details in ComplaintLogForm.get_operator_code_objects()], })
def post(self, request): # this is to keep backward compatibility with the old system data = request.POST.copy() if 'CHSOrganisationID' not in data: data['CHSOrganisationID'] = data.get('CHSOrgansationID') form = ProviderExtractForm(data) if form.is_valid(): data = form.cleaned_data try: case = Case.objects.get(reference__iexact=data['CHSCRN']) except Case.DoesNotExist: return DRFResponse( {'detail': 'Not found'}, content_type='application/json', status=404, headers={'Access-Control-Allow-Origin': '*'})
def post(self, request): # this is to keep backward compatibility with the old system data = request.POST.copy() if "CHSOrganisationID" not in data: data["CHSOrganisationID"] = data.get("CHSOrgansationID") form = ProviderExtractForm(data) if form.is_valid(): data = form.cleaned_data try: case = Case.objects.get(reference__iexact=data["CHSCRN"]) except Case.DoesNotExist: return DRFResponse( {"detail": "Not found"}, content_type="application/json", status=404, headers={"Access-Control-Allow-Origin": "*"}, )
content_type="application/json", status=404, headers={"Access-Control-Allow-Origin": "*"}, ) self.check_object_permissions(request, case) logger.info("Provider case exported", extra={ "USERNAME": request.user.username, "POSTDATA": request.POST }) return ProviderExtractFormatter(case).format() else: return DRFResponse(form.errors, content_type="text/xml", status=400, headers={"Access-Control-Allow-Origin": "*"}) class UserViewSet(CLAProviderPermissionViewSetMixin, BaseUserViewSet): model = Staff serializer_class = StaffSerializer permission_classes = (CLAProviderClientIDPermission, IsManagerOrMePermission) def get_queryset(self): this_provider = get_object_or_404(Staff, user=self.request.user).provider qs = super(UserViewSet, self).get_queryset().filter(provider=this_provider)
class CaseViewSet( CallCentrePermissionsViewSetMixin, mixins.CreateModelMixin, FullCaseViewSet ): serializer_class = CaseListSerializer serializer_detail_class = CaseSerializer # using CreateCaseSerializer during creation queryset = Case.objects.all().select_related('diagnosis', 'eligibility_check', 'personal_details') queryset_detail = Case.objects.all().select_related( 'eligibility_check', 'personal_details', 'adaptation_details', 'matter_type1', 'matter_type2', 'diagnosis', 'media_code', 'eligibility_check__category', 'created_by' ) filter_backends = ( AscCaseOrderingFilter, SearchFilter, ) def get_serializer_class(self): # if POST create request => use special Serializer # otherwise use standard one if self.request.method == 'POST' and not self.kwargs.get('reference'): return CreateCaseSerializer return super(CaseViewSet, self).get_serializer_class() def get_dashboard_qs(self, qs): if self.request.user.operator.is_manager: qs = qs.filter( Q(requires_action_by=REQUIRES_ACTION_BY.OPERATOR) | Q(requires_action_by=REQUIRES_ACTION_BY.OPERATOR_MANAGER)) else: qs = qs.filter(requires_action_by=REQUIRES_ACTION_BY.OPERATOR) qs = qs.filter( Q(requires_action_at__isnull=True) | Q(requires_action_at__lte=timezone.now()) ) return qs def pre_save(self, obj, *args, **kwargs): super(CaseViewSet, self).pre_save(obj, *args, **kwargs) user = self.request.user if not obj.pk and not isinstance(user, AnonymousUser): obj.created_by = user @link() def assign_suggest(self, request, reference=None, **kwargs): """ @return: dict - 'suggested_provider' (single item) ; 'suitable_providers' all possible providers for this category. """ as_of = None if 'as_of' in request.GET and (settings.DEBUG or settings.TEST_MODE): as_of = parser.parse(request.GET.get('as_of')) as_of = as_of.replace(tzinfo=timezone.get_current_timezone()) obj = self.get_object() helper = ProviderAllocationHelper(as_of=as_of) if hasattr(obj, 'eligibility_check') and obj.eligibility_check != None and obj.eligibility_check.category: category = obj.eligibility_check.category suggested = helper.get_suggested_provider(category) if suggested: suggested_provider = ProviderSerializer(suggested).data else: suggested_provider = None else: category = None suggested_provider = None suitable_providers = [ ProviderSerializer(p).data for p in helper.get_qualifying_providers(category)] suggestions = {'suggested_provider': suggested_provider, 'suitable_providers': suitable_providers, 'as_of': helper.as_of } return DRFResponse(suggestions) @action() def assign(self, request, reference=None, **kwargs): """ Assigns the case to a provider """ obj = self.get_object() helper = ProviderAllocationHelper() category = obj.eligibility_check.category if obj.eligibility_check else None suitable_providers = helper.get_qualifying_providers(category) # find given provider in suitable - avoid extra lookup and ensures # valid provider for sp in suitable_providers: if sp.id == int(request.DATA['provider_id']): p = sp break else: raise ValueError("Provider not found") # if we're inside office hours then: # Randomly assign to provider who offers this category of service # else it should be the on duty provider data = request.DATA.copy() data['provider'] = p.pk form = ProviderAllocationForm(case=obj, data=data, providers=suitable_providers) if form.is_valid(): provider = form.save(request.user) notify_case_assigned(provider, form.case) provider_serialised = ProviderSerializer(provider) return DRFResponse(data=provider_serialised.data) return DRFResponse( dict(form.errors), status=status.HTTP_400_BAD_REQUEST ) @action() def defer_assignment(self, request, **kwargs): obj = self.get_object() form = DeferAssignmentCaseForm(case=obj, data=request.DATA) if form.is_valid(): form.save(request.user) return DRFResponse(status=status.HTTP_204_NO_CONTENT) return DRFResponse( dict(form.errors), status=status.HTTP_400_BAD_REQUEST ) @action() def decline_help(self, request, reference=None, **kwargs): return self._form_action(request, DeclineHelpCaseForm) @action() def suspend(self, request, reference=None, **kwargs): return self._form_action(request, SuspendCaseForm) @action() def assign_alternative_help(self, request, **kwargs): return self._form_action(request, AlternativeHelpForm) def post_save(self, obj, created=False): super(CaseViewSet, self).post_save(obj, created=created) if created: event = event_registry.get_event('case')() event.process( obj, status='created', created_by=self.request.user, notes="Case created" ) @link() def search_for_personal_details(self, request, reference=None, **kwargs): """ You can only call this endpoint if the case doesn't have any personal_details record attached. This is by design as it feels slighly more secure than allowing clients to use a dedicated endpoint that they can call whenever they want. If things change in the future, feel free to add a dedicated endpoint for this though. Should return just ('reference', 'full_name', 'postcode', 'dob') and should NOT include vulnerable users. """ obj = self.get_object() if obj.personal_details: return DRFResponse( {'error': 'This case is already linked to a Person'}, status=status.HTTP_400_BAD_REQUEST ) person_q = request.QUERY_PARAMS.get('person_q', '') or '' if len(person_q) >= 3: users = PersonalDetails.objects.filter( full_name__icontains=person_q ).exclude(vulnerable_user=True) else: users = [] data = [BarePersonalDetailsSerializer(user).data for user in users] return DRFResponse(data) @action() def link_personal_details(self, request, reference=None, **kwargs): """ TODO: refactor everything! * if not DATA.personal_details => return 400 * if obj.personal_details != None => return 400 * if personal_details does not exist => return 400 """ def error_response(msg): return DRFResponse( {'error': msg}, status=status.HTTP_400_BAD_REQUEST ) obj = self.get_object() # check PARAM exists pd_ref = request.DATA.get('personal_details', None) if not pd_ref: return error_response('Param "personal_details" required') # check that case doesn't have personal_details if obj.personal_details: return error_response('A person is already linked to this case') # check that personal details exists try: pd_ref = UUID(pd_ref, version=4) personal_details = PersonalDetails.objects.get(reference=pd_ref) except ValueError, PersonalDetails.DoesNotExist: return error_response('Person with reference "%s" not found' % pd_ref) # link personal details to case obj.personal_details = personal_details obj.save(update_fields=['personal_details', 'modified']) return DRFResponse(status=status.HTTP_204_NO_CONTENT)
def error_response(msg): return DRFResponse( {'error': msg}, status=status.HTTP_400_BAD_REQUEST )
def is_eligible(self, request, *args, **kwargs): obj = self.get_object() response, ec, reasons = obj.get_eligibility_state() return DRFResponse({"is_eligible": response})
def validate(self, request, **kwargs): obj = self.get_object() return DRFResponse(obj.validate())
def __new__(cls, data=None, errors=None, *args, **kwargs): payload = cls.format(data, errors) return DRFResponse(payload, *args, **kwargs)
class CaseViewSet(CLAProviderPermissionViewSetMixin, FullCaseViewSet): serializer_class = CaseListSerializer serializer_detail_class = CaseSerializer queryset = Case.objects.exclude(provider=None).select_related( "diagnosis", "eligibility_check", "personal_details") queryset_detail = Case.objects.exclude(provider=None).select_related( "eligibility_check", "personal_details", "adaptation_details", "matter_type1", "matter_type2", "diagnosis", "media_code", "eligibility_check__category", "created_by", ) filter_backends = (DescCaseOrderingFilter, SearchFilter) ordering_fields = ( "modified", "null_priority", "priority", "personal_details__full_name", "personal_details__postcode", ) def get_queryset(self, **kwargs): """ Returns the following: all: no querystring new: only == 'new' opened: only == 'opened' accepted: only == 'accepted' closed: only == 'closed' """ this_provider = get_object_or_404(Staff, user=self.request.user).provider qs = (super(CaseViewSet, self).get_queryset(**kwargs).filter( provider=this_provider).exclude(outcome_code="IRCB")) only_param = self.request.QUERY_PARAMS.get("only") if only_param == "new": qs = qs.filter(provider_viewed__isnull=True, provider_accepted__isnull=True, provider_closed__isnull=True) elif only_param == "opened": qs = qs.filter(provider_viewed__isnull=False, provider_accepted__isnull=True, provider_closed__isnull=True) elif only_param == "accepted": qs = qs.filter(provider_accepted__isnull=False, provider_closed__isnull=True) elif only_param == "closed": qs = qs.filter(provider_closed__isnull=False) return qs @action() def reject(self, request, reference=None, **kwargs): """ Rejects a case """ return self._form_action(request, Form=RejectCaseForm) @action() def accept(self, request, reference=None, **kwargs): """ Accepts a case """ return self._form_action(request, Form=AcceptCaseForm, no_body=False) @action() def close(self, request, reference=None, **kwargs): """ Closes a case """ return self._form_action(request, Form=CloseCaseForm) @action() def reopen(self, request, reference=None, **kwargs): """ Reopens a case """ return self._form_action(request, Form=ReopenCaseForm, no_body=False) @link() def legal_help_form_extract(self, *args, **kwargs): case = self.get_object() data = { "case": CaseSerializer(instance=case).data, "personal_details": PersonalDetailsSerializer(instance=case.personal_details).data, "eligibility_check": ExtendedEligibilityCheckSerializer( instance=case.eligibility_check).data, } return DRFResponse(data)
class CaseViewSet(CLAProviderPermissionViewSetMixin, FullCaseViewSet): serializer_class = CaseListSerializer serializer_detail_class = CaseSerializer queryset = Case.objects.exclude(provider=None).select_related( 'diagnosis', 'eligibility_check', 'personal_details') queryset_detail = Case.objects.exclude(provider=None).select_related( 'eligibility_check', 'personal_details', 'adaptation_details', 'matter_type1', 'matter_type2', 'diagnosis', 'media_code', 'eligibility_check__category', 'created_by') filter_backends = ( DescCaseOrderingFilter, SearchFilter, ) ordering_fields = ('modified', 'null_priority', 'priority', 'personal_details__full_name', 'personal_details__postcode') ordering = ('null_priority', '-priority', '-modified') def get_queryset(self, **kwargs): """ Returns the following: all: no querystring new: only == 'new' opened: only == 'opened' accepted: only == 'accepted' closed: only == 'closed' """ this_provider = get_object_or_404(Staff, user=self.request.user).provider qs = super(CaseViewSet, self).get_queryset(**kwargs).filter( provider=this_provider).exclude(outcome_code='IRCB') only_param = self.request.QUERY_PARAMS.get('only') if only_param == 'new': qs = qs.filter(provider_viewed__isnull=True, provider_accepted__isnull=True, provider_closed__isnull=True) elif only_param == 'opened': qs = qs.filter(provider_viewed__isnull=False, provider_accepted__isnull=True, provider_closed__isnull=True) elif only_param == 'accepted': qs = qs.filter(provider_accepted__isnull=False, provider_closed__isnull=True) elif only_param == 'closed': qs = qs.filter(provider_closed__isnull=False) return qs @action() def reject(self, request, reference=None, **kwargs): """ Rejects a case """ return self._form_action(request, Form=RejectCaseForm) @action() def accept(self, request, reference=None, **kwargs): """ Accepts a case """ return self._form_action(request, Form=AcceptCaseForm, no_body=False) @action() def close(self, request, reference=None, **kwargs): """ Closes a case """ return self._form_action(request, Form=CloseCaseForm) @link() def legal_help_form_extract(self, *args, **kwargs): case = self.get_object() data = { 'case': CaseSerializer(instance=case).data, 'personal_details': PersonalDetailsSerializer(instance=case.personal_details).data, 'eligibility_check': ExtendedEligibilityCheckSerializer( instance=case.eligibility_check).data } return DRFResponse(data)
status=404, headers={'Access-Control-Allow-Origin': '*'}) self.check_object_permissions(request, case) statsd.incr('provider_extract.exported') logger.info('Provider case exported', extra={ 'USERNAME': request.user.username, 'POSTDATA': request.POST }) return ProviderExtractFormatter(case).format() else: statsd.incr('provider_extract.malformed') return DRFResponse(form.errors, content_type='text/xml', status=400, headers={'Access-Control-Allow-Origin': '*'}) class UserViewSet(CLAProviderPermissionViewSetMixin, BaseUserViewSet): model = Staff serializer_class = StaffSerializer permission_classes = (CLAProviderClientIDPermission, IsManagerOrMePermission) def get_queryset(self): this_provider = get_object_or_404(Staff, user=self.request.user).provider qs = super(UserViewSet, self).get_queryset().filter(provider=this_provider)