Untitled

 avatar
unknown
plain_text
5 months ago
10 kB
2
Indexable
from datetime import datetime
from typing import List

from sqlalchemy import update
from strawberry import mutation, type

from app.graphql.schema import Info
from app.graphql.types.field_detail_type import (
    CreateFieldDetailsInput,
    DeleteFieldDetailsInput,
    FieldDetailType,
    UpdateFieldDetailsInput,
)
from app.models import FieldDetail, Validation

field_format_mapping = {"Uppercase": "U", "Lowercase": "L", "Titlecase": "T"}


@type
class UpdateFieldDetailsMutationPayload:
    field_details: List[FieldDetailType]
    success: bool
    message: str = ""


@type
class CreateFieldDetailsMutationPayload:
    field_details: List[FieldDetailType]
    success: bool
    message: str = ""


@type
class DeleteFieldDetailsMutationPayload:
    field_details: List[FieldDetailType]
    success: bool
    message: str = ""


@type
class FieldDetailsMutation:
    def _update_select_field(self, field_detail, current_user, session):
        """Handle updates for select and select-multiple fields."""
        stmt = (
            update(FieldDetail)
            .where(FieldDetail.id == field_detail.id)
            .values(
                label=field_detail.label,
                name=field_detail.name,
                type=field_detail.type,
                order=field_detail.order,
                options=field_detail.options if field_detail.options else None,
                updated_by=current_user,
            )
        )
        session.execute(stmt)

    def _update_text_field(self, field_detail, current_user, session):
        """Handle updates for text and textarea fields."""
        field_format_value = (
            field_format_mapping.get(field_detail.field_format)
            if field_detail.field_format
            else None
        )
        validation_record = (
            session.query(Validation)
            .filter_by(type=field_detail.validation_value)
            .first()
        )
        if validation_record:
            stmt = (
                update(FieldDetail)
                .where(FieldDetail.id == field_detail.id)
                .values(
                    label=field_detail.label,
                    name=field_detail.name,
                    type=field_detail.type,
                    order=field_detail.order,
                    field_format=field_format_value,
                    validation_id=validation_record.id,
                    updated_by=current_user,
                )
            )
            session.execute(stmt)
            return True
        return False

    @mutation
    def update_field_details(
        self, info: Info, input: List[UpdateFieldDetailsInput]
    ) -> UpdateFieldDetailsMutationPayload:
        # Use the context manager to manage the database session
        try:
            current_user = info.context.current_user.login
            session = info.context.session
            updated_field_details_ids = []

            for field_detail in input:
                if field_detail.type in ["select", "select-multiple"]:
                    self._update_select_field(field_detail, current_user, session)
                elif field_detail.type in ["text", "textarea"]:
                    success = self._update_text_field(
                        field_detail, current_user, session
                    )
                    if not success:
                        return UpdateFieldDetailsMutationPayload(
                            field_details=[],
                            success=False,
                            message=f"Validation type '{field_detail.validation_value}' not found",
                        )
                updated_field_details_ids.append(field_detail.id)

            session.commit()

            updated_field_details = (
                session.query(FieldDetail)
                .filter(FieldDetail.id.in_(updated_field_details_ids))
                .all()
            )

            return UpdateFieldDetailsMutationPayload(
                field_details=updated_field_details,
                success=True,
                message="Field details updated successfully",
            )

        except Exception as e:
            session.rollback()
            return UpdateFieldDetailsMutationPayload(
                field_details=[],
                success=False,
                message=f"Update failed: {str(e)}",
            )

    @mutation
    def create_field_details(
        self, info: Info, input: List[CreateFieldDetailsInput]
    ) -> CreateFieldDetailsMutationPayload:
        try:
            current_user = info.context.current_user.login
            created_field_details_ids = []

            # Define default values
            field_detail_default = dict(
                rcvd_from_reltio=None,
                is_dynamic="Y",
                is_active="Y",
                is_editable="Y",
                is_deleted=0,
                is_visible="Y",
                is_downstream="Y",
                is_published="Y",
                default_option="Y",
                created_date=datetime.now(),
                created_by=current_user,
                updated_by=current_user,
            )

            for field_detail in input:
                field_format_value = (
                    field_format_mapping.get(field_detail.field_format)
                    if field_detail.type in ["text", "textarea"]
                    else None
                )

                validation_record = (
                    info.context.session.query(Validation)
                    .filter_by(type=field_detail.validation_value)
                    .first()
                )
                validation_id = validation_record.id if validation_record else None

                options_value = (
                    field_detail.options
                    if field_detail.type in ["select", "select-multiple"]
                    else None
                )

                # Merge default values with the input values
                merged_field_detail = {
                    **field_detail.__dict__,
                    **field_detail_default,
                    "field_format": field_format_value,
                    "validation_id": validation_id,
                    "options": options_value,
                }

                new_field_detail = FieldDetail(
                    label=merged_field_detail["label"],
                    name=merged_field_detail["name"],
                    type=merged_field_detail["type"],
                    order=merged_field_detail["order"],
                    field_format=merged_field_detail["field_format"],
                    validation_id=merged_field_detail["validation_id"],
                    options=merged_field_detail["options"],
                    rcvd_from_reltio=merged_field_detail["rcvd_from_reltio"],
                    is_dynamic=merged_field_detail["is_dynamic"],
                    is_active=merged_field_detail["is_active"],
                    is_editable=merged_field_detail["is_editable"],
                    is_deleted=merged_field_detail["is_deleted"],
                    is_visible=merged_field_detail["is_visible"],
                    is_downstream=merged_field_detail["is_downstream"],
                    is_published=merged_field_detail["is_published"],
                    default_option=merged_field_detail["default_option"],
                    created_date=merged_field_detail["created_date"],
                    created_by=merged_field_detail["created_by"],
                    updated_by=merged_field_detail["updated_by"],
                )

                info.context.session.add(new_field_detail)
                info.context.session.flush()  # Ensures the new field detail gets an ID before commit
                created_field_details_ids.append(new_field_detail.id)

            info.context.session.commit()

            created_field_details = (
                info.context.session.query(FieldDetail)
                .filter(FieldDetail.id.in_(created_field_details_ids))
                .all()
            )

            return CreateFieldDetailsMutationPayload(
                field_details=created_field_details,
                success=True,
                message="Field details created successfully",
            )

        except Exception as e:
            info.context.session.rollback()
            return CreateFieldDetailsMutationPayload(
                field_details=[],
                success=False,
                message=f"Creation failed: {str(e)}",
            )

    @mutation
    def delete_field_details(
        self, info: Info, input: List[DeleteFieldDetailsInput]
    ) -> DeleteFieldDetailsMutationPayload:
        try:
            deleted_field_details = []
            total_deleted = 0
            for field_detail in input:
                stmt = (
                    update(FieldDetail)
                    .where(FieldDetail.id == field_detail.id)
                    .values(is_deleted=True)
                )
                result = info.context.session.execute(stmt)
                total_deleted += result.rowcount
                # Fetch the deleted content object
                deleted_field_detail = info.context.session.query(FieldDetail).get(
                    field_detail.id
                )
                deleted_field_details.append(deleted_field_detail)

            info.context.session.commit()

            if total_deleted > 0:
                return DeleteFieldDetailsMutationPayload(
                    field_details=deleted_field_details,
                    success=True,
                    message=f"{total_deleted} field detail(s) deleted successfully",
                )
            else:
                return DeleteFieldDetailsMutationPayload(
                    field_details=[],
                    success=False,
                    message="No field detail was deleted",
                )
        except Exception as e:
            info.context.session.rollback()
            return DeleteFieldDetailsMutationPayload(
                field_details=[],
                success=False,
                message=f"Deletion failed: {str(e)}",
            )
Editor is loading...
Leave a Comment