Skip to main content
This guide is intended for developers and technically proficient users. Setting up the MCP server requires Node.js, a terminal, and basic familiarity with configuration files.

57 Tools

Every iklim.co API capability is exposed as an MCP tool β€” lightning, thunderstorm, precipitation, forecast, alarms, and more.

Auto Auth

JWT tokens are acquired and refreshed automatically. Just provide your credentials and the server handles the rest.

HMAC-Signed

Every request is signed with HMAC-SHA256. Credentials never travel in plain text and replay attacks are blocked with a per-request nonce.

Overview

The iklim.co MCP Server implements the Model Context Protocol and exposes the full iklim.co REST API as 57 tools across 9 categories. Any MCP-compatible AI client (Claude, OpenClaw, and others) can query live weather data, manage alarms, and handle user accounts through natural language.
CategoryToolsScope
⚑ Lightning2Lightning strike data
πŸŒͺ️ Thunderstorm3Thunderstorm cell tracking
🌧️ Precipitation2Radar precipitation data
🌀️ Forecast3Hourly / daily / current weather
πŸ‘€ Auth & User11Authentication and user management
🏒 Account8Account and subscription management
πŸ“ Point Alarms6GPS-based alert subscriptions
πŸ—ΊοΈ Geo Alarms12Boundary-based alerts + city/district/neighborhood catalog
πŸ“… Forecast Alarms10Threshold-based forecast alerts + city/district catalog
Total57

Requirements

  • Node.js >= 18 (ES2022 support required)
  • npm >= 9
  • iklim.co API credentials: HMAC secret, username, and password

Installation

The source code is publicly available at git.tarla.io/iklim.co/mcp-server.
git clone https://git.tarla.io/iklim.co/mcp-server.git
cd mcp-server
npm install
npm run build

Environment Variables

The following variables must be set before the server starts. For local development, create a .env file in the mcp-server directory (already in .gitignore):
# .env
IKLIM_ENV=test                     # prod | test | local  (used when IKLIM_BASE_URL is not set)
IKLIM_BASE_URL=                    # Optional. Overrides IKLIM_ENV when set
IKLIM_HMAC_SECRET=<secret>         # Required. HMAC-SHA256 key for request signing
IKLIM_USERNAME=<email>             # Required. API account e-mail
IKLIM_PASSWORD=<password>          # Required. API account password
IKLIM_TOKEN_STORE_PATH=            # Optional. Path for persisting access/refresh tokens
IKLIM_HTTP_LOG_PATH=               # Optional. API request log file path
IKLIM_HTTP_LOG_MAX_BYTES=5242880   # Optional. Rotate threshold in bytes (default: 5 MB)
IKLIM_HTTP_LOG_MAX_FILES=5         # Optional. Number of rotated files to keep
IKLIM_HTTP_LOG_REQUEST_BODY_MAX_BYTES=16384   # Optional. Request body log size limit
IKLIM_HTTP_LOG_RESPONSE_BODY_MAX_BYTES=16384  # Optional. Response body log size limit
Base URL by environment:
IKLIM_ENVURL
prodhttps://api.iklim.co
testhttps://api-test.iklim.co
localhttp://localhost:8080
When IKLIM_HTTP_LOG_PATH is set, every API call is written as a single-line JSON log entry. Sensitive fields (Authorization, X-Signature, password, token, etc.) are automatically masked.

Build & Run

# Compile TypeScript (outputs to dist/)
npm run build

# Start the compiled server
npm start

# Development mode β€” no build step required
npm run dev
A successful start prints:
iklim.co MCP server running
The server communicates over stdio transport. It is designed to be managed by an MCP client, not run interactively in a terminal.

MCP Client Configuration

Claude CLI (.mcp.json)

Place a .mcp.json file in your project root. Claude CLI picks it up automatically:
{
  "mcpServers": {
    "iklim": {
      "command": "node",
      "args": ["/absolute/path/to/mcp-server/dist/index.js"],
      "env": {
        "IKLIM_ENV": "test",
        "IKLIM_HMAC_SECRET": "<secret>",
        "IKLIM_USERNAME": "<email>",
        "IKLIM_PASSWORD": "<password>"
      }
    }
  }
}
To register the server globally, add the same mcpServers block to ~/.claude/settings.json.

