Skip to main content
Glama
Dathis

ZHAW Moodle MCP Server

by Dathis
README.md
# Moodle MCP for Swiss universities

[![PyPI](https://img.shields.io/pypi/v/swiss-moodle-mcp)](https://pypi.org/project/swiss-moodle-mcp/)
[![CI](https://github.com/Dathis/swiss-moodle-mcp/actions/workflows/ci.yml/badge.svg)](https://github.com/Dathis/swiss-moodle-mcp/actions/workflows/ci.yml)
[![License: MIT](https://img.shields.io/badge/license-MIT-blue)](https://github.com/Dathis/swiss-moodle-mcp/blob/main/LICENSE)

Use your university's Moodle from Claude: courses, materials, downloads, deadlines and
announcements. Works with ZHAW, FHNW, ETH, EPFL and the other Swiss universities below, and with any
other Moodle 4 site. You log in yourself (usually with SWITCH edu-ID) — your password is never seen
or stored, and everything stays on your computer.

> Unofficial student project, not affiliated with any university. Course material is for personal
> study only.

Formerly **zhaw-moodle-mcp**. Existing setups keep working: `uvx zhaw-moodle-mcp` now installs this
package, and your login and settings stay where they are. For the Claude Desktop extension,
install the new `swiss-moodle-<version>.mcpb` over the old one.

## Quick start

### Claude Desktop (recommended)

1. Download `swiss-moodle-<version>.mcpb` from the
   [latest release](https://github.com/Dathis/swiss-moodle-mcp/releases/latest).
2. Double-click it, or in Claude Desktop open **Settings → Extensions → Advanced settings →
   Install Extension…** and pick the file. Click **Install**.
3. Enter your university under **University**: its short name from the table below (e.g. `fhnw`)
   or the web address of your Moodle. You can also leave it empty and simply tell Claude in the
   chat which university you study at.
4. Open a new chat and ask *"Which Moodle courses do I have?"*. The first start takes a few
   seconds; then a browser opens for the login.

To switch universities later, change **University** in the extension's settings (or, if you left
it empty, ask Claude to switch). In the chat's
**+ → prompts** menu you find ready-made study sessions: study assistant, last lecture summary,
deadlines overview, what's new, exam preparation.

### Claude Code

Install [uv](https://docs.astral.sh/uv/), then (with your university's short name):

```bash
claude mcp add moodle -e MOODLE_MCP_INSTITUTION=fhnw -- uvx swiss-moodle-mcp@latest
```

### Ask Claude

*"Summarise the last lecture of Software Engineering 1"*, *"Show all my deadlines as a table"*,
*"Sync all my courses"*, *"What's new since Monday?"*. Files go to a folder named after your
university in your home directory (e.g. `~/FHNW`).

## Universities

| University | Short name | Moodle | Status |
|---|---|---|---|
| ZHAW | `zhaw` | moodle.zhaw.ch | tested |
| BFH | `bfh` | moodle.bfh.ch | not tested yet |
| EPFL | `epfl` | moodle.epfl.ch | not tested yet |
| ETH | `ethz` | moodle-app2.let.ethz.ch | not tested yet |
| FFHS | `ffhs` | moodle.ffhs.ch | not tested yet |
| FHGR | `fhgr` | moodle.fhgr.ch | not tested yet |
| FHNW | `fhnw` | moodle.fhnw.ch | not tested yet |
| HES-SO | `hes-so` | cyberlearn.hes-so.ch | not tested yet |
| HFTM | `hftm` | moodle.hftm.ch | not tested yet |
| OST | `ost` | moodle.ost.ch | not tested yet |
| PHLU | `phlu` | moodle.phlu.ch | not tested yet |
| UNIFR | `unifr` | moodle.unifr.ch | not tested yet |
| UNIGE | `unige` | moodle.unige.ch | not tested yet |
| UNIL | `unil` | moodle.unil.ch | not tested yet |
| UNINE | `unine` | moodle.unine.ch | not tested yet |
| USI | `usi` | www.icorsi.ch | not tested yet |
| SUPSI | `supsi` | www.icorsi.ch | not tested yet |

"Not tested yet": the site runs Moodle 4, but nobody has used this server there
yet. It should work - you can help by running `uvx swiss-moodle-mcp doctor`, which tries every
feature on one of your courses and prints a report without course names or personal data, and
posting it as a [compatibility report](https://github.com/Dathis/swiss-moodle-mcp/issues/new?template=university-report.yml).

**Not listed?** Use the address of your Moodle instead of a short name (copy it from the browser
while you are on your Moodle). The Moodle must be version 4.0 or newer; other learning platforms
(ILIAS, OLAT, Canvas) are not supported.

## Good to know

- **Browser:** login uses your default browser if it is Chrome, Edge, Brave or Vivaldi, otherwise
  another installed one (Firefox and Safari are not supported).
- **Updates:** the extension is updated by installing a newer `.mcpb`; with `uvx ...@latest`
  (Claude Code) updates install automatically when Claude starts.
- **Extension does not start:** it runs with [uv](https://docs.astral.sh/uv/). If Claude Desktop
  reports that `uv` is missing, install uv and restart Claude completely (also from the tray).
- Sync never deletes local files. Logging out (ask Claude, or `uvx swiss-moodle-mcp logout`) removes the
  stored session and the login browser profile; a running server notices it.
- Session and settings live in `~/.swiss-moodle-mcp` on Windows (outside AppData, so Claude from the
  Microsoft Store and the command line share them) and in the usual app folders on macOS/Linux,
  with a separate `instances/<moodle host>` folder per Moodle site. Folders named
  `zhaw-moodle-mcp` from older versions keep being used.

## Configuration

Choose your university once with `uvx swiss-moodle-mcp setup` (a list to pick from, or
`setup fhnw`, or `setup <address of your Moodle>`); `uvx swiss-moodle-mcp universities` lists the
known ones and `uvx swiss-moodle-mcp status` shows what is set. You can also just tell Claude your
university (*"I study at FHNW"*); it stores the choice for you. If you used this server before
v0.5, ZHAW stays selected.

The extension asks for the university, download folder and browser in its settings. Otherwise
run `uvx swiss-moodle-mcp config-path` to see where `config.toml` goes:

```toml
[moodle]
institution = "zhaw"  # or bfh, epfl, ethz, ffhs, fhgr, fhnw, hes-so, hftm, ost, phlu, unifr,
                      # unige, unil, unine, usi, supsi - or the address of any other Moodle
# download_directory = "~/Studium/{short}"  # default ~/ZHAW, ~/FHNW, ...

[browser]
name = "auto"  # or "chrome", "msedge", "brave", "vivaldi"
# executable_path = "C:/path/to/browser.exe"  # any other Chromium-based browser
```

## Development

```bash
uv sync
uv run pytest
uv run ruff check .
```

In this folder Claude Code picks up the server from `.mcp.json`, plus a
[study assistant](https://github.com/Dathis/swiss-moodle-mcp/blob/main/.claude/agents/study-assistant.md) subagent (copy it to `~/.claude/agents/` to use it
everywhere). Build the Claude Desktop extension with `uv run python scripts/build_extension.py` (needs Node.js).
Pushing a `vX.Y.Z` tag that matches `pyproject.toml` publishes to PyPI and attaches the `.mcpb`
to a GitHub release.

TDQS

A4.1/5.0

Scored across 16 tools

Disambiguation4/5

Most tools target a distinct Moodle action and resource type, and the descriptions make the differences clear. A few closely related pairs—such as list_resources vs get_course and get_deadlines vs list_assignments—could be confused at selection time, but the usage guidance separates them well.

Naming Consistency4/5

All tools share the moodle_ prefix and nearly all follow a verb_noun pattern such as list_courses, read_file, and get_announcements. The convention is broken slightly by moodle_auth_status and the bare verbs login/logout, though the overall pattern remains predictable.

Tool Count4/5

With 16 tools, the set is just above the typical well-scoped 3-15 range, but each tool serves a distinct workflow spanning auth, course navigation, content access, search, deadlines, announcements, and change tracking. No tool feels redundant, so the count is justified.

Completeness5/5

The server covers the full read-side workflow for a student-facing Moodle assistant: session handling, course discovery, structural overview, content extraction and download, offline syncing, search, deadlines, assignments, announcements, and recent changes. There are no obvious dead ends for the core workflows implied by the tool set.

Maintenance

ActivityMaintained
ResponsivenessNo issues