Skip to main content
AllMCPs
BrowseBestCategoriesStackCompareToolsGuidesBlog Log in Submit MCP

Stay in the loop

Get new MCP servers and top picks in your inbox.

AllMCPs

The open directory for discovering and installing Model Context Protocol servers.

Explore

  • Browse servers
  • Best MCP servers
  • Categories
  • MCP clients
  • Agent prompts
  • Stack Builder
  • Compare servers
  • Tags index
  • Submit a server
  • Pricing

Learn

  • Guides hub
  • What is MCP?
  • Install guide
  • Troubleshooting
  • Security
  • Blog
  • Blog RSS

Tools

  • All tools
  • Config generator
  • Config validator
  • MCP playground
  • OpenAPI β†’ MCP
  • Badge generator

For agents

  • API docs
  • Trust & traffic
  • llms.txt β†— (opens in a new tab)
  • Catalog JSON β†— (opens in a new tab)
  • Remote MCP β†— (opens in a new tab)

Company

  • About
  • Contact
  • X (@AllMCPs) β†— (opens in a new tab)
  • GitHub β†— (opens in a new tab)
  • Terms
  • Privacy
AllMCPs VerifiedAllMCPs VerifiedFeatured on Nick LaunchesFeatured on Nick LaunchesLaunch Llama NewsletterLaunch Llama NewsletterVerified DR - allmcps.comVerified DR - allmcps.comFeatured on SaaSGrowFeatured on SaaSGrowFeatured on Twelve ToolsFeatured on Twelve ToolsFeatured on Saaspa.geFeatured on Saaspa.geFeatured on Findly.toolsFeatured on Findly.toolsFeatured on Startup FameFeatured on Startup FameFeatured on LaunchKiwiFeatured on LaunchKiwiFeatured on ScrollLaunchFeatured on ScrollLaunchFeatured on DailyPingsFeatured on DailyPingsFazier badgeFazier badgeFeatured on NewTool.siteFeatured on NewTool.siteFeatured on saasfame.comFeatured on saasfame.comDR Checker - Domain RatingDR Checker - Domain RatingListed on Turbo0Listed on Turbo0Launched on LaunchBoard - Product Launch PlatformLaunched on LaunchBoard - Product Launch PlatformList on SimilarlabsList on Similarlabshttps://codetrendy.comhttps://codetrendy.comListed on DevTool.ioFeatured on BuildlistFeatured on BuildlistAllMCPs VerifiedAllMCPs VerifiedFeatured on Nick LaunchesFeatured on Nick LaunchesLaunch Llama NewsletterLaunch Llama NewsletterVerified DR - allmcps.comVerified DR - allmcps.comFeatured on SaaSGrowFeatured on SaaSGrowFeatured on Twelve ToolsFeatured on Twelve ToolsFeatured on Saaspa.geFeatured on Saaspa.geFeatured on Findly.toolsFeatured on Findly.toolsFeatured on Startup FameFeatured on Startup FameFeatured on LaunchKiwiFeatured on LaunchKiwiFeatured on ScrollLaunchFeatured on ScrollLaunchFeatured on DailyPingsFeatured on DailyPingsFazier badgeFazier badgeFeatured on NewTool.siteFeatured on NewTool.siteFeatured on saasfame.comFeatured on saasfame.comDR Checker - Domain RatingDR Checker - Domain RatingListed on Turbo0Listed on Turbo0Launched on LaunchBoard - Product Launch PlatformLaunched on LaunchBoard - Product Launch PlatformList on SimilarlabsList on Similarlabshttps://codetrendy.comhttps://codetrendy.comListed on DevTool.ioFeatured on BuildlistFeatured on Buildlist
Β© 2026 Jackalope Digital LLC. All rights reserved.
  1. Home
  2. πŸ’» Developer Tools
  3. Laserfiche Mcp
L
Health: Not checked yetWe have not completed a health check for this listing yet.Last checked 8/11/2026, 12:13:34 AM

Laserfiche Mcp

Enrichment pendingWe haven’t run our AI enrichment pass on this listing yet, so the overview, use cases, and FAQ below may be sparse or missing. We work through the catalog over time β€” check back soon.
View Repository

