emission-factors MCP server
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@emission-factors MCP serverWhat's the Scope 2 emission factor for ZIP 94105?"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
emission-factors MCP server
Give Claude, Cursor, Cline, or any MCP client live access to US electricity data by ZIP code - grid-carbon emission factors, retail rates, hourly grid carbon intensity, power-plant emissions, and utility tariffs.
Backed by emission-factors.com, which wraps EPA eGRID, EIA-861, EIA-930, EPA CAMD, and OpenEI URDB into one ZIP-keyed API.
Free. No API key, no signup. The API is rate-limited per IP (2,000 requests/hour).
What you can ask
Once connected, your agent can answer things like:
"My HQ in ZIP 94105 uses 1.2M kWh/year. What's our Scope 2 carbon footprint and annual electricity cost?"
"Compare Denver, Austin, and Columbus for a new data center on grid carbon intensity and electricity price."
"What hour of the day is cleanest to run a 500 kW batch job in California this week?"
"Enrich this list of 40 store ZIP codes with each site's emission factor and carbon-free percentage."
"Which are the dirtiest power plants in Texas by CO2 over the last week?"
"Rank Ashburn VA, Abilene TX and The Dalles OR for a 10 MW data center on carbon and power cost."
"Our plant burns 40,000 therms of gas and 3,000 gallons of diesel a year - what's our Scope 1?"
"What's the actual PG&E residential tariff for 94105, not the state average?"
Related MCP server: RMI Utility Transition Hub — MCP Server
Why use it
Scope 2 carbon accounting - GHG Protocol location- and market-based emission factors for 33,700+ US ZIP codes (CDP, CSRD, California SB 253 inputs).
Site selection - compare candidate locations on both carbon intensity and electricity cost in one conversation.
Demand-response and load-shifting analysis - hourly grid carbon from EIA-930 (fixed per-fuel factors on in-BA generation: for timing, not inventory reporting).
Plant-level emissions - EPA CAMD data for fossil units over 25 MW: per-facility summaries or unit-hour records, published quarterly.
Agents and automation - a clean tool surface so an LLM can fetch authoritative government data instead of hallucinating factors.
Quick start
There are two ways to run this. Most people want Option A.
Option A - Remote server (recommended, zero install)
Nothing to install, always up to date. The hosted endpoint is https://emission-factors.com/mcp (Streamable HTTP, no key).
Claude (web, desktop app, mobile) - Add to Claude. The link opens Claude's custom-connector dialog with the name and URL filled in; select Add, then Connect. By hand: Customize -> Connectors -> Add custom connector, URL https://emission-factors.com/mcp, OAuth fields empty.
Claude Code
claude mcp add --transport http emission-factors https://emission-factors.com/mcpCursor - add to ~/.cursor/mcp.json:
{
"mcpServers": {
"emission-factors": {
"url": "https://emission-factors.com/mcp"
}
}
}Cline / Continue / Zed / other clients - add a remote (Streamable HTTP) MCP server with URL https://emission-factors.com/mcp. No key needed.
Claude Desktop's
claude_desktop_config.jsononly starts local (stdio) servers - a"url"entry there does nothing. Use the connector link above, or Option B.
Option B - Local stdio server (this package)
Runs the server as a local process that proxies the same public API. Useful for clients that only support stdio transport, or if you want to self-host.
Run straight from GitHub (builds on install, requires Node 18+):
{
"mcpServers": {
"emission-factors": {
"command": "npx",
"args": ["-y", "github:rozetyp/emission-factors-mcp"]
}
}
}Or clone and run from source:
git clone https://github.com/rozetyp/emission-factors-mcp.git
cd emission-factors-mcp
npm install # builds dist/ via the prepare script{
"mcpServers": {
"emission-factors": {
"command": "node",
"args": ["/absolute/path/to/emission-factors-mcp/dist/index.js"]
}
}
}Optional environment variable: EMISSION_FACTORS_API_BASE (defaults to https://emission-factors.com) if you run your own instance of the API.
Tools
Eleven tools, keyed by US ZIP code (or a direct code where noted). The remote server and this stdio build expose the same set.
Tool | Purpose | Key inputs |
| EPA eGRID CO2e + full generation mix for a ZIP |
|
| Same, resolved from lat/lon via Census geocoder |
|
| Emission factors for up to 100 ZIPs at once |
|
| Scope 2 CO2e for a ZIP + kWh, location-based and market-based (Green-e residual mix) |
|
| Hourly grid carbon intensity (EIA-930, ~24h lag) |
|
| Plant emissions (EPA CAMD): facility summaries or unit-hour records |
|
| Utility-specific tariff, not state average (OpenEI URDB) |
|
| State-average retail rate by sector (EIA-861) |
|
| Rank 2-25 candidate sites on grid carbon, $/kWh and cleanest daily window |
|
| Cleanest N-hour window of the day to run a flexible load, in local time |
|
| Scope 1 CO2e for fuels burned on site (EPA GHG Emission Factors Hub) |
|
All tools return JSON. See full API docs for exact response shapes.
Data sources
Data | Source | Notes |
Grid emission factors | EPA eGRID2023 Rev2 (+ eGRID2024 from Cornerstone via year=2024) | Annual, location-based, 27 subregions |
Residual mix (market-based Scope 2) | Green-e Residual Mix 2025 (2023 data) | Per eGRID subregion |
Fuel combustion factors (Scope 1) | GHG Emission Factors Hub 2026 (Cornerstone, successor to EPA's Hub); EPA 2025 via | 63 fuels, AR6 GWPs (AR5 for 2025) |
Retail electricity rates | EIA Form 861 | State-level monthly average by sector |
Hourly grid carbon intensity | EIA-930 | Derived from hourly fuel mix, ~24h lag |
Plant-level emissions | EPA CAMD | fossil units >25 MW, published quarterly (45+ days after quarter end) |
Utility-specific tariffs | OpenEI URDB (NREL) | ZIP matched to its utility by EIA ID |
ZIP / lat-lon resolution | US Census (ZCTA + Geocoder) | ZIP -> eGRID subregion mapping |
Rate limits and auth
No API key, no signup. Every request is anonymous.
2,000 requests/hour per IP. Generous for interactive use; if you hit it you get an HTTP 429 with a
retryAfterhint.The external-data endpoints are cached server-side (24h rates, 1h hourly intensity, 7d tariffs, 24h plant emissions), so repeated calls are fast and don't burn upstream quotas.
Also available
REST API - the same data over plain HTTP:
curl "https://emission-factors.com/api/lookup?zip=94105". See the API docs and OpenAPI spec.Hosted MCP setup guide - emission-factors.com/mcp-setup
Machine-readable summary for agents - emission-factors.com/llms.txt
Development
npm install # install deps and build (prepare -> tsc)
npm run build # compile TypeScript to dist/
npm run dev # watch mode
npm start # run the built server over stdioQuick smoke test with the MCP Inspector:
npx @modelcontextprotocol/inspector node dist/index.jsThe server is a thin proxy: each tool maps to one /api/* endpoint on emission-factors.com, validates inputs, and returns the JSON response. There is no local state and no key handling.
License
MIT - see LICENSE. Data belongs to its respective US government sources (EPA, EIA, Census) and NREL/OpenEI; this project and the API are an unofficial wrapper, not affiliated with those agencies.
Available Tools
11 toolscalculate_emissionsARead-onlyInspect
Calculate Scope 2 CO2e for a facility from its ZIP and kWh, using both GHG Protocol methods: location-based (eGRID subregion rate) and market-based (Green-e residual mix applied to kWh not covered by RECs, PPAs or green tariffs). Returns kg CO2e for each method with the factors used.
| Name | Required | Description | Default |
|---|---|---|---|
| kwh | Yes | Electricity consumption in kWh | |
| zip | Yes | 5-digit US ZIP code (ZIP+4 accepted) | |
| year | No | eGRID edition (default 2023). Market-based needs 2023. | |
| renewable_kwh | No | Optional: kWh covered by contractual instruments (RECs, PPAs, green tariff). Counted at zero in the market-based result. Default 0. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations cover the safety profile (readOnlyHint=true), so the bar is lower, and the description adds real substance: it discloses that both GHG Protocol methods are computed, the factor sources (eGRID subregion, Green-e residual mix), and how renewable_kwh is treated as zero in the market-based result. It also states the return payload (kg CO2e per method with factors used), which matters since there is no output schema.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three sentences, front-loaded with the core action and inputs before method detail. Every clause carries information (methods, factor sources, REC/PPA treatment, return format) with no filler or restatement of the title.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a read-only calculator with no output schema, the description adequately explains inputs, methodology, and the shape of the result. Gaps are minor: no mention of the year parameter's effect on market-based results, and no note on whether results are annualized or single-period, but the essential calling information is present.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the baseline is 3; the schema already documents kwh, zip pattern, year enum, and renewable_kwh. The description echoes the contractual-instrument semantics of renewable_kwh but adds no syntax or interaction detail beyond what the schema states, and never mentions the year parameter.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description names a specific verb (Calculate), a specific resource and scope (Scope 2 CO2e for a facility), and the exact inputs (ZIP, kWh) plus both accounting methods. It clearly distinguishes itself from the sibling calculate_fuel_emissions by being the electricity/Scope 2 tool.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Usage is only implied: the agent can infer this is the tool for electricity-based Scope 2, but nothing states when to pick it over calculate_fuel_emissions, compare_sites, or lookup_emission_factor. No exclusions or prerequisites (e.g., US-only ZIP, year constraint) are framed as usage guidance.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
calculate_fuel_emissionsARead-onlyInspect
Calculate Scope 1 stationary-combustion emissions (CO2, CH4, N2O and CO2e) for fuels burned on site, using the GHG Emission Factors Hub 2026 (Cornerstone, successor to EPA's Hub; IPCC AR6 GWPs) by default, or EPA's 2025 edition (AR5) with edition=2025. Pass one or more items with fuel, quantity and unit, e.g. natural gas in therms/ccf/mcf/scf, propane/diesel/heating oil in gallons, coal in short tons. Biomass CO2 is reported separately (biogenic). Stationary sources only: for vehicle fuel the CO2 per gallon is the same, but CH4/N2O factors differ and are not included. Returns per-item and total CO2e. Pair with calculate_emissions for a facility's electricity (Scope 2).
| Name | Required | Description | Default |
|---|---|---|---|
| items | Yes | ||
| edition | No | Hub edition: 2026 (default; Cornerstone, AR6 GWPs) or 2025 (EPA, AR5 GWPs). Fuel factors are the same; CO2e differs slightly. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, so safety is covered; the description goes further by disclosing the default factor set (Cornerstone/AR6) versus edition=2025 (AR5) and that CO2e shifts slightly, plus that biomass CO2 is reported separately as biogenic. It does not discuss error handling or the 50-item cap, but the substantive behavioral caveats are present.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Long but dense and front-loaded: purpose first, then defaults, then input format with examples, then scope exclusions, then return values and sibling pairing. Every sentence carries information, though the description sits at the upper end of acceptable length.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With only a readOnlyHint annotation and no output schema, the description carries the burden well: it states the returned shape ('per-item and total CO2e'), the default and alternate editions, the biogenic reporting convention, and the boundary against vehicle-fuel and Scope 2 use cases.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 50% (quantity is undocumented), so the description must add meaning, and it does: it maps fuel classes to plausible units ('natural gas in therms/ccf/mcf/scf, propane/diesel/heating oil in gallons, coal in short tons') and explains the edition switch's effect on CO2e. This exceeds the baseline for a half-documented schema, though it does not fully document the quantity parameter's bounds.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource with precise scope: 'Calculate Scope 1 stationary-combustion emissions (CO2, CH4, N2O and CO2e) for fuels burned on site.' It names the factor source and explicitly confines itself to stationary sources, which distinguishes it from calculate_emissions (Scope 2 electricity) named in the same description.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicit when-to-use ('fuels burned on site', 'stationary sources only'), when-not ('for vehicle fuel the CO2 per gallon is the same, but CH4/N2O factors differ and are not included'), and the alternative to pair with ('Pair with calculate_emissions for a facility's electricity (Scope 2)'). Routing is unambiguous.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
cleanest_hoursARead-onlyInspect
Find the cleanest (lowest grid carbon) contiguous window of N hours in the day to run a flexible load (batch jobs, EV charging, pumping, HVAC pre-cooling) at a US ZIP code or balancing authority. Based on the hour-of-day pattern of the last 7 days (168 hours) of EIA-930 data, in local time. Returns the cleanest and dirtiest windows, % saved vs the daily average, and all hours ranked. A scheduling guide from recent history, not a forecast.
| Name | Required | Description | Default |
|---|---|---|---|
| ba | No | Balancing authority code (e.g. CISO, ERCO, PJM, MISO, NYIS). Use this OR zip. | |
| zip | No | 5-digit US ZIP code (or use ba) | |
| duration | No | Window length in hours (default 4) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare readOnlyHint, so the description carries the rest and does so well: data source (EIA-930, last 7 days / 168 hours), local-time basis, and the return contents (cleanest and dirtiest windows, % saved vs daily average, all hours ranked). It doesn't discuss caveats like data lag or coverage gaps, keeping it from a 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three dense sentences that are front-loaded with the purpose, then the data basis, then the return values. Every clause earns its place, and the 'not a forecast' caveat is placed last for emphasis without padding.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description usefully sketches the return shape (cleanest/dirtiest windows, % saved, ranked hours), and the annotations cover the safety profile. It is essentially complete, though exact field names and units remain unstated.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the schema already documents ba, zip, and duration (including default 4 and the 1–12 range). The description only restates 'N hours' and the ZIP/BA target, adding little beyond what the structured fields provide. Baseline 3 is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb ('Find') and a precisely scoped resource: the lowest-carbon contiguous N-hour window for flexible loads at a ZIP or balancing authority. This distinguishes it clearly from siblings like hourly_intensity (raw hourly data) and the emissions calculators.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives concrete usage context (batch jobs, EV charging, pumping, HVAC pre-cooling) and an explicit when-not clause: 'A scheduling guide from recent history, not a forecast.' It does not name alternative sibling tools, so it stops short of a 5.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
compare_sitesARead-onlyInspect
Compare and rank 2-25 candidate US sites (ZIP codes) for a facility, data center or EV/flexible load on grid carbon and electricity cost in one call. Per site: eGRID CO2e kg/kWh (location-based), Green-e residual mix (market-based), carbon-free %, $/kWh for the sector (the average of the ZIP's primary full-service utility - full-service first, then public power, IOU, co-op, the same heuristic as lookup's utility.primary - unless a delivery-only utility serves the ZIP (retail choice), else the state average; all EIA-861 2023, see rate_basis), and the cleanest daily window from the 7-day hourly profile of its balancing authority. With annual_kwh, also annual tCO2e and cost. Returns competition ranks by carbon, cost and combined, gap percentages, and best_* = null with *_tied lists when sites tie.
| Name | Required | Description | Default |
|---|---|---|---|
| zips | Yes | Candidate US ZIP codes (5 digits or ZIP+4) | |
| sector | No | Retail rate sector. Default COM (commercial); use IND for industrial/data-center loads. | |
| duration | No | Length of the cleanest daily window in hours (default 4) | |
| annual_kwh | No | Optional annual consumption in kWh (e.g. 87,600,000 for a 10 MW constant load) to get annual tCO2e and cost per site |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare readOnlyHint=true, so the description carries the behavioral load and does so richly: data provenance (eGRID location-based vs Green-e market-based, EIA-861 2023), the exact utility-selection fallback chain, the rate_basis escape hatch, and tie semantics (best_* = null with *_tied lists). This is well beyond what the annotation provides.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The purpose and site scope are front-loaded in the first clause, and the trailing sentences are dense but each clause carries distinct information (rate heuristic, window, annual outputs, tie handling). The heavy nested parenthetical about utility selection is the one place where readability suffers.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description must explain returns, and it does: per-site metrics, competition ranks by carbon/cost/combined, gap percentages, and best_*/_tied null behavior. An agent has everything needed to call it correctly and interpret the result.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the baseline is 3; however the description adds real meaning by explaining how $/kWh is derived (full-service first, then public power/IOU/co-op, delivery-only retail choice, else state average) and how duration maps to the cleanest window, which the schema does not convey.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Opens with a specific verb+resource+scope: 'Compare and rank 2-25 candidate US sites (ZIP codes)' and names the decision dimensions (carbon, cost). It is clearly distinguishable from siblings like lookup_batch (single-lookup batch) and cleanest_hours (window only) because it explicitly aggregates ranking output across sites.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
States the intended load types (facility, data center, EV/flexible load) and 'in one call' implies the batch-comparison use case, plus it routes rate-sector choice ('use IND for industrial/data-center loads'). It cross-references the lookup utility.primary heuristic for consistency, but gives no explicit when-not or 'use X instead for a single site' alternative.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
electricity_rateARead-onlyInspect
Get the latest monthly average retail electricity rate ($/kWh and cents/kWh) for any US ZIP code, broken out by sector (residential, commercial, industrial, etc.). Data is state-level from EIA Form 861 - a ballpark, not utility- or ZIP-specific tariffs (use utility_tariff for those).
| Name | Required | Description | Default |
|---|---|---|---|
| zip | Yes | 5-digit US ZIP code |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare readOnlyHint=true; the description adds the material behavioral fact that the underlying data is state-level from EIA Form 861, so ZIP-level precision should not be assumed. That granularity caveat is exactly the kind of context an agent needs, though it says nothing about freshness lag or coverage gaps for non-US ZIPs.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two tight sentences, front-loaded with the resource and units, then the caveat and sibling routing. No filler and nothing repeated from the schema.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description carries the return-value burden and does so: it specifies units ($/kWh and cents/kWh), the sector dimension, the monthly averaging period, and the geographic granularity. Nothing needed to call or interpret the tool is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Only one parameter, and schema description coverage is 100% (the ZIP pattern and format are fully documented in the schema). The description adds no parameter-level meaning beyond the schema, so the baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource (get the latest monthly average retail electricity rate) plus units, geography, and the sector breakout. It also names the sibling it is not (utility_tariff), so an agent can distinguish it without opening schemas.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly frames the when-not case ('a ballpark, not utility- or ZIP-specific tariffs') and routes to the correct alternative by name ('use utility_tariff for those'). The condition selecting each tool is unambiguous.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
hourly_intensityARead-onlyInspect
Get hourly grid carbon intensity (kg CO2e per kWh) for any US ZIP code, derived from EIA-930 hourly fuel-mix data. Data lags up to about a day (not real-time). Returns time series with per-hour fuel mix, total generation, and carbon intensity. For timing and analysis (demand response, load shifting, grid patterns), not inventory reporting: it uses fixed per-fuel combustion factors on in-BA generation (no imports), so its values don't match eGRID's annual factors. For live or forecast intensity, WattTime or Electricity Maps are better options.
| Name | Required | Description | Default |
|---|---|---|---|
| ba | No | Balancing authority code directly (e.g. CISO, ERCO, PJM, MISO, NYIS). Use this OR zip. | |
| zip | No | 5-digit US ZIP code (or use ba parameter) | |
| hours | No | Number of most recent hours to return (default 24, max 168 = 1 week). | |
| aggregate | No | Optional: return the 24-hour average profile over the last 7 days (168 hours) instead of the hourly series. Buckets are UTC hours; for a local-time scheduling window use cleanest_hours. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare readOnlyHint=true, so the description carries the behavioral load and does it well: it discloses staleness (data lags up to a day, not real-time), what the response contains (per-hour fuel mix, total generation, carbon intensity), and the methodology caveat (fixed per-fuel combustion factors on in-BA generation, no imports, so values won't match eGRID annual factors). These are exactly the traits an agent needs to avoid misusing the output.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three sentences, zero filler, and front-loaded: the core capability and scope come first, followed by latency, output shape, and the fit/exclusion guidance. Every sentence carries distinct decision-relevant information.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, yet the description states the return shape (time series with per-hour fuel mix, total generation, carbon intensity). Combined with latency, methodology, and alternative routing, an agent has everything needed to select and call this correctly.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3 and the schema already documents ba/zip/hours/aggregate. The description adds genuine meaning on top: it clarifies aggregate's semantics (24-hour average profile over the trailing 168 hours), warns that buckets are UTC, and redirects local-time windows to cleanest_hours. It adds little on hours/ba/zip, keeping it just above baseline.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource+scope: hourly grid carbon intensity (kg CO2e/kWh) for any US ZIP code, derived from EIA-930 fuel-mix data. It also names the specific alternative tools (cleanest_hours, WattTime, Electricity Maps) and the data source, so an agent can distinguish it from siblings like calculate_emissions or lookup_emission_factor without opening schemas.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives explicit when-to-use (demand response, load shifting, grid pattern timing/analysis) and when-not (inventory reporting, because methodology differs from eGRID). It routes the agent to alternatives for live/forecast data (WattTime, Electricity Maps) and to cleanest_hours for local-time scheduling windows. This is as complete as usage guidance gets.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
lookup_batchARead-onlyInspect
Look up emission factors for up to 100 ZIP codes in one call (split longer lists). Returns one compact row per ZIP - subregion, CO2e kg/kWh (location-based), residual mix (market-based), carbon-free %, utility - unless full is true, which returns every field (about 2 KB per ZIP).
| Name | Required | Description | Default |
|---|---|---|---|
| full | No | Return complete candidate records (all pollutants, generation mix) instead of compact rows. Default false. | |
| zips | Yes | Array of US ZIP codes (5 digits or ZIP+4) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With only readOnlyHint=true in annotations, the description carries most of the behavioral burden and does it well: it lists the exact returned fields per row, explains the full=true switch and its ~2 KB per-ZIP payload size, and flags the 100-item cap. It omits error behavior (e.g., unmatched or invalid ZIPs), which keeps it from a 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Purpose and batch limit are front-loaded in the first clause, and the second clause packs the return shape, the full flag, and a payload estimate with no filler. Two sentences, zero waste.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, and the description compensates by enumerating the compact row fields and the fields returned when full=true, so the agent knows what it gets. Combined with the read-only annotation and 100% parameter coverage, nothing needed for correct invocation is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so baseline is 3, but the description adds meaning beyond the schema by quantifying full=true output (~2 KB per ZIP, every field) and by restating the 100-ZIP batch limit for zips. The size/field detail is genuinely incremental over the schema's terse parameter descriptions.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Specific verb (look up) plus resource (emission factors) with an explicit batch scope (up to 100 ZIP codes in one call). An agent can distinguish this from single-value siblings like lookup_emission_factor or lookup_by_coordinates purely from the description.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description gives a concrete usage rule — batch up to 100 ZIPs per call and split longer lists — which tells the agent when this tool applies. It does not, however, explicitly name the alternative for single-ZIP lookups or state exclusions, so it stops short of full when/when-not routing.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
lookup_by_coordinatesARead-onlyInspect
Look up emission factors by latitude/longitude. Uses US Census Geocoder to resolve to ZIP first, then returns the same data as lookup_emission_factor. Useful when you have a facility address or lat/lon but no ZIP.
| Name | Required | Description | Default |
|---|---|---|---|
| lat | Yes | Latitude (decimal degrees) | |
| lon | Yes | Longitude (decimal degrees) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
readOnlyHint=true already covers the safety profile, and the description adds real behavioral context: an external US Census Geocoder round-trip before the lookup, and equivalence of output to lookup_emission_factor. It omits failure behavior (non-US coordinates, geocode misses), which keeps it short of a 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three short sentences, front-loaded with what it does, then the mechanism, then the use case. No filler and every sentence carries distinct information.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description usefully states the return equals lookup_emission_factor's data, and explains the geocoding step. The main unaddressed gap is that the US Census Geocoder is US-only, so non-US coordinates fail silently as far as the description tells the agent.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% and both parameters (lat, lon) are documented in the schema. The description restates 'latitude/longitude' without adding units, range, or formatting guidance, so baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('look up emission factors') plus the input dimension ('by latitude/longitude'), and explicitly distinguishes itself from the sibling lookup_emission_factor by noting it returns the same data after geocoding. An agent can tell the two apart without opening a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives a clear selecting condition: 'Useful when you have a facility address or lat/lon but no ZIP,' which implicitly routes ZIP-holders to lookup_emission_factor. It never states that alternative as an explicit instruction, so the guidance is clear but not fully closed-loop.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
lookup_emission_factorARead-onlyInspect
Look up EPA eGRID electricity emission factors for a US ZIP code. Returns CO2e (kg/kWh and lb/MWh), CO2, CH4, N2O, NOx, SO2, non-baseload rate, carbon-free %, generation mix (coal/gas/nuclear/hydro/wind/solar etc.), eGRID subregion code, the data year, and the Green-e residual mix rate (the market-based Scope 2 factor). For Scope 2 emissions from a kWh total, use calculate_emissions, which does the arithmetic for both methods.
| Name | Required | Description | Default |
|---|---|---|---|
| zip | Yes | 5-digit US ZIP code (e.g. "94105"); ZIP+4 accepted | |
| year | No | eGRID edition: 2023 (default, official EPA) or 2024 (EPA's public eGRID code run on 2024 data by Cornerstone; EPA has not published eGRID2024) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already establish readOnlyHint=true, so the safety profile is covered, but the description adds real value beyond that: it discloses the distinction between location-based and market-based Scope 2 factors, the presence of the Green-e residual mix rate, the data year, and the important provenance caveat about the 2024 eGRID edition not being EPA-published. That provenance detail is behaviorally meaningful and not derivable from structured fields.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
It is front-loaded with purpose, then output contents, then alternative routing — a sensible order with no filler sentences. The long enumeration of return values is somewhat dense, but since no output schema exists, the listing is largely justified rather than wasteful.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description appropriately carries the burden of describing return values, and it does so comprehensively. Both parameters are covered by a 100%-coverage schema, and the alternative tool is named, so an agent has what it needs to call this correctly; only the coordinate/batch variants are unaddressed.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, and the schema itself already explains the ZIP pattern and the 2023/2024 edition enum in detail, so the baseline is 3. The description adds essentially no parameter-level detail beyond what the schema provides, leaving the schema to do all the work.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb and resource ('Look up EPA eGRID electricity emission factors for a US ZIP code') and immediately enumerates the returned quantities, so the agent knows exactly what domain this covers. It is clearly distinguishable from siblings like utility_tariff or electricity_rate, which are about rates rather than emission factors.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It explicitly routes the agent: 'For Scope 2 emissions from a kWh total, use calculate_emissions, which does the arithmetic for both methods' — naming the alternative and the condition that selects it. However, it is silent on the other closely related siblings (lookup_by_coordinates, lookup_batch) that an agent might otherwise confuse with this ZIP-based lookup.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
plant_emissionsARead-onlyInspect
Get emissions from EPA Clean Air Markets Division (CAMD) for a specific US power plant or a state: fossil units over 25 MW reporting to the Acid Rain Program and CSAPR. Per facility returns total CO2 (short tons), gross generation (MWh), heat input (mmBtu), NOx and SO2 (lb), primary fuel type, operating hours, and derived emissions rate (kg CO2/MWh). CAMD publishes by quarter, so the default window is the last 7 days of the latest published quarter (latest_published_date in the response); later dates are not available yet. Default output is a per-facility summary from daily data; format=hourly returns unit-hour records for small windows. Use for plant-specific carbon accounting, state-level fossil emissions and "dirtiest plants in [state]" queries.
| Name | Required | Description | Default |
|---|---|---|---|
| end | No | Custom end date YYYY-MM-DD (optional, overrides days). | |
| days | No | Number of most recent days to include (1-90, default 7). | |
| begin | No | Custom begin date YYYY-MM-DD (optional, overrides days). | |
| limit | No | Summary only: return the top N facilities by CO2 (default 25); facilities_total gives the full count. | |
| state | No | 2-letter US state code for state-wide aggregate (e.g. TX, CA, PA). | |
| format | No | "summary" (default) aggregates by facility; "hourly" returns raw CAMD unit-hour records, about 0.8 KB each (a 9-unit plant-day was 172 KB), so use it with facility_id and 1-2 days. | |
| facility_id | No | EPA CAMD/ORIS facility code (e.g. 3 for Barry, AL). Find codes in the summary_by_facility of a state query, or at https://campd.epa.gov/. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only provide readOnlyHint=true, so the description carries the behavioral burden and does so well. It discloses the quarterly publication cadence, the default 7-day window based on the latest published quarter, data unavailability for later dates, return fields, and the hourly format's size implications. This is rich operational context beyond the annotation.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is front-loaded with purpose and data scope, then moves logically to defaults, format behavior, and use cases. It is dense but every sentence earns its place. Slightly long but justified by the complexity of the tool.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a read-only data retrieval tool with no output schema and 100% parameter coverage, the description is complete: it explains data source, scope, defaults, format trade-offs, return fields, and use cases. Nothing essential for correct invocation is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so parameters are already well documented. The description adds meaning by explaining the default window ('last 7 days of the latest published quarter') and the relationship between state and facility_id, but it does not add syntax or constraints beyond the schema. Baseline 3 is appropriate when the schema does the heavy lifting.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb and resource ('Get emissions from EPA Clean Air Markets Division (CAMD)') and defines the precise data scope (fossil units over 25 MW reporting to the Acid Rain Program and CSAPR). It clearly distinguishes the tool from general emissions tools by emphasizing plant- and state-level CAMD data.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It gives clear contexts for use: 'plant-specific carbon accounting, state-level fossil emissions and "dirtiest plants in [state]" queries.' It also explains when to use format=hourly versus default summary. However, it does not name explicit alternatives among siblings such as calculate_emissions or cleanest_hours, so routing remains partially inferential.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
utility_tariffARead-onlyInspect
Get the actual utility-specific electricity rate (not state average) for a US ZIP code or named utility. Returns the current default tariff with effective rate ($/kWh), fixed monthly charge, tier count, TOU indicator, and effective date. Data source: OpenEI URDB (NREL-hosted). With a ZIP, matches the ZIP's utility by EIA ID. Returns currently-effective tariffs; when URDB has none flagged as default (common for Commercial/Industrial) it returns the most recent ones and says so in warnings, including when the newest available tariff has expired. Does not cover Texas retail electric providers (deregulated market) - use electricity_rate there.
| Name | Required | Description | Default |
|---|---|---|---|
| zip | No | 5-digit US ZIP code | |
| eiaid | No | EIA utility ID (joins with EIA Form 861) | |
| limit | No | Max tariffs to return (1-20, default 5) | |
| sector | No | Default "Residential" (case-insensitive; RES/COM/IND codes accepted) | |
| utility | No | Utility name (e.g. "Pacific Gas & Electric Co", "Consolidated Edison Co-NY Inc") |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Goes well beyond the readOnlyHint annotation: discloses the data source (OpenEI URDB/NREL), the fallback behavior when no default tariff exists (returns most recent and flags it in warnings), and the expired-tariff warning case. This is exactly the behavioral context a safe-read annotation does not provide.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loads what it returns and the data source, then layers fallback and exclusion notes. Dense and information-rich, though a few clauses (e.g., the expired-tariff parenthetical) could be tightened. Every sentence still carries distinct information.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description compensates by enumerating the returned fields (effective rate, fixed monthly charge, tier count, TOU indicator, effective date). Combined with the fallback/warning behavior and data source, an agent has everything needed to call and interpret it.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3; the description adds meaning by explaining that a ZIP is resolved to the ZIP's utility via EIA ID, tying the zip and eiaid parameters together. It does not clarify utility-name matching, but the schema already documents all five parameters.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource (get the utility-specific electricity rate) and sharply distinguishes itself from the state-average rate and from the sibling electricity_rate tool. An agent can tell exactly what this returns and how it differs from alternatives without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly names the when-not case and the alternative: 'Does not cover Texas retail electric providers (deregulated market) - use electricity_rate there.' This routes the agent away from the wrong tool. Input-method selection (ZIP vs eiaid) is also touched on via the ZIP-to-EIA-ID matching note.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
Tool Schema Changelog
Recent tool additions, removals, and schema changes observed during successful MCP inspections.
11 tool updates
v1.7.1- First observed
calculate_emissions - First observed
calculate_fuel_emissions - First observed
cleanest_hours - First observed
compare_sites - First observed
electricity_rate - First observed
hourly_intensity - First observed
lookup_batch - First observed
lookup_by_coordinates - First observed
lookup_emission_factor - First observed
plant_emissions - First observed
utility_tariff
TDQS
Scored across 11 tools
Most tools have distinct roles, and descriptions proactively cross-reference each other (electricity_rate vs utility_tariff, hourly_intensity vs eGRID, fuel vs electricity). The three lookup_* tools overlap conceptually but are cleanly split by input type (batch ZIPs, coordinates, single ZIP). compare_sites and cleanest_hours partially recombine underlying lookups, but their high-level intent is distinct.
Roughly half the tools follow a verb_noun pattern (lookup_*, calculate_*, compare_sites), while the rest are bare noun phrases (electricity_rate, hourly_intensity, plant_emissions, utility_tariff, cleanest_hours). All are readable snake_case, but the naming scheme is mixed rather than systematic.
11 tools is well within the healthy range and each maps to a meaningful capability (ZIP/lat-lon lookups, batch, rates, Scope 1 and 2 calculations, hourly intensity, plant data, site comparison, scheduling). No tool feels like filler or a redundant variant.
Coverage is strong for the US electricity-emissions domain: single/batch/coordinate factor lookups, state and utility rates, Scope 2 and Scope 1 calculators, hourly intensity, plant emissions, site ranking, and cleanest-hour scheduling. Gaps are minor and largely acknowledged (no forecasting, US-only scope), workable via external services.
Maintenance
Related MCP Connectors
Carbon MCP — UK Carbon Intensity API (free, no auth)
EPA Emissions MCP — wraps EPA Envirofacts REST API (free, no auth)
GridStatus MCP — wraps the GridStatus.io REST API (api.gridstatus.io/v1)
Live US retail electricity plans, utility price-to-compare rates, ZIP-to-utility lookup. Read-only.
Related MCP Servers
- AlicenseNot gradedqualityAmaintenanceBrowse and query the U.S. Energy Information Administration API v2 — electricity, petroleum, natural gas, coal, forecasts, and more via MCP. STDIO or Streamable HTTP.315 npm2Apache 2.0
- FlicenseAqualityBmaintenanceEnables natural-language querying of US utility emissions, generation mix, and climate alignment data through any MCP client.7-
- AlicenseAqualityBmaintenanceLive and historical electricity prices, demand, generation mix and carbon intensity for 25 grid zones (US, Europe, GB, Australia). Hosted endpoint plus local stdio bridge; free sample mode, free API key, or x402 pay-per-call.6MIT
- AlicenseNot gradedqualityBmaintenanceProvides real-time grid carbon intensity, power generation breakdown, and carbon-intensity forecasts for any zone or lat/lon location.0MIT