-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Hide cancelled samples from customers (#3510)(patch)
- Loading branch information
Showing
12 changed files
with
232 additions
and
83 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
from pydantic import BaseModel | ||
|
||
|
||
class CollaboratorSamplesRequest(BaseModel): | ||
enquiry: str | ||
customer: str | ||
limit: int = 50 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
from pydantic import BaseModel | ||
|
||
from cg.constants.subject import Sex | ||
|
||
|
||
class CustomerDto(BaseModel): | ||
internal_id: str | ||
name: str | ||
|
||
|
||
class SampleDTO(BaseModel): | ||
name: str | None = None | ||
internal_id: str | None = None | ||
data_analysis: str | None = None | ||
data_delivery: str | None = None | ||
application: str | None = None | ||
mother: str | None = None | ||
father: str | None = None | ||
family_name: str | None = None | ||
case_internal_id: str | None = None | ||
require_qc_ok: bool | None = None | ||
sex: Sex | None = None | ||
source: str | None = None | ||
priority: str | None = None | ||
formalin_fixation_time: int | None = None | ||
post_formalin_fixation_time: int | None = None | ||
tissue_block_size: str | None = None | ||
cohorts: list[str] | None = None | ||
phenotype_groups: list[str] | None = None | ||
phenotype_terms: list[str] | None = None | ||
subject_id: str | None = None | ||
synopsis: str | None = None | ||
age_at_sampling: int | None = None | ||
comment: str | None = None | ||
control: str | None = None | ||
elution_buffer: str | None = None | ||
container: str | None = None | ||
container_name: str | None = None | ||
well_position: str | None = None | ||
volume: int | None = None | ||
concentration_ng_ul: int | None = None | ||
panels: list[str] | None = None | ||
status: str | None = None | ||
tumour: bool | None = None | ||
reference_genome: str | None = None | ||
customer: CustomerDto | None = None | ||
|
||
|
||
class SamplesResponse(BaseModel): | ||
samples: list[SampleDTO] | ||
total: int |
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
from http import HTTPStatus | ||
from flask import Blueprint, jsonify, request | ||
|
||
from cg.server.dto.samples.collaborator_samples_request import CollaboratorSamplesRequest | ||
from cg.server.dto.samples.samples_response import SamplesResponse | ||
from cg.server.endpoints.utils import before_request | ||
from cg.server.ext import sample_service | ||
|
||
|
||
SAMPLES_BLUEPRINT = Blueprint("samples", __name__, url_prefix="/api/v1") | ||
SAMPLES_BLUEPRINT.before_request(before_request) | ||
|
||
|
||
@SAMPLES_BLUEPRINT.route("/samples_in_collaboration") | ||
def get_samples_in_collaboration(): | ||
data = CollaboratorSamplesRequest.model_validate(request.values.to_dict()) | ||
response: SamplesResponse = sample_service.get_collaborator_samples(data) | ||
return jsonify(response.model_dump()), HTTPStatus.OK |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,71 @@ | ||
import logging | ||
from functools import wraps | ||
from http import HTTPStatus | ||
|
||
import cachecontrol | ||
import requests | ||
from flask import abort, current_app, g, jsonify, make_response, request | ||
from google.auth import exceptions | ||
from google.auth.transport import requests as google_requests | ||
from google.oauth2 import id_token | ||
|
||
|
||
from cg.server.ext import db | ||
from cg.store.models import User | ||
|
||
LOG = logging.getLogger(__name__) | ||
|
||
session = requests.session() | ||
cached_session = cachecontrol.CacheControl(session) | ||
|
||
|
||
def verify_google_token(token): | ||
request = google_requests.Request(session=cached_session) | ||
return id_token.verify_oauth2_token(id_token=token, request=request) | ||
|
||
|
||
def is_public(route_function): | ||
@wraps(route_function) | ||
def public_endpoint(*args, **kwargs): | ||
return route_function(*args, **kwargs) | ||
|
||
public_endpoint.is_public = True | ||
return public_endpoint | ||
|
||
|
||
def before_request(): | ||
"""Authorize API routes with JSON Web Tokens.""" | ||
if not request.is_secure: | ||
return abort( | ||
make_response(jsonify(message="Only https requests accepted"), HTTPStatus.FORBIDDEN) | ||
) | ||
|
||
if request.method == "OPTIONS": | ||
return make_response(jsonify(ok=True), HTTPStatus.NO_CONTENT) | ||
|
||
endpoint_func = current_app.view_functions[request.endpoint] | ||
if getattr(endpoint_func, "is_public", None): | ||
return | ||
|
||
auth_header = request.headers.get("Authorization") | ||
if not auth_header: | ||
return abort( | ||
make_response(jsonify(message="no JWT token found on request"), HTTPStatus.UNAUTHORIZED) | ||
) | ||
|
||
jwt_token = auth_header.split("Bearer ")[-1] | ||
try: | ||
user_data = verify_google_token(jwt_token) | ||
except (exceptions.OAuthError, ValueError) as e: | ||
LOG.error(f"Error {e} occurred while decoding JWT token: {jwt_token}") | ||
return abort( | ||
make_response(jsonify(message="outdated login certificate"), HTTPStatus.UNAUTHORIZED) | ||
) | ||
|
||
user: User = db.get_user_by_email(user_data["email"]) | ||
if user is None or not user.order_portal_login: | ||
message = f"{user_data['email']} doesn't have access" | ||
LOG.error(message) | ||
return abort(make_response(jsonify(message=message), HTTPStatus.FORBIDDEN)) | ||
|
||
g.current_user = user |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.