REST API

API Reference

Four calculate endpoints. Each takes an activity in JSON and returns the emissions, the emission factor used, where that factor comes from, and the formula.

Base URL

https://zerocarbon.org.in/api/v1

Every endpoint takes POST with a JSON body (Content-Type: application/json). Electricity, fuel and flight work without a key in a rate-limited test mode. Spend needs an API key (see Authentication).

Endpoints

EndpointScopeKey
POST /calculate/electricityScope 2Optional
POST /calculate/fuelScope 1Optional
POST /calculate/flightScope 3 (business travel)Optional
POST /calculate/spendScope 3 (purchased goods)Required

Electricity

POST/api/v1/calculate/electricityNo key needed (rate-limited test mode)

Location-based Scope 2 using the national grid average for the country. The factor is the one the ZeroCarbon ledger itself would apply.

FieldTypeDescription
kwhnumberRequired. Electricity consumed, in kWh (0.01 to 100,000,000). amount_kwh is accepted as an alias.
country_codestringISO country code, required (an API key falls back to its company’s country). country is accepted as an alias.
statestringOptional. Echoed back but not applied: per-state factors are not used for corporate Scope 2.

Example

terminalbash
curl -X POST https://zerocarbon.org.in/api/v1/calculate/electricity \
  -H "Content-Type: application/json" \
  -d '{"kwh": 1000, "country_code": "IN"}'
200 OKjson
{
  "success": true,
  "data": {
    "emissions_kg_co2e": 675,
    "emission_factor": 0.675,
    "emission_factor_label": "0.675 kgCO2e/kWh (CEA_CO2_Baseline_v22_FY2025-26 (weighted_average, AR5))",
    "emission_factor_source": "CEA_CO2_Baseline_v22_FY2025-26",
    "scope": "scope_2",
    "activity": { "value": 1000, "unit": "kWh" },
    "formula": "1000 kWh × 0.675 kgCO2e/kWh = 675.0000 kgCO2e",
    "details": {
      "kwh": 1000,
      "country_code": "IN",
      "state": null,
      "state_applied": false,
      "methodology": "Location-based Scope 2 (GHG Protocol), national grid average"
    }
  }
}

The factor depends on the country: "country_code": "GB" returns 0.13096 kgCO2e/kWh from DESNZ_2026. A country with no published grid factor is refused with no_factor_for_country.

Fuel

POST/api/v1/calculate/fuelNo key needed (rate-limited test mode)

Scope 1 combustion of a fuel you burn.

FieldTypeDescription
fuel_typestringRequired. One of petrol, diesel, natural_gas, lpg, coal, cng, furnace_oil.
amountnumberRequired. Quantity burned (0.01 to 100,000,000).
unitstringL (or liters), kg or m3. Units are fuel-specific: litres for petrol, diesel and furnace oil; kg for LPG, CNG and coal; m3 for natural gas. A mismatch is refused, not converted.
variantstringRequired for coal: bituminous or lignite.
countrystringISO country code, required (an API key falls back to its company’s country).

Example

terminalbash
curl -X POST https://zerocarbon.org.in/api/v1/calculate/fuel \
  -H "Content-Type: application/json" \
  -d '{"fuel_type": "diesel", "amount": 100, "unit": "L", "country": "IN"}'
200 OKjson
{
  "success": true,
  "data": {
    "emissions_kg_co2e": 268.795,
    "emission_factor": 2.687954,
    "emission_factor_label": "2.687954 kgCO2e/liter (IndiaGHGProgram_IPCC2006 (ipcc_default, AR5))",
    "emission_factor_source": "IndiaGHGProgram_IPCC2006",
    "scope": "scope_1",
    "activity": { "value": 100, "unit": "L" },
    "formula": "100 liter × 2.687954 kgCO2e/liter = 268.7950 kgCO2e",
    "details": { "fuel_type": "diesel", "amount": 100, "unit": "L", "variant": null, "country": "IN" }
  }
}

Flight

POST/api/v1/calculate/flightNo key needed (rate-limited test mode)

Scope 3 business travel, priced per passenger-km. The distance is never estimated from a route, so distance_km is required.

FieldTypeDescription
distance_kmnumberRequired. One-way great-circle distance in km (1 to 20,000).
passengersnumberDefaults to 1.
cabin_classstringDefaults to economy. Only economy is priced today; other classes are refused with cabin_class_unsupported.
round_tripbooleanDefaults to false. true doubles the distance.
origin, destinationstringOptional 3-letter airport codes. Echoed back; they do not set the distance.
countrystringISO country code for the factor, required (an API key falls back to its company’s country).

