Connect and authenticate

Beta availability
HERE Location Reasoning is currently available to beta participants. For information about joining the beta, visit HERE Location Reasoning.

Connect to HERE Location Reasoning by creating an OAuth 2.0 access token, starting an MCP session, discovering available tools, and calling a tool.

Follow the MCP session lifecycle in this order:

  1. initialize creates an MCP session and returns server capabilities and the Mcp-Session-Id header.
  2. notifications/initialized tells the server that the client is ready for normal operations.
  3. tools/list returns the available tools and their schemas.
  4. tools/call runs a tool request. This method requires a valid bearer token.

For an end-to-end walkthrough, see Get started with HERE Location Reasoning.

Before you begin

Locate the following credentials that you received during customer onboarding:

  • HERE Access Key ID
  • HERE Access Key Secret

Use these credentials to create a short-lived OAuth 2.0 bearer token before you call a tool.

Send requests to the MCP endpoint

Send all MCP requests to the HERE Location Reasoning endpoint:

https://hlr.here.ai/mcp

All requests must include:

  • HTTP method: POST
  • Content-Type header: application/json
  • Request body: a JSON-RPC 2.0 payload

Create an OAuth 2.0 access token

HERE Location Reasoning uses HERE Account OAuth 2.0 tokens for authentication. Sign a request with your Access Key Secret by using HMAC-SHA256, then exchange the signed request for a JSON Web Token (JWT).

Use this token endpoint:

https://account.api.here.com/oauth2/token

The JWT is short-lived. Create a new token when the current token expires.

Create a token in Python

import base64
import hashlib
import hmac
import time
import urllib.parse
import uuid

import httpx

TOKEN_URL = "https://account.api.here.com/oauth2/token"
KEY_ID = "<YOUR_ACCESS_KEY_ID>"
KEY_SECRET = "<YOUR_ACCESS_KEY_SECRET>"


def get_here_token() -> str:
    """Create a HERE OAuth 2.0 token with HMAC-SHA256 signed credentials."""
    timestamp = str(int(time.time()))
    nonce = uuid.uuid4().hex

    params = sorted([
        ("grant_type", "client_credentials"),
        ("oauth_consumer_key", KEY_ID),
        ("oauth_nonce", nonce),
        ("oauth_signature_method", "HMAC-SHA256"),
        ("oauth_timestamp", timestamp),
        ("oauth_version", "1.0"),
    ])

    encoded_params = urllib.parse.urlencode(params, quote_via=urllib.parse.quote)
    signature_base = "&".join([
        "POST",
        urllib.parse.quote(TOKEN_URL, safe=""),
        urllib.parse.quote(encoded_params, safe=""),
    ])
    signing_key = urllib.parse.quote(KEY_SECRET, safe="") + "&"
    signature = base64.b64encode(
        hmac.new(
            signing_key.encode(),
            signature_base.encode(),
            hashlib.sha256,
        ).digest()
    ).decode()

    authorization = (
        f'OAuth realm="",'
        f'oauth_consumer_key="{KEY_ID}",'
        f'oauth_nonce="{nonce}",'
        f'oauth_signature="{urllib.parse.quote(signature, safe="")}",'
        f'oauth_signature_method="HMAC-SHA256",'
        f'oauth_timestamp="{timestamp}",'
        f'oauth_version="1.0"'
    )

    response = httpx.post(
        TOKEN_URL,
        content=b"grant_type=client_credentials",
        headers={
            "Content-Type": "application/x-www-form-urlencoded",
            "Authorization": authorization,
        },
        timeout=30,
    )
    response.raise_for_status()
    return response.json()["access_token"]

Create a token with the HERE OLP CLI

Install the HERE OLP CLI, then run the following commands:

# Store the credentials in the file that the CLI imports.
cat > ~/.here/credentials.properties << EOF
here.token.endpoint.url=https://account.api.here.com/oauth2/token
here.client.id=<YOUR_CLIENT_ID>
here.access.key.id=<YOUR_ACCESS_KEY_ID>
here.access.key.secret=<YOUR_ACCESS_KEY_SECRET>
EOF

# Import the credentials as the gateway profile.
olp credentials import gateway ~/.here/credentials.properties

