Commit Graph
73 Commits
Author SHA1 Message Date
wangweiandCopilot 31fe71eb94 Forward judge_language through score, async, and session endpoints
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-07-01 18:02:13 +08:00
wangweiandCopilot bd5658c3ac Wire judge-prompt localization into factory and inline scorer
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-07-01 17:58:43 +08:00
wangweiandCopilot 555328cb3b Add judge-prompt localizer with graceful fallback and drift detection
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-07-01 17:55:26 +08:00
wangwei 4e74e1b247 update for ragas 2026-07-01 17:53:00 +08:00
wangweiandCopilot 2bb804b059 Extract shared build_metric_registry factory (DRY)
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-07-01 17:52:55 +08:00
wangweiandCopilot 4a646b6b9c Add judge_language config plumbing (settings + scenario + ScoreRequest)
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-07-01 17:47:21 +08:00
wangweiandCopilot 03e682b89c docs: add Chinese judge-prompt adaptation design spec
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-07-01 17:32:22 +08:00
wangwei 9828b1d44c update 2026-06-27 14:31:45 +08:00
wangweiandCopilot 1df4010acc fix(llm): resolve score runtime config from saved profiles
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-26 20:34:01 +08:00
wangweiandCopilot 754a30ad59 feat(session-async): add /api/score/session_async with incremental session report aggregation
- New POST /api/score/session_async endpoint: same session_id calls append to one shared report
- New GET /api/score/sessions/{session_id}: returns call_count, metric_means, all job records
- New GET /api/score/session/jobs/{job_id}: individual call status
- SessionScoreJobManager: deterministic run_id from session_id, per-session mutex for CSV append, advisor regenerated on every call
- SessionScoreRequest (extends ScoreRequest + session_id), SessionScoreJobResponse, SessionStatus models added
- 24 new tests, all passing

chore(weighted-score): comment out 综合加权得分 display and computation

- report.js: hide 综合加权得分 card in report detail page
- score_jobs.js: hide 综合 chip in async job list
- report_builder.py: overall_ws=None (computation disabled)
- summary.py: weighted_score summary line disabled
- evaluator.py: weighted_score/sample_weight columns no longer written to scores.csv
- score.py /api/score: weighted_score always returns null
- score_job_manager.py + session_score_manager.py: weighted=None
- Updated 3 tests to match new behaviour (6 pre-existing failures unchanged)

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-26 16:09:33 +08:00
wangweiandCopilot e1751447df feat(advisor): add 0.85 advisory threshold triggering LLM suggestions
- Add advisory_threshold=0.85 field to MetricRule (higher-is-better metrics)
- diagnose() now emits severity='low' for scores in (warning_threshold, 0.85)
- noise_sensitivity (lower-is-better) keeps its existing two-tier thresholds
- writer.py: severity labels mapped to Chinese (严重/警告/待优化)
- llm_analyzer.py: prompt explains low/warning/critical tiers in Chinese
- Tests: 5 new cases for 'low' severity, updated log summary assertions

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-25 11:35:49 +08:00
wangweiandCopilot 4fd515d2d9 feat: async score jobs — POST /api/score/async + 评分记录 page
Each async score job:
- Runs InlineScorer.score() in thread pool
- Writes standard run artifacts (metadata.json, scores.csv, summary.md)
- Runs optimization_advisor => optimization_advice.md
- Result appears in 运行列表 and 报告详情 with full report

New endpoints:
- POST /api/score/async  (202, job_id immediate)
- GET  /api/score/jobs   (list all jobs)
- GET  /api/score/jobs/{id} (single job status)

Frontend:
- 评分记录 nav page with card list
- 5s auto-polling for queued/running jobs
- 查看报告 button navigates to existing 报告详情 page

