icos-mcp
OfficialServer Configuration
Describes the environment variables required to run the server.
| Name | Required | Description | Default |
|---|---|---|---|
| ICOS_PROXY | No | Points the server at another proxy (the RC, a test instance). | |
| ICOS_MCP_TOKEN | No | Token used by a local stdio caller (the operator); it never speaks for an HTTP caller. | |
| ICOS_MCP_CONFIG | No | Path to a config.json that sets the proxy, the Host header to send it, the base of download links, and an ordered list of store rules. | |
| ICOS_MCP_PUBLIC_URL | No | Sets the endpoint named by the landing page. | https://mcp.icos-cp.eu |
Instructions
Guidance the server publishes about itself, which clients place ahead of the tool catalog so the model reads it before choosing anything.
ICOS (Integrated Carbon Observation System) observations: atmospheric greenhouse gases (CO2, CH4, N2O, CO, radon, 14CO2) and meteorology at ICOS stations, surface-ocean CO2 (SOCAT and ICOS ocean), and ecosystem fluxes (FLUXNET and near-real-time ETC data).
How to use these tools:
search_variables to find the variable id -- ids look like icos-obspack.co2.co2. Prefer the primary measurement over its companions (std_dev, nvalue, flags). find_stations lists the stations carrying a variable, near a place, in a box or by name -- use it to turn "Hyltemossa" into HTM150.
estimate before get_data: it says how many rows a selection has.
For a mean, total, range or count, call aggregate -- it computes over the WHOLE selection on the server, by station, day, month or year. Never average rows from get_data yourself: get_data returns at most a few thousand rows, for looking at; for anything larger give the user its download_url.
The ecosystem fluxes NEE, GPP and RECO are served by /query as their PRESCRIBED reference slices -- NEE_VUT_REF (variable u* threshold, reference variant), GPP_NT_VUT_REF and RECO_NT_VUT_REF (night-time partitioning). Use those. The other variants (CUT, the u* percentiles, daytime partitioning) live in the zarr cubes NEE, GPP and RECO: search_variables lists them with access "zarr", and describe_variable gives the xarray line that reads any slice. Their UNITS differ by store: icos-fluxnet's daily/weekly/monthly/yearly NEE is gC m-2 d-1 (yearly gC m-2 y-1), the near-real-time icos-eco-nrt NEE is umol m-2 s-1 per half-hour -- say which when comparing.
The released stores (icos-fluxnet, icos-obspack releases) end months before today. For the latest days or weeks -- "this week", "latest", "recent" -- use the near-real-time data: icos-eco-nrt for ecosystem fluxes and meteorology, the NRT tail of icos-obspack for gases.
Two ocean stores, easily confused: icos-socat is the ICOS OCEAN NETWORK's own release (ICOS ships and stations, ICOS Ocean Level 2, its own DOI) -- "ICOS ocean data" means this one; socat is the GLOBAL SOCAT synthesis (every contributor worldwide, SOCAT v2026, the SOCAT DOI) -- "SOCAT" means this one, and socat-gridded is its monthly 1x1 degree grid. Cite the store you actually used.
For a gridded product, estimate's rows ARE the grid cells with data: that number answers "how many cells", do not count them by hand.
Always cite: every data answer carries the citation, licence (CC BY 4.0) and DOI. Pass them on to the user.
Essential Climate Variables: ICOS provides the OBSERVATIONS that GCOS ECV products are built from, not the ECV products. A variable's ecv names the ECV it contributes to, ecv_role says whether it was measured or derived and how, and describe_variable gives its CF mapping, the unit conversion and any vocabulary_issues -- CF's "net downward" land carbon flux is NEP, the NEGATIVE of NEE. list_datasets names each store's ECVs; search_variables finds variables by ECV name. Station ids are CASE-SENSITIVE: atmosphere stations are a trigram plus the sampling height (HTM150 = Hyltemossa, 150 m), FLUXNET sites are mixed-case site codes (SE-Htm).
Capabilities
Features and capabilities supported by this server
Protocol revision2025-11-25
| Capability | Details |
|---|---|
| tools | {
"listChanged": false
} |
| prompts | {
"listChanged": false
} |
| resources | {
"subscribe": false,
"listChanged": false
} |
Tools
Functions exposed to the LLM to take actions
| Name | Description |
|---|---|
| list_datasetsA | List the ICOS datasets: one per data store, with domain (atmosphere, ocean, ecosystem), time and space coverage, licence and DOI. |
| search_variablesA | Find variable ids in the ICOS catalogue by name, quantity or unit. The ids are what estimate and get_data take. Primary measurements come before their companions (standard deviation, value counts, flags). |
| describe_variableB | One variable in full: names, unit, which dataset, its coverage, how its quality flag is read, licence and DOI. For a multi-dimensional variable read through zarr (access 'zarr'), its axes with their labels, the slice /query serves (prescribed) and an xarray line for any other slice. |
| estimateA | How big a selection is -- rows, stations, time span -- without fetching it. Call this before get_data. |
| get_dataA | Observations for one variable, filtered by box, time, station, cruise, height and quality control. Returns at most max_rows rows as a table, the total, a download URL for the whole selection, and the citation the user must be given with any use of the data. |
| get_citationA | How to cite a variable's data: the citation text, licence and DOI from its data passport, and -- for a selection (stations, a time window, a box) -- every data object it came from, in full. Data answers carry a short citation and only the COUNT of their sources; this lists them. |
| aggregateA | Statistics over a WHOLE selection, computed on the server: count, mean,
min, max, sum and standard deviation of one variable, overall or per
station, year, month or day. Use this for any average, total, range or
trend instead of reading rows. Any size: a selection over 500,000 rows
is split by time on the server and merged exactly. |
| find_stationsA | The stations that carry a variable: id, name, position, sampling height, country, ecosystem -- near a point (sorted by distance), in a box, by name or by country. The ids are what estimate and get_data take as station=. |
Prompts
Interactive templates invoked by user choice
| Name | Description |
|---|---|
| station_record | Plot or describe one station's time series. |
| compare_stations | Compare one quantity across several stations. |
| ocean_region | What surface-ocean CO2 observations exist in a region. |
Resources
Contextual data attached and managed by the client
| Name | Description |
|---|---|
| catalogue | every queryable variable of the public stores: id, names, unit, QC flag, store |
| llms_txt | the service's own guide for language models |
| data_passport | what the data passport in every answer contains and how to cite |
TDQS
Scored across 8 tools
Each tool maps to a distinct step in the data-access pipeline: discovery (search_variables, find_stations, list_datasets), metadata (describe_variable), sizing (estimate), retrieval (get_data), statistics (aggregate) and attribution (get_citation). The closest pairs — search_variables vs describe_variable and estimate vs aggregate — are explicitly separated by their descriptions (find ids vs read one variable in full; size vs statistics).
Seven of eight names follow a predictable verb_noun pattern (get_data, find_stations, search_variables, list_datasets, describe_variable, get_citation). Only 'estimate' and 'aggregate' are bare verbs, but they remain unambiguous in context.
Eight tools is well-scoped for a read-only scientific data catalogue, covering discovery, inspection, retrieval, aggregation and citation without redundancy. No tool feels padded or missing from the workflow.
The surface covers the full read-only lifecycle: catalogue/dataset/station discovery, variable description, size estimation before fetching, filtered retrieval with download URL, server-side aggregation and citation metadata. Trimming isn't a concern since get_data returns a download link for the full selection, so no bulk-export gap remains.