Files
FinDataHub 11d36d1c1e fix(repo): 修正 Scripts 目录索引大小写并补齐未入库脚本
问题
- 索引中该目录记为小写 `scripts/`,工作区实为 `Scripts/`。因 core.ignorecase=true,
  本地 `git diff -- Scripts/bin/x.py` 会**静默返回空**(看似无改动),
  且在大小写敏感环境(Linux CI / Docker 挂载)会检出 `scripts/`,
  与全仓所有 `Scripts/...` 引用不匹配。
- 该目录此前 10 个脚本(check_python_version.py、perf_snapshot.py、
  install_collector_launchd.py、mysql_toggle.sh 等)从未入库,
  而 CI 第 31 行正调用 `Scripts/bin/check_python_version.py --strict` ——
  全新检出必然失败。

改动
- 索引路径统一为 `Scripts/`(工作区文件未移动,仅索引改名)。
- 补齐上述 10 个未跟踪脚本及其测试。

影响
- 修正前索引 35 条(全为小写路径),修正后 45 条。
2026-09-18 22:37:32 +08:00

90 lines
3.3 KiB
Python
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# coding=utf-8
"""insights.py 数据洞察模块单元测试.
重点覆盖:
- parse_date:多分支日期解析(None / datetime / 8位数字 / 长字符串 / 短字符串)
该函数被 overview_db 和 query_latest_date 调用,是整个洞察模块的日期处理核心。
"""
import os
import sys
from datetime import datetime
from unittest.mock import MagicMock, patch
import pytest
# 将 Scripts/bin 加入 sys.path
_bin_dir = os.path.join(os.path.dirname(__file__), "..")
if _bin_dir not in sys.path:
sys.path.insert(0, _bin_dir)
# conftest 注入的 pymysql mock 缺少 cursors.DictCursor,补齐
_pymysql_mock = sys.modules.get("pymysql")
if _pymysql_mock is not None and not hasattr(_pymysql_mock, "cursors"):
_pymysql_mock.cursors = MagicMock(DictCursor=dict)
# insights.py 模块级执行 args = parser.parse_args(),
# 需将 sys.argv 设为最小值避免 argparse 解析 pytest 参数。
_old_argv = sys.argv
sys.argv = ["insights.py"]
try:
import insights
finally:
sys.argv = _old_argv
# ── parse_date ────────────────────────────────────────────
class TestParseDate:
"""parse_date 多分支日期解析测试."""
def test_none_returns_none(self):
"""None 输入 → 返回 None."""
assert insights.parse_date(None) is None
def test_empty_string_returns_none(self):
"""空字符串 → 返回 None(falsy 分支)."""
assert insights.parse_date("") is None
def test_datetime_object_formatted(self):
"""datetime 对象 → 格式化为 YYYY-MM-DD HH:MM:SS."""
dt = datetime(2024, 3, 15, 14, 30, 45)
assert insights.parse_date(dt) == "2024-03-15 14:30:45"
def test_eight_digit_string_to_date(self):
"""8 位纯数字字符串 → 格式化为 YYYY-MM-DD."""
assert insights.parse_date("20240315") == "2024-03-15"
def test_nineteen_char_string_truncated(self):
""">=19 字符 → 截取前 19 字符(YYYY-MM-DD HH:MM:SS 部分)."""
s = "2024-03-15 14:30:45.123456"
assert insights.parse_date(s) == "2024-03-15 14:30:45"
def test_ten_char_string_truncated(self):
"""10-18 字符 → 截取前 10 字符(YYYY-MM-DD 部分)."""
assert insights.parse_date("2024-03-15") == "2024-03-15"
def test_short_string_returned_as_is(self):
"""<10 字符 → 原样返回."""
assert insights.parse_date("short") == "short"
def test_whitespace_stripped_before_processing(self):
"""输入前后空白被 strip."""
assert insights.parse_date(" 20240315 ") == "2024-03-15"
def test_non_date_eight_digits_still_formatted(self):
"""8 位纯数字但不代表日期 → 仍按格式拼接(函数不做语义校验)."""
result = insights.parse_date("12345678")
assert result == "1234-56-78"
def test_int_input_converted_to_string(self):
"""整数输入 → str() 转换后走字符串分支."""
result = insights.parse_date(20240315)
assert result == "2024-03-15"
def test_fourteen_digit_int_truncated_to_10(self):
"""14 位整数 → 转 str 后按 >=10 且 <19 分支截取前 10 位."""
result = insights.parse_date(20240315143045)
assert result == "2024031514"