Table of Contents |
---|
Purpose
This WS is designed to authorize users scopes. Requested scopes should be allowed for user role, client type and clients broker scopes.
Key points
This method should be reachable only by the eHealth authorization front-end application.
This method is idempotent.
After creating Approval user should be redirected to
redirect_uri
withcode
andstate
(if it was specified in request) query parameter.
Specification
Validations
Validate token
Check Authorization header with Bearer token exists
in case of error - return 401 ('Authorization header is not set or doesn't contain Bearer token')
Check that token is valid and not expired
in case of error - return 401 ('Invalid access token')
Validate user
Extract
user_id
from tokenCheck user is not blocked (is_blocked <> true)
in case of error - return 401
Check user scopes in order to perform this action (scope = 'app:authorize')
in case of invalid scope - return 403 (“Your scope does not allow to access this resource. Missing allowances: app:authorize”)
Validate client
Check
client_id
field exists in request and is not emptyin case of error - return 422 ('can't be blank')
Check client is not blocked (is_blocked <> true)
in case of error - return 401 ('Client is blocked)
Validate redirect uri
Check
redirect_uri
field exists in request and is not emptyin case of error - return 422 ('can't be blank')
Check redirect uri belongs to client through mithril database,
connections
table usingclient_id
in case error - return 401 ('The redirection URI provided does not match a pre-registered value.')
Validate scope
Check
scope
field exists in request and is not emptyin case error - return 422 ('Requested scope is empty. Scope not passed or user has no roles or global roles.')
Extract
user_id
from token. Search for user roles and global user roles in mithril database. Check that value inscope
field exists in scopes for user roles or global rolesin case error - return 401 ('Scope is not allowed by user role.')
Get client type scopes by
client_id
. Check that value inscope
field exists in scopes for client typein case error return 401 ('Scope is not allowed by client type.')
Validate confidant person and relationship (optional)
This additional validations must be done only for patients token - if person_id
exists in token details and is not empty.
Get applicant_person_id
from token details, compare it to person_id
from token:
if equal - check whether person corresponds to following rules:
persons age < no_self_registration_age global parameter;
persons age between no_self_registration_age and person_full_legal_capacity_age global parameters and person does not have document with type from PIS_PERSON_LEGAL_CAPACITY_DOCUMENT_TYPES config parameter;
persons age > person_full_legal_capacity_age global parameter and exists at least one active and approved confidant person relationship for person (using following process Check confidant person relationship with person_id =
person_id
from token details - expected:ok, :approved
response)if person does not correspond to rules - skip validation
if person corresponds to rules - check that requested scopes exist in PIS_READ_ONLY_SCOPES_ALLOWED config parameter
in case of error - return 422 ('Requested scopes do not match with allowed scopes for the user.')
if not equal - get confidant person relationship status using following process Check confidant person relationship with person_id =
person_id
and confidant_person_id =applicant_person_id
from token details:if process returns
:error, :not_found
- return 401 ('Can’t confirm relationship')if process returns
:ok, :approved
- skip validationif process returns
:ok, :not_approved
- check that requested scopes exist in PIS_NOT_VERIFIED_RELATIONSHIP_SCOPES_ALLOWED config parameterin case of error - return 422 ('Requested scopes do not match with allowed scopes for the user.')
Check relationship between patient and confidant person (optional)
This validation must be done only in case user_id
and applicant_user_id
are different as it means that it is a part of confidant person process. In such case we must ensure that relationship between both persons exist and is valid
Get person_id
and applicant_person_id
from token details
Check relationship using Relationship between Confidant Patient and Related Patient validation algorithm and having person_id and applicant_person_id
If relationship doesn’t exist - return 401 ('Can’t confirm relationship')
Maximum tokes limit for client (optional)
Get maximum tokens limit for client from maximum_tokens_limit
field in priv_settings of client:
if value exists and is not empty - get current tokens count of client from Redis database, key
client_tokens_limit_<<client_id>>
(withclient_id
= id of client from request; if key does not exist in Redis database - assume that count for client = 0), compare two values:if current tokens count < maximum tokens limit - authorize an approval for a client, update current tokens count for client in Redis database (add 1 to key
client_tokens_limit_<<client_id>>
value)if current tokens count >= maximum tokens limit - return 401 ('Maximum tokens limit for client exceeded')
if value does not exist or is empty or NULL - skip validation
Service logic
Determine scopes to be approvedIf relationship confirmed - proceed with requested scopesIf relationship exists but not confirmed - filter requested scopes with allowed scopes (envPIS_NOT_VERIFIED_RELATIONSHIP_SCOPES_ALLOWED). So get only scopes that is in allowed list
Approve requested scopes for
client_id
anduser_id
.(list of scopes determined in p.1)Add or update approved scopes list for user and client in mithril database,
apps
table, set:id = autogenerate uuid (for new record)
scope =
scope
user_id =
user_id
client_id =
client_id
applicant_user_id = value of
details.applicant_user_id
from Authorization header token, if exists, elseuser_id
inserted_at = now() (for new record)
updated_at = now()
Generate ‘authorization code’ token, save token to mithril database, tokens table, set:
id = token uuid
name = 'authorization_code'
value = hashed token
expires_at = date and time when token will be expired in unix-time format
details = additional details of token (scope_request,
client_id
, grant_type, redirect_uri, applicant_user_id, applicant_person_id, app_id)applicant_user_id = value of
details.applicant_user_id
from Authorization header token (if exists)applicant_person_id = value of
details.applicant_person_id
from Authorization header token (if exists)app_id = uuid of approval between
user_id
,applicant_user_id
andclient_id
user_id =
user_id
inserted_at = now()
updated_at = now()
Generate urgent data – add authorization code token value to
redirect_uri
value.Render a response according to specification.