Skip to content

Conversation

@MeongW
Copy link
Contributor

@MeongW MeongW commented Aug 18, 2025

🚀 관련 이슈

🔑 주요 변경사항

  • 계약서 내보내기

✔️ 체크 리스트

  • Merge 하려는 브랜치가 올바른가? (main branch에 실수로 PR 생성 금지)
  • Merge 하려는 PR 및 Commit들을 로컬에서 실행했을 때 에러가 발생하지 않았는가?
  • 라벨을 등록했는가?
  • 리뷰어를 지정했는가?

📢 To Reviewers

📸 스크린샷 or 실행영상

↗️ 개선 사항

Summary by CodeRabbit

  • 신규 기능

    • 계약서 내보내기 전 과정(미리보기, 서명 수집, 비밀번호 설정, 최종 PDF 생성/다운로드/이메일 전송) 지원
    • 실시간 동기화(WebSocket)로 서명·상태 업데이트 공유
    • 비밀번호 보호된 최종 PDF 제공 및 임시 미리보기 링크 발급
  • 개선

    • 바이너리 응답(PDF/이미지) 처리 및 CORS 설정 강화
    • 오류 코드 확장으로 계약·PDF 처리 실패 상황 안내 향상
  • 작업

    • 배포 워크플로우 이미지 경로/태그 정리 및 배포 이미지 고정
    • Docker 이미지에 서비스 계정 구성 추가
    • 개발용 Redis 정리 엔드포인트 추가
    • 설정 서브모듈 업데이트

@coderabbitai
Copy link

coderabbitai bot commented Aug 18, 2025

Caution

Review failed

The pull request is closed.

Walkthrough

CI/CD workflow updates image naming and deploy source. Dockerfile now copies Firebase service account into classpath. A large contract export/signing feature is added: new REST/WebSocket endpoints, Redis-backed sync service, DTOs/VOs, MyBatis mapper/XML, S3 byte APIs, utilities (encryption, file, number formatting), and servlet config/CORS changes. Some legacy chat methods are removed.

Changes

