Read what the package says now
I set out to build a carbon-aware scheduler on GridCarbon (github.com/gridcarbon/clients), an MCP server that promised live grid carbon intensity for 45 zones with no API key. Every version on npm, 0.1.0 and 0.1.1 of 26 August 2026 and 0.1.2 of 31 August, now carries the same deprecation notice: 'The gridcarbon API was shut down on 2026-09-13.' The repository is archived with no stars, created on 26 August and last pushed on 13 September, which gives about eighteen days of life to a project whose README called it 'pre-alpha', and nobody can accuse it of overstating that. The only named author is an address at gridcarbon.dev, the code is MIT and the data CC BY 4.0, and a request to api.gridcarbon.dev for France returned HTTP 410 when I tried it on 17 October 2026. The project's site now points to a Zenodo snapshot of 1,460,467 rows up to 4 September (doi:10.5281/zenodo.22299989). Someone still downloaded the package 21 times in the week to 12 October.
Credit what it did
The claims were true while it ran. It covered 33 European bidding zones, 11 US balancing authorities and aggregates, and Great Britain, through four tools: get_carbon_intensity, get_intensity_history, list_zones and compare_zones; it said plainly that it reported average, production-based intensity, summing each fuel's megawatts times an emission factor and dividing by total output, with imports not modelled, no marginal figure and no day-ahead forecast. Its factors were IPCC AR5 lifecycle medians (gas 490, hard coal 820, nuclear 12, onshore wind 11, solar 48 gCO2eq/kWh), and it admitted that pricing lignite at 820 underestimated it. Its data ran two to four hours late for ENTSO-E zones, 11 to 28 hours for the EIA, and one to two hours for Great Britain.
Find where the key lived
The weak point sat in the word 'keyless'. The MCP server was a thin client of the operator's hosted API, and that API held the ENTSO-E credentials on a Cloudflare Worker; the user needed no key because the operator had one, and when the operator stopped paying for the Worker, every installed copy stopped with it. Nothing in the client could be repointed. A keyless hosted wrapper is a dependency on someone else's credentials and someone else's goodwill, and a scheduler that writes to a site's chargers cannot rest on either.
Use a source with an owner
So I built the design on the Carbon Intensity API for Great Britain, which its documentation at carbon-intensity.github.io/api-definitions describes as 'developed by National Energy System Operator (NESO)'; the project site names Environmental Defense Fund Europe, the University of Oxford Department of Computer Science and WWF as partners. It needs no key, its licence is CC BY 4.0, and it publishes half-hourly forecasts by postcode or region, though the documentation calls the output an 'indicative trend' and the regional endpoints still carry a beta label.
Three differences from GridCarbon matter more than the owner. NESO counts direct CO2 from generation only, so its own factors list on 17 October gave combined-cycle gas 394, coal 937, and nuclear, wind and solar zero; GridCarbon's lifecycle figures cannot be mixed with these in one report. NESO models imports, at 474 for Dutch and 53 for French. And the national series carries an estimated actual beside each forecast, while the regional series carries a forecast only, even for half-hours already past.
Schedule by forecast, report with care
The solution reads the 48-hour regional forecast for a site's outward postcode, takes the deadline a person has set for each flexible load, and writes the lowest-intensity window that meets it to the charge controller or job scheduler. For postcode SL1, which NESO places in South England, the forecast fetched at 21:39 UTC on 16 October ran from 80 to 255 gCO2/kWh across 97 half-hours, and the spread is the whole case for moving a load. A three-hour fleet charge begun at 17:00 UTC on Saturday averaged 242; the same charge between 01:30 and 04:30 on Sunday averaged 140. A two-hour battery charge moved from that evening into midday Saturday fell from 133 to 84.
Those figures are forecast regional averages. Average intensity tells you how dirty the mix was, not what your extra kilowatt-hour caused; the stricter test is marginal intensity, which neither NESO nor GridCarbon published, so moving a load by average is a reasonable heuristic and not proof of avoided emissions, and anyone who reports the difference between 242 and 140 as tonnes saved has claimed more than either data set can show. The design's Scope 2 log keeps forecast and estimated actual in separate columns, records that the regional half-hours have no actual, and stamps every figure with its source, method and fetch time.
See the design, its diagram and the demo at the solution. Ground an emissions figure in a source with an owner, and keep the method tag with the number. GridCarbon's numbers outlived its API by a Zenodo deposit.