income_level(도시근로자 월평균 대비 %) 필드를 활용하여 특별공급 자격 검증:
- 신혼부부·생애최초: 160% 이하 (맞벌이 민간분양 상한)
- 신생아: 200% 이하 (맞벌이 기준)
- 청년: 140% 이하
- 다자녀·노부모부양: 소득 기준 없음
- 미입력 시 검증 생략 (기존 동작 유지)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Replace `or 70` fallback with explicit None-check so that
min_match_score=0 ("notify all matches") is no longer silently
coerced to 70
- Add test: 200 OK + sent_ids=[] must not mark matches notified
- Add test: threshold=0 correctly pushes low-score matches
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Replace os.remove() in conftest autouse fixture with per-table DELETE
to avoid Windows SQLite file-lock PermissionError being swallowed
silently and leaking state across tests. Remove the inline DELETE
workaround from test_profile_api.py that was coupling the test to
internal DB knowledge.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
지역 점수를 35점(광역 10 + 자치구 S/A/B/C/D 티어 0~25)으로 재배분하고,
자격 점수를 25점(첫 자격 15 + 추가당 5, 최대 +10) 곡선으로 변경.
총점 구성: 지역 35 + 유형 10 + 면적 15 + 가격 15 + 자격 25 = 100.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add _extract_district() helper with DISTRICT_PATTERN regex (서울 only)
- collect_all() now passes RCRIT_PBLANC_DE_FROM param (30-day window) to all detail endpoints
- collect_all() skips announcements where compute_status() returns '완료'
- collect_all() stamps district on each parsed announcement before upsert
- upsert_announcement(): add district to INSERT/VALUES/ON CONFLICT UPDATE; data.setdefault('district', None)
- ANNOUNCEMENT_COLUMNS: add 'district' (closes deferred gap from Task 2 review)
- 9 new tests in realestate-lab/tests/test_collector.py (6 unit + 3 integration)
- Full suite: 22 passed
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- mark_matches_notified: pass tuple(match_ids) to conn.execute for consistency
- get_unnotified_matches: add a.status to SELECT so notifier/formatter can skip stale '완료' matches
- add regression test: test_get_unnotified_matches_includes_status
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Replace deprecated mktemp with mkstemp to eliminate TOCTOU race, narrow
OSError catches to PermissionError (Windows SQLite lock intent only), and
add a deferred-import comment for clarity.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- _enrich_items()로 통합: 가격 범위 + match_score/reasons/eligible_types
- 프로필 기반 매칭 점수가 공고 카드에 바로 표시됨
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- announcements 테이블에 is_bookmarked 컬럼 추가 (마이그레이션 포함)
- PATCH /announcements/{id}/bookmark 토글 API 추가
- 공고 목록에 모델 기반 가격 범위(min_price, max_price_display) 포함
- 대시보드에 즐겨찾기 목록 + 개별 이벤트 일정 형식 반환
- 지역 검색을 LIKE 부분 매칭으로 변경
- 수집 시 일정 정보 없는 공고 건너뛰기
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- sqlite3.connect timeout=10 추가 (기본 0초 → 즉시 실패 방지)
- run_matching() 단일 connection으로 통합 (프로필 조회~매칭~저장)
- matches/refresh 엔드포인트 에러 핸들링 추가
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>