Dify: change /api/score -> /api/score/async, no response parsing needed

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-24 17:24:22 +08:00
wangwei abcd61ec8f docs: add async score jobs implementation plan 2026-06-24 17:08:01 +08:00
wangwei 363e8b0f27 docs: add async score jobs design spec 2026-06-24 17:04:06 +08:00
wangweiandCopilot b870ed8730 feat: make contexts optional in /api/score
When contexts is absent, metrics that require retrieved_contexts
(faithfulness, context_recall, context_precision, noise_sensitivity)
are automatically skipped and appear in skipped_metrics.
Only answer_relevancy, factual_correctness, semantic_similarity
remain computable without contexts.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-24 14:42:03 +08:00
wangweiandCopilot 791738bb07 feat: rename project to 'Siemens RAGAS 评估平台' in frontend
- index.html: page title, brand-mark, brand-sub
- server.py: FastAPI app title
- app.css: comment header

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-24 10:20:23 +08:00
wangweiandCopilot 630b70cc2a docs: add project-overview.html — full project documentation
Covers: overview, architecture, modules, data flows (4 flows),
RAGAS metrics (7), API reference, weight config, deployment,
tech stack, directory structure. Self-contained HTML with
Siemens teal theme, sidebar scrollspy, responsive layout.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-24 10:17:08 +08:00
wangweiandCopilot a781ba1e4a config: set default judge_model=gpt-5, embedding_model=text-embedding-3-small
gpt-5.4/5.5/5.2/5.4-mini/5.4-nano are incompatible with RAGAS 0.4.3
because they require max_completion_tokens instead of max_tokens.
gpt-5 / gpt-4.1 support max_tokens and json_object mode required by RAGAS.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 15:29:01 +08:00
wangweiandCopilot 2ad2c1ea9d docs: update /api/score example to use gpt-5.4 and text-embedding-3-small
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 15:11:34 +08:00
wangweiandCopilot f8e308b7dc fix: use max_tokens=8 for chat model connectivity test
max_tokens=1 triggers 'min-output limit' errors on gpt-5.x models.
Using 8 tokens is still cheap but satisfies all known model minimums.
Falls back to max_completion_tokens=8 if max_tokens is not supported.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 15:03:27 +08:00
wangweiandCopilot fb420656ec fix: use /embeddings endpoint for embedding models in connectivity test
text-embedding-* and other embedding models must call /embeddings not
/chat/completions. Added _is_embedding_model() heuristic that checks model
name keywords to route to the correct endpoint automatically.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 14:53:32 +08:00
wangweiandCopilot 05419db1f9 fix: support max_completion_tokens for newer models (gpt-5.x) in connectivity test
Newer OpenAI models (gpt-5.4 etc.) reject max_tokens and require
max_completion_tokens. Try max_completion_tokens first, fall back to
max_tokens for older models / compatible APIs.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 14:51:28 +08:00
wangweiandCopilot 1dc7ab9727 fix: restore LLM profile test connectivity buttons (lost from git)
Frontend test functionality was implemented but never committed to git.
Re-adds:
- profiles.js: testCard(), testForm(), _showTestResult(), test btn in renderCard
- api.js: testProfile(id) and probeConnectivity(body) methods
- index.html: 测试连通性 button + result div in profile form
- app.css: .btn-test and .profile-test-result styles

Backend /probe and /{id}/test endpoints were already present in llm_profiles.py.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 13:58:43 +08:00
wangweiandCopilot 7cc3aff95a fix: hide #view-apidocs when [hidden] attribute is set
#view-apidocs has 'display: flex' in CSS which overrides the browser's
default '[hidden] { display: none }' user-agent style, causing the API
docs iframe to remain visible and bleed into the LLM config page.

Fix: add explicit '#view-apidocs[hidden] { display: none }' rule.
Also exclude apidocs from @media print to prevent iframe printing.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 13:34:24 +08:00
wangweiandCopilot ad2651ce27 feat: configure full logging in webmain.py — all API logs to file + console
- RotatingFileHandler: logs/server_YYYY-MM-DD.log (50MB, keep 7 files)
- Console handler: colored timestamp + level + logger name + message
- webapp.* and rag_eval.* loggers captured at configured level
- uvicorn access/error logs also routed to same handlers
- File always captures DEBUG; console level controlled by --log-level arg
- Added --log-level and --log-file CLI arguments to webmain.py

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 11:46:34 +08:00
wangweiandCopilot fb42116616 fix: add setuptools package discovery config to pyproject.toml
Newer setuptools (Linux) raises error when multiple top-level dirs are found.
Explicitly include only rag_eval/apps/webapp and exclude runtime data dirs.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 11:29:35 +08:00
wangweiandCopilot a629bd516c chore: add .gitattributes to enforce LF for shell scripts and Python files
Prevents CRLF line endings on .sh files which cause '/usr/bin/env: bash\r'
errors when running on Linux.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 11:22:24 +08:00
wangweiandCopilot ac410e7a5d feat: add detailed logging to all API routes and global access log middleware
Each API module now logs:
- evaluations: trigger (scenario path, task_id), status polls, list
- runs: list (count), detail (run_id, metrics, sample counts)
- scenarios: list (total, valid, error counts)
- pipeline: submit (docs_path, models, max_docs), status polls, list
- llm_profiles: CRUD ops (name, model, id), probe/test (model, ok, latency), apply (patched fields)
- score: already had per-request logging

Global middleware (webapp.access logger):
- Every API request: METHOD path -> status (latency_ms) at INFO
- Static file requests demoted to DEBUG to reduce noise

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 10:35:00 +08:00
wangweiandCopilot 1304fec1c4 fix: change ScoreRequest json_schema_extra from examples list to example dict
Swagger UI Try it out was sending the {summary, value} wrapper as request body
instead of just the value contents, causing 422 errors. The 'example' (singular)
key is correctly used as the schema-level example by Swagger UI.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-23 10:03:46 +08:00
wangweiandCopilot 5ced129ff7 feat: add detailed request logging to /api/score and global 422 handler
- Log incoming request (client, content-type, metrics, has_gt) on each /api/score call
- Log scoring result (latency, skipped metrics, scores) on success
- Register global RequestValidationError handler: logs url/content-type/errors
  so 422 causes are visible in server log without checking HTTP response body
- Fix jsonable_encoder for exc.errors() to handle non-serializable ctx objects

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 18:14:01 +08:00
wangweiandCopilot ebf1fc7be8 docs: enhance /api/score OpenAPI docs with full Chinese docstring and response example
- Add detailed Chinese route docstring covering all 7 metrics, contexts format,
  ground_truth optional behavior, and Bearer auth instructions
- Add 200 response content example for Swagger UI Try-it-out
- Bump app version to 0.3.0

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 15:52:30 +08:00
wangweiandCopilot 1bcb208f92 feat: Dify score API complete — add SCORE_API_TOKEN to .env.example
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 15:28:20 +08:00
wangweiandCopilot a03a24be4e feat: add POST /api/score endpoint for Dify real-time scoring
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 15:14:19 +08:00
wangweiandCopilot e4d4e4968b feat: add InlineScorer service with LLM client caching
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 15:03:43 +08:00
wangweiandCopilot 761faf9c42 feat: add ScoreRequest/ScoreResponse models and SCORE_API_TOKEN setting
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 15:00:05 +08:00
wangwei 9ad6ad4ebc docs: add Dify score API implementation plan 2026-06-22 14:55:43 +08:00
wangweiandCopilot eee96eb158 docs: add Dify score API integration design spec
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 14:51:52 +08:00
wangweiandCopilot ccf25eb1f9 feat: add Linux deployment scripts (deploy/start/stop/run_eval)
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 14:28:44 +08:00
wangweiandCopilot 199b3af611 docs: add Linux deploy script design spec
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-22 14:18:14 +08:00
wangweiandCopilot f9e3ba0f64 feat: add weight config panel to 新建评估 and weighted_score card to report
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 17:28:15 +08:00
wangweiandCopilot 36e5506e2a feat: report_builder uses weighted means; ReportData gains weighted_score_mean
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 17:16:09 +08:00
wangweiandCopilot 835614189e feat: ScenarioInfo exposes metric_weights and doc_weights from YAML
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 17:05:26 +08:00
wangweiandCopilot ce0d2291b0 feat: yaml_patcher and ProfileApplyRequest support metric_weights and doc_weights
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 17:02:21 +08:00
wangweiandCopilot 480f6d66ea feat: use weighted metric means and add weighted_score row to summary.md
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 16:59:56 +08:00
wangweiandCopilot d371ef7d24 feat: add weighted_score and sample_weight columns to score rows
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 16:53:45 +08:00
wangweiandCopilot 8617eaa5aa feat: add metric_weights and doc_weights to Scenario schema and dataclass
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 16:50:33 +08:00
wangweiandCopilot e0b064587f feat: add metric/doc weight computation module (weights.py)
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 16:47:47 +08:00
wangwei 078097af00 docs: add metric/doc weights implementation plan 2026-06-18 16:43:08 +08:00
wangweiandCopilot ca586bf9bb docs: add metric and doc weights feature design spec
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-18 16:37:18 +08:00
wangwei 9ad2daff73 feat: restore API文档 nav item (iframe /docs) without touching other 4 modules 2026-06-17 11:24:16 +08:00
wangwei e8af5b906c chore: remove API docs iframe nav item, rename title to RAGAS 评估控制台 2026-06-17 11:18:01 +08:00
wangwei 8ea2b9c7d2 feat: add API文档 nav item with embedded Swagger UI iframe 2026-06-17 11:09:55 +08:00
wangwei 074800b741 feat: add history report switcher dropdown in report detail view 2026-06-17 10:35:56 +08:00
wangwei 3019390592 feat: add export-to-PDF via browser print with @media print CSS 2026-06-17 10:28:01 +08:00
wangwei 24956bbf75 更新 2026-06-16 18:12:33 +08:00
wangweiandClaude ca01e44ad2 feat(webapp): add session persistence via URL hash routing + sessionStorage
- app.js: hash-based router (#runs / #new / #profiles / #report/{runId})
  - navigate() pushes history entries for back/forward support
  - _restoreSession() reads hash on load and popstate
  - sessionStorage fallback for same-tab refreshes
  - run-card highlights selected run (.run-card.selected)
- runner.js: use App.navigate() for report redirect; persist lastRunId to sessionStorage
- index.html: report nav button starts disabled (enabled on run select/restore)
- app.css: .run-card.selected with petrol border + ring

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-16 17:55:07 +08:00
wangweiandClaude 1a2cc534b8 feat(webapp): add optimization advice section to report UI
- index.html: add section ⑤ advice block (hidden by default, shown when advice_markdown present)
- report.js: add renderAdvice() called in render(), simple Markdown→HTML converter
- app.js: add noise_sensitivity / factual_correctness / semantic_similarity to shortMetric map
- app.css: add .advice-panel, .advice-badge, .advice-md styles (purple left-border theme)

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-16 17:26:37 +08:00
wangweiandClaude 91c0dab4f9 fix(advisor): fix LLM API call, wire advice_markdown to webapp, update .env.example timeouts
- llm_analyzer.py: use llm.langchain_llm.ainvoke() (correct RAGAS 0.4.3 API)
- webapp/models.py: add advice_markdown field to ReportData
- webapp/services/run_reader.py: add read_advice_markdown() reading optimization_advice.md
- webapp/services/report_builder.py: pass advice_markdown into ReportData
- .env.example: OPENAI_TIMEOUT_SECONDS 30→180, RAGAS_METRIC_TIMEOUT_SECONDS 45→300

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-16 17:12:32 +08:00
wangweiandClaude f5c2dce64a feat(advisor): add optimization advisor module
- rag_eval/advisor/: new package with rules engine, LLM analyzer, writer
  - rules.py: 7-metric diagnostic rules (warning/critical thresholds, top-3 low samples)
  - llm_analyzer.py: Chinese optimization report via judge_model, graceful fallback
  - writer.py: writes optimization_advice.md + log summary
  - __init__.py: run_advisor() entry point (no-op when optimization_advisor=False)
- Scenario.optimization_advisor: new bool field (default False)
- ScenarioModel: same field added, loader.py透传
- RunArtifactPaths.advice_md: new path field
- factory.py: build_models() now public; build_metric_pipeline() accepts pre-built llm/embeddings
- runner.py: lifts llm, passes to pipeline and advisor; calls run_advisor() at end
- siemens online YAML: optimization_advisor: true enabled
- tests: 9 rules tests + 6 writer tests, all pass
- docs: advisor section added to engine-flow.md and architecture.md

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-16 17:06:19 +08:00
wangwei d68399d39b chore: update startup scripts and .env.example for LLM profile feature 2026-06-16 17:03:25 +08:00
wangwei 719c3b4ca4 test: ensure test package structure and all webapp tests pass 2026-06-16 16:27:54 +08:00
wangwei 5b60ed12ea feat: add LLM role-assignment panel to 新建评估 view 2026-06-16 16:27:00 +08:00
wangwei dc8baf8662 feat: add LLM配置 management page (profiles view) 2026-06-16 16:25:20 +08:00
wangwei e329f59139 feat: add yaml_patcher service to apply LLM profiles to scenario YAML 2026-06-16 16:21:19 +08:00
wangwei b19054bd66 feat: add /api/llm-profiles CRUD router 2026-06-16 16:18:40 +08:00
wangwei 5d09deb420 feat: add ProfileManager service with JSON persistence 2026-06-16 16:14:31 +08:00
wangwei b98af29449 feat: add LLMProfile pydantic models 2026-06-16 16:10:37 +08:00
wangweiandClaude 4173a40d93 feat(scripts): add run_eval.bat / run_eval.ps1 evaluation launcher scripts
Both scripts support:
  - Shortcut args: online (default), offline, or any custom .yaml path
  - Second arg: log level (DEBUG/INFO/WARNING/ERROR), default INFO
  - Auto-timestamped log file saved to logs\eval_<date>_<time>.log
  - Sets PYTHONIOENCODING=utf-8 and PYTHONPATH=. automatically
  - Friendly error/success banners with log file path

Usage:
  run_eval.bat                    # online eval
  run_eval.bat offline DEBUG      # offline eval with DEBUG logs
  .\run_eval.ps1 online DEBUG     # PowerShell equivalent

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-16 11:16:53 +08:00
wangweiandClaude 629304aa6d feat(logging): add structured evaluation logs for metric-level debugging
- pipeline.py: log each metric score/timeout/error with sample_id,
  elapsed time, and score value; log NaN list per sample; progress
  counter N/total after each sample completes
- evaluator.py: log eval start, dataset counts, adapter enrichment
  progress (per-sample OK/FAIL with elapsed), metric scoring summary,
  and per-metric NaN rate at end of run
- runner.py: _setup_logging() helper writes to stderr + optional file;
  ragas/httpx/openai noisy loggers throttled to WARNING
- main.py: add --log-file and --log-level CLI flags

Usage:
  python main.py --scenario scenarios/online/... --log-file logs/eval.log --log-level DEBUG

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-16 10:48:41 +08:00
wangweiandClaude Opus 4 1ff4a3943a feat(dataset-builder): add retry logic and ASCII-safe logging for Siemens PDF pipeline
- question_generator.py: add max_retries=3/retry_delay=5s loop with
  exponential backoff on LLM timeout or server errors; encode filenames
  with ascii/replace before printing to avoid UnicodeEncodeError on
  Windows cp1252 consoles
- runner.py: encode PDF filenames ASCII-safe for progress messages;
  catch generation failures per-document and skip (or re-raise) based
  on failure_mode, preventing one bad doc from aborting the whole build

Co-Authored-By: Claude Opus 4 <noreply@anthropic.com>
2026-06-15 23:06:33 +08:00
wangweiandClaude Sonnet 4 75ae7927ad Add Siemens CT document evaluation scenario (three-step pipeline)
- scenarios/siemens_build/siemens-pdf-build.yaml: dataset build for all 17
  Siemens medical-imaging PDFs (aliyun_docmind parser, 10 questions/doc,
  failure_mode=skip, ~170 question total)
- scenarios/offline/siemens-pdf-offline-smoke.yaml: offline evaluation using
  source chunks as contexts and ground_truth as answer (up to 30 samples)
- scenarios/online/siemens-pdf-question-bank-online.yaml: online evaluation
  calling siemens_pdf_qa adapter, batch_size=4, up to 50 samples
- apps/siemens_pdf_qa/adapter.py: Siemens-specific adapter with bilingual
  (zh/en) system prompt and strict evidence-grounding for CT domain
- scripts/build_siemens_offline_smoke.py: helper to derive offline smoke CSV
  from completed dataset build artifacts (run after dataset build step)
- docs/superpowers/specs/2026-06-15-siemens-scenario-design.md: design spec

All three scenarios are automatically discovered by the web console.

Co-Authored-By: Claude Sonnet 4 <noreply@anthropic.com>
2026-06-15 17:00:52 +08:00
wangweiandClaude Sonnet 4 1288a366d1 Fix start.bat (ASCII-only, guaranteed window stays open) + add start.ps1
- start.bat: remove all Chinese characters (caused silent failure when
  Windows batch parser ran before chcp 65001 took effect); add :error
  label so window stays open with pause on any failure
- start.ps1: PowerShell alternative launcher with coloured output,
  works without worrying about cmd.exe encoding issues

Co-Authored-By: Claude Sonnet 4 <noreply@anthropic.com>
2026-06-15 16:14:53 +08:00
wangweiandClaude Sonnet 4 e89695e490 Add RAGAS evaluation web console (FastAPI + vanilla JS)
- webapp/: FastAPI backend with runs/scenarios/evaluations API routers;
  services for run_reader, report_builder, scenario_scanner, task_manager
  (lazy ragas import — server boots even without ragas); Pydantic models
- webapp/static/: single-page console (layout A: left-nav + main area);
  report detail with metric cards, Chart.js distribution histogram,
  grouping table, lowest-score sample review; trigger evaluation + log polling
- webmain.py: uvicorn entry point (alongside existing main.py CLI)
- start.bat: Windows one-click launcher with env checks and auto-browser open
- rag_eval/datasets/: implement missing loader + normalizer modules
  (load_dataset_records, normalize_records) required by evaluator
- scripts/seed_sample_run.py: generate realistic demo run artifacts
- .gitignore: exclude datasets/ data files but keep rag_eval/datasets/ source

Co-Authored-By: Claude Sonnet 4 <noreply@anthropic.com>
2026-06-15 15:53:57 +08:00