MCP server for self-hosted Laserfiche repositories β€” search and read documents from Claude.

Quick Install

Automated & IDE Setup

Copy the AI prompt to install this server into Claude Code, Cursor, or another agent β€” or use 1-click editor setup below.

Add to CursorAdd to VS Code
Manual Client & Custom JSON ConfigExpand JSON β–Ύ

Install Config Generator

Choose your client
claude_desktop_config.json
{
  "mcpServers": {
    "laserfiche-mcp": {
      "command": "npx",
      "args": [
        "-y",
        "laserfiche-mcp"
      ]
    }
  }
}

πŸ’‘ Paste into ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) or %APPDATA%\Claude\claude_desktop_config.json (Windows)

Install Directory Badge Claim listing AlternativesπŸ’» More in Developer Tools

Documentation Overview

laserfiche-mcp

PyPI version Python versions CI License: MIT MCP

Community project β€” not affiliated with or endorsed by Laserfiche.

A Model Context Protocol server that lets Claude (Desktop, Code, or any MCP client) search and read documents in a Laserfiche repository.

Current release v2.2.0 β€” read and write tools for self-hosted Repository API v1 and v2, a one-click Claude Desktop extension, and an optional remote HTTP transport with per-user OAuth for web clients. See the changelog for detail and the roadmap for what's next.

What you can do with it

Once connected, Claude can:

Read (always available):

  • Search the repository with native Laserfiche search syntax, by name pattern, or via the LLM-friendly search_natural flow (asks the server for templates first, then runs with automatic 400 repair)
  • List the contents of any folder, look up an entry by ID or path, read all template field values, list field/tag/template/link definitions and audit reasons
  • Inspect document metadata, fetch the raw edoc as base64, or extract text server-side (PDF via pypdf) β€” all via get_document_edoc(..., mode=...)

Write (opt-in via LF_READ_ONLY=false):

  • Create folders, import documents, copy entries (async), rename and move entries
  • Set, merge, and clear fields, tags, and links on an entry
  • Assign and remove templates β€” with optional client-side validation of repository-required fields before the API call
  • Delete entries (folders cascade), edocs, and specific page ranges β€” all with a two-step previewβ†’confirm-token flow, HMAC-signed and bound to operation + entry, expiring after 5 minutes

Operate safely β€” every write checks the entry's path against LF_WRITE_PATHS_ALLOW / LF_WRITE_PATHS_DENY, folder deletes refuse unless force_large_delete=true when child count exceeds LF_DELETE_FOLDER_MAX_DESCENDANTS, and LF_WRITE_TOOLS_ALLOWED can scope a deployment to e.g. metadata-only writes.

Install

Two ways to run it, depending on who you are.

For everyone β€” the Claude Desktop extension

Chat with your Laserfiche repository from Claude Desktop β€” no terminal, no config files.

1. Download

Download the extension (always the newest version), or browse the latest release. You'll need Claude Desktop installed first.

2. Double-click & connect

Double-click the file, click Install, and fill in the short form that appears:

FieldWhat to enter
Repository API URLYour Laserfiche server address, e.g. https://your-server/LFRepositoryAPI
Repository nameThe repository you pick when signing in to Laserfiche Web Access
UsernameA Laserfiche account that can read the repository
PasswordThat account's password β€” stored safely in your computer's keychain

Not sure what goes where? Ask whoever runs Laserfiche at your organization β€” it takes them a minute.

3. Ask

Open a chat and try:

  • "Find every invoice from March in the Accounting folder."
  • "What's in the Onboarding folder? Summarize the newest document."
  • "Search for contracts mentioning Acme and list them with dates."

[!NOTE] Claude can look, but never change or delete β€” the extension is read-only by default, and your password lives in your operating system's keychain, not a text file.

Full walkthrough for end users and team rollouts: docs/desktop-extension.md.

For developers β€” the Python package

bash
uvx laserfiche-mcp            # run directly, no install
pip install laserfiche-mcp    # or add it to your environment

Requires Python 3.10+ and a reachable Laserfiche Repository API Server (self-hosted) with a service account that can read it, plus any MCP client (Claude Desktop, Claude Code, MCP Inspector). For local development:

bash
git clone https://github.com/SamuelSHernandez/laserfiche-mcp
cd laserfiche-mcp
uv sync --extra dev

Configure

Copy the example file and fill in your repository details:

bash
cp .env.example .env
$EDITOR .env

Minimum required variables for self-hosted password-grant auth:

VariableExample
LF_REPO_API_URLhttps://lf.example.com/LFRepositoryAPI
LF_REPOSITORY_IDmy-repo
LF_API_VERSIONv1 (default) or v2 β€” see below
LF_USERNAMEservice-account
LF_PASSWORD(your service account password)
LF_AUTH_MODEpassword
LF_READ_ONLYtrue (default β€” see Writes section below)

Optional write-mode variables (all default off; see the Safety model section for context):

VariableDefaultPurpose
LF_READ_ONLYtrueSet false to register the write tools
LF_WRITE_PATHS_ALLOWunsetComma-separated path prefixes where writes are permitted (case-insensitive)
LF_WRITE_PATHS_DENYunsetComma-separated path prefixes where writes are refused (deny wins over allow)
LF_WRITE_TOOLS_ALLOWEDunsetComma-separated write-tool names to scope what registers; e.g. metadata-only
LF_DELETE_FOLDER_MAX_DESCENDANTS50Refuse folder deletes above this immediate-child count unless force_large_delete=true
LF_REQUIRE_AUDIT_REASONfalseWhen true, delete_entry refuses to execute without audit_reason_id
LF_VALIDATE_REQUIRED_FIELDStrueValidate repo-wide required fields client-side before assign_template PUTs
LF_VALIDATE_NAMEStruePre-flight field / tag / template / link-type names against cached schema definitions; returns invalid_*_name instead of an opaque 400
LF_SCHEMA_CACHE_TTL_SECONDS300Cache window for the schema-definition lookups that back LF_VALIDATE_NAMES and LF_VALIDATE_REQUIRED_FIELDS. Set to 0 to disable caching.
LF_IMPORT_MAX_BYTES25 MBClient-side cap on import_document payload size
LF_EDOC_MAX_BYTES25 MBCap on get_document_edoc downloads in bytes/text modes

See .env.example for the full list including OAuth config, pagination limits, request timeout, retry attempts, and SSL verification.

API version note: LFRepositoryAPI ships with different routing surfaces across builds. Older self-hosted installs expose /v1/... paths; newer ones expose /v2/.... Probe your server with:

Terminal
curl {LF_REPO_API_URL}/v1/Repositories
curl {LF_REPO_API_URL}/v2/Repositories

Whichever returns a 200 with a JSON repo list is your version. If the wrong value is set, every call fails with 400 UnsupportedApiVersion. The default is v1 because that is what most current on-prem installations expose.

Auth note: Laserfiche self-hosted does not accept HTTP Basic auth. The server exchanges your username/password for a bearer token at POST /{api_version}/Repositories/{repository_id}/Token on first request and refreshes it automatically before expiry. The same flow works on both v1 and v2.

Connect to Claude Desktop

Edit ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) or %APPDATA%\Claude\claude_desktop_config.json (Windows):

config.json
{
  "mcpServers": {
    "laserfiche": {
      "command": "uvx",
      "args": ["laserfiche-mcp"],
      "env": {
        "LF_REPO_API_URL": "https://lf.example.com/LFRepositoryAPI",
        "LF_REPOSITORY_ID": "my-repo",
        "LF_API_VERSION": "v1",
        "LF_USERNAME": "service-account",
        "LF_PASSWORD": "replace-me",
        "LF_AUTH_MODE": "password",
        "LF_READ_ONLY": "true"
      }
    }
  }
}

Restart Claude Desktop. The Laserfiche tools will appear in the tool picker.

Connect to Claude Code

Terminal
claude mcp add laserfiche -- uvx laserfiche-mcp

(Pass env vars via --env LF_REPO_API_URL=... flags or set them in your shell before running Claude Code.)

Test it locally with the MCP Inspector

Terminal
npx @modelcontextprotocol/inspector uvx laserfiche-mcp

This opens a UI where you can call each tool directly and watch the JSON-RPC traffic β€” useful for verifying endpoint shapes against your specific Repository API Server version before wiring it into Claude.

Remote HTTP (web clients)