# Print an OAuth 2.0 bearer token.
olp api token get --profile gateway

Add the token to a request

Send the JWT as a bearer token when you call tools/call:

Authorization: Bearer <HERE_JWT>

Start and use an MCP session

MCP uses a stateful JSON-RPC 2.0 interface. Start a session, save its session ID, and include that ID in every later request in the session.

1. Initialize the session

Send an initialize request. A successful response includes the Mcp-Session-Id header.

Mcp-Session-Id: <value-from-initialize-response>

Save this value. Include it in every request after initialize; otherwise, requests can fail or route to a different session.

2. Notify HERE Location Reasoning that the client is ready

Send notifications/initialized after initialization. This notification does not return a response body.

3. List available tools

Send tools/list to retrieve available tools and their schemas.

4. Call a tool

Send tools/call with the session ID and a valid bearer token.

Authentication requirements

A bearer token is required only for tools/call. You can send an Authorization header with other methods, but it is not required.

MethodRequires bearer tokenDescription
initializeNoStarts an MCP session and returns server information.
notifications/initializedNoConfirms that the client is ready after initialization.
tools/listNoLists available tools and their schemas.
resources/listNoLists available MCP resources.
resources/readNoReads an MCP resource by URI.
tools/callYesRuns a location tool.

Run a complete session with cURL

HERE_LOCATION_REASONING_URL="https://hlr.here.ai/mcp"
TOKEN="<YOUR_HERE_JWT>"

# 1. Initialize the session. Save Mcp-Session-Id from the response headers.
curl -s -D - -X POST "$HERE_LOCATION_REASONING_URL" \
  -H "Content-Type: application/json" \
  -d '{
    "jsonrpc": "2.0",
    "id": 1,
    "method": "initialize",
    "params": {
      "protocolVersion": "2025-03-26",
      "capabilities": {},
      "clientInfo": {"name": "curl", "version": "1.0"}
    }
  }'

SESSION_ID="<from-response-header>"

# 2. Tell the server that the client is ready.
curl -s -X POST "$HERE_LOCATION_REASONING_URL" \
  -H "Content-Type: application/json" \
  -H "Mcp-Session-Id: $SESSION_ID" \
  -d '{
    "jsonrpc": "2.0",
    "method": "notifications/initialized",
    "params": {}
  }'

# 3. List the tools available in this session.
curl -s -X POST "$HERE_LOCATION_REASONING_URL" \
  -H "Content-Type: application/json" \
  -H "Mcp-Session-Id: $SESSION_ID" \
  -d '{
    "jsonrpc": "2.0",
    "id": 2,
    "method": "tools/list",
    "params": {}
  }'

# 4. Call a tool. This request requires a bearer token.
curl -s -X POST "$HERE_LOCATION_REASONING_URL" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Mcp-Session-Id: $SESSION_ID" \
  -d '{
    "jsonrpc": "2.0",
    "id": 3,
    "method": "tools/call",
    "params": {
      "name": "hlr___geocode",
      "arguments": {"q": "Berlin, Germany"}
    }
  }'

Troubleshoot connection and authentication errors

HTTP 401: Unauthorized

This error occurs when:

  • A tools/call request does not include the Authorization header.
  • The bearer token has expired.
  • The token signature is invalid.

Create a new token by using the OAuth 2.0 flow, then retry the request.

HTTP 403: Forbidden

This error occurs when the token is valid but the account is not authorized to use HERE Location Reasoning.

Contact your HERE account representative to verify your entitlements.

HTTP 429: Too Many Requests

This error occurs when the request rate exceeds the per-customer limit.

Stop sending requests and retry after a short delay. If you consistently receive this error, contact your HERE account representative to discuss rate limit adjustments.

JSON-RPC errors

Tool execution errors use a standard JSON-RPC error response, even when the HTTP status is 200:

{
  "jsonrpc": "2.0",
  "id": 3,
  "error": {
    "code": -32000,
    "message": "validation failed: ..."
  }
}

These errors indicate a tool-parameter problem, such as invalid input or a missing required field, rather than an authentication problem.

Next steps


Did this page help you?