# How to Author .geolibre.json Projects Headlessly with AI Clients

> Learn to author .geolibre.json projects headlessly with AI clients. Use Python MCP server or FastAPI API for programmatic creation and modification, ensuring data integrity with atomic writes and schema validation.

- Repository: [Open Geospatial Solutions/GeoLibre](https://github.com/opengeos/GeoLibre)
- Tags: how-to-guide
- Published: 2026-08-22

---

**AI clients can create and modify GeoLibre projects programmatically using the Python MCP server or FastAPI HTTP API, which perform atomic writes and validate every change against the project schema before saving.**

GeoLibre stores complete workspace configurations—including layers, styles, and view states—in a single [`.geolibre.json`](https://github.com/opengeos/GeoLibre/blob/main/.geolibre.json) file defined by the schema in [`docs/project-format.md`](https://github.com/opengeos/GeoLibre/blob/main/docs/project-format.md). Headless authoring enables automated pipelines and AI agents to build these projects without launching the GUI, using either a pure-Python MCP server or a language-agnostic HTTP interface. Both implementations share a common safety contract that validates project markers and performs atomic file operations to prevent corruption.

## The Two-Layer Headless Architecture

GeoLibre provides complementary interfaces for headless project manipulation, each suited to different integration scenarios.

### Python MCP Server

The **Python MCP server** (`geolibre[mcp]`) offers a widget-free authoring engine that loads JSON projects, applies discrete edits, and writes them back atomically. Located in [`python/src/geolibre/mcp/server.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/mcp/server.py), the `build_server` function initializes an `MCPServer` instance with tools like `create_project`, `add_geojson_layer`, and `set_view`. Each tool executes within an edit context manager (lines 83-99) that guarantees the file remains a valid GeoLibre project throughout the operation.

### FastAPI Side-Car

The **FastAPI side-car** exposes the same toolset through REST endpoints for remote AI services or polyglot environments. Defined in [`backend/geolibre_server_api/main.py`](https://github.com/opengeos/GeoLibre/blob/main/backend/geolibre_server_api/main.py) (starting at line 558), routes like `/project/create` and `/layer/add` wrap the MCP server tools, returning identical JSON payloads to ensure consistency between interfaces.

## Creating Projects with the Python MCP Server

To begin headless authoring, install the optional MCP SDK and initialize a workspace that enforces safe file extensions.

```python

# pip install "geolibre[mcp]"

from geolibre.mcp import MCPServer
from geolibre.mcp.server import build_server
from geolibre.mcp.workspace import Workspace

# Create sandboxed workspace (restricts writes to allowed PROJECT_SUFFIXES)

ws = Workspace(root_path="tmp_workspace")
server = build_server(ws)

def call(name, **kwargs):
    return server.call(name, **kwargs)

```

### Initializing a New Project

Use the `create_project` tool to generate a valid project file containing the required markers (`mapView` or `basemapStyleUrl`), as defined by `PROJECT_MARKERS` in [`python/src/geolibre/mcp/server.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/mcp/server.py) (lines 77-78).

```python
proj = call(
    "create_project",
    path="my_demo.geolibre.json",
    name="Demo project",
    overwrite=True,
)
print("Created:", proj["path"])

```

### Adding Data Layers

Add geospatial data using specialized layer tools that accept inline GeoJSON or remote sources. The following example embeds a point feature collection with a specific style:

```python
geojson = {
    "type": "FeatureCollection",
    "features": [
        {
            "type": "Feature",
            "geometry": {"type": "Point", "coordinates": [-122.4, 37.8]},
            "properties": {"name": "San Francisco"}
        }
    ]
}

call(
    "add_geojson_layer",
    path=proj["path"],
    name="City points",
    geojson=geojson,
    style={"circle-radius": 6, "circle-color": "#ff6600"},
)

```

### Configuring View and Exporting

Adjust the map viewport and export standalone HTML without opening the UI:

```python

# Set initial view

call(
    "set_view",
    path=proj["path"],
    center=[-122.4, 37.8],
    zoom=10,
    bearing=0,
    pitch=0,
)

# Export self-contained HTML

html = call(
    "export_html",
    path=proj["path"],
    out="my_demo.html",
)
print("HTML exported to:", html["out"])

```

## Using the HTTP API for Language-Agnostic Workflows

For AI clients written in languages other than Python, the FastAPI backend provides identical functionality through HTTP requests. The endpoints in [`backend/geolibre_server_api/main.py`](https://github.com/opengeos/GeoLibre/blob/main/backend/geolibre_server_api/main.py) mirror the MCP tools, returning JSON structures that include `path`, `name`, and `layerCount`.

```http
POST /api/create_project HTTP/1.1
Host: localhost:8765
Content-Type: application/json

{
  "path": "remote_demo.geolibre.json",
  "name": "Remote demo",
  "overwrite": true
}

```

```http
POST /api/add_geojson_layer HTTP/1.1
Host: localhost:8765
Content-Type: application/json

{
  "path": "remote_demo.geolibre.json",
  "name": "Cities",
  "geojson": {
    "type": "FeatureCollection",
    "features": [
      {"type": "Feature", "geometry": {"type": "Point", "coordinates": [-122.4, 37.8]}}
    ]
  },
  "style": {"circle-color": "#00ff00", "circle-radius": 5}
}

```

```http
POST /api/export_html HTTP/1.1
Host: localhost:8765
Content-Type: application/json

{
  "path": "remote_demo.geolibre.json",
  "out": "remote_demo.html"
}

```

## Safety Contracts and Validation

Both the MCP server and HTTP API enforce strict safety contracts defined in [`python/src/geolibre/authoring.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/authoring.py) to prevent data corruption.

### Project Validation Markers

Before any edit, the system verifies that the file contains at least one of the `PROJECT_MARKERS`: `"mapView"` or `"basemapStyleUrl"`. This check, implemented in [`python/src/geolibre/mcp/server.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/mcp/server.py), ensures only valid GeoLibre projects are manipulated.

### Atomic Write Operations

All changes use atomic file operations via the `save_project` function in [`python/src/geolibre/authoring.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/authoring.py) (lines 105-114). The implementation writes to a temporary file before moving it into place, preventing partial writes during crashes.

### Size Limit Protections

The system rejects projects exceeding 256 MiB (`MAX_PROJECT_BYTES` in [`python/src/geolibre/authoring.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/authoring.py), lines 42-44) to prevent memory exhaustion during automated processing.

## Summary

- **Headless authoring** of [`.geolibre.json`](https://github.com/opengeos/GeoLibre/blob/main/.geolibre.json) projects is supported through both a Python MCP server and a FastAPI HTTP API, enabling AI clients to create, edit, and export workspaces programmatically.
- The **Python MCP server** in [`python/src/geolibre/mcp/server.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/mcp/server.py) provides tools like `create_project`, `add_geojson_layer`, and `set_view` that execute within validated, atomic edit contexts.
- The **FastAPI side-car** in [`backend/geolibre_server_api/main.py`](https://github.com/opengeos/GeoLibre/blob/main/backend/geolibre_server_api/main.py) exposes identical functionality via REST endpoints for remote or polyglot AI services.
- **Safety contracts** require project files to contain `mapView` or `basemapStyleUrl` markers, enforce a 256 MiB size limit, and use atomic writes to prevent corruption.
- Both interfaces generate files compatible with GeoLibre's desktop, web, and Jupyter deployments without requiring GUI interaction.

## Frequently Asked Questions

### What is the maximum file size for .geolibre.json projects in headless mode?

GeoLibre enforces a **256 MiB limit** (`MAX_PROJECT_BYTES` in [`python/src/geolibre/authoring.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/authoring.py)) to prevent memory exhaustion during automated processing. Projects exceeding this threshold are rejected before any write operation begins.

### How does the MCP server prevent corrupted project files during crashes?

The server uses **atomic writes** implemented in [`python/src/geolibre/authoring.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/authoring.py) (lines 105-114). It writes changes to a temporary file first, then moves the file into place only after validation succeeds. This ensures the target path never contains a partially written JSON structure.

### Can I author .geolibre.json projects using languages other than Python?

Yes. The **FastAPI side-car** exposes the full toolset via HTTP endpoints defined in [`backend/geolibre_server_api/main.py`](https://github.com/opengeos/GeoLibre/blob/main/backend/geolibre_server_api/main.py), allowing any language capable of making REST requests—such as JavaScript, Go, or Rust—to create and modify projects using the same JSON payloads as the Python client.

### What markers are required for a file to be recognized as a valid GeoLibre project?

Valid project files must contain at least one of the `PROJECT_MARKERS` defined in [`python/src/geolibre/mcp/server.py`](https://github.com/opengeos/GeoLibre/blob/main/python/src/geolibre/mcp/server.py) (lines 77-78): either `"mapView"` or `"basemapStyleUrl"`. The headless tools validate these keys before applying any edits to ensure schema compliance.