Sign in

John From Albany

@johnfromalbany.bsky.social
191 followers 16 following 15K posts

Upstate Mets Fan - metsnewslinks.com - Mets & Mets Minor Leagues Media Credentials for the Syracuse Mets, Binghamton Rumble Ponies & Brooklyn Cyclones

PostsRepliesMedia
John From Albany @johnfromalbany.bsky.social · 1h
dlvr.it
Mets Calendar Classics - Mets Post Season Games Played On This Date: October 3rd
  NY Post Front Page, 10/4/2024 Year: 2024; NLWCS Game #3; Thursday; Oct 3, NYM 4 @ MIL 2; boxscore; WP: Edwin Diaz; LP: Devin Williams; Save: David Peterson; Time: 2:50; Day; Attendance: 41,594; Record: 2-1; W; Mets win the Wild Card Series 2-1. Francisco Lindor SS: 2 for 3; 2B; 1 run; 1 walk; Mark Vientos 3B: 0 for 4; 3 Ks; Luisangel Acuña 2B: 0 for 0; Brandon Nimmo LF: 1 for 4; 1 run; 1 K; Pete Alonso 1B: 1 for 4; HR; 1 run; 3 RBIs; 1 K; Jose Iglesias 2B-3B: 0 for 4; Jesse Winker DH: 0 for 2; SB,2·HBP; 1 run; 1 K; Starling Marte RF: 1 for 4; 1 RBI; 1 K; Harrison Bader CF: 0 for 0; Tyrone Taylor CF-RF: 0 for 4; 1 K; Francisco Alvarez C: 0 for 3; 1 K; Jose Quintana: 6 innings; no runs; 4 hits; 1 walk; 5 Ks; José Buttó: 0.1 inning; 2 runs; 2 ERs; 2 hits; 2 HRs; Edwin Díaz, W (1-0): 1.2 innings; no runs; 2 walks; 3 Ks; David Peterson, S (1): 1 inning; no runs; 1 hit; 1 K;
000
John From Albany @johnfromalbany.bsky.social · 3h
dlvr.it
Around the Majors with Mets News and Links - 10/3/2026
Here are the top Stories from every Major League team courtesy from our friends at SportSpyder. Note - this page updates throughout the day - come back later today for the latest news.
000
John From Albany @johnfromalbany.bsky.social · 11h
dlvr.it
Ernest Dove: New York Mets System - Season In Review - 10/2/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 14h
dlvr.it
How did the Mets’ hitters do versus preseason ZiPS projections?
The other day, ChrisF and I had a back-and-forth about reasonable expectations. Click Link Below to Read Article. http://dlvr.it/TVlY8W
000
John From Albany @johnfromalbany.bsky.social · 15h
dlvr.it
Lunch Time Links - Top MLB Headlines Now - 10/2/2026
Here are some of the News and Headlines around Major League Baseball courtesy from our friends at SportSpyder.
010
John From Albany @johnfromalbany.bsky.social · 17h
dlvr.it
MACK – Let’s Revisit -RHSP - Jose Chirinos
 