OpenClaw

The openclaw mcp set command does not support a separate env flag β€” pass everything as a single JSON object:
openclaw mcp set iklim '{"type":"stdio","command":"node","args":["/absolute/path/to/mcp-server/dist/index.js"],"env":{"IKLIM_ENV":"test","IKLIM_HMAC_SECRET":"<secret>","IKLIM_USERNAME":"<email>","IKLIM_PASSWORD":"<password>"}}'
Or edit ~/.openclaw/openclaw.json directly:
{
  "mcp": {
    "iklim": {
      "type": "stdio",
      "command": "node",
      "args": ["/absolute/path/to/mcp-server/dist/index.js"],
      "env": {
        "IKLIM_ENV": "test",
        "IKLIM_HMAC_SECRET": "<secret>",
        "IKLIM_USERNAME": "<email>",
        "IKLIM_PASSWORD": "<password>"
      }
    }
  }
}

Other MCP Clients

Any client that supports the MCP stdio standard can connect. Required parameters:
ParameterValue
transportstdio
commandnode
args["<absolute path to dist/index.js>"]
envThe four variables above

Tool Catalog

⚑ Lightning

ToolDescription
get_lightnings_withinQueries lightning strikes within a circular area defined by center coordinates and radius
get_lightnings_pageReturns paginated lightning data for a time interval

πŸŒͺ️ Thunderstorm

ToolDescription
get_thunderstorms_withinQueries thunderstorm cells within a circular area
get_thunderstorms_pageReturns paginated thunderstorm data for a time interval
get_thunderstorm_detailsFetches historical details for a specific storm event by eventId

🌧️ Precipitation

ToolDescription
get_precipitations_withinQueries radar precipitation data within a circular area; optionally filter by intensityThreshold
get_precipitations_pageReturns paginated precipitation data; intensityThreshold is required
Intensity levels (lowest β†’ highest): DRIZZLE < LIGHT < MODERATE < HEAVY < VERY_HEAVY < EXTREME

🌀️ Forecast

ToolDescription
get_hourly_forecastHourly forecasts for 1–14 days; supports 53 selectable metrics
get_daily_forecastDaily aggregate forecasts; same parameters as hourly (excluding solar panel fields)
get_current_weatherMost recent weather observation for a coordinate
WEATHER_ICON, TEMPERATURE, APPARENT_TEMPERATURE, DEW_POINT_TEMPERATURE, HUMIDITY, CLOUD_COVER, CLOUD_COVER_LOW, CLOUD_COVER_MID, CLOUD_COVER_HIGH, WIND_SPEED, WIND_GUST, WIND_DIRECTION, WIND_SPEED_AT_100M, WIND_DIRECTION_AT_100M, PRECIPITATION, RAIN, SHOWERS, SNOWFALL, SNOW_DEPTH, PRECIPITATION_PROBABILITY, WEATHER_CODE, PRESSURE_MSL, SURFACE_PRESSURE, VISIBILITY, EVAPOTRANSPIRATION, ET0_FAO_EVAPOTRANSPIRATION, VAPOUR_PRESSURE_DEFICIT, CAPE, LIFTED_INDEX, CONVECTIVE_INHIBITION, SUNSHINE_DURATION, SHORTWAVE_RADIATION, DIRECT_RADIATION, DIFFUSE_RADIATION, DIRECT_NORMAL_IRRADIANCE, GLOBAL_TILTED_IRRADIANCE, TERRESTRIAL_RADIATION, SHORTWAVE_RADIATION_INSTANT, DIRECT_RADIATION_INSTANT, DIFFUSE_RADIATION_INSTANT, DIRECT_NORMAL_IRRADIANCE_INSTANT, GLOBAL_TILTED_IRRADIANCE_INSTANT, TERRESTRIAL_RADIATION_INSTANT, SOIL_TEMPERATURE_0CM, SOIL_TEMPERATURE_6CM, SOIL_TEMPERATURE_18CM, SOIL_TEMPERATURE_54CM, SOIL_MOISTURE_0_TO_1CM, SOIL_MOISTURE_1_TO_3CM, SOIL_MOISTURE_3_TO_9CM, SOIL_MOISTURE_9_TO_27CM, SOIL_MOISTURE_27_TO_81CM, IS_DAY

