Claude
Skills
Sign in
Back

mlb-player-analyzer

Included with Lifetime
$97 forever

Deep-dive analysis of a single MLB player (hitter or pitcher) for the Yahoo Fantasy Baseball 2K25 league. Web-searches FanGraphs (ATC projections), Baseball Savant (xwOBA/xBA/xERA), MLB.com (lineups, probables), RotoWire (weather, injuries), and RotoBaller (closer depth) to produce the full set of structured player signals defined in the signal framework. Emits form_score, matchup_score, opportunity_score, daily_quality, regression_index, obp_contribution, sb_opportunity, role_certainty for hitters and qs_probability, k_ceiling, era_whip_risk, streamability_score, two_start_bonus, save_role_certainty for pitchers. Use when you need to analyze player, compute daily_quality, compute regression index, produce player signals, run a hitter analysis, run a pitcher analysis, or prep start/sit inputs for the lineup optimizer.

General

What this skill does


# MLB Player Analyzer

## Table of Contents
- [Example](#example)
- [Workflow](#workflow)
- [Common Patterns](#common-patterns)
- [Guardrails](#guardrails)
- [Quick Reference](#quick-reference)

## Example

**Scenario**: Hitter analysis for Junior Caminero (TB 3B), today's opponent BOS, opp SP Brayan Bello (RHP), park Fenway, light wind.

**Inputs assembled from web search**:
- Last 15 days xwOBA: .410 vs season xwOBA .355 (Baseball Savant)
- Bello 2026 K/9: 8.1, xFIP 4.05, wOBA-vs-RHH .335 (FanGraphs)
- Fenway park factor: 103 R, 105 HR (FanGraphs park factors)
- Caminero vs RHP wOBA: .360 (FanGraphs splits)
- Weather: 62F, 8mph wind LF-to-CF (RotoWire)
- Lineup: confirmed #3 hitter (MLB.com starting lineups)
- Season actual wOBA .340 vs xwOBA .370 -> unlucky +.030

**Signal computation**:

| Signal | Value | Quick read |
|---|---|---|
| form_score | 66 | rolling xwOBA 15% above season baseline |
| matchup_score | 58 | decent park, neutral SP, slight wind-aided |
| opportunity_score | 78 | #3 slot, ~4.6 expected PAs |
| daily_quality | 66 | START-tier (>=60) |
| regression_index | +15 | unlucky, buy-window |
| obp_contribution | 62 | projected .355 OBP x 4.6 PAs |
| sb_opportunity | 35 | Bello holds runners average, BOS catcher CS 28%, Caminero sprint 26.5 ft/s |
| role_certainty | 100 | confirmed lineup posted |

**Recommendation to lineup-optimizer**: `daily_quality = 66` -> START. `regression_index = +15` suggests no need to sit on any recent cold-streak noise.

**Pitcher counter-example (pitcher start)**: Bowden Francis (TOR) at COL. daily_quality replaced by `streamability_score`. Coors kills `streamability_score` regardless of raw stuff; skill would emit qs_probability ~28, k_ceiling ~40, era_whip_risk ~82 -> streamability_score ~32 (sub-70 threshold -> SIT / DO NOT STREAM).

## Workflow

Copy this checklist and track progress:

```
MLB Player Analysis Progress:
- [ ] Step 1: Classify player (hitter vs pitcher; SP vs RP)
- [ ] Step 2: Collect season + 15-day performance (Savant, FanGraphs)
- [ ] Step 3: Collect today's context (opp SP/hitters, park, weather, lineup)
- [ ] Step 4: Compute normalized component scores
- [ ] Step 5: Compute composite signals (daily_quality or streamability_score)
- [ ] Step 6: Check regression_index and role_certainty
- [ ] Step 7: Validate against rubric and emit signal file
```

**Step 1: Classify player**

Determine role: hitter (any position player), SP (starter), RP (reliever, closer or setup). The signal set is different per role. See [resources/methodology.md](resources/methodology.md#role-classification) for role determination rules when a player has dual eligibility (two-way player, opener + bulk).

- [ ] Confirm today's role: is the player in today's lineup? Is the SP on the probable-pitcher chart today?
- [ ] If RP: is this a save-role RP or middle-relief RP? Closer depth lookup required.

**Step 2: Collect performance data**

Web-search the primary sources. Every URL goes in the signal file's `source_urls:` list.

- [ ] Baseball Savant player page: season xwOBA, 15-day xwOBA, xBA, barrel %, hard-hit %, sprint speed (hitters); xERA, whiff %, chase %, CSW (pitchers)
- [ ] FanGraphs player page: ATC projections (rest-of-season rate stats), splits tab (vs LHP / vs RHP)
- [ ] If search fails for any metric: record the attempt, set `confidence: 0.3`, and note the gap in the red-team field

See [resources/data-cheatsheet](resources/methodology.md#source-cheatsheet) for exact URL patterns.

**Step 3: Collect today's context**

- [ ] Opp SP (from MLB.com probable pitchers or matchup-analyzer signal if already emitted)
- [ ] Park factor (from FanGraphs park factors, or matchup-analyzer's `park_hitter_factor` / `park_pitcher_factor`)
- [ ] Weather (from RotoWire weather-forecast, or matchup-analyzer's `weather_risk`)
- [ ] Confirmed lineup slot (from MLB.com starting-lineups; posts ~2-3h pre-game)
- [ ] If a matchup-analyzer signal file exists for today's game, consume those signals -- do not re-derive

**Step 4: Compute normalized component scores**

All raw stats are converted to 0-100 (unipolar) or +/-100 (bipolar) per the signal framework. See [resources/methodology.md](resources/methodology.md#normalization-formulas) for each formula.

- [ ] Hitter: form_score, matchup_score, opportunity_score (components of daily_quality)
- [ ] Hitter: regression_index, obp_contribution, sb_opportunity, role_certainty
- [ ] Pitcher: qs_probability, k_ceiling, era_whip_risk
- [ ] Pitcher RP: save_role_certainty

**Step 5: Compute composite signals**

- [ ] Hitter primary: `daily_quality = 0.35 * form_score + 0.40 * matchup_score + 0.25 * opportunity_score`
- [ ] Pitcher SP primary: `streamability_score = 0.40 * qs_probability + 0.30 * k_ceiling + 0.30 * (100 - era_whip_risk)`
- [ ] Pitcher SP weekly: `two_start_bonus` (bool from FantasyPros two-start page)

**Step 6: Check regression and role**

- [ ] `regression_index = clamp((xwOBA - wOBA) * 500, -100, +100)`. Positive = unlucky (buy). Negative = lucky (sell / fade).
- [ ] `role_certainty` (hitter): 100 = confirmed in today's lineup, 70 = probable per beat reporter, 40 = platoon uncertain, 0 = benched or injured
- [ ] `save_role_certainty` (RP): 100 = locked closer per RotoBaller, 50 = timeshare, 20 = 7th-inning guy

**Step 7: Validate and emit**

- [ ] Fill [resources/template.md](resources/template.md) frontmatter and tables
- [ ] Score against [resources/evaluators/rubric_mlb_player_analyzer.json](resources/evaluators/rubric_mlb_player_analyzer.json). Target average >= 3.5
- [ ] Every numeric signal has `confidence` and at least one `source_url`
- [ ] Call `mlb-signal-emitter` (validation); on failure, log to `tracker/decisions-log.md`

## Common Patterns

**Pattern 1: Hot Streak Hitter (Sell-the-News)**

- **Profile**: Rolling 15-day wOBA well above xwOBA (actual outperforming expected)
- **Signal signature**: `form_score` high (>=70), `regression_index` negative (e.g., -25)
- **Read**: Production is BABIP-aided and not backed by Statcast quality. Do not overweight recent numbers.
- **Action feed to lineup-optimizer**: trim daily_quality by ~5 points mentally; flag for the waiver-analyst if the user is considering selling high

**Pattern 2: Cold Hitter with Loud Contact (Buy-Window)**

- **Profile**: Rolling 15-day wOBA below season average but xwOBA still strong (>=season xwOBA)
- **Signal signature**: `form_score` depressed, `regression_index` positive (>=+20), barrel% still good
- **Read**: Bad-luck stretch. Underlying contact quality intact. Start through it.
- **Action**: keep daily_quality weight as computed; flag positive regression to category-strategist (this is the guy who will pop next week)

**Pattern 3: Two-Start Pitcher in a Bad Park**

- **Profile**: SP with two starts this scoring week, one of which is at COL / CIN / BOS
- **Signal signature**: `two_start_bonus = true`, but one start has `era_whip_risk` >= 70
- **Read**: Volume pays in K and QS, but a blowup in Coors could torch ERA/WHIP for the week
- **Action**: Emit both starts as separate pitcher signals, each with its own streamability_score; streaming-strategist decides whether to eat the bad park for the volume

**Pattern 4: Closer in Committee / Role Uncertainty**

- **Profile**: RP with save opportunities but manager has said "mix-and-match" or "matchup based"
- **Signal signature**: `save_role_certainty` <= 50, `k_ceiling` decent, `era_whip_risk` low
- **Read**: Rostering pays only if saves materialize. Great ratios but the fantasy cat (SV) is unreliable.
- **Action**: Note explicitly in the signal body. Waiver-analyst uses this to decide FAAB willingness.

## Guardrails

1. **Cite every fact.** Every numeric input (xwOBA, projected PAs, park factor, CS%) must trace to a URL in `source_urls:`. Unsourced claims fail the rubric's Source Citation criterion.

2. **OBP matters more than AVG for this league.** Our batting cats are R/HR/RBI/SB/OBP (not AVG). When computing `obp_contribution` and w
Files: 4
Size: 47.8 KB
Complexity: 44/100
Category: General

Related in General