Example

terminalbash
curl -X POST https://zerocarbon.org.in/api/v1/calculate/flight \
  -H "Content-Type: application/json" \
  -d '{"distance_km": 1150, "passengers": 2, "cabin_class": "economy", "country": "IN"}'
200 OKjson
{
  "success": true,
  "data": {
    "emissions_kg_co2e": 296.7,
    "emission_factor": 0.129,
    "emission_factor_label": "0.129 kgCO2e/km (IndiaGHGProgram_BusinessTravel (ipcc_default, AR5))",
    "emission_factor_source": "IndiaGHGProgram_BusinessTravel",
    "scope": "scope_3",
    "activity": { "value": 2300, "unit": "km" },
    "formula": "2300 km × 0.129 kgCO2e/km = 296.7000 kgCO2e",
    "distance_km": 1150,
    "details": {
      "origin": null,
      "destination": null,
      "cabin_class": "economy",
      "passengers": 2,
      "round_trip": false,
      "haul": "medium_haul",
      "passenger_km": 2300
    }
  }
}

Spend

POST/api/v1/calculate/spendAPI key required

Spend-based (EEIO) estimate for purchased goods and services, from Indian input-output tables. Use physical quantities (kWh, litres, kg) when you have them: they are far more accurate than spend.

FieldTypeDescription
amountnumberRequired. Amount spent (0.01 to 1,000,000,000).
categorystringRequired. One of metals, construction_materials, chemicals, textiles, electronics, professional_services.
currencystringDefaults to INR. Only INR is accepted: convert other currencies at the transaction-date rate first.
descriptionstringOptional. Echoed back in details.

Example

terminalbash
curl -X POST https://zerocarbon.org.in/api/v1/calculate/spend \
  -H "Authorization: Bearer $ZEROCARBON_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"amount": 50000, "currency": "INR", "category": "metals"}'

The response has the same data fields as the other endpoints, plus matched_category, methodology and details (amount, currency, category, description). Without a key the endpoint returns 401.

Response fields

FieldTypeDescription
emissions_kg_co2enumberResult in kg CO2e, rounded to 3 decimals.
emission_factornumberThe factor applied, per unit of activity.
emission_factor_labelstringFactor with unit, dataset, methodology and GWP basis.
emission_factor_sourcestringThe dataset the factor comes from, e.g. CEA_CO2_Baseline_v22_FY2025-26.
scopestringscope_1, scope_2 or scope_3.
activityobjectThe quantity priced and its unit.
formulastringThe arithmetic, so the number can be checked by hand.
detailsobjectEcho of the inputs and the method used.

Factors are updated when the publisher releases a new edition, so the numbers above can change.

Errors and refusals

When the API cannot price an input it refuses with a reason instead of guessing. A refusal is a 422 with a machine-readable code and a guidance string:

422 (POST /calculate/flight without distance_km)json
{
  "success": false,
  "error": "distance_km is required: route distances are not estimated.",
  "code": "distance_required",
  "guidance": "Send the one-way great-circle distance in km (from your booking or an airport-distance tool)."
}

Refusal codes you can see:

  • distance_required - flight without distance_km
  • cabin_class_unsupported - a cabin class other than economy
  • no_factor_for_country - no published factor covers that country
  • subtype_required - coal without variant
  • unmappable_activity - a unit that does not fit the fuel (e.g. LPG in litres)
  • unsupported_input - a spend category or fuel the library has no factor for
  • currency_unsupported - spend in a currency other than INR

Malformed requests, bad keys and rate limits use an error object instead:

422 (kwh sent as a string)json
{
  "success": false,
  "error": {
    "code": "VALIDATION_ERROR",
    "message": "Invalid request data",
    "details": { "fields": { "kwh": "kwh must be a number" } }
  }
}
  • 400 BAD_REQUEST - e.g. electricity without kwh
  • 401 UNAUTHORIZED - missing key on spend, or a key that is not valid
  • 422 VALIDATION_ERROR - a field of the wrong type or outside its range
  • 429 - rate limit reached (see rate limits)

To read the code from either shape: typeof body.error === 'string' ? body.code : body.error.code.

MCP server

The same calculations are available to AI agents over the Model Context Protocol at https://zerocarbon.org.in/api/v1/mcp (JSON-RPC over HTTP). Without a key, agents can call the calculation tools such as calculate_emissions; tools that read or write your company data need an API key in the Authorization header.