Skip to main content
Glama
codesyntax

Plone Dynamic Pages MCP Server

by codesyntax
README.md
# Plone Dynamic Pages MCP Server

An MCP server that **extends the official [`@plone/mcp`](https://github.com/plone/plone-mcp) server** with seven additional tools for managing Plone sites built with the [cs_dynamicpages](https://github.com/codesyntax/cs_dynamicpages) product. Call `plone_configure` once per session, then use the full official toolset plus the dynamic-layout tools.

## 🚀 Key Features

*   **Official toolset included**: All `@plone/mcp` tools (blocks, workflow, translations, users, navigation tree, vocabularies, search) are available as-is.
*   **Dynamic Layout Management**: Analyze full page structures, including rows and featured items.
*   **Full CRUD Operations**: Create, patch, move, and delete Plone content and layout components.
*   **Universal Content Support**: Generic `plone_create_content` tool for any Plone content type (Folder, Document, Link, etc.).
*   **Local File Integration**: `plone_upload_local_asset` uploads files straight from your filesystem.

---

## 🛠️ Dynamic Pages Tools (added on top of `@plone/mcp`)

| Tool | Description |
| :--- | :--- |
| `plone_get_site_definitions` | Fetches site-specific definitions (Schemas and Row Types) from Plone. |
| `plone_get_dynamic_page_content` | Returns the full JSON structure of a DynamicPage (Rows + Featured Items). Handles up to 1000 items. |
| `plone_create_dynamic_page_row` | Creates a new layout section (`DynamicPageRow`) in a page, optionally with nested featured items. |
| `plone_create_dynamic_page_row_featured` | Creates a featured item (`DynamicPageRowFeatured`) within an existing row. |
| `plone_move_dynamic_page_row` | Reorders layout rows (top, bottom, or a specific position). |
| `plone_upload_file` | Uploads images or files using Base64 data. |
| `plone_upload_local_asset` | Reads a file from the local filesystem and uploads it to Plone. |

Everything else comes from the official package: `plone_configure`, `plone_create_content`, `plone_update_content`, `plone_delete_content`, `plone_search`, `plone_get_navigation_tree`, `plone_get_block_schemas`, workflow and translations tools, etc.

---

## ⚠️ Differences from the standalone v1 server

Earlier versions of this server shipped their own `set_session_context` / `check_credentials_status` / `create_dynamic_page_row` tools and authenticated with a `__ac` cookie. As of v2 the server delegates to `@plone/mcp`:

- Connect with `plone_configure({ baseUrl, token })` or `plone_configure({})` using `PLONE_BASE_URL` / `PLONE_TOKEN` (or username/password). The client does **not** support cookie auth; use a token or basic auth.
- Tool arguments use site-relative **paths** (e.g. `/rows`, `/en/home`), not full `++api++` URLs.
- `create_content`/`search_content`/`patch_content`/`delete_content` map to `plone_create_content`/`plone_search`/`plone_update_content`/`plone_delete_content`.

---

## đź’» Installation & Usage

The server runs over STDIO (no Plone-side changes required) and can be launched either directly from the GitHub repository via `npx` or from a local clone of this repo.

### Quick Start: run via npx from GitHub (no cloning required)

Add the following configuration to your **Opencode** (`opencode.json`):

```json
{
  "mcp": {
    "cs-dynamicpages-mcp": {
      "type": "local",
      "command": ["npx", "-y", "github:codesyntax/cs-dynamicpages-mcp"],
      "enabled": true
    }
  }
}
```

`npx` fetches the repository from GitHub and launches the server automatically; nothing else needs to be installed.

### Running from a local clone

Clone the repository and install its dependencies:

```bash
git clone https://github.com/codesyntax/cs-dynamicpages-mcp
cd cs-dynamicpages-mcp
npm install
```

Then point your MCP client at the local entry point instead of the GitHub package:

```json
{
  "mcp": {
    "cs-dynamicpages-mcp": {
      "type": "local",
      "command": ["npx", "tsx", "src/local.ts"],
      "enabled": true
    }
  }
}
```

or simply run it directly with `npm start`.

### Environment Variables

*   `PLONE_BASE_URL`: The base URL of your Plone site (used by `plone_configure` as a fallback).
*   `PLONE_TOKEN`: Bearer token for authentication.
*   `PLONE_USERNAME` / `PLONE_PASSWORD`: Basic auth credentials.

*Note: You can also set these dynamically during a session with the `plone_configure` tool.*

Requires **Node.js 22+** (the same requirement as `@plone/mcp`).

---

## 🏗️ Project Structure

*   **`src/local.ts`**: Entry point for local `stdio` execution (the extended server).
*   **`src/extended-server.ts`**: Creates the `@plone/mcp` server and registers the dynamic pages tools.
*   **`src/tools/registerDynamicPagesTools.ts`**: The seven dynamic pages tools and their registration.
*   **`src/dynamicPages/`**: Pure helpers (payload builders, ordering computation, hierarchy reassembly) shared by the tools.

---

## đź§Ş Development

```bash
npm install
npm test          # vitest unit + handler seam tests
npm run typecheck # tsc --noEmit
npm start         # run the stdio server directly
```

This project pins `@plone/mcp` to the released `1.0.0-alpha.1` package; bump it in `package.json` to pick up newer releases.

---

## đź”’ Security

This server handles credentials strictly within your local environment. The `@plone/mcp` code runs from `node_modules` on your machine, and your API tokens are only ever sent to the Plone site you configure. Ensure you trust the source before providing sensitive API tokens.

TDQS

B3.1/5.0

Scored across 13 tools

Disambiguation4/5

Most tools have clear, distinct purposes (e.g., get_site_definitions vs. get_dynamic_page_content). However, overlap exists between create_content and the specialized row creation tools, and between upload_file and upload_local_asset, which could lead to confusion about which to use.

Naming Consistency5/5

All tool names follow a consistent verb_noun pattern using lowercase with underscores (e.g., create_content, patch_content, search_content). The naming is uniform and predictable, with no mixing of conventions.

Tool Count5/5

The server has 13 tools, which is within the ideal 3-15 range. Each tool serves a distinct functional need—configuration, CRUD, dynamic page operations, and file uploads—without being excessive or sparse.

Completeness4/5

The tool set covers the core domain of Dynamic Page management, including creation, retrieval, update, delete, search, and specialized row operations. A notable gap is the lack of a generic get_content tool for non-DynamicPage objects, but search_content can serve that purpose, so the gap is minor.

Maintenance

ActivityMaintained
ResponsivenessNo issues