samipote

Untitled

May 2nd, 2024
77
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 32.94 KB | None | 0 0
  1. library(httr)
  2. library(rvest)
  3. library(jsonlite)
  4. library(tidyr)
  5. library(xml2)
  6. library(dplyr)
  7. library(gt)
  8. library(png)
  9. library(webshot2)
  10. library(lubridate)
  11. library(stringr)
  12. library(janitor)
  13. library(gsheet)
  14. library(openxlsx)
  15. library(purrr)
  16. library(gtExtras)
  17. library(nflfastR)
  18. library(readr)
  19.  
  20.  
  21.  
  22. # team names --------------------------------------------------------------
  23.  
  24.  
  25. teams_url <- "https://en.wikipedia.org/wiki/National_Football_League"
  26.  
  27. team_table <- read_html(teams_url) %>% html_nodes("table.wikitable") %>%
  28. html_table() %>% .[[1]] %>%
  29. select("full_name" = "Club[66]") %>%
  30. filter(full_name != "American Football Conference", full_name != "National Football Conference", !grepl("relocated", full_name)) %>%
  31. mutate(full_name = gsub("[^a-zA-Z0-9 ]", "", full_name)) %>%
  32. separate(full_name, c("location","name"),sep="\\s+(?=\\S*$)") %>%
  33. mutate(full_name = paste0(location, " ", name),
  34. abbr = case_when(name == "Bills" ~ "BUF",
  35. name == "Dolphins" ~ "MIA",
  36. name == "Patriots" ~ "NE",
  37. name == "Jets" ~ "NYJ",
  38. name == "Ravens" ~ "BAL",
  39. name == "Bengals" ~ "CIN",
  40. name == "Browns" ~ "CLE",
  41. name == "Steelers" ~ "PIT",
  42. name == "Texans" ~ "HOU",
  43. name == "Colts" ~ "IND",
  44. name == "Jaguars" ~ "JAX",
  45. name == "Titans" ~ "TEN",
  46. name == "Broncos" ~ "DEN",
  47. name == "Chiefs" ~ "KC",
  48. name == "Raiders" ~ "LV",
  49. name == "Chargers" ~ "LAC",
  50. name == "Cowboys" ~ "DAL",
  51. name == "Giants" ~ "NYG",
  52. name == "Eagles" ~ "PHI",
  53. name == "Commanders" ~ "WAS",
  54. name == "Bears" ~ "CHI",
  55. name == "Lions" ~ "DET",
  56. name == "Packers" ~ "GB",
  57. name == "Vikings" ~ "MIN",
  58. name == "Falcons" ~ "ATL",
  59. name == "Panthers" ~ "CAR",
  60. name == "Saints" ~ "NO",
  61. name == "Buccaneers" ~ "TB",
  62. name == "Cardinals" ~ "ARI",
  63. name == "Rams" ~ "LAR",
  64. name == "49ers" ~ "SF",
  65. name == "Seahawks" ~ "SEA"))
  66.  
  67. american_to_prob <- function(american_odds) {
  68. probability <- case_when(
  69. is.na(american_odds) ~ 0,
  70. american_odds >= 0 ~ 100 / (american_odds + 100),
  71. TRUE ~ (-american_odds) / (american_odds - 100)
  72. )
  73. return(abs(probability))
  74. }
  75.  
  76. # odds api setup ----------------------------------------------------------
  77.  
  78.  
  79. api <- "935bb399373baa6304a140c7a6cee4fc"
  80. base <- "https://api.the-odds-api.com"
  81. sport <- "americanfootball_nfl"
  82. markets <- "h2h,spreads,totals"
  83. endpoint <- paste0("/v4/sports/", sport, "/odds/?apiKey=", api, "&regions=us&markets=", markets, "&bookmakers=draftkings,fanduel&oddsFormat=american")
  84.  
  85. #sports <- GET(paste0("https://api.the-odds-api.com/v4/sports/?apiKey=", api))
  86.  
  87. url <- paste0(base, endpoint)
  88.  
  89. response_nfl <- GET(url)
  90.  
  91. weekdays_vector <- c("Monday", "Sunday", "Saturday", "Friday", "Thursday", "Wednesday", "Tuesday")
  92.  
  93. # Get the day of the week as a numeric value (1 for Monday, 2 for Tuesday, etc.)
  94. day_of_week_num <- match(weekdays(Sys.Date()), weekdays_vector) #- 1
  95.  
  96. week_filter_date <- Sys.Date()+day_of_week_num
  97.  
  98. # Check the response status
  99. content_nfl <- fromJSON(content(response_nfl, "text")) %>%
  100. unnest(., cols = c(bookmakers)) %>%
  101. unnest(., cols = c(markets), names_sep = "_") %>%
  102. unnest(., cols = c(markets_outcomes), names_sep = "_") %>%
  103. mutate(commence_time = with_tz(ymd_hms(commence_time, tz = "UTC"), tzone = "America/New_York"),
  104. week = case_when(commence_time >= as.Date("2023-09-07") & commence_time < as.Date("2023-09-12") ~ "week_1",
  105. commence_time >= as.Date("2023-09-14") & commence_time < as.Date("2023-09-19") ~ "week_2",
  106. commence_time >= as.Date("2023-09-21") & commence_time < as.Date("2023-09-26") ~ "week_3",
  107. commence_time >= as.Date("2023-09-28") & commence_time < as.Date("2023-10-03") ~ "week_4",
  108. commence_time >= as.Date("2023-10-05") & commence_time < as.Date("2023-10-10") ~ "week_5",
  109. commence_time >= as.Date("2023-10-12") & commence_time < as.Date("2023-10-17") ~ "week_6",
  110. commence_time >= as.Date("2023-10-19") & commence_time < as.Date("2023-10-24") ~ "week_7",
  111. commence_time >= as.Date("2023-10-26") & commence_time < as.Date("2023-10-31") ~ "week_8",
  112. commence_time >= as.Date("2023-11-02") & commence_time < as.Date("2023-11-07") ~ "week_9",
  113. commence_time >= as.Date("2023-11-09") & commence_time < as.Date("2023-11-14") ~ "week_10",
  114. commence_time >= as.Date("2023-11-16") & commence_time < as.Date("2023-11-21") ~ "week_11",
  115. commence_time >= as.Date("2023-11-23") & commence_time < as.Date("2023-11-28") ~ "week_12",
  116. commence_time >= as.Date("2023-11-30") & commence_time < as.Date("2023-12-05") ~ "week_13",
  117. commence_time >= as.Date("2023-12-07") & commence_time < as.Date("2023-12-12") ~ "week_14",
  118. commence_time >= as.Date("2023-12-14") & commence_time < as.Date("2023-12-19") ~ "week_15",
  119. commence_time >= as.Date("2023-12-21") & commence_time < as.Date("2023-12-26") ~ "week_16",
  120. commence_time >= as.Date("2023-12-28") & commence_time < as.Date("2023-01-02") ~ "week_17",
  121. commence_time >= as.Date("2024-01-04") & commence_time < as.Date("2024-01-09") ~ "week_18",
  122. TRUE ~ "Unknown"),
  123. week_filter = ifelse(commence_time <= as.Date(week_filter_date), 1, 0))
  124.  
  125. nfl_week_raw <- unique(content_nfl %>% filter(week_filter == 1) %>% select(week)) %>% pull()
  126. nfl_week <- toupper(gsub(pattern = "_", replacement = " ", x = nfl_week_raw))
  127. nfl_week_int <- nfl_week %>% gsub("[^0-9]", "", .) %>% as.integer()
  128.  
  129.  
  130.  
  131. # odds df -----------------------------------------------------------------
  132.  
  133.  
  134. odds_df <- content_nfl %>% filter(week_filter == 1) %>%
  135. clean_names() %>%
  136. mutate(markets_outcomes_name = case_when(markets_outcomes_name == away_team ~ "away",
  137. markets_outcomes_name == home_team ~ "home",
  138. markets_outcomes_name == "Over" ~ "over",
  139. markets_outcomes_name == "Under" ~ "under",
  140. TRUE ~ markets_outcomes_name),
  141. key = ifelse(key == "draftkings", "dk", ifelse(key == "fanduel", "fd", NA)),
  142. prob = american_to_prob(markets_outcomes_price)) %>%
  143. select(-c(id, sport_key, sport_title, last_update, markets_last_update, title)) %>%
  144. rename("market" = "markets_key", "outcome" = "markets_outcomes_name", "odds" = "markets_outcomes_price", "points" = "markets_outcomes_point", "book" = "key") %>%
  145. select(-c(odds)) %>%
  146. pivot_wider(names_from = c(outcome, market), values_from = c(prob, points)) %>%
  147. select(-c(week_filter, prob_away_spreads, prob_home_spreads, prob_over_totals, prob_under_totals, points_under_totals)) %>%
  148. rename("home_prob" = "prob_home_h2h", "away_prob" = "prob_away_h2h", "home_spread" = "points_home_spreads", "away_spread" = "points_away_spreads",
  149. "total" = "points_over_totals", "home_points" = "points_home_h2h", "away_points" = "points_away_h2h", "site" = "book") %>%
  150. mutate(type = "book") %>%
  151. left_join(., team_table, by = c("home_team" = "full_name")) %>%
  152. mutate(home_team = abbr) %>%
  153. select(-c(location, name, abbr)) %>%
  154. left_join(., team_table, by = c("away_team" = "full_name")) %>%
  155. mutate(away_team = abbr) %>%
  156. select(-c(location, name, abbr)) %>%
  157. mutate(game_id = paste0(away_team, " - ", home_team)) %>%
  158. select(c(commence_time, week, game_id, everything())) %>%
  159. mutate(home_points = (total / 2) - (home_spread / 2),
  160. away_points = (total / 2) - (away_spread / 2)) %>%
  161. select(c(commence_time, week, type, site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread, away_points, home_points, total))
  162.  
  163.  
  164. # functions for data manipulation ----------------------------------------------------
  165.  
  166. spread_to_prob_data <- read.csv(text = gsheet2text("https://docs.google.com/spreadsheets/d/11SFGATUQL3nGYuTULjfVvWme-XxWUO2snfTjX14Mt7o/edit#gid=893808082", format = "csv"), stringsAsFactors = FALSE) %>%
  167. clean_names()
  168.  
  169. spread_to_prob <- function(x){
  170. differences <- abs(spread_to_prob_data$line - x)
  171. closest_index <- which.min(differences)
  172. closest_value <- spread_to_prob_data$prob[closest_index]
  173. # prob <- spread_to_prob_data[spread_to_prob_data$line %in% x, ]$prob
  174. return(closest_value)
  175. }
  176.  
  177. prob_to_spread <- function(x){
  178. differences <- abs(spread_to_prob_data$prob - x)
  179. closest_index <- which.min(differences)
  180. closest_value <- spread_to_prob_data$line[closest_index]
  181. return(closest_value)
  182. }
  183.  
  184. split_string_space <- function(x) {
  185. str_split(x, " ")[[1]]
  186. }
  187.  
  188. split_string_pm <- function(x) {
  189. str_split(x, "PM")[[1]]
  190. }
  191.  
  192. # action network ----------------------------------------------------------
  193.  
  194.  
  195. actionnetwork_url <- read.csv(text = gsheet2text("https://docs.google.com/spreadsheets/d/1_frMB6ICtpAxl1r7Vs1suQ625R-ra8oDjII9rr91M1I", format = "csv"), stringsAsFactors = FALSE) %>% pull()
  196.  
  197.  
  198. actionnetwork_df <- read.xlsx(actionnetwork_url) %>%
  199. clean_names() %>%
  200. select(-c(tm)) %>%
  201. filter(!is.na(projection)) %>%
  202. mutate(game_number = ceiling(row_number()/2)) %>%
  203. rowwise() %>%
  204. mutate(actionnetwork_prob = spread_to_prob(projection)) %>%
  205. ungroup() %>%
  206. left_join(., team_table, by = c("team" = "name")) %>%
  207. mutate(team = abbr) %>%
  208. select(-c(location, full_name, odds, edge, conf, abbr, full_name)) %>%
  209. mutate(side = ifelse(row_number()%%2 == 1, "away_team", "home_team")) %>%
  210. pivot_wider(names_from = side, values_from = c(team, projection, actionnetwork_prob)) %>%
  211. select(-game_number) %>%
  212. rename("away_team" = "team_away_team", "home_team" = "team_home_team", "actionnetwork_away_spread" = "projection_away_team", "actionnetwork_home_spread" = "projection_home_team", "actionnetwork_away_prob" = "actionnetwork_prob_away_team", "actionnetwork_home_prob" = "actionnetwork_prob_home_team") %>%
  213. mutate(game_id = paste0(away_team, " - ", home_team)) %>%
  214. select(game_id, everything()) %>%
  215. rename("away_spread" = "actionnetwork_away_spread", "home_spread" = "actionnetwork_home_spread", "away_prob" = "actionnetwork_away_prob", "home_prob" = "actionnetwork_home_prob") %>%
  216. mutate(site = "action") %>%
  217. select(site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread)
  218.  
  219.  
  220. # oddsshark ---------------------------------------------------------------
  221.  
  222.  
  223. oddsshark_url <- "https://www.oddsshark.com/nfl/computer-picks"
  224. oddsshark_count <- read_html(oddsshark_url) %>%
  225. html_nodes(xpath = '/html/body/div[1]/div[2]/main/div[2]/div/article/div/div[2]/div/div[2]/div[1]/div') %>%
  226. html_text() %>%
  227. str_count(., "/") / 3 +1
  228.  
  229.  
  230. oddsshark_df <- data.frame()
  231.  
  232. for (n in 1:oddsshark_count){
  233. oddsshark_away_team <- read_html(oddsshark_url) %>% html_nodes(xpath = paste0('/html/body/div[1]/div[2]/main/div[2]/div/article/div/div[2]/div/div[2]/div[1]/div/div[', n, ']/div[2]/table/tbody/tr[2]/td[1]/div/span[1]')) %>% html_text()
  234. oddsshark_home_team <- read_html(oddsshark_url) %>% html_nodes(xpath = paste0('/html/body/div[1]/div[2]/main/div[2]/div/article/div/div[2]/div/div[2]/div[1]/div/div[', n, ']/div[2]/table/tbody/tr[2]/td[1]/div/span[3]')) %>% html_text()
  235. oddsshark_away_score <- read_html(oddsshark_url) %>% html_nodes(xpath = paste0('/html/body/div[1]/div[2]/main/div[2]/div/article/div/div[2]/div/div[2]/div[1]/div/div[', n, ']/div[2]/table/tbody/tr[2]/td[2]/div/span[2]')) %>% html_text()
  236. oddsshark_home_score <- read_html(oddsshark_url) %>% html_nodes(xpath = paste0('/html/body/div[1]/div[2]/main/div[2]/div/article/div/div[2]/div/div[2]/div[1]/div/div[', n, ']/div[2]/table/tbody/tr[3]/td[1]/div/span[2]')) %>% html_text()
  237. iteration_result <- data.frame(
  238. game = n,
  239. away_team = ifelse(length(oddsshark_away_team) == 0, NA, oddsshark_away_team),
  240. home_team = ifelse(length(oddsshark_home_team) == 0, NA, oddsshark_home_team),
  241. oddsshark_away_score = ifelse(length(oddsshark_away_score) == 0, NA, oddsshark_away_score),
  242. oddsshark_home_score = ifelse(length(oddsshark_home_score) == 0, NA, oddsshark_home_score)
  243. )
  244. oddsshark_df <- rbind(oddsshark_df, iteration_result)
  245. }
  246.  
  247. oddsshark_df2 <- oddsshark_df %>%
  248. left_join(., team_table, by = c("away_team" = "name")) %>%
  249. mutate(away_team = full_name) %>%
  250. select(-c(location, full_name)) %>%
  251. left_join(., team_table, by = c("home_team" = "name")) %>%
  252. mutate(home_team = full_name) %>%
  253. select(-c(location, full_name)) %>%
  254. filter(!is.na(away_team)) %>%
  255. mutate(oddsshark_home_score = as.numeric(oddsshark_home_score),
  256. oddsshark_away_score = as.numeric(oddsshark_away_score),
  257. oddsshark_home_spread = oddsshark_away_score - oddsshark_home_score,
  258. oddsshark_away_spread = oddsshark_home_score - oddsshark_away_score) %>%
  259. rowwise() %>%
  260. mutate(oddsshark_away_prob = spread_to_prob(oddsshark_away_spread)) %>%
  261. ungroup() %>%
  262. rowwise() %>%
  263. mutate(oddsshark_home_prob = spread_to_prob(oddsshark_home_spread)) %>%
  264. ungroup() %>%
  265. select(-game) %>%
  266. mutate(away_team = abbr.x,
  267. home_team = abbr.y,
  268. game_id = paste0(away_team, " - ", home_team)) %>%
  269. select(game_id, everything()) %>%
  270. select(-c(abbr.x,abbr.y)) %>%
  271. rename("away_points" = "oddsshark_away_score", "home_points" = "oddsshark_home_score", "home_spread" = "oddsshark_home_spread", "away_spread" = "oddsshark_away_spread", "home_prob" = "oddsshark_home_prob", "away_prob" = "oddsshark_away_prob") %>%
  272. mutate(total = away_points+home_points,
  273. site = "shark") %>%
  274. select(site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread, away_points, home_points, total)
  275.  
  276.  
  277.  
  278.  
  279. # dimers ------------------------------------------------------------------
  280.  
  281.  
  282. dimers_url <- "https://www.dimers.com/bet-hub/nfl/schedule"
  283. dimers_df <- read_html(dimers_url) %>%
  284. html_nodes(xpath = '/html/body/app-root/main/app-fixture-page/div[1]/app-match-list-block/div/div[2]') %>%
  285. html_text() %>%
  286. strsplit(",") %>% # Split by comma
  287. unlist() %>% # Flatten the list
  288. data.frame(Strings = .) %>%
  289. mutate(across(Strings, ~map(.x, split_string_space))) %>%
  290. unnest_wider(everything(), names_sep = "_") %>%
  291. filter(!is.na(Strings_3), grepl("%", Strings_7)) %>%
  292. select("away_team" = "Strings_5", "home_team" = "Strings_11", "dimers_away_prob" = "Strings_7", "dimers_home_prob" = "Strings_13") %>%
  293. mutate(dimers_away_prob = as.numeric(sub("%", "", dimers_away_prob))/100,
  294. dimers_home_prob = as.numeric(sub("%", "", dimers_home_prob))/100) %>%
  295. left_join(., team_table, by = c("away_team" = "name")) %>%
  296. mutate(away_team = full_name) %>%
  297. select(-c(location, full_name)) %>%
  298. left_join(., team_table, by = c("home_team" = "name")) %>%
  299. mutate(home_team = full_name) %>%
  300. select(-c(location, full_name)) %>%
  301. filter(!is.na(away_team)) %>%
  302. rowwise() %>%
  303. mutate(dimers_home_spread = prob_to_spread(dimers_home_prob)) %>%
  304. ungroup() %>%
  305. rowwise() %>%
  306. mutate(dimers_away_spread = prob_to_spread(dimers_away_prob)) %>%
  307. ungroup() %>%
  308. mutate(away_team = abbr.x,
  309. home_team = abbr.y) %>%
  310. select(-c(abbr.x, abbr.y)) %>%
  311. mutate(game_id = paste0(away_team, " - ", home_team)) %>%
  312. select(game_id, everything()) %>%
  313. rename("away_prob" = "dimers_away_prob", "home_prob" = "dimers_home_prob", "away_spread" = "dimers_away_spread", "home_spread" = "dimers_home_spread") %>%
  314. mutate(site = "dimers") %>%
  315. select(site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread)
  316.  
  317.  
  318.  
  319. # dratings ----------------------------------------------------------------
  320.  
  321. dratings_url1 <- "https://www.dratings.com/predictor/nfl-football-predictions/upcoming/1#scroll-upcoming"
  322. dratings_raw1 <- ifelse(length(html_table(read_html(dratings_url1))) == 4, html_table(read_html(dratings_url1))[1], NA)[[1]]
  323. dratings_url2 <- "https://www.dratings.com/predictor/nfl-football-predictions/upcoming/2#scroll-upcoming"
  324. dratings_raw2 <- ifelse(length(html_table(read_html(dratings_url2))) == 4, html_table(read_html(dratings_url2))[1], NA)[[1]]
  325. dratings_url3 <- "https://www.dratings.com/predictor/nfl-football-predictions/upcoming/3#scroll-upcoming"
  326. dratings_raw3 <- ifelse(length(html_table(read_html(dratings_url3))) == 4, html_table(read_html(dratings_url3))[1], NA)[[1]]
  327. dratings_url4 <- "https://www.dratings.com/predictor/nfl-football-predictions/upcoming/4#scroll-upcoming"
  328. dratings_raw4 <- ifelse(length(html_table(read_html(dratings_url4))) == 4, html_table(read_html(dratings_url4))[1], NA)[[1]]
  329. dratings_url5 <- "https://www.dratings.com/predictor/nfl-football-predictions/upcoming/5#scroll-upcoming"
  330. dratings_raw5 <- ifelse(length(html_table(read_html(dratings_url5))) == 4, html_table(read_html(dratings_url5))[1], NA)[[1]]
  331. dratings_url6 <- "https://www.dratings.com/predictor/nfl-football-predictions/upcoming/6#scroll-upcoming"
  332. dratings_raw6 <- ifelse(length(html_table(read_html(dratings_url6))) == 4, html_table(read_html(dratings_url6))[1], NA)[[1]]
  333.  
  334. df_list <- list(dratings_raw1, dratings_raw2, dratings_raw3, dratings_raw4, dratings_raw5, dratings_raw6)
  335.  
  336. filtered_df_list <- lapply(df_list, function(df) {
  337. if (is.data.frame(df)) {
  338. df <- df %>% filter_all(any_vars(!is.na(.)))
  339. if (nrow(df) > 0) {
  340. return(df)
  341. }
  342. }
  343. return(NULL)
  344. })
  345.  
  346. # Remove NULL entries and bind rows
  347. filtered_df_list <- do.call(rbind, Filter(Negate(is.null), filtered_df_list))
  348.  
  349.  
  350. dratings1 <- filtered_df_list %>%
  351. select(c(Teams, Win, Points)) %>%
  352. clean_names() %>%
  353. as.data.frame() %>%
  354. separate(win, into = c("away_ml_dr", "home_ml_dr"), sep = "%") %>%
  355. mutate(away_points_dr = substr(points, 1, 4),
  356. home_points_dr = substr(points, 5, nchar(points)))
  357.  
  358. pattern1 <- paste(team_table$full_name, collapse = "|")
  359. matches1 <- str_extract_all(dratings1$teams, pattern1)
  360. dratings1$away_team <- sapply(matches1, function(x) x[1])
  361. dratings1$home_team <- sapply(matches1, function(x) x[2])
  362.  
  363. dratings_df <- dratings1 %>%
  364. left_join(., team_table, by = join_by("away_team" == "full_name")) %>%
  365. mutate(away_team = abbr) %>%
  366. select(-c(location, name, abbr)) %>%
  367. left_join(., team_table, by = join_by("home_team" == "full_name")) %>%
  368. mutate(home_team = abbr) %>%
  369. select(-c(location, name, abbr, points, teams)) %>%
  370. mutate(game_id = paste0(away_team, " - ", home_team),
  371. away_points_dr = as.numeric(away_points_dr),
  372. home_points_dr = as.numeric(home_points_dr),
  373. away_ml_dr = as.numeric(away_ml_dr) / 100,
  374. home_ml_dr = as.numeric(home_ml_dr) / 100,
  375. total_points_dr = away_points_dr + home_points_dr,
  376. home_spread_dr = away_points_dr - home_points_dr,
  377. away_spread_dr = -home_spread_dr) %>%
  378. select(c(game_id, away_team, home_team, away_ml_dr, home_ml_dr, away_points_dr, home_points_dr, total_points_dr, away_spread_dr, home_spread_dr)) %>%
  379. rename("away_prob" = "away_ml_dr", "home_prob" = "home_ml_dr", "away_points" = "away_points_dr", "home_points" = "home_points_dr", "away_spread" = "away_spread_dr", "home_spread" = "home_spread_dr", "total" = "total_points_dr") %>%
  380. mutate(site = "dratings") %>%
  381. select(site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread, away_points, home_points, total)
  382.  
  383.  
  384. # the athletic ------------------------------------------------------------
  385.  
  386.  
  387.  
  388. athletic_raw <- read.csv(text = gsheet2text("https://docs.google.com/spreadsheets/d/1RQCAGCBGofH6RauXLfumxs1wkgYXw-sFVRr-ZPpdQKc", format = "csv"), stringsAsFactors = FALSE)
  389. athletic_week <- read.csv(text = gsheet2text("https://docs.google.com/spreadsheets/d/1RQCAGCBGofH6RauXLfumxs1wkgYXw-sFVRr-ZPpdQKc", format = "csv"), stringsAsFactors = FALSE)[1,1]
  390.  
  391.  
  392. athletic_df <- athletic_raw %>%
  393. select(c(team, xmov, xtot, xwin)) %>%
  394. mutate(xwin = as.integer(gsub("%", "", xwin))/100,
  395. game_number = ceiling(row_number()/2),
  396. xmov = ifelse(xmov == "even", 0, as.double(xmov))) %>%
  397. left_join(., team_table, by = c("team" = "name")) %>%
  398. mutate(team = abbr) %>%
  399. select(-c(location, full_name, abbr)) %>%
  400. pivot_longer(cols = c(xmov, xtot, xwin), names_to = "stat_name", values_to = "stat_num") %>%
  401. filter(!is.na(stat_num)) %>%
  402. pivot_wider(names_from = stat_name , values_from = c(team, stat_num)) %>%
  403. unnest_wider(col = team_xwin, names_sep = "_") %>%
  404. rename("away_team" = "team_xwin_1", "home_team" = "team_xwin_2") %>%
  405. unnest_wider(col = stat_num_xwin, names_sep = "_") %>%
  406. rename("away_prob" = "stat_num_xwin_1", "home_prob" = "stat_num_xwin_2") %>%
  407. unnest_wider(col = team_xmov, names_sep = "_") %>%
  408. unnest_wider(col = team_xtot, names_sep = "_") %>%
  409. unnest_wider(col = stat_num_xmov, names_sep = "_") %>%
  410. unnest_wider(col = stat_num_xtot, names_sep = "_") %>%
  411. rename("total" = "stat_num_xtot_1") %>%
  412. mutate(home_spread = ifelse(home_prob > away_prob, stat_num_xmov_1, -stat_num_xmov_1),
  413. game_id = paste0(away_team, " - ", home_team),
  414. home_points = (total / 2) - (home_spread / 2),
  415. away_points = (total / 2) + (home_spread / 2)) %>%
  416. mutate(away_spread = -home_spread,
  417. site = "athletic") %>%
  418. select(site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread, away_points, home_points, total) %>%
  419. as.data.frame()
  420.  
  421.  
  422.  
  423.  
  424. # final plays -----------------------------------------------------------
  425.  
  426. predictions_df <- bind_rows(actionnetwork_df, oddsshark_df2, dimers_df, dratings_df, athletic_df) %>%
  427. mutate(type = "projection") %>%
  428. inner_join(., odds_df %>% select(game_id, commence_time, week), by = "game_id", relationship = "many-to-many") %>%
  429. select(c(commence_time, week, type, site, game_id, away_team, home_team, away_prob, home_prob, away_spread, home_spread, away_points, home_points, total))
  430.  
  431.  
  432. nfl_game_data <- bind_rows(odds_df, predictions_df) %>%
  433. filter(!is.na(commence_time)) %>%
  434. select(-c(type)) %>%
  435. pivot_wider(names_from = c(site), values_from = c(away_prob, home_prob, away_spread, home_spread, away_points, home_points, total), values_fn = mean) %>%
  436. mutate(favorite_team = ifelse(home_spread_dk < 0, home_team, away_team),
  437. favorite_spread_book = ifelse(home_spread_dk < 0, home_spread_dk, away_spread_dk)) %>%
  438. left_join(., teams_colors_logos %>% select(team_abbr, team_logo_espn), by = join_by("favorite_team" == "team_abbr")) %>%
  439. mutate(favorite_team_icon = team_logo_espn) %>%
  440. select(-any_of(c("team_logo_espn", "away_points_action", "away_points_dimers", "home_points_action", "home_points_dimers"))) %>%
  441. left_join(., teams_colors_logos %>% select(team_abbr, team_logo_espn), by = join_by("away_team" == "team_abbr")) %>%
  442. rename("away_team_icon" = "team_logo_espn") %>%
  443. left_join(., teams_colors_logos %>% select(team_abbr, team_logo_espn), by = join_by("home_team" == "team_abbr")) %>%
  444. rename("home_team_icon" = "team_logo_espn") %>%
  445. select_if(~!all(is.na(.))) %>%
  446. mutate(#action
  447. favorite_spread_delta_home_action = ifelse("home_spread_action" %in% names(.) & favorite_team == home_team, home_spread_action - home_spread_dk, NA),
  448. favorite_spread_delta_away_action = ifelse("away_spread_action" %in% names(.) & favorite_team == away_team, away_spread_action - away_spread_dk, NA),
  449. favorite_spread_delta_action = ifelse(is.na(favorite_spread_delta_home_action), favorite_spread_delta_away_action, favorite_spread_delta_home_action),
  450. #athletic
  451. favorite_spread_delta_home_athletic = ifelse("home_spread_athletic" %in% names(.) & favorite_team == home_team, home_spread_athletic - home_spread_dk, NA),
  452. favorite_spread_delta_away_athletic = ifelse("away_spread_athletic" %in% names(.) & favorite_team == away_team, away_spread_athletic - away_spread_dk, NA),
  453. favorite_spread_delta_athletic = ifelse(is.na(favorite_spread_delta_home_athletic), favorite_spread_delta_away_athletic, favorite_spread_delta_home_athletic),
  454. #dratings
  455. favorite_spread_delta_home_dratings = ifelse("home_spread_dratings" %in% names(.) & favorite_team == home_team, home_spread_dratings - home_spread_dk, NA),
  456. favorite_spread_delta_away_dratings = ifelse("away_spread_dratings" %in% names(.) & favorite_team == away_team, away_spread_dratings - away_spread_dk, NA),
  457. favorite_spread_delta_dratings = ifelse(is.na(favorite_spread_delta_home_dratings), favorite_spread_delta_away_dratings, favorite_spread_delta_home_dratings),
  458. #dimers
  459. favorite_spread_delta_home_dimers = ifelse("home_spread_dimers" %in% names(.) & favorite_team == home_team, home_spread_dimers - home_spread_dk, NA),
  460. favorite_spread_delta_away_dimers = ifelse("away_spread_dimers" %in% names(.) & favorite_team == away_team, away_spread_dimers - away_spread_dk, NA),
  461. favorite_spread_delta_dimers = ifelse(is.na(favorite_spread_delta_home_dimers), favorite_spread_delta_away_dimers, favorite_spread_delta_home_dimers),
  462. #oddsshark
  463. favorite_spread_delta_home_shark = ifelse("home_spread_shark" %in% names(.) & favorite_team == home_team, home_spread_shark - home_spread_dk, NA),
  464. favorite_spread_delta_away_shark = ifelse("away_spread_shark" %in% names(.) & favorite_team == away_team, away_spread_shark - away_spread_dk, NA),
  465. favorite_spread_delta_shark = ifelse(is.na(favorite_spread_delta_home_shark), favorite_spread_delta_away_shark, favorite_spread_delta_home_shark)) %>%
  466. select(!starts_with("favorite_spread_delta_away")) %>%
  467. select(!starts_with("favorite_spread_delta_home")) %>%
  468. rowwise() %>%
  469. mutate(total_delta_athletic = ifelse("total_athletic" %in% names(.), total_athletic - total_dk, NA),
  470. total_delta_dratings = ifelse("total_dratings" %in% names(.), total_dratings - total_dk, NA),
  471. total_delta_shark = ifelse("total_shark" %in% names(.), total_shark - total_dk, NA)) %>%
  472. select_if(~!all(is.na(.))) %>%
  473. mutate(game_time = paste(weekdays(commence_time), format(commence_time, "%I:%M%p")),
  474. game_time = gsub(" 0", " ", game_time)) %>%
  475. arrange(commence_time) %>%
  476. mutate(favorite_and_spread = paste0(favorite_team, " ", favorite_spread_book)) %>%
  477. select(any_of(c("game_time", "away_team_icon", "away_team", "home_team", "home_team_icon", "favorite_and_spread",
  478. "away_points_athletic", "home_points_athletic", "away_points_dratings", "home_points_dratings", "away_points_shark", "home_points_shark",
  479. "favorite_spread_delta_athletic", "favorite_spread_delta_action", "favorite_spread_delta_dratings", "favorite_spread_delta_dimers", "favorite_spread_delta_shark",
  480. "total_delta_athletic", "total_delta_dratings", "total_delta_shark")))
  481.  
  482. projection_count <- nrow(unique(predictions_df %>% filter(!is.na(home_points)) %>% select(site)))
  483. spread_delta_count <- nrow(unique(predictions_df %>% filter(!is.na(home_spread)) %>% select(site)))
  484. total_delta_count <- projection_count
  485.  
  486. #projection_count<-3
  487. #spread_delta_count<-5
  488.  
  489. short <- c(9,16)
  490. long <- c(9, 11, 19, 20)
  491. dotted_line_vector <- if(projection_count == 2 & spread_delta_count == 3) short else long
  492.  
  493. nfl_game_gt <- try({nfl_game_data %>%
  494. group_by(game_time) %>%
  495. gt() %>%
  496. gt_img_rows(columns = away_team_icon) %>%
  497. gt_img_rows(columns = home_team_icon) %>%
  498. fmt_number(columns = contains("points"), decimals = 1) %>%
  499. fmt_number(columns = contains("total_delta"), decimals = 1, force_sign = TRUE) %>%
  500. fmt_number(columns = contains("spread_delta"), decimals = 1, force_sign = TRUE) %>%
  501. tab_spanner(columns = contains("points_dratings"),
  502. label = "DRatings",
  503. id = "projection_dratings") %>%
  504. tab_spanner(columns = contains("points_athletic"),
  505. label = "The Athletic",
  506. id = "projection_athletic") %>%
  507. tab_spanner(columns = contains("points_shark"),
  508. label = "OddsShark",
  509. id = "projection_shark") %>%
  510. tab_spanner(spanners = contains("projection"),
  511. label = "Projections") %>%
  512. tab_spanner(columns = contains("spread_delta"),
  513. label = "Spread",
  514. id = "spread_delta") %>%
  515. tab_spanner(columns = contains("total_delta"),
  516. label = "Total",
  517. id = "total_delta") %>%
  518. cols_label(contains("favorite_spread_delta_dratings") ~ "DRatings",
  519. contains("favorite_spread_delta_action") ~ "Action",
  520. contains("favorite_spread_delta_athletic") ~ "Athletic",
  521. contains("favorite_spread_delta_shark") ~ "Shark",
  522. contains("favorite_spread_delta_dimers") ~ "Dimers",
  523. contains("total_delta_athletic") ~ "Athletic",
  524. contains("total_delta_shark") ~ "Shark",
  525. contains("total_delta_dratings") ~ "DRatings",
  526. contains("away_points") ~ "Away",
  527. contains("home_points") ~ "Home",
  528. contains("away_team") ~ "AWAY",
  529. contains("home_team") ~ "HOME",
  530. contains("icon") ~ "",
  531. contains("favorite_and_spread") ~ "Spread") %>%
  532. tab_spanner(columns = contains("spread_delta"),
  533. spanners = c("spread_delta", "total_delta"),
  534. label = "Deltas") %>%
  535. tab_header(paste0(nfl_week, " Games")) %>%
  536. data_color(columns = contains("spread_delta"),
  537. bins = c(-11, -2, 0, 2, 11),
  538. method = "bin",
  539. palette = c("#bf90ee", "white", "white", "lightgreen"),
  540. na_color = "white") %>%
  541. data_color(columns = contains("total_delta"),
  542. bins = c(-11, -2, 0, 2, 11),
  543. method = "bin",
  544. palette = c("#90bfee", "white", "white", "#eebf90"),
  545. na_color = "white") %>%
  546. data_color(columns = contains("home_points"),
  547. palette = c("white", "#ee9090"),
  548. domain = c(12, 36),
  549. na_color = "white") %>%
  550. data_color(columns = contains("away_points"),
  551. palette = c("white", "#ee9090"),
  552. domain = c(12, 36),
  553. na_color = "white") %>%
  554. cols_align(align = "center") %>%
  555. cols_align(columns = "away_team_icon", align = "right") %>%
  556. cols_align(columns = "home_team_icon", align = "left") %>%
  557. tab_style(style = cell_borders(sides = c("right"), style = "solid", weight = px(3)),
  558. locations = list(cells_body(columns = c(home_points_shark, favorite_and_spread)),
  559. cells_column_labels(columns = c(home_points_shark, favorite_and_spread)))) %>%
  560. tab_style(style = cell_borders(sides = c("right"), style = "solid"),
  561. locations = list(cells_body(columns = contains("home_points_athletic")),
  562. cells_column_labels(columns = contains("home_points_athletic")))) %>%
  563. tab_style(style = cell_borders(sides = c("right"), style = "solid"),
  564. locations = list(cells_body(columns = contains("home_points_drating")),
  565. cells_column_labels(columns = contains("home_points_drating")))) %>%
  566. tab_style(style = cell_borders(sides = c("right"), style = "solid", weight = px(3)),
  567. locations = list(cells_body(columns = favorite_spread_delta_shark),
  568. cells_column_labels(columns = favorite_spread_delta_shark))) %>%
  569. tab_source_note(source_note = md("Odds provided by **odds-api.com**; projections provided by **theathletic.com**, **actionnetwork.com**, **dratings.com**, **dimers.com**, and **oddsshark.com**")) %>%
  570. tab_style(style = cell_text(weight = "bold"),
  571. locations = list(cells_row_groups(),
  572. cells_column_spanners())) %>%
  573. cols_width(contains("delta") ~ px(80),
  574. favorite_and_spread ~ px(90))},
  575. silent = TRUE)
  576.  
  577.  
  578. ifelse(class(nfl_game_gt) != "try-error",
  579. gtsave(nfl_game_gt,
  580. expand = 1000, filename = "NFL_Game_Values.png", vheight = 300, vwidth =1500),
  581. NA)
  582.  
  583.  
  584. # predictions -------------------------------------------------------------
  585.  
  586. current <- try({read_rds(file = paste0("NFL/predictions_games.rds"))}, silent = TRUE)
  587. new <- bind_rows(odds_df, predictions_df) %>%
  588. filter(!is.na(commence_time)) %>%
  589. select(-c(type)) %>%
  590. pivot_wider(names_from = c(site), values_from = c(away_prob, home_prob, away_spread, home_spread, away_points, home_points, total), values_fn = mean) %>%
  591. mutate(append_filter = as.integer(as.Date(commence_time) - today())) %>%
  592. filter(append_filter == 0) %>%
  593. bind_rows(., current)
  594.  
  595. write_rds(new, file = paste0("NFL/predictions_games.rds"))
Advertisement
Add Comment
Please, Sign In to add comment