선형 run-rate는 노트북 등 일회성 지출을 남은 날에 곱해 비현실적 값(2천만) 생성.
AI가 분류를 보고 일회성을 일평균에서 제외해 추정 + 근거 문장 반환(경과일/총일수 전달).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
이번 달 집계(수입·지출·전월대비·예산·분류별)만 Claude Haiku에 보내 2~3개 코멘트 생성.
POST /account/ai-comment(유료 게이트), 거래 원문 미전송. 미설정/실패 시 빈 코멘트→카드 숨김.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Tomcat 기본 파트 수 제한(10)에 categoryHints/walletHints를 이름마다 파트로 보내 초과 → 500.
힌트를 줄바꿈으로 합친 단일 필드로 받아 파트 3개로 축소.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
/account/ocr/receipt-ai — 이미지를 Haiku 비전에 보내 금액·상호·날짜·분류·계좌를 한 번에 추출.
AI 미설정/실패 시 recognized=false → 프론트가 기존 Google Vision OCR 로 폴백.
Claude 호출/응답파싱 공통화(callClaude), 프롬프트 힌트주입 공통화(withHints).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- BoardService: create/addComment에서 isSpam 감지 시 자동 블라인드 처리, 포인트 미지급
- ReportMapper: listReported 쿼리 확장 — 신고 누적 OR 스팸 감지 블라인드 항목 모두 포함
- ReportedItem: blockReason 필드 추가
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
작성: 10P, 일 50P 한도(5회), 스팸 키워드 포함 시 미지급
추천 받음(작성자): +5P, 일 50P 한도
비추천 받음(작성자): -1P
남의 글 추천(투표자): +1P, 일 10P 한도
추천 취소(투표자): -1P
addPoints에 GREATEST(0,...) 적용 — 잔액 음수 방지
- AiEntryParser: /v1/messages(Haiku) 호출로 '어제 스타벅스 5천원'→{type,amount,merchant,date} 추출
- AccountService.parseText: AI 우선 시도, 미설정/실패/미인식 시 기존 규칙기반 파서로 폴백(무중단)
- app.anthropic-api-key/anthropic-model 설정(키 없으면 AI 비활성)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
서비스 컨테이너(MariaDB/Redis) 후처리 cleanup 이 러너에서 멈춰 15분 타임아웃 →
'가짜 실패'로 표시되던 문제 회피. 배포 잡은 clean bootJar 로 jar 만 만들어 ship.
테스트 게이트는 ci.yaml(같은 push 에서 실행)이 담당.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@SpringBootTest(contextLoads) 시작 시 DefaultCategorySeeder 가 테이블을 조회하는데
CI 는 SQL_INIT_MODE 미설정(never)이라 스키마가 없어 BadSqlGrammarException 으로 실패했음.
운영과 동일하게 always 로 초기화 → 애플 로그인 커밋(a10e16c) 배포도 함께 통과.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- POST /api/auth/apple — nimbus-jose-jwt 로 애플 공개키(JWKS) 서명 검증 + iss/aud(번들ID)/exp 확인
- member.apple_id 컬럼(멱등 ALTER) + findByAppleId/linkApple, 구글과 동일한 이메일 자동연결 로직
- app.apple-client-id 설정(기본 kr.sblog.slimbudget)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- GET /api/board/reports — 글/댓글 신고 대상별 집계(UNION, 신고 많은 순)
- POST /api/board/reports/dismiss — 블라인드 없이 신고 기록만 초기화
- 관리자 신고 관리 화면 백엔드
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
JDBC driver마다 column alias의 대소문자를 다르게 반환할 수 있어
entryId → entry_id, tagName → tag_name 으로 소문자 통일.
NPE 방지를 위한 null 체크도 추가.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
list() 에서 항목마다 findTagNamesByEntryId() 를 개별 호출하던 N+1 을
findTagsByEntryIds() 배치 쿼리 1회로 대체.
항목 수가 많을 때 타임아웃/과부하 방지.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- budget 테이블에 year/month 추가, (member,category)→(member,category,year,month) 유니크 교체
기존 상시 예산은 현재 월로 1회 이관
- 예산 조회/생성/현황/기간차트를 월별로(findByMember에 year/month)
- copyMonth: 다른 월 예산을 대상 월로 복사(같은 분류 덮어씀) + POST /budgets/copy
- 백업 복구 시 예산은 현재 월로 등록
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- GET /board/my/posts, /board/my/comments (페이징)
- PostSummary 에 category 추가, MyCommentResponse(글 제목·카테고리 포함)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- 만료 강등 스케줄러: 해지(자동갱신 off) 건만 강등(자동갱신은 마켓/RTDN 관리)
- POST /api/billing/restore: 최근 결제 기준 멤버십 복원(기기변경·재설치)
- POST /api/billing/google/rtdn: Google Play 실시간 알림 수신 스캐폴드(비인증, 로깅)
- 실연동 지점(영수증 검증·RTDN 처리)은 TODO 로 표시
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- DELETE /api/auth/me: 본인 계정과 모든 데이터 영구 삭제
- 게시판(글/댓글/추천/이미지)·가계부 전체·포인트·결제기록·세션 → 회원 순 삭제
- WithdrawMapper(게시판/포인트/결제/세션) + BackupMapper(가계부) 재사용
- AuthServiceTest 생성자 보강
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- member.plan_product, plan_auto_renew 컬럼(구독 상품·자동갱신)
- GET /api/billing/subscription: 플랜·만료일·다음결제일·자동갱신
- POST /api/billing/cancel: 자동갱신 중단(만료일까지 이용), /resume: 재개
- verify 시 상품·자동갱신 기록, 만료 강등·관리자 변경 시 구독정보 정리
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>