-
Notifications
You must be signed in to change notification settings - Fork 8
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #27 from Q-Niranjan/develop-0.4
Implement Document Upload Functionality for MinIO
- Loading branch information
Showing
14 changed files
with
483 additions
and
2 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
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
81 changes: 81 additions & 0 deletions
81
src/openg2p_portal_api/controllers/document_file_controller.py
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,81 @@ | ||
from typing import Annotated | ||
|
||
from fastapi import APIRouter, Depends, File, UploadFile | ||
from openg2p_fastapi_auth.dependencies import JwtBearerAuth | ||
from openg2p_fastapi_auth.models.credentials import AuthCredentials | ||
from openg2p_fastapi_common.controller import BaseController | ||
from openg2p_fastapi_common.errors.http_exceptions import ( | ||
BadRequestError, | ||
UnauthorizedError, | ||
) | ||
|
||
from openg2p_portal_api.models.document_file import DocumentFile | ||
|
||
from ..config import Settings | ||
from ..services.document_file_service import DocumentFileService | ||
|
||
_config = Settings.get_config() | ||
|
||
|
||
class DocumentFileController(BaseController): | ||
def __init__(self, **kwargs): | ||
super().__init__(**kwargs) | ||
self._file_service = DocumentFileService.get_component() | ||
|
||
self.router = APIRouter() | ||
self.router.tags += ["document"] | ||
self.router.add_api_route( | ||
"/uploadDocument/{programid}", | ||
self.upload_document, | ||
responses={200: {"model": DocumentFile}}, | ||
methods=["POST"], | ||
) | ||
|
||
self.router.add_api_route( | ||
"/getDocument/{document_id}", | ||
self.get_document_by_id, | ||
responses={200: {"model": DocumentFile}}, | ||
methods=["GET"], | ||
) | ||
|
||
@property | ||
def file_service(self): | ||
if not self._file_service: | ||
self._file_service = DocumentFileService.get_component() | ||
return self._file_service | ||
|
||
async def upload_document( | ||
self, | ||
programid: int, | ||
auth: Annotated[AuthCredentials, Depends(JwtBearerAuth())], | ||
file_tag: str = None, | ||
file: UploadFile = File(...), | ||
): | ||
if not auth.partner_id: | ||
raise UnauthorizedError( | ||
message="Unauthorized. Partner Not Found in Registry." | ||
) | ||
|
||
try: | ||
message = await self.file_service.upload_document( | ||
file=file, programid=programid, file_tag=file_tag | ||
) | ||
return message | ||
except Exception: | ||
raise BadRequestError(message="File upload failed!") from None | ||
|
||
async def get_document_by_id( | ||
self, | ||
document_id: int, | ||
auth: Annotated[AuthCredentials, Depends(JwtBearerAuth())], | ||
): | ||
if not auth.partner_id: | ||
raise UnauthorizedError( | ||
message="Unauthorized. Partner Not Found in Registry." | ||
) | ||
|
||
try: | ||
document = await self.file_service.get_document_by_id(document_id) | ||
return document | ||
except Exception: | ||
raise BadRequestError(message="Failed to retrieve document by ID") from None |
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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
from openg2p_fastapi_common.errors.http_exceptions import BadRequestError | ||
|
||
|
||
def handle_exception(e, message_prefix="Error"): | ||
"""Helper function to raise BadRequestError with a formatted message.""" | ||
raise BadRequestError(message=f"{message_prefix}: {str(e)}") from None |
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,6 @@ | ||
from pydantic import BaseModel, ConfigDict | ||
|
||
|
||
class DocumentFile(BaseModel): | ||
model_config = ConfigDict(from_attributes=True) | ||
name: str |
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,29 @@ | ||
from openg2p_fastapi_common.models import BaseORMModel | ||
from sqlalchemy import Boolean, ForeignKey, Integer, String | ||
from sqlalchemy.orm import Mapped, mapped_column, relationship | ||
|
||
|
||
class DocumentFileORM(BaseORMModel): | ||
__tablename__ = "storage_file" | ||
|
||
id: Mapped[int] = mapped_column(primary_key=True) | ||
name: Mapped[str] = mapped_column(String, nullable=False, index=True) | ||
slug: Mapped[str] = mapped_column(String, nullable=True, index=True) | ||
relative_path: Mapped[str] = mapped_column(String, nullable=True) | ||
file_size: Mapped[int] = mapped_column(Integer, nullable=True) | ||
human_file_size: Mapped[str] = mapped_column(String, nullable=True) | ||
checksum: Mapped[str] = mapped_column(String(40), nullable=True, index=True) | ||
filename: Mapped[str] = mapped_column(String, nullable=True) | ||
extension: Mapped[str] = mapped_column(String, nullable=True) | ||
mimetype: Mapped[str] = mapped_column(String, nullable=True) | ||
to_delete: Mapped[bool] = mapped_column(Boolean, default=False) | ||
active: Mapped[bool] = mapped_column(Boolean, default=True) | ||
file_type: Mapped[str] = mapped_column(String, nullable=True) | ||
|
||
backend_id: Mapped[int] = mapped_column( | ||
ForeignKey("storage_backend.id"), nullable=False, index=True | ||
) | ||
company_id: Mapped[int] = mapped_column(ForeignKey("res_partner.id"), nullable=True) | ||
|
||
backend = relationship("DocumentStoreORM", back_populates="documents") | ||
partner = relationship("PartnerORM", back_populates="documents") |
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,20 @@ | ||
from typing import Dict, List | ||
|
||
from openg2p_fastapi_common.models import BaseORMModel | ||
from sqlalchemy import JSON, Boolean, Integer, String | ||
from sqlalchemy.orm import Mapped, mapped_column, relationship | ||
|
||
from openg2p_portal_api.models.orm.document_file_orm import DocumentFileORM | ||
|
||
|
||
class DocumentStoreORM(BaseORMModel): | ||
__tablename__ = "storage_backend" | ||
|
||
id: Mapped[int] = mapped_column(Integer, primary_key=True) | ||
name: Mapped[str] = mapped_column(String, nullable=False, index=True) | ||
server_env_defaults: Mapped[Dict[str, str]] = mapped_column(JSON, nullable=False) | ||
is_public: Mapped[bool] = mapped_column(Boolean, default=False) | ||
|
||
documents: Mapped[List["DocumentFileORM"]] = relationship( | ||
"DocumentFileORM", back_populates="backend" | ||
) |
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,10 @@ | ||
from openg2p_fastapi_common.models import BaseORMModel | ||
from sqlalchemy import String | ||
from sqlalchemy.orm import Mapped, mapped_column | ||
|
||
|
||
class DocumentTagORM(BaseORMModel): | ||
__tablename__ = "g2p_document_tag" | ||
|
||
id: Mapped[int] = mapped_column(primary_key=True) | ||
name: Mapped[str] = mapped_column(String, nullable=False, index=True) |
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.