Assignment 4

Author

Brennan Stout

Published

October 5, 2026

Web scraping and APIs

# install.packages(c("rvest", "dplyr", "tidyr", "stringr",
#                    "readr", "polite", "janitor", "WDI"))
# install.packages("robotstxt")

library(rvest)
Warning: package 'rvest' was built under R version 4.5.3
library(dplyr)
Warning: package 'dplyr' was built under R version 4.5.3

Attaching package: 'dplyr'
The following objects are masked from 'package:stats':

    filter, lag
The following objects are masked from 'package:base':

    intersect, setdiff, setequal, union
library(stringr)
Warning: package 'stringr' was built under R version 4.5.3
library(readr)
Warning: package 'readr' was built under R version 4.5.3

Attaching package: 'readr'
The following object is masked from 'package:rvest':

    guess_encoding
## ---- 0. Ask permission first ----------------------------------------------
## Always before the first request. robotstxt::paths_allowed() returns TRUE or
## FALSE for the exact path you intend to fetch.

robotstxt::paths_allowed("https://en.wikipedia.org/wiki/List_of_countries_by_foreign-exchange_reserves")

 en.wikipedia.org                      
[1] TRUE
## ---- 1. The sandbox: books.toscrape.com ------------------------------------
## Built and published for scraping practice. 1,000 books, 50 pages, no
## JavaScript. Learn the verbs here before you point them at anyone's server.

books_pg <- read_html("https://books.toscrape.com/catalogue/page-1.html")

books <- tibble(
  title  = books_pg |> html_elements("article.product_pod h3 a") |> html_attr("title"),
  price  = books_pg |> html_elements("article.product_pod p.price_color") |> html_text2(),
  rating = books_pg |> html_elements("article.product_pod p.star-rating") |>
    html_attr("class") |> str_remove("star-rating ")
) |>
  mutate(price_gbp = parse_number(price))

head(books)
# A tibble: 6 × 4
  title                                 price  rating price_gbp
  <chr>                                 <chr>  <chr>      <dbl>
1 A Light in the Attic                  £51.77 Three       51.8
2 Tipping the Velvet                    £53.74 One         53.7
3 Soumission                            £50.10 One         50.1
4 Sharp Objects                         £47.82 Four        47.8
5 Sapiens: A Brief History of Humankind £54.23 Five        54.2
6 The Requiem Red                       £22.65 One         22.7
library(knitr)
library(kableExtra)
Warning: package 'kableExtra' was built under R version 4.5.2

Attaching package: 'kableExtra'
The following object is masked from 'package:dplyr':

    group_rows
## ---- 2. The Wikipedia table -----------------------------------------------
## html_table() does the parsing. The work is everything after it.

wiki_url <- paste0("https://en.wikipedia.org/wiki/",
                   "List_of_countries_by_foreign-exchange_reserves")

wiki_pg <- read_html(wiki_url)

## Never assume the table you want is [[1]]. Look first.
tabs <- wiki_pg |> html_elements("table.wikitable")
length(tabs)                      # how many candidates?
[1] 2
tabs |> html_table() |> lapply(\(x) dim(x))
[[1]]
[1] 198   8

