Skip to main content

Python client for the Kaneo project management API

Project description

kaneo

CI PyPI Python License: MIT

A Python SDK and MCP server for the Kaneo project management API.

Use it as a Python library in your scripts, or as an MCP server that plugs straight into Claude Code, Cursor, Windsurf, or any MCP-compatible AI tool.

Installation

pip install kaneo          # just the SDK
pip install kaneo[mcp]     # SDK + MCP server for AI agents

Requires Python 3.10+.


Python SDK

Quick Start

from kaneo import KaneoClient

# picks up KANEO_TOKEN from your environment
client = KaneoClient()

# or pass it directly
client = KaneoClient(token="your-api-token")

# list every project in a workspace
projects = client.projects.list(workspace_id="your-workspace-id")
for p in projects:
    print(f"{p.name} ({p.slug})")

# create a task
task = client.tasks.create(
    project_id="your-project-id",
    title="Fix the login bug",
    priority="high",
    status="to-do",
    description="Users are seeing 500 errors on /login",
)
print(f"Created: {task.id}")

# move it to in-progress
updated = client.tasks.update_status(task.id, "in-progress")
print(f"Status: {updated.status}")

Environment Variables

Variable Required Default Description
KANEO_TOKEN Yes (unless passed to constructor) Your Kaneo API token
KANEO_BASE_URL No https://cloud.kaneo.app/api API base URL

You can always override these by passing token and base_url to KaneoClient().

Self-hosted Kaneo

If you're running your own Kaneo instance, just point the client at it:

export KANEO_TOKEN=your-token
export KANEO_BASE_URL=https://kaneo.yourdomain.com/api
# or in code
client = KaneoClient(
    token="your-token",
    base_url="https://kaneo.yourdomain.com/api",
)

Projects

# list all projects in a workspace
projects = client.projects.list(workspace_id="ws-id")

# get a single project (comes with its tasks)
project = client.projects.get(project_id="proj-id", workspace_id="ws-id")
print(project.name, project.is_public, len(project.tasks))

# create one
project = client.projects.create(
    workspace_id="ws-id",
    name="My Project",
    slug="MP",
    icon="Layout",
)

# delete it
client.projects.delete(project_id="proj-id")

Tasks

# list all tasks in a project (pulled from every board column)
tasks = client.tasks.list(project_id="proj-id")

# get a single task
task = client.tasks.get(task_id="task-id")

# create a task with all the options
task = client.tasks.create(
    project_id="proj-id",
    title="Implement OAuth",
    priority="high",        # no-priority | low | medium | high | urgent
    status="to-do",         # backlog | to-do | in-progress | done | cancelled
    description="Add Google OAuth support",
    due_date="2026-12-31",  # optional
    user_id="user-id",      # optional assignee
)

# update fields individually
client.tasks.update_status(task.id, "in-progress")
client.tasks.update_priority(task.id, "urgent")
client.tasks.update_title(task.id, "Implement OAuth 2.0")
client.tasks.update_description(task.id, "Add Google and GitHub OAuth")

# delete
client.tasks.delete(task_id="task-id")

Priorities: no-priority, low, medium, high, urgent

Statuses: backlog, to-do, in-progress, done, cancelled

Pass something invalid and you'll get a ValueError before the API is even called.

Columns

# add a column to a project board
client.columns.create(
    project_id="proj-id",
    name="In Review",
    is_final=False,  # True for columns that mean "done"
)

# remove a column
client.columns.delete(column_id="col-id")

Config

# check what the server has enabled
config = client.config.get()
print(config.has_smtp)
print(config.has_github_sign_in)
print(config.disable_registration)

Error Handling

Every exception carries a status_code so you know exactly what went wrong:

from kaneo.exceptions import AuthError, NotFoundError, ValidationError, ServerError

try:
    task = client.tasks.get("nonexistent-id")
except NotFoundError as e:
    print(f"Not found (HTTP {e.status_code})")
except AuthError:
    print("Bad token — check KANEO_TOKEN")
except ValidationError as e:
    print(f"Bad request: {e}")
except ServerError:
    print("Kaneo is having a bad day — try again later")
Exception HTTP Status When
AuthError 401 Invalid or missing token
NotFoundError 404 Resource doesn't exist
ValidationError 400 Bad input or missing fields
ServerError 5xx Server-side failure
KaneoError Any other 4xx Catch-all base class

MCP Server (for AI agents)

The MCP server wraps the SDK and exposes every operation as a tool over the Model Context Protocol. Your AI agent discovers the tools automatically — no extra prompting needed.

