mirror of
https://github.com/modelscope/FunASR.git
synced 2026-10-12 02:19:18 +00:00
162 lines
5.0 KiB
Python
162 lines
5.0 KiB
Python
import gzip
|
|
import importlib.util
|
|
import json
|
|
import subprocess
|
|
import sys
|
|
from datetime import datetime, timezone
|
|
from pathlib import Path
|
|
|
|
|
|
def load_module():
|
|
script = Path(__file__).resolve().parents[1] / "scripts" / "collect_website_traffic.py"
|
|
spec = importlib.util.spec_from_file_location("collect_website_traffic", script)
|
|
module = importlib.util.module_from_spec(spec)
|
|
spec.loader.exec_module(module)
|
|
return module
|
|
|
|
|
|
def access_line(
|
|
ip,
|
|
timestamp,
|
|
path,
|
|
*,
|
|
status=200,
|
|
referrer="-",
|
|
user_agent="Mozilla/5.0 Chrome/142.0",
|
|
):
|
|
return (
|
|
f'{ip} - - [{timestamp}] "GET {path} HTTP/2.0" {status} 123 '
|
|
f'"{referrer}" "{user_agent}"\n'
|
|
)
|
|
|
|
|
|
def test_parse_access_log_line_normalizes_path_and_referrer():
|
|
module = load_module()
|
|
record = module.parse_access_log_line(
|
|
access_line(
|
|
"203.0.113.5",
|
|
"23/Jul/2026:11:00:00 +0800",
|
|
"/docs/guide.html?source=release",
|
|
referrer="https://www.google.com/search?q=funasr",
|
|
)
|
|
)
|
|
|
|
assert record.client_ip == "203.0.113.5"
|
|
assert record.timestamp.isoformat() == "2026-07-23T11:00:00+08:00"
|
|
assert record.method == "GET"
|
|
assert record.path == "/docs/guide.html"
|
|
assert record.status == 200
|
|
assert record.referrer_host == "www.google.com"
|
|
|
|
|
|
def test_aggregate_filters_bots_assets_failures_and_old_requests():
|
|
module = load_module()
|
|
lines = [
|
|
access_line("203.0.113.10", "23/Jul/2026:09:00:00 +0800", "/"),
|
|
access_line("203.0.113.10", "23/Jul/2026:09:01:00 +0800", "/docs/quickstart.html"),
|
|
access_line(
|
|
"203.0.113.20",
|
|
"23/Jul/2026:09:02:00 +0800",
|
|
"/en/blog/local-asr.html",
|
|
referrer="https://news.ycombinator.com/item?id=1",
|
|
),
|
|
access_line("203.0.113.20", "23/Jul/2026:09:03:00 +0800", "/donors.html"),
|
|
access_line(
|
|
"198.51.100.1",
|
|
"23/Jul/2026:09:04:00 +0800",
|
|
"/docs/quickstart.html",
|
|
user_agent="Googlebot/2.1",
|
|
),
|
|
access_line("198.51.100.2", "23/Jul/2026:09:05:00 +0800", "/assets/app.js"),
|
|
access_line("198.51.100.3", "23/Jul/2026:09:06:00 +0800", "/docs/missing.html", status=404),
|
|
access_line("198.51.100.4", "20/Jun/2026:09:07:00 +0800", "/docs/old.html"),
|
|
]
|
|
records = [module.parse_access_log_line(line) for line in lines]
|
|
|
|
metrics = module.aggregate_records(
|
|
records,
|
|
now=datetime(2026, 7, 23, 12, 0, tzinfo=timezone.utc),
|
|
days=30,
|
|
top_limit=10,
|
|
)
|
|
|
|
assert metrics["page_views"] == 4
|
|
assert metrics["unique_visitors"] == 2
|
|
assert metrics["sections"] == {
|
|
"homepage": {"page_views": 1, "unique_visitors": 1},
|
|
"docs": {"page_views": 1, "unique_visitors": 1},
|
|
"blog": {"page_views": 1, "unique_visitors": 1},
|
|
"donors": {"page_views": 1, "unique_visitors": 1},
|
|
"other": {"page_views": 0, "unique_visitors": 0},
|
|
}
|
|
assert metrics["filtered"]["bots"] == 1
|
|
assert metrics["filtered"]["static_assets"] == 1
|
|
assert metrics["filtered"]["non_success"] == 1
|
|
assert metrics["filtered"]["outside_window"] == 1
|
|
assert metrics["top_referrers"] == [{"host": "news.ycombinator.com", "page_views": 1}]
|
|
serialized = json.dumps(metrics)
|
|
assert "203.0.113" not in serialized
|
|
assert "Mozilla" not in serialized
|
|
|
|
|
|
def test_iter_log_lines_supports_plain_and_gzip_files(tmp_path):
|
|
module = load_module()
|
|
plain = tmp_path / "access.log"
|
|
compressed = tmp_path / "access.log.1.gz"
|
|
plain.write_text("plain\n")
|
|
with gzip.open(compressed, "wt") as handle:
|
|
handle.write("compressed\n")
|
|
|
|
assert list(module.iter_log_lines([plain, compressed])) == ["plain\n", "compressed\n"]
|
|
|
|
|
|
def test_classify_owned_product_guides_as_docs():
|
|
module = load_module()
|
|
|
|
for path in (
|
|
"/quickstart.html",
|
|
"/en/quickstart.html",
|
|
"/models.html",
|
|
"/en/models.html",
|
|
"/vs-whisper.html",
|
|
"/en/vs-whisper.html",
|
|
"/ecosystem.html",
|
|
"/en/llama-cpp.html",
|
|
):
|
|
assert module.classify_page(path) == "docs"
|
|
|
|
|
|
def test_cli_outputs_aggregate_json_without_identifiers(tmp_path):
|
|
script = Path(__file__).resolve().parents[1] / "scripts" / "collect_website_traffic.py"
|
|
log = tmp_path / "access.log"
|
|
log.write_text(
|
|
access_line(
|
|
"203.0.113.55",
|
|
"23/Jul/2026:09:00:00 +0800",
|
|
"/docs/deployment.html",
|
|
)
|
|
)
|
|
|
|
result = subprocess.run(
|
|
[
|
|
sys.executable,
|
|
str(script),
|
|
"--log",
|
|
str(log),
|
|
"--now",
|
|
"2026-07-23T12:00:00+00:00",
|
|
"--days",
|
|
"30",
|
|
"--format",
|
|
"json",
|
|
],
|
|
check=True,
|
|
capture_output=True,
|
|
text=True,
|
|
)
|
|
payload = json.loads(result.stdout)
|
|
|
|
assert payload["page_views"] == 1
|
|
assert payload["sections"]["docs"]["page_views"] == 1
|
|
assert "203.0.113.55" not in result.stdout
|