Skip to content

Employment Hero Payroll MCP by usefulapi

by usefulapi.io · remote · no sign-in to list tools · v1.0.0 · published by io.usefulapi

Read Employment Hero Payroll pay runs, payslips, timesheets and leave; approve or decline leave.

Deletes · 2Final · 3Changes · 3

26 tools: 2 can delete or cancel things, 3 do something that can't be undone, 3 change things and 18 only read.

Scanned Oct 21, 2026

4 checks matched something in the tool definitions. No finding is not a safety guarantee. How the checks work.

claude mcp add --transport http keypay https://keypay.usefulapi.io/mcp

Findings

Matches of fixed checks, with the text they matched.

4 warn
  • The server marks "keypay_list_pay_run_summaries" read-only (readOnlyHint: true), and its own name, description or input give the class "irreversible".

    Matched text

    annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_list_pay_run_summaries" says "list": a word for reading.

    What this check looks for
  • The server marks "keypay_get_pay_run_payslips" read-only (readOnlyHint: true), and its own name, description or input give the class "irreversible".

    Matched text

    annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_get_pay_run_payslips" says "get": a word for reading.

    What this check looks for
  • The server marks "keypay_list_pay_schedules" read-only (readOnlyHint: true), and its own name, description or input give the class "write".

    Matched text

    annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_list_pay_schedules" says "list": a word for reading.

    What this check looks for
  • The server marks "keypay_list_pay_categories" read-only (readOnlyHint: true), and its own name, description or input give the class "irreversible".

    Matched text

    annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_list_pay_categories" says "list": a word for reading.

    What this check looks for

Tools

Open a tool for its reasons and full description. Descriptions are the publisher's own words, shown as they are.

26 tools

Deletes or cancels 2Claude Code: deny
  • keypay_approve_leave_requestWRITE: approves a pending leave request (the employee is notified and the leave is applied to their pay).No findings

    Why it is in this group

    • The name "keypay_approve_leave_request" says "approve": a word for a change.
    • The description says "Cannot be undone".
    • The server marks it destructive (destructiveHint: true).
    Description, as the server wrote it
    WRITE: approves a pending leave request (the employee is notified and the leave is applied to their pay). Check the request first with keypay_get_leave_request. Cannot be undone through this server. POST /business/{businessId}/employee/{employeeId}/leaverequest/{leaveRequestId}/approve.

    Annotations the server declares

    • title: Approve leave request
    • readOnlyHint: false
    • destructiveHint: true
    • idempotentHint: false
    • openWorldHint: true
  • keypay_decline_leave_requestWRITE: declines a leave request, with an optional reason the employee sees.No findings

    Why it is in this group

    • The name "keypay_decline_leave_request" says "request": a word for a change.
    • The server marks it destructive (destructiveHint: true).
    Description, as the server wrote it
    WRITE: declines a leave request, with an optional reason the employee sees. Check the request first with keypay_get_leave_request. POST /business/{businessId}/employee/{employeeId}/leaverequest/{leaveRequestId}/decline.

    Annotations the server declares

    • title: Decline leave request
    • readOnlyHint: false
    • destructiveHint: true
    • idempotentHint: false
    • openWorldHint: true
Can't be undone 3Claude Code: ask
  • keypay_get_pay_run_payslipsPay slip data for every employee in a pay run, keyed by employee: earnings lines, deductions, tax, super, leave taken and accrued, gross/net and year-to-date totals.1 finding

    Why it is in this group

    • The name "keypay_get_pay_run_payslips" says "get": a word for reading.
    • The description's first verb is "pay": a word that usually means money moves, which cannot be taken back.
    • The server marks it read-only (readOnlyHint: true), but an annotation never lowers a class.

    Findings

    • Warn

      The server marks "keypay_get_pay_run_payslips" read-only (readOnlyHint: true), and its own name, description or input give the class "irreversible".

      Matched text

      annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_get_pay_run_payslips" says "get": a word for reading.

      What this check looks for
    Description, as the server wrote it
    Pay slip data for every employee in a pay run, keyed by employee: earnings lines, deductions, tax, super, leave taken and accrued, gross/net and year-to-date totals. Large for big pay runs. Bank account numbers and tax/identity numbers are removed. GET /business/{businessId}/payrun/{payRunId}/payslips.

    Annotations the server declares

    • title: Get pay slip data
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_pay_categoriesPay categories (earnings types) of the business: id, name, rate unit, loadings, super rate, whether leave accrues.1 finding

    Why it is in this group

    • The name "keypay_list_pay_categories" says "list": a word for reading.
    • The description's first verb is "pay": a word that usually means money moves, which cannot be taken back.
    • The server marks it read-only (readOnlyHint: true), but an annotation never lowers a class.

    Findings

    • Warn

      The server marks "keypay_list_pay_categories" read-only (readOnlyHint: true), and its own name, description or input give the class "irreversible".

      Matched text

      annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_list_pay_categories" says "list": a word for reading.

      What this check looks for
    Description, as the server wrote it
    Pay categories (earnings types) of the business: id, name, rate unit, loadings, super rate, whether leave accrues. GET /business/{businessId}/paycategory (OData).

    Annotations the server declares

    • title: List pay categories
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_pay_run_summariesPay runs with their totals: total hours, gross wages and net wages, plus the usual pay run fields.1 finding

    Why it is in this group

    • The name "keypay_list_pay_run_summaries" says "list": a word for reading.
    • The description's first verb is "pay": a word that usually means money moves, which cannot be taken back.
    • The server marks it read-only (readOnlyHint: true), but an annotation never lowers a class.

    Findings

    • Warn

      The server marks "keypay_list_pay_run_summaries" read-only (readOnlyHint: true), and its own name, description or input give the class "irreversible".

      Matched text

      annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_list_pay_run_summaries" says "list": a word for reading.

      What this check looks for
    Description, as the server wrote it
    Pay runs with their totals: total hours, gross wages and net wages, plus the usual pay run fields. GET /business/{businessId}/payrun/summary (OData).

    Annotations the server declares

    • title: List pay run summaries
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
Changes things 3Claude Code: ask
  • keypay_list_pay_schedulesPay schedules of the business: id, name, frequency, last date paid, last pay run.1 finding

    Why it is in this group

    • The name "keypay_list_pay_schedules" says "list": a word for reading.
    • The description's first verb is "schedule": a word for a change.
    • The server marks it read-only (readOnlyHint: true), but an annotation never lowers a class.

    Findings

    • Warn

      The server marks "keypay_list_pay_schedules" read-only (readOnlyHint: true), and its own name, description or input give the class "write".

      Matched text

      annotations: {"readOnlyHint":true,"destructiveHint":false,"openWorldHint":true}; The name "keypay_list_pay_schedules" says "list": a word for reading.

      What this check looks for
    Description, as the server wrote it
    Pay schedules of the business: id, name, frequency, last date paid, last pay run. Bank and tax account details are removed. GET /business/{businessId}/payschedule (OData).

    Annotations the server declares

    • title: List pay schedules
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_report_gross_to_netGross-to-net report per employee: earnings by pay category, tax, deductions, super, net pay.No findings

    Why it is in this group

    • Nothing in its name or description says what it does, so it is counted as a write.
    • The server marks it read-only (readOnlyHint: true), but an annotation never lowers a class.
    Description, as the server wrote it
    Gross-to-net report per employee: earnings by pay category, tax, deductions, super, net pay. Choose a date range (from_date + to_date) or one finalised pay run (pay_run_id). The report has no paging: at most 200 rows are returned (narrow with employee_id or location_id). GET /business/{businessId}/report/grosstonet.

    Annotations the server declares

    • title: Gross to net report
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_report_leave_balancesLeave balances of all employees as at a date, per leave category.No findings

    Why it is in this group

    • Nothing in its name or description says what it does, so it is counted as a write.
    • The server marks it read-only (readOnlyHint: true), but an annotation never lowers a class.
    Description, as the server wrote it
    Leave balances of all employees as at a date, per leave category. The report has no paging: at most 200 rows are returned (narrow with location_id or leave_category_id). For one employee use keypay_get_leave_balances. GET /business/{businessId}/report/leavebalances.

    Annotations the server declares

    • title: Leave balances report
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
Only reads 18Claude Code: allow
  • keypay_get_businessOne business by id: name, legal name, contact, address, ABN/company details, leave year, standard hours, pay cycle.No findings

    Why it is in this group

    • The name "keypay_get_business" says "get": a word for reading.
    Description, as the server wrote it
    One business by id: name, legal name, contact, address, ABN/company details, leave year, standard hours, pay cycle. GET /business/{businessId}.

    Annotations the server declares

    • title: Get business
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_employeeOne employee's full record: name, contact, employment type, status, start/end date, pay schedule, primary location and pay category, rate and rate unit, hours per week, award, leav…No findings

    Why it is in this group

    • The name "keypay_get_employee" says "get": a word for reading.
    Description, as the server wrote it
    One employee's full record: name, contact, employment type, status, start/end date, pay schedule, primary location and pay category, rate and rate unit, hours per week, award, leave template, work types, tags. Tax file / national insurance / IRD / NRIC numbers, bank accounts and super member numbers are removed. GET /business/{businessId}/employee/unstructured/{employeeId}.

    Annotations the server declares

    • title: Get employee
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_leave_balancesAn employee's leave balances per leave category (accrued amount and unit), optionally as at a date.No findings

    Why it is in this group

    • The name "keypay_get_leave_balances" says "get": a word for reading.
    Description, as the server wrote it
    An employee's leave balances per leave category (accrued amount and unit), optionally as at a date. GET /business/{businessId}/employee/{employeeId}/leavebalances.

    Annotations the server declares

    • title: Get employee leave balances
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_leave_requestOne leave request: employee, category, dates, hours, status, notes.No findings

    Why it is in this group

    • The name "keypay_get_leave_request" says "get": a word for reading.
    Description, as the server wrote it
    One leave request: employee, category, dates, hours, status, notes. GET /business/{businessId}/employee/{employeeId}/leaverequest/{leaveRequestId}.

    Annotations the server declares

    • title: Get leave request
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_pay_runOne pay run by id: pay schedule, period, date paid, whether it is finalised, notation.No findings

    Why it is in this group

    • The name "keypay_get_pay_run" says "get": a word for reading.
    Description, as the server wrote it
    One pay run by id: pay schedule, period, date paid, whether it is finalised, notation. GET /business/{businessId}/payrun/{payRunId}.

    Annotations the server declares

    • title: Get pay run
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_pay_run_summaryOne pay run with its total hours, gross wages and net wages.No findings

    Why it is in this group

    • The name "keypay_get_pay_run_summary" says "get": a word for reading.
    Description, as the server wrote it
    One pay run with its total hours, gross wages and net wages. GET /business/{businessId}/payrun/{payRunId}/summary.

    Annotations the server declares

    • title: Get pay run summary
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_pay_run_totalsPer-employee totals of a pay run (gross, net, tax withheld, super and the like; the fields depend on the region).No findings

    Why it is in this group

    • The name "keypay_get_pay_run_totals" says "get": a word for reading.
    Description, as the server wrote it
    Per-employee totals of a pay run (gross, net, tax withheld, super and the like; the fields depend on the region). Bank payment details are removed. GET /business/{businessId}/payrun/{payRunId}/totals.

    Annotations the server declares

    • title: Get pay run totals
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_timesheetOne timesheet line by id.No findings

    Why it is in this group

    • The name "keypay_get_timesheet" says "get": a word for reading.
    Description, as the server wrote it
    One timesheet line by id. GET /business/{businessId}/timesheet/{timesheetLineId}.

    Annotations the server declares

    • title: Get timesheet line
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_get_userThe Employment Hero Payroll user this API key belongs to: id, email, display name and time zone.No findings

    Why it is in this group

    • The name "keypay_get_user" says "get": a word for reading.
    Description, as the server wrote it
    The Employment Hero Payroll user this API key belongs to: id, email, display name and time zone. GET /user.

    Annotations the server declares

    • title: Get current user
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_businessesList the payroll businesses this user can access: id, name, region, legal name, contact details, pay cycle, number of employees.No findings

    Why it is in this group

    • The name "keypay_list_businesses" says "list": a word for reading.
    Description, as the server wrote it
    List the payroll businesses this user can access: id, name, region, legal name, contact details, pay cycle, number of employees. Start here: most other tools need a business id. GET /business (OData).

    Annotations the server declares

    • title: List businesses
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_employeesList the business's employees with basic details: id, name, preferred name, gender, date of birth, contact details, address, start and end date, external id.No findings

    Why it is in this group

    • The name "keypay_list_employees" says "list": a word for reading.
    Description, as the server wrote it
    List the business's employees with basic details: id, name, preferred name, gender, date of birth, contact details, address, start and end date, external id. Tax file, bank and super details are not part of this list. Filter with OData, e.g. "Surname eq 'Smith'". GET /business/{businessId}/employee/details (OData).

    Annotations the server declares

    • title: List employees
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_leave_categoriesLeave categories of the business (annual, personal/sick, long service...): id, name, unit type, accrual rule.No findings

    Why it is in this group

    • The name "keypay_list_leave_categories" says "list": a word for reading.
    Description, as the server wrote it
    Leave categories of the business (annual, personal/sick, long service...): id, name, unit type, accrual rule. GET /business/{businessId}/leavecategory (OData).

    Annotations the server declares

    • title: List leave categories
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_leave_requestsList the business's leave requests: employee, leave category, from/to date, total hours, status (Approved, Pending, Rejected, Cancelled), notes.No findings

    Why it is in this group

    • The name "keypay_list_leave_requests" says "list": a word for reading.
    Description, as the server wrote it
    List the business's leave requests: employee, leave category, from/to date, total hours, status (Approved, Pending, Rejected, Cancelled), notes. Filter by status, dates, category, location or employee. GET /business/{businessId}/leaverequest.

    Annotations the server declares

    • title: List leave requests
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_locationsLocations of the business (sites, departments): id, name, parent, fully qualified name, state.No findings

    Why it is in this group

    • The name "keypay_list_locations" says "list": a word for reading.
    Description, as the server wrote it
    Locations of the business (sites, departments): id, name, parent, fully qualified name, state. GET /business/{businessId}/location (OData).

    Annotations the server declares

    • title: List locations
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_pay_run_warningsWarnings on a pay run (for example an employee paid below their award rate or with a negative net pay): type, employee and message.No findings

    Why it is in this group

    • The name "keypay_list_pay_run_warnings" says "list": a word for reading.
    Description, as the server wrote it
    Warnings on a pay run (for example an employee paid below their award rate or with a negative net pay): type, employee and message. GET /business/{businessId}/payrun/{payRunId}/warnings.

    Annotations the server declares

    • title: List pay run warnings
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_pay_runsList the business's pay runs: id, pay schedule, pay period start/end, date paid, finalised flag, payslips published, notation.No findings

    Why it is in this group

    • The name "keypay_list_pay_runs" says "list": a word for reading.
    Description, as the server wrote it
    List the business's pay runs: id, pay schedule, pay period start/end, date paid, finalised flag, payslips published, notation. Newest first with orderby "PayPeriodEnding desc". GET /business/{businessId}/payrun (OData).

    Annotations the server declares

    • title: List pay runs
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_timesheetsList the business's timesheet lines: employee, start/end time, units, work type, location, status, comments, breaks.No findings

    Why it is in this group

    • The name "keypay_list_timesheets" says "list": a word for reading.
    Description, as the server wrote it
    List the business's timesheet lines: employee, start/end time, units, work type, location, status, comments, breaks. Filter by employee or date with OData, e.g. "EmployeeId eq 123 and StartTime gt datetime'2026-04-01T00:00:00'". GET /business/{businessId}/timesheet (OData: $filter, $orderby, $top, $skip).

    Annotations the server declares

    • title: List timesheets
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true
  • keypay_list_work_typesWork types of the business: id, name, pay category, leave category, short code.No findings

    Why it is in this group

    • The name "keypay_list_work_types" says "list": a word for reading.
    Description, as the server wrote it
    Work types of the business: id, name, pay category, leave category, short code. GET /business/{businessId}/worktype (OData).

    Annotations the server declares

    • title: List work types
    • readOnlyHint: true
    • destructiveHint: false
    • openWorldHint: true