000
John From Albany @johnfromalbany.bsky.social · 18h
dlvr.it
Arizona Fall Mets Prospect Profile: RHP Brendan Girton 10/2/26
Brendan Girton, Photo courtesy of the Brooklyn Cyclones The one player joining the Mets contingent in the Arizona Fall League in 2026  that did not see time on the IL is Right-Handed Pitcher Brendan Girton.   Drafted in 2024, Brendan started 2025 in Brooklyn where he shined.  After throwing 5 perfect innings with a 6 Ks in a no June decision, he was named the South Atlantic League Pitcher of the Week for June 10-15, 2025.  He also threw 10 straight outings where he allowed 1 or fewer runs.  His 2025 Brooklyn record: 3-3, 2.59 ERA, 91 Ks in 76.1 innings, 34 walks, 1.114 WHIP. Brendan started off the 2026 season in the Binghamton rotation, but after he went 1-4 with a 6.71 ERA in 15 games, 57.2 innings as a starter, he moved to the bullpen.  After a few rocky multi-inning relief outings, Brendan settled in to a 1-inning relief role where he faired much better.  Not counting one bad 4-run outing, he posted a 1.64 ERA in 11 innings, 9 Ks, 2 walks, 6 hits, 1 HR.   Pitch Arsenal: 4-Seam Fastball (92-96), 2-Seam Fastball (91-94). Slider (86-89), Sweeper (82-85, Splitter (86-88).   Loading player profile… #pp-widget { max-width: 820px; margin: 0 auto; font-family: 'Barlow Condensed', -apple-system, 'Segoe UI', Arial, sans-serif; color: #1a1a1a; } #pp-widget * { box-sizing: border-box; } #pp-widget .pp-loading { text-align: center; padding: 30px; color: #6c757d; font-size: 18px; } #pp-widget .pp-card { background: #fff; border-radius: 12px; box-shadow: 0 2px 8px rgba(0,0,0,0.12); overflow: hidden; margin-bottom: 20px; } /* header */ #pp-widget .pp-header { background: linear-gradient(135deg, #002D72 0%, #FF5910 100%); color: #fff; padding: 22px; } #pp-widget .pp-head-row { display: flex; align-items: center; gap: 18px; margin-bottom: 14px; flex-wrap: wrap; } #pp-widget .pp-headshot { width: 92px; height: 92px; border-radius: 50%; border: 3px solid #fff; background: #fff; object-fit: cover; flex-shrink: 0; } #pp-widget .pp-number { font-size: 44px; font-weight: 700; opacity: 0.9; } #pp-widget .pp-name h1 { font-size: 34px; margin: 0 0 2px 0; line-height: 1.1; color: #fff; } #pp-widget .pp-pos { font-size: 18px; opacity: 0.92; } #pp-widget .pp-bio { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 10px; font-size: 15px; } #pp-widget .pp-bio-item { background: rgba(255,255,255,0.14); padding: 7px 11px; border-radius: 6px; } #pp-widget .pp-bio-label { opacity: 0.82; font-size: 12px; text-transform: uppercase; letter-spacing: 0.5px; margin-bottom: 1px; } /* jump nav */ #pp-widget .pp-nav { display: flex; gap: 8px; flex-wrap: wrap; padding: 10px 22px; background: #f8f9fa; border-bottom: 1px solid #e9ecef; } #pp-widget .pp-nav a { color: #002D72; font-weight: 600; text-decoration: none; font-size: 15px; padding: 4px 10px; border-radius: 14px; border: 1px solid #d7dbe0; background: #fff; } #pp-widget .pp-nav a:hover { background: #002D72; color: #fff; } /* sections */ #pp-widget .pp-section { padding: 20px 22px; } #pp-widget .pp-title { font-size: 22px; font-weight: 700; color: #002D72; margin: 0 0 12px 0; padding-bottom: 6px; border-bottom: 2px solid #FF5910; } #pp-widget .pp-sub { font-size: 17px; font-weight: 700; color: #002D72; margin: 16px 0 6px 0; } #pp-widget .pp-note { font-size: 13px; color: #6c757d; margin: 6px 0 0 0; } #pp-widget .pp-empty { font-size: 15px; color: #6c757d; padding: 8px 0; } /* quick stat boxes */ #pp-widget .pp-quick { display: grid; grid-template-columns: repeat(auto-fit, minmax(88px, 1fr)); gap: 12px; margin-bottom: 8px; } #pp-widget .pp-qbox { text-align: center; padding: 12px 6px; background: #f8f9fa; border: 1px solid #e9ecef; border-radius: 8px; } #pp-widget .pp-qval { font-size: 26px; font-weight: 700; color: #002D72; } #pp-widget .pp-qlbl { font-size: 12px; color: #6c757d; text-transform: uppercase; letter-spacing: 0.5px; } /* tables */ #pp-widget .pp-twrap { overflow-x: auto; -webkit-overflow-scrolling: touch; } #pp-widget table.pp-table { width: 100%; border-collapse: collapse; margin-bottom: 6px; } #pp-widget table.pp-table th { background: #002D72; color: #fff; padding: 9px 6px; text-align: center; font-size: 12px; font-weight: 600; text-transform: uppercase; white-space: nowrap; } #pp-widget table.pp-table td { padding: 8px 6px; text-align: center; border-bottom: 1px solid #e9ecef; font-size: 14px; white-space: nowrap; } #pp-widget table.pp-table tr:hover td { background: #f8f9fa; } #pp-widget td.pp-left, #pp-widget th.pp-left { text-align: left; } #pp-widget .pp-yr { font-weight: 600; color: #002D72; } #pp-widget .pp-lvl { display: inline-block; background: #002D72; color: #fff; border-radius: 10px; font-size: 11px; font-weight: 700; padding: 1px 8px; margin-left: 6px; vertical-align: 1px; } #pp-widget tr.pp-total td { font-weight: 700; background: #fff4ee; border-top: 2px solid #FF5910; } #pp-widget tr.pp-career td { font-weight: 700; background: #eaf0fa; border-top: 2px solid #002D72; } /* v2.4: repeated header rows inside long tables */ #pp-widget table.pp-table tr.pp-rehead th { border-top: 2px solid #FF5910; } #pp-widget td.pp-lnk a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget td.pp-lnk a:hover { text-decoration: underline; } /* splits + fielding + game log season chips */ #pp-widget .pp-chips { display: flex; gap: 6px; flex-wrap: wrap; margin-bottom: 10px; } #pp-widget .pp-chip { border: 1px solid #002D72; color: #002D72; background: #fff; border-radius: 14px; padding: 3px 12px; font-size: 14px; font-weight: 600; cursor: pointer; font-family: inherit; } #pp-widget .pp-chip.pp-on { background: #002D72; color: #fff; } /* videos */ #pp-widget .pp-vids { display: grid; grid-template-columns: repeat(auto-fill, minmax(230px, 1fr)); gap: 14px; } #pp-widget .pp-vcard { border: 1px solid #e9ecef; border-radius: 8px; overflow: hidden; background: #fff; } #pp-widget .pp-vcard-x { grid-column: 1 / -1; max-width: 560px; } #pp-widget .pp-vcard-x blockquote { margin: 0 auto; } #pp-widget .pp-vthumb { position: relative; cursor: pointer; background: #000; } #pp-widget .pp-vthumb img { width: 100%; display: block; aspect-ratio: 16/9; object-fit: cover; } #pp-widget .pp-vplay { position: absolute; top: 50%; left: 50%; transform: translate(-50%,-50%); width: 44px; height: 44px; border-radius: 50%; background: rgba(0,45,114,0.85); color: #fff; display: flex; align-items: center; justify-content: center; font-size: 18px; pointer-events: none; } #pp-widget .pp-vdur { position: absolute; right: 6px; bottom: 6px; background: rgba(0,0,0,0.75); color: #fff; font-size: 11px; padding: 1px 6px; border-radius: 3px; } #pp-widget .pp-vbody { padding: 8px 10px 10px 10px; } #pp-widget .pp-vtitle { font-size: 14px; font-weight: 600; line-height: 1.25; color: #1a1a1a; margin-bottom: 4px; } #pp-widget .pp-vmeta { font-size: 12px; color: #6c757d; display: flex; justify-content: space-between; } #pp-widget .pp-vmeta a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget .pp-vcard video { width: 100%; display: block; aspect-ratio: 16/9; background: #000; } #pp-widget .pp-vlink { display: block; background: #002D72; color: #fff; text-align: center; padding: 34px 10px; font-weight: 700; text-decoration: none; } /* footer */ #pp-widget .pp-footer { padding: 12px 22px; background: #f8f9fa; text-align: center; font-size: 12px; color: #6c757d; } #pp-widget .pp-footer a { color: #002D72; font-weight: 600; text-decoration: none; } @media (max-width: 600px) { #pp-widget .pp-header { padding: 15px; } #pp-widget .pp-name h1 { font-size: 26px; } #pp-widget .pp-number { font-size: 34px; } #pp-widget .pp-section { padding: 15px 12px; } #pp-widget table.pp-table th, #pp-widget table.pp-table td { padding: 6px 4px; font-size: 12px; } } (function () { // ================= CONFIG - EDIT THIS ================= var PLAYER_ID = 694858; // { code: totals }. // Tries the Stats API careerStatSplits call first; if nothing comes // back, sums every season's statSplits for that level instead. function loadCareerSplits(group, sportId, seasons, accF) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=careerStatSplits&group=' + group + '&sportId=' + sportId + '&sitCodes=' + SIT_CODE_STR) .then(function (d) { return splitsOf(d); }) .catch(function () { return []; }) .then(function (sp) { var direct = sumByCode(sp, accF, true); if (Object.keys(direct).length) return direct; return Promise.all(seasons.map(function (yr) { return loadSplits(group, yr, [sportId]); })) .then(function (arrs) { var out = {}; arrs.forEach(function (list) { var yrTot = sumByCode(list, accF, false); Object.keys(yrTot).forEach(function (c) { out[c] = addTot(out[c] || {}, yrTot[c]); }); }); return out; }); }); } var MONTH_NAMES = ['','January','February','March','April','May','June','July','August','September','October','November','December']; function loadMonthly(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=byMonth&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return (n(a.month) - n(b.month)) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: GAME LOG (v2.4) ---------------- function loadGameLog(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=gameLog&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return String(b.date || '').localeCompare(String(a.date || '')) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: PITCH ARSENAL / VELO (v2.4) ---------------- // Only levels with pitch tracking: MLB (1), AAA (11), Low-A (14). var PITCH_SPORT_IDS = [1, 11, 14]; function loadPitchData(season) { return Promise.all(PITCH_SPORT_IDS.map(function (sid) { var ars = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchArsenal&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); var log = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchLog&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); return Promise.all([ars, log]).then(function (r) { return { sportId: sid, arsenal: r[0], log: r[1] }; }); })); } // ---------------- FETCH: TRANSACTIONS ---------------- function loadTransactions() { var end = new Date().toISOString().slice(0,10); return jget(API + '/transactions?playerId=' + PLAYER_ID + '&startDate=2010-01-01&endDate=' + end) .then(function (d) { var tx = (d.transactions || []).slice(); tx.sort(function (a, b) { return String(b.date).localeCompare(String(a.date)); }); return tx.slice(0, TX_MAX); }) .catch(function () { return []; }); } // ---------------- FETCH: FILM ROOM VIDEOS ---------------- var GQL = 'query Search($query: String!, $page: Int, $limit: Int, $feedPreference: FeedPreference, ' + '$languagePreference: LanguagePreference, $contentPreference: ContentPreference, $queryType: QueryType = STRUCTURED) {\n' + ' search(query: $query, limit: $limit, page: $page, feedPreference: $feedPreference, ' + 'languagePreference: $languagePreference, contentPreference: $contentPreference, queryType: $queryType) {\n' + ' plays {\n mediaPlayback {\n slug\n title\n blurb\n date\n' + ' feeds {\n type\n duration\n' + ' image { cuts { width src } }\n' + ' playbacks { name url }\n }\n }\n }\n }\n}'; function gqlVars(queryStr, limit) { return { queryType: null, query: queryStr, limit: limit || VIDEO_LIMIT, page: 0, languagePreference: 'EN', contentPreference: 'CMS_FIRST' }; } function videoSearchUrl(queryStr, limit) { return 'https://fastball-gateway.mlb.com/graphql' + '?query=' + encodeURIComponent(GQL) + '&operationName=Search' + '&variables=' + encodeURIComponent(JSON.stringify(gqlVars(queryStr, limit))); } function proxyPlayerUrl(person) { var teamId = (person && person.currentTeam && person.currentTeam.id) || ''; var last = (person && (person.lastName || (person.fullName || '').split(' ').pop())) || ''; return PROXY_URL + '?player=' + PLAYER_ID + '&team=' + teamId + '&name=' + encodeURIComponent(last) + '&limit=' + VIDEO_LIMIT; } var ppJsonpCount = 0; function jsonpCall(baseUrl) { return new Promise(function (resolve, reject) { var cb = 'ppVidCb' + (++ppJsonpCount); var s = document.createElement('script'); var timer = setTimeout(function () { cleanup(); reject(new Error('proxy timeout')); }, 30000); function cleanup() { clearTimeout(timer); try { delete window[cb]; } catch (e) { window[cb] = undefined; } if (s.parentNode) s.parentNode.removeChild(s); } window[cb] = function (data) { cleanup(); resolve(data); }; s.onerror = function () { cleanup(); reject(new Error('proxy load error')); }; s.src = baseUrl + '&callback=' + cb; document.head.appendChild(s); }); } function proxyJson(baseUrl) { return fetch(baseUrl).then(function (r) { if (!r.ok) throw new Error('proxy HTTP ' + r.status); return r.json(); }); } function gqlPost(queryStr, limit) { return fetch('https://fastball-gateway.mlb.com/graphql', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ query: GQL, operationName: 'Search', variables: gqlVars(queryStr, limit) }) }).then(function (r) { if (!r.ok) throw new Error('HTTP ' + r.status + ' (POST)'); return r.json(); }); } function gqlFetch(queryStr, limit) { return jget(videoSearchUrl(queryStr, limit)) .catch(function () { return gqlPost(queryStr, limit); }); } function fmtDur(sec) { if (sec == null || sec === '') return ''; if (typeof sec === 'string' && sec.indexOf(':') > -1) return sec.replace(/^00:0?/, ''); var x = parseInt(sec, 10); if (isNaN(x)) return ''; return Math.floor(x / 60) + ':' + ('0' + (x % 60)).slice(-2); } function pickPlayback(feeds) { if (!feeds || !feeds.length) return { mp4: null, thumb: '', dur: '' }; var ranked = feeds.slice().sort(function (a, b) { return ((a.type === 'CMS') ? 0 : 1) - ((b.type === 'CMS') ? 0 : 1); }); var mp4 = null, thumb = '', dur = ''; for (var i = 0; i < ranked.length; i++) { var f = ranked[i]; if (!dur && f.duration) dur = fmtDur(f.duration); if (!thumb && f.image && f.image.cuts && f.image.cuts.length) { var cuts = f.image.cuts.slice().sort(function (a, b) { return (b.width||0) - (a.width||0); }); var mid = cuts.filter(function (c) { return c.width && c.width 1) { html += ' ' + esc(yr) + ' ' + esc(opts.totalLabel) + ' ' + cellsHTML(totF(yrTot)) + ' '; } // v2.4: repeat the column header row every HEADER_REPEAT seasons if (n(HEADER_REPEAT) > 0 && (si + 1) % n(HEADER_REPEAT) === 0 && si < seasons.length - 1) { html += headRowHTML('Year / Team', cols, 'pp-rehead'); } }); if (seasons.length) { html += ' ' + esc(opts.careerLabel) + ' ' + cellsHTML(totF(career)) + ' '; } return html ? tableHTML(opts.id, 'Year / Team', cols, html) : ''; } // ---------------- MAIN ---------------- loadPerson().then(function (person) { if (!person) { root.innerHTML = 'Player not found for ID ' + PLAYER_ID + '.'; return; } return Promise.all([ loadYearByYear('hitting'), loadYearByYear('pitching'), loadYearByYear('fielding'), loadTransactions(), loadVideos(person), loadJersey(person) ]) .then(function (res) { render(person, res[5], res[0], res[1], res[2], res[3], res[4]); }); }) .catch(function (e) { root.innerHTML = 'Could not load profile (' + esc(e.message) + '). Please refresh.'; }); function render(person, jersey, hitRows, pitRows, fldRows, txs, vids) { var isPitcher = person.primaryPosition && person.primaryPosition.code === '1'; var hasHit = hitRows.some(function (r) { return n(r.stat.atBats) || n(r.stat.plateAppearances); }); var hasPit = pitRows.some(function (r) { return ipToOuts(r.stat.inningsPitched) || n(r.stat.gamesPlayed); }); var usePit = isPitcher && hasPit; var showPitches = usePit && SHOW_PITCHES; var showGameLog = n(RECENT_GAMES) > 0 && (hasPit || hasHit); var headshot = 'https://img.mlbstatic.com/mlb-photos/image/upload/d_people:generic:headshot:67:current.png' + '/w_180,q_auto:best/v1/people/' + PLAYER_ID + '/headshot/milb/current'; var birth = [person.birthCity, person.birthStateProvince, person.birthCountry].filter(Boolean).join(', '); var teamName = (person.currentTeam && person.currentTeam.name) || 'New York Mets Organization'; var h = ''; // ---- header ---- h += '' + '' + (jersey ? '#' + esc(jersey) + '' : '') + ' ' + esc(person.fullName) + ' ' + '' + esc((person.primaryPosition && person.primaryPosition.name) || '') + ' • ' + esc(teamName) + '' + '' + 'Full Name' + esc(person.fullFMLName || person.fullName) + '' + 'Bats/Throws' + esc(((person.batSide||{}).code||'') + '/' + ((person.pitchHand||{}).code||'')) + '' + 'Height/Weight' + esc((person.height||'') + ' / ' + (person.weight ? person.weight + ' lbs' : '')) + '' + 'Born' + esc(fmtDate(person.birthDate) + (person.currentAge ? ' (Age ' + person.currentAge + ')' : '')) + '' + (birth ? 'Birthplace' + esc(birth) + '' : '') + (HOW_ACQUIRED ? 'How Acquired' + esc(HOW_ACQUIRED) + '' : '') + EXTRA_BOXES.map(function (b) { if (!b || !b.value) return ''; return '' + esc(b.label || '') + '' + esc(b.value) + ''; }).join('') + ''; // ---- jump nav ---- h += 'Stats' + (showPitches ? 'Pitches' : '') + 'Splits' + 'Fielding' + (showGameLog ? 'Game Log' : '') + 'VideosTransactions'; // ---- stats ---- h += ' Statistics '; var groups = []; if (isPitcher) { if (hasPit) groups.push('P'); if (hasHit) groups.push('H'); } else { if (hasHit) groups.push('H'); if (hasPit) groups.push('P'); } if (!groups.length) h += 'No stats available yet.'; groups.forEach(function (g) { var rows = (g === 'H') ? hitRows : pitRows; var isP = (g === 'P'); var gLbl = isP ? 'Pitching' : 'Hitting'; var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); var winter = rows.filter(function (r) { return r.sportId === 17; }); var mlbT = buildStatsTable(mlb, isP, { id: 'pp-mlb-' + g, totalLabel: 'MLB Total', careerLabel: 'MLB Career' }); var milbT = buildStatsTable(milb, isP, { id: 'pp-milb-' + g, totalLabel: 'MiLB Total', careerLabel: 'MiLB Career', rates: !isP }); var winterT = buildStatsTable(winter, isP, { id: 'pp-winter-' + g, totalLabel: 'Total', careerLabel: 'Winter/AFL Career' }); if (mlbT) h += 'MLB ' + gLbl + '' + mlbT; if (milbT) h += 'Minor League ' + gLbl + '' + milbT; if (winterT) h += 'Winter Ball / AFL ' + gLbl + '' + winterT; }); h += ''; // ---- pitch arsenal (v2.4, pitchers only) ---- if (showPitches) { h += ' Pitch Arsenal ' + 'Loading pitch data…'; } // ---- splits ---- h += ' Splits ' + 'Loading splits…'; // ---- fielding (v2.3) ---- h += ' Fielding ' + 'Loading fielding…'; // ---- game log (v2.4) ---- if (showGameLog) { h += ' Game Log ' + 'Loading game log…'; } // ---- videos ---- h += ' Video Highlights '; var autoVids = vids.list || []; var hasAny = MANUAL_VIDEOS.length || autoVids.length; var hasXPost = false; if (hasAny) { h += ''; MANUAL_VIDEOS.forEach(function (v) { var yt = ytEmbedUrl(v.url); var xp = xPostUrl(v.url); if (xp) { hasXPost = true; h += '' + '' + '' + esc(v.title || 'View post on X') + '' + '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + 'View on X'; return; } h += ''; if (yt) { h += ''; } else if (/\.mp4(\?|$)/i.test(v.url || '')) { h += ''; } else if (isMlbVideoUrl(v.url)) { var mlbEmb = mlbEmbedUrl(v.url); if (mlbEmb) { h += ''; } else { h += '► Watch on MLB.com'; } } else { h += '► Watch Video'; } h += '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + (isMlbVideoUrl(v.url) ? 'View on MLB.com' : '') + ''; }); autoVids.forEach(function (v, i) { h += '' + '' + (v.thumb ? '' : '') + '►' + (v.dur ? '' + esc(v.dur) + '' : '') + '' + esc(v.title) + '' + '' + esc(fmtDate(v.date)) + '' + 'Watch on MiLB.com' + ''; }); h += ''; if (autoVids.length) { h += 'Auto-updated from MLB Film Room. Full library: ' + 'milb.com/video/topic/playerid-' + PLAYER_ID + ''; } } if (!autoVids.length && !MANUAL_VIDEOS.length) { h += '' + (vids.error ? 'The automatic video feed could not load (' + esc(vids.error) + '). ' + 'If this keeps happening, set PROXY_URL in the config to your Apps Script passthrough. ' : 'No clips found in the Film Room index for this player yet. ') + 'Full library: MiLB.com.'; } else if (!autoVids.length && vids.error) { h += 'The automatic video feed could not load (' + esc(vids.error) + ').'; } h += ''; // ---- transactions ---- h += ' Transactions '; if (txs.length) { var trows = ''; txs.forEach(function (t) { trows += ' ' + esc(fmtDate(t.date)) + ' ' + ' ' + esc(t.typeDesc || '') + ' ' + ' ' + esc(t.description || '') + ' '; }); h += ' Date Type Transaction ' + trows + ' '; } else { h += 'No transactions on record.'; } h += ''; // ---- footer ---- h += 'Stats & transactions from the MLB Stats API • Videos from MLB Film Room • ' + 'MiLB.com Player Page • ' + 'MLB.com Player Page' + ''; root.innerHTML = h; if (hasXPost) loadXWidgets(); // ---- header stat boxes (v2.4: separate MLB / MiLB rows) ---- buildQuickStats(usePit ? pitRows : hitRows, usePit); // ---- video inline playback ---- root.querySelectorAll('.pp-vthumb').forEach(function (el) { el.addEventListener('click', function () { var mp4 = el.getAttribute('data-mp4'); if (!mp4) { var link = el.getAttribute('data-link'); if (link) window.open(link, '_blank'); return; } var v = document.createElement('video'); v.controls = true; v.autoplay = true; v.src = mp4; v.setAttribute('playsinline',''); el.parentNode.replaceChild(v, el); }); }); var group = usePit ? 'pitching' : 'hitting'; var groupRows = usePit ? pitRows : hitRows; if (showPitches) initPitches(pitRows); initSplits(group, groupRows, usePit); initFielding(fldRows); if (showGameLog) initGameLog(group, groupRows, usePit); } // ---------------- HEADER STAT BOXES (v2.4) ---------------- // One row of boxes per HEADER_STATS entry ('MLB' / 'MiLB') for the // player's most recent season. A row is skipped if the player has // no stats at that level in that season. function buildQuickStats(rows, isPitching) { var box = document.getElementById('pp-quick'); if (!box || !rows.length || !HEADER_STATS || !HEADER_STATS.length) return; var reg = rows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) return; var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); var yr = reg.filter(function (r) { return r.season === latest; }); var accF = isPitching ? pitAccumulate : hitAccumulate; var html = ''; HEADER_STATS.forEach(function (lvlKey) { var isMlb = /^mlb$/i.test(String(lvlKey)); var list = yr.filter(function (r) { return isMlb ? r.sportId === 1 : isMilbSport(r.sportId); }); if (!list.length) return; var tot = {}; list.forEach(function (r) { accF(tot, r.stat); }); var items; if (isPitching) { items = [ [n(tot.wins) + '-' + n(tot.losses), 'W-L'], [era(n(tot.earnedRuns), n(tot.outs)), 'ERA'], [outsToIp(n(tot.outs)), 'IP'], [n(tot.strikeOuts), 'SO'], [whip(n(tot.baseOnBalls), n(tot.hits), n(tot.outs)), 'WHIP'] ]; } else { var c = hitTotalCells(tot, false); // [G,AB,R,H,2B,3B,HR,RBI,SB,BB,SO,AVG,OBP,SLG,OPS] items = [ [c[11], 'AVG'], [c[6], 'HR'], [c[7], 'RBI'], [c[8], 'SB'], [c[14], 'OPS'] ]; } html += '' + (isMlb ? 'MLB ' : 'MiLB ') + esc(latest) + ' Stats' + items.map(function (it) { return '' + esc(it[0]) + '' + esc(it[1]) + ''; }).join('') + ''; }); box.innerHTML = html; } // ---------------- PITCH ARSENAL UI (v2.4) ---------------- var PITCH_COLS = ['Usage','Avg MPH','Top MPH','Pitches']; function initPitches(pitRows) { var body = document.getElementById('pp-pitch-body'); var title = document.getElementById('pp-pitch-title'); if (!body) return; var reg = pitRows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) { body.innerHTML = 'No pitch data available.'; return; } var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); if (title) title.innerHTML = 'Pitch Arsenal — ' + esc(latest); loadPitchData(latest).then(function (res) { var out = ''; res.forEach(function (r) { var map = {}; function slot(code, desc) { return map[code] = map[code] || { code: code, desc: desc || code, usage: null, avg: null, max: null, count: 0, sum: 0, cnt: 0 }; } (r.arsenal || []).forEach(function (s) { var st = s.stat || {}; var t = st.type || {}; var code = t.code || t.description; if (!code) return; var m = slot(code, t.description); var p = Number(st.percentage); if (!isNaN(p) && st.percentage != null) m.usage = p m.max) m.max = v; m.sum += v; m.cnt++; }); var list = Object.keys(map).map(function (k) { return map[k]; }); if (!list.length) return; list.forEach(function (m) { if (m.avg == null && m.cnt) m.avg = m.sum / m.cnt; if (!m.count && m.cnt) m.count = m.cnt; }); var totalCnt = list.reduce(function (a, m) { return a + n(m.count); }, 0); list.forEach(function (m) { if (m.usage == null && totalCnt) m.usage = 100 * n(m.count) / totalCnt; }); list.sort(function (a, b) { return (n(b.usage)) - (n(a.usage)); }); var rowsHtml = list.map(function (m) { return ' ' + esc(m.desc) + ' ' + cellsHTML([ m.usage != null ? m.usage.toFixed(1) + '%' : '--', m.avg != null ? m.avg.toFixed(1) : '--', m.max != null ? m.max.toFixed(1) : '--', m.count || '--' ]) + ' '; }).join(''); out += '' + esc(levelLabel(r.sportId, '')) + '' + ' ' + theadHTML('Pitch', PITCH_COLS) + '' + rowsHtml + ' '; }); body.innerHTML = out ? out + '' + esc(latest) + ' pitch tracking by level (MLB, AAA and Low-A only). Usage and average velocity from the MLB Stats API pitch arsenal; top velocity is the hardest tracked pitch of that type in the pitch log.' : 'No pitch-tracking data returned for ' + esc(latest) + ' (available for MLB, AAA and Low-A only).'; }).catch(function (e) { body.innerHTML = 'Pitch data could not load (' + esc(e && e.message) + ').'; }); } // ---------------- SPLITS UI (v2.4: career + season chips) ---------------- // v2.4.1: pitching splits use PIT_SPLIT_COLS / pitSplitTotalCells. function initSplits(group, rows, isPitching) { var chips = document.getElementById('pp-split-chips'); var body = document.getElementById('pp-split-body'); if (!chips || !body) return; var seasonsMap = {}, sidsAll = {}; rows.forEach(function (r) { if (r.sportId === 17) return; // winter splits not indexed the same way (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; sidsAll[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { body.innerHTML = 'No splits available.'; return; } chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var defs = isPitching ? SIT_CODES_PIT : SIT_CODES; var sCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS; var accF = isPitching ? pitAccumulate : hitAccumulate; var totF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, false); }; var careerCache = null; // ---- career view: MLB table + Minor Leagues table ---- function showCareer() { body.innerHTML = 'Loading career splits…'; if (!careerCache) { var sids = Object.keys(sidsAll).map(Number); careerCache = Promise.all(sids.map(function (sid) { var yrs = seasons.filter(function (s) { return seasonsMap[s][sid]; }); return loadCareerSplits(group, sid, yrs, accF).then(function (byCode) { return { sportId: sid, byCode: byCode }; }); })); } careerCache.then(function (res) { function tableFor(filterFn) { var html = ''; defs.forEach(function (def) { var tot = {}, any = false; res.filter(filterFn).forEach(function (r) { if (r.byCode[def.code]) { addTot(tot, r.byCode[def.code]); any = true; } }); if (any) html += ' ' + esc(def.label) + ' ' + cellsHTML(totF(tot)) + ' '; }); return html ? ' ' + theadHTML('Split', sCols) + '' + html + ' ' : ''; } var mlbT = tableFor(function (r) { return r.sportId === 1; }); var milbT = tableFor(function (r) { return isMilbSport(r.sportId); }); var out = ''; if (mlbT) out += 'MLB — Career Splits' + mlbT; if (milbT) out += 'Minor Leagues — Career Splits' + milbT; body.innerHTML = out ? out + 'Career splits (regular season). Minor league line combines every MiLB level. Rate stats are recomputed from the summed raw counts. Pick a season above for the year-by-year, per-level breakdown.' : 'No career split data available.'; }).catch(function (e) { body.innerHTML = 'Career splits could not load (' + esc(e && e.message) + ').'; }); } // ---- season view: per-level splits + By Month (unchanged from v2.3.1) ---- function showSeason(season) { body.innerHTML = 'Loading ' + esc(season) + ' splits…'; var sportIds = Object.keys(seasonsMap[season]).map(Number); Promise.all([ loadSplits(group, season, sportIds), loadMonthly(group, season, sportIds) ]) .then(function (res) { var splits = res[0], months = res[1]; if (!splits.length && !months.length) { body.innerHTML = 'No split data for ' + esc(season) + '.'; return; } var out = ''; var shtml = ''; defs.forEach(function (def) { var byLevel = {}; splits.filter(function (s) { return s.split && s.split.code === def.code; }) .forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = lvl || ('sid' + s._sportId); var g = byLevel[key] = byLevel[key] || { lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); Object.keys(byLevel).map(function (k) { return byLevel[k]; }) .sort(function (a, b) { return b.sportId - a.sportId; }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); shtml += ' ' + esc(def.label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(totF(tot)) + ' '; }); }); if (shtml) { out += ' ' + theadHTML('Split', sCols) + '' + shtml + ' '; } if (months.length) { var mCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS_RATES; var mTotF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, true); }; var byMonth = {}; months.forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = n(s.month) + '|' + (lvl || 'sid' + s._sportId); var g = byMonth[key] = byMonth[key] || { month: n(s.month), lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); var mhtml = ''; Object.keys(byMonth).map(function (k) { return byMonth[k]; }) .sort(function (a, b) { return (a.month - b.month) || (b.sportId - a.sportId); }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); var label = MONTH_NAMES[g.month] || ('Month ' + g.month); mhtml += ' ' + esc(label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(mTotF(tot)) + ' '; }); out += 'By Month' + ' ' + theadHTML('Month', mCols) + '' + mhtml + ' '; } body.innerHTML = out ? out + 'Splits and monthly totals shown per level for the selected season (regular season). Splits combine all teams at the same level into one line.' : 'No split data for ' + esc(season) + '.'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); var s = b.getAttribute('data-season'); if (s === 'ALL') showCareer(); else showSeason(s); }); showCareer(); } // ---------------- FIELDING UI (v2.3) ---------------- function initFielding(rows) { var chips = document.getElementById('pp-fld-chips'); var body = document.getElementById('pp-fld-body'); if (!chips || !body) return; rows = rows.filter(function (r) { return r.sportId !== 17 && r.position && (n(r.stat.gamesPlayed) || n(r.stat.chances) || ipToOuts(r.stat.innings)); }); if (!rows.length) { chips.innerHTML = ''; body.innerHTML = 'No fielding data available yet.'; return; } var seasonsMap = {}; rows.forEach(function (r) { seasonsMap[r.season] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); function buildRows(list, withLevel) { var groups = {}; list.forEach(function (r) { var key = r.position + (withLevel ? '|' + r.level : ''); if (!groups[key]) groups[key] = { pos: r.position, lvl: withLevel ? r.level : '', sportId: r.sportId, tot: {} }; fldAccumulate(groups[key].tot, r.stat); }); return Object.keys(groups).map(function (k) { return groups[k]; }) .sort(function (a, b) { var pa = POS_ORDER[a.pos] != null ? POS_ORDER[a.pos] : 99; var pb = POS_ORDER[b.pos] != null ? POS_ORDER[b.pos] : 99; return (pa - pb) || (a.sportId - b.sportId); }) .map(function (g) { return ' ' + esc(g.pos) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(fldTotalCells(g.tot)) + ' '; }).join(''); } function fldTable(rowsHTML) { return ' ' + theadHTML('Pos', FLD_COLS) + '' + rowsHTML + ' '; } function show(season) { var out = ''; if (season === 'ALL') { var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); if (mlb.length) out += 'MLB — Career Totals by Position' + fldTable(buildRows(mlb, false)); if (milb.length) out += 'Minor Leagues — Career Totals by Position' + fldTable(buildRows(milb, false)); body.innerHTML = out ? out + 'Career fielding totals by position (regular season). FLD% is recomputed from combined PO/A/TC. Pick a season above for the year-by-year breakdown.' : 'No fielding data available yet.'; } else { var yr = rows.filter(function (r) { return r.season === season; }); out = yr.length ? fldTable(buildRows(yr, true)) : ''; body.innerHTML = out ? out + '' + esc(season) + ' fielding by position; multiple teams at the same level are combined into one line.' : 'No fielding data for ' + esc(season) + '.'; } } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('ALL'); } // ---------------- GAME LOG UI (v2.4) ---------------- // Default chip: "Last N Games" across all levels of the most recent // season (most recent first, each date links to Gameday) plus a // totals row. Season chips show the full game log for that year. var GL_PIT_COLS = ['Dec','IP','H','R','ER','HR','BB','SO','P']; var GL_HIT_COLS = ['AB','R','H','2B','3B','HR','RBI','BB','SO','SB']; function glDecision(st) { if (n(st.wins)) return 'W'; if (n(st.losses)) return 'L'; if (n(st.saves)) return 'SV'; if (n(st.holds)) return 'HLD'; if (n(st.blownSaves)) return 'BS'; return ''; } function glTheadHTML(cols) { return ' Date Opp Lvl ' + cols.map(function (c) { return ' ' + c + ' '; }).join('') + ' '; } function glRowHTML(s, isPitching) { var st = s.stat || {}; var lvl = levelLabel(s._sportId, s.league && s.league.name); var opp = (s.opponent && (s.opponent.abbreviation || s.opponent.name)) || ''; var oppTxt = (s.isHome === false ? '@ ' : 'vs ') + opp; var pk = s.game && s.game.gamePk; var gd = pk ? (s._sportId === 1 ? 'https://www.mlb.com/gameday/' : 'https://www.milb.com/gameday/') + pk : ''; var dateCell = gd ? '' + esc(fmtDate(s.date)) + '' : esc(fmtDate(s.date)); var cells = isPitching ? [ glDecision(st), st.inningsPitched || '0.0', n(st.hits), n(st.runs), n(st.earnedRuns), n(st.homeRuns), n(st.baseOnBalls), n(st.strikeOuts), st.numberOfPitches != null ? n(st.numberOfPitches) : '--' ] : [ n(st.atBats), n(st.runs), n(st.hits), n(st.doubles), n(st.triples), n(st.homeRuns), n(st.rbi), n(st.baseOnBalls), n(st.strikeOuts), n(st.stolenBases) ]; return ' ' + dateCell + ' ' + ' ' + esc(oppTxt) + ' ' + ' ' + (lvl ? '' + esc(lvl) + '' : '') + ' ' + cellsHTML(cells) + ' '; } function glTotalRowHTML(list, isPitching, label) { var tot = {}, pitches = 0, hasPitches = false; list.forEach(function (s) { var st = s.stat || {}; (isPitching ? pitAccumulate : hitAccumulate)(tot, st); if (st.numberOfPitches != null) { pitches += n(st.numberOfPitches); hasPitches = true; } }); var cells, txt; if (isPitching) { txt = label + ' (' + era(n(tot.earnedRuns), n(tot.outs)) + ' ERA)'; cells = [ '', outsToIp(n(tot.outs)), n(tot.hits), n(tot.runs), n(tot.earnedRuns), n(tot.homeRuns), n(tot.baseOnBalls), n(tot.strikeOuts), hasPitches ? pitches : '--' ]; } else { txt = label + ' (' + fmtAvg(tot.atBats ? tot.hits / tot.atBats : NaN) + ' AVG)'; cells = [ n(tot.atBats), n(tot.runs), n(tot.hits), n(tot.doubles), n(tot.triples), n(tot.homeRuns), n(tot.rbi), n(tot.baseOnBalls), n(tot.strikeOuts), n(tot.stolenBases) ]; } return ' ' + esc(txt) + ' ' + cellsHTML(cells) + ' '; } function initGameLog(group, rows, isPitching) { var chips = document.getElementById('pp-gl-chips'); var body = document.getElementById('pp-gl-body'); if (!chips || !body) return; var seasonsMap = {}; rows.forEach(function (r) { if (r.sportId === 17) return; (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { chips.innerHTML = ''; body.innerHTML = 'No game log available.'; return; } var N = n(RECENT_GAMES); chips.innerHTML = 'Last ' + N + ' Games' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var cols = isPitching ? GL_PIT_COLS : GL_HIT_COLS; var cache = {}; function fetchSeason(season) { if (!cache[season]) cache[season] = loadGameLog(group, season, Object.keys(seasonsMap[season]).map(Number)); return cache[season]; } function tableHTMLFor(list, totalLabel) { return ' ' + glTheadHTML(cols) + '' + list.map(function (s) { return glRowHTML(s, isPitching); }).join('') + (list.length > 1 ? glTotalRowHTML(list, isPitching, totalLabel) : '') + ' '; } function show(key) { var recent = key === 'RECENT'; var season = recent ? seasons[0] : key; body.innerHTML = 'Loading ' + (recent ? 'recent games' : esc(season) + ' game log') + '…'; fetchSeason(season).then(function (all) { var list = recent ? all.slice(0, N) : all; if (!list.length) { body.innerHTML = 'No games on record for ' + esc(season) + '.'; return; } body.innerHTML = tableHTMLFor(list, recent ? 'Last ' + list.length : esc(season) + ' Total') + '' + (recent ? 'Most recent ' + list.length + ' games across all levels (' + esc(season) + '), newest first. ' : esc(season) + ' game log, all levels, newest first. ') + 'Dates link to the Gameday box score. Pick a season above for the full log.'; }).catch(function (e) { body.innerHTML = 'Game log could not load (' + esc(e && e.message) + ').'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('RECENT'); } })();
001
John From Albany @johnfromalbany.bsky.social · 19h
dlvr.it
Reese Kaplan -- Former NY Mets Starting Pitchers Who are FAs
One of the ongoing debates among Mets fans is the pressure of performing in New York City and the experience of various players available in free agency who either flourished or foundered at Citifield.   With POBO David Stearns declaring the need to reinforce the starting rotation as priority number one for the theoretically existing 2027 season  it is interesting to note that in free agency a baker’s dozen of former Mets hurlers are available to the highest bidder.  Some could make sense.  Others might not. Former Mets Starting Pitchers Up for Bid * 38 year old Chris Bassitt had a very productive single season for the Mets back in 2022 when he went 15-9 with a 3.42 ERA.  That level of mid rotation effectiveness led to his free agent departure at year’s end.  He had a similar first year in Toronto bt it’s been mostly downhill as he enters the twilight of his playing career.  During 2026 he went 9-5 with a 4.59 ERA for the Orioles, so it’s not as if he would cost very much but he may not be a proper fit anymore.  * Paul Blackburn was not nearly as well regarded while a member of the team.  At age 33 he’s been a space filler as a starting pitcher.  He owns a ten-year losing record and a career ERA of 4.46.  Last season the Yankees converted him to full time reliever and he flourished.  For the season over 62 games he went 7-2 with a microscopic 1.66 ERA.  Some teams might feel his conversion to bullpen work was what he needed while others would look at the whole ledger of mediocrity and not want to gamble that one good year made up for nine terrible ones.  The memories are way too negative for the Mets to place him on their radar. * Injury plagued Griffin Canning was surprisingly decent when no one had any real knowledge of nor confidence in him when Stearns acquired him for part of the 2025 season.  His contract has a $5 million mutual option at year’s end and after a Padres 5-9 season with an ERA of 5.59 it’s unlikely he will be brought back.  He’s not a true difference maker and unless it was bargain hunting as a primary motivation he doesn’t seem to be a good fit either. * Now 40 year old Carlos Carrasco hasn’t had an ERA below 5.64 in the three years since hitting the road.  No thanks. * Clay Holmes was something of a found miracle when the Mets converted him from reliever to starter.  His injuries interrupted this transition but the numbers certainly don’t lie.  For the Mets he delivered a 3.53 ERA in 2025 and was at just 2.39 when he was dealt away in the trade deadline housecleaning.  His option for 2027 would be $12 million, a full million below his current salary.  He’s likely not going to take that paycheck and will again opt to test free agency.  Keep your interest in this guy active. * Frankie Montas is now 34.  He will spend his age 35 season somewhere other than Citifield.  * A VERY interesting and hard to sell option for next season would be a reunion with former Met and former Brewer Freddy Peralta fresh off his September Pitcher of the Month award for the Rays. Peralta likely wouldn’t want to come back to the Mets any more than Mets fans would welcome him with open arms, but he is one of the better pitchers available for people with deep pockets.    * A lot of people kept waiting for southpaw David Peterson to blossom into a top flight pitcher.  Finally in his walk year he was the first kicked out of the 2026 Mets clubhouse.  He finished his season with a 4.79 ERA though most of the suffering was felt by Mets fans.  For the Cubs his ERA dropped to 3.70.  He’s available to a high bidder.  We hope David Stearns has blocked his agent’s number. * Lefty Jose Quintana has turned in consecutive season ERAs of 3.96 and 5.44 for the Cubs and Rockies respectively.  Turning 38 next year his best days are behind him and he shouldn’t be a real consideration either.  * Future Hall of Famer Max Scherzer is available to the highest bidder but already at age 42 he’s not going to get a megabucks annual rate nor will it be for more than a year or two.  His 2026 numbers were awful and it’s been that way for the past few years.  He’s likely a fifth starter at best at this point in his long career. No thanks. * Former Met and Yankee Luis Severino has a $22 million player option for his age 34 season.  Given his two consecutive years of an ERA well north of 4.00 you can bet he’s exercising that option rather than test free agency for less money. * Justin Verlander has announced probable retirement.  He’s had a great career but not a viable option for the Mets.  * Taijuan Walker is going to be 35 and fighting for a job somewhere other than in Queens.  
000
John From Albany @johnfromalbany.bsky.social · 21h
dlvr.it
MACK - Chain Position Analysis - First Base
  Okay... so much for catcher. We move on to a position we didn't have to worry about for years... first base. We have RED prospects, BLUE prospects, and ALMOST prospects. Here we go... RED Prospect -  AAA/Syracuse Billy Amick (23) - a big-time surprise. His combined 38-HR and 108-RBI is large. His 161-K in 450-AB is acceptable. And his 62-BB are just icing. It seems to me that the furthest he is away from Queens in the break, and yet, the break may be the start of the MLB season. BLUE Prospect -  MLB - Jared Young (31) - this is your first base caretaker until Amick is deemed ready. He had 308-AB for the Mets in 2026, hitting a respectable .266, with 9-HR. He struck out only 63 time, in 308 at-bats. And I don't remember him ever embarrassing himself like others that played first this past season. He probably has no future past an Amick promotion, unless he hits like hell, forcing Amick into a DH role he has one minor league option left). AAA Nick Lorusso (26) - Lorusso's claim to fame in 2026 was his 19-Hr for AA/Binghamton. Add to that the two he hit for AAA/Syracuse and his combined power stats were 22-HR, 65-RBI, .459-slug% and .777-OPS. The problem is there wasn't much else past these numbers.  Lorusso needs a full season in the Cuse'. Right now, he just consistently hits all pitcher, left or right, below .250. AA Corey Collins (24) - Collins is interesting. First, and most important, he is not a complete player yet. He's still finding his way. First... the good... 18 home runs (10 at the AA level) ... 61-RBI... AA-BA: .250... the bad? Tailed off in last 28 days (.184) ... questionable splits... against RHP: 14-HR but .234. LHP: only 4-HR but .253-BA.  He only had 136-AA in Binghamton, so there is a lot to said to start him back up there in the spring. Yeah, Amick should start in Syracuse, and the next guy needs to play more in Brooklyn, leaving Lorusso as the odd guy out.   A+ Randy Guzman - (21) - Guzman made a splash this past season at A/St. Lucie (208-AB, 66-K, 12-HR, 41-RBI, 28-BB, .274/.377/.514/.891, but took off after being promoted to A+ Brooklyn (28-AB, 7-K, 1-HR, 6-RBI, .393/.438/.536/.973. As expected, his HR/AB% went down at Coney. He missed a lot of games due to injury. The bottom line here is 28 at-bats does not warrant a promotion to AA/Binghamton. And Collins is in the way anyway. Bring him back next to that roller coaster. DSL - Jonnhan Sanchez - (19) - I'm not used to the Mets having decent bats at the DSL level... heck, I'm not used to decent pitching either. Sanchez is off to a great start: 152-AB, 3-HR, 38-RBI, 10-doubles, .309/.459/.447/.907. Splits: last 90: .255. home: .377, away: .253, August: .160. I definitely will work on a visa here and get him to Florida as soon as I can to get in the lab. ALMOST prospect - AAA Ryan Clifford - (23) - my, how the mighty has fallen. At last year around now, we were critical of the amount of strikeouts he had and his .237 batting average; however, we were comforted with his 23-HR, 93-RBI output. This year, still a shitey number of K's but his homers have fallen to 18, his ribbys are a miserable 56, and his BA was a resounding .180. Is he still an 'almost'? I really don't think so, but I have to respect that he has done better in the past.  Amick has obviously passed him as the #1 candidate for not only- the next first baseman, but also possibly the designated hitter. Probably others have passed him as the 2nd and 3rd candidate at first. Still, I would like to hope he can return as a DH candidate in the future. A+/Brooklyn - Cole Mathis - (23) - had 120 at-bats this past season at the A+ level: 3-HR, 24-RBI, .225-BA. Frankly, I'm not sure I have him as an almost prospect. The only place he has professionally hit decently so far is in the fall. I do like the name though, and I followed him for his for three years in the top party school in South Carolina. Must be that. FCL Reed Stallman - (23) - Stallman is just gettin' going and, based on the fact he turns 24 in March, he must turn on the jets. He only has 56 professional at-bats under his belt and all of them have been at the FCL level. still, he hit .318 for Mississippi State last season and those 56-AB produced a .250-BA. Obviously, start this off as St. Lucie's starting first baseman and let's see what we got here. Mack's spin - The addition of Amick changed everything.  First, Pete is gone. You have to get over that if you want to analyze the Mets future at this position. I get it. Having no Alonso is like a death in the family. Cremate the dude and move on.  My guess, by opening day 2028, there will be no more chatter on Alonso. Until then, Young is good enough to hold down the fort until Billy is ready.  Collins and Guzman are still developing. but offer possible future help here. It might not kill the Mets to hold onto Brett Baty until this position solidifies. Rating - B-  
000
John From Albany @johnfromalbany.bsky.social · 02/10/2026
dlvr.it
Mets Calendar Classics - Mets Post Season Games Played On This Date: October 2nd
  NY Post Back Page 10/3/2024 Year: 2024; NLWCS Game #2; Wednesday; Oct 2, NYM 3 @ MIL 5; boxscore; WP: Joe Ross; LP: Phil Maton; Save: Devin Williams; Time: 2:43; Day; Attendance: 40,350; Record: 1-1; L;  Lindor SS;  0 for 2; 1 RBI; 2 walks; Iglesias, J 2B-3B;  1 for 5; 1 run; 2 Ks; Vientos 3B;  1 for 4; 1 K; Acuña 2B;  0 for 0; Winker PH;  0 for 1; Nimmo LF;  1 for 3; 1 RBI; Alonso 1B;  1 for 4; 1 K; Martinez, J DH;  0 for 3; 1 walk; 1 K; Marte, S RF;  2 for 3; 1 run; 1 walk; Bader CF;  0 for 0; Taylor, T CF-RF;  1 for 4; 1 run; 1 K; Alvarez, F C;  1 for 4; 1 RBI; 1 K; Manaea; 5 innings; 2 runs; 2 ERs; 6 hits; 1 HR; 4 Ks; Garrett, R (H, 1); 1 inning; no runs; 1 hit; 1 K; Stanek (H, 1); 1 inning; no runs; Maton, P (L, 0-1)(BS, 1); 1 inning; 3 runs; 3 ERs; 4 hits; 2 HRs; 
000
John From Albany @johnfromalbany.bsky.social · 02/10/2026
dlvr.it
Around the Majors with Mets News and Links - 10/2/2026
Here are the top Stories from every Major League team courtesy from our friends at SportSpyder. Note - this page updates throughout the day - come back later today for the latest news.
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Mets YouTube Channel: Who is Sean Manaea's favorite Pokémon? - 10/1/26
Name Email * Message *
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Mets YouTube Channel: Carson Benge's longest home run of the season was CRUSHED 🤯 - 10/1/26
Team W L10 STRK Brewers 103 59 .636 - 8-2 W5 Cubs 89 73 .549 14.0 5-5 W1 Pirates 82 80 .506 21.0 7-3 W1 Cardinals 77 85 .475 26.0 2-8 L4 Reds 75 87 .463 28.0 4-6 L1 NL West Team W L L10 STRK Dodgers 100 62 .617 - 8-2 W3 Padres 91 71 .562 9.0 8-2 W2 D-backs 86 76 .531 14.0 6-4 L2 Giants 65 97 .401 35.0 2-8 L5 Rockies 58 104 .358 42.0 2-8 L1 American League AL East Team W L L10 STRK Rays 98 64 .605 - 5-5 L1 Yankees 93 68 .578 4.5 5-5 W1 Red Sox 87 75 .537 11.0 5-5 L1 Orioles 79 82 .491 18.5 6-4 L1 Blue Jays 79 83 .488 19.0 4-6 W1 Team W L10 STRK Guardians 85 77 .525 - 8-2 L1 White Sox 84 78 .519 1.0 7-3 W1 Twins 77 85 .475 8.0 6-4 W1 Tigers 76 86 .469 9.0 4-6 L1 Royals 69 93 .426 16.0 2-8 W1 AL West Team W L L10 STRK Astros 81 81 .500 - 5-5 W2 Rangers 80 82 .494 1.0 4-6 L1 Mariners 76 86 .469 5.0 6-4 W2 Athletics 64 98 .395 17.0 3-7 L2 Angels 62 100 .383 19.0 4-6 L2 Last Updated: 10/1/2026, 1:51:02 PM Live Baseball Scores: MLB, American, European and Asian baseball livescore. Fastest live - real time - scores, results and scores after innings. Name Email * Message *
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Mets YouTube Channel: Top 10 Home Runs | Carson Benge Rookie Season - 10/1/26
Name Email * Message *
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Mets YouTube Channel: A.J. Ewing knew he had a shot at getting drafted once he saw scouts in the stands 💪 - 10/1/26
Featured Posts Featured, Mets Prospects, New York Mets Binghamton Rumble Ponies, Featured, Media Guide Featured, Media Guide, Syracuse Mets More Featured Posts. Syracuse Mets and Binghamton Rumble Ponies Photos Mets Videos Binghamton Rumble Ponies, Mets Videos Max Goodman - Speaking of the Mets: Will Mets go after Tarik Skubal? Reacting LIVE to David Stearns’ end-of-season presser - 9/28/26 Max Goodman, Mets Videos, Speaking of the Mets SNY on YouTube: "Francisco Lindor goes to a place no shortstop has ever been, 200 stolen bases & now 300 home runs!" - 9/28/26 Mets Videos, New York Mets More Mets Videos. Mets360 More Mets360. Mack's Mets More Mack's Mets. The Mediagoon More Mediagoon. MLB Leaders 43 42 42 41 35 45 45 41 41 37 113 106 101 97 96 116 112 107 106 102 180 179 175 170 168 191 185 181 175 174 248 239 239 211 205 205 252 231 221 200 200 200 18 16 15 14 14 18 16 16 15 14 14 14 14 14 Standings MLB Standings National League NL East Team W L10 STRK Braves 94 68 .580 - 5-5 L1 Phillies 88 74 .543 6.0 4-6 W1 Marlins 80 82 .494 14.0 5-5 W1 Nationals 77 85 .475 17.0 6-4 W1 Mets 74 88 .457 20.0 5-5 L1 NL Central Team W L10 STRK Brewers 103 59 .636 - 8-2 W5 Cubs 89 73 .549 14.0 5-5 W1 Pirates 82 80 .506 21.0 7-3 W1 Cardinals 77 85 .475 26.0 2-8 L4 Reds 75 87 .463 28.0 4-6 L1 NL West Team W L PCT L10 STRK Dodgers 100 62 .617 - 8-2 W3 Padres 91 71 .562 9.0 8-2 W2 D-backs 86 76 .531 14.0 6-4 L2 Giants 65 97 .401 35.0 2-8 L5 Rockies 58 104 .358 42.0 2-8 L1 American League AL East Team W L10 STRK Rays 98 64 .605 - 5-5 L1 Yankees 93 68 .578 4.5 5-5 W1 Red Sox 87 75 .537 11.0 5-5 L1 Orioles 79 82 .491 18.5 6-4 L1 Blue Jays 79 83 .488 19.0 4-6 W1 AL Central Team W L10 STRK Guardians 85 77 .525 - 8-2 L1 White Sox 84 78 .519 1.0 7-3 W1 Twins 77 85 .475 8.0 6-4 W1 Tigers 76 86 .469 9.0 4-6 L1 Royals 69 93 .426 16.0 2-8 W1 AL West Team W L PCT L10 STRK Astros 81 81 .500 - 5-5 W2 Rangers 80 82 .494 1.0 4-6 L1 Mariners 76 86 .469 5.0 6-4 W2 Athletics 64 98 .395 17.0 3-7 L2 Angels 62 100 .383 19.0 4-6 L2 Last Updated: 10/1/2026, 11:18:59 AM Live broadcasts via TuneIn Live Baseball Scores: MLB, American, European and Asian baseball livescore. Fastest live - real time - scores, results and scores after innings. Name Email * Message *
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Lunch Time Links - Top MLB Headlines Now - 10/1/2026
Here are some of the News and Headlines around Major League Baseball courtesy from our friends at SportSpyder.
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
The 2026 Mets were painted into a corner with three veteran starters
It’s a barrier they won’t face in 2027 Click Link Below to Read Article. http://dlvr.it/TVkW1Y
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
MACK – Let’s Revisit - C - Julio Zayas
 
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Peyton Prescott 10/1/26 Player Profile
Photo from Brooklyn Cyclones Via X Another player heading to the Arizona Fall league that that missed considerable time in 2026 is RHP Peyton Prescott.  Peyton was selected by the Mets in the 5th round in the 2025 MLB Draft after having Tommy John surgery that previous Spring. As a Florida State University Sophomore in 2025, Peyton touched triple digits. He saw his first and only action in 2026 on September 4, 2026 for St. Lucie - 1 inning, no runs, no hits, 1 walk, 2 Ks.   MLB.com listed Peyton as the Mets Sleeper Prospect in the AFL saying: "Prescott finally made his organizational debut with one inning for Single-A St. Lucie, sitting between 94.5 and 96.5 mph with that four-seamer while sprinkling in cutters, sliders, changeups and curveballs over the 18-pitch outing. The slider and changeup were both whiff-heavy options as an amateur, but the biggest thing for Prescott will be just establishing a broader foundation of innings heading into his second full season." Baseball America: "Prescott has an athletic operation but fringe control and more of a relief profile. Starting is not completely off the table, though, because he pitches in the mid 90s with a full array of solid secondaries, including an average mid-80s splitter, an average mid-80s slider and a low-80s downer curveball." Keith Law The Athletic: "Florida State right-hander Peyton Prescott (5) is up to 100 with a 55 changeup but gets crushed by right-handed batters, as his slider is fringy and he leaves it up too often. He has an incredibly short arm action with a ton of effort, so he’ll stay in relief, where he pitched for the Seminoles this spring and posted a 5.15 ERA with a 27 percent strikeout rate." In addition to Keith Law, ESPN, and MLB.com also saw him as a high-leverage relief arm.   Peyton will be fun to watch and track his performance this Fall.   Loading player profile… #pp-widget { max-width: 820px; margin: 0 auto; font-family: 'Barlow Condensed', -apple-system, 'Segoe UI', Arial, sans-serif; color: #1a1a1a; } #pp-widget * { box-sizing: border-box; } #pp-widget .pp-loading { text-align: center; padding: 30px; color: #6c757d; font-size: 18px; } #pp-widget .pp-card { background: #fff; border-radius: 12px; box-shadow: 0 2px 8px rgba(0,0,0,0.12); overflow: hidden; margin-bottom: 20px; } /* header */ #pp-widget .pp-header { background: linear-gradient(135deg, #002D72 0%, #FF5910 100%); color: #fff; padding: 22px; } #pp-widget .pp-head-row { display: flex; align-items: center; gap: 18px; margin-bottom: 14px; flex-wrap: wrap; } #pp-widget .pp-headshot { width: 92px; height: 92px; border-radius: 50%; border: 3px solid #fff; background: #fff; object-fit: cover; flex-shrink: 0; } #pp-widget .pp-number { font-size: 44px; font-weight: 700; opacity: 0.9; } #pp-widget .pp-name h1 { font-size: 34px; margin: 0 0 2px 0; line-height: 1.1; color: #fff; } #pp-widget .pp-pos { font-size: 18px; opacity: 0.92; } #pp-widget .pp-bio { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 10px; font-size: 15px; } #pp-widget .pp-bio-item { background: rgba(255,255,255,0.14); padding: 7px 11px; border-radius: 6px; } #pp-widget .pp-bio-label { opacity: 0.82; font-size: 12px; text-transform: uppercase; letter-spacing: 0.5px; margin-bottom: 1px; } /* jump nav */ #pp-widget .pp-nav { display: flex; gap: 8px; flex-wrap: wrap; padding: 10px 22px; background: #f8f9fa; border-bottom: 1px solid #e9ecef; } #pp-widget .pp-nav a { color: #002D72; font-weight: 600; text-decoration: none; font-size: 15px; padding: 4px 10px; border-radius: 14px; border: 1px solid #d7dbe0; background: #fff; } #pp-widget .pp-nav a:hover { background: #002D72; color: #fff; } /* sections */ #pp-widget .pp-section { padding: 20px 22px; } #pp-widget .pp-title { font-size: 22px; font-weight: 700; color: #002D72; margin: 0 0 12px 0; padding-bottom: 6px; border-bottom: 2px solid #FF5910; } #pp-widget .pp-sub { font-size: 17px; font-weight: 700; color: #002D72; margin: 16px 0 6px 0; } #pp-widget .pp-note { font-size: 13px; color: #6c757d; margin: 6px 0 0 0; } #pp-widget .pp-empty { font-size: 15px; color: #6c757d; padding: 8px 0; } /* quick stat boxes */ #pp-widget .pp-quick { display: grid; grid-template-columns: repeat(auto-fit, minmax(88px, 1fr)); gap: 12px; margin-bottom: 8px; } #pp-widget .pp-qbox { text-align: center; padding: 12px 6px; background: #f8f9fa; border: 1px solid #e9ecef; border-radius: 8px; } #pp-widget .pp-qval { font-size: 26px; font-weight: 700; color: #002D72; } #pp-widget .pp-qlbl { font-size: 12px; color: #6c757d; text-transform: uppercase; letter-spacing: 0.5px; } /* tables */ #pp-widget .pp-twrap { overflow-x: auto; -webkit-overflow-scrolling: touch; } #pp-widget table.pp-table { width: 100%; border-collapse: collapse; margin-bottom: 6px; } #pp-widget table.pp-table th { background: #002D72; color: #fff; padding: 9px 6px; text-align: center; font-size: 12px; font-weight: 600; text-transform: uppercase; white-space: nowrap; } #pp-widget table.pp-table td { padding: 8px 6px; text-align: center; border-bottom: 1px solid #e9ecef; font-size: 14px; white-space: nowrap; } #pp-widget table.pp-table tr:hover td { background: #f8f9fa; } #pp-widget td.pp-left, #pp-widget th.pp-left { text-align: left; } #pp-widget .pp-yr { font-weight: 600; color: #002D72; } #pp-widget .pp-lvl { display: inline-block; background: #002D72; color: #fff; border-radius: 10px; font-size: 11px; font-weight: 700; padding: 1px 8px; margin-left: 6px; vertical-align: 1px; } #pp-widget tr.pp-total td { font-weight: 700; background: #fff4ee; border-top: 2px solid #FF5910; } #pp-widget tr.pp-career td { font-weight: 700; background: #eaf0fa; border-top: 2px solid #002D72; } /* v2.4: repeated header rows inside long tables */ #pp-widget table.pp-table tr.pp-rehead th { border-top: 2px solid #FF5910; } #pp-widget td.pp-lnk a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget td.pp-lnk a:hover { text-decoration: underline; } /* splits + fielding + game log season chips */ #pp-widget .pp-chips { display: flex; gap: 6px; flex-wrap: wrap; margin-bottom: 10px; } #pp-widget .pp-chip { border: 1px solid #002D72; color: #002D72; background: #fff; border-radius: 14px; padding: 3px 12px; font-size: 14px; font-weight: 600; cursor: pointer; font-family: inherit; } #pp-widget .pp-chip.pp-on { background: #002D72; color: #fff; } /* videos */ #pp-widget .pp-vids { display: grid; grid-template-columns: repeat(auto-fill, minmax(230px, 1fr)); gap: 14px; } #pp-widget .pp-vcard { border: 1px solid #e9ecef; border-radius: 8px; overflow: hidden; background: #fff; } #pp-widget .pp-vcard-x { grid-column: 1 / -1; max-width: 560px; } #pp-widget .pp-vcard-x blockquote { margin: 0 auto; } #pp-widget .pp-vthumb { position: relative; cursor: pointer; background: #000; } #pp-widget .pp-vthumb img { width: 100%; display: block; aspect-ratio: 16/9; object-fit: cover; } #pp-widget .pp-vplay { position: absolute; top: 50%; left: 50%; transform: translate(-50%,-50%); width: 44px; height: 44px; border-radius: 50%; background: rgba(0,45,114,0.85); color: #fff; display: flex; align-items: center; justify-content: center; font-size: 18px; pointer-events: none; } #pp-widget .pp-vdur { position: absolute; right: 6px; bottom: 6px; background: rgba(0,0,0,0.75); color: #fff; font-size: 11px; padding: 1px 6px; border-radius: 3px; } #pp-widget .pp-vbody { padding: 8px 10px 10px 10px; } #pp-widget .pp-vtitle { font-size: 14px; font-weight: 600; line-height: 1.25; color: #1a1a1a; margin-bottom: 4px; } #pp-widget .pp-vmeta { font-size: 12px; color: #6c757d; display: flex; justify-content: space-between; } #pp-widget .pp-vmeta a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget .pp-vcard video { width: 100%; display: block; aspect-ratio: 16/9; background: #000; } #pp-widget .pp-vlink { display: block; background: #002D72; color: #fff; text-align: center; padding: 34px 10px; font-weight: 700; text-decoration: none; } /* footer */ #pp-widget .pp-footer { padding: 12px 22px; background: #f8f9fa; text-align: center; font-size: 12px; color: #6c757d; } #pp-widget .pp-footer a { color: #002D72; font-weight: 600; text-decoration: none; } @media (max-width: 600px) { #pp-widget .pp-header { padding: 15px; } #pp-widget .pp-name h1 { font-size: 26px; } #pp-widget .pp-number { font-size: 34px; } #pp-widget .pp-section { padding: 15px 12px; } #pp-widget table.pp-table th, #pp-widget table.pp-table td { padding: 6px 4px; font-size: 12px; } } (function () { // ================= CONFIG - EDIT THIS ================= var PLAYER_ID = 807290; // { code: totals }. // Tries the Stats API careerStatSplits call first; if nothing comes // back, sums every season's statSplits for that level instead. function loadCareerSplits(group, sportId, seasons, accF) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=careerStatSplits&group=' + group + '&sportId=' + sportId + '&sitCodes=' + SIT_CODE_STR) .then(function (d) { return splitsOf(d); }) .catch(function () { return []; }) .then(function (sp) { var direct = sumByCode(sp, accF, true); if (Object.keys(direct).length) return direct; return Promise.all(seasons.map(function (yr) { return loadSplits(group, yr, [sportId]); })) .then(function (arrs) { var out = {}; arrs.forEach(function (list) { var yrTot = sumByCode(list, accF, false); Object.keys(yrTot).forEach(function (c) { out[c] = addTot(out[c] || {}, yrTot[c]); }); }); return out; }); }); } var MONTH_NAMES = ['','January','February','March','April','May','June','July','August','September','October','November','December']; function loadMonthly(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=byMonth&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return (n(a.month) - n(b.month)) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: GAME LOG (v2.4) ---------------- function loadGameLog(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=gameLog&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return String(b.date || '').localeCompare(String(a.date || '')) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: PITCH ARSENAL / VELO (v2.4) ---------------- // Only levels with pitch tracking: MLB (1), AAA (11), Low-A (14). var PITCH_SPORT_IDS = [1, 11, 14]; function loadPitchData(season) { return Promise.all(PITCH_SPORT_IDS.map(function (sid) { var ars = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchArsenal&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); var log = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchLog&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); return Promise.all([ars, log]).then(function (r) { return { sportId: sid, arsenal: r[0], log: r[1] }; }); })); } // ---------------- FETCH: TRANSACTIONS ---------------- function loadTransactions() { var end = new Date().toISOString().slice(0,10); return jget(API + '/transactions?playerId=' + PLAYER_ID + '&startDate=2010-01-01&endDate=' + end) .then(function (d) { var tx = (d.transactions || []).slice(); tx.sort(function (a, b) { return String(b.date).localeCompare(String(a.date)); }); return tx.slice(0, TX_MAX); }) .catch(function () { return []; }); } // ---------------- FETCH: FILM ROOM VIDEOS ---------------- var GQL = 'query Search($query: String!, $page: Int, $limit: Int, $feedPreference: FeedPreference, ' + '$languagePreference: LanguagePreference, $contentPreference: ContentPreference, $queryType: QueryType = STRUCTURED) {\n' + ' search(query: $query, limit: $limit, page: $page, feedPreference: $feedPreference, ' + 'languagePreference: $languagePreference, contentPreference: $contentPreference, queryType: $queryType) {\n' + ' plays {\n mediaPlayback {\n slug\n title\n blurb\n date\n' + ' feeds {\n type\n duration\n' + ' image { cuts { width src } }\n' + ' playbacks { name url }\n }\n }\n }\n }\n}'; function gqlVars(queryStr, limit) { return { queryType: null, query: queryStr, limit: limit || VIDEO_LIMIT, page: 0, languagePreference: 'EN', contentPreference: 'CMS_FIRST' }; } function videoSearchUrl(queryStr, limit) { return 'https://fastball-gateway.mlb.com/graphql' + '?query=' + encodeURIComponent(GQL) + '&operationName=Search' + '&variables=' + encodeURIComponent(JSON.stringify(gqlVars(queryStr, limit))); } function proxyPlayerUrl(person) { var teamId = (person && person.currentTeam && person.currentTeam.id) || ''; var last = (person && (person.lastName || (person.fullName || '').split(' ').pop())) || ''; return PROXY_URL + '?player=' + PLAYER_ID + '&team=' + teamId + '&name=' + encodeURIComponent(last) + '&limit=' + VIDEO_LIMIT; } var ppJsonpCount = 0; function jsonpCall(baseUrl) { return new Promise(function (resolve, reject) { var cb = 'ppVidCb' + (++ppJsonpCount); var s = document.createElement('script'); var timer = setTimeout(function () { cleanup(); reject(new Error('proxy timeout')); }, 30000); function cleanup() { clearTimeout(timer); try { delete window[cb]; } catch (e) { window[cb] = undefined; } if (s.parentNode) s.parentNode.removeChild(s); } window[cb] = function (data) { cleanup(); resolve(data); }; s.onerror = function () { cleanup(); reject(new Error('proxy load error')); }; s.src = baseUrl + '&callback=' + cb; document.head.appendChild(s); }); } function proxyJson(baseUrl) { return fetch(baseUrl).then(function (r) { if (!r.ok) throw new Error('proxy HTTP ' + r.status); return r.json(); }); } function gqlPost(queryStr, limit) { return fetch('https://fastball-gateway.mlb.com/graphql', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ query: GQL, operationName: 'Search', variables: gqlVars(queryStr, limit) }) }).then(function (r) { if (!r.ok) throw new Error('HTTP ' + r.status + ' (POST)'); return r.json(); }); } function gqlFetch(queryStr, limit) { return jget(videoSearchUrl(queryStr, limit)) .catch(function () { return gqlPost(queryStr, limit); }); } function fmtDur(sec) { if (sec == null || sec === '') return ''; if (typeof sec === 'string' && sec.indexOf(':') > -1) return sec.replace(/^00:0?/, ''); var x = parseInt(sec, 10); if (isNaN(x)) return ''; return Math.floor(x / 60) + ':' + ('0' + (x % 60)).slice(-2); } function pickPlayback(feeds) { if (!feeds || !feeds.length) return { mp4: null, thumb: '', dur: '' }; var ranked = feeds.slice().sort(function (a, b) { return ((a.type === 'CMS') ? 0 : 1) - ((b.type === 'CMS') ? 0 : 1); }); var mp4 = null, thumb = '', dur = ''; for (var i = 0; i < ranked.length; i++) { var f = ranked[i]; if (!dur && f.duration) dur = fmtDur(f.duration); if (!thumb && f.image && f.image.cuts && f.image.cuts.length) { var cuts = f.image.cuts.slice().sort(function (a, b) { return (b.width||0) - (a.width||0); }); var mid = cuts.filter(function (c) { return c.width && c.width 1) { html += ' ' + esc(yr) + ' ' + esc(opts.totalLabel) + ' ' + cellsHTML(totF(yrTot)) + ' '; } // v2.4: repeat the column header row every HEADER_REPEAT seasons if (n(HEADER_REPEAT) > 0 && (si + 1) % n(HEADER_REPEAT) === 0 && si < seasons.length - 1) { html += headRowHTML('Year / Team', cols, 'pp-rehead'); } }); if (seasons.length) { html += ' ' + esc(opts.careerLabel) + ' ' + cellsHTML(totF(career)) + ' '; } return html ? tableHTML(opts.id, 'Year / Team', cols, html) : ''; } // ---------------- MAIN ---------------- loadPerson().then(function (person) { if (!person) { root.innerHTML = 'Player not found for ID ' + PLAYER_ID + '.'; return; } return Promise.all([ loadYearByYear('hitting'), loadYearByYear('pitching'), loadYearByYear('fielding'), loadTransactions(), loadVideos(person), loadJersey(person) ]) .then(function (res) { render(person, res[5], res[0], res[1], res[2], res[3], res[4]); }); }) .catch(function (e) { root.innerHTML = 'Could not load profile (' + esc(e.message) + '). Please refresh.'; }); function render(person, jersey, hitRows, pitRows, fldRows, txs, vids) { var isPitcher = person.primaryPosition && person.primaryPosition.code === '1'; var hasHit = hitRows.some(function (r) { return n(r.stat.atBats) || n(r.stat.plateAppearances); }); var hasPit = pitRows.some(function (r) { return ipToOuts(r.stat.inningsPitched) || n(r.stat.gamesPlayed); }); var usePit = isPitcher && hasPit; var showPitches = usePit && SHOW_PITCHES; var showGameLog = n(RECENT_GAMES) > 0 && (hasPit || hasHit); var headshot = 'https://img.mlbstatic.com/mlb-photos/image/upload/d_people:generic:headshot:67:current.png' + '/w_180,q_auto:best/v1/people/' + PLAYER_ID + '/headshot/milb/current'; var birth = [person.birthCity, person.birthStateProvince, person.birthCountry].filter(Boolean).join(', '); var teamName = (person.currentTeam && person.currentTeam.name) || 'New York Mets Organization'; var h = ''; // ---- header ---- h += '' + '' + (jersey ? '#' + esc(jersey) + '' : '') + ' ' + esc(person.fullName) + ' ' + '' + esc((person.primaryPosition && person.primaryPosition.name) || '') + ' • ' + esc(teamName) + '' + '' + 'Full Name' + esc(person.fullFMLName || person.fullName) + '' + 'Bats/Throws' + esc(((person.batSide||{}).code||'') + '/' + ((person.pitchHand||{}).code||'')) + '' + 'Height/Weight' + esc((person.height||'') + ' / ' + (person.weight ? person.weight + ' lbs' : '')) + '' + 'Born' + esc(fmtDate(person.birthDate) + (person.currentAge ? ' (Age ' + person.currentAge + ')' : '')) + '' + (birth ? 'Birthplace' + esc(birth) + '' : '') + (HOW_ACQUIRED ? 'How Acquired' + esc(HOW_ACQUIRED) + '' : '') + EXTRA_BOXES.map(function (b) { if (!b || !b.value) return ''; return '' + esc(b.label || '') + '' + esc(b.value) + ''; }).join('') + ''; // ---- jump nav ---- h += 'Stats' + (showPitches ? 'Pitches' : '') + 'Splits' + 'Fielding' + (showGameLog ? 'Game Log' : '') + 'VideosTransactions'; // ---- stats ---- h += ' Statistics '; var groups = []; if (isPitcher) { if (hasPit) groups.push('P'); if (hasHit) groups.push('H'); } else { if (hasHit) groups.push('H'); if (hasPit) groups.push('P'); } if (!groups.length) h += 'No stats available yet.'; groups.forEach(function (g) { var rows = (g === 'H') ? hitRows : pitRows; var isP = (g === 'P'); var gLbl = isP ? 'Pitching' : 'Hitting'; var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); var winter = rows.filter(function (r) { return r.sportId === 17; }); var mlbT = buildStatsTable(mlb, isP, { id: 'pp-mlb-' + g, totalLabel: 'MLB Total', careerLabel: 'MLB Career' }); var milbT = buildStatsTable(milb, isP, { id: 'pp-milb-' + g, totalLabel: 'MiLB Total', careerLabel: 'MiLB Career', rates: !isP }); var winterT = buildStatsTable(winter, isP, { id: 'pp-winter-' + g, totalLabel: 'Total', careerLabel: 'Winter/AFL Career' }); if (mlbT) h += 'MLB ' + gLbl + '' + mlbT; if (milbT) h += 'Minor League ' + gLbl + '' + milbT; if (winterT) h += 'Winter Ball / AFL ' + gLbl + '' + winterT; }); h += ''; // ---- pitch arsenal (v2.4, pitchers only) ---- if (showPitches) { h += ' Pitch Arsenal ' + 'Loading pitch data…'; } // ---- splits ---- h += ' Splits ' + 'Loading splits…'; // ---- fielding (v2.3) ---- h += ' Fielding ' + 'Loading fielding…'; // ---- game log (v2.4) ---- if (showGameLog) { h += ' Game Log ' + 'Loading game log…'; } // ---- videos ---- h += ' Video Highlights '; var autoVids = vids.list || []; var hasAny = MANUAL_VIDEOS.length || autoVids.length; var hasXPost = false; if (hasAny) { h += ''; MANUAL_VIDEOS.forEach(function (v) { var yt = ytEmbedUrl(v.url); var xp = xPostUrl(v.url); if (xp) { hasXPost = true; h += '' + '' + '' + esc(v.title || 'View post on X') + '' + '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + 'View on X'; return; } h += ''; if (yt) { h += ''; } else if (/\.mp4(\?|$)/i.test(v.url || '')) { h += ''; } else if (isMlbVideoUrl(v.url)) { var mlbEmb = mlbEmbedUrl(v.url); if (mlbEmb) { h += ''; } else { h += '► Watch on MLB.com'; } } else { h += '► Watch Video'; } h += '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + (isMlbVideoUrl(v.url) ? 'View on MLB.com' : '') + ''; }); autoVids.forEach(function (v, i) { h += '' + '' + (v.thumb ? '' : '') + '►' + (v.dur ? '' + esc(v.dur) + '' : '') + '' + esc(v.title) + '' + '' + esc(fmtDate(v.date)) + '' + 'Watch on MiLB.com' + ''; }); h += ''; if (autoVids.length) { h += 'Auto-updated from MLB Film Room. Full library: ' + 'milb.com/video/topic/playerid-' + PLAYER_ID + ''; } } if (!autoVids.length && !MANUAL_VIDEOS.length) { h += '' + (vids.error ? 'The automatic video feed could not load (' + esc(vids.error) + '). ' + 'If this keeps happening, set PROXY_URL in the config to your Apps Script passthrough. ' : 'No clips found in the Film Room index for this player yet. ') + 'Full library: MiLB.com.'; } else if (!autoVids.length && vids.error) { h += 'The automatic video feed could not load (' + esc(vids.error) + ').'; } h += ''; // ---- transactions ---- h += ' Transactions '; if (txs.length) { var trows = ''; txs.forEach(function (t) { trows += ' ' + esc(fmtDate(t.date)) + ' ' + ' ' + esc(t.typeDesc || '') + ' ' + ' ' + esc(t.description || '') + ' '; }); h += ' Date Type Transaction ' + trows + ' '; } else { h += 'No transactions on record.'; } h += ''; // ---- footer ---- h += 'Stats & transactions from the MLB Stats API • Videos from MLB Film Room • ' + 'MiLB.com Player Page • ' + 'MLB.com Player Page' + ''; root.innerHTML = h; if (hasXPost) loadXWidgets(); // ---- header stat boxes (v2.4: separate MLB / MiLB rows) ---- buildQuickStats(usePit ? pitRows : hitRows, usePit); // ---- video inline playback ---- root.querySelectorAll('.pp-vthumb').forEach(function (el) { el.addEventListener('click', function () { var mp4 = el.getAttribute('data-mp4'); if (!mp4) { var link = el.getAttribute('data-link'); if (link) window.open(link, '_blank'); return; } var v = document.createElement('video'); v.controls = true; v.autoplay = true; v.src = mp4; v.setAttribute('playsinline',''); el.parentNode.replaceChild(v, el); }); }); var group = usePit ? 'pitching' : 'hitting'; var groupRows = usePit ? pitRows : hitRows; if (showPitches) initPitches(pitRows); initSplits(group, groupRows, usePit); initFielding(fldRows); if (showGameLog) initGameLog(group, groupRows, usePit); } // ---------------- HEADER STAT BOXES (v2.4) ---------------- // One row of boxes per HEADER_STATS entry ('MLB' / 'MiLB') for the // player's most recent season. A row is skipped if the player has // no stats at that level in that season. function buildQuickStats(rows, isPitching) { var box = document.getElementById('pp-quick'); if (!box || !rows.length || !HEADER_STATS || !HEADER_STATS.length) return; var reg = rows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) return; var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); var yr = reg.filter(function (r) { return r.season === latest; }); var accF = isPitching ? pitAccumulate : hitAccumulate; var html = ''; HEADER_STATS.forEach(function (lvlKey) { var isMlb = /^mlb$/i.test(String(lvlKey)); var list = yr.filter(function (r) { return isMlb ? r.sportId === 1 : isMilbSport(r.sportId); }); if (!list.length) return; var tot = {}; list.forEach(function (r) { accF(tot, r.stat); }); var items; if (isPitching) { items = [ [n(tot.wins) + '-' + n(tot.losses), 'W-L'], [era(n(tot.earnedRuns), n(tot.outs)), 'ERA'], [outsToIp(n(tot.outs)), 'IP'], [n(tot.strikeOuts), 'SO'], [whip(n(tot.baseOnBalls), n(tot.hits), n(tot.outs)), 'WHIP'] ]; } else { var c = hitTotalCells(tot, false); // [G,AB,R,H,2B,3B,HR,RBI,SB,BB,SO,AVG,OBP,SLG,OPS] items = [ [c[11], 'AVG'], [c[6], 'HR'], [c[7], 'RBI'], [c[8], 'SB'], [c[14], 'OPS'] ]; } html += '' + (isMlb ? 'MLB ' : 'MiLB ') + esc(latest) + ' Stats' + items.map(function (it) { return '' + esc(it[0]) + '' + esc(it[1]) + ''; }).join('') + ''; }); box.innerHTML = html; } // ---------------- PITCH ARSENAL UI (v2.4) ---------------- var PITCH_COLS = ['Usage','Avg MPH','Top MPH','Pitches']; function initPitches(pitRows) { var body = document.getElementById('pp-pitch-body'); var title = document.getElementById('pp-pitch-title'); if (!body) return; var reg = pitRows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) { body.innerHTML = 'No pitch data available.'; return; } var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); if (title) title.innerHTML = 'Pitch Arsenal — ' + esc(latest); loadPitchData(latest).then(function (res) { var out = ''; res.forEach(function (r) { var map = {}; function slot(code, desc) { return map[code] = map[code] || { code: code, desc: desc || code, usage: null, avg: null, max: null, count: 0, sum: 0, cnt: 0 }; } (r.arsenal || []).forEach(function (s) { var st = s.stat || {}; var t = st.type || {}; var code = t.code || t.description; if (!code) return; var m = slot(code, t.description); var p = Number(st.percentage); if (!isNaN(p) && st.percentage != null) m.usage = p m.max) m.max = v; m.sum += v; m.cnt++; }); var list = Object.keys(map).map(function (k) { return map[k]; }); if (!list.length) return; list.forEach(function (m) { if (m.avg == null && m.cnt) m.avg = m.sum / m.cnt; if (!m.count && m.cnt) m.count = m.cnt; }); var totalCnt = list.reduce(function (a, m) { return a + n(m.count); }, 0); list.forEach(function (m) { if (m.usage == null && totalCnt) m.usage = 100 * n(m.count) / totalCnt; }); list.sort(function (a, b) { return (n(b.usage)) - (n(a.usage)); }); var rowsHtml = list.map(function (m) { return ' ' + esc(m.desc) + ' ' + cellsHTML([ m.usage != null ? m.usage.toFixed(1) + '%' : '--', m.avg != null ? m.avg.toFixed(1) : '--', m.max != null ? m.max.toFixed(1) : '--', m.count || '--' ]) + ' '; }).join(''); out += '' + esc(levelLabel(r.sportId, '')) + '' + ' ' + theadHTML('Pitch', PITCH_COLS) + '' + rowsHtml + ' '; }); body.innerHTML = out ? out + '' + esc(latest) + ' pitch tracking by level (MLB, AAA and Low-A only). Usage and average velocity from the MLB Stats API pitch arsenal; top velocity is the hardest tracked pitch of that type in the pitch log.' : 'No pitch-tracking data returned for ' + esc(latest) + ' (available for MLB, AAA and Low-A only).'; }).catch(function (e) { body.innerHTML = 'Pitch data could not load (' + esc(e && e.message) + ').'; }); } // ---------------- SPLITS UI (v2.4: career + season chips) ---------------- // v2.4.1: pitching splits use PIT_SPLIT_COLS / pitSplitTotalCells. function initSplits(group, rows, isPitching) { var chips = document.getElementById('pp-split-chips'); var body = document.getElementById('pp-split-body'); if (!chips || !body) return; var seasonsMap = {}, sidsAll = {}; rows.forEach(function (r) { if (r.sportId === 17) return; // winter splits not indexed the same way (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; sidsAll[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { body.innerHTML = 'No splits available.'; return; } chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var defs = isPitching ? SIT_CODES_PIT : SIT_CODES; var sCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS; var accF = isPitching ? pitAccumulate : hitAccumulate; var totF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, false); }; var careerCache = null; // ---- career view: MLB table + Minor Leagues table ---- function showCareer() { body.innerHTML = 'Loading career splits…'; if (!careerCache) { var sids = Object.keys(sidsAll).map(Number); careerCache = Promise.all(sids.map(function (sid) { var yrs = seasons.filter(function (s) { return seasonsMap[s][sid]; }); return loadCareerSplits(group, sid, yrs, accF).then(function (byCode) { return { sportId: sid, byCode: byCode }; }); })); } careerCache.then(function (res) { function tableFor(filterFn) { var html = ''; defs.forEach(function (def) { var tot = {}, any = false; res.filter(filterFn).forEach(function (r) { if (r.byCode[def.code]) { addTot(tot, r.byCode[def.code]); any = true; } }); if (any) html += ' ' + esc(def.label) + ' ' + cellsHTML(totF(tot)) + ' '; }); return html ? ' ' + theadHTML('Split', sCols) + '' + html + ' ' : ''; } var mlbT = tableFor(function (r) { return r.sportId === 1; }); var milbT = tableFor(function (r) { return isMilbSport(r.sportId); }); var out = ''; if (mlbT) out += 'MLB — Career Splits' + mlbT; if (milbT) out += 'Minor Leagues — Career Splits' + milbT; body.innerHTML = out ? out + 'Career splits (regular season). Minor league line combines every MiLB level. Rate stats are recomputed from the summed raw counts. Pick a season above for the year-by-year, per-level breakdown.' : 'No career split data available.'; }).catch(function (e) { body.innerHTML = 'Career splits could not load (' + esc(e && e.message) + ').'; }); } // ---- season view: per-level splits + By Month (unchanged from v2.3.1) ---- function showSeason(season) { body.innerHTML = 'Loading ' + esc(season) + ' splits…'; var sportIds = Object.keys(seasonsMap[season]).map(Number); Promise.all([ loadSplits(group, season, sportIds), loadMonthly(group, season, sportIds) ]) .then(function (res) { var splits = res[0], months = res[1]; if (!splits.length && !months.length) { body.innerHTML = 'No split data for ' + esc(season) + '.'; return; } var out = ''; var shtml = ''; defs.forEach(function (def) { var byLevel = {}; splits.filter(function (s) { return s.split && s.split.code === def.code; }) .forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = lvl || ('sid' + s._sportId); var g = byLevel[key] = byLevel[key] || { lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); Object.keys(byLevel).map(function (k) { return byLevel[k]; }) .sort(function (a, b) { return b.sportId - a.sportId; }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); shtml += ' ' + esc(def.label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(totF(tot)) + ' '; }); }); if (shtml) { out += ' ' + theadHTML('Split', sCols) + '' + shtml + ' '; } if (months.length) { var mCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS_RATES; var mTotF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, true); }; var byMonth = {}; months.forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = n(s.month) + '|' + (lvl || 'sid' + s._sportId); var g = byMonth[key] = byMonth[key] || { month: n(s.month), lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); var mhtml = ''; Object.keys(byMonth).map(function (k) { return byMonth[k]; }) .sort(function (a, b) { return (a.month - b.month) || (b.sportId - a.sportId); }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); var label = MONTH_NAMES[g.month] || ('Month ' + g.month); mhtml += ' ' + esc(label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(mTotF(tot)) + ' '; }); out += 'By Month' + ' ' + theadHTML('Month', mCols) + '' + mhtml + ' '; } body.innerHTML = out ? out + 'Splits and monthly totals shown per level for the selected season (regular season). Splits combine all teams at the same level into one line.' : 'No split data for ' + esc(season) + '.'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); var s = b.getAttribute('data-season'); if (s === 'ALL') showCareer(); else showSeason(s); }); showCareer(); } // ---------------- FIELDING UI (v2.3) ---------------- function initFielding(rows) { var chips = document.getElementById('pp-fld-chips'); var body = document.getElementById('pp-fld-body'); if (!chips || !body) return; rows = rows.filter(function (r) { return r.sportId !== 17 && r.position && (n(r.stat.gamesPlayed) || n(r.stat.chances) || ipToOuts(r.stat.innings)); }); if (!rows.length) { chips.innerHTML = ''; body.innerHTML = 'No fielding data available yet.'; return; } var seasonsMap = {}; rows.forEach(function (r) { seasonsMap[r.season] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); function buildRows(list, withLevel) { var groups = {}; list.forEach(function (r) { var key = r.position + (withLevel ? '|' + r.level : ''); if (!groups[key]) groups[key] = { pos: r.position, lvl: withLevel ? r.level : '', sportId: r.sportId, tot: {} }; fldAccumulate(groups[key].tot, r.stat); }); return Object.keys(groups).map(function (k) { return groups[k]; }) .sort(function (a, b) { var pa = POS_ORDER[a.pos] != null ? POS_ORDER[a.pos] : 99; var pb = POS_ORDER[b.pos] != null ? POS_ORDER[b.pos] : 99; return (pa - pb) || (a.sportId - b.sportId); }) .map(function (g) { return ' ' + esc(g.pos) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(fldTotalCells(g.tot)) + ' '; }).join(''); } function fldTable(rowsHTML) { return ' ' + theadHTML('Pos', FLD_COLS) + '' + rowsHTML + ' '; } function show(season) { var out = ''; if (season === 'ALL') { var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); if (mlb.length) out += 'MLB — Career Totals by Position' + fldTable(buildRows(mlb, false)); if (milb.length) out += 'Minor Leagues — Career Totals by Position' + fldTable(buildRows(milb, false)); body.innerHTML = out ? out + 'Career fielding totals by position (regular season). FLD% is recomputed from combined PO/A/TC. Pick a season above for the year-by-year breakdown.' : 'No fielding data available yet.'; } else { var yr = rows.filter(function (r) { return r.season === season; }); out = yr.length ? fldTable(buildRows(yr, true)) : ''; body.innerHTML = out ? out + '' + esc(season) + ' fielding by position; multiple teams at the same level are combined into one line.' : 'No fielding data for ' + esc(season) + '.'; } } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('ALL'); } // ---------------- GAME LOG UI (v2.4) ---------------- // Default chip: "Last N Games" across all levels of the most recent // season (most recent first, each date links to Gameday) plus a // totals row. Season chips show the full game log for that year. var GL_PIT_COLS = ['Dec','IP','H','R','ER','HR','BB','SO','P']; var GL_HIT_COLS = ['AB','R','H','2B','3B','HR','RBI','BB','SO','SB']; function glDecision(st) { if (n(st.wins)) return 'W'; if (n(st.losses)) return 'L'; if (n(st.saves)) return 'SV'; if (n(st.holds)) return 'HLD'; if (n(st.blownSaves)) return 'BS'; return ''; } function glTheadHTML(cols) { return ' Date Opp Lvl ' + cols.map(function (c) { return ' ' + c + ' '; }).join('') + ' '; } function glRowHTML(s, isPitching) { var st = s.stat || {}; var lvl = levelLabel(s._sportId, s.league && s.league.name); var opp = (s.opponent && (s.opponent.abbreviation || s.opponent.name)) || ''; var oppTxt = (s.isHome === false ? '@ ' : 'vs ') + opp; var pk = s.game && s.game.gamePk; var gd = pk ? (s._sportId === 1 ? 'https://www.mlb.com/gameday/' : 'https://www.milb.com/gameday/') + pk : ''; var dateCell = gd ? '' + esc(fmtDate(s.date)) + '' : esc(fmtDate(s.date)); var cells = isPitching ? [ glDecision(st), st.inningsPitched || '0.0', n(st.hits), n(st.runs), n(st.earnedRuns), n(st.homeRuns), n(st.baseOnBalls), n(st.strikeOuts), st.numberOfPitches != null ? n(st.numberOfPitches) : '--' ] : [ n(st.atBats), n(st.runs), n(st.hits), n(st.doubles), n(st.triples), n(st.homeRuns), n(st.rbi), n(st.baseOnBalls), n(st.strikeOuts), n(st.stolenBases) ]; return ' ' + dateCell + ' ' + ' ' + esc(oppTxt) + ' ' + ' ' + (lvl ? '' + esc(lvl) + '' : '') + ' ' + cellsHTML(cells) + ' '; } function glTotalRowHTML(list, isPitching, label) { var tot = {}, pitches = 0, hasPitches = false; list.forEach(function (s) { var st = s.stat || {}; (isPitching ? pitAccumulate : hitAccumulate)(tot, st); if (st.numberOfPitches != null) { pitches += n(st.numberOfPitches); hasPitches = true; } }); var cells, txt; if (isPitching) { txt = label + ' (' + era(n(tot.earnedRuns), n(tot.outs)) + ' ERA)'; cells = [ '', outsToIp(n(tot.outs)), n(tot.hits), n(tot.runs), n(tot.earnedRuns), n(tot.homeRuns), n(tot.baseOnBalls), n(tot.strikeOuts), hasPitches ? pitches : '--' ]; } else { txt = label + ' (' + fmtAvg(tot.atBats ? tot.hits / tot.atBats : NaN) + ' AVG)'; cells = [ n(tot.atBats), n(tot.runs), n(tot.hits), n(tot.doubles), n(tot.triples), n(tot.homeRuns), n(tot.rbi), n(tot.baseOnBalls), n(tot.strikeOuts), n(tot.stolenBases) ]; } return ' ' + esc(txt) + ' ' + cellsHTML(cells) + ' '; } function initGameLog(group, rows, isPitching) { var chips = document.getElementById('pp-gl-chips'); var body = document.getElementById('pp-gl-body'); if (!chips || !body) return; var seasonsMap = {}; rows.forEach(function (r) { if (r.sportId === 17) return; (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { chips.innerHTML = ''; body.innerHTML = 'No game log available.'; return; } var N = n(RECENT_GAMES); chips.innerHTML = 'Last ' + N + ' Games' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var cols = isPitching ? GL_PIT_COLS : GL_HIT_COLS; var cache = {}; function fetchSeason(season) { if (!cache[season]) cache[season] = loadGameLog(group, season, Object.keys(seasonsMap[season]).map(Number)); return cache[season]; } function tableHTMLFor(list, totalLabel) { return ' ' + glTheadHTML(cols) + '' + list.map(function (s) { return glRowHTML(s, isPitching); }).join('') + (list.length > 1 ? glTotalRowHTML(list, isPitching, totalLabel) : '') + ' '; } function show(key) { var recent = key === 'RECENT'; var season = recent ? seasons[0] : key; body.innerHTML = 'Loading ' + (recent ? 'recent games' : esc(season) + ' game log') + '…'; fetchSeason(season).then(function (all) { var list = recent ? all.slice(0, N) : all; if (!list.length) { body.innerHTML = 'No games on record for ' + esc(season) + '.'; return; } body.innerHTML = tableHTMLFor(list, recent ? 'Last ' + list.length : esc(season) + ' Total') + '' + (recent ? 'Most recent ' + list.length + ' games across all levels (' + esc(season) + '), newest first. ' : esc(season) + ' game log, all levels, newest first. ') + 'Dates link to the Gameday box score. Pick a season above for the full log.'; }).catch(function (e) { body.innerHTML = 'Game log could not load (' + esc(e && e.message) + ').'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('RECENT'); } })();
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Amazing Away Games: Olympic Stadium, Montreal. Six Home Runs on Opening Day!
April 4, 1988. Mets 10, Expos 6 The 1988 Mets were certainly aware of the shadow they were playing under. Two years removed from the chaotic, magical, and entirely unrepeatable 1986 World Championship. The 1980s Mets were a cultural phenomenon, with names like Hernandez, Strawberry, Carter, Gooden, and Darling all over your televisions and newspapers. They expected to dismantle the competition, and that's what they did in 1988, winning 100 games. They won their division by 15 games. You want...
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
RVH — Race for Six: The Final Board
  The regular season is over. The race is over. And the Mets finished inside the six. With Sunday's loss in Washington, New York finished 74–88 and locked in the fifth-best lottery odds for the 2027 Draft. That's a meaningful reversal from where this series last stood. On September 10, the Mets were seventh among lottery-eligible clubs, with a 39.4% chance of a top-six pick. They went 6–10 the rest of the way, and the teams around them finally started winning. Final result: fifth seed, 62.6% chance at a top-six selection. The Final Lottery Board Seed Team Top-six odds 1 Colorado 87.6% 2 Angels 87.6% 3 Athletics 87.6% 4 Kansas City 73.0% 5 Mets 62.6% 6 Cincinnati 51.2% 7 Detroit 39.2% 8 Seattle 28.7% 9 Washington 19.9% San Francisco and Pittsburgh are ineligible for the lottery and can't pick better than 10th. The Mets' Odds, Pick by Pick Pick Odds No. 1 8.7% No. 2 9.3% No. 3 10.0% No. 4 10.9% No. 5 11.7% No. 6 12.0% Top six (total) 62.6% Outside the top six 37.4% Notice the shape. The odds rise with each pick. The Mets' most likely lottery outcome is sixth, not first. That's how a fifth seed behaves: fewer chances at the first draw, but more chances as the higher seeds come off the board. Remember the Distinction A top-six pick isn't just a better pick. It's a protected pick. Under the current rules, the Mets' first selection drops 10 spots because they exceeded the second CBT threshold. A lottery pick from No. 1 through No. 6 is exempt. The Mets keep it, and the 10-spot penalty shifts to their second selection. Miss the top six, and the math turns hard. If the Mets fall out of the lottery, their natural slot is seventh through ninth, most likely seventh (21.2%). The penalty then pushes that pick down 10 spots, to roughly 17th through 19th. We've seen this movie. This July, the Mets' first pick fell from No. 17 to No. 27. So the lottery isn't picking between fifth and seventh. It's picking between a top-six pick and a high-teens pick. The Money Follows the Pick The protection isn't just about who the Mets can draft. It's about how much they can spend. Every pick in the first 10 rounds carries an assigned slot value, and those values add up to a team's bonus pool. Here's what those slots were worth in 2026: Pick 2026 slot value No. 1 $11,350,600 No. 2 $10,507,000 No. 3 $9,740,100 No. 4 $8,988,400 No. 5 $8,336,500 No. 6 $7,746,100 No. 17 $4,868,600 No. 18 $4,695,500 No. 19 $4,530,500 That's a swing of roughly $3 million to $7 million in the draft budget. And it isn't limited to one player. Teams at the top of the draft often sign their first pick below slot and use the savings to buy talent later in the class. A bigger pool means more flexibility across the whole draft, not just a better first name on the board. The Mets know the other side of that. With their penalized pick at No. 27 this July, their bonus pool was $6.73 million, 28th of 30 teams. Weighting the slot values by this year's lottery odds, the Mets' first pick is worth roughly $7.6 million in expected slot value, compared with about $4.8 million for a non-lottery pick. That's the real stake of this series. Not the talent gap between pick 6 and pick 17, which reasonable people can debate. It's whether the Mets' first selection, and the budget attached to it, is protected from a structural penalty. Now the Asterisk Here's the problem with everything above. It may all be moot. The draft lottery, the CBT pick penalty, and the bonus pool system all come from the Collective Bargaining Agreement. That agreement expires December 1. The lottery is scheduled for December. That means every rule that produced this board is on the table in the next negotiation: the lottery itself, its weighting, the eligibility limits, the 10-spot penalty, and the slot values that set each team's budget. Owners and players could keep the system as it is. They could change the odds. They could change how penalty picks are protected. They could restructure bonus pools. They could scrap the lottery altogether. And if there's a lockout, even the timing of the lottery becomes an open question. The Mets did their part. They finished fifth. What that finish is worth will be decided at the bargaining table, not on the field. Closing the Series When we started the Race for Six, the question was simple: could a lost season still produce a meaningful draft asset? The answer turned out to be yes. But it was never really about losing. The Mets played some of the best baseball in the sport after the deadline. They slid out of the race, then back into it. They finished with better than even odds of protecting their first pick, and the budget that comes with it. That's the best version of a lost season: the kids developed, the team competed, and the draft position held. Now the lottery gets to decide. Or the new CBA does. We'll see what gets negotiated... Sources: MLB final standings; Tankathon penalty-adjusted 2027 lottery odds; MLB Pipeline 2026 slot values and bonus pools; MLB CBA/CBT rules. Final qualification: Odds reflect Tankathon's penalty-adjusted table, which accounts for lottery-ineligible teams. The projected post-penalty range for a non-lottery Mets pick and the expected slot value are my estimates. Slot values shown are 2026 figures; 2027 values have not been set. The current CBA expires December 1, 2026, and the lottery, its odds, the CBT pick penalty, and the bonus pool system could all change under the next agreement.
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Paul Articulates – setting up the off-season
You may be watching the MLB  playoffs, or you may be taking a break from it all after a rough season.  Either way, if you are a true Mets fan, you are already thinking about what comes next. As you can see by the “Important dates” listing in the side column of our site, there are some pretty big things coming up for the front office.  This would include key decisions on who would receive Qualifying Offers, what potential trades can be negotiated, and where to pick up club options that are available.  You are also anxiously awaiting the decisions of those who have player options. This post aims to arm you with some important data to consider as these pivotal decisions come down. The Calander:  MLB’s activity timeline is always tied to the end of the World Series.  On the fifth day after the World Series ends, personnel actions open up: Trades can formally be enacted, free agents are allowed to sign with other teams, and Qualifying Offers (QOs) must be finalized.  The series will end some time between October 29th and November 2nd depending upon how many games are required.  This pegs those key personnel dates between November 3rd (early series completion) and November 7th (late series completion).  In addition to the post-series activities, players that have received QOs are given until November 18th to decide whether to accept or reject.  Another significant date is December 1st, when the collective bargaining agreement expires.  If there is no agreement before then, expect all baseball activity to halt until there is resolution. The Payroll: The current 28-man active roster for the Mets contains a lot more youth than prior rosters, with many players under team control or arbitration eligible players.  Only eight players remain with long term contracts in place that commit salary and one of them, Bo Bichette, has the ability to opt out of the remaining two years on his deal.  These eight (assuming Bo stays) commit the team to $217.35M which is far below last year’s roughly $350M in salary obligation.   A caveat here is that Jorge Polanco, who is under contract to receive $23M next year, is on the IL but barring a trade or release will be on the active roster in 2027. Another caveat is that the 12 players making league minimum (assumed to be $1M next year but subject to the CBA negotiations) will add $12M to the bottom line and the eleven arbitration eligible players will add more.  Here are the current commitments: This table can be expanded to include the full 28-man roster by including estimates of $1M salaries for those earning MLB minimum salary and estimates from Sportrac of post-arbitration salaries for the rest.  I started to do that, but realized that it was futile because all of the “fill in the blanks” information is deeply dependent upon what is agreed upon in the new Collective Bargaining Agreement whenever that is finalized.  Instead, here is a table of the arbitration eligible players over the next two seasons from the current team: All the other players are controllable for the next few years. Although these names are from the 40-man roster, we are primarily focused on the active roster (26 players for most of the season, 28 players in September).  If you keep all of the players from these two tables, there are only three slots remaining for free agent acquisitions or minor league call-ups.  Clearly there will have to be some movement, and several articles within the last week have already discussed those potential choices.Time to put your GM hat on and start envisioning the 2027 roster.  Good luck!
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Mets Calendar Classics - Mets Post Season Games Played On This Date: October 1st
NY Post Back Page, 10/2/2024 Year: 2024; NLWCS Game #1; Tuesday; Oct 1, NYM 8 @ MIL 4; boxscore; WP: Luis Severino; LP: Joel Payamps; Time: 2:43; Day; Attendance: 40,022; Record: 1-0; W; Lindor SS;  0 for 4; 1 run; 1 walk; 1 K; Iglesias, J 2B-3B;  1 for 5; 1 run; 1 RBI; 1 K; Nimmo LF;  1 for 5; 1 run; 1 K; Vientos 3B;  2 for 4; 2 runs; 2 RBIs; 1 K; Acuña 2B;  0 for 0; Alonso 1B;  0 for 1; 1 run; 3 walks; Winker DH;  1 for 2; Triple; 1 run; 2 RBIs; Martinez, J PH-DH;  1 for 2; 2 RBIs; 1 K; Marte, S RF;  0 for 2; 1 RBI; 1 walk; Bader CF;  0 for 0; Taylor, T CF-RF;  1 for 4; double; 1 run; 2 Ks; Alvarez, F C;  0 for 4; 1 K; Severino, L (W, 1-0); 6 innings; 4 runs; 3 ERs; 8 hits; 2 walks; 3 Ks; Buttó; 2 innings; no runs; 3 Ks; Stanek; 1 inning; no runs; 1 K; 
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Around the Majors with Mets News and Links - 10/1/2026
Here are the top Stories from every Major League team courtesy from our friends at SportSpyder. Note - this page updates throughout the day - come back later today for the latest news.
000
John From Albany @johnfromalbany.bsky.social · 01/10/2026
dlvr.it
Ernest Dove: David Stearns New York Mets Draft Class Evaluations - 9/30/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
Rumble Ponies YouTube Channel: Delivering Memorable Customer Service: Rumble Ponies Training Video - 9/30/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
SNY on YouTube: Two years ago today, the Mets clinched a postseason berth with a win over the Braves - 9/30/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
Wednesday catch-all thread (9/30/26)
Please use this thread all week to discuss any Mets-specific topic you wish. Click Link Below to Read Article. http://dlvr.it/TVjgb0
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
MACK – Let’s Revisit - OF - Aiden Smith
 
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
Arizona Fall Mets Prospect Profile: RHP Ryan Lambert
Ryan Lambert, Photo by Matt Kipp, courtesy of the Binghamton Rumble Ponies After missing two months from AAA ball in 2026 with an IL and rehab stint from July 11 to September 10, Ryan Lambert heads to the Arizona Fall League to get some work and try to replicate his 2025 success.   In 2025, Lambert regularly hit 99 MPH with his fastball, K'd 81 batters with a 1.62 ERA and a 4.86 BB/9 rate in 50 innings for Brooklyn and Binghamton and started off 2026 as the #29 on Baseball America's Mets Prospect List and #18 on MLB.com's MLB Pipeline Prospect List. MLB Pipeline said he had the best fastball in the Mets Minor Leagues and Baseball America said "Lambert’s fastball is one of the best in the minor leagues." Anthony DiComo wrote this about Ryan Lambert n February 2026: "...Lambert is the hardest-throwing pitcher in camp. During the earliest days of Spring Training, he hit 99.6 mph on the radar gun. He eclipsed 100 mph last year..." Unfortunately, Lambert's 2025 success did not translate to AAA this year.  He saw his BB/9 rate rise to 10.24, his ERA to 8.07 and his velocity average closer to 95 than his previous 99.   In July, he ended up on the IL with an undisclosed injury, and after rehab appearances in St. Lucie and Brooklyn, threw six games for Syracuse in September going 0-1 with a 13.50 ERA and a 2.786 WHIP in 4.2 innings. After 2025 and his 2026 Spring outings, many saw Ryan Lambert as a future Mets bullpen piece.  Not Rule 5 Eligible until 2027, he will have this Fall and the 2027 Syracuse season to try to get back on track. Loading player profile… #pp-widget { max-width: 820px; margin: 0 auto; font-family: 'Barlow Condensed', -apple-system, 'Segoe UI', Arial, sans-serif; color: #1a1a1a; } #pp-widget * { box-sizing: border-box; } #pp-widget .pp-loading { text-align: center; padding: 30px; color: #6c757d; font-size: 18px; } #pp-widget .pp-card { background: #fff; border-radius: 12px; box-shadow: 0 2px 8px rgba(0,0,0,0.12); overflow: hidden; margin-bottom: 20px; } /* header */ #pp-widget .pp-header { background: linear-gradient(135deg, #002D72 0%, #FF5910 100%); color: #fff; padding: 22px; } #pp-widget .pp-head-row { display: flex; align-items: center; gap: 18px; margin-bottom: 14px; flex-wrap: wrap; } #pp-widget .pp-headshot { width: 92px; height: 92px; border-radius: 50%; border: 3px solid #fff; background: #fff; object-fit: cover; flex-shrink: 0; } #pp-widget .pp-number { font-size: 44px; font-weight: 700; opacity: 0.9; } #pp-widget .pp-name h1 { font-size: 34px; margin: 0 0 2px 0; line-height: 1.1; color: #fff; } #pp-widget .pp-pos { font-size: 18px; opacity: 0.92; } #pp-widget .pp-bio { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 10px; font-size: 15px; } #pp-widget .pp-bio-item { background: rgba(255,255,255,0.14); padding: 7px 11px; border-radius: 6px; } #pp-widget .pp-bio-label { opacity: 0.82; font-size: 12px; text-transform: uppercase; letter-spacing: 0.5px; margin-bottom: 1px; } /* jump nav */ #pp-widget .pp-nav { display: flex; gap: 8px; flex-wrap: wrap; padding: 10px 22px; background: #f8f9fa; border-bottom: 1px solid #e9ecef; } #pp-widget .pp-nav a { color: #002D72; font-weight: 600; text-decoration: none; font-size: 15px; padding: 4px 10px; border-radius: 14px; border: 1px solid #d7dbe0; background: #fff; } #pp-widget .pp-nav a:hover { background: #002D72; color: #fff; } /* sections */ #pp-widget .pp-section { padding: 20px 22px; } #pp-widget .pp-title { font-size: 22px; font-weight: 700; color: #002D72; margin: 0 0 12px 0; padding-bottom: 6px; border-bottom: 2px solid #FF5910; } #pp-widget .pp-sub { font-size: 17px; font-weight: 700; color: #002D72; margin: 16px 0 6px 0; } #pp-widget .pp-note { font-size: 13px; color: #6c757d; margin: 6px 0 0 0; } #pp-widget .pp-empty { font-size: 15px; color: #6c757d; padding: 8px 0; } /* quick stat boxes */ #pp-widget .pp-quick { display: grid; grid-template-columns: repeat(auto-fit, minmax(88px, 1fr)); gap: 12px; margin-bottom: 8px; } #pp-widget .pp-qbox { text-align: center; padding: 12px 6px; background: #f8f9fa; border: 1px solid #e9ecef; border-radius: 8px; } #pp-widget .pp-qval { font-size: 26px; font-weight: 700; color: #002D72; } #pp-widget .pp-qlbl { font-size: 12px; color: #6c757d; text-transform: uppercase; letter-spacing: 0.5px; } /* tables */ #pp-widget .pp-twrap { overflow-x: auto; -webkit-overflow-scrolling: touch; } #pp-widget table.pp-table { width: 100%; border-collapse: collapse; margin-bottom: 6px; } #pp-widget table.pp-table th { background: #002D72; color: #fff; padding: 9px 6px; text-align: center; font-size: 12px; font-weight: 600; text-transform: uppercase; white-space: nowrap; } #pp-widget table.pp-table td { padding: 8px 6px; text-align: center; border-bottom: 1px solid #e9ecef; font-size: 14px; white-space: nowrap; } #pp-widget table.pp-table tr:hover td { background: #f8f9fa; } #pp-widget td.pp-left, #pp-widget th.pp-left { text-align: left; } #pp-widget .pp-yr { font-weight: 600; color: #002D72; } #pp-widget .pp-lvl { display: inline-block; background: #002D72; color: #fff; border-radius: 10px; font-size: 11px; font-weight: 700; padding: 1px 8px; margin-left: 6px; vertical-align: 1px; } #pp-widget tr.pp-total td { font-weight: 700; background: #fff4ee; border-top: 2px solid #FF5910; } #pp-widget tr.pp-career td { font-weight: 700; background: #eaf0fa; border-top: 2px solid #002D72; } /* v2.4: repeated header rows inside long tables */ #pp-widget table.pp-table tr.pp-rehead th { border-top: 2px solid #FF5910; } #pp-widget td.pp-lnk a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget td.pp-lnk a:hover { text-decoration: underline; } /* splits + fielding + game log season chips */ #pp-widget .pp-chips { display: flex; gap: 6px; flex-wrap: wrap; margin-bottom: 10px; } #pp-widget .pp-chip { border: 1px solid #002D72; color: #002D72; background: #fff; border-radius: 14px; padding: 3px 12px; font-size: 14px; font-weight: 600; cursor: pointer; font-family: inherit; } #pp-widget .pp-chip.pp-on { background: #002D72; color: #fff; } /* videos */ #pp-widget .pp-vids { display: grid; grid-template-columns: repeat(auto-fill, minmax(230px, 1fr)); gap: 14px; } #pp-widget .pp-vcard { border: 1px solid #e9ecef; border-radius: 8px; overflow: hidden; background: #fff; } #pp-widget .pp-vcard-x { grid-column: 1 / -1; max-width: 560px; } #pp-widget .pp-vcard-x blockquote { margin: 0 auto; } #pp-widget .pp-vthumb { position: relative; cursor: pointer; background: #000; } #pp-widget .pp-vthumb img { width: 100%; display: block; aspect-ratio: 16/9; object-fit: cover; } #pp-widget .pp-vplay { position: absolute; top: 50%; left: 50%; transform: translate(-50%,-50%); width: 44px; height: 44px; border-radius: 50%; background: rgba(0,45,114,0.85); color: #fff; display: flex; align-items: center; justify-content: center; font-size: 18px; pointer-events: none; } #pp-widget .pp-vdur { position: absolute; right: 6px; bottom: 6px; background: rgba(0,0,0,0.75); color: #fff; font-size: 11px; padding: 1px 6px; border-radius: 3px; } #pp-widget .pp-vbody { padding: 8px 10px 10px 10px; } #pp-widget .pp-vtitle { font-size: 14px; font-weight: 600; line-height: 1.25; color: #1a1a1a; margin-bottom: 4px; } #pp-widget .pp-vmeta { font-size: 12px; color: #6c757d; display: flex; justify-content: space-between; } #pp-widget .pp-vmeta a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget .pp-vcard video { width: 100%; display: block; aspect-ratio: 16/9; background: #000; } #pp-widget .pp-vlink { display: block; background: #002D72; color: #fff; text-align: center; padding: 34px 10px; font-weight: 700; text-decoration: none; } /* footer */ #pp-widget .pp-footer { padding: 12px 22px; background: #f8f9fa; text-align: center; font-size: 12px; color: #6c757d; } #pp-widget .pp-footer a { color: #002D72; font-weight: 600; text-decoration: none; } @media (max-width: 600px) { #pp-widget .pp-header { padding: 15px; } #pp-widget .pp-name h1 { font-size: 26px; } #pp-widget .pp-number { font-size: 34px; } #pp-widget .pp-section { padding: 15px 12px; } #pp-widget table.pp-table th, #pp-widget table.pp-table td { padding: 6px 4px; font-size: 12px; } } (function () { // ================= CONFIG - EDIT THIS ================= var PLAYER_ID = 822038; // { code: totals }. // Tries the Stats API careerStatSplits call first; if nothing comes // back, sums every season's statSplits for that level instead. function loadCareerSplits(group, sportId, seasons, accF) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=careerStatSplits&group=' + group + '&sportId=' + sportId + '&sitCodes=' + SIT_CODE_STR) .then(function (d) { return splitsOf(d); }) .catch(function () { return []; }) .then(function (sp) { var direct = sumByCode(sp, accF, true); if (Object.keys(direct).length) return direct; return Promise.all(seasons.map(function (yr) { return loadSplits(group, yr, [sportId]); })) .then(function (arrs) { var out = {}; arrs.forEach(function (list) { var yrTot = sumByCode(list, accF, false); Object.keys(yrTot).forEach(function (c) { out[c] = addTot(out[c] || {}, yrTot[c]); }); }); return out; }); }); } var MONTH_NAMES = ['','January','February','March','April','May','June','July','August','September','October','November','December']; function loadMonthly(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=byMonth&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return (n(a.month) - n(b.month)) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: GAME LOG (v2.4) ---------------- function loadGameLog(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=gameLog&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return String(b.date || '').localeCompare(String(a.date || '')) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: PITCH ARSENAL / VELO (v2.4) ---------------- // Only levels with pitch tracking: MLB (1), AAA (11), Low-A (14). var PITCH_SPORT_IDS = [1, 11, 14]; function loadPitchData(season) { return Promise.all(PITCH_SPORT_IDS.map(function (sid) { var ars = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchArsenal&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); var log = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchLog&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); return Promise.all([ars, log]).then(function (r) { return { sportId: sid, arsenal: r[0], log: r[1] }; }); })); } // ---------------- FETCH: TRANSACTIONS ---------------- function loadTransactions() { var end = new Date().toISOString().slice(0,10); return jget(API + '/transactions?playerId=' + PLAYER_ID + '&startDate=2010-01-01&endDate=' + end) .then(function (d) { var tx = (d.transactions || []).slice(); tx.sort(function (a, b) { return String(b.date).localeCompare(String(a.date)); }); return tx.slice(0, TX_MAX); }) .catch(function () { return []; }); } // ---------------- FETCH: FILM ROOM VIDEOS ---------------- var GQL = 'query Search($query: String!, $page: Int, $limit: Int, $feedPreference: FeedPreference, ' + '$languagePreference: LanguagePreference, $contentPreference: ContentPreference, $queryType: QueryType = STRUCTURED) {\n' + ' search(query: $query, limit: $limit, page: $page, feedPreference: $feedPreference, ' + 'languagePreference: $languagePreference, contentPreference: $contentPreference, queryType: $queryType) {\n' + ' plays {\n mediaPlayback {\n slug\n title\n blurb\n date\n' + ' feeds {\n type\n duration\n' + ' image { cuts { width src } }\n' + ' playbacks { name url }\n }\n }\n }\n }\n}'; function gqlVars(queryStr, limit) { return { queryType: null, query: queryStr, limit: limit || VIDEO_LIMIT, page: 0, languagePreference: 'EN', contentPreference: 'CMS_FIRST' }; } function videoSearchUrl(queryStr, limit) { return 'https://fastball-gateway.mlb.com/graphql' + '?query=' + encodeURIComponent(GQL) + '&operationName=Search' + '&variables=' + encodeURIComponent(JSON.stringify(gqlVars(queryStr, limit))); } function proxyPlayerUrl(person) { var teamId = (person && person.currentTeam && person.currentTeam.id) || ''; var last = (person && (person.lastName || (person.fullName || '').split(' ').pop())) || ''; return PROXY_URL + '?player=' + PLAYER_ID + '&team=' + teamId + '&name=' + encodeURIComponent(last) + '&limit=' + VIDEO_LIMIT; } var ppJsonpCount = 0; function jsonpCall(baseUrl) { return new Promise(function (resolve, reject) { var cb = 'ppVidCb' + (++ppJsonpCount); var s = document.createElement('script'); var timer = setTimeout(function () { cleanup(); reject(new Error('proxy timeout')); }, 30000); function cleanup() { clearTimeout(timer); try { delete window[cb]; } catch (e) { window[cb] = undefined; } if (s.parentNode) s.parentNode.removeChild(s); } window[cb] = function (data) { cleanup(); resolve(data); }; s.onerror = function () { cleanup(); reject(new Error('proxy load error')); }; s.src = baseUrl + '&callback=' + cb; document.head.appendChild(s); }); } function proxyJson(baseUrl) { return fetch(baseUrl).then(function (r) { if (!r.ok) throw new Error('proxy HTTP ' + r.status); return r.json(); }); } function gqlPost(queryStr, limit) { return fetch('https://fastball-gateway.mlb.com/graphql', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ query: GQL, operationName: 'Search', variables: gqlVars(queryStr, limit) }) }).then(function (r) { if (!r.ok) throw new Error('HTTP ' + r.status + ' (POST)'); return r.json(); }); } function gqlFetch(queryStr, limit) { return jget(videoSearchUrl(queryStr, limit)) .catch(function () { return gqlPost(queryStr, limit); }); } function fmtDur(sec) { if (sec == null || sec === '') return ''; if (typeof sec === 'string' && sec.indexOf(':') > -1) return sec.replace(/^00:0?/, ''); var x = parseInt(sec, 10); if (isNaN(x)) return ''; return Math.floor(x / 60) + ':' + ('0' + (x % 60)).slice(-2); } function pickPlayback(feeds) { if (!feeds || !feeds.length) return { mp4: null, thumb: '', dur: '' }; var ranked = feeds.slice().sort(function (a, b) { return ((a.type === 'CMS') ? 0 : 1) - ((b.type === 'CMS') ? 0 : 1); }); var mp4 = null, thumb = '', dur = ''; for (var i = 0; i < ranked.length; i++) { var f = ranked[i]; if (!dur && f.duration) dur = fmtDur(f.duration); if (!thumb && f.image && f.image.cuts && f.image.cuts.length) { var cuts = f.image.cuts.slice().sort(function (a, b) { return (b.width||0) - (a.width||0); }); var mid = cuts.filter(function (c) { return c.width && c.width 1) { html += ' ' + esc(yr) + ' ' + esc(opts.totalLabel) + ' ' + cellsHTML(totF(yrTot)) + ' '; } // v2.4: repeat the column header row every HEADER_REPEAT seasons if (n(HEADER_REPEAT) > 0 && (si + 1) % n(HEADER_REPEAT) === 0 && si < seasons.length - 1) { html += headRowHTML('Year / Team', cols, 'pp-rehead'); } }); if (seasons.length) { html += ' ' + esc(opts.careerLabel) + ' ' + cellsHTML(totF(career)) + ' '; } return html ? tableHTML(opts.id, 'Year / Team', cols, html) : ''; } // ---------------- MAIN ---------------- loadPerson().then(function (person) { if (!person) { root.innerHTML = 'Player not found for ID ' + PLAYER_ID + '.'; return; } return Promise.all([ loadYearByYear('hitting'), loadYearByYear('pitching'), loadYearByYear('fielding'), loadTransactions(), loadVideos(person), loadJersey(person) ]) .then(function (res) { render(person, res[5], res[0], res[1], res[2], res[3], res[4]); }); }) .catch(function (e) { root.innerHTML = 'Could not load profile (' + esc(e.message) + '). Please refresh.'; }); function render(person, jersey, hitRows, pitRows, fldRows, txs, vids) { var isPitcher = person.primaryPosition && person.primaryPosition.code === '1'; var hasHit = hitRows.some(function (r) { return n(r.stat.atBats) || n(r.stat.plateAppearances); }); var hasPit = pitRows.some(function (r) { return ipToOuts(r.stat.inningsPitched) || n(r.stat.gamesPlayed); }); var usePit = isPitcher && hasPit; var showPitches = usePit && SHOW_PITCHES; var showGameLog = n(RECENT_GAMES) > 0 && (hasPit || hasHit); var headshot = 'https://img.mlbstatic.com/mlb-photos/image/upload/d_people:generic:headshot:67:current.png' + '/w_180,q_auto:best/v1/people/' + PLAYER_ID + '/headshot/milb/current'; var birth = [person.birthCity, person.birthStateProvince, person.birthCountry].filter(Boolean).join(', '); var teamName = (person.currentTeam && person.currentTeam.name) || 'New York Mets Organization'; var h = ''; // ---- header ---- h += '' + '' + (jersey ? '#' + esc(jersey) + '' : '') + ' ' + esc(person.fullName) + ' ' + '' + esc((person.primaryPosition && person.primaryPosition.name) || '') + ' • ' + esc(teamName) + '' + '' + 'Full Name' + esc(person.fullFMLName || person.fullName) + '' + 'Bats/Throws' + esc(((person.batSide||{}).code||'') + '/' + ((person.pitchHand||{}).code||'')) + '' + 'Height/Weight' + esc((person.height||'') + ' / ' + (person.weight ? person.weight + ' lbs' : '')) + '' + 'Born' + esc(fmtDate(person.birthDate) + (person.currentAge ? ' (Age ' + person.currentAge + ')' : '')) + '' + (birth ? 'Birthplace' + esc(birth) + '' : '') + (HOW_ACQUIRED ? 'How Acquired' + esc(HOW_ACQUIRED) + '' : '') + EXTRA_BOXES.map(function (b) { if (!b || !b.value) return ''; return '' + esc(b.label || '') + '' + esc(b.value) + ''; }).join('') + ''; // ---- jump nav ---- h += 'Stats' + (showPitches ? 'Pitches' : '') + 'Splits' + 'Fielding' + (showGameLog ? 'Game Log' : '') + 'VideosTransactions'; // ---- stats ---- h += ' Statistics '; var groups = []; if (isPitcher) { if (hasPit) groups.push('P'); if (hasHit) groups.push('H'); } else { if (hasHit) groups.push('H'); if (hasPit) groups.push('P'); } if (!groups.length) h += 'No stats available yet.'; groups.forEach(function (g) { var rows = (g === 'H') ? hitRows : pitRows; var isP = (g === 'P'); var gLbl = isP ? 'Pitching' : 'Hitting'; var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); var winter = rows.filter(function (r) { return r.sportId === 17; }); var mlbT = buildStatsTable(mlb, isP, { id: 'pp-mlb-' + g, totalLabel: 'MLB Total', careerLabel: 'MLB Career' }); var milbT = buildStatsTable(milb, isP, { id: 'pp-milb-' + g, totalLabel: 'MiLB Total', careerLabel: 'MiLB Career', rates: !isP }); var winterT = buildStatsTable(winter, isP, { id: 'pp-winter-' + g, totalLabel: 'Total', careerLabel: 'Winter/AFL Career' }); if (mlbT) h += 'MLB ' + gLbl + '' + mlbT; if (milbT) h += 'Minor League ' + gLbl + '' + milbT; if (winterT) h += 'Winter Ball / AFL ' + gLbl + '' + winterT; }); h += ''; // ---- pitch arsenal (v2.4, pitchers only) ---- if (showPitches) { h += ' Pitch Arsenal ' + 'Loading pitch data…'; } // ---- splits ---- h += ' Splits ' + 'Loading splits…'; // ---- fielding (v2.3) ---- h += ' Fielding ' + 'Loading fielding…'; // ---- game log (v2.4) ---- if (showGameLog) { h += ' Game Log ' + 'Loading game log…'; } // ---- videos ---- h += ' Video Highlights '; var autoVids = vids.list || []; var hasAny = MANUAL_VIDEOS.length || autoVids.length; var hasXPost = false; if (hasAny) { h += ''; MANUAL_VIDEOS.forEach(function (v) { var yt = ytEmbedUrl(v.url); var xp = xPostUrl(v.url); if (xp) { hasXPost = true; h += '' + '' + '' + esc(v.title || 'View post on X') + '' + '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + 'View on X'; return; } h += ''; if (yt) { h += ''; } else if (/\.mp4(\?|$)/i.test(v.url || '')) { h += ''; } else if (isMlbVideoUrl(v.url)) { var mlbEmb = mlbEmbedUrl(v.url); if (mlbEmb) { h += ''; } else { h += '► Watch on MLB.com'; } } else { h += '► Watch Video'; } h += '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + (isMlbVideoUrl(v.url) ? 'View on MLB.com' : '') + ''; }); autoVids.forEach(function (v, i) { h += '' + '' + (v.thumb ? '' : '') + '►' + (v.dur ? '' + esc(v.dur) + '' : '') + '' + esc(v.title) + '' + '' + esc(fmtDate(v.date)) + '' + 'Watch on MiLB.com' + ''; }); h += ''; if (autoVids.length) { h += 'Auto-updated from MLB Film Room. Full library: ' + 'milb.com/video/topic/playerid-' + PLAYER_ID + ''; } } if (!autoVids.length && !MANUAL_VIDEOS.length) { h += '' + (vids.error ? 'The automatic video feed could not load (' + esc(vids.error) + '). ' + 'If this keeps happening, set PROXY_URL in the config to your Apps Script passthrough. ' : 'No clips found in the Film Room index for this player yet. ') + 'Full library: MiLB.com.'; } else if (!autoVids.length && vids.error) { h += 'The automatic video feed could not load (' + esc(vids.error) + ').'; } h += ''; // ---- transactions ---- h += ' Transactions '; if (txs.length) { var trows = ''; txs.forEach(function (t) { trows += ' ' + esc(fmtDate(t.date)) + ' ' + ' ' + esc(t.typeDesc || '') + ' ' + ' ' + esc(t.description || '') + ' '; }); h += ' Date Type Transaction ' + trows + ' '; } else { h += 'No transactions on record.'; } h += ''; // ---- footer ---- h += 'Stats & transactions from the MLB Stats API • Videos from MLB Film Room • ' + 'MiLB.com Player Page • ' + 'MLB.com Player Page' + ''; root.innerHTML = h; if (hasXPost) loadXWidgets(); // ---- header stat boxes (v2.4: separate MLB / MiLB rows) ---- buildQuickStats(usePit ? pitRows : hitRows, usePit); // ---- video inline playback ---- root.querySelectorAll('.pp-vthumb').forEach(function (el) { el.addEventListener('click', function () { var mp4 = el.getAttribute('data-mp4'); if (!mp4) { var link = el.getAttribute('data-link'); if (link) window.open(link, '_blank'); return; } var v = document.createElement('video'); v.controls = true; v.autoplay = true; v.src = mp4; v.setAttribute('playsinline',''); el.parentNode.replaceChild(v, el); }); }); var group = usePit ? 'pitching' : 'hitting'; var groupRows = usePit ? pitRows : hitRows; if (showPitches) initPitches(pitRows); initSplits(group, groupRows, usePit); initFielding(fldRows); if (showGameLog) initGameLog(group, groupRows, usePit); } // ---------------- HEADER STAT BOXES (v2.4) ---------------- // One row of boxes per HEADER_STATS entry ('MLB' / 'MiLB') for the // player's most recent season. A row is skipped if the player has // no stats at that level in that season. function buildQuickStats(rows, isPitching) { var box = document.getElementById('pp-quick'); if (!box || !rows.length || !HEADER_STATS || !HEADER_STATS.length) return; var reg = rows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) return; var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); var yr = reg.filter(function (r) { return r.season === latest; }); var accF = isPitching ? pitAccumulate : hitAccumulate; var html = ''; HEADER_STATS.forEach(function (lvlKey) { var isMlb = /^mlb$/i.test(String(lvlKey)); var list = yr.filter(function (r) { return isMlb ? r.sportId === 1 : isMilbSport(r.sportId); }); if (!list.length) return; var tot = {}; list.forEach(function (r) { accF(tot, r.stat); }); var items; if (isPitching) { items = [ [n(tot.wins) + '-' + n(tot.losses), 'W-L'], [era(n(tot.earnedRuns), n(tot.outs)), 'ERA'], [outsToIp(n(tot.outs)), 'IP'], [n(tot.strikeOuts), 'SO'], [whip(n(tot.baseOnBalls), n(tot.hits), n(tot.outs)), 'WHIP'] ]; } else { var c = hitTotalCells(tot, false); // [G,AB,R,H,2B,3B,HR,RBI,SB,BB,SO,AVG,OBP,SLG,OPS] items = [ [c[11], 'AVG'], [c[6], 'HR'], [c[7], 'RBI'], [c[8], 'SB'], [c[14], 'OPS'] ]; } html += '' + (isMlb ? 'MLB ' : 'MiLB ') + esc(latest) + ' Stats' + items.map(function (it) { return '' + esc(it[0]) + '' + esc(it[1]) + ''; }).join('') + ''; }); box.innerHTML = html; } // ---------------- PITCH ARSENAL UI (v2.4) ---------------- var PITCH_COLS = ['Usage','Avg MPH','Top MPH','Pitches']; function initPitches(pitRows) { var body = document.getElementById('pp-pitch-body'); var title = document.getElementById('pp-pitch-title'); if (!body) return; var reg = pitRows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) { body.innerHTML = 'No pitch data available.'; return; } var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); if (title) title.innerHTML = 'Pitch Arsenal — ' + esc(latest); loadPitchData(latest).then(function (res) { var out = ''; res.forEach(function (r) { var map = {}; function slot(code, desc) { return map[code] = map[code] || { code: code, desc: desc || code, usage: null, avg: null, max: null, count: 0, sum: 0, cnt: 0 }; } (r.arsenal || []).forEach(function (s) { var st = s.stat || {}; var t = st.type || {}; var code = t.code || t.description; if (!code) return; var m = slot(code, t.description); var p = Number(st.percentage); if (!isNaN(p) && st.percentage != null) m.usage = p m.max) m.max = v; m.sum += v; m.cnt++; }); var list = Object.keys(map).map(function (k) { return map[k]; }); if (!list.length) return; list.forEach(function (m) { if (m.avg == null && m.cnt) m.avg = m.sum / m.cnt; if (!m.count && m.cnt) m.count = m.cnt; }); var totalCnt = list.reduce(function (a, m) { return a + n(m.count); }, 0); list.forEach(function (m) { if (m.usage == null && totalCnt) m.usage = 100 * n(m.count) / totalCnt; }); list.sort(function (a, b) { return (n(b.usage)) - (n(a.usage)); }); var rowsHtml = list.map(function (m) { return ' ' + esc(m.desc) + ' ' + cellsHTML([ m.usage != null ? m.usage.toFixed(1) + '%' : '--', m.avg != null ? m.avg.toFixed(1) : '--', m.max != null ? m.max.toFixed(1) : '--', m.count || '--' ]) + ' '; }).join(''); out += '' + esc(levelLabel(r.sportId, '')) + '' + ' ' + theadHTML('Pitch', PITCH_COLS) + '' + rowsHtml + ' '; }); body.innerHTML = out ? out + '' + esc(latest) + ' pitch tracking by level (MLB, AAA and Low-A only). Usage and average velocity from the MLB Stats API pitch arsenal; top velocity is the hardest tracked pitch of that type in the pitch log.' : 'No pitch-tracking data returned for ' + esc(latest) + ' (available for MLB, AAA and Low-A only).'; }).catch(function (e) { body.innerHTML = 'Pitch data could not load (' + esc(e && e.message) + ').'; }); } // ---------------- SPLITS UI (v2.4: career + season chips) ---------------- // v2.4.1: pitching splits use PIT_SPLIT_COLS / pitSplitTotalCells. function initSplits(group, rows, isPitching) { var chips = document.getElementById('pp-split-chips'); var body = document.getElementById('pp-split-body'); if (!chips || !body) return; var seasonsMap = {}, sidsAll = {}; rows.forEach(function (r) { if (r.sportId === 17) return; // winter splits not indexed the same way (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; sidsAll[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { body.innerHTML = 'No splits available.'; return; } chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var defs = isPitching ? SIT_CODES_PIT : SIT_CODES; var sCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS; var accF = isPitching ? pitAccumulate : hitAccumulate; var totF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, false); }; var careerCache = null; // ---- career view: MLB table + Minor Leagues table ---- function showCareer() { body.innerHTML = 'Loading career splits…'; if (!careerCache) { var sids = Object.keys(sidsAll).map(Number); careerCache = Promise.all(sids.map(function (sid) { var yrs = seasons.filter(function (s) { return seasonsMap[s][sid]; }); return loadCareerSplits(group, sid, yrs, accF).then(function (byCode) { return { sportId: sid, byCode: byCode }; }); })); } careerCache.then(function (res) { function tableFor(filterFn) { var html = ''; defs.forEach(function (def) { var tot = {}, any = false; res.filter(filterFn).forEach(function (r) { if (r.byCode[def.code]) { addTot(tot, r.byCode[def.code]); any = true; } }); if (any) html += ' ' + esc(def.label) + ' ' + cellsHTML(totF(tot)) + ' '; }); return html ? ' ' + theadHTML('Split', sCols) + '' + html + ' ' : ''; } var mlbT = tableFor(function (r) { return r.sportId === 1; }); var milbT = tableFor(function (r) { return isMilbSport(r.sportId); }); var out = ''; if (mlbT) out += 'MLB — Career Splits' + mlbT; if (milbT) out += 'Minor Leagues — Career Splits' + milbT; body.innerHTML = out ? out + 'Career splits (regular season). Minor league line combines every MiLB level. Rate stats are recomputed from the summed raw counts. Pick a season above for the year-by-year, per-level breakdown.' : 'No career split data available.'; }).catch(function (e) { body.innerHTML = 'Career splits could not load (' + esc(e && e.message) + ').'; }); } // ---- season view: per-level splits + By Month (unchanged from v2.3.1) ---- function showSeason(season) { body.innerHTML = 'Loading ' + esc(season) + ' splits…'; var sportIds = Object.keys(seasonsMap[season]).map(Number); Promise.all([ loadSplits(group, season, sportIds), loadMonthly(group, season, sportIds) ]) .then(function (res) { var splits = res[0], months = res[1]; if (!splits.length && !months.length) { body.innerHTML = 'No split data for ' + esc(season) + '.'; return; } var out = ''; var shtml = ''; defs.forEach(function (def) { var byLevel = {}; splits.filter(function (s) { return s.split && s.split.code === def.code; }) .forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = lvl || ('sid' + s._sportId); var g = byLevel[key] = byLevel[key] || { lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); Object.keys(byLevel).map(function (k) { return byLevel[k]; }) .sort(function (a, b) { return b.sportId - a.sportId; }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); shtml += ' ' + esc(def.label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(totF(tot)) + ' '; }); }); if (shtml) { out += ' ' + theadHTML('Split', sCols) + '' + shtml + ' '; } if (months.length) { var mCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS_RATES; var mTotF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, true); }; var byMonth = {}; months.forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = n(s.month) + '|' + (lvl || 'sid' + s._sportId); var g = byMonth[key] = byMonth[key] || { month: n(s.month), lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); var mhtml = ''; Object.keys(byMonth).map(function (k) { return byMonth[k]; }) .sort(function (a, b) { return (a.month - b.month) || (b.sportId - a.sportId); }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); var label = MONTH_NAMES[g.month] || ('Month ' + g.month); mhtml += ' ' + esc(label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(mTotF(tot)) + ' '; }); out += 'By Month' + ' ' + theadHTML('Month', mCols) + '' + mhtml + ' '; } body.innerHTML = out ? out + 'Splits and monthly totals shown per level for the selected season (regular season). Splits combine all teams at the same level into one line.' : 'No split data for ' + esc(season) + '.'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); var s = b.getAttribute('data-season'); if (s === 'ALL') showCareer(); else showSeason(s); }); showCareer(); } // ---------------- FIELDING UI (v2.3) ---------------- function initFielding(rows) { var chips = document.getElementById('pp-fld-chips'); var body = document.getElementById('pp-fld-body'); if (!chips || !body) return; rows = rows.filter(function (r) { return r.sportId !== 17 && r.position && (n(r.stat.gamesPlayed) || n(r.stat.chances) || ipToOuts(r.stat.innings)); }); if (!rows.length) { chips.innerHTML = ''; body.innerHTML = 'No fielding data available yet.'; return; } var seasonsMap = {}; rows.forEach(function (r) { seasonsMap[r.season] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); function buildRows(list, withLevel) { var groups = {}; list.forEach(function (r) { var key = r.position + (withLevel ? '|' + r.level : ''); if (!groups[key]) groups[key] = { pos: r.position, lvl: withLevel ? r.level : '', sportId: r.sportId, tot: {} }; fldAccumulate(groups[key].tot, r.stat); }); return Object.keys(groups).map(function (k) { return groups[k]; }) .sort(function (a, b) { var pa = POS_ORDER[a.pos] != null ? POS_ORDER[a.pos] : 99; var pb = POS_ORDER[b.pos] != null ? POS_ORDER[b.pos] : 99; return (pa - pb) || (a.sportId - b.sportId); }) .map(function (g) { return ' ' + esc(g.pos) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(fldTotalCells(g.tot)) + ' '; }).join(''); } function fldTable(rowsHTML) { return ' ' + theadHTML('Pos', FLD_COLS) + '' + rowsHTML + ' '; } function show(season) { var out = ''; if (season === 'ALL') { var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); if (mlb.length) out += 'MLB — Career Totals by Position' + fldTable(buildRows(mlb, false)); if (milb.length) out += 'Minor Leagues — Career Totals by Position' + fldTable(buildRows(milb, false)); body.innerHTML = out ? out + 'Career fielding totals by position (regular season). FLD% is recomputed from combined PO/A/TC. Pick a season above for the year-by-year breakdown.' : 'No fielding data available yet.'; } else { var yr = rows.filter(function (r) { return r.season === season; }); out = yr.length ? fldTable(buildRows(yr, true)) : ''; body.innerHTML = out ? out + '' + esc(season) + ' fielding by position; multiple teams at the same level are combined into one line.' : 'No fielding data for ' + esc(season) + '.'; } } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('ALL'); } // ---------------- GAME LOG UI (v2.4) ---------------- // Default chip: "Last N Games" across all levels of the most recent // season (most recent first, each date links to Gameday) plus a // totals row. Season chips show the full game log for that year. var GL_PIT_COLS = ['Dec','IP','H','R','ER','HR','BB','SO','P']; var GL_HIT_COLS = ['AB','R','H','2B','3B','HR','RBI','BB','SO','SB']; function glDecision(st) { if (n(st.wins)) return 'W'; if (n(st.losses)) return 'L'; if (n(st.saves)) return 'SV'; if (n(st.holds)) return 'HLD'; if (n(st.blownSaves)) return 'BS'; return ''; } function glTheadHTML(cols) { return ' Date Opp Lvl ' + cols.map(function (c) { return ' ' + c + ' '; }).join('') + ' '; } function glRowHTML(s, isPitching) { var st = s.stat || {}; var lvl = levelLabel(s._sportId, s.league && s.league.name); var opp = (s.opponent && (s.opponent.abbreviation || s.opponent.name)) || ''; var oppTxt = (s.isHome === false ? '@ ' : 'vs ') + opp; var pk = s.game && s.game.gamePk; var gd = pk ? (s._sportId === 1 ? 'https://www.mlb.com/gameday/' : 'https://www.milb.com/gameday/') + pk : ''; var dateCell = gd ? '' + esc(fmtDate(s.date)) + '' : esc(fmtDate(s.date)); var cells = isPitching ? [ glDecision(st), st.inningsPitched || '0.0', n(st.hits), n(st.runs), n(st.earnedRuns), n(st.homeRuns), n(st.baseOnBalls), n(st.strikeOuts), st.numberOfPitches != null ? n(st.numberOfPitches) : '--' ] : [ n(st.atBats), n(st.runs), n(st.hits), n(st.doubles), n(st.triples), n(st.homeRuns), n(st.rbi), n(st.baseOnBalls), n(st.strikeOuts), n(st.stolenBases) ]; return ' ' + dateCell + ' ' + ' ' + esc(oppTxt) + ' ' + ' ' + (lvl ? '' + esc(lvl) + '' : '') + ' ' + cellsHTML(cells) + ' '; } function glTotalRowHTML(list, isPitching, label) { var tot = {}, pitches = 0, hasPitches = false; list.forEach(function (s) { var st = s.stat || {}; (isPitching ? pitAccumulate : hitAccumulate)(tot, st); if (st.numberOfPitches != null) { pitches += n(st.numberOfPitches); hasPitches = true; } }); var cells, txt; if (isPitching) { txt = label + ' (' + era(n(tot.earnedRuns), n(tot.outs)) + ' ERA)'; cells = [ '', outsToIp(n(tot.outs)), n(tot.hits), n(tot.runs), n(tot.earnedRuns), n(tot.homeRuns), n(tot.baseOnBalls), n(tot.strikeOuts), hasPitches ? pitches : '--' ]; } else { txt = label + ' (' + fmtAvg(tot.atBats ? tot.hits / tot.atBats : NaN) + ' AVG)'; cells = [ n(tot.atBats), n(tot.runs), n(tot.hits), n(tot.doubles), n(tot.triples), n(tot.homeRuns), n(tot.rbi), n(tot.baseOnBalls), n(tot.strikeOuts), n(tot.stolenBases) ]; } return ' ' + esc(txt) + ' ' + cellsHTML(cells) + ' '; } function initGameLog(group, rows, isPitching) { var chips = document.getElementById('pp-gl-chips'); var body = document.getElementById('pp-gl-body'); if (!chips || !body) return; var seasonsMap = {}; rows.forEach(function (r) { if (r.sportId === 17) return; (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { chips.innerHTML = ''; body.innerHTML = 'No game log available.'; return; } var N = n(RECENT_GAMES); chips.innerHTML = 'Last ' + N + ' Games' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var cols = isPitching ? GL_PIT_COLS : GL_HIT_COLS; var cache = {}; function fetchSeason(season) { if (!cache[season]) cache[season] = loadGameLog(group, season, Object.keys(seasonsMap[season]).map(Number)); return cache[season]; } function tableHTMLFor(list, totalLabel) { return ' ' + glTheadHTML(cols) + '' + list.map(function (s) { return glRowHTML(s, isPitching); }).join('') + (list.length > 1 ? glTotalRowHTML(list, isPitching, totalLabel) : '') + ' '; } function show(key) { var recent = key === 'RECENT'; var season = recent ? seasons[0] : key; body.innerHTML = 'Loading ' + (recent ? 'recent games' : esc(season) + ' game log') + '…'; fetchSeason(season).then(function (all) { var list = recent ? all.slice(0, N) : all; if (!list.length) { body.innerHTML = 'No games on record for ' + esc(season) + '.'; return; } body.innerHTML = tableHTMLFor(list, recent ? 'Last ' + list.length : esc(season) + ' Total') + '' + (recent ? 'Most recent ' + list.length + ' games across all levels (' + esc(season) + '), newest first. ' : esc(season) + ' game log, all levels, newest first. ') + 'Dates link to the Gameday box score. Pick a season above for the full log.'; }).catch(function (e) { body.innerHTML = 'Game log could not load (' + esc(e && e.message) + ').'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('RECENT'); } })();
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
Tom Brennan - 10 Most Disappointing 2026 Mets Minor Leaguers; Lower Minors Success May Not Be Indicative of Future Success
   “HOW THE HECK DID THESE PROSPECTS DO SO POORLY?” Some guys in their Mets minors tutelage phase literally performed far below my (and others’) pre-season expectations for most if not all of the 2026 season.  When it comes to hitters… Climbing the minor league ladder is simply… Survival of the Hittest. Poor pitchers OTOH can and do cough up excessive bases on balls and HRs. That being said… Let’s consider my top 10 flops of 2026… - I add in where they landed in my Top 50 list a year ago, in parens: Ryan Lambert (2025 rank: # 17) - through September 13, an 8.00 ERA in 27 innings, with 30 walks and 4 hit batsmen. Handing out more freebies than Freddy Krueger of Halloween. I worried about him when I saw him throw a particularly bad outing in spring training, which I thought was jitters, but was more of a warning sign of things to come.  Last year, in A and AA, a stellar 1.62 ERA with 81 Ks in 50 innings, and prior to spring training, I hoped he would break camp with the Mets. Not even close. Ryan Clifford (2025 rank: # 6) - I was hopeful pre-season that he would improve over his decent 2025 that had him ranked as high as the Mets minor league prospect. Instead, his 2026 was kind of weak starting out, then collapsed in an heap after mid-May. Ks in incredible quantities. .178, with 170 Ks in 111 AAA games. I wrote the following in my ranking last year for Clifford, which he apparently did not read:  …to Clifford, I would say: ”OK, you’ve proved you can walk a lot, now ATTACK!”  Be aggressive. Less walks, higher average, more HRs. Essentially: From here on out, please be the next Nick Kurtz.  Attack.I bring up his need to ATTACK, because others are already inferring it, but not saying it directly.  Who are those “others”?  The people who put together Baseball Top 100 lists, who do not include Clifford. ATTACK! Colin Houck (2025 rank: # 42) - the former 32nd overall pick in 2023, Houck was horrific most of the year, strikeout-wise, but he finished 12 for his last 42, which might be an indicator of turnaround progress. He ended up hitting .212 in 99 High A games, with 154 Ks. He is well down the infield prospects list in the Mets system now, and needs to figure it out or exit stage right after 2027. Antonio Jimenez (2025 rank: # 22) - the 102nd overall pick in 2025, Jimenez hit an OK .247 while in low A St Lucie, but just .160 in 54 Brooklyn High A games. Daiverson Gutierrez (2025 rank: # 30) - he did skip a level from the FCL to High A Brooklyn, but hit just .198, due to a ghastly .155 average ON THE ROAD. I cut him slack, since he jumped over St. Lucie and I expect the just-turned 21 year old catcher to improve in 2027 at the plate. Jacob Reimer (2025 rank: # 7) - he substantially step things up up late in the season, but only got into 88 AA games. Prior to the season, I was certain he’d be promoted to AAA by midseason. He’s missed more than 40% of games over the past 3 seasons.  He was hitting .212 when he got hurt on June 17. He hit much better for average after he returned, but with diminished power. Not a complete wash out season, but a big disappointment, far below most everyone’s expectations. Brendan Girton (2025 rank: # 29) - in 16 relief outings and 15 starts in AA, he went just 1-4, 6.72, more than double his 2025 ERA of 3.10. Joel Diaz (2025 rank: # 40) - 0-9, 6.75 ERA, 1.89 WHIP? Ouch. He was somewhat better in the second half, but a very bad season pitching in pitcher-friendly Brooklyn. So, Girton and Diaz pitched in 50 games and went 1-13.  (Will Watson was 0-7, so that trio went 1-20.) Eli Serrano III (2025 rank: # 20) -  the 111th overall pick in 2024 came into 2026 ranked pretty highly (less highly by me) due to his perceived tools. Injuries came, and the lefty outfielder’s  season was abysmal. 265 at bats, and a .185 average renders him a suspect rather than a prospect. Career .209 hitter in 652 pro at bats is simply NG.   - Ask me anything more about Serrano III, and I will take the 5th. Boston Baro (2025 rank: # 24) - how could I be disappointed with a guy who hits .324 with a .395 OBP?  Being limited to 38 PAs due to his shoulder(?) injury, that’s how.   - If he gets 100% healthy next year, watch out. The talent is there. Any Mets minor league players that I did not list here that you felt should have made this Truly Troubled Ten List? When NO Mets minor league team makes the playoffs, trust me, there are > 10 Troubled Players in River City. DON’T GET TOO DANGED EXCITED BY LOWER MINORS STATS They may indicate future major league success… …or just the ability to succeed at lower minor league levels. Two past pitchers come to mind as examples: 1. Jaison Valera In 2016-18 in the low minors, Vilera tossed 193 innings, allowed just 131 hits, and was 13-4 with a 1.80 ERA. CANNOT MISS, RIGHT? Wrong. From 2019 -2022, he went 8-18, allowing 145 runs in 178 innings. So 2016-18 forecast nothing, really. 2. Mark Cohoon  He pitched in the Mets minors 2008-13. He was 9-2, 2.15 in Low A. He was 9-3, 1.97 in Full A.  - So far, so great.  But…he declined as opponents’ abilities inclined. He was 23-23, 3.86 in AA. He was 4-12, 6.77 in AAA. So his early seasons forecasted…well…nothing, really. Coming Soon… Keep An Eye Out For… My Top Ten Minor League Outperforming Delights in 2026. SAW THIS IN A FACEBOOK POST: Trevor Rogers on Pete Alonso: "He's one of the best teammates ever. ... It's probably the best second half performance I've ever seen from a hitter. He could very well be a Hall of Famer when it's all said and done. The fact that I played with him, it's special." Sentiments like that don’t show up in an Excel schedule. METS GAME 162 FAREWELL THEME SONG “I’m Going Home”, by 10 Years After. “The song became a massive cultural touchstone after the band performed an explosive, high-energy rendition of it at the Woodstock Festival on August 17, 1969.” The New York Mets won on August 17, 1969, by the way, defeating the San Diego Padres by a score of 3–2 at Shea Stadium. We Metsies these days, tho’, always head home after game 162, don’t we? FOR US…IT IS 40 YEARS AFTER. CLICK THE LINK BELOW FOR A ROUGHLY “60 YEARS AFTER” LISTEN! I’M GOING HOME - 10 YEARS After
010
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
Reese Kaplan -- More Thoughts on the 2027 Infield Shuffle
Open any online thread these days and there’s been nearly a quantum shift in fan attitude towards much beleaguered infielder Brett Baty.  To his credit he has shown defensive versatility playing in the outfield, 3rd base, 2nd base, 1st base and most recently at shortstop.  Yes, he did finish the 2026 season strongly wit the bat but the overall numbers are still rightly aligned wit the mediocrity he’s shown consistently since his first arrival to the major leagues in 2022.  The ending ledger gave him a .236 average with 11 HRs and 56 RBIs.  For the people advocating more Baty, note that with this mediocre .236 average his lifetime mark is just .233. Some folks who live on the good ship Optimism feel that a platoon of Jared Young and Brett Baty at first base is the best path forward.  More realistic Mets aficionados would be quick to point out that there is no significant track record for Young who had what appears to be an outlier positive year in 2026 while Baty provided more of the same below average offense.  Others point out the lackluster output the Mets received from one of many David Stearns mistakes in the acquisition of Marcus Semien and his $26 million salary.  For the season Semien provided just a .215 average along with 15 HRs and 55 RBIs while his once celebrated defensive skill seemed to decline significantly.  Still owed $46 million between the 2027 and 2028 seasons, you’re not likely going to be able to move him in trade except for an equally bad contract.  His release would mean a lot of Steven Cohen dollars flushed down the Stearns drain. Thinking about Baty at 2B does not solve that problem.  In fact, making Semien into the world’s most expensive bench player accomplishes very little offensively.  However, Baty has one thing in his profile that many others do not.  He still possesses a minor league option and could theoretically start the season in Syracuse due to roster crunch and minor league infielder ongoing development. On the flip side, a guy who is out of minor league options is younger but too often injured Ronny Mauricio.  In just 328 major league ABs Mauricio hit 11 HRs, drove in 27 and hit .232.  What he’s shown is more power and more speed than Baty has but he’s never been given the same playing opportunities.  Being a switch hitter he’s a bit more offensively versatile than is Baty and showcasing him early in the 2027 season lays the groundwork for a possible in-season trade.  His end of season three home runs in two days certainly caught everyone’s eyes. Behind him in the minors (and one in the majors) are four additional second base options.  The minor league ones are the most exciting but in all cases there has not been a substantial amount of AAA experience for any of them. At the top of the list is infielder Jefferson Rojas whose minor league stat sheet is fairly eye popping.  Split between three minor league stops and two organizations Rojas finished the year hitting .274 with 27 HRs, 93 RBIs and 21 stolen bases.   His 6 game tenure in Syracuse did not seem to intimidate him but it isn’t enough time to draw definitive conclusions.  Starting him in AAA allows the Mets to see how he handles the advanced competition while the 2B issue plays itself out for the big club. Second in this group is newcomer Emilien Pitre who while with the Mets hit a robust .375, finishing his combined 2026 season north of .300.  He doesn’t have a lot of power with just 15 HRs over 949 minor league ABs but that was accompanied by 56 stolen bases.  The lefty hitting infielder is a few years older than Rojas and played his final 26 games in Syracuse so he might be ready to make the jump sooner. A little further down this middle infielder hierarchy is speedster Mitch Voit.  He swiped 45 bases between A and AA this past season while hitting .273 with 13 HRs and driving in 59.  He would seem well suited to continue his minor league progression with an eye towards a possible major league debut in 2028.  Finally there is still the question surrounding A.J. Ewing who also has logged significant minor league playing time at 2B.  If the Mets were to insert another outfielder to accompany Juan Soto and Carson Benge then they would need to find a place for Ewing to play.  Second base could be it.
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
Around the Majors with Mets News and Links - 9/30/2026
Here are the top Stories from every Major League team courtesy from our friends at SportSpyder. Note - this page updates throughout the day - come back later today for the latest news.
000
John From Albany @johnfromalbany.bsky.social · 30/09/2026
dlvr.it
SNY on YouTube: Point/Counterpoint: Should Mets try to sign Tarik Skubal in the offseason? | Baseball Night in NY - 9/29/26
Name Email * Message *
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Press Release: Museum’s Autumn Glory Exhibit Receives Refresh Heading into Postseason Play
Sept. 29, 2026 -- Stories of More than a Century of Historic Moments told in Cooperstown -- (COOPERSTOWN, NY) – As the 2026 Major League Baseball Postseason gets underway, the National Baseball Hall of Fame and Museum brings the stories of the game’s most memorable moments to life in an exciting new fashion. The Autumn Glory exhibit, located on the Museum’s third floor, has been refreshed with new artifacts, documents and photos that tell the story of the modern World Series – starting in 1903 – as well as pre-World Series era champions, Championship and Division Series moments and title-series history from additional leagues. Artifacts now on display in Autumn Glory at the Museum include: The last-out ball from the 1986 World Series, signed by Gary Carter and Jesse Orosco of the World Champion Mets Trophy presented to the Homestead Grays, the 1940 champions of the Negro National League One half of the jersey literally torn off Cardinals third baseman David Freese after he clouted his walk-off home run in Game 6 of the 2011 World Series Shoes worn by Freddie Freeman in Game 1 of the 2024 World Series when the Dodgers’ first baseman hit the Fall Classic’s first walk-off grand slam The last-out ball from the 2004 World Series when the Red Sox won their first title in 86 years A ball thrown by Yankees pitcher Don Larsen during his perfect game in Game 5 of the 1956 World Series A jersey worn during the final game of the 2017 Little League World Series by catcher Seiya Arai of the championship-winning team from Japan A ball thrown by Boston pitcher Bill Dinneen for the last out of the first modern World Series in 1903 The Autumn Glory exhibit will be updated again following the completion of the World Series with artifacts from the 2026 Postseason. Admission to the Museum’s Autumn Glory is included with regular Museum admission. For more information on Museum exhibits, please click here . The National Baseball Hall of Fame and Museum is open seven days a week year round, with the exception of Thanksgiving, Christmas and New Year’s Day. From Labor Day through the start of Memorial Day Weekend, the Museum observes daily regular hours of 9 a.m. until 5 p.m. Ticket prices are $35 for adults (13 and over), $29 for seniors (65 and over) and $26 for juniors (ages 7-12) and $25 for those holding current memberships in the VFW, Disabled American Veterans, American Legion and AMVets organizations. Members are always admitted free of charge and there is no charge for children 6 years of age or younger. This institution is an equal opportunity provider. For more information, visit our website at baseballhall.org or call 888-HALL-OF-FAME (888-425-5633) or 607-547-7200.
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Examining the high point in OPS for each Mets hitter with at least 200 PA
Throughout the year, we look at the numbers and try to make sense of them the best we can. Click Link Below to Read Article. http://dlvr.it/TVhpbj
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
MACK – Let’s Revisit - C - Ronald Hernandez
 
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Arizona Fall Mets Prospect Profile: Infielder Boston Baro
  Boston Baro, photo courtesy of milb.com Limited to 11 games in 2026 due to a shoulder injury in March and a later quad injury, Boston Baro is heading to the Arizona Fall League to make up for lost time. Drafted by the Mets in the 8th round of the 2023 Draft and signing to a $700K bonus to keep him out of a commitment to UCLA, Boston Baro had a solid year for the St. Lucie Mets in 2024 slashing .288/.368/.399 with 42 steals in 84 games. After being the youngest player on Brooklyn's opening day roster in 2025, Boston got off to a slow start but seemed to start to figure things out in July and August only to miss the balance of the season with a hamstring injury on August 27th.    Placed on the 60-day IL with a right shoulder injury to start the 2026 season, he played two rehab games in May for the FCL Mets before suffering a quad injury that kept him out of action until late August where he played 9 games for St. Lucie. Per the Brooklyn Cyclones August 27, 2025 Game Notes: In 2025 - "Ranked as the Mets' No. 19 prospect by MLB Pipeline and No. 15 by Baseball America...Entered 2025 as the Mets' No. 15 farmhand by BA and No. 17 in their first re-rank...No. 25 and No. 23, respectively, in 2024...Entered 2025 as MLB Pipeline's No. 14 Mets' farmhand." Baro's lack of playing time in 2026 coupled with an influx of prospects to the Mets system at the 2026 trade deadline, pushed him off the Top 30 Mets Prospect lists.   Baseball America says that Baro has a "a picturesque lefthanded swing" but project him to be a left handed super utility player.  They have his Scouting Grades as Hit: 50 | Power: 30 | Run: 55 | Field: 50 | Arm: 55.   Hopefully he can stay healthy this Fall and get back to advancing up the Mets Minor League system next year. Loading player profile… #pp-widget { max-width: 820px; margin: 0 auto; font-family: 'Barlow Condensed', -apple-system, 'Segoe UI', Arial, sans-serif; color: #1a1a1a; } #pp-widget * { box-sizing: border-box; } #pp-widget .pp-loading { text-align: center; padding: 30px; color: #6c757d; font-size: 18px; } #pp-widget .pp-card { background: #fff; border-radius: 12px; box-shadow: 0 2px 8px rgba(0,0,0,0.12); overflow: hidden; margin-bottom: 20px; } /* header */ #pp-widget .pp-header { background: linear-gradient(135deg, #002D72 0%, #FF5910 100%); color: #fff; padding: 22px; } #pp-widget .pp-head-row { display: flex; align-items: center; gap: 18px; margin-bottom: 14px; flex-wrap: wrap; } #pp-widget .pp-headshot { width: 92px; height: 92px; border-radius: 50%; border: 3px solid #fff; background: #fff; object-fit: cover; flex-shrink: 0; } #pp-widget .pp-number { font-size: 44px; font-weight: 700; opacity: 0.9; } #pp-widget .pp-name h1 { font-size: 34px; margin: 0 0 2px 0; line-height: 1.1; color: #fff; } #pp-widget .pp-pos { font-size: 18px; opacity: 0.92; } #pp-widget .pp-bio { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 10px; font-size: 15px; } #pp-widget .pp-bio-item { background: rgba(255,255,255,0.14); padding: 7px 11px; border-radius: 6px; } #pp-widget .pp-bio-label { opacity: 0.82; font-size: 12px; text-transform: uppercase; letter-spacing: 0.5px; margin-bottom: 1px; } /* jump nav */ #pp-widget .pp-nav { display: flex; gap: 8px; flex-wrap: wrap; padding: 10px 22px; background: #f8f9fa; border-bottom: 1px solid #e9ecef; } #pp-widget .pp-nav a { color: #002D72; font-weight: 600; text-decoration: none; font-size: 15px; padding: 4px 10px; border-radius: 14px; border: 1px solid #d7dbe0; background: #fff; } #pp-widget .pp-nav a:hover { background: #002D72; color: #fff; } /* sections */ #pp-widget .pp-section { padding: 20px 22px; } #pp-widget .pp-title { font-size: 22px; font-weight: 700; color: #002D72; margin: 0 0 12px 0; padding-bottom: 6px; border-bottom: 2px solid #FF5910; } #pp-widget .pp-sub { font-size: 17px; font-weight: 700; color: #002D72; margin: 16px 0 6px 0; } #pp-widget .pp-note { font-size: 13px; color: #6c757d; margin: 6px 0 0 0; } #pp-widget .pp-empty { font-size: 15px; color: #6c757d; padding: 8px 0; } /* quick stat boxes */ #pp-widget .pp-quick { display: grid; grid-template-columns: repeat(auto-fit, minmax(88px, 1fr)); gap: 12px; margin-bottom: 8px; } #pp-widget .pp-qbox { text-align: center; padding: 12px 6px; background: #f8f9fa; border: 1px solid #e9ecef; border-radius: 8px; } #pp-widget .pp-qval { font-size: 26px; font-weight: 700; color: #002D72; } #pp-widget .pp-qlbl { font-size: 12px; color: #6c757d; text-transform: uppercase; letter-spacing: 0.5px; } /* tables */ #pp-widget .pp-twrap { overflow-x: auto; -webkit-overflow-scrolling: touch; } #pp-widget table.pp-table { width: 100%; border-collapse: collapse; margin-bottom: 6px; } #pp-widget table.pp-table th { background: #002D72; color: #fff; padding: 9px 6px; text-align: center; font-size: 12px; font-weight: 600; text-transform: uppercase; white-space: nowrap; } #pp-widget table.pp-table td { padding: 8px 6px; text-align: center; border-bottom: 1px solid #e9ecef; font-size: 14px; white-space: nowrap; } #pp-widget table.pp-table tr:hover td { background: #f8f9fa; } #pp-widget td.pp-left, #pp-widget th.pp-left { text-align: left; } #pp-widget .pp-yr { font-weight: 600; color: #002D72; } #pp-widget .pp-lvl { display: inline-block; background: #002D72; color: #fff; border-radius: 10px; font-size: 11px; font-weight: 700; padding: 1px 8px; margin-left: 6px; vertical-align: 1px; } #pp-widget tr.pp-total td { font-weight: 700; background: #fff4ee; border-top: 2px solid #FF5910; } #pp-widget tr.pp-career td { font-weight: 700; background: #eaf0fa; border-top: 2px solid #002D72; } /* v2.4: repeated header rows inside long tables */ #pp-widget table.pp-table tr.pp-rehead th { border-top: 2px solid #FF5910; } #pp-widget td.pp-lnk a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget td.pp-lnk a:hover { text-decoration: underline; } /* splits + fielding + game log season chips */ #pp-widget .pp-chips { display: flex; gap: 6px; flex-wrap: wrap; margin-bottom: 10px; } #pp-widget .pp-chip { border: 1px solid #002D72; color: #002D72; background: #fff; border-radius: 14px; padding: 3px 12px; font-size: 14px; font-weight: 600; cursor: pointer; font-family: inherit; } #pp-widget .pp-chip.pp-on { background: #002D72; color: #fff; } /* videos */ #pp-widget .pp-vids { display: grid; grid-template-columns: repeat(auto-fill, minmax(230px, 1fr)); gap: 14px; } #pp-widget .pp-vcard { border: 1px solid #e9ecef; border-radius: 8px; overflow: hidden; background: #fff; } #pp-widget .pp-vcard-x { grid-column: 1 / -1; max-width: 560px; } #pp-widget .pp-vcard-x blockquote { margin: 0 auto; } #pp-widget .pp-vthumb { position: relative; cursor: pointer; background: #000; } #pp-widget .pp-vthumb img { width: 100%; display: block; aspect-ratio: 16/9; object-fit: cover; } #pp-widget .pp-vplay { position: absolute; top: 50%; left: 50%; transform: translate(-50%,-50%); width: 44px; height: 44px; border-radius: 50%; background: rgba(0,45,114,0.85); color: #fff; display: flex; align-items: center; justify-content: center; font-size: 18px; pointer-events: none; } #pp-widget .pp-vdur { position: absolute; right: 6px; bottom: 6px; background: rgba(0,0,0,0.75); color: #fff; font-size: 11px; padding: 1px 6px; border-radius: 3px; } #pp-widget .pp-vbody { padding: 8px 10px 10px 10px; } #pp-widget .pp-vtitle { font-size: 14px; font-weight: 600; line-height: 1.25; color: #1a1a1a; margin-bottom: 4px; } #pp-widget .pp-vmeta { font-size: 12px; color: #6c757d; display: flex; justify-content: space-between; } #pp-widget .pp-vmeta a { color: #002D72; font-weight: 600; text-decoration: none; } #pp-widget .pp-vcard video { width: 100%; display: block; aspect-ratio: 16/9; background: #000; } #pp-widget .pp-vlink { display: block; background: #002D72; color: #fff; text-align: center; padding: 34px 10px; font-weight: 700; text-decoration: none; } /* footer */ #pp-widget .pp-footer { padding: 12px 22px; background: #f8f9fa; text-align: center; font-size: 12px; color: #6c757d; } #pp-widget .pp-footer a { color: #002D72; font-weight: 600; text-decoration: none; } @media (max-width: 600px) { #pp-widget .pp-header { padding: 15px; } #pp-widget .pp-name h1 { font-size: 26px; } #pp-widget .pp-number { font-size: 34px; } #pp-widget .pp-section { padding: 15px 12px; } #pp-widget table.pp-table th, #pp-widget table.pp-table td { padding: 6px 4px; font-size: 12px; } } (function () { // ================= CONFIG - EDIT THIS ================= var PLAYER_ID = 805951; // { code: totals }. // Tries the Stats API careerStatSplits call first; if nothing comes // back, sums every season's statSplits for that level instead. function loadCareerSplits(group, sportId, seasons, accF) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=careerStatSplits&group=' + group + '&sportId=' + sportId + '&sitCodes=' + SIT_CODE_STR) .then(function (d) { return splitsOf(d); }) .catch(function () { return []; }) .then(function (sp) { var direct = sumByCode(sp, accF, true); if (Object.keys(direct).length) return direct; return Promise.all(seasons.map(function (yr) { return loadSplits(group, yr, [sportId]); })) .then(function (arrs) { var out = {}; arrs.forEach(function (list) { var yrTot = sumByCode(list, accF, false); Object.keys(yrTot).forEach(function (c) { out[c] = addTot(out[c] || {}, yrTot[c]); }); }); return out; }); }); } var MONTH_NAMES = ['','January','February','March','April','May','June','July','August','September','October','November','December']; function loadMonthly(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=byMonth&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return (n(a.month) - n(b.month)) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: GAME LOG (v2.4) ---------------- function loadGameLog(group, season, sportIds) { return Promise.all(sportIds.map(function (sid) { return jget(API + '/people/' + PLAYER_ID + '/stats?stats=gameLog&group=' + group + '&season=' + season + '&sportId=' + sid) .then(function (d) { return splitsOf(d).map(function (s) { s._sportId = sid; return s; }); }) .catch(function () { return []; }); })).then(function (arrs) { var out = []; arrs.forEach(function (a) { a.forEach(function (s) { out.push(s); }); }); out.sort(function (a, b) { return String(b.date || '').localeCompare(String(a.date || '')) || (b._sportId - a._sportId); }); return out; }); } // ---------------- FETCH: PITCH ARSENAL / VELO (v2.4) ---------------- // Only levels with pitch tracking: MLB (1), AAA (11), Low-A (14). var PITCH_SPORT_IDS = [1, 11, 14]; function loadPitchData(season) { return Promise.all(PITCH_SPORT_IDS.map(function (sid) { var ars = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchArsenal&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); var log = jget(API + '/people/' + PLAYER_ID + '/stats?stats=pitchLog&group=pitching&season=' + season + '&sportId=' + sid) .then(splitsOf).catch(function () { return []; }); return Promise.all([ars, log]).then(function (r) { return { sportId: sid, arsenal: r[0], log: r[1] }; }); })); } // ---------------- FETCH: TRANSACTIONS ---------------- function loadTransactions() { var end = new Date().toISOString().slice(0,10); return jget(API + '/transactions?playerId=' + PLAYER_ID + '&startDate=2010-01-01&endDate=' + end) .then(function (d) { var tx = (d.transactions || []).slice(); tx.sort(function (a, b) { return String(b.date).localeCompare(String(a.date)); }); return tx.slice(0, TX_MAX); }) .catch(function () { return []; }); } // ---------------- FETCH: FILM ROOM VIDEOS ---------------- var GQL = 'query Search($query: String!, $page: Int, $limit: Int, $feedPreference: FeedPreference, ' + '$languagePreference: LanguagePreference, $contentPreference: ContentPreference, $queryType: QueryType = STRUCTURED) {\n' + ' search(query: $query, limit: $limit, page: $page, feedPreference: $feedPreference, ' + 'languagePreference: $languagePreference, contentPreference: $contentPreference, queryType: $queryType) {\n' + ' plays {\n mediaPlayback {\n slug\n title\n blurb\n date\n' + ' feeds {\n type\n duration\n' + ' image { cuts { width src } }\n' + ' playbacks { name url }\n }\n }\n }\n }\n}'; function gqlVars(queryStr, limit) { return { queryType: null, query: queryStr, limit: limit || VIDEO_LIMIT, page: 0, languagePreference: 'EN', contentPreference: 'CMS_FIRST' }; } function videoSearchUrl(queryStr, limit) { return 'https://fastball-gateway.mlb.com/graphql' + '?query=' + encodeURIComponent(GQL) + '&operationName=Search' + '&variables=' + encodeURIComponent(JSON.stringify(gqlVars(queryStr, limit))); } function proxyPlayerUrl(person) { var teamId = (person && person.currentTeam && person.currentTeam.id) || ''; var last = (person && (person.lastName || (person.fullName || '').split(' ').pop())) || ''; return PROXY_URL + '?player=' + PLAYER_ID + '&team=' + teamId + '&name=' + encodeURIComponent(last) + '&limit=' + VIDEO_LIMIT; } var ppJsonpCount = 0; function jsonpCall(baseUrl) { return new Promise(function (resolve, reject) { var cb = 'ppVidCb' + (++ppJsonpCount); var s = document.createElement('script'); var timer = setTimeout(function () { cleanup(); reject(new Error('proxy timeout')); }, 30000); function cleanup() { clearTimeout(timer); try { delete window[cb]; } catch (e) { window[cb] = undefined; } if (s.parentNode) s.parentNode.removeChild(s); } window[cb] = function (data) { cleanup(); resolve(data); }; s.onerror = function () { cleanup(); reject(new Error('proxy load error')); }; s.src = baseUrl + '&callback=' + cb; document.head.appendChild(s); }); } function proxyJson(baseUrl) { return fetch(baseUrl).then(function (r) { if (!r.ok) throw new Error('proxy HTTP ' + r.status); return r.json(); }); } function gqlPost(queryStr, limit) { return fetch('https://fastball-gateway.mlb.com/graphql', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ query: GQL, operationName: 'Search', variables: gqlVars(queryStr, limit) }) }).then(function (r) { if (!r.ok) throw new Error('HTTP ' + r.status + ' (POST)'); return r.json(); }); } function gqlFetch(queryStr, limit) { return jget(videoSearchUrl(queryStr, limit)) .catch(function () { return gqlPost(queryStr, limit); }); } function fmtDur(sec) { if (sec == null || sec === '') return ''; if (typeof sec === 'string' && sec.indexOf(':') > -1) return sec.replace(/^00:0?/, ''); var x = parseInt(sec, 10); if (isNaN(x)) return ''; return Math.floor(x / 60) + ':' + ('0' + (x % 60)).slice(-2); } function pickPlayback(feeds) { if (!feeds || !feeds.length) return { mp4: null, thumb: '', dur: '' }; var ranked = feeds.slice().sort(function (a, b) { return ((a.type === 'CMS') ? 0 : 1) - ((b.type === 'CMS') ? 0 : 1); }); var mp4 = null, thumb = '', dur = ''; for (var i = 0; i < ranked.length; i++) { var f = ranked[i]; if (!dur && f.duration) dur = fmtDur(f.duration); if (!thumb && f.image && f.image.cuts && f.image.cuts.length) { var cuts = f.image.cuts.slice().sort(function (a, b) { return (b.width||0) - (a.width||0); }); var mid = cuts.filter(function (c) { return c.width && c.width 1) { html += ' ' + esc(yr) + ' ' + esc(opts.totalLabel) + ' ' + cellsHTML(totF(yrTot)) + ' '; } // v2.4: repeat the column header row every HEADER_REPEAT seasons if (n(HEADER_REPEAT) > 0 && (si + 1) % n(HEADER_REPEAT) === 0 && si < seasons.length - 1) { html += headRowHTML('Year / Team', cols, 'pp-rehead'); } }); if (seasons.length) { html += ' ' + esc(opts.careerLabel) + ' ' + cellsHTML(totF(career)) + ' '; } return html ? tableHTML(opts.id, 'Year / Team', cols, html) : ''; } // ---------------- MAIN ---------------- loadPerson().then(function (person) { if (!person) { root.innerHTML = 'Player not found for ID ' + PLAYER_ID + '.'; return; } return Promise.all([ loadYearByYear('hitting'), loadYearByYear('pitching'), loadYearByYear('fielding'), loadTransactions(), loadVideos(person), loadJersey(person) ]) .then(function (res) { render(person, res[5], res[0], res[1], res[2], res[3], res[4]); }); }) .catch(function (e) { root.innerHTML = 'Could not load profile (' + esc(e.message) + '). Please refresh.'; }); function render(person, jersey, hitRows, pitRows, fldRows, txs, vids) { var isPitcher = person.primaryPosition && person.primaryPosition.code === '1'; var hasHit = hitRows.some(function (r) { return n(r.stat.atBats) || n(r.stat.plateAppearances); }); var hasPit = pitRows.some(function (r) { return ipToOuts(r.stat.inningsPitched) || n(r.stat.gamesPlayed); }); var usePit = isPitcher && hasPit; var showPitches = usePit && SHOW_PITCHES; var showGameLog = n(RECENT_GAMES) > 0 && (hasPit || hasHit); var headshot = 'https://img.mlbstatic.com/mlb-photos/image/upload/d_people:generic:headshot:67:current.png' + '/w_180,q_auto:best/v1/people/' + PLAYER_ID + '/headshot/milb/current'; var birth = [person.birthCity, person.birthStateProvince, person.birthCountry].filter(Boolean).join(', '); var teamName = (person.currentTeam && person.currentTeam.name) || 'New York Mets Organization'; var h = ''; // ---- header ---- h += '' + '' + (jersey ? '#' + esc(jersey) + '' : '') + ' ' + esc(person.fullName) + ' ' + '' + esc((person.primaryPosition && person.primaryPosition.name) || '') + ' • ' + esc(teamName) + '' + '' + 'Full Name' + esc(person.fullFMLName || person.fullName) + '' + 'Bats/Throws' + esc(((person.batSide||{}).code||'') + '/' + ((person.pitchHand||{}).code||'')) + '' + 'Height/Weight' + esc((person.height||'') + ' / ' + (person.weight ? person.weight + ' lbs' : '')) + '' + 'Born' + esc(fmtDate(person.birthDate) + (person.currentAge ? ' (Age ' + person.currentAge + ')' : '')) + '' + (birth ? 'Birthplace' + esc(birth) + '' : '') + (HOW_ACQUIRED ? 'How Acquired' + esc(HOW_ACQUIRED) + '' : '') + EXTRA_BOXES.map(function (b) { if (!b || !b.value) return ''; return '' + esc(b.label || '') + '' + esc(b.value) + ''; }).join('') + ''; // ---- jump nav ---- h += 'Stats' + (showPitches ? 'Pitches' : '') + 'Splits' + 'Fielding' + (showGameLog ? 'Game Log' : '') + 'VideosTransactions'; // ---- stats ---- h += ' Statistics '; var groups = []; if (isPitcher) { if (hasPit) groups.push('P'); if (hasHit) groups.push('H'); } else { if (hasHit) groups.push('H'); if (hasPit) groups.push('P'); } if (!groups.length) h += 'No stats available yet.'; groups.forEach(function (g) { var rows = (g === 'H') ? hitRows : pitRows; var isP = (g === 'P'); var gLbl = isP ? 'Pitching' : 'Hitting'; var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); var winter = rows.filter(function (r) { return r.sportId === 17; }); var mlbT = buildStatsTable(mlb, isP, { id: 'pp-mlb-' + g, totalLabel: 'MLB Total', careerLabel: 'MLB Career' }); var milbT = buildStatsTable(milb, isP, { id: 'pp-milb-' + g, totalLabel: 'MiLB Total', careerLabel: 'MiLB Career', rates: !isP }); var winterT = buildStatsTable(winter, isP, { id: 'pp-winter-' + g, totalLabel: 'Total', careerLabel: 'Winter/AFL Career' }); if (mlbT) h += 'MLB ' + gLbl + '' + mlbT; if (milbT) h += 'Minor League ' + gLbl + '' + milbT; if (winterT) h += 'Winter Ball / AFL ' + gLbl + '' + winterT; }); h += ''; // ---- pitch arsenal (v2.4, pitchers only) ---- if (showPitches) { h += ' Pitch Arsenal ' + 'Loading pitch data…'; } // ---- splits ---- h += ' Splits ' + 'Loading splits…'; // ---- fielding (v2.3) ---- h += ' Fielding ' + 'Loading fielding…'; // ---- game log (v2.4) ---- if (showGameLog) { h += ' Game Log ' + 'Loading game log…'; } // ---- videos ---- h += ' Video Highlights '; var autoVids = vids.list || []; var hasAny = MANUAL_VIDEOS.length || autoVids.length; var hasXPost = false; if (hasAny) { h += ''; MANUAL_VIDEOS.forEach(function (v) { var yt = ytEmbedUrl(v.url); var xp = xPostUrl(v.url); if (xp) { hasXPost = true; h += '' + '' + '' + esc(v.title || 'View post on X') + '' + '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + 'View on X'; return; } h += ''; if (yt) { h += ''; } else if (/\.mp4(\?|$)/i.test(v.url || '')) { h += ''; } else if (isMlbVideoUrl(v.url)) { var mlbEmb = mlbEmbedUrl(v.url); if (mlbEmb) { h += ''; } else { h += '► Watch on MLB.com'; } } else { h += '► Watch Video'; } h += '' + esc(v.title || 'Video') + '' + '' + esc(fmtDate(v.date)) + '' + (isMlbVideoUrl(v.url) ? 'View on MLB.com' : '') + ''; }); autoVids.forEach(function (v, i) { h += '' + '' + (v.thumb ? '' : '') + '►' + (v.dur ? '' + esc(v.dur) + '' : '') + '' + esc(v.title) + '' + '' + esc(fmtDate(v.date)) + '' + 'Watch on MiLB.com' + ''; }); h += ''; if (autoVids.length) { h += 'Auto-updated from MLB Film Room. Full library: ' + 'milb.com/video/topic/playerid-' + PLAYER_ID + ''; } } if (!autoVids.length && !MANUAL_VIDEOS.length) { h += '' + (vids.error ? 'The automatic video feed could not load (' + esc(vids.error) + '). ' + 'If this keeps happening, set PROXY_URL in the config to your Apps Script passthrough. ' : 'No clips found in the Film Room index for this player yet. ') + 'Full library: MiLB.com.'; } else if (!autoVids.length && vids.error) { h += 'The automatic video feed could not load (' + esc(vids.error) + ').'; } h += ''; // ---- transactions ---- h += ' Transactions '; if (txs.length) { var trows = ''; txs.forEach(function (t) { trows += ' ' + esc(fmtDate(t.date)) + ' ' + ' ' + esc(t.typeDesc || '') + ' ' + ' ' + esc(t.description || '') + ' '; }); h += ' Date Type Transaction ' + trows + ' '; } else { h += 'No transactions on record.'; } h += ''; // ---- footer ---- h += 'Stats & transactions from the MLB Stats API • Videos from MLB Film Room • ' + 'MiLB.com Player Page • ' + 'MLB.com Player Page' + ''; root.innerHTML = h; if (hasXPost) loadXWidgets(); // ---- header stat boxes (v2.4: separate MLB / MiLB rows) ---- buildQuickStats(usePit ? pitRows : hitRows, usePit); // ---- video inline playback ---- root.querySelectorAll('.pp-vthumb').forEach(function (el) { el.addEventListener('click', function () { var mp4 = el.getAttribute('data-mp4'); if (!mp4) { var link = el.getAttribute('data-link'); if (link) window.open(link, '_blank'); return; } var v = document.createElement('video'); v.controls = true; v.autoplay = true; v.src = mp4; v.setAttribute('playsinline',''); el.parentNode.replaceChild(v, el); }); }); var group = usePit ? 'pitching' : 'hitting'; var groupRows = usePit ? pitRows : hitRows; if (showPitches) initPitches(pitRows); initSplits(group, groupRows, usePit); initFielding(fldRows); if (showGameLog) initGameLog(group, groupRows, usePit); } // ---------------- HEADER STAT BOXES (v2.4) ---------------- // One row of boxes per HEADER_STATS entry ('MLB' / 'MiLB') for the // player's most recent season. A row is skipped if the player has // no stats at that level in that season. function buildQuickStats(rows, isPitching) { var box = document.getElementById('pp-quick'); if (!box || !rows.length || !HEADER_STATS || !HEADER_STATS.length) return; var reg = rows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) return; var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); var yr = reg.filter(function (r) { return r.season === latest; }); var accF = isPitching ? pitAccumulate : hitAccumulate; var html = ''; HEADER_STATS.forEach(function (lvlKey) { var isMlb = /^mlb$/i.test(String(lvlKey)); var list = yr.filter(function (r) { return isMlb ? r.sportId === 1 : isMilbSport(r.sportId); }); if (!list.length) return; var tot = {}; list.forEach(function (r) { accF(tot, r.stat); }); var items; if (isPitching) { items = [ [n(tot.wins) + '-' + n(tot.losses), 'W-L'], [era(n(tot.earnedRuns), n(tot.outs)), 'ERA'], [outsToIp(n(tot.outs)), 'IP'], [n(tot.strikeOuts), 'SO'], [whip(n(tot.baseOnBalls), n(tot.hits), n(tot.outs)), 'WHIP'] ]; } else { var c = hitTotalCells(tot, false); // [G,AB,R,H,2B,3B,HR,RBI,SB,BB,SO,AVG,OBP,SLG,OPS] items = [ [c[11], 'AVG'], [c[6], 'HR'], [c[7], 'RBI'], [c[8], 'SB'], [c[14], 'OPS'] ]; } html += '' + (isMlb ? 'MLB ' : 'MiLB ') + esc(latest) + ' Stats' + items.map(function (it) { return '' + esc(it[0]) + '' + esc(it[1]) + ''; }).join('') + ''; }); box.innerHTML = html; } // ---------------- PITCH ARSENAL UI (v2.4) ---------------- var PITCH_COLS = ['Usage','Avg MPH','Top MPH','Pitches']; function initPitches(pitRows) { var body = document.getElementById('pp-pitch-body'); var title = document.getElementById('pp-pitch-title'); if (!body) return; var reg = pitRows.filter(function (r) { return r.sportId !== 17; }); if (!reg.length) { body.innerHTML = 'No pitch data available.'; return; } var latest = reg.reduce(function (m, r) { return r.season > m ? r.season : m; }, '0'); if (title) title.innerHTML = 'Pitch Arsenal — ' + esc(latest); loadPitchData(latest).then(function (res) { var out = ''; res.forEach(function (r) { var map = {}; function slot(code, desc) { return map[code] = map[code] || { code: code, desc: desc || code, usage: null, avg: null, max: null, count: 0, sum: 0, cnt: 0 }; } (r.arsenal || []).forEach(function (s) { var st = s.stat || {}; var t = st.type || {}; var code = t.code || t.description; if (!code) return; var m = slot(code, t.description); var p = Number(st.percentage); if (!isNaN(p) && st.percentage != null) m.usage = p m.max) m.max = v; m.sum += v; m.cnt++; }); var list = Object.keys(map).map(function (k) { return map[k]; }); if (!list.length) return; list.forEach(function (m) { if (m.avg == null && m.cnt) m.avg = m.sum / m.cnt; if (!m.count && m.cnt) m.count = m.cnt; }); var totalCnt = list.reduce(function (a, m) { return a + n(m.count); }, 0); list.forEach(function (m) { if (m.usage == null && totalCnt) m.usage = 100 * n(m.count) / totalCnt; }); list.sort(function (a, b) { return (n(b.usage)) - (n(a.usage)); }); var rowsHtml = list.map(function (m) { return ' ' + esc(m.desc) + ' ' + cellsHTML([ m.usage != null ? m.usage.toFixed(1) + '%' : '--', m.avg != null ? m.avg.toFixed(1) : '--', m.max != null ? m.max.toFixed(1) : '--', m.count || '--' ]) + ' '; }).join(''); out += '' + esc(levelLabel(r.sportId, '')) + '' + ' ' + theadHTML('Pitch', PITCH_COLS) + '' + rowsHtml + ' '; }); body.innerHTML = out ? out + '' + esc(latest) + ' pitch tracking by level (MLB, AAA and Low-A only). Usage and average velocity from the MLB Stats API pitch arsenal; top velocity is the hardest tracked pitch of that type in the pitch log.' : 'No pitch-tracking data returned for ' + esc(latest) + ' (available for MLB, AAA and Low-A only).'; }).catch(function (e) { body.innerHTML = 'Pitch data could not load (' + esc(e && e.message) + ').'; }); } // ---------------- SPLITS UI (v2.4: career + season chips) ---------------- // v2.4.1: pitching splits use PIT_SPLIT_COLS / pitSplitTotalCells. function initSplits(group, rows, isPitching) { var chips = document.getElementById('pp-split-chips'); var body = document.getElementById('pp-split-body'); if (!chips || !body) return; var seasonsMap = {}, sidsAll = {}; rows.forEach(function (r) { if (r.sportId === 17) return; // winter splits not indexed the same way (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; sidsAll[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { body.innerHTML = 'No splits available.'; return; } chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var defs = isPitching ? SIT_CODES_PIT : SIT_CODES; var sCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS; var accF = isPitching ? pitAccumulate : hitAccumulate; var totF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, false); }; var careerCache = null; // ---- career view: MLB table + Minor Leagues table ---- function showCareer() { body.innerHTML = 'Loading career splits…'; if (!careerCache) { var sids = Object.keys(sidsAll).map(Number); careerCache = Promise.all(sids.map(function (sid) { var yrs = seasons.filter(function (s) { return seasonsMap[s][sid]; }); return loadCareerSplits(group, sid, yrs, accF).then(function (byCode) { return { sportId: sid, byCode: byCode }; }); })); } careerCache.then(function (res) { function tableFor(filterFn) { var html = ''; defs.forEach(function (def) { var tot = {}, any = false; res.filter(filterFn).forEach(function (r) { if (r.byCode[def.code]) { addTot(tot, r.byCode[def.code]); any = true; } }); if (any) html += ' ' + esc(def.label) + ' ' + cellsHTML(totF(tot)) + ' '; }); return html ? ' ' + theadHTML('Split', sCols) + '' + html + ' ' : ''; } var mlbT = tableFor(function (r) { return r.sportId === 1; }); var milbT = tableFor(function (r) { return isMilbSport(r.sportId); }); var out = ''; if (mlbT) out += 'MLB — Career Splits' + mlbT; if (milbT) out += 'Minor Leagues — Career Splits' + milbT; body.innerHTML = out ? out + 'Career splits (regular season). Minor league line combines every MiLB level. Rate stats are recomputed from the summed raw counts. Pick a season above for the year-by-year, per-level breakdown.' : 'No career split data available.'; }).catch(function (e) { body.innerHTML = 'Career splits could not load (' + esc(e && e.message) + ').'; }); } // ---- season view: per-level splits + By Month (unchanged from v2.3.1) ---- function showSeason(season) { body.innerHTML = 'Loading ' + esc(season) + ' splits…'; var sportIds = Object.keys(seasonsMap[season]).map(Number); Promise.all([ loadSplits(group, season, sportIds), loadMonthly(group, season, sportIds) ]) .then(function (res) { var splits = res[0], months = res[1]; if (!splits.length && !months.length) { body.innerHTML = 'No split data for ' + esc(season) + '.'; return; } var out = ''; var shtml = ''; defs.forEach(function (def) { var byLevel = {}; splits.filter(function (s) { return s.split && s.split.code === def.code; }) .forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = lvl || ('sid' + s._sportId); var g = byLevel[key] = byLevel[key] || { lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); Object.keys(byLevel).map(function (k) { return byLevel[k]; }) .sort(function (a, b) { return b.sportId - a.sportId; }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); shtml += ' ' + esc(def.label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(totF(tot)) + ' '; }); }); if (shtml) { out += ' ' + theadHTML('Split', sCols) + '' + shtml + ' '; } if (months.length) { var mCols = isPitching ? PIT_SPLIT_COLS : HIT_COLS_RATES; var mTotF = function (t) { return isPitching ? pitSplitTotalCells(t) : hitTotalCells(t, true); }; var byMonth = {}; months.forEach(function (s) { var lvl = levelLabel(s._sportId, s.league && s.league.name); var key = n(s.month) + '|' + (lvl || 'sid' + s._sportId); var g = byMonth[key] = byMonth[key] || { month: n(s.month), lvl: lvl, sportId: s._sportId, team: [], noteam: [] }; (s.team ? g.team : g.noteam).push(s); }); var mhtml = ''; Object.keys(byMonth).map(function (k) { return byMonth[k]; }) .sort(function (a, b) { return (a.month - b.month) || (b.sportId - a.sportId); }) .forEach(function (g) { var use = g.team.length ? g.team : g.noteam; var tot = {}; use.forEach(function (s) { accF(tot, s.stat || {}); }); var label = MONTH_NAMES[g.month] || ('Month ' + g.month); mhtml += ' ' + esc(label) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(mTotF(tot)) + ' '; }); out += 'By Month' + ' ' + theadHTML('Month', mCols) + '' + mhtml + ' '; } body.innerHTML = out ? out + 'Splits and monthly totals shown per level for the selected season (regular season). Splits combine all teams at the same level into one line.' : 'No split data for ' + esc(season) + '.'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); var s = b.getAttribute('data-season'); if (s === 'ALL') showCareer(); else showSeason(s); }); showCareer(); } // ---------------- FIELDING UI (v2.3) ---------------- function initFielding(rows) { var chips = document.getElementById('pp-fld-chips'); var body = document.getElementById('pp-fld-body'); if (!chips || !body) return; rows = rows.filter(function (r) { return r.sportId !== 17 && r.position && (n(r.stat.gamesPlayed) || n(r.stat.chances) || ipToOuts(r.stat.innings)); }); if (!rows.length) { chips.innerHTML = ''; body.innerHTML = 'No fielding data available yet.'; return; } var seasonsMap = {}; rows.forEach(function (r) { seasonsMap[r.season] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); chips.innerHTML = 'Career Totals' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); function buildRows(list, withLevel) { var groups = {}; list.forEach(function (r) { var key = r.position + (withLevel ? '|' + r.level : ''); if (!groups[key]) groups[key] = { pos: r.position, lvl: withLevel ? r.level : '', sportId: r.sportId, tot: {} }; fldAccumulate(groups[key].tot, r.stat); }); return Object.keys(groups).map(function (k) { return groups[k]; }) .sort(function (a, b) { var pa = POS_ORDER[a.pos] != null ? POS_ORDER[a.pos] : 99; var pb = POS_ORDER[b.pos] != null ? POS_ORDER[b.pos] : 99; return (pa - pb) || (a.sportId - b.sportId); }) .map(function (g) { return ' ' + esc(g.pos) + (g.lvl ? '' + esc(g.lvl) + '' : '') + '' + cellsHTML(fldTotalCells(g.tot)) + ' '; }).join(''); } function fldTable(rowsHTML) { return ' ' + theadHTML('Pos', FLD_COLS) + '' + rowsHTML + ' '; } function show(season) { var out = ''; if (season === 'ALL') { var mlb = rows.filter(function (r) { return r.sportId === 1; }); var milb = rows.filter(function (r) { return isMilbSport(r.sportId); }); if (mlb.length) out += 'MLB — Career Totals by Position' + fldTable(buildRows(mlb, false)); if (milb.length) out += 'Minor Leagues — Career Totals by Position' + fldTable(buildRows(milb, false)); body.innerHTML = out ? out + 'Career fielding totals by position (regular season). FLD% is recomputed from combined PO/A/TC. Pick a season above for the year-by-year breakdown.' : 'No fielding data available yet.'; } else { var yr = rows.filter(function (r) { return r.season === season; }); out = yr.length ? fldTable(buildRows(yr, true)) : ''; body.innerHTML = out ? out + '' + esc(season) + ' fielding by position; multiple teams at the same level are combined into one line.' : 'No fielding data for ' + esc(season) + '.'; } } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('ALL'); } // ---------------- GAME LOG UI (v2.4) ---------------- // Default chip: "Last N Games" across all levels of the most recent // season (most recent first, each date links to Gameday) plus a // totals row. Season chips show the full game log for that year. var GL_PIT_COLS = ['Dec','IP','H','R','ER','HR','BB','SO','P']; var GL_HIT_COLS = ['AB','R','H','2B','3B','HR','RBI','BB','SO','SB']; function glDecision(st) { if (n(st.wins)) return 'W'; if (n(st.losses)) return 'L'; if (n(st.saves)) return 'SV'; if (n(st.holds)) return 'HLD'; if (n(st.blownSaves)) return 'BS'; return ''; } function glTheadHTML(cols) { return ' Date Opp Lvl ' + cols.map(function (c) { return ' ' + c + ' '; }).join('') + ' '; } function glRowHTML(s, isPitching) { var st = s.stat || {}; var lvl = levelLabel(s._sportId, s.league && s.league.name); var opp = (s.opponent && (s.opponent.abbreviation || s.opponent.name)) || ''; var oppTxt = (s.isHome === false ? '@ ' : 'vs ') + opp; var pk = s.game && s.game.gamePk; var gd = pk ? (s._sportId === 1 ? 'https://www.mlb.com/gameday/' : 'https://www.milb.com/gameday/') + pk : ''; var dateCell = gd ? '' + esc(fmtDate(s.date)) + '' : esc(fmtDate(s.date)); var cells = isPitching ? [ glDecision(st), st.inningsPitched || '0.0', n(st.hits), n(st.runs), n(st.earnedRuns), n(st.homeRuns), n(st.baseOnBalls), n(st.strikeOuts), st.numberOfPitches != null ? n(st.numberOfPitches) : '--' ] : [ n(st.atBats), n(st.runs), n(st.hits), n(st.doubles), n(st.triples), n(st.homeRuns), n(st.rbi), n(st.baseOnBalls), n(st.strikeOuts), n(st.stolenBases) ]; return ' ' + dateCell + ' ' + ' ' + esc(oppTxt) + ' ' + ' ' + (lvl ? '' + esc(lvl) + '' : '') + ' ' + cellsHTML(cells) + ' '; } function glTotalRowHTML(list, isPitching, label) { var tot = {}, pitches = 0, hasPitches = false; list.forEach(function (s) { var st = s.stat || {}; (isPitching ? pitAccumulate : hitAccumulate)(tot, st); if (st.numberOfPitches != null) { pitches += n(st.numberOfPitches); hasPitches = true; } }); var cells, txt; if (isPitching) { txt = label + ' (' + era(n(tot.earnedRuns), n(tot.outs)) + ' ERA)'; cells = [ '', outsToIp(n(tot.outs)), n(tot.hits), n(tot.runs), n(tot.earnedRuns), n(tot.homeRuns), n(tot.baseOnBalls), n(tot.strikeOuts), hasPitches ? pitches : '--' ]; } else { txt = label + ' (' + fmtAvg(tot.atBats ? tot.hits / tot.atBats : NaN) + ' AVG)'; cells = [ n(tot.atBats), n(tot.runs), n(tot.hits), n(tot.doubles), n(tot.triples), n(tot.homeRuns), n(tot.rbi), n(tot.baseOnBalls), n(tot.strikeOuts), n(tot.stolenBases) ]; } return ' ' + esc(txt) + ' ' + cellsHTML(cells) + ' '; } function initGameLog(group, rows, isPitching) { var chips = document.getElementById('pp-gl-chips'); var body = document.getElementById('pp-gl-body'); if (!chips || !body) return; var seasonsMap = {}; rows.forEach(function (r) { if (r.sportId === 17) return; (seasonsMap[r.season] = seasonsMap[r.season] || {})[r.sportId] = true; }); var seasons = Object.keys(seasonsMap).sort().reverse(); if (!seasons.length) { chips.innerHTML = ''; body.innerHTML = 'No game log available.'; return; } var N = n(RECENT_GAMES); chips.innerHTML = 'Last ' + N + ' Games' + seasons.map(function (s) { return '' + esc(s) + ''; }).join(''); var cols = isPitching ? GL_PIT_COLS : GL_HIT_COLS; var cache = {}; function fetchSeason(season) { if (!cache[season]) cache[season] = loadGameLog(group, season, Object.keys(seasonsMap[season]).map(Number)); return cache[season]; } function tableHTMLFor(list, totalLabel) { return ' ' + glTheadHTML(cols) + '' + list.map(function (s) { return glRowHTML(s, isPitching); }).join('') + (list.length > 1 ? glTotalRowHTML(list, isPitching, totalLabel) : '') + ' '; } function show(key) { var recent = key === 'RECENT'; var season = recent ? seasons[0] : key; body.innerHTML = 'Loading ' + (recent ? 'recent games' : esc(season) + ' game log') + '…'; fetchSeason(season).then(function (all) { var list = recent ? all.slice(0, N) : all; if (!list.length) { body.innerHTML = 'No games on record for ' + esc(season) + '.'; return; } body.innerHTML = tableHTMLFor(list, recent ? 'Last ' + list.length : esc(season) + ' Total') + '' + (recent ? 'Most recent ' + list.length + ' games across all levels (' + esc(season) + '), newest first. ' : esc(season) + ' game log, all levels, newest first. ') + 'Dates link to the Gameday box score. Pick a season above for the full log.'; }).catch(function (e) { body.innerHTML = 'Game log could not load (' + esc(e && e.message) + ').'; }); } chips.addEventListener('click', function (e) { var b = e.target.closest('.pp-chip'); if (!b) return; chips.querySelectorAll('.pp-chip').forEach(function (c) { c.classList.remove('pp-on'); }); b.classList.add('pp-on'); show(b.getAttribute('data-season')); }); show('RECENT'); } })();
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Steve Sica - Mets' Arizona Fall League Preview
The MLB regular season came to an end on Sunday, but the Arizona Fall League starts up this coming Saturday. Eight Met prospects will head to the desert this fall to represent the Surprise Saguaros in AFL play. They'll play alongside fellow prospects from the Kansas City Royals, Texas Rangers, and Cleveland Guardians. They'll also be taking the field alongside their hated division rival, the Philadelphia Phillies. It's always an unusual sight to see Mets and Phillies uniforms on the same team, but that's part of the charm of the Arizona Fall League. The Mets will send three hitters and five pitchers each with their own intriguing backstory. Let's start with the hitters. In years past, the Mets have either sent top prospects or prospects who were injured during the regular MiLB season. This year, the Mets have opted to send players who could use more reps after spending the majority of the summer on the IL.  Cole Mathis will be the highest-ranked prospect for the Mets in the AFL at number 13. He was the return piece from the Chicago Cubs in the deal that sent David Peterson and Tyrone Taylor to the Cubbies in late June. Due to injuries, he only played 13 games in the Mets' system. The Mets will hope to keep him healthy during his time in the AFL and give him the chance to showcase his skills. The potential is certainly there as he was a 2nd-round draft pick in 2024. It'll be Mathis' second year in a row in the AFL. He played there last year and put up an OPS of .839 in 16 games. Boston Baro was a top-30 prospect coming into 2026. Injuries derailed the 22-year-old's process for most of this season. He was a textbook case to head to the AFL, as he only appeared in 11 games primarily in Low-A St. Lucie. The Mets were hoping to get him in High-A and potentially Double-A at some point this season, but a trip to the AFL might be just what he needs to shake off an injury-plagued season and springboard himself into a better 2027. Bruin Agbayani, Benny Agbayani's son, will be the last Met hitter heading to the AFL. At just 19 years old, he'll be one of the youngest players in the desert this season. With only 18 MiLB games under his belt in the last two seasons, sending him to the highly competitive AFL was an unusual choice by the Mets, but it also shows confidence in his abilities. If he's anything like his father, he'll be a fan favorite in no time. The Mets' pitching core heading to the desert is one of the most intriguing groups I've seen them send to the AFL in quite some time. You have Calvin Ziegler, a top pitching prospect before injuries grounded him to just 20 innings pitched from 2024-26. After missing all of 2025, he pitched 13 innings in 2026 and ended his MiLB season with a shutout inning in Double-A Binghamton. Ziegler was once thought of as highly as McLean, Scott, and Tong were during their time in MiLB. If he can stay healthy, he'll be one of the most watched Met prospects this month in Arizona. The Mets' fifth-round draft pick from 2025, Peyton Prescott, will join Ziegler in Surprise. He didn't see any action in 2025 and pitched just one inning in 2026. Like Ziegler, the Mets will hope to see a larger sample size from Prescott in the next six weeks of the AFL season. The Florida State product looks to put himself back in the top-30 Met prospect rankings. Irving Cota and Brendan Girton are two pitchers who put together excellent seasons in High-A but struggled at the Double-A level. Cota dominated in Brooklyn in 2026, pitching to a 0.73 ERA in 24 innings and five starts. He got hammered in his lone Double-A start before injuries cost him significant playing time. Girton, on the other hand, pitched to a 2.79 ERA for Brooklyn in 2025. He made 17 starts and struck out 91. He would not repeat that success for Double-A Binghamton in 2026. In 83 innings of work, he got tagged with a 6.72 ERA. The talent level in the AFL is on par with Double-A, so this will be a good opportunity for both pitchers to work on their craft and hopefully gain some confidence against some of the best hitters MiLB has to offer. Ryan Lambert rounds out the Met roster to the AFL. In 2025, he was one of, if not the best, relievers in MiLB. In 50 innings split between High-A and Double-A, he pitched to a 1.62 ERA, striking out 81 batters and helping lead Binghamton to an Eastern League title. Fast forward to 2026, and it's just the opposite. Triple-A wasn't kind to Lambert, as he was walloped for a 7.71 ERA in 25 innings of work. The International League is notorious for grinding down pitchers, and Lambert fell victim to this. The AFL is a hitter-friendly league due to the cool, dry desert air in October, but when Lambert is on, he can shut down anyone. We'll see if he can recapture his 2025 dominance this fall.
001
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Cautious Optimist -- The Mets Are Finally A Start Up With A Big Investor: They Need to Act Like One
  If you don't know where you where you are going every road will take you there On the other hand, even if you know where you trying to go, you still have to figure out how to get there.   Many promising roads prove to be dead ends.  The Cohen Mets have never lacked for a destination.  From the day he took over ownership of the team, Steve Cohen identified two goals for the Mets: Win a championship within five years and enjoy the sort of sustained success over the long term that would make the Mets one of the premier franchises in the baseball.  They have, however, lacked a roadmap for achieving those goals.  It may well be true that you don't know what you've got till it's gone.  But it is equally true that you don't know what you've gotten yourself into until you've moved in. That is surely the situation Cohen and his team found themselves in.  As a result they found themselves trying to solve a myriad of problems simultaneously almost from the outset, including: *     Figure out how to structure the organization, as the one they                   inherited was little more than a family organization. *     Develop a talent evaluation and development program. *      Assess the talent at the major and minor league levels. *      Create a pipeline of talent in the minors that would set them up for            ongoing success, while *      Adding enough talent at the major league level to win a                            championship in the near term. And more. The task they faced would have been easier with an expansion team, starting afresh.   These are challenging conditions for authoring a credible roadmap to success, and it is not surprising that the Mets were guilty of overpromising and underperforming. In fact, in retrospect, I don't believe the Mets fully understood that they lacked the talent in the major leagues to compete for a championship in the near term until last offseason, nor did they appreciate that they did not have sufficient talent in the minors -- let alone a pipeline -- adequate to secure sustained success over the longer term until this season. They were mislead by the surprising success of the 2024 team and by the high ranking of their minor league system in 2025. The disastrous second half of the 2025 season was eye opening regarding prospects for imminent success at the major league level; and the putrid first half performance of all their minor league affiliates in 2026 sounded a similar alarm about their overall talent level on the farm. They were a year late on both accounts, but it's hard to blame them for that given the misleading signals they had received. It's easy to fault the FO for underperforming, but the real mistake was overpromising in the face of so little information.  Maybe they believed that all their problems could be solved by money.  In which case they were no more mistaken than was the majority of the fanbase. And they did end up spending lots of money, much of it to clean up the mess, clear the brush, and pay down a few poor decisions that displayed more hubris than insight. But the truth is that once the FO realized that there was no way that the core of the existing team could compete for a championship at any reasonable cost over the short term, they shifted gears and pushed out their window for competing to 2028. And then once they realized that they lacked the talent in the minors necessary to supplement the major league roster, they turned their attention to infusing talent into the farm system, at key positions up and down the leagues. At the same time, they obviously decided that the approach to developing talent needed an upgrade as well. The Mets overall have been around for over 65 years, but the Cohen Mets took a few years to achieve the status of a genuine startup.  They reformulated the time frame for their goals, set out to structure their organization, bring talent abroad and create a product that would succeed in the market place.  All they needed was a plan. Their first effort at creating a plan was not well conceived.  Rather than throw good money after bad at the major league level, they would bide time by creating a bridge team that would be competitive until the minor league replacements for the both the bridge players and those the team let go in the purge of the 2025 offseason would arrive in 2026. The plan was doomed from the outset.  The bridge signings were disastrous and had provided little reason to think they would merge with the remaining post purge players to form a competitive team.  Half the signings had injury histories and spotty performance records.  The saving grace in all but one case was the short duration of the the contracts. Once the expected injuries occurred and the better players from the farm were called to major league duty, it became obvious that there just wasn't that much left on the form across all the positions that would need replacements.  What a mess. On the other hand, the Mets did a hell of a job correcting for the deficit of minor league talent both in the draft and in the trade deadline deals they made. Like a good startup, they quickly and decisively pivoted from their orginal plan.  Instead of a bridge team to be supplemented by talent drawn from the minors, the new plan has adopted the opposite approach.  The championship team and the teams thereafter will be fundamentally be drawn from the talent now in the minors and soon to be supplemented by even more talent at key positions.  That core is as much formed by Benge, Ewing, McLean, Scott and Thornton as it is by Lindor and Soto.  The only bridge player worth taking seriously at this point is Bichette. Semien and Polanco have no real place on this team going forward.  They haven't earned time over the likes of the top prospects on the infeild, Voit, Petri and Rojas, among others not all that far behind them.  Tong and Santucci are knocking on the door.  What we are looking at is a reversal of approach where the vets will be brought in to supplement the in house talent, and not the other way around. I believe that we have witnessed in effect a revision of the original plan (which only came into being last offseason) in the light of the new evidence presented by this season's performance. New manager, additional baseball voices, an infusion of a good deal of talent into the farm system. We are almost at a dawn of a new beginning, but we haven't yet chosen the roadmap we will follow.  I say that because while there is no doubt that the future will be driven primarily by in house talent finding their ways to the majors: talent that has been chosen for speed, versatility, athleticism and defense, the fact is that it is not obvious that enought of that talent will be ready next year. Which leaves us with two possible roadmaps:. Two options I think there are two paths that can be successful, and I am pretty sure that fans (and perhaps voices within the organization as well) will disagree about which to pursue. These are:  * The transformation continues* The hybrid approach steady the ship and pick your spots as you continue transformation According to the latter plan, keep some of the vets. -- Lindor, Bichette (his choice, not ours), Manaea, Senga;  the new talent from the minors is infused slowly with respect to position players, with only one of the three top prospects (in my view of them) -- Rojas, Petri and Voit -- making the roster to start the season, unless Reimer or someone else like Amick, becomes part of the 1B platoon.  Gaps in pitching -- both starters and relievers are created by a mix of FA, trades and promotions from the farm.  Pitching is the anchor of the team that is being built: pitching and defense.  The team has exhausted its inhouse pitching talent ready to compete for starting jobs -- when you add Tong and Santucci to the current mix.  You don't have a top rotation guy or an innings eater.  Witht eh exception of McLean no one currently on the staff can be counted on for for a majority of 6-7 innings performances and no ne is an ACE.  So we need to go outside the house and look for trades and free agenst, but not as bridges, but as the additional pieces to complement the home developed talent.. This is true whether we chose the hybrid or the transformational plan.  The advantage of the transofrmation plan is that we infuse mor talent into the mix immediately through trades. As long as it is clear that the main driver is transformation, I can see slowing down the process this year while bringing in heavy duty talent -- especially pitching talent to set us up for the long haul. Our hand may be forced to take on more minor league talent -- perhaps prematurely -- if Bichette opts out And so we return to money. You knew we couldn't escape it.   If we go the hybrid strategy for the next year or two, we will be asking Cohen to pay for a high priced pitcher or two, a platoon right hander at 1B (either Goldschmidt or Tucker until Amich or Reimer is available. If one of thoese pitchers is Skubal we are talking real money. But our ask is greate still.  Because the one think we have to do no matter which plan which choose is close the books on Semien, probably do the same with Polanco who will give us less than a full season at best, get rid of low priced players like Vientos, and the slew of AAAA players from Wagaman to Melendez to Pasche and Morel who created one of the worst benches in baseball.   And replace them with short term professional major leaguers. Semien is 47million over two years; Polanco is 20 million for a half a season.  Add the price of a Skubal or an extension for another top of the line pitcher obtainable in a trade and an innings eate -- not to mention tow or three bullpen pieces and your are looking at another 100million in payroll for this one year.  It's not my money but I think it may be worth it.  Manaea come off  the books and do Senga and Bichette (I predict after next year) and the payroll is right back where it belons.  You don't pass on what you need if the additional costs last only one year and do not carry over.  But hey it's not my money. The transformation approach is not terrible.  You trade Alvarez along with Semien for someone take the contract and you get a B player back -- maybe a good bench player.  That clears a lot of salary.  Maybe you trade Lindor as well and you pay off half his contract and get top flight minor league talent or a back of the bullpen guy as well as anothe rpiece, and you financial commitments go way down -- especially in Bichette leave. I think the Mets may choose either to close the books on players or add new talent but not both.  This is not acceptalble as we don't want to lose momentum and weare only paying for one year increases. Would you pay Polanco even at his best 20m for next year to platoon with Young or Baty at 1st base?   Of course not.  There are going to be lots of other 1 or 2yr options from the right side that can give you terrific defense and real pop against lefties (e.g. Goldschmidt or Walker).  I am sure there are others as well, maybe Reimer. I don't know yet. Do you think you will get more out of Semien than you will out of either Voit, Rojas or Petri?  I don't think so, and certainly not the year after next.  Voit, Rojas and Petri will cost you under 1m/year no matter who you choose, so in effect at worse you will have to pay no more than 1m more to get better performance and change the speed and defense of your team by bringing one of them up to play second over the next two years.  To me that is a no brainer.  And if you can save some of that money with a trade of Semien where you pay more than half of his salary and throw in a pitcher like Wenninger, I am all for it. Don't compound mistakes.   Remember, if you are a start up, you don't act as if you were a value company like GE or Wells Fargo.  You are in the growth phase. And we can no longer estimate the role of a bench Whether it means no Baty and/or no Mauricio is up to them.   It's going to a special time in Mets Land.  Startups always are.
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Around the Majors with Mets News and Links - 9/29/2026
Here are the top Stories from every Major League team courtesy from our friends at SportSpyder. Note - this page updates throughout the day - come back later today for the latest news.
000
John From Albany @johnfromalbany.bsky.social · 29/09/2026
dlvr.it
Stearns: No Mulligans, No Excuses — And Plenty of Work Ahead for the Mets
There are end-of-season press conferences, and then there are end-of-September press conferences for a team that was supposed to be playing in October. David Stearns knows the difference. And he wasn't interested in pretending otherwise. “Anytime we're having an end of season press conference at the end of September, it's not where you want to be,” Stearns said as he opened his postseason autopsy of a Mets season that began with enormous expectations and ended with the organization already...
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
SNY on YouTube: David Stearns on what went wrong for Mets in 2026, his plans to make the team better moving forward - 9/28/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
Press Release: 2027 Ford C. Frick Award Ballot Finalized
Sept. 28, 2026 -- Winner to be Announced Dec. 9 at Baseball’s Winter Meetings -- (COOPERSTOWN, NY) – Ten of the National Pastime’s most historic and respected voices have been named as the finalists for the 2027 Ford C. Frick Award, presented annually for excellence in baseball broadcasting by the National Baseball Hall of Fame and Museum. This ballot will mark the first election featuring a composite ballot of local and national voices whose broadcast careers concluded prior to the advent of the Wild Card in 1994. The election cycle will then return, starting with the 2028 Frick Award, to four straight years of candidates whose careers began or mostly comprise the years after the advent of the Wild Card era. The cycle then repeats. The 2027 Frick Award ballot consists of 10 candidates, including a requirement that at least one candidate be a foreign language broadcaster. The 10 finalists for the 2027 Frick Award are: Buddy Blattner, Ken Coleman, Dizzy Dean, Earl Gillespie, Merle Harmon, Ned Martin, Monte Moore, Gustavo Lopez Moreno, Bill O’Donnell and Jack Quinlan. The winner of the 2027 Frick Award will be announced on Dec. 9 at Baseball’s Winter Meetings in San Diego and will be honored during the July 24 Awards Presentation as part of the July 23-26 Hall of Fame Weekend 2027 in Cooperstown. Moore and Moreno are the only living candidates on the ballot. Criteria for selection is as follows: “Commitment to excellence, quality of broadcasting abilities, reverence within the game, popularity with fans, and recognition by peers.” To be considered, an active or retired broadcaster must have a minimum of 10 years of continuous major league broadcast service with a ball club, network, or a combination of the two. The 2027 Frick Award ballot was created by a subcommittee of the voting electorate that included past Frick honorees Joe Castiglione, Bob Costas, Tom Hamilton and Eric Nadel and broadcast historian Curt Smith. Final voting for the 2027 Frick Award will be conducted by an electorate comprised of the 14 living Frick Award recipients and two broadcast historians/columnists, including past Frick honorees Marty Brennaman, Joe Buck, Castiglione, Costas, Hamilton, Ken Harrelson, Pat Hughes, Jaime Jarrín, Tony Kubek, Denny Matthews, Al Michaels, Jon Miller, Nadel and Dave Van Horne, and historians/columnists Barry Horn (formerly of the Dallas Morning News), and Smith (historian). The 10 finalists for the 2027 Frick Award: Blattner worked 26 seasons for outlets primarily in the 1950s and 1960s including the Liberty Game of the Day, Mutual Game of the Day, ABC Game of the Week, CBS Game of the Week and NBC, along with several stops with individual teams. Coleman spent 35 years with the Indians (1954-63), Reds (1975-78) and Red Sox (1966-74, 79-89), calling the action for five World Series teams. Dean, elected to the Hall of Fame as a pitcher in 1953, made his mark as the voice of CBS’ Game of the Week from 1955-65 following several seasons with the Cardinals and Browns. Gillespie called 11 seasons of games with the Milwaukee Braves (1953-63), including the 1957 and 1958 World Series for NBC Radio. Harmon worked for 30 seasons with the Kansas City A’s (1955-61), Milwaukee Braves (1964-65), Minnesota Twins (1967-69), Milwaukee Brewers (1970-79) and Texas Rangers (1982-89) along with the ABC Game of the Week (1965) and NBC Game of the Week (1980-82). Martin worked as the Red Sox’s radio and television voice from 1961-92, covering the 1975 World Series for NBC-TV along with three Red Sox World Series teams. Moore called games for 22 years (1962-77, 1987-1992) for the Athletics and spent three years as Game of the Week announcer for NBC-TV and six years with USA Network. Moreno called games for 23 years with the San Diego Padres (1969-91), bringing Padres’ action to Spanish-speaking fans from the club’s inception. O’Donnell joined the Orioles broadcast team in 1966 after spending 13 years as the voice of Syracuse University football, calling Baltimore games for 17 seasons. He was a member of NBC’s Game of the Week team from 1969 to 1976. Quinlan called Cubs games from 1955-64 before his promising career was cut short by a fatal automobile accident in Spring Training of 1965. Additional information on the 10 finalists can be found at baseballhall.org . The annual award is named in memory of Hall of Famer Ford C. Frick, renowned sportswriter, radio broadcaster, National League president and MLB Commissioner. Past recipients of the Ford C. Frick Award: FORD C. FRICK AWARD RECIPIENTS 1978 Mel Allen 1994 Bob Murphy 2011 Dave Van Horne Red Barber 1995 Bob Wolff 2012 Tim McCarver 1979 Bob Elson 1996 Herb Carneal 2013 Tom Cheek 1980 Russ Hodges 1997 Jimmy Dudley 2014 Eric Nadel 1981 Ernie Harwell 1998 Jaime Jarrín 2015 Dick Enberg 1982 Vin Scully 1999 Arch McDonald 2016 Graham McNamee 1983 Jack Brickhouse 2000 Marty Brennaman 2017 Bill King 1984 Curt Gowdy 2001 Felo Ramírez 2018 Bob Costas 1985 Buck Canel 2002 Harry Kalas 2019 Al Helfer 1986 Bob Prince 2003 Bob Uecker 2020 Ken Harrelson 1987 Jack Buck 2004 Lon Simmons 2021 Al Michaels 1988 Lindsey Nelson 2005 Jerry Coleman 2022 Jack Graney 1989 Harry Caray 2006 Gene Elston 2023 Pat Hughes 1990 1991 1992 1993 By Saam Joe Garagiola Milo Hamilton Chuck Thompson 2007 2008 2009 2010 Denny Matthews Dave Niehaus Tony Kubek Jon Miller 2024 2025 2026 Joe Castiglione Tom Hamilton Joe Buck The National Baseball Hall of Fame and Museum is an independent nonprofit educational institution, dedicated to fostering an appreciation of the historical development of baseball and its impact on our culture by collecting, preserving, exhibiting and interpreting its collections for a global audience as well as honoring those who have made outstanding contributions to our National Pastime. Opening its doors for the first time on June 12, 1939, the Hall of Fame has stood as the definitive repository of the game’s treasures and as a symbol of the most profound individual honor bestowed on an athlete. It is every fan’s "Field of Dreams," with its stories, legends and magic shared from generation to generation.
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
Max Goodman - Speaking of the Mets: Will Mets go after Tarik Skubal? Reacting LIVE to David Stearns’ end-of-season presser - 9/28/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
Max Goodman - Speaking of the Mets: Why David Stearns is so encouraged about Mets despite such a disappointing season - 9/28/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
Mets YouTube Channel: LIVE: David Stearns Press Conference | September 28, 2026 - 9/28/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
SNY on YouTube: J.J. McCarthy in, Brian Burns out: what's next for Big Blue? | NYG411 - 9/28/26
Featured Posts Featured, Mets Prospects, New York Mets Binghamton Rumble Ponies, Featured, Media Guide Featured, Media Guide, Syracuse Mets More Featured Posts. Syracuse Mets and Binghamton Rumble Ponies Photos Mets Videos Mets Videos, New York Mets Mets Videos, New York Mets Mets Videos, New York Mets Game Highlights, Mets Videos, New York Mets More Mets Videos. Mets360 More Mets360. More Mack's Mets. The Mediagoon More Mediagoon. MLB Leaders 43 42 42 41 35 45 45 41 41 37 113 106 101 97 96 116 111 107 106 102 180 179 175 170 168 191 185 181 175 174 248 239 239 211 205 205 252 231 221 200 200 200 18 16 15 14 14 18 16 16 15 14 14 14 14 14 Standings MLB Standings National League NL East Team W L10 Braves 94 68 .580 - 5-5 L1 Phillies 88 74 .543 6.0 4-6 W1 Marlins 80 82 .494 14.0 5-5 W1 Nationals 77 85 .475 17.0 6-4 W1 Mets 74 88 .457 20.0 5-5 L1 NL Central Team W L10 STRK Brewers 103 59 .636 - 8-2 W5 Cubs 89 73 .549 14.0 5-5 W1 Pirates 82 80 .506 21.0 7-3 W1 Cardinals 77 85 .475 26.0 2-8 L4 Reds 75 87 .463 28.0 4-6 L1 NL West Team W L L10 STRK Dodgers 100 62 .617 - 8-2 W3 Padres 91 71 .562 9.0 8-2 W2 D-backs 86 76 .531 14.0 6-4 L2 Giants 65 97 .401 35.0 2-8 L5 Rockies 58 104 .358 42.0 2-8 L1 American League AL East Team W L L10 STRK Rays 98 64 .605 - 5-5 L1 Yankees 93 68 .578 4.5 5-5 W1 Red Sox 87 75 .537 11.0 5-5 L1 Orioles 79 82 .491 18.5 6-4 L1 Blue Jays 79 83 .488 19.0 4-6 W1 AL Central Team W L10 STRK Guardians 85 77 .525 - 8-2 L1 White Sox 84 78 .519 1.0 7-3 W1 Twins 77 85 .475 8.0 6-4 W1 Tigers 76 86 .469 9.0 4-6 L1 Royals 69 93 .426 16.0 2-8 W1 AL West Team W L L10 STRK Astros 81 81 .500 - 5-5 W2 Rangers 80 82 .494 1.0 4-6 L1 Mariners 76 86 .469 5.0 6-4 W2 Athletics 64 98 .395 17.0 3-7 L2 Angels 62 100 .383 19.0 4-6 L2 Last Updated: 9/28/2026, 10:52:03 AM Live Baseball Scores: MLB, American, European and Asian baseball livescore. Fastest live - real time - scores, results and scores after innings. Name Email * Message *
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
SNY on YouTube: "Francisco Lindor goes to a place no shortstop has ever been, 200 stolen bases & now 300 home runs!" - 9/28/26
Mets News and Links, Metsnewslinks.com, Mets Prospects, Winter Ball Stats and Scores, MLB Mets plus Syracuse, Binghamton, Brooklyn & St. Lucie Mets.
000
John From Albany @johnfromalbany.bsky.social · 28/09/2026
dlvr.it
Lunch Time Links - Top MLB Headlines Now - 9/28/2026
Here are some of the News and Headlines around Major League Baseball courtesy from our friends at SportSpyder.
000