Cohort / File(s) Summary
CI/CD pipeline
.github/workflows/cd.yml
Adjusted IMAGE_NAME, registry tag format, deploy image source to ghcr.io/itzeep/backend:latest, and compose image to secrets.IMAGE_NAME.
Container build & config submodule
Dockerfile, config-submodule
Dockerfile copies Firebase service account JSON into Tomcat classes and sets perms; submodule pointer updated.
Chat service cleanup
src/.../chat/service/ContractChatServiceImpl.java
Removed implementations of presence broadcast and final-contract request/accept; left as comments.
Contract controllers (REST)
src/.../contract/controller/ContractController.java, .../ContractControllerImpl.java
Added export workflow endpoints: start/preview/temp URL/role, signatures, status, password, final PDF save/select/download/email; multipart handling and access checks.
Admin/utility REST
src/.../contract/controller/RedisCleanupController.java
New dev-only Redis cleanup endpoints for contract export keys and flush operations.
WebSocket handler
src/.../contract/websocket/ContractExportWebSocketHandler.java
New STOMP endpoints for join/status/signature/password updates; broadcasts status/errors.
Export sync service
src/.../contract/service/ContractExportSyncService.java
New Redis-backed orchestrator for signatures, passwords, PDF generation/encryption, S3 uploads, and WS notifications.
Service interface & impl
src/.../contract/service/ContractService.java, .../ContractServiceImpl.java
Major expansion: AI PDF generation, signature storage, final PDF save/select/stream/email, user birth-date retrieval, DB upsert, fallbacks.
DTOs
src/.../contract/dto/*
Added/expanded DTOs: ContractExportStatusDTO, ContractPasswordDTO, DBFinalContractDTO, FinalContractDTO overhaul, FindContractDTO, LegalityRequestDTO annotations, PasswordSubmitDTO, PrioritySignatureDTO, SaveFinalContractDTO (with toDTO), SaveSignatureDTO, SignatureSubmitDTO.
Enums
src/.../contract/enums/SignedType.java, src/.../precontract/enums/ContractDuration.java
New SignedType enum; ContractDuration gains years field and updated constants.
Mapper interface & XML
src/.../contract/mapper/ContractMapper.java, src/.../resources/.../ContractMapper.xml
Reworked final-contract init/upsert, signature insert/select, final PDF fields (key/hash), user info selects; removed legacy methods.
VOs
src/.../contract/vo/ElectronicSignature.java, .../FinalContract.java
New value objects for signatures and final contract metadata.
Mongo repo
src/.../contract/repository/ContractMongoRepository.java
Comment addition only.
S3 service
src/.../global/file/service/S3ServiceInterface.java, .../S3ServiceImpl.java
Added uploadBytes and downloadBytes APIs.
Utilities
src/.../global/common/util/ImgAesCryptoUtil.java, .../MultipartFileUtils.java, .../NumberFormatUtil.java
New AES-GCM encryption/hash utils, MultipartFile/File conversion helpers, and Korean number formatting.
Web config
src/.../global/config/ServletConfig.java
Added ByteArrayHttpMessageConverter; introduced CORS mappings; removed LocalDate formatter setup.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  participant U as User (Owner/Buyer)
  participant WS as WebSocket (STOMP)
  participant Sync as ContractExportSyncService
  participant Redis as Redis
  participant S3 as S3
  participant AI as AI Server
  participant Svc as ContractService

  U->>WS: /contract/{id}/export/join
  WS->>Sync: getExportStatus(id)
  Sync->>Redis: load or init status
  Redis-->>Sync: status
  Sync-->>WS: status
  WS-->>U: status

  U->>WS: submitSignature(SignatureSubmitDTO)
  WS->>Sync: updateSignature(id, dto)
  Sync->>Redis: save status (owner/buyer signatures)
  alt both signatures present
    Sync->>Svc: generateContractWithSignatures(...)
    Svc->>AI: request PDF with signatures
    AI-->>Svc: PDF bytes (or fail -> fallback)
    Svc->>S3: upload temp/signed
    S3-->>Svc: URL/Key
    Sync->>Redis: update status (generation)
  end
  Sync-->>WS: updated status
  WS-->>U: updated status

  U->>WS: submitPassword(PasswordSubmitDTO)
  WS->>Sync: updatePassword(id, dto)
  Sync->>Redis: store per-role password
  alt both passwords set
    Sync->>Sync: generateFinalPdf(id)
    Sync->>Svc: saveFinalContract(...)
    Svc->>S3: upload encrypted final PDF
    S3-->>Svc: URL/Key
    Sync->>Redis: mark complete + finalPdfUrl
    Sync-->>WS: broadcast status complete
  end
Loading
sequenceDiagram
  autonumber
  participant U as User
  participant REST as ContractControllerImpl
  participant Sync as ContractExportSyncService
  participant Svc as ContractService
  participant S3 as S3
  participant Redis as Redis

  U->>REST: GET /export/preview or /start
  REST->>Svc: startContractExport / preview generation
  Svc-->>REST: PDF bytes or temp URL
  REST-->>U: PDF bytes/URL

  U->>REST: POST /finalContract (password/DTO)
  REST->>Svc: saveFinalContract(...)
  Svc->>S3: upload encrypted PDF
  S3-->>Svc: URL
  Svc-->>REST: bytes/ack
  REST-->>U: response

  U->>REST: GET /download-pdf
  REST->>Svc: getSignedPdfWithPassword via Sync
  Sync->>Redis: fetch role/passwords
  Sync->>S3: download encrypted PDF
  S3-->>Sync: bytes
  Sync-->>REST: bytes
  REST-->>U: PDF stream
Loading

Estimated code review effort

🎯 5 (Critical) | ⏱️ ~120 minutes

Possibly related PRs

Suggested labels

✨ feature

Suggested reviewers

  • Whatdoyumin

Poem

귀 쫑긋, 깡총깡총 토끼 개발자 말하길:
서명은 모였고, 비번도 착!
레디스에 기억, S3로 착륙—찰칵!
웹소켓 타고 소식 전파, PDF는 번쩍📄
오늘도 배포는 ghcr로 쓩—럭키럭키🥕

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ast-grep (0.38.6)
src/main/java/org/scoula/domain/chat/service/ContractChatServiceImpl.java
src/main/java/org/scoula/domain/contract/service/ContractServiceImpl.java

Tip

🔌 Remote MCP (Model Context Protocol) integration is now available!

Pro plan users can now connect to remote MCP servers from the Integrations page. Connect with popular remote MCPs such as Notion and Linear to add more context to your reviews and chats.


📜 Recent review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 36e754e and 1df0958.

📒 Files selected for processing (36)
  • .github/workflows/cd.yml (4 hunks)
  • Dockerfile (1 hunks)
  • config-submodule (1 hunks)
  • src/main/java/org/scoula/domain/chat/service/ContractChatServiceImpl.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/controller/ContractController.java (3 hunks)
  • src/main/java/org/scoula/domain/contract/controller/ContractControllerImpl.java (3 hunks)
  • src/main/java/org/scoula/domain/contract/controller/RedisCleanupController.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/ContractExportStatusDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/ContractPasswordDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/DBFinalContractDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/FinalContractDTO.java (2 hunks)
  • src/main/java/org/scoula/domain/contract/dto/FindContractDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/LegalityRequestDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/PasswordSubmitDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/PrioritySignatureDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/SaveFinalContractDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/SaveSignatureDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/dto/SignatureSubmitDTO.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/enums/SignedType.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/exception/ContractException.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/mapper/ContractMapper.java (2 hunks)
  • src/main/java/org/scoula/domain/contract/repository/ContractMongoRepository.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/service/ContractExportSyncService.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/service/ContractService.java (2 hunks)
  • src/main/java/org/scoula/domain/contract/service/ContractServiceImpl.java (5 hunks)
  • src/main/java/org/scoula/domain/contract/vo/ElectronicSignature.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/vo/FinalContract.java (1 hunks)
  • src/main/java/org/scoula/domain/contract/websocket/ContractExportWebSocketHandler.java (1 hunks)
  • src/main/java/org/scoula/domain/precontract/enums/ContractDuration.java (1 hunks)
  • src/main/java/org/scoula/global/common/util/ImgAesCryptoUtil.java (1 hunks)
  • src/main/java/org/scoula/global/common/util/MultipartFileUtils.java (1 hunks)
  • src/main/java/org/scoula/global/common/util/NumberFormatUtil.java (1 hunks)
  • src/main/java/org/scoula/global/config/ServletConfig.java (2 hunks)
  • src/main/java/org/scoula/global/file/service/S3ServiceImpl.java (3 hunks)
  • src/main/java/org/scoula/global/file/service/S3ServiceInterface.java (1 hunks)
  • src/main/resources/org/scoula/domain/contract/mapper/ContractMapper.xml (1 hunks)
✨ Finishing Touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feat/contract-export

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.

Support

Need help? Create a ticket on our support page for assistance with any issues or questions.

CodeRabbit Commands (Invoked using PR/Issue comments)

Type @coderabbitai help to get the list of available commands.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Status, Documentation and Community

  • Visit our Status Page to check the current availability of CodeRabbit.
  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

@MeongW MeongW merged commit a879a79 into develop Aug 18, 2025
2 of 4 checks passed
Copy link

@github-advanced-security github-advanced-security bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

CodeQL found more than 20 potential problems in the proposed changes. Check the Files changed tab for more details.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants