feat: implement local scenario engine for playbook execution (issue #80) #102

Merged
jihoson merged 3 commits from feature/issue-80-scenario-engine into main 2026-02-08 20:47:34 +09:00
Collaborator

Summary

  • ScenarioEngine: condition-action 매칭 엔진 (zero API calls, sub-100ms)
  • AND 로직 기반 조건 평가 (RSI, 거래량, 가격 등)
  • GlobalRule 포트폴리오 레벨 룰 (개별 시나리오보다 우선)
  • first-match-wins 우선순위 매칭
  • 38 tests, 92% coverage

Test plan

  • TestEvaluateCondition: 16 tests (경계값, AND 로직, 누락 데이터)
  • TestCheckGlobalRules: 9 tests (연산자, 누락 필드, 우선순위)
  • TestEvaluate: 14 tests (매칭, 기본값, 글로벌 룰 우선순위)
  • 전체 413 tests passed

Closes #80

## Summary - ScenarioEngine: condition-action 매칭 엔진 (zero API calls, sub-100ms) - AND 로직 기반 조건 평가 (RSI, 거래량, 가격 등) - GlobalRule 포트폴리오 레벨 룰 (개별 시나리오보다 우선) - first-match-wins 우선순위 매칭 - 38 tests, 92% coverage ## Test plan - [x] TestEvaluateCondition: 16 tests (경계값, AND 로직, 누락 데이터) - [x] TestCheckGlobalRules: 9 tests (연산자, 누락 필드, 우선순위) - [x] TestEvaluate: 14 tests (매칭, 기본값, 글로벌 룰 우선순위) - [x] 전체 413 tests passed Closes #80
agentson added 1 commit 2026-02-08 15:09:32 +09:00
feat: implement local scenario engine for playbook execution (issue #80)
Some checks failed
CI / test (pull_request) Has been cancelled
9599b188e8
ScenarioEngine evaluates pre-defined playbook scenarios against real-time
market data with sub-100ms execution (zero API calls). Supports condition
AND-matching, global portfolio rules, and first-match-wins priority.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
agentson added 1 commit 2026-02-08 16:23:56 +09:00
fix: add safe type casting and missing-key warnings in ScenarioEngine
Some checks failed
CI / test (pull_request) Has been cancelled
d2fc829380
Addresses PR #102 review findings:
- _safe_float() prevents TypeError from str/Decimal/invalid market_data values
- Warning logs when condition references a key missing from market_data
- 5 new tests: string, percent string, Decimal, mixed invalid types, log check

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
agentson added 1 commit 2026-02-08 20:41:23 +09:00
fix: deduplicate missing-key warnings and normalize match_details
Some checks failed
CI / test (pull_request) Has been cancelled
e711d6702a
Addresses second round of PR #102 review:
- _warn_missing_key(): logs each missing key only once per engine instance
  to prevent log spam in high-frequency trading loops
- _build_match_details(): uses _safe_float() normalized values instead of
  raw market_data to ensure consistent float types in logging/analysis
- Test: verify warning fires exactly once across repeated calls
- Test: verify match_details contains normalized float values

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Author
Collaborator

리뷰 반영 커밋 요약

1차 리뷰 반영 (d2fc829)

Finding 1: TypeError 방지

  • _safe_float() 정적 메서드 추가 — str, Decimal, "30%" 등 비정상 타입을 안전하게 float | None으로 변환
  • evaluate_condition()의 모든 market_data 값 접근을 _safe_float()로 래핑
  • 장중 루프 중단 위험 제거

Finding 2 (부분): 키 누락 시 warning 로그

  • 조건이 설정됐는데 해당 키가 market_data에 없을 때 logger.warning 추가
  • 키 매핑 어댑터는 Issue 1-7 (main.py 통합)에서 처리 예정

테스트 추가 (38 → 43 tests)

  • test_string_value_no_exception — 문자열 숫자 "25" 처리
  • test_percent_string_returns_false"30%" → False (예외 없음)
  • test_decimal_value_no_exceptionDecimal("25.0") 처리
  • test_mixed_invalid_types_no_exception — list, dict, object 등
  • test_missing_key_logs_warning — 키 누락 시 warning 확인

2차 리뷰 반영 (e711d67)

Finding 1: Log Spam 방지

  • _warned_keys: set[str] + _warn_missing_key() 메서드 추가
  • 동일 키 누락 경고를 엔진 인스턴스당 1회로 제한 (고빈도 루프에서 로그 폭발 방지)

Open Q2: match_details 정규화

  • _build_match_details()_safe_float() 정규화 값을 저장하도록 변경
  • 원본 raw 값 대신 일관된 float 타입으로 로깅/분석 혼란 제거

테스트 추가 (43 → 44 tests)

  • test_missing_key_logs_warning_once — 3회 호출 시 warning 1회만 발생 확인
  • test_match_details_normalized — string 입력이 float로 정규화되어 저장됨 확인

범위 밖 → Issue 1-7로 이관

  • market_data 키 매핑 어댑터 (caller 책임)
  • HOLD 시 손절 모니터링 플래그 (trading loop 책임)
  • % 문자열 정규화 정책 (데이터 소스 레벨)
  • ScenarioEngine 싱글톤 유지 (main.py 초기화)
## 리뷰 반영 커밋 요약 ### 1차 리뷰 반영 (`d2fc829`) **Finding 1: TypeError 방지** - `_safe_float()` 정적 메서드 추가 — `str`, `Decimal`, `"30%"` 등 비정상 타입을 안전하게 `float | None`으로 변환 - `evaluate_condition()`의 모든 market_data 값 접근을 `_safe_float()`로 래핑 - 장중 루프 중단 위험 제거 **Finding 2 (부분): 키 누락 시 warning 로그** - 조건이 설정됐는데 해당 키가 market_data에 없을 때 `logger.warning` 추가 - 키 매핑 어댑터는 Issue 1-7 (main.py 통합)에서 처리 예정 **테스트 추가 (38 → 43 tests)** - `test_string_value_no_exception` — 문자열 숫자 `"25"` 처리 - `test_percent_string_returns_false` — `"30%"` → False (예외 없음) - `test_decimal_value_no_exception` — `Decimal("25.0")` 처리 - `test_mixed_invalid_types_no_exception` — list, dict, object 등 - `test_missing_key_logs_warning` — 키 누락 시 warning 확인 --- ### 2차 리뷰 반영 (`e711d67`) **Finding 1: Log Spam 방지** - `_warned_keys: set[str]` + `_warn_missing_key()` 메서드 추가 - 동일 키 누락 경고를 엔진 인스턴스당 1회로 제한 (고빈도 루프에서 로그 폭발 방지) **Open Q2: match_details 정규화** - `_build_match_details()`가 `_safe_float()` 정규화 값을 저장하도록 변경 - 원본 raw 값 대신 일관된 float 타입으로 로깅/분석 혼란 제거 **테스트 추가 (43 → 44 tests)** - `test_missing_key_logs_warning_once` — 3회 호출 시 warning 1회만 발생 확인 - `test_match_details_normalized` — string 입력이 float로 정규화되어 저장됨 확인 --- ### 범위 밖 → Issue 1-7로 이관 - market_data 키 매핑 어댑터 (caller 책임) - HOLD 시 손절 모니터링 플래그 (trading loop 책임) - `%` 문자열 정규화 정책 (데이터 소스 레벨) - ScenarioEngine 싱글톤 유지 (main.py 초기화)
jihoson merged commit aaa74894dd into main 2026-02-08 20:47:34 +09:00
Sign in to join this conversation.
No Reviewers
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: jihoson/The-Ouroboros#102