[[2]]
[1] 28 13
reserves_raw <- tabs[[1]] |> html_table()
glimpse(reserves_raw)
Rows: 198
Columns: 8
$ `Country(as recognized by the UN)` <chr> "Country(as recognized by the UN)",…
$ Continent                          <chr> "Continent", "Continent", "Asia", "…
$ `Foreign exchange reserves`        <chr> "Including gold", "US$ million", "3…
$ `Foreign exchange reserves`        <chr> "Including gold", "Change", "4,299"…
$ `Foreign exchange reserves`        <chr> "Excluding gold", "US$ million", "3…
$ `Foreign exchange reserves`        <chr> "Excluding gold", "Change", "115,49…
$ `Last reporteddate`                <chr> "Last reporteddate", "Last reported…
$ Ref.                               <chr> "Ref.", "Ref.", "[3]", "[4]", "[5]"…
## Clean-up. Wikipedia tables arrive with footnote markers, thin spaces,
## multi-row headers and a stray total row. Expect to redo this when the
## article is edited — which is the point of the exercise.
new_names <- c('a_1', 'a_2', 'a_3', 'a_4', 'a_5', 'a_6', 'a_7', 'a_8')
names(reserves_raw) <- make.unique(dput(names(reserves_raw)))
c("Country(as recognized by the UN)", "Continent", "Foreign exchange reserves", 
"Foreign exchange reserves", "Foreign exchange reserves", "Foreign exchange reserves", 
"Last reporteddate", "Ref.")
reserves_raw %>% 
  rename_with(~new_names)
# A tibble: 198 × 8
   a_1                              a_2      a_3   a_4   a_5   a_6   a_7   a_8  
   <chr>                            <chr>    <chr> <chr> <chr> <chr> <chr> <chr>
 1 Country(as recognized by the UN) Contine… Incl… Incl… Excl… Excl… Last… Ref. 
 2 Country(as recognized by the UN) Contine… US$ … Chan… US$ … Chan… Last… Ref. 
 3 China                            Asia     3,85… 4,299 3,50… 115,… 1 Au… [3]  
 4 Japan                            Asia     1,28… 18,4… 1,25… 16,2… 30 J… [4]  
 5 Switzerland                      Europe   939,… 13,9… 932,… 24,4… 30 J… [5]  
 6 India                            Asia     785,… 45,2… 671,… 56,7… 04 S… [6]  
 7 Russia                           Europe/… 761,… 5,600 434,… 1,517 21 A… [7]  
 8 Taiwan                           Asia     597,… 7,920 544,… 1,071 30 J… [8]  
 9 Saudi Arabia                     Asia     487,… 60,3… 494,… 60,3… 31 M… [9]  
10 Hong Kong *                      Asia     445,… 20,7… 441,… 25,5… 30 J… [10] 
# ℹ 188 more rows
reserves <- reserves_raw %>%
  slice(-(1:2)) %>%
  setNames(c(
    "country",
    "continent",
    "reserves_inc_gold_usd_m",
    "reserves_inc_gold_change",
    "reserves_exc_gold_usd_m",
    "reserves_exc_gold_change",
    "last_reported_date",
    "reference"
  )) %>%
  mutate(
    across(
      c(reserves_inc_gold_usd_m, reserves_inc_gold_change,
        reserves_exc_gold_usd_m, reserves_exc_gold_change),
      readr::parse_number
    ),
    reference = readr::parse_number(reference)
  ) %>%
   as.data.frame()
Warning: There were 3 warnings in `mutate()`.
The first warning was:
ℹ In argument: `across(...)`.
Caused by warning:
! 154 parsing failures.
row col expected                                                                                                                                                                                                 actual
 18  -- a number —.mw-parser-output .sr-only{border:0;clip:rect(0,0,0,0);clip-path:polygon(0px 0px,0px 0px,0px 0px);height:1px;margin:-1px;overflow:hidden;padding:0;position:absolute;width:1px;white-space:nowrap}N/a
 23  -- a number —N/a                                                                                                                                                                                                  
 25  -- a number —N/a                                                                                                                                                                                                  
 26  -- a number —N/a                                                                                                                                                                                                  
 30  -- a number —N/a                                                                                                                                                                                                  
... ... ........ ......................................................................................................................................................................................................
See problems(...) for more details.
ℹ Run `dplyr::last_dplyr_warnings()` to see the 2 remaining warnings.
reserves %>%
  kable(
    format = "html",
    col.names = c("Country", "Continent", "Reserves ($M)", "Change", "Reserves ($M)", "Change", "Date", "Ref"),
    format.args = list(big.mark = ",")
  ) %>%
  kable_styling(bootstrap_options = c("striped", "hover", "condensed")) %>%
  add_header_above(c(" " = 2, "Including Gold" = 2, "Excluding Gold" = 2, " " = 2))