The default transport is stdio β€” for local clients that launch the server as a subprocess (Claude Desktop, Claude Code, Cursor, Gemini CLI). Web and cloud clients (claude.ai custom connectors, ChatGPT connectors) can't spawn a local process; they connect to a URL. The same server can serve those clients over Streamable HTTP:

bash
laserfiche-mcp --http                 # binds 127.0.0.1:8000, path /mcp
laserfiche-mcp --http --port 9000     # override port for this run

Configuration (all optional, LF_* env like everything else):

VariableDefaultPurpose
LF_HTTP_HOST127.0.0.1Bind interface. Loopback by default β€” not reachable off the machine.
LF_HTTP_PORT8000Listen port.
LF_HTTP_PATH/mcpEndpoint path; clients connect to http(s)://host:port/mcp.
LF_HTTP_AUTH_TOKEN(unset)Static shared bearer token. Simplest auth; ignored when OAuth is on.
LF_HTTP_OAUTH_ISSUER(unset)Turns on per-user OAuth β€” verifies each caller's token against this authorization server.

The --http server chooses its auth by precedence: OAuth (if LF_HTTP_OAUTH_ISSUER is set) β†’ static token (if LF_HTTP_AUTH_TOKEN) β†’ none (loopback only). OAuth is the multi-user path for claude.ai / ChatGPT; see Per-user OAuth below.

Verify locally with the Inspector (point it at the URL, not the command):

bash
laserfiche-mcp --http &
npx @modelcontextprotocol/inspector   # then connect to http://127.0.0.1:8000/mcp

Per-user OAuth

For a multi-user connector, run the server as an OAuth 2.1 Resource Server β€” each user signs in through your existing identity provider (LFDS, Microsoft Entra, Okta, Auth0, Google) and the server verifies their token:

Terminal
pip install 'laserfiche-mcp[oauth]'

LF_HTTP_OAUTH_ISSUER="https://login.microsoftonline.com/<tenant>/v2.0" \
LF_HTTP_PUBLIC_URL="https://lf.example.com/mcp" \
LF_HTTP_OAUTH_AUDIENCE="api://laserfiche-mcp" \
LF_HTTP_OAUTH_REQUIRED_SCOPES="laserfiche.read" \
  laserfiche-mcp --http --host 0.0.0.0

The server then serves protected-resource metadata (RFC 9728), so claude.ai / ChatGPT discover your authorization server, run the authorization_code + PKCE flow, and present a bearer token that this server verifies (signature via JWKS, plus aud / iss / exp / scopes). This is authentication at the edge β€” verified requests still reach Laserfiche via the shared service account, so the Laserfiche audit trail shows that account, not the end user. Full details, including IdP registration and the security checklist, are in docs/remote-http.md.

Connecting a web client

claude.ai and ChatGPT connectors need a public HTTPS URL. In practice that means putting this server behind a reverse proxy (or a tunnel like cloudflared / ngrok for a spike) and adding the resulting https://…/mcp URL as a custom connector in the client's settings.

[!WARNING] Read this before exposing --http to a network.

  • Configure auth: OAuth (LF_HTTP_OAUTH_ISSUER) for multi-user, or at least a long random LF_HTTP_AUTH_TOKEN. Binding off-loopback with neither logs a warning and leaves your repository reachable unauthenticated.
  • Terminate TLS at a reverse proxy in front of this server (it speaks plain HTTP).
  • Your Laserfiche server is self-hosted behind a firewall; a public connector needs a deliberate network path in to it (VPN / DMZ / tunnel).
  • See docs/remote-http.md for the full deployment and security checklist.

Tools

Tool names below are shown in their original verb-first form (get_entry, set_fields, ...) for readability. In v2.0 every tool is also registered under the laserfiche_{resource}_{verb} form (laserfiche_entry_get, laserfiche_field_set, ...). Both names resolve to the same function. The laserfiche_* names are the recommended path; the old names remain as deprecation aliases through v2.x and will be removed in v3.0. The authoritative mapping lives in _V2_RENAME_MAP in src/laserfiche_mcp/server.py.

Reads (always registered)

