2026-06-27 17:25:55 -05:00
2026-06-27 17:25:55 -05:00
2026-06-27 17:25:55 -05:00
2026-06-27 17:25:55 -05:00
2026-06-27 17:25:55 -05:00
2026-06-27 17:25:55 -05:00

openproject (Claude Code plugin)

Lets Claude interact with a self-hosted OpenProject instance over its API v3 — projects, work packages, time entries, comments, users, and metadata — through one stdlib-only Python CLI. No pip install, no external dependencies: just a Python 3 interpreter.

Built for a single-user, local-network install (server at http://10.2.0.2:5683).

Setup

  1. Get an API token: OpenProject → My Account → Access tokens → API.

  2. Put it in config.json at the plugin root:

    {
      "url": "http://10.2.0.2:5683",
      "api_key": "opapi-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
      "default_project": null
    }
    

    config.json is gitignored so the token never lands in version control. Environment variables OPENPROJECT_URL / OPENPROJECT_API_KEY override the file.

  3. Verify:

    python3 skills/openproject/scripts/op.py ping
    

What's inside

.claude-plugin/plugin.json        plugin manifest
config.json                       server URL + API token (gitignored)
commands/                         /op-ping /op-work /op-show /op-projects
                                  /op-create /op-update /op-comment /op-time
skills/openproject/
  SKILL.md                        when/how Claude uses this; full command table
  reference/filters.md            filter & query JSON syntax
  reference/api-map.md            endpoint catalog (wrapped vs. raw)
  scripts/op.py                   the CLI (argparse dispatch)
  scripts/opclient.py             HTTP client library (HAL+JSON, paging, resolvers)
  scripts/xlsx_read.py            stdlib .xlsx reader (no openpyxl) for imports

CLI quick reference

OP=skills/openproject/scripts/op.py
python3 $OP ping
python3 $OP projects --search infra
python3 $OP wp list --assignee me --status open
python3 $OP wp show 1234
python3 $OP wp create --project "Infrastructure" --type Task --subject "..." --assignee me
python3 $OP wp update 1234 --status "In progress" --done-ratio 50
python3 $OP wp comment 1234 --text "..."
python3 $OP wp relate 1234 --to 1240 --type blocks
python3 $OP time log --wp 1234 --hours 1.5 --comment "..."
python3 $OP project create --name "New Project"
python3 $OP members add --project new-project --user jdoe --role Member
python3 $OP wp delete 1234 --yes        # destructive — guarded
python3 $OP raw GET /api/v3/statuses    # escape hatch

Import a spreadsheet

Build a whole project from an .xlsx — one parent Summary task per Category, each row a child Task. Dry run by default; add --execute to write.

# Preview (writes nothing)
python3 $OP import xlsx "Plan.xlsx" --sheet "To-Do List" --project-name "My Project"
# Commit
python3 $OP import xlsx "Plan.xlsx" --sheet "To-Do List" --project-name "My Project" \
  --identifier my-project --merge-category "Display & Technology=Display & Tech" --execute

Columns are auto-detected (Task/Category/Owner/Priority/Status/Due/Notes/#). Priority H/M/L → High/Normal/Low; Status Open/In Progress/Complete → New/In progress/Closed. Owners are matched to existing users or noted in the description. Free-text dependencies are preserved in the description (link them with wp relate).

Add --json to any command for raw HAL+JSON. Names (project/type/status/priority/ assignee) resolve to ids automatically; --assignee me and --assignee none are special. Work-package updates fetch lockVersion automatically (optimistic locking).

Safety

Full CRUD is enabled, with guards: deletes require --yes, and Claude is instructed to show an item before changing it and to confirm destructive actions with you first. The token is never printed or written into OpenProject content.

S
Description
Claude Code plugin for self-hosted OpenProject — projects, work packages, time entries, and comments over API v3 via a stdlib-only Python CLI.
Readme 80 KiB
Languages
Python 100%