refactor: BE/WEB/XR リファクタリングレビューの High 指摘を解消 - #554
Conversation
BE_refacter / WEB_refacter / INFRA_refacter / XR_refacter の4スキルを実行し、
検出された High 指摘と関連する安全な Medium 項目を修正。
## Backend
- services/agent/ 配下4モジュール(chat/resume_draft/resume_import/skill_display)に
重複していた LLM リトライ+トークン集計ロジックを services/agent/llm/retry.py と
_utils.py(コードフェンス剥がし)に抽出
- 呼び出し元ゼロの死コード(intelligence_generator 系、PDF/Markdown 計約275行)を削除
- routers/agent.py と routers/github_link/endpoints.py に重複していた
日次レート制限429変換ロジックを routers/_shared.py に抽出
- resume.py の冗長なローカル import を解消
- resume_import のリトライ回復パス・共通429ヘルパーの単体テストを追加
## Frontend
- useNotifications.ts の4箇所の catch {} 握りつぶしに logger.warn を追加し、
失敗パスのテストを追加(CLAUDE.md の例外握りつぶし禁止ルール対応)
- useMasterData.ts / useAuthSession.ts の同種の握りつぶしにも logger.warn を追加
- useCareerExportActions.ts のテストを新規追加(認証ゲート・活性制御の分岐)
## Cross-realm
- 存在しない backend エンドポイントを参照する死コード
web/src/api/ai-resume.ts と PATHS.aiResume を削除
## 見送った項目(レビュー自身が優先度低・時期尚早と判断)
- Infra: cloud_run の secret_manager 分割・CI matrix 化(state影響/挙動変更リスクに対し
実利小、HCL重複率は既に0%)
- Backend Medium: routers/agent.py package化、resume_generator._build_html分割、
github_collector._collect_repo_signals分割、_SequentialFakeLLM統合
- Web Medium/Low: AgentChatWidget のリサイズロジック重複(Rule of Three未達)、
setAtPath.ts の再帰共通化、hooks/ ディレクトリ再編
検証: make ci(lint / test-backend 616 passed / test-web 359 passed / build-web)全て green
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>Warning Review limit reached
Next review available in:41 minutes Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: defaults Review profile: CHILL Plan: Pro Plus Run ID: 📒 Files selected for processing (5)
📝 WalkthroughWalkthroughThe PR centralizes agent LLM retry, parsing, usage accounting, and daily-limit handling; adds backend and frontend tests; removes obsolete intelligence-report and AI-resume API code; and adds frontend warning logs for caught errors. ChangesAgent LLM orchestration
Agent daily-limit routing
Resume project sorting
Intelligence report removal
Web API and error observability
Estimated code review effort: 4 (Complex) | ~45 minutes Sequence Diagram(s)sequenceDiagram
participant AgentService
participant RetryHelper
participant LLM
participant Parser
AgentService->>RetryHelper: Submit generation request
RetryHelper->>LLM: Generate response
LLM-->>RetryHelper: Response and usage
RetryHelper->>Parser: Parse response
Parser-->>RetryHelper: Parsed output or error
RetryHelper->>LLM: Retry with feedback
LLM-->>RetryHelper: Retry response and usage
RetryHelper-->>AgentService: Output and aggregated usage
Possibly related PRs
Suggested labels: 🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
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. Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (2)
backend/app/services/agent/resume_draft/draft_service.py (1)
21-21: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low valueShared types imported through
..chat_serviceinstead of the canonical..llm.base.llm/base.pyis now documented as the source of truth forAgentResponseParseError/AgentUsage; the re-export inchat_serviceexists only for backward compatibility, so newly-migrated services needlessly depend on the chat module (including its import-time prompt file read).
backend/app/services/agent/resume_draft/draft_service.py#L21-L21: change tofrom ..llm.base import AgentResponseParseError, AgentUsage.backend/app/services/agent/resume_import/import_service.py#L23-L23: change tofrom ..llm.base import AgentResponseParseError, AgentUsage.backend/app/services/agent/skill_display/proposer.py#L20-L20: change tofrom ..llm.base import AgentResponseParseError, AgentUsage.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@backend/app/services/agent/resume_draft/draft_service.py` at line 21, Update the imports in draft_service.py (line 21), import_service.py (line 23), and proposer.py (line 20) to source AgentResponseParseError and AgentUsage from the canonical ..llm.base module instead of ..chat_service; no other changes are needed.backend/app/services/agent/_utils.py (1)
11-15: 🎯 Functional Correctness | 🔵 Trivial | 💤 Low valueFence stripping only handles a lowercase
jsontag.
text.strip("")also removes any trailing backticks anywhere at the ends, andremoveprefix("json")missesJSON` / other language tags, leaving the tag in the payload and forcing an unnecessary retry. A regex-based fence strip would be more robust; behavior today still degrades safely via the parse-error retry path, so this is optional.♻️ Optional: regex-based fence strip
+import re++_FENCE_RE = re.compile(r"^```[A-Za-z0-9_+-]*\s*\n?(.*?)\n?```$", re.DOTALL)+ def strip_code_fence(raw: str) -> str: text = raw.strip() - if text.startswith("```"):- text = text.strip("`")- text = text.removeprefix("json").strip()- return text+ match = _FENCE_RE.match(text)+ return match.group(1).strip() if match else text🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@backend/app/services/agent/_utils.py` around lines 11 - 15, Update strip_code_fence to remove complete Markdown code fences without stripping unrelated trailing backticks, and accept case-insensitive or arbitrary language tags such as JSON. Use a compiled regex matching the opening fence, optional language identifier, payload, and closing fence; return the trimmed captured payload when matched, otherwise preserve the original trimmed text.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@backend/tests/test_routers_shared.py`:
- Around line 28-32: Update test_enforce_agent_daily_limit_allows_under_limit to
explicitly set AGENT_DAILY_LIMIT to 2 before calling enforce_agent_daily_limit,
using the test’s existing configuration/environment override mechanism so the
single request always remains under the limit.
---
Nitpick comments:
In `@backend/app/services/agent/_utils.py`:
- Around line 11-15: Update strip_code_fence to remove complete Markdown code
fences without stripping unrelated trailing backticks, and accept
case-insensitive or arbitrary language tags such as JSON. Use a compiled regex
matching the opening fence, optional language identifier, payload, and closing
fence; return the trimmed captured payload when matched, otherwise preserve the
original trimmed text.
In `@backend/app/services/agent/resume_draft/draft_service.py`:
- Line 21: Update the imports in draft_service.py (line 21), import_service.py
(line 23), and proposer.py (line 20) to source AgentResponseParseError and
AgentUsage from the canonical ..llm.base module instead of ..chat_service; no
other changes are needed.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro Plus
Run ID: 5c7e317f-2079-4b6e-87f8-94e785a2c554
📒 Files selected for processing (23)
backend/app/repositories/resume.pybackend/app/routers/_shared.pybackend/app/routers/agent.pybackend/app/routers/github_link/endpoints.pybackend/app/services/agent/_utils.pybackend/app/services/agent/chat_service.pybackend/app/services/agent/llm/base.pybackend/app/services/agent/llm/retry.pybackend/app/services/agent/resume_draft/draft_service.pybackend/app/services/agent/resume_import/import_service.pybackend/app/services/agent/skill_display/proposer.pybackend/app/services/markdown/generators/intelligence_generator.pybackend/app/services/markdown/templates/intelligence_template.pybackend/app/services/pdf/generators/intelligence_generator.pybackend/tests/test_resume_import_service.pybackend/tests/test_routers_shared.pyweb/src/api/ai-resume.tsweb/src/api/paths.tsweb/src/hooks/career/useCareerExportActions.test.tsweb/src/hooks/useAuthSession.tsweb/src/hooks/useMasterData.tsweb/src/hooks/useNotifications.test.tsweb/src/hooks/useNotifications.ts
💤 Files with no reviewable changes (5)
- backend/app/services/markdown/templates/intelligence_template.py
- backend/app/services/markdown/generators/intelligence_generator.py
- web/src/api/ai-resume.ts
- backend/app/services/pdf/generators/intelligence_generator.py
- web/src/api/paths.ts
Uh oh!
There was an error while loading. Please reload this page.
- draft_service.py / import_service.py / proposer.py の AgentResponseParseError / AgentUsage の import を後方互換用の chat_service 経由から正本の llm.base に変更 - strip_code_fence を正規表現ベースに強化し、大文字小文字混在の言語タグや 無関係な末尾バッククォートの誤削除を防止 - test_enforce_agent_daily_limit_allows_under_limit で AGENT_DAILY_LIMIT を 明示的に設定し、環境依存で失敗しないよう決定論化 Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Uh oh!
There was an error while loading. Please reload this page.
Summary
/goalによるリファクタリングスキル一括実行タスク。BE_refacter/WEB_refacter/INFRA_refacter/XR_refacterの4スキルを並列実行してレビューし、検出された High 指摘全件と、関連する安全な Medium 項目を修正した。Backend
services/agent/配下4モジュール(chat / resume_draft / resume_import / skill_display)に一言一句コピーされていた「LLM呼び出し→1回リトライ→トークン合算」ロジックをservices/agent/llm/retry.pyと_utils.py(コードフェンス剥がし)に抽出(Rule of Three 到達済み)intelligence_generator系 PDF/Markdown、計約275行)を削除routers/agent.pyとrouters/github_link/endpoints.pyに重複していた日次レート制限429変換ロジックをrouters/_shared.pyに抽出resume.pyの冗長なローカル import を解消resume_importのリトライ回復パス・共通429ヘルパーの単体テストを追加(616 tests, 90% coverage)Frontend
useNotifications.tsの4箇所のcatch {}握りつぶしにlogger.warnを追加し、失敗パスのテストを追加(CLAUDE.md「例外の握りつぶし禁止」ルール対応)useMasterData.ts/useAuthSession.tsの同種の握りつぶしにもlogger.warnを追加useCareerExportActions.ts(認証ゲート・活性制御ロジック)のテストを新規追加(359 tests)Cross-realm
web/src/api/ai-resume.tsとPATHS.aiResumeを削除見送った項目(レビュー自身が優先度低・時期尚早と判断したもの。過剰な抽象化を避けるため今回は対応しない)
cloud_runの secret_manager module 分割(Terraform state 影響あり)・CI matrix 化(挙動変更リスクあり)。HCL重複率は既に0%(過去のsymlink統合で解消済み)で緊急度なしrouters/agent.pypackage化、resume_generator._build_html分割、github_collector._collect_repo_signals分割、_SequentialFakeLLM統合AgentChatWidgetのリサイズロジック重複(Rule of Three 未達、2箇所のみ)、setAtPath.tsの再帰共通化、hooks/ディレクトリ再編各レビューの詳細レポートは
report/*.md(gitignore 対象のためリポジトリには含まれない)。Test plan
make ci(lint-backend / typecheck-backend / test-backend / lint-web / test-web / build-web)全て greenmake codegen-types差分なし確認済み(OpenAPI契約に影響する変更なし)🤖 Generated with Claude Code
Summary by CodeRabbit
New Features
Bug Fixes
Removed