Skip to main content
Glama
D&D 5e Tool Server

D&D 5e Tool Server

by Terranslayer

D&D 5e Tool Server

A Python project that connects a language model to Dungeons & Dragons rules, reference data, and saved campaign notes through the Model Context Protocol (MCP).

The idea is simple: let the model narrate, and use Python for dice rolls, rule calculations, and state changes. The server exposes 27 tools. The core tools run locally without an API key.

Try it

Requires Python 3.12+ and uv.

uv sync --frozen
uv run --offline --no-sync python -B -m scripts.demo_offline
uv run --offline --no-sync pytest

The demo uses fixed dice inputs, looks up a Goblin and Fireball in the bundled reference data, then saves and reloads an encounter in a temporary folder. It prints JSON, including an attack total of 23 against AC 15, 7 damage, and an encounter budget of 300 adjusted XP. It does not require a model or change your campaign notes.

See the demo walkthrough for the inputs, expected output, and relevant source files.

Related MCP server: DM20 Protocol

What it does

Area

Examples

Dice and rules

Advantage, attacks, damage, spell save DCs

Encounters

XP budgets, difficulty, monsters by challenge rating

Reference lookup

Monsters, spells, conditions, rules, English/Chinese terms

Campaign state

Notes, initiative order, hit points, locations, quest flags

Optional search

Semantic search over module text using embeddings and LanceDB

The reference data is the 2014 rules / SRD 5.1. Search requires an embedding API key; ordinary rules and exact lookups do not.

Connect a client

Start the server from this repository's root:

uv run --no-sync python -m dnd5e_engine.server

Configure an MCP client to launch that command with this folder as its working directory. Some clients need an absolute executable path. The included .mcp.json is a configuration example; support for automatically reading it depends on the client.

Example workflows cover preparation, module parsing, and running a session. They are optional instructions to load into a compatible client, and are not automatically installed.

For semantic search, copy .env.example to .env, set OPENAI_EMBEDDING_API_KEY, and run uv run python scripts/build_index.py. Keep personal notes and credentials outside version control.

How it is organized

dnd5e_engine/       MCP wrappers, rules, lookup, retrieval, and state services
data/srd_2014/     Bundled reference data and attribution
vault/             Markdown templates and empty campaign folders
examples/workflows/ Optional client workflows
scripts/           Offline demo and reference/index loaders
tests/             Rules, lookup, state, and integration checks

The design notes explain why rules, narration, and storage are separate.

Limits and next steps

This is a local personal project. The tests cover tool behavior; they do not measure whether a model consistently selects the right tool. Campaign filtering is a search option, not a multi-user authorization system. A useful next step is a fixed set of model-only and tool-assisted scenarios, including wrong arguments and missing rules.

License

Code: MIT. SRD 5.1: © Wizards of the Coast, used under CC BY 4.0. The bundled JSON comes from 5e-bits/5e-database; see attribution.

Available Tools

27 tools
apply_hp_changeA

改某 combatant 的 HP(delta<0 伤害:临时HP先抵、夹到0;delta>0 治疗:不超 max)。 到 0 标 status=down。返回新 hp + status。

Inputs: delta (required), campaign (required), encounter (required), combatant_id (required), +1 more.

create_noteA

创建一条 vault 笔记(YAML frontmatter + 正文)。note_type 见 NOTE_TYPES (npc/location/faction/monster/character/encounter/quest/session/campaign_state/ campaign/scene/clue/map);campaign-scoped 类型需传 campaign。自动写入 id/type/name。 overwrite=True 时覆盖同名笔记(用于模组解析等可续/幂等重跑)。

Inputs: name (required), note_type (required), body, campaign, +2 more.

cr_to_xpA

挑战等级转经验值(接受 '1/4'、'5' 等)。

Inputs: cr (required).

encounter_budgetA

按队伍各角色等级求某难度的 XP 预算(2014)。

Inputs: party_levels (required), difficulty.

evaluate_encounterB

评估遭遇难度(2014:含遭遇乘数 + 队伍人数偏移)。monsters: [{'cr'|'xp', 'count'}]。

Inputs: monsters (required), party_levels (required), ruleset.

index_moduleA

把一段模组散文切块嵌入并追加进向量库(带 campaign/source/license/note_id 元数据), 使其可经 semantic_search 按战役召回。需已配置 OpenAI key。返回 {count}。

Inputs: text (required), source (required), license (required), campaign (required), +2 more.

list_notesA

列出 vault 笔记(可按 note_type / campaign 过滤),返回 {notes:[{path,name,type}]}。

Inputs: campaign, note_type.

load_play_contextA

开局/续团一次性载入某战役实例:当前状态(state.md)、风格档案、活动遭遇概要。 返回 {campaign, variant, state, style, active_encounters}。solo-dm 带团入口。

Inputs: campaign (required), variant.

load_styleA

加载某战役的风格档案(系统提示片段/语气样例/禁忌);缺失则返回中性缺省。 备团/解析/带团前调用,使产出贴合该团语气。返回 {campaign, found, frontmatter, body}。

Inputs: campaign (required).

lookup_conditionA

按名字(中/英)或 slug 查 SRD 状态,返回数据 + 中文名 + 来源引用。

Inputs: query (required).

lookup_monsterB

按名字(中/英)或 slug 查 SRD 怪物,返回数据 + 中文名 + 来源引用。