Including Gold
Excluding Gold
Country Continent Reserves ($M) Change Reserves ($M) Change Date Ref
China Asia 3,854,885 4,299.000 3,504,805 115,499 1 August 2026 3
Japan Asia 1,287,470 18,400.000 1,259,248 16,230 30 June 2026 4
Switzerland Europe 939,140 13,935.000 932,282 24,490 30 June 2026 5
India Asia 785,710 45,290.000 671,900 56,790 04 September 2026 6
Russia Europe/Asia 761,200 5,600.000 434,487 1,517 21 August 2026 7
Taiwan Asia 597,150 7,920.000 544,300 1,071 30 June 2026 8
Saudi Arabia Asia 487,370 60,367.000 494,482 60,366 31 May 2026 9
Hong Kong * Asia 445,900 20,700.000 441,788 25,572 30 June 2026 10
South Korea Asia 427,400 400.000 423,100 12,200 30 June 2026 11
Singapore Asia 426,830 43,535.000 419,329 44,520 30 June 2026 12
Brazil Americas 366,913 21,658.000 344,173 361 30 Apr 2026 13
Germany Europe 345,338 9,863.000 91,071 9,275 1 Oct 2024 14
Thailand Asia 300,180 62,313.000 269,687 52,456 1 Jul 2026 15
Italy Europe 279,631 14,225.000 79,064 1,240 1 Nov 2024 16
France Europe 272,693 1,132.000 66,641 143 1 Nov 2024 17
Mexico Americas 255,605 1,495.000 236,200 9 30 Jan 2026 18
United States Americas 253,767 811.000 242,726 811 22 Aug 2025 19
Israel Asia 231,880 1,560.000 NA NA 6 Oct 2025 20
Poland Europe 223,200 4,800.000 188,140 1,257 7 Jan 2025 21
Turkey Asia 218,158 34,137.000 76,585 12,670 30 Jan 2026 22
United Arab Emirates Asia 210,000 5,340.000 199,400 87 1 Nov 2024 23
United Kingdom Europe 189,228 4,870.000 161,908 5,910 1 Nov 2024 24
Indonesia Asia 159,246 3,382.000 NA NA 1 Nov 2024 25
Czech Republic Europe 149,416 507.000 145,012 168 1 Nov 2024 26
Netherlands Europe 125,451 212.000 NA NA 1 Mar 2024 27
Canada Americas 123,084 4,990.000 NA NA 1 Nov 2024 28
Malaysia Asia 119,700 17,459.000 113,877 14,225 1 Oct 2024 29
Philippines Asia 112,434 328.000 101,081 41 1 Nov 2024 30
Spain Europe 100,983 2.380 77,348 2,300 1 Nov 2024 31
Iraq Asia 100,000 15,000.000 NA NA 25 Mar 2024 32
Romania Europe 95,127 3,585.000 78,224 1,203 31 Jan 2026 33
Vietnam Asia 93,342 1,241.000 NA NA 1 Mar 2024 34
Denmark Europe 93,196 763.000 88,450 273 1 Nov 2024 35
Belgium Europe 82,000 14,200.000 67,200 79 1 Mar 2024 36
Norway Europe 80,110 1,430.000 NA NA 1 Oct 2024 37
Peru Americas 73,483 201.000 NA NA 1 Mar 2024 38
Libya Africa 70,524 238.000 NA NA 1 Mar 2024 39
Algeria Africa 68,028 1,880.000 NA NA 1 Mar 2024 40
South Africa Africa 67,450 1,186.000 54,862 143 31 Mar 2025 41
Australia Oceania 65,018 119.000 57,998 267 7 Nov 2024 42
Qatar Asia 64,560 8,931.000 NA NA 1 Mar 2024 43
Sweden Europe 62,438 271.000 52,395 209 7 Nov 2024 44
Colombia Americas 57,269 124.000 NA NA 8 Mar 2024 45
Portugal Europe 53,710 7,800.000 NA NA 1 Mar 2024 46
Kuwait Asia 46,420 1,112.000 NA NA 1 Mar 2024 47
Chile Americas 42,527 2,373.000 NA NA 1 Mar 2024 48
Hungary Europe 41,344 4,749.000 NA NA 1 Mar 2024 49
Ukraine Europe 40,507 1,212.000 NA NA 1 Mar 2024 50
Bangladesh Asia 37,660 1,552.000 NA NA 03 Jul 2026 51
Argentina Americas 36,625 2,207.000 NA NA 1 Jun 2026 52
Serbia Europe 35,770 4.213 NA NA 11 Sept 2026 53
Bulgaria Europe 35,395 692.000 NA NA 1 Mar 2024 54
Egypt Africa 35,310 3,161.000 NA NA 1 Mar 2024 55
Nigeria Africa 34,980 465.000 NA NA 1 Mar 2024 56
Austria Europe 34,856 954.000 34,671 187 1 Mar 2024 57
Kazakhstan Asia 34,500 938.000 NA NA 1 Mar 2024 58
Uzbekistan Asia 32,195 950.000 NA NA 1 Mar 2024 59
Morocco Africa 32,037 213.000 NA NA 1 Mar 2024 60
New Zealand Oceania 31,712 1,916.000 NA NA 1 Mar 2024 61
Pakistan Asia 26,791 3,885.000 NA NA 19 Sep 2026 NA
Iran Asia 24,300 1,641.000 23,600 210 1 Mar 2024 62
Macau * Asia 24,283 1,566.000 NA NA 1 Mar 2024 63
Guatemala Americas 21,390 1,300.000 NA NA 1 Mar 2024 64
Turkmenistan Asia 20,600 45.000 NA NA 1 Mar 2024 65
Cambodia Asia 18,496 67.000 NA NA 1 Mar 2024 66
Jordan Asia 18,765 187.000 NA NA 1 Mar 2024 67
Nepal Asia 18,400 1,857.000 NA NA 11 Mar 2024 68
Oman Asia 16,163 548.000 NA NA 1 Mar 2024 69
Uruguay Americas 15,449 1.176 15,441 11 1 Mar 2024 70
Lebanon Asia 14,738 692.000 NA NA 1 Mar 2024 71
Dominican Republic Americas 14,371 1,145.000 NA NA 1 Mar 2024 72
Angola Africa 14,200 40.000 NA NA 15 Mar 2024 73
Costa Rica Americas 13,200 320.000 NA NA 1 Mar 2024 74
Ireland Europe 12,599 130.000 11,874 2 1 Mar 2024 75
Azerbaijan Asia 11,650 142.000 NA NA 1 Mar 2024 76
Ivory Coast Africa 9,800 18.000 NA NA 1 Mar 2024 77
Paraguay Americas 9,707 805.000 9,168 7 1 Mar 2024 78
North Korea Asia 9,109 73.000 NA NA 1 Mar 2024 79
Bosnia and Herzegovina Europe 8,711 391.000 NA NA 1 Mar 2024 80
Belarus Europe 8,697 165.000 4,333 19 31 Aug 2024 81
Tunisia Africa 8,623 539.000 NA NA 21 Mar 2024 82
Finland Europe 7,995 22.000 NA NA 1 Mar 2024 83
Slovakia Europe 7,650 441.000 NA NA 1 Mar 2024 84
Honduras Americas 7,390 580.000 NA NA 21 Mar 2024 85
Tanzania Africa 7,022 600.000 NA NA 22 Mar 2024 86
Iceland Europe 6,847 24.000 6,668 9 15 Mar 2024 87
Myanmar Asia 6,700 800.000 NA NA 1 Mar 2024 88
Sri Lanka Asia 6,467 475.000 6,425 2 31 Oct 2024 89
Panama Americas 6,143 200.000 NA NA 1 Mar 2024 90
Venezuela Americas 5,908 776.000 NA NA 1 Mar 2024 91
Trinidad and Tobago Americas 5,800 44.000 NA NA 18 Mar 2024 92
Moldova Europe 5,600 600.000 NA NA 30 Aug 2024 93
Mauritius Africa 5,591 196.000 5,497 27 1 Mar 2024 94
Bahrain Asia 5,500 128.000 NA NA 25 Mar 2024 95
Albania Europe 5,290 200.000 5,290 47 31 Apr 2024 96
Georgia Europe 5,224 25.580 NA NA 25 Mar 2024 97
Mongolia Asia 5,120 500.000 NA NA 20 Mar 2024 98
Botswana Africa 5,080 267.000 NA NA 1 Mar 2024 99
Jamaica Americas 4,921 300.000 NA NA 5 Mar 2024 100
Lithuania Europe 4,900 440.000 NA NA 1 Mar 2024 101
Vatican City Europe 4,339 950.000 NA NA 1 Mar 2024 102
Armenia Asia 4,298 600.000 NA NA 25 Mar 2024 103
Nicaragua Americas 3,980 1,100.000 NA NA 1 Mar 2024 104
Greece Europe 3,926 107.000 3,869 8 1 Mar 2024 105
Latvia Europe 3,913 13.000 NA NA 1 Mar 2024 106
Uganda Africa 3,700 259.000 NA NA 1 Mar 2024 107
Andorra Europe 3,689 11.000 NA NA 20 Mar 2024 108
Brunei Asia 3,664 107.000 NA NA 1 Mar 2024 109
Cameroon Africa 3,459 180.000 NA NA 1 Mar 2024 110
Ethiopia Africa 3,430 170.000 NA NA 1 Mar 2024 111
Ghana Africa 3,368 452.000 NA NA 1 Mar 2024 112
Ecuador Americas 3,305 747.000 NA NA 1 Mar 2024 113
Kyrgyzstan Asia 2,976 193.000 NA NA 1 Mar 2024 114
Croatia Europe 2,935 159.000 NA NA 1 Mar 2024 115
Slovenia Europe 2,519 62.000 NA NA 1 Mar 2024 116
El Salvador Americas 2,510 39.000 NA NA 1 Mar 2024 117
Cuba Americas 2,500 10,391.000 NA NA 15 Mar 2024 118
Kenya Africa 2,490 1,073.000 NA NA 5 Mar 2024 119
Papua New Guinea Oceania 2,339 500.000 NA NA 1 Mar 2024 120
Haiti Americas 2,296 1,256.000 NA NA 1 Mar 2024 121
Estonia Europe 2,065 145.000 NA NA 1 Mar 2024 122
Namibia Africa 2,019 25.000 NA NA 1 Mar 2024 123
Bahamas Americas 1,758 85.000 NA NA 1 Mar 2024 124
Bolivia Americas 1,769 471.000 NA NA 1 Mar 2024 125
Madagascar Africa 1,620 127.000 NA NA 19 Mar 2024 126
Montenegro Europe 1,558 26.000 NA NA 1 Mar 2024 127
Mauritania Africa 1,493 37.000 NA NA 1 Mar 2024 128
Tajikistan Asia 1,482 19.000 NA NA 1 Mar 2024 129
Rwanda Africa 1,458 7.000 NA NA 1 Mar 2024 130
Zambia Africa 6,500 16.000 NA NA 12 JUN 2026 131
Guinea Africa 1,425 33.000 NA NA 15 Mar 2024 133
Gabon Africa 1,377 90.000 NA NA 1 Mar 2024 134
Cyprus Asia 1,271 200.000 NA NA 1 Mar 2024 135
Luxembourg Europe 1,119 34.000 NA NA 5 Mar 2024 136
Laos Asia 1,099 23.000 NA NA 1 Mar 2024 137
Curaçao * Americas 1,080 30.000 NA NA 20 Mar 2024 138
Fiji Oceania 1,065 22.000 NA NA 5 Mar 2024 139
Niger Africa 1,053 24.000 NA NA 1 Mar 2024 140
Aruba * Americas 1,017 30.000 NA NA 15 Mar 2024 141
Bhutan Asia 972 3.000 NA NA 10 Mar 2024 142
Kosovo * Europe 950 15.000 NA NA 1 Mar 2024 143
Malta Europe 937 9.000 NA NA 20 Mar 2024 144
Lesotho Africa 785 11.000 NA NA 1 Mar 2024 145
Barbados Americas 770 2.000 NA NA 1 Mar 2024 146
San Marino Europe 716 243.000 NA NA 1 Mar 2024 147
Cape Verde Africa 712 25.000 NA NA 1 Mar 2024 148
Gambia Africa 698 6.000 NA NA 1 Mar 2024 149
Palestine * Asia 671 12.000 NA NA 1 Mar 2024 150
Timor-Leste Asia 654 2.000 NA NA 1 Mar 2024 151
Suriname Americas 647 30.000 NA NA 8 Mar 2024 152
Maldives Asia 644 6.000 NA NA 1 September 2026 153
Sierra Leone Africa 624 2.000 NA NA 2 Mar 2024 154
Mali Africa 604 19.000 NA NA 1 Mar 2024 155
Guyana Americas 553 20.000 NA NA 10 Mar 2024 156
Solomon Islands Oceania 551 24.000 NA NA 8 Mar 2024 157
Seychelles Africa 546 19.000 NA NA 1 Mar 2024 158
Vanuatu Oceania 509 2.000 NA NA 1 Mar 2024 159
Democratic Republic of the Congo Africa 505 160.000 NA NA 14 Mar 2024 160
Djibouti Africa 504 3.000 NA NA 1 Mar 2024 161
Malawi Africa 488 17.000 NA NA 1 Mar 2024 162
Eswatini Africa 467 27.000 NA NA 1 Mar 2024 163
Afghanistan Asia 443 32.000 NA NA 1 Oct 2024 164
Republic of the Congo Africa 443 20.000 NA NA 1 Mar 2024 165
Syria Asia 401 16.000 NA NA 1 Mar 2024 166
Federated States of Micronesia Oceania 395 2.000 NA NA 1 Mar 2024 167
Central African Republic Africa 375 14.000 NA NA 1 Mar 2024 168
Saint Kitts and Nevis Americas 365 14.000 NA NA 1 Mar 2024 169
Liberia Africa 342 7.000 NA NA 1 Mar 2024 170
Guinea-Bissau Africa 329 3.000 NA NA 1 Mar 2024 171
Antigua and Barbuda Americas 285 6.000 NA NA 1 Mar 2024 172
Belize Americas 281 4.000 NA NA 1 Mar 2024 173
Saint Lucia * Americas 258 2.000 NA NA 1 Mar 2024 174
Yemen Asia 250 5.000 NA NA 1 Mar 2024 175
Grenada Americas 247 11.000 NA NA 1 Mar 2024 176
Tonga Oceania 226 3.000 NA NA 1 Mar 2024 177
Togo Africa 208 7.000 NA NA 1 Mar 2024 178
Comoros Africa 197 5.000 NA NA 1 Mar 2024 179
Saint Vincent and the Grenadines * Americas 192 1.000 NA NA 1 Mar 2024 180
Eritrea Africa 189 2.000 NA NA 1 Mar 2024 181
Samoa Oceania 188 3.000 NA NA 1 Mar 2024 182
São Tomé and Príncipe Africa 186 2.000 NA NA 1 Mar 2024 183
Sudan Africa 172 5.000 NA NA 1 Mar 2024 184
Dominica Americas 168 6.000 NA NA 1 Mar 2024 185
Senegal Africa 164 12.000 NA NA 1 Mar 2024 186
Zimbabwe Africa 159 8.000 NA NA 1 Mar 2024 187
Chad Africa 143 4.000 NA NA 1 Mar 2024 188
Burundi Africa 105 6.000 NA NA 1 Mar 2024 189
South Sudan Africa 80 7.000 NA NA 2 Mar 2024 190
Benin Africa 69 9.000 NA NA 1 Mar 2024 191
Montserrat Americas 54 5.000 NA NA 1 Mar 2024 192
Equatorial Guinea Africa 46 2.000 NA NA 1 Mar 2024 193
Burkina Faso Africa 42 3.000 NA NA 1 Mar 2024 194
Somalia Africa 37 5.000 NA NA 1 Mar 2024 195
Kiribati Oceania 8 2.000 NA NA 1 Mar 2024 196
Mozambique Africa 4 0.800 NA NA 31 Jul 2025 197
North Macedonia Europe 4 0.100 NA NA 31 Aug 2025 198
## ---- 3. The same quantity, from an API -------------------------------------
## Foreign reserves are published by the World Bank as FI.RES.TOTL.CD,
## "Total reserves (includes gold, current US$)". One call, versioned,
## documented, and identical for whoever runs it.