πŸ‘€ Auth & User

ToolDescription
auth_registerCreates a new user account
auth_logoutInvalidates the current JWT token
user_get_meReturns the authenticated user’s profile
user_getReturns a user’s details by userId
user_create(Admin) Creates a new user with roles and status
user_update(Admin) Updates user fields by userId
user_listReturns a paginated user list; filterable by roles, status
user_unblockUnblocks a blocked user
user_change_passwordChanges password with oldPassword and newPassword
user_password_reset_requestSends a password reset e-mail
user_password_resetUpdates password using a reset token

🏒 Account

ToolDescription
account_getReturns account details by userId
account_createCreates a new account (INDIVIDUAL or ORGANIZATION)
account_updateUpdates account fields by accountId
account_activation_requestSends an activation e-mail
account_activateActivates the account using an e-mail verification token
account_phone_activation_requestSends an SMS verification code
account_activate_phoneVerifies the phone number using an SMS token
account_update_subscriptionChanges the subscription plan

πŸ“ Point Alarms

GPS-coordinate-based alert subscriptions for events within a configurable radius.
ToolDescription
point_alarm_registerCreates a new point alarm
point_alarm_updateUpdates an existing alarm
point_alarm_deleteDeletes an alarm
point_alarm_get_by_idReturns a single alarm’s details
point_alarm_get_by_recipientLists all alarms for a recipient
point_alarm_listPaginated alarm list; filterable by recipientIds

πŸ—ΊοΈ Geo Alarms

Administrative boundary, polygon, or H3 address-based alert subscriptions. Three boundary types are supported:
// Administrative boundary
{ "type": "ADMINISTRATIVE", "cityId": 6, "districtId": 60 }

// Polygon
{ "type": "POLYGON", "polygon": { "exterior": [{"lat": 39.9, "lng": 32.8}, ...] } }

// H3 cell index
{ "type": "H3INDEX", "h3Address": "8f2830828052d25" }
CRUD tools (geo_alarm_register, geo_alarm_update, geo_alarm_delete, geo_alarm_get_by_id, geo_alarm_get_by_recipient, geo_alarm_list) share the same signature as Point Alarms. Location catalog:
ToolDescription
geo_alarm_list_citiesLists all cities
geo_alarm_get_cityReturns city details by cityId
geo_alarm_list_districtsLists districts by cityId
geo_alarm_get_districtReturns district details by districtId
geo_alarm_list_neighborhoodsLists neighborhoods by districtId
geo_alarm_get_neighborhoodReturns neighborhood details by neighborhoodId

πŸ“… Forecast Alarms

Threshold-based alerts delivered at 04:00 UTC (morning) or 16:00 UTC (evening). Threshold parameters:
ParameterValues
precipitationThresholdNumeric value in mm
snowFallThresholdLIGHT | MODERATE | HEAVY
windGustThresholdSTRONG_WIND | STORM | SEVERE_STORM | HURRICANE
hotTemperatureThresholdHOT_SNAP | HEAVY_HOT_SNAP | EXTREME_HOT_SNAP
coldTemperatureThresholdCOLD_SNAP | HEAVY_COLD_SNAP | EXTREME_COLD_SNAP
CRUD tools follow the same signature as Point Alarms. Additional location catalog tools: forecast_alarm_list_cities, forecast_alarm_get_city, forecast_alarm_list_districts, forecast_alarm_get_district.

Architecture

