Skip to content

Commit

Permalink
job_seekers_views: raise a 403 error when using a wrong user kind
Browse files Browse the repository at this point in the history
In job_seekers_views, GetOrCreate views come in two different flavors:
- CheckNIRForJobSeeker, only for job seekers
- CheckNIRForSender, SearchByEmailForSender etc, for senders/hire

It is virtually impossible to be on the wrong flavor by mistake, because
of the session system: we check the user kind and create a session that
can be used on that flavor only.

However we keep a safety rail: a 403 error when a user kind does not
match the current flavor.
  • Loading branch information
EwenKorr committed Jan 20, 2025
1 parent d2b9d02 commit 4311bf9
Show file tree
Hide file tree
Showing 3 changed files with 54 additions and 48 deletions.
6 changes: 2 additions & 4 deletions itou/www/job_seekers_views/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -308,8 +308,7 @@ def setup(self, request, *args, **kwargs):

def dispatch(self, request, *args, **kwargs):
if self.sender.kind not in [UserKind.PRESCRIBER, UserKind.EMPLOYER]:
logger.info(f"dispatch ({request.path}) : {self.sender.kind} in sender tunnel")
return HttpResponseRedirect(reverse("apply:start", kwargs={"company_pk": self.company.pk}))
raise PermissionDenied()
return super().dispatch(request, *args, **kwargs)


Expand All @@ -329,8 +328,7 @@ def setup(self, request, *args, **kwargs):

def dispatch(self, request, *args, **kwargs):
if not self.job_seeker.is_job_seeker:
logger.info(f"dispatch ({request.path}) : {request.user.kind} in jobseeker tunnel")
return HttpResponseRedirect(reverse("apply:start", kwargs={"company_pk": self.company.pk}))
raise PermissionDenied()
return super().dispatch(request, *args, **kwargs)

def get(self, request, *args, **kwargs):
Expand Down
44 changes: 0 additions & 44 deletions tests/www/apply/test_submit.py
Original file line number Diff line number Diff line change
Expand Up @@ -549,27 +549,6 @@ def test_apply_as_job_seeker_temporary_nir(self, client):
html=True,
)

def test_apply_as_job_seeker_on_sender_tunnel(self, client):
company = CompanyFactory()
user = JobSeekerFactory()
client.force_login(user)

# Init session (as it would be in apply:start)
session = client.session
session_name = str(uuid.uuid4())
session[session_name] = {
"config": {
"tunnel": "job_seeker",
"from_url": reverse("companies_views:card", kwargs={"siae_id": company.pk}),
},
"apply": {"company_pk": company.pk},
}
session.save()
response = client.get(reverse("job_seekers_views:check_nir_for_sender", kwargs={"session_uuid": session_name}))
assertRedirects(
response, reverse("apply:start", kwargs={"company_pk": company.pk}), fetch_redirect_response=False
)

def test_apply_as_job_seeker_from_job_description(self, client):
company = CompanyWithMembershipAndJobsFactory(romes=("N1101", "N1105"))
job_description = company.job_description_through.first()
Expand Down Expand Up @@ -1866,29 +1845,6 @@ def test_apply_as_prescriber(self, client, pdf_file):
response = client.get(next_url)
assert response.status_code == 200

def test_apply_as_prescriber_on_job_seeker_tunnel(self, client):
company = CompanyFactory()
user = PrescriberFactory()
client.force_login(user)

# Init session (as it would be in apply:start)
session = client.session
session_name = str(uuid.uuid4())
session[session_name] = {
"config": {
"tunnel": "sender",
"from_url": reverse("companies_views:card", kwargs={"siae_id": company.pk}),
"session_kind": JobSeekerSessionKinds.GET_OR_CREATE,
},
"apply": {"company_pk": company.pk},
}
session.save()

response = client.get(
reverse("job_seekers_views:check_nir_for_job_seeker", kwargs={"session_uuid": session_name})
)
assert response.status_code == 404 # session_kind doesn't match

def test_check_info_as_prescriber_for_job_seeker_with_incomplete_info(self, client):
company = CompanyFactory(with_membership=True, with_jobs=True, romes=("N1101", "N1105"))
user = PrescriberFactory()
Expand Down
52 changes: 52 additions & 0 deletions tests/www/job_seekers_views/test_create_or_update.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,36 @@ def test_start_create_forbidden_for_job_seekers(self, client):
response = client.get(start_url)
assert response.status_code == 403

def test_create_forbidden_for_job_seekers(self, client):
TUNNELS = ["sender", "hire", "gps"]
company = CompanyFactory()
job_seeker = JobSeekerFactory()

client.force_login(job_seeker)

for tunnel in TUNNELS:
# Init session, since a job seeker cannot access the start view this should be impossible
session = client.session
session_name = str(uuid.uuid4())
session[session_name] = {
"config": {
"tunnel": tunnel,
"from_url": reverse("companies_views:card", kwargs={"siae_id": company.pk}),
"session_kind": JobSeekerSessionKinds.GET_OR_CREATE,
},
"apply": {"company_pk": company.pk},
}
session.save()
response = client.get(
reverse("job_seekers_views:check_nir_for_sender", kwargs={"session_uuid": session_name})
)
assert response.status_code == 403

response = client.get(
reverse("job_seekers_views:check_nir_for_hire", kwargs={"session_uuid": session_name})
)
assert response.status_code == 403

def test_check_nir_with_session(self, client):
company = CompanyFactory(with_membership=True)
user = JobSeekerFactory(jobseeker_profile__birthdate=None, jobseeker_profile__nir="")
Expand Down Expand Up @@ -224,6 +254,28 @@ def test_start_get_or_create_sender(
html=True,
)

def test_check_nir_for_jobseeker_forbidden_for_sender(self, client):
company = CompanyFactory(with_membership=True)
user = company.members.get()
client.force_login(user)

# Init a job_seeker session for a sender (should be impossible, the tunnels
# are well separated in apply StartView)
session = client.session
session_name = str(uuid.uuid4())
session[session_name] = {
"config": {
"from_url": reverse("companies_views:card", kwargs={"siae_id": company.pk}),
"session_kind": JobSeekerSessionKinds.CHECK_NIR_JOB_SEEKER,
},
"apply": {"company_pk": company.pk},
}
session.save()
response = client.get(
reverse("job_seekers_views:check_nir_for_job_seeker", kwargs={"session_uuid": session_name})
)
assert response.status_code == 403

def test_check_nir_with_session(self, client):
company = CompanyFactory(with_membership=True)
client.force_login(company.members.get())
Expand Down

0 comments on commit 4311bf9

Please sign in to comment.