Skip to main content
Glama

easyJOB Model Context Protocol (MCP) Server

A clean, stable, and highly configurable Model Context Protocol (MCP) server for the easyJOB REST API.

This server manages dynamic OAuth authentication token fetching and caching, simplifies complex multi-query workflows (such as looking up user and job IDs to record time), and provides full read/write access to easyJOB via generic endpoints.


Safety model

This server is normally pointed at a production easyJOB instance holding real agency data, so it is deliberately narrow in what it can change:

  • The only writes it performs are time recordings: booking hours and correcting your own entries. Nothing else is created, restructured or deleted.

  • update_time_record verifies ownership against EASYJOB_USERNAME and refuses to touch anyone else's timesheet. The API token itself can write other people's records, so this guard lives in the server rather than in the caller.

  • track_time_batch defaults to a dry run: it validates and returns a preview without writing. A batch is applied all-or-nothing, so it never lands half-done.

  • Identical entries on the same day for the same job are refused as duplicates unless allow_duplicate is set explicitly.

  • The generic create_or_update_entity and delete_entity tools can touch any record, so they are hidden and blocked unless you set EASYJOB_ENABLE_GENERIC_WRITES=1. Everything above works without them.

  • Query failures are detected properly: easyJOB signals them with HTTP 200, either as an error envelope or as an empty body (see API-NOTES.md), which previously could turn a typo into a silently empty report.


Related MCP server: OAuth MCP Server

Features

Automated token management — fetches and caches the OAuth bearer token, retries transient network failures, and refreshes automatically when the API rejects a token.

Analysis (read-only)

Tool

Purpose

search_jobs

Find jobs by number, name, short name or customer; shows whether each accepts bookings

get_job_details

Complete job context in one call: header, customer, positions and hours booked per position

list_job_activities

Positions (Leistungen) with budget, booked and remaining hours — how you pick a valid activity_id

job_budget_report

Budget vs. actual per position, remaining budget, burn rate, hours per contributor

list_time_records

The individual records booked in a date range

timesheet_report

Totals grouped by day, job, activity or customer, plus working days with no bookings

team_hours_report

Hours per employee, optionally against recorded attendance (Arbeitszeit)

list_absences

Who is absent in a range, with type and days

get_user_id

Internal user ID of the configured login

query_entities

Escape hatch for arbitrary FetchsonQuery reads

Time recording (write)

Tool

Purpose

track_time

Book hours on one job, with validation and duplicate protection

track_time_batch

Validate and preview several entries, then book them after confirmation

update_time_record

Correct one of your own records (hours, description, date, times, position)

Budgets are read from each position's EstimateQuantity. Quantities in hours (Std., h) are used directly, quantities in days (Tag(e), Tage, AT) are converted at EASYJOB_HOURS_PER_DAY (default 8). Units such as pauschal, Stck. or Monat(e) are not time budgets and are reported as budgetHours: null alongside their raw quantity.


easyjob-sync — booking Super Productivity time into easyJOB

Super Productivity (MIT, macOS/Windows/Linux) serves as the local tracker. Its Local REST API only listens on 127.0.0.1, so the bridge is a CLI that runs on your own machine — the containerised MCP server cannot reach it. Both share the same easyJOB client.

One-time setup

  1. In Super Productivity: Settings → Misc → "Enable local REST API".

  2. List what the tracker knows and map each project to an easyJOB job and position:

node --env-file=.env bin/easyjob-sync.js status
node --env-file=.env bin/easyjob-sync.js projects
node --env-file=.env bin/easyjob-sync.js map <spProjectId> --job UNI_2604_131 --activity 43966
node --env-file=.env bin/easyjob-sync.js map-tag <spTagId> --activity 43969   # tag overrides the position
node --env-file=.env bin/easyjob-sync.js map <spProjectId> --ignore           # never book this project

The mapping lives in ~/.config/easyjob-sync/config.json (override with EASYJOB_SYNC_CONFIG). Super Productivity has no field for foreign keys, which is why the mapping is kept here rather than in the tracker.

Daily use

node --env-file=.env bin/easyjob-sync.js preview --from 2026-07-01 --to 2026-07-31
node --env-file=.env bin/easyjob-sync.js push    --from 2026-07-01 --to 2026-07-31 --yes

preview never writes. push refuses to write without --yes, validates every target job and position first, and aborts before writing anything if one is invalid.

How the mapping works

  • Time comes from each task's timeSpentOnDay, the finest granularity the tracker stores. Entries are grouped per day + job + position, so one day on one position becomes exactly one easyJOB record, with the task titles as description.

  • Rounding happens once per group (default 15 minutes, roundToMinutes), never per task, so several small tasks cannot inflate a day. The preview shows both the rounded and the exact figure.

  • Task-days below minMinutes (default 5) are dropped as tracking noise and listed as skipped.

  • Re-running is safe. Each record carries ExternalReference = sp:<date>:<jobId>:<activityId> plus ThirdPartyApp = super-productivity, and existing references are recognised and skipped rather than booked twice.

  • Projects without a mapping are never booked; they are reported with their hours so you can decide.