Toolv2 namePurpose
search_entrieslaserfiche_entry_searchRun a raw Laserfiche search query, e.g. {LF:Name="*.pdf"}
search_by_namelaserfiche_entry_search_by_nameConvenience wrapper: name pattern + optional folder scope
search_naturallaserfiche_entry_search_naturalTwo-mode guided search: ask for grammar+templates, then run with auto-repair on 400
list_folderlaserfiche_folder_listList children of a folder by ID
get_entrylaserfiche_entry_getFetch metadata for one entry by ID
get_entry_by_pathlaserfiche_entry_get_by_pathResolve a full path to an entry
get_field_valueslaserfiche_field_values_getRead all template fields assigned to an entry
get_document_textlaserfiche_document_get_textServer-side extracted text (v2 only; v1 use get_document_edoc(mode="text"))
get_document_edoclaserfiche_document_get_edocInspect edoc (info), download bytes (bytes), or extract text (text)
list_repositorieslaserfiche_repository_listList repos for this account; falls back to the configured repo if endpoint disabled
list_field_definitionslaserfiche_field_definition_listEnumerate all field definitions; pass summary_only=true for a {count, names} shape
list_tag_definitionslaserfiche_tag_definition_listEnumerate tag definitions; supports summary_only
list_template_definitionslaserfiche_template_definition_listEnumerate template definitions; supports summary_only
list_link_definitionslaserfiche_link_definition_listEnumerate entry-link type definitions; supports summary_only
get_template_fieldslaserfiche_template_field_listAtomic "what fields does this template need" lookup; pass required_only=true to filter to mandatory fields. Replaces the three-call chain (list_template_definitions β†’ list_field_definitions β†’ manual filter).
get_audit_reasonslaserfiche_audit_reason_listAudit reasons available to the authenticated user (for delete/export)
get_task_statuslaserfiche_task_get_statusPoll the status of an async operation (delete, copy)
wait_for_tasklaserfiche_task_waitBlock until an async operation reaches a terminal state

Writes (registered only when LF_READ_ONLY=false)

Toolv2 namePurposeTwo-step token?
set_fieldslaserfiche_field_setOVERWRITE all field values on an entry (fields not in the body are deleted)β€”
merge_fieldslaserfiche_field_mergeGET-then-PUT helper: update specific fields, preserve the restβ€”
set_tagslaserfiche_tag_setOVERWRITE all tags on an entryβ€”
merge_tagslaserfiche_tag_mergeAdd/remove specific tags without touching othersβ€”
set_linkslaserfiche_link_setOVERWRITE all entry linksβ€”
assign_templatelaserfiche_template_assignAssign a template, optionally with initial field values (preflight-validated)β€”
remove_templatelaserfiche_template_removeClear the template assignmentβ€”
create_folderlaserfiche_folder_createCreate a child folder under a parentβ€”
import_documentlaserfiche_document_importMultipart upload from a local file path; capped by LF_IMPORT_MAX_BYTESβ€”
copy_entrylaserfiche_entry_copyAsync copy via CopyAsync; returns an operation token to pollβ€”
rename_entrylaserfiche_entry_renameRename an entry β€” preview shows old/new path, then re-call with the tokenyes
move_entrylaserfiche_entry_moveMove (optionally rename) β€” fence applies to both source AND destination pathsyes
delete_entrylaserfiche_entry_deleteDelete an entry (folders cascade); preview shows child count + batch-cap statusyes
delete_edoclaserfiche_document_edoc_deleteWipe the electronic-document content; entry + metadata remainyes
delete_pageslaserfiche_document_pages_deleteDelete specific page ranges; refuses empty page_range (would mean "delete all")yes

Tools with two-step token return a preview + HMAC-signed confirmation_token on first call. Surface the preview to the user; on go-ahead, re-call with the same arguments plus the token. Tokens are bound to (operation, entry_id, entry_name), expire after 5 minutes, and are invalidated by server restart.

Using search_natural

search_entries requires hand-written Laserfiche query syntax. If the server rejects the query the only feedback the LLM gets is a generic HTTP 400 β€” there's nothing actionable to retry against. search_natural is the LLM-friendly path:

  1. First call β€” pass the user's question and (optionally) a folder_path to scope the answer; leave lf_query unset. The tool samples up to ten entries from that folder, returns the templates and field names it found, the Laserfiche search grammar reference, and 2–3 candidate query strings the LLM can choose from or refine.
  2. Second call β€” same question, plus the chosen lf_query. On HTTP 400, the tool tries up to two automatic repairs (escape unescaped quotes inside values, then wildcard-wrap bare Name= values if fuzzy=True) before returning a structured error with all attempts visible so the LLM can author a fresh query.