This is not a safety rating, and no finding is not a safety guarantee. The groups and findings come from fixed checks of the tool definitions the server returned on the date shown, not from its code or what it does when called. How the checks work.

Install

Pinned to version 1.0.0. Values in angle brackets are yours to fill in.

claude mcp add --transport http keypay https://keypay.usefulapi.io/mcp

Run in a terminal.

Claude Code permissions

Allow the reads, ask before a change, deny the deletes. Paste into .claude/settings.json.

.claude/settings.json
{
  "permissions": {
    "allow": [
      "mcp__keypay__keypay_get_user",
      "mcp__keypay__keypay_list_businesses",
      "mcp__keypay__keypay_get_business",
      "mcp__keypay__keypay_list_employees",
      "mcp__keypay__keypay_get_employee",
      "mcp__keypay__keypay_get_leave_balances",
      "mcp__keypay__keypay_list_pay_runs",
      "mcp__keypay__keypay_get_pay_run",
      "mcp__keypay__keypay_get_pay_run_summary",
      "mcp__keypay__keypay_get_pay_run_totals",
      "mcp__keypay__keypay_list_pay_run_warnings",
      "mcp__keypay__keypay_list_timesheets",
      "mcp__keypay__keypay_get_timesheet",
      "mcp__keypay__keypay_list_leave_requests",
      "mcp__keypay__keypay_get_leave_request",
      "mcp__keypay__keypay_list_leave_categories",
      "mcp__keypay__keypay_list_locations",
      "mcp__keypay__keypay_list_work_types"
    ],
    "ask": [
      "mcp__keypay__keypay_list_pay_run_summaries",
      "mcp__keypay__keypay_get_pay_run_payslips",
      "mcp__keypay__keypay_list_pay_schedules",
      "mcp__keypay__keypay_list_pay_categories",
      "mcp__keypay__keypay_report_gross_to_net",
      "mcp__keypay__keypay_report_leave_balances"
    ],
    "deny": [
      "mcp__keypay__keypay_approve_leave_request",
      "mcp__keypay__keypay_decline_leave_request"
    ]
  }
}

Tools that only read are allowed, tools that change things ask first, tools that delete or cancel are denied. It assumes the server is installed as keypay. Review it before you use it.