your AI tool  <--stdin/stdout-->  kaneo-mcp  <--HTTPS-->  Kaneo API

Install

pip install kaneo[mcp]

Claude Code

Add to ~/.claude/settings.json:

{
  "mcpServers": {
    "kaneo": {
      "command": "kaneo-mcp",
      "env": {
        "KANEO_TOKEN": "your-api-token",
        "KANEO_WORKSPACE_ID": "your-workspace-id"
      }
    }
  }
}

Self-hosted? Just add KANEO_BASE_URL:

{
  "mcpServers": {
    "kaneo": {
      "command": "kaneo-mcp",
      "env": {
        "KANEO_TOKEN": "your-api-token",
        "KANEO_WORKSPACE_ID": "your-workspace-id",
        "KANEO_BASE_URL": "https://kaneo.yourdomain.com/api"
      }
    }
  }
}

Cursor

Add to .cursor/mcp.json:

{
  "mcpServers": {
    "kaneo": {
      "command": "kaneo-mcp",
      "env": {
        "KANEO_TOKEN": "your-api-token",
        "KANEO_WORKSPACE_ID": "your-workspace-id"
      }
    }
  }
}

Available Tools

Tool What it does
get_config Check server settings (SMTP, SSO, registration)
list_projects List all projects in a workspace
get_project Get a project with its tasks
create_project Create a new project
delete_project Delete a project
list_tasks List all tasks in a project
get_task Get a single task by ID
create_task Create a task with title, priority, status, description, due date, assignee
delete_task Delete a task
update_task_status Move a task: backlog / to-do / in-progress / done / cancelled
update_task_priority Reprioritize: no-priority / low / medium / high / urgent
update_task_title Rename a task
update_task_description Edit task description (markdown supported)
create_column Add a board column
delete_column Remove a board column

MCP Environment Variables

Variable Required Default Description
KANEO_TOKEN Yes API token
KANEO_BASE_URL No https://cloud.kaneo.app/api For self-hosted instances
KANEO_WORKSPACE_ID No Default workspace (saves passing it to every project tool)

Development

git clone https://github.com/drtinkerer/kaneo-python-client.git
cd kaneo-python-client
pip install -e ".[dev,mcp]"

# run tests
pytest tests/ -v

# with coverage
pytest tests/ --cov=src/kaneo --cov-report=term-missing

# lint
black --check src/ tests/
isort --check-only src/ tests/
flake8 src/ tests/ --max-line-length=88

# build
pip install build && python -m build

Project Layout

src/kaneo/
  client.py             HTTP client, auth, error handling
  exceptions.py         typed exceptions (AuthError, NotFoundError, etc.)
  models/
    project.py          Project dataclass
    task.py             Task dataclass
    config.py           Config dataclass
  resources/
    projects.py         list, get, create, delete
    tasks.py            CRUD + field-level updates
    columns.py          create, delete
    config.py           get
  mcp/
    server.py           MCP server wrapping the SDK

License

MIT

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

kaneo-0.1.0.tar.gz (12.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

kaneo-0.1.0-py3-none-any.whl (12.9 kB view details)

Uploaded Python 3

File details

Details for the file kaneo-0.1.0.tar.gz.

File metadata

  • Download URL: kaneo-0.1.0.tar.gz
  • Upload date:
  • Size: 12.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for kaneo-0.1.0.tar.gz
Algorithm Hash digest
SHA256 8eff3a5c453ad2e1bf2a4b8db626540ce76598360806d7c108c759903ef386b3
MD5 465c45b85ea5e5fe3a640620e8a17b96
BLAKE2b-256 196cf9bef1acba844f12681997aecf378abd295099471a3febb3ddcf1ab3b4bd

See more details on using hashes here.

Provenance

The following attestation bundles were made for kaneo-0.1.0.tar.gz:

Publisher: publish-pypi.yml on drtinkerer/kaneo-python-client

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file kaneo-0.1.0-py3-none-any.whl.

File metadata

  • Download URL: kaneo-0.1.0-py3-none-any.whl
  • Upload date:
  • Size: 12.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for kaneo-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 5f5aa9cf238c9fc76222f85fbdc68c532aff9ac757f7fb9619ad8778a5633387
MD5 11de53f85fc925c160e1cbef0c0f307b
BLAKE2b-256 1b54a579d1ebd2fc70f85b4d6497b18f11e3738f917fd2e43988a0877d9d7317

See more details on using hashes here.

Provenance

The following attestation bundles were made for kaneo-0.1.0-py3-none-any.whl:

Publisher: publish-pypi.yml on drtinkerer/kaneo-python-client

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page