- MLB の Stats API を使用
- GAS で予定取得し変換、Googleカレンダーに登録
- 特定チーム(今回はエンゼルス)の予定を取得
- 時刻は日本時間に
- タイトルのチーム名は3文字の省略形(LAA など)に
const CALENDAR_ID = '[GOOGLE_CALENDAR_ID]';
function fetchAngelsSchedule() {
const apiUrl = 'https://statsapi.mlb.com/api/v1/schedule?teamId=108&season=2023&sportId=1';
const response = UrlFetchApp.fetch(apiUrl);
const data = JSON.parse(response.getContentText());
const games = data.dates.flatMap(date => date.games);
return games.map(game => {
const gameDate = new Date(game.gameDate);
const end = new Date(gameDate.getTime() + 3 * 60 * 60 * 1000);
const isHome = game.teams.home.team.id === 108;
const opponent = isHome ? game.teams.away.team : game.teams.home.team;
const opponentShortName = getShortName(opponent);
return {
start: gameDate,
end: end,
opponent: opponentShortName,
isHome: isHome,
};
});
}
function getShortName(team) {
const shortNames = {
'Baltimore Orioles': 'BAL',
'Boston Red Sox': 'BOS',
'New York Yankees': 'NYY',
'Tampa Bay Rays': 'TBR',
'Toronto Blue Jays': 'TOR',
'Chicago White Sox': 'CWS',
'Cleveland Guardians': 'CLE',
'Detroit Tigers': 'DET',
'Kansas City Royals': 'KC',
'Minnesota Twins': 'MIN',
'Los Angeles Angels': 'LAA',
'Oakland Athletics': 'OAK',
'Seattle Mariners': 'SEA',
'Texas Rangers': 'TEX',
'Houston Astros': 'HOU',
'Atlanta Braves': 'ATL',
'Miami Marlins': 'MIA',
'New York Mets': 'NYM',
'Philadelphia Phillies': 'PHI',
'Washington Nationals': 'WSH',
'Chicago Cubs': 'CHC',
'Cincinnati Reds': 'CIN',
'Milwaukee Brewers': 'MIL',
'Pittsburgh Pirates': 'PIT',
'St. Louis Cardinals': 'STL',
'Arizona Diamondbacks': 'ARI',
'Colorado Rockies': 'COL',
'Los Angeles Dodgers': 'LAD',
'San Diego Padres': 'SDP',
'San Francisco Giants': 'SFG',
};
return shortNames[team.name] || team.name;
}
function convertToJST(date) {
const jstDate = new Date(date.toLocaleString('en-US', { timeZone: 'Asia/Tokyo' }));
return jstDate;
}
function addAngelsScheduleToCalendar() {
const calendar = CalendarApp.getCalendarById(CALENDAR_ID);
const games = fetchAngelsSchedule();
const seasonStart = new Date(2023, 2, 31);
const seasonEnd = new Date(2023, 9, 31);
games.forEach(game => {
const startJST = convertToJST(game.start);
const endJST = convertToJST(game.end);
if (startJST >= seasonStart && startJST <= seasonEnd) {
const title = game.isHome ? `LAA vs ${game.opponent}` : `${game.opponent} vs LAA`;
const rangeStart = new Date(startJST.getTime() - 24 * 60 * 60 * 1000);
const rangeEnd = new Date(startJST.getTime() + 24 * 60 * 60 * 1000);
const events = calendar.getEvents(rangeStart, rangeEnd, { search: title });
const isEventExist = events.some(event => {
const eventStart = event.getStartTime();
return eventStart.getYear() === startJST.getYear() &&
eventStart.getMonth() === startJST.getMonth() &&
eventStart.getDate() === startJST.getDate();
});
if (!isEventExist) {
calendar.createEvent(title, startJST, endJST);
}
}
});
}