library(WDI)
Warning: package 'WDI' was built under R version 4.5.3
reserves_api <- WDI(indicator = "FI.RES.TOTL.CD",
                    start = 2015, end = 2024, extra = TRUE)
head(reserves_api)
      country iso2c iso3c year FI.RES.TOTL.CD status lastupdated
1 Afghanistan    AF   AFG 2024             NA         2026-07-13
2 Afghanistan    AF   AFG 2023             NA         2026-07-13
3 Afghanistan    AF   AFG 2022             NA         2026-07-13
4 Afghanistan    AF   AFG 2021             NA         2026-07-13
5 Afghanistan    AF   AFG 2020     9748946327         2026-07-13
6 Afghanistan    AF   AFG 2019     8497655795         2026-07-13
                                             region capital longitude latitude
1 Middle East, North Africa, Afghanistan & Pakistan   Kabul   69.1761  34.5228
2 Middle East, North Africa, Afghanistan & Pakistan   Kabul   69.1761  34.5228
3 Middle East, North Africa, Afghanistan & Pakistan   Kabul   69.1761  34.5228
4 Middle East, North Africa, Afghanistan & Pakistan   Kabul   69.1761  34.5228
5 Middle East, North Africa, Afghanistan & Pakistan   Kabul   69.1761  34.5228
6 Middle East, North Africa, Afghanistan & Pakistan   Kabul   69.1761  34.5228
      income lending
1 Low income     IDA
2 Low income     IDA
3 Low income     IDA
4 Low income     IDA
5 Low income     IDA
6 Low income     IDA
## ---- 4. Cache what you pulled ----------------------------------------------
write_csv(reserves, paste0("reserves_wiki_", Sys.Date(), ".csv"))

—- 5. The question this script exists to raise ————————— Compare 2 and 3. Same concept, two data-generating processes: - Wikipedia: edited by volunteers, sourced from many places, no schema, no versioning, no uncertainty, changes without notice - World Bank: one compiler, documented methodology, stable indicator code Scraping was the wrong tool here. Knowing when it is the only tool is the skill this course is actually teaching.

The time stamps on the World Bank data is probably the most imporant part of understanding the scraping, this gives a point of reference to check the data against. While Wikipedia is a decent source, to get those same timestamp if would likely require scraping (or using the api) of each bank being referenced in the table. As is stated, scraping is best when it is the only tool available. APIs or other data access points get around all of those messy data issues which come from even the most successful scraping attempts.

AI note Gemini was used for dealing with the tibble and visualizations.