The page-size cap for search_natural is the dedicated LF_MAX_PAGE_SIZE env var (default 100) β€” some self-hosted SimpleSearches implementations reject $top values above an internal limit, so this defaults lower than the list/folder cap.

get_document_edoc modes

On v1 servers the Laserfiche Text export endpoint doesn't exist, so get_document_text cannot return anything. get_document_edoc gained a mode parameter as the workaround:

ModeUse it when
infoYou only need metadata (size, content-type). Default.
bytesYou want the raw file as base64 β€” capped at LF_EDOC_MAX_BYTES (25 MB by default; override per-call with max_bytes).
textYou want extracted text. PDFs go through pypdf server-side; text/* is decoded directly; anything else returns a structured "use mode=bytes" error. OCR is not attempted.

All tool descriptions are written to read like prompts β€” they tell the model when to use the tool, valid input shapes, and what kind of follow-up is expected. See src/laserfiche_mcp/server.py.

Errors

Every tool returns a stable dict on failure instead of raising β€” so the LLM gets actionable, structured data instead of Error executing tool ....

config.json
{
  "mode": "error",
  "operation": "laserfiche_entry_delete",
  "kind": "not_found",
  "error": "not_found",
  "status_code": 404,
  "server_error_code": null,
  "server_message": null,
  "reason": "Server returned 404 β€” the entry, path, or endpoint does not exist.",
  "request_id": "9f2c…",
  "upstream_trace_id": null,
  "entry_id": 999
}

kind is one of five canonical ToolErrorKind values β€” LLMs branch on this for category-level decisions (retry vs ask user vs abort):

KindMeaning
not_foundThe named entry, path, or endpoint doesn't exist. Verify with the user.
permission_deniedCredentials, ACLs, or local fence config refused the operation.
rate_limitedThe server told the caller to slow down. Back off and retry.
invalid_inputThe request is malformed or fails a local pre-flight. Fix and re-call.
upstream_unavailableLF returned 5xx, 405, or an opaque failure. Retry once, then surface.

error is the more-specific subkind. Server-mapped subkinds:

SubkindTriggers
auth_failedHTTP 401/403, LF errorCode 9010, or LF 9528 ("LFDS unreachable" β€” usually creds too)
required_field_missingLF errorCode 9039/9066
not_foundHTTP 404
method_not_allowedHTTP 405 β€” usually an MCP routing bug
unsupported_media_typeHTTP 415 β€” usually a wire-format bug (missing Content-Type)
rate_limitedHTTP 429
server_errorHTTP 5xx or unrecognized failure

Tools also have pre-server mode: error shapes (path_not_allowed, path_traversal_blocked, exceeds_batch_cap, invalid_confirmation_token, missing_required_fields, page_range_required, invalid_page_range, invalid_name, invalid_field_name, invalid_tag_name, invalid_template_name, invalid_link_type, file_not_found, size_exceeds_cap, tool_not_allowed). list_repositories returns mode: fallback instead of erroring when the server doesn't expose the endpoint β€” see the docstring for the response shape.

See docs/error-contract.md for the full taxonomy, per-tool triggers, and the kind ↔ subkind mapping.

Safety model

Wondering what Claude actually sees and where your document content goes? See Data handling & privacy β€” it covers the data flow, what leaves the machine, and how to scope a service account so sensitive folders are never exposed. The rest of this section is about the write-mode guards.

Writes are off by default. When you enable them (LF_READ_ONLY=false), the following guards are available β€” all independent, all opt-in except as noted:

  • Path-prefix fences (LF_WRITE_PATHS_ALLOW, LF_WRITE_PATHS_DENY) β€” every write checks the entry's fullPath (or the parent's for creates) against the configured prefixes. Case-insensitive, deny wins over allow, both \ and / accepted. move_entry fences on BOTH source and destination paths so a token from an allowed source can't be replayed to land in a denied folder. Strongest single fence β€” recommended for any non-trivial deployment.
  • Tool-level allowlist (LF_WRITE_TOOLS_ALLOWED) β€” restrict which write tools register at all. Example: merge_fields,merge_tags,assign_template for a metadata-only deployment that can't create or delete anything.
  • Folder-delete batch cap (LF_DELETE_FOLDER_MAX_DESCENDANTS, default 50) β€” delete_entry on a folder with more immediate children refuses unless force_large_delete=true is passed alongside the confirmation token. The preview surfaces exceeds_batch_cap: true so the LLM can explain the size before re-calling.
  • Audit-reason requirement (LF_REQUIRE_AUDIT_REASON, default false) β€” when true, delete_entry refuses without an audit_reason_id. Use get_audit_reasons to enumerate valid IDs.
  • Required-field validation (LF_VALIDATE_REQUIRED_FIELDS, default true) β€” assign_template lists FieldDefinitions, finds isRequired: true fields, checks them against what's on the entry and what's in the caller's fields=, and returns a structured missing_required_fields error before the PUT β€” instead of the server's opaque Multistatus response. [9039].
  • Two-step confirmation tokens (always on for destructive ops) β€” rename_entry, move_entry, delete_entry, delete_edoc, delete_pages return a preview + HMAC-signed token on first call; execute on second call. Tokens bind to (operation, entry_id, entry_name), expire after 5 minutes, invalidate on server restart.

Recommended starting config for write mode

jsonc
"env": {
  "LF_READ_ONLY": "false",
  "LF_WRITE_PATHS_ALLOW": "\\Sandbox\\mcp-test",        // scope to a sandbox first
  "LF_WRITE_TOOLS_ALLOWED": "create_folder,import_document,merge_fields,merge_tags,assign_template,delete_entry",
  "LF_DELETE_FOLDER_MAX_DESCENDANTS": "10",
  "LF_REQUIRE_AUDIT_REASON": "false"                    // turn on once you have a workflow
}

Pre-create the sandbox folder by hand in the Laserfiche web client; the fence needs an existing parent to read its fullPath. Once smoke-tested, broaden the tool list β€” path scope is still the strongest fence regardless of which tools are registered.

Roadmap

  • v2.x follow-ups (deferred from the v2.0 audit) β€” write-tool collapses (field_update(mode), tag_update(add, remove), link_update(mode)), preview/execute splits of the 5 destructive tools, parameter-description polish for the JSON schema the LLM sees, structured JSON logging (LF_LOG_FORMAT=json) with a redact() helper. Working notes in docs/internal/TODO.md.
  • Server-side audit logging β€” sidecar file with rotation, capturing every write tool call with the authenticated user, target entry, and outcome.
  • Cloud β€” Laserfiche Cloud support (signin.laserfiche.com JWT-signed client_credentials flow plus the api.laserfiche.com v2-only endpoint surface).
  • v3.0 β€” Remove the verb-first deprecation aliases (get_entry, set_fields, ...). Only the laserfiche_{resource}_{verb} names remain.
  • Beyond β€” Workflow trigger tools, async /Searches flow for large result sets, server-side text extraction for Office documents.

Development

bash
uv sync --extra dev
uv run pytest                  # mocked HTTP, enforces 80% coverage baseline
uv run ruff check src tests
uv run mypy src

Tests use pytest-httpx to mock the Repository API and committed fixture PDFs to exercise the text-extraction paths β€” they don't require a real Laserfiche server.

Opt-in integration tests

bash
LF_INTEGRATION_TEST=1 uv run pytest tests/test_integration.py

Reads the same LF_* env vars the server uses at runtime. Optional overrides:

  • LF_INTEGRATION_FOLDER_PATH β€” folder used in the search_natural Mode A test (defaults to repository root)
  • LF_INTEGRATION_PDF_ENTRY_ID β€” known PDF entry; if unset, edoc tests skip
  • LF_INTEGRATION_SAFE_QUERY β€” a query expected to return results on your repo (defaults to {LF:Name="*"})

Use this before tagging a release if you have a reachable repository β€” it catches issues that mocked HTTP can't surface (server-side query syntax quirks, real PDF extraction, transport-level rejections).

Contributing

Issues and PRs welcome β€” particularly:

  • Endpoint corrections for Repository API Server builds the v1 / v2 wire format hasn't been validated against
  • Laserfiche Cloud client + JWT-signed client_credentials assertion flow
  • Server-side audit logging for write-mode deployments (sidecar file + rotation)
  • Structured JSON logging + per-tool-call redaction (LF_LOG_FORMAT=json)
  • Async /Searches flow for very large result sets

This is a community project, not affiliated with or endorsed by Laserfiche.

License

Released under the MIT License. Copyright (c) 2026 Samuel S. Hernandez.

Related MCP Servers

View all in Developer Tools View all alternatives
  • Blog logoBlog

    Search and read the Radixia blog (enterprise AI, cloud, open source) via MCP.

    πŸ’» Developer Tools0 views
    Compare vs Blog β†’
  • A
    Agent Skills Search Server

    Search and discover Agent Skills from the skills.sh registry. Powered by HAPI MCP server.

    πŸ’» Developer Tools0 views
    Compare vs Agent Skills Search Server β†’
  • Claude Task Master logoClaude Task Master

    AI-powered task management system for AI-driven development. Features PRD parsing, task expansion, multi-provider support (Claude, OpenAI, Gemini, Perplexity, xAI), and selective tool loading for optimized context usage.

    πŸ’» Developer Tools7 views
    Compare vs Claude Task Master β†’
  • A
    Ai Netcafe

    Compare LLM cost & latency on one prompt, translate PDF keeping layout, cited research, make PPTX

    πŸ’» Developer Tools0 views
    Compare vs Ai Netcafe β†’

Frequently Asked Questions about Laserfiche Mcp

Add the following block to your claude_desktop_config.json under mcpServers: "mcpServers": { "laserfiche-mcp": { "command": "npx", "args": ["-y", "laserfiche-mcp"] } }

AllMCPs Directory Badge

Full Badge Customizer

Showcase your server listing on GitHub or your project documentation. Embed this dynamic SVG badge to highlight official listing status and live engagement.

Badge Style:
Live Dynamic SVG PreviewLaserfiche Mcp AllMCPs Directory Badge
Markdown (GitHub README)
[![AllMCPs](https://allmcps.com/api/badge/laserfiche-mcp?style=directory)](https://allmcps.com/mcp/laserfiche-mcp)
HTML Embed
<a href="https://allmcps.com/mcp/laserfiche-mcp"><img src="https://allmcps.com/api/badge/laserfiche-mcp?style=directory" alt="Laserfiche Mcp on AllMCPs" /></a>

Technical Specs & Signals

CategoryπŸ’»Developer Tools
More technical detailsExpand β–Ύ
TransportSTDIO
RuntimeNode.js
0/4 checks healthy over the last 6h
Views0
Unique ViewsTotal visits recorded for this listing page on AllMCPs.
Installs0
Installs & Copy ActionsTotal times users copied install commands or configuration snippets for this server.
27Quality signal: Emerging Β· 27/100How this signal is calculated β–Ύ
Server availabilityNot measured

Not scored for repo-hosted servers β€” we can't reach the running server, only its GitHub page. Hosted MCP endpoints are health-checked live.

Verified ownership8/20
Documentation & tools11/30
Adoption & activity1/15
Community engagement0/10

A guidance signal from public completeness & health data β€” not a user rating. New listings start lower and rise as they add docs, get verified, and grow adoption. Signals we can't observe for a listing are skipped, not counted against it.

β˜… Spotlight Slot

Feature Your MCP Server

Get maximum visibility for your server across our directory, search results, and detail pages.

Spotlight Your Server

Own this project?

This directory is pre-filled from public sources. Claim via GitHub README, site badge, or DNS TXT to get the verified badge and attach your website.

Free dofollow backlink: after claiming, verify your product site and place a dofollow AllMCPs badge β€” we recheck it stays live.

Claim & get free dofollow

Share & Embed

Add our SVG badge (dark/light directory styles) or embeddable widget to your site.

Explore more

More in πŸ’» Developer Tools β†’Best MCP servers for Developers β†’Alternatives to Laserfiche Mcp β†’Install in Claude DesktopInstall in CursorInstall in VS Code