src/
β”œβ”€β”€ index.ts          # MCP server bootstrap, tool routing
β”œβ”€β”€ config.ts         # Environment variable parsing
β”œβ”€β”€ auth.ts           # JWT token management (auto-refresh)
β”œβ”€β”€ client.ts         # HTTP API client (HMAC signing)
β”œβ”€β”€ security.ts       # HMAC-SHA256, nonce, idempotency key
└── tools/
    β”œβ”€β”€ lightnings.ts
    β”œβ”€β”€ thunderstorms.ts
    β”œβ”€β”€ precipitations.ts
    β”œβ”€β”€ forecasts.ts
    β”œβ”€β”€ auth.ts
    β”œβ”€β”€ accounts.ts
    β”œβ”€β”€ point-alarms.ts
    β”œβ”€β”€ geo-alarms.ts
    └── forecast-alarms.ts
Request flow:
MCP Client
    β”‚
    β–Ό
index.ts  (CallToolRequestSchema)
    β”‚
    β–Ό
tools/<category>.ts  ← Zod validation
    β”‚
    β–Ό
client.ts  (apiGet / apiPost / apiPatch / apiDelete)
    β”‚  β”œβ”€β”€ auth.ts β†’ get valid JWT (auto-refresh if needed)
    β”‚  └── security.ts β†’ generate HMAC-SHA256 signature
    β”‚
    β–Ό
iklim.co REST API

Authentication & Security

Every API interaction uses two independent security layers: JWT-based authentication and HMAC-SHA256 request signing. Both are applied to every request.

Automatic Auth Flow

The server logs in automatically on the first tool call. No manual login step is needed.
First tool call
    β”‚
    β–Ό
getValidAccessToken()          ← auth.ts
    β”‚
    β”œβ”€ No token state β†’ login()
    β”‚       POST /v1/auth/login  { username, password }
    β”‚       ← { accessToken, refreshToken }
    β”‚       Decode JWT payload β†’ calculate expiry
    β”‚       Save to tokenState
    β”‚
    β”œβ”€ accessToken expiring soon (< 30 s) β†’ refresh()
    β”‚       POST /v1/auth/refresh  { refreshToken }
    β”‚       ← { accessToken, refreshToken }
    β”‚       Update tokenState
    β”‚
    └─ accessToken valid β†’ return directly
The login and refresh endpoints do not include an Authorization: Bearer header β€” they are authenticated by HMAC signature alone.

HTTP Request Headers

HeaderValueNotes
Content-Typeapplication/jsonFixed
AuthorizationBearer <accessToken>Normal API requests only; omitted for login/refresh
X-Signaturehex stringHMAC-SHA256 signature
X-TimestampUnix epoch (ms)Date.now() as a string
X-NonceUUID v4Unique per request β€” prevents replay attacks
X-Idempotency-KeyUUID v4POST, PUT, PATCH, and DELETE requests

HMAC-SHA256 Signature

The X-Signature value is the HMAC-SHA256 of four components joined by |:
data_to_sign = "METHOD|PATH_WITH_QUERY|TIMESTAMP|BODY"
X-Signature  = HMAC-SHA256(data_to_sign, IKLIM_HMAC_SECRET) β†’ hex
Example β€” GET request:
METHOD    = "GET"
PATH      = "/v1/users?pageNumber=0&pageSize=10"
TIMESTAMP = "1774349677000"
BODY      = ""   ← empty for GET

data_to_sign = "GET|/v1/users?pageNumber=0&pageSize=10|1774349677000|"
X-Signature  = HMAC-SHA256(data_to_sign, secret) β†’ "a3f9c2..."
Example β€” POST request:
METHOD    = "POST"
PATH      = "/v1/lightnings/within"
TIMESTAMP = "1774349677000"
BODY      = '{"center":{"lat":39.87,"lng":32.74},"radius":50000,...}'

data_to_sign = "POST|/v1/lightnings/within|1774349677000|{\"center\":...}"
X-Signature  = HMAC-SHA256(data_to_sign, secret) β†’ "7be41d..."

Security Recommendations

  • Never commit IKLIM_HMAC_SECRET or IKLIM_PASSWORD to source control or git history
  • In production, use system environment variables or a secrets manager instead of a .env file
  • Use separate credentials for each environment (prod / test / local)
  • Rotate the HMAC secret regularly