Upstream repair release. Six data sources changed their URLs, file layouts, or access terms between April and August 2026, and seven code paths were returning wrong or empty data without raising an error. Every source was re-tested against its live endpoint on 2 August 2026, and a weekly canary now watches them.
Every \donttest{} example that reaches an upstream
source is wrapped in try(). 13 blocks were affected. CRAN
runs these in its additional-issues donttest check, on build machines
the upstream host routinely refuses or rate-limits, and an example that
could not reach it was an ERROR rather than a printed condition. The
options(op) cache restore stays outside the
try() so it runs either way.
This is the CRAN Repository Policy requirement that a package using an internet resource fail gracefully when the resource is unavailable. It is the rule obr was archived under on 2026-08-22.
co2_euets_emissions() and
co2_euets_allocations() gain a scheme argument
and a scheme column. From compliance year 2024 DG CLIMA
publishes the new EU ETS2 (buildings, road transport, small industry) in
the same file as ETS1 installations, as one aggregate account per member
state carrying activity code 60. These 25 accounts added 981 Mt to the
2024 file, about 45% of the reported total, so any country-year sum
roughly doubled. The default is now "ets1", which is what
the function returned before ETS2 existed. Pass
scheme = "ets2" or "all" for the rest. Only
compliance year 2024 carries ETS2 emissions so far.co2_vrod() read sheet 1, which is now a “READ FIRST”
cover sheet, and returned a 98-row single-column frame of prose instead
of the project register. It now reads the PROJECTS sheet
(11,468 projects, 170 columns), locates the header row, and takes a
sheet argument. It also picks the newest release by the
date in the filename rather than lexically, which had selected the 2021
file because v4 sorts above v2026.co2_vrod() and co2_ukets() now guess
column types from the whole sheet. Several VROD columns stay blank well
past readxl’s default 1000-row window and only fill in later, so they
were typed as logical and every later value was discarded: 9 columns and
13,156 values in the 2026-06 release, including all 3,737 project
registration dates and the project owner field.co2_euets_surrendered() returned zero rows for older
compliance files. Their header sits below a preamble (row 11 in the 2015
file) rather than on row 1, so every identifier parsed as
NA and the country filter dropped everything. The header
row is now located, and the identifier columns are required, so a layout
change errors rather than returning an empty frame.co2_icap_prices() excludes ICAP’s “(download)” copies
of systems by default. ICAP publishes a second entry for several systems
carrying the same prices under a (download) suffix, so
asking for one system returned it twice, duplicating it in any chart or
average. Pass include_download = TRUE to keep them.co2_euets_installations() returned zero rows for any
country filter, because a banner row above the header meant
no column matched and the identifiers came back as NA. It
now finds the header row. The function also warns that DG CLIMA’s only
bulk registry file is a snapshot dated 28 August 2012, which no amount
of parsing fixes.co2_icap_prices(jurisdiction = ...) matched exactly
against names that ICAP spells out in full and pads with a trailing
space, so the documented "EU ETS" example returned an empty
data frame. Names are now trimmed, short aliases ("EU ETS",
"RGGI", "UK ETS", and others) resolve to the
official names, and an unmatched name errors with the list of valid ones
instead of returning nothing.co2_euets_emissions() and
co2_euets_allocations() work again. DG CLIMA added two
banner rows above the header of the data sheet; the parser
now locates the header row rather than assuming it is first. A latent
bug that assumed the emissions and allocation blocks had equal row
counts (they differ, allocations start a year later) is fixed by joining
on installation and year.co2_ukets() works again. The registry moved the
compliance report from section 4 to section 5 and renamed it, and sheet
1 of the new workbook is an empty “Information” sheet. Both sections are
now tried, the filename match is looser, and the Data sheet
is read.co2_ukets_allocations() works again. DESNZ dropped the
month from the filename (...-table-march-2025.xlsx became
...-table-2026.xlsx), which the old pattern required.co2_rff_pricing() works again, reading the
v2025.0.0 tag. The World Carbon Pricing Database stopped
distributing through GitHub on 30 May 2026 and stripped the data from
the default branch; new releases sit behind an emailed token. The
version default changed from "v2026.1" to
"v2025.0.0", the last openly published snapshot.co2_offsets_db() walks back up to 180 days (was 7) and
probes every day rather than stepping weekly past isolated snapshots.
CarbonPlan’s daily publishing became irregular during 2026 and the last
snapshot seen is 1 June 2026, so the function warns when the newest
available snapshot is more than a fortnight old.co2_world_bank() gains a path argument.
The dashboard host began rejecting non-browser clients in 2026: every
programmatic request returns HTTP 403 regardless of user agent, so the
file cannot be fetched automatically. Download it in a browser and pass
the local path. The function reports the direct URL when the fetch
fails, and the /about page it used to scrape is now
/about-us.co2_ecp_prices() reads the emissions-weighted carbon
price dataset published alongside WCPD at worldcarbonpricing.org. These
endpoints are open and updated with each release, making this the live
route to World Carbon Pricing Database derived data now that the GitHub
distribution has stopped. Covers prices by jurisdiction and sector plus
coverage shares by jurisdiction and sector. The publisher’s
region endpoint is accepted but currently has no data file
behind it for any gas, and says so rather than failing obscurely.co2_icap_systems() lists the ICAP systems with date
ranges and observation counts, so the exact jurisdiction
names are discoverable."Total Credits \r\nIssued", which
is now "Total Credits Issued".llms.txt and llms-full.txt are generated
from the package’s own Rd files by
inst/tools/build-llms-txt.R. They were hand-maintained and
had drifted, advertising a stale version, old signatures, and none of
the new functions.endpoint-canary GitHub Actions workflow exercises
every live source weekly and opens an issue when one breaks. Empty
results count as failures, since that is how the VROD and installations
bugs hid. The script is at inst/canary/check-endpoints.R
and runs locally.co2_euets_files() consequently lists far more vintages, and
all of them now parse: verified emissions back to 2015 and compliance
back to 2012. Making that work meant handling three layout differences
between vintages, namely a data sheet named after the year rather than
data (2021), a Read Me preamble inside the data sheet
pushing the header to about row 21 (2022-2024), and allocation columns
spelled ALLOCATED_ rather than ALLOCATION_
(2016 and earlier). As a cross-check, German 2015 emissions now read as
464.7 Mt from every file vintage between 2016 and 2025.httr2
writes the response body to the destination before raising on an HTTP
error, so a 403 or 404 left the error page sitting in the cache and
every later call served that instead of retrying. Downloads now land in
a temporary file and are moved into place only on success.no lines available in input, which points at neither the
source nor the network. The download now aborts naming the URL and the
status.co2_icap_prices() builds its result by column instead
of row-binding about 45,000 single-row data frames, cutting a call from
roughly 15 seconds to under 1.NA.CRAN policy compliance pass. No functional API changes.
\dontrun{} roxygen examples to
\donttest{}. These examples wrap public, unauthenticated
data fetches from ‘UK ETS’, ‘RGGI’, California Cap-and-Trade, ‘ICAP’,
World Bank, ‘RFF’, Berkeley VROD, and ‘CarbonPlan OffsetsDB’. Each
converted example now also sets
options(carbondata.cache_dir = tempdir()) around the call
and restores the prior value afterwards, so running the example on CRAN
does not write to the user’s home filespace.co2_offsets_db() example now guards the
arrow::read_parquet() call with
requireNamespace("arrow", quietly = TRUE) so the example
does not error when arrow (in Suggests) is not
installed.\dontrun{} remain:
co2_euets_emissions() and
co2_euets_allocations(): DG CLIMA wide-format file schema
drifted in 2026, so these functions currently abort. Marked
\dontrun{} with a comment pending a parser update.co2_cad_trust(): placeholder that always aborts (CAD
Trust has no unauthenticated public API).co2_euets_emissions() fetches verified greenhouse-gas
emissions by installation and year from the European Environment
Agency.co2_euets_allocations() fetches free allowance
allocations.co2_euets_surrendered() fetches surrendered units per
installation per year.co2_euets_price() fetches EUA auction settlement prices
from EEX public reports.co2_euets_installations() returns the EU ETS
installation registry.co2_ukets() fetches UK ETS prices, verified emissions,
and allocations.co2_rggi() fetches RGGI auction prices, quarterly
emissions, and allowance distribution from the COATS system.co2_california() fetches California Cap-and-Trade
auction settlement prices, emissions, and auction volumes.co2_icap_prices() fetches the ICAP Allowance Price
Explorer dataset covering 20+ ETS jurisdictions globally.co2_world_bank() fetches the World Bank Carbon Pricing
Dashboard (carbon taxes + ETS, 70+ initiatives).co2_rff_pricing() fetches the RFF World Carbon Pricing
Database (Dolphin, Pollitt, Newbery 2020).co2_vrod() fetches the Berkeley Voluntary Registry
Offsets Database aggregating Verra, Gold Standard, ACR, CAR, and ART
TREES.co2_offsets_db() queries the CarbonPlan OffsetsDB REST
API.co2_cad_trust() queries the Climate Action Data Trust
(CAD Trust) API for Article 6-aligned carbon credit metadata.co2_markets() lists all supported markets with coverage
metadata.co2_clear_cache() empties the local download
cache.co2_cache_info() reports what is cached and how much
space it uses.