"""Tests for src.parser — natural language time query parsing.""" import sys from pathlib import Path from datetime import datetime, timedelta from unittest.mock import patch sys.path.insert(0, str(Path(__file__).resolve().parent.parent)) from src.parser import parse_query, describe_query class TestParseQuery: def test_latest_week(self): assert parse_query("最新一周") == {"mode": "latest"} assert parse_query("分析最新一周") == {"mode": "latest"} def test_prev_week(self): assert parse_query("上周") == {"mode": "prev"} assert parse_query("分析上一周") == {"mode": "prev"} def test_yesterday(self): result = parse_query("昨天") expected_date = (datetime.now() - timedelta(days=1)).strftime("%Y-%m-%d") assert result == {"mode": "day", "date": expected_date} def test_day_before_yesterday(self): result = parse_query("前天") expected_date = (datetime.now() - timedelta(days=2)).strftime("%Y-%m-%d") assert result == {"mode": "day", "date": expected_date} def test_today(self): result = parse_query("今天") expected_date = datetime.now().strftime("%Y-%m-%d") assert result == {"mode": "day", "date": expected_date} def test_specific_date_iso(self): result = parse_query("2026-03-15") assert result == {"mode": "day", "date": "2026-03-15"} def test_specific_date_chinese(self): result = parse_query("26年3月15日") assert result == {"mode": "day", "date": "2026-03-15"} def test_month_chinese(self): result = parse_query("26年2月") assert result == {"mode": "month", "year": 2026, "month": 2} def test_month_full_year(self): result = parse_query("2025年12月") assert result == {"mode": "month", "year": 2025, "month": 12} def test_month_previous(self): result = parse_query("上个月") now = datetime.now() expected_month = now.month - 1 expected_year = now.year if expected_month < 1: expected_month = 12 expected_year -= 1 assert result == {"mode": "month", "year": expected_year, "month": expected_month} def test_week_w_notation(self): result = parse_query("W9") assert result == {"mode": "week", "year": datetime.now().year, "week": 9} def test_year_week(self): result = parse_query("2026年W12") assert result == {"mode": "week", "year": 2026, "week": 12} def test_range_tilde(self): result = parse_query("1.15~3.3") year = datetime.now().year assert result == {"mode": "range", "start": f"{year}-01-15", "end": f"{year}-03-03"} def test_range_chinese_dates(self): result = parse_query("2026-01-15~2026-03-03") assert result == {"mode": "range", "start": "2026-01-15", "end": "2026-03-03"} def test_unrecognized_returns_none(self): assert parse_query("hello world") is None def test_prefix_stripped(self): result = parse_query("分析昨天") expected_date = (datetime.now() - timedelta(days=1)).strftime("%Y-%m-%d") assert result == {"mode": "day", "date": expected_date} class TestDescribeQuery: def test_latest(self): assert describe_query({"mode": "latest"}) == "最新一周" def test_prev(self): assert describe_query({"mode": "prev"}) == "上一周" def test_week(self): assert describe_query({"mode": "week", "year": 2026, "week": 9}) == "2026年 第9周" def test_month(self): assert describe_query({"mode": "month", "year": 2026, "month": 3}) == "2026年3月" def test_day(self): assert describe_query({"mode": "day", "date": "2026-03-15"}) == "2026-03-15" def test_range(self): assert describe_query({"mode": "range", "start": "2026-01-15", "end": "2026-03-03"}) == "2026-01-15 ~ 2026-03-03"