Inputs: query (required).

lookup_ruleA

关键词检索 SRD 规则条目;查不到则明确返回 found=false,绝不编造。

Inputs: query (required).

lookup_spellA

按名字(中/英)或 slug 查 SRD 法术,返回数据 + 中文名 + 来源引用。

Inputs: query (required).

manage_combat_stateA

推先攻游标(advance_turn:越界则 round+1、归零)/ 给 combatant 设清 conditions / 设 spell_slots。 返回 {round, turn_index, active_combatant, changed}。

Inputs: campaign (required), encounter (required), variant, spell_slots, +4 more.

monsters_by_crA

列出某 CR(或 CR 区间 min..max)的 SRD 怪物,供按遭遇预算选合法怪物。 接受 '1/4'、'5' 等。返回 {count, monsters:[{index,name_en,name_zh,cr}], citation}。

Inputs: min_cr (required), max_cr.

read_noteA

读取 vault 笔记,返回 {path, frontmatter, body}。

Inputs: path (required).

resolve_attackB

解析攻击骰。nat20 必中且暴击,nat1 必失。

Inputs: target_ac (required), attack_bonus (required), advantage, disadvantage.

resolve_checkB

解析属性/技能/豁免检定(d20 + 调整值 vs DC)。检定时 nat20/nat1 不自动成败。

Inputs: dc (required), modifier (required), advantage, disadvantage, +1 more.

roll_damageA

掷伤害。暴击只翻倍骰子数、调整值只加一次。

Inputs: dice_notation (required), crit, modifier.

roll_diceA

掷骰。notation 如 '2d6+3'。advantage/disadvantage 仅对单个 d20 有效。 返回统一结构:notation, rolls, natural, modifier, advantage, disadvantage, crit, total。 natural 仅在单颗骰时为该骰点数,多颗骰时为 None。

Inputs: notation (required), crit, advantage, disadvantage.

spell_attack_bonusA

法术攻击加值 = 熟练 + 属性调整。

Inputs: ability_mod (required), proficiency_bonus (required).

spell_save_dcA

法术豁免 DC = 8 + 熟练 + 属性调整。

Inputs: ability_mod (required), proficiency_bonus (required).

start_encounterA

开一场运行态遭遇(落在 variants//,不动模板)。combatants 每项含 name/side/initiative/ac/hp{value,max,temp?};自动补 id、按先攻降序、round=1/turn_index=0。

Inputs: name (required), campaign (required), combatants (required), summary, +2 more.

translate_termC

中英术语映射(en2zh / zh2en)。

Inputs: term (required), direction.

update_campaign_stateA

合并 patch 进运行态 state.md(current/clocks/quests/world_flags 等);首次自动建。 world_flags 增量合并(不清旧旗标),其它 key 整体替换。返回合并后状态。

Inputs: campaign (required), patch, variant.

validate_module_graphA

确定性校验某战役模组依赖图:孤立场景(unreachable_scene)/无来源线索(clue_without_source)/ 悬空链接(dangling_link)。返回 {campaign, counts, issues}。

Inputs: campaign (required).

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

Loading tool schema changelog…

    TDQS

    B3.2/5.0

    Scored across 27 tools

    Disambiguation4/5

    Most tools target distinct resources or actions: lookups, dice resolution, combat state, notes, and semantic search. A few potential overlaps exist (roll_dice vs resolve_attack/check, manage_combat_state vs apply_hp_change), but the descriptions provide enough clarification.

    Naming Consistency4/5

    The dominant pattern is snake_case verb_noun (lookup_monster, create_note, resolve_attack, start_encounter), which is predictable. A few exceptions like spell_save_dc and cr_to_xp break the pattern slightly, but overall naming remains readable and consistent.

    Tool Count2/5

    27 tools exceeds the 25-tool threshold and feels heavy for a single server. Several simple formula helpers like spell_save_dc, spell_attack_bonus, and cr_to_xp could reasonably be consolidated without losing capability.

    Completeness3/5

    The server covers many areas well: SRD lookups, combat resolution, encounter budgeting, campaign state, notes, and semantic indexing. However, there are visible gaps: no note delete operation, no explicit encounter end or combatant removal, and no spell listing/search beyond exact-name lookup.

    Maintenance

    ActivitySlowing
    ResponsivenessNo recent community issues

    Related MCP Connectors

    Related MCP Servers

    • A
      license
      B
      quality
      B
      maintenance
      Provides comprehensive access to Dungeons & Dragons 5th Edition content through the Open5e API. It enables users to search for game mechanics, generate character builds, and create balanced encounters via natural language.
      37
      22
      MIT
    • A
      license
      B
      quality
      D
      maintenance
      A comprehensive MCP server for managing AI-assisted Dungeons & Dragons campaigns, featuring tools for character sheets, combat tracking, and world-building. It enables players and DMs to interact with 5e game mechanics and query personal PDF rulebooks using RAG capabilities.
      64
      97
      2
      MIT
    • A
      license
      Not graded
      quality
      D
      maintenance
      Connects AI assistants to Dungeons & Dragons 5e game information via the Model Context Protocol, enabling queries for spells, monsters, equipment, and more.
      53
      MIT
    • F
      license
      A
      quality
      B
      maintenance
      Enables D&D 5e game masters and players to access complete game reference data, search spells, monsters, items, and calculate encounter difficulty, all through natural language.
      46
      8
      -