Time unit

Super Productivity does not document whether its API reports milliseconds or seconds, and being wrong by a factor of 1000 would book nonsense. The unit is therefore derived from the data (a single day cannot exceed 86400 seconds, and the app ticks in whole seconds). If the range is too small to tell, the tool stops and asks you to set timeUnit to "ms" or "s" in the config rather than guessing. The detected unit and the reason are printed on every run.


Installation & Setup

1. Install Dependencies

Run the following command inside this directory to install the @modelcontextprotocol/sdk:

npm install

2. Configuration (Environment Variables)

The server reads its configuration from environment variables. You can set these in your terminal, a .env file (if running locally/testing), or directly in your MCP client's configuration (e.g., Claude Desktop).

Environment Variable

Description

EASYJOB_API_BASE_URL

Required. The absolute URL to the easyJOB app (e.g., https://drid.because.cloud/drid/app).

EASYJOB_USERNAME

The easyJOB login name (used for password grant token lookup & user ID resolution).

EASYJOB_PASSWORD

The easyJOB password (used for password grant token lookup).

EASYJOB_CLIENT_ID

OAuth Client ID (if using client credentials flow or required for password flow).

EASYJOB_CLIENT_SECRET

OAuth Client Secret (if using client credentials flow).

EASYJOB_TOKEN_URL

Optional. Custom OAuth Token URL (defaults to ${EASYJOB_API_BASE_URL}/oauth/token).

EASYJOB_API_TOKEN

Optional. A static, long-lived bearer token (bypasses automatic auth flows).

EASYJOB_HOURS_PER_DAY

Optional. Factor for converting day-based position budgets into hours (default 8).

EASYJOB_ENABLE_GENERIC_WRITES

Optional. Set to 1 to unlock create_or_update_entity and delete_entity. Leave unset on production.


Integration in Claude Desktop

To configure the server in Claude Desktop, edit your claude_desktop_config.json configuration file:

On Linux/macOS: ~/.config/Claude/claude_desktop_config.json or ~/Library/Application Support/Claude/claude_desktop_config.json

Add the server config:

{
  "mcpServers": {
    "easyjob": {
      "command": "node",
      "args": ["/absolute/path/to/jolly-hypatia/index.js"],
      "env": {
        "EASYJOB_API_BASE_URL": "https://drid.because.cloud/drid/app",
        "EASYJOB_USERNAME": "your_username",
        "EASYJOB_PASSWORD": "your_password",
        "EASYJOB_CLIENT_ID": "optional_client_id",
        "EASYJOB_CLIENT_SECRET": "optional_client_secret"
      }
    }
  }
}

Restart Claude Desktop after editing the configuration.


Available Tools

1. get_user_id

  • Description: Get the internal easyJOB User ID for the user configured in the environment (EASYJOB_USERNAME).

  • Arguments: None. (Resolves strictly to the authenticated user context for security).

2. search_jobs

  • Description: Search for jobs by name, short name, or job number.

  • Arguments:

    • query (string, required): Wildcard search term.

3. track_time

  • Description: Log working hours on a specific job in easyJOB. Creates a TimeRecording entry strictly for the configured user timesheet.

  • Arguments:

    • job_id (integer, required): Internal ID of the Job.

    • amount (number, required): Time in hours (e.g., 1.5 or 0.25).

    • description (string, required): Work description.

    • date (string, optional): Date in YYYY-MM-DD format (defaults to today).

    • time_recording_type_id (integer, optional): Custom work type ID (from Activity/Leistung table).

4. query_entities

  • Description: Run a custom FetchsonQuery.

  • Arguments:

    • query (object, required): A FetchsonQuery JSON definition.

5. create_or_update_entity

  • Description: Create or update any entity in easyJOB.

  • Arguments:

    • entity (string, required): Entity name (e.g., 'Task').

    • data (object, required): Entity fields and values.

  • Note: Creating or updating TimeRecording entities via this tool is disabled for security. Use track_time instead.

6. delete_entity

  • Description: Delete an entity by ID.

  • Arguments:

    • entity (string, required): Entity name.

    • id (integer, required): Target entity ID.


Available Prompts

1. import-hours

  • Description: A guided prompt template to help the AI dry-run map, verify, and import a batch of working hours (timesheet) into easyJOB.

  • Arguments:

    • hoursList (string, required): The list or table of working hours to log.


Available Resources

1. easyjob://docs/skill

  • Description: The complete integration guide and safety protocols (content of SKILL.md) read dynamically from disk.

2. easyjob://user/profile

  • Description: Dynamically retrieves the profile, department details, and status of the currently authenticated user from the easyJOB database.

Install Server
F
license - not found
A
quality
B
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

View all related MCP servers

Related MCP Connectors

  • GetJobzi MCP server for job search, application tracking, and career forecasting.

  • The MCP server for Azure DevOps, bringing the power of Azure DevOps directly to your agents.

  • A MCP server built for developers enabling Git based project management with project and personal…

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/chrustek-studio/easyjob-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server