Mycal

io.github.Junhui20由 GitHub 账号 Junhui20 发布v0.1.4更新于 Oct 24, 2026

Malaysia public holidays, school terms, business days & a leave optimizer (13 tools).

已验证STDIO仅桌面位置与生活效率与工作流

概览

AI 生成的概览

本地 MCP 服务器,让助手查询马来西亚各州公共假期、学校学期与考试、工作日计算及请假规划。

可以做什么
  • 按年份、州属、类型或月份查询马来西亚公共假期,并判断某日期是假期、周末、工作日还是上课日
  • 查找下一个假期、日期区间内的假期、长周末以及近期数据变更
  • 计算两个日期之间的工作日数量,或在某日期上增加若干工作日
  • 通过请假优化器建议最省假的请假方案,以获得最长连续假期
  • 列出各州属并将 KL、JB 等别名解析为规范州属代码
  • 获取学校学期、学校假期以及 SPM、STPM、MUET、PT3 考试时间表
适用场景
适合处理马来西亚日期相关事务:围绕各州假期与周末安排会议或截止日期、围绕长周末规划年假,或查询学校学期与考试时间用于安排。
运行要求
通过 npx 以本地进程方式运行 npm 包 @catlabtech/mycal-mcp-server,需要 Node.js 以及访问该项目托管 API 的网络连接。未声明需要 API 密钥或环境变量。
安装前请注意
该服务器是第三方托管 API 的客户端,查询内容(日期、州属、请假方案)会发送到该外部服务。假期与学校数据来自官方宪报和政府部门,但用于正式或法律用途前应自行核实。工具均为只读查询。

安装

在 SourceWeft 中

  1. 打开 控制台中的 Mycal,将其添加到工作区。
  2. 为需要使用其工具的对话启用该服务。

Desktop only,通过 STDIO。 STDIO 服务会启动本地进程,因此需要 SourceWeft 桌面宿主。

其他 MCP 客户端

参照 仓库 中的启动说明。

README

Malaysia Calendar API

Malaysia's most complete calendar API — public holidays, school calendar, exam schedules, and MCP server for AI tools.

[npm: mycal-core] [npm: mycal-sdk] [npm: mycal-mcp-server] [License: MIT] [Deploys on Cloudflare]

Data source: Official government gazette (JPM BKPP), JAKIM, KPM, MPM. Not scraped from third-party websites.

Links

Packages

Published to npm under the @catlabtech scope:

PackagePurposeInstall
@catlabtech/mycal-coreShared types, Zod schemas, and calendar/business-day logicnpm install @catlabtech/mycal-core
@catlabtech/mycal-sdkTypeScript client SDK for the REST APInpm install @catlabtech/mycal-sdk
@catlabtech/mycal-mcp-serverMCP server exposing 13 calendar tools for AI agentsnpm install @catlabtech/mycal-mcp-server

Features

  • 50 public holidays for 2026 from official gazette (Warta Kerajaan) — federal + state-specific
  • 13 states + 3 Federal Territories with aliases (KL, JB, Penang, etc.)
  • Weekend-aware — Kedah/Kelantan/Terengganu use Fri-Sat (Kumpulan A), all others use Sat-Sun (Kumpulan B), with Johor's historical switch tracked
  • Cuti ganti (replacement holiday) auto-calculation per state weekend config
  • Business day calculator — per-state, holiday-aware
  • School calendar — terms, holidays, KPM cuti perayaan (Lampiran A/B/C)
  • Exam schedules — SPM, STPM, MUET, PT3
  • iCal subscription feeds — per-state .ics feeds
  • MCP Server for AI agents — 13 tools for Claude, ChatGPT, and other assistants
  • TypeScript SDK (@catlabtech/mycal-sdk) with typed responses
  • OpenAPI 3.1 spec + interactive docs
  • Trilingual — Bahasa Melayu, English, Chinese names (三语支持)

Quick Start

bash
# Clone and installgit clone https://github.com/Junhui20/malaysia-calendar-api.gitcd malaysia-calendar-apipnpm install
# Build shared packagespnpm --filter @catlabtech/mycal-core buildpnpm --filter @catlabtech/mycal-sdk build
# Run API locally (http://localhost:8787)cd packages/api && npx wrangler dev
# Run web site locally (http://localhost:4321)pnpm --filter @mycal/web dev
# Validate datapnpm validate
# Run testspnpm test

API Examples

Base URL: https://mycal-api.huijun00100101.workers.dev/v1

List holidays

bash
# All holidays for Selangor in 2026curl "https://mycal-api.huijun00100101.workers.dev/v1/holidays?year=2026&state=selangor"
# Islamic holidays onlycurl "https://mycal-api.huijun00100101.workers.dev/v1/holidays?year=2026&type=islamic"
# March holidays for KLcurl "https://mycal-api.huijun00100101.workers.dev/v1/holidays?year=2026&state=KL&month=3"

Check a date

bash
# Is March 21 a holiday/weekend/working day?curl "https://mycal-api.huijun00100101.workers.dev/v1/holidays/check?date=2026-03-21&state=KL"

Response:

json
{  "data": {    "date": "2026-03-21",    "dayOfWeek": "Saturday",    "isHoliday": true,    "isWeekend": true,    "isWorkingDay": false,    "isSchoolDay": false,    "holidays": [      {        "id": "2026-hari-raya-aidilfitri-1",        "name": { "ms": "Hari Raya Aidilfitri", "en": "Eid al-Fitr", "zh": "开斋节" },        "type": "islamic",        "status": "confirmed"      }    ]  }}

Business days

bash
# Count working days in March for Selangorcurl "https://mycal-api.huijun00100101.workers.dev/v1/business-days?start=2026-03-01&end=2026-03-31&state=selangor"
# Add 10 business days to a datecurl "https://mycal-api.huijun00100101.workers.dev/v1/business-days/add?date=2026-03-01&days=10&state=selangor"

School calendar

bash
# Is this a school day?curl "https://mycal-api.huijun00100101.workers.dev/v1/school/is-school-day?date=2026-03-21&state=selangor"
# School holidays for Kumpulan Bcurl "https://mycal-api.huijun00100101.workers.dev/v1/school/holidays?year=2026&group=B"
# Exam schedulecurl "https://mycal-api.huijun00100101.workers.dev/v1/school/exams?year=2026&type=spm"

Next holiday

bash
# Next holiday for Penangcurl "https://mycal-api.huijun00100101.workers.dev/v1/holidays/next?state=penang"

State resolution

bash
# Resolve aliascurl "https://mycal-api.huijun00100101.workers.dev/v1/states/resolve?q=kl"# -> { "data": { "canonical": "kuala-lumpur", "group": "B" } }

Full API Reference

EndpointDescription
GET /v1/holidaysList holidays (filter by year, state, type, status, month)
GET /v1/holidays/checkIs this date a holiday/weekend/working day/school day?
GET /v1/holidays/todayToday's holiday status
GET /v1/holidays/nextNext upcoming holiday
GET /v1/holidays/betweenHolidays in date range
GET /v1/holidays/leave-optimizerSuggest annual-leave days to spend for the longest consecutive break
GET /v1/business-daysCount business days between dates
GET /v1/business-days/addAdd N business days to a date
GET /v1/statesAll 13 states + 3 FTs with weekend config
GET /v1/states/resolveResolve alias (KL, penang, jb) to canonical code
GET /v1/school/termsSchool term dates + day counts
GET /v1/school/holidaysSchool holidays + KPM cuti perayaan
GET /v1/school/examsSPM, STPM, MUET, PT3 schedule
GET /v1/school/is-school-dayIs this a school day?
GET /v1/feed/ical/:stateiCal subscription feed
GET /v1/feed/csv/:stateCSV/spreadsheet export of holidays
GET /v1/data/*Raw, cacheable open-data snapshots — manifest, states, holidays/:year, all (no API key required)
GET /v1/prayer-times/:zoneJAKIM prayer times for a zone (MYT-formatted); GET /v1/prayer-times/zones lists the zone directory
POST /v1/keysIssue an API key (admin-gated for now; GET /v1/keys/whoami checks the caller's tier)

See the full OpenAPI 3.1 spec for request/response schemas.

SDK Usage

typescript
import { MyCalClient } from "@catlabtech/mycal-sdk";
const cal = new MyCalClient();
// Check if a date is a working dayconst result = await cal.check("2026-03-21", "selangor");console.log(result.isWorkingDay); // false
// List holidaysconst holidays = await cal.holidays({ year: 2026, state: "KL" });
// Business daysconst workDays = await cal.businessDays("2026-03-01", "2026-03-31", "selangor");console.log(workDays.businessDays); // 22
// School calendarconst terms = await cal.school.terms({ year: 2026, group: "B" });const exams = await cal.school.exams({ year: 2026, type: "spm" });const isSchool = await cal.school.isSchoolDay("2026-03-21", "selangor");

MCP Server

Connect the Malaysia Calendar API to Claude, ChatGPT, or any MCP-compatible AI assistant.

Setup with Claude Desktop / Claude Code

Add to your MCP configuration:

json
{  "mcpServers": {    "malaysia-calendar": {      "command": "npx",      "args": ["@catlabtech/mycal-mcp-server"]    }  }}

Available Tools (13)

ToolDescription
get_malaysia_holidaysGet public holidays (filter by year, state, type)
check_malaysia_holidayCheck if a date is a holiday or working day
next_malaysia_holidayFind the next upcoming holiday
malaysia_business_daysCount working days between two dates
malaysia_long_weekendsFind long weekends (3+ days)
malaysia_leave_optimizerFind the most efficient leave days to take to maximise consecutive days off
list_malaysia_statesList all states with weekend config
resolve_malaysia_stateResolve alias (KL, JB) to canonical code
malaysia_holiday_changesRecent data changes
malaysia_school_termsSchool term dates and day counts
malaysia_school_holidaysSchool holidays (cuti penggal, cuti perayaan)
malaysia_examsSPM, STPM, MUET, PT3 exam schedule
malaysia_is_school_dayCheck if a date is a school day

State Codes

CodeAliasesGroupWeekend
johorjhr, jbBSat-Sun (was Fri-Sat 2014-2024)
kedahkd, kdhAFri-Sat
kelantankel, kbAFri-Sat
terengganutrg, ktAFri-Sat
perakprk, ipohBSat-Sun
pulau-pinangpenang, pgBSat-Sun
selangorsel, sgrBSat-Sun
negeri-sembilanns, n9BSat-Sun
melakamlk, malaccaBSat-Sun
pahangphg, kuantanBSat-Sun
perlispls, kangarBSat-Sun
sabahsbh, kkBSat-Sun
sarawakswk, kuchingBSat-Sun
kuala-lumpurklBSat-Sun
wp-putrajayaputrajaya, pjyBSat-Sun
wp-labuanlabuan, lbnBSat-Sun

State aliases are case-insensitive. Use GET /v1/states/resolve?q=kl to resolve any alias to the canonical code.

Project Structure

malaysia-calendar-api/├── data/                        # JSON data files (source of truth / 数据源)│   ├── holidays/│   │   ├── 2024.json            # Holiday data per year│   │   ├── 2025.json│   │   └── 2026.json│   ├── school/│   │   ├── terms-2026.json      # School terms (Kumpulan A + B)│   │   ├── holidays-2026.json   # School holidays + KPM cuti perayaan│   │   └── exams-2026.json      # SPM, STPM, MUET, PT3 schedules│   ├── states.json              # 13 states + 3 FT, aliases, weekend history│   └── known-fixed-holidays.json├── packages/│   ├── core/                    # Shared business logic (types, schemas, utils)│   │   └── src/│   │       ├── types.ts         # Holiday, State, SchoolTerm, Exam interfaces│   │       ├── schemas.ts       # Zod validation schemas│   │       ├── filter.ts        # Query filtering logic│   │       ├── replacement.ts   # Cuti ganti calculation│   │       ├── state-resolver.ts│   │       ├── business-days.ts│   │       └── school.ts        # School term/holiday/exam logic│   ├── api/                     # Hono API on Cloudflare Workers│   ├── mcp-server/              # MCP Server (13 tools)│   ├── sdk/                     # TypeScript client SDK (@catlabtech/mycal-sdk)│   └── web/                     # Astro + Starlight — marketing site, demos, docs├── scripts/│   ├── validate-data.ts         # 5-layer data validation pipeline│   └── sync-to-kv.ts           # JSON -> Cloudflare KV denormalization├── openapi.yaml                 # OpenAPI 3.1 spec (spec-first)├── pnpm-workspace.yaml└── turbo.json

Data Sources

All data is sourced from official Malaysian government publications:

SourceDataURL
JPM BKPPFederal Gazette / Warta Kerajaan (public holidays)kabinet.gov.my
JAKIMTakwim Hijri-Miladi (Islamic calendar)e-solat.gov.my
KPMKalendar Akademik / school calendar (Lampiran A/B/C)moe.gov.my
MPMSTPM & MUET exam schedulesmpm.edu.my
State PortalsState-specific holidays (13 states)*.gov.my

Holiday data includes gazette references (e.g., P.U.(B) 305/2025) for traceability.

Deploy

Two parts deploy independently:

API → Cloudflare Workers

bash
pnpm --filter @catlabtech/mycal-core buildcd packages/api && npx wrangler deploy

Website → Cloudflare Pages

bash
pnpm --filter @catlabtech/mycal-core buildpnpm --filter @catlabtech/mycal-sdk buildpnpm --filter @mycal/web build
# Direct upload via wrangler (requires CLOUDFLARE_API_TOKEN + CLOUDFLARE_ACCOUNT_ID)cd packages/webnpx wrangler pages deploy dist --project-name=mycal-web

First-time Pages setup:

  1. Create a Pages project named mycal-web in the Cloudflare dashboard.
  2. Either connect the GitHub repo for automatic builds, or rely on the GitHub Actions workflow (.github/workflows/deploy.yml) to push via wrangler pages deploy.
  3. Required GitHub secrets: CLOUDFLARE_API_TOKEN, CLOUDFLARE_ACCOUNT_ID.

CI/CD

GitHub Actions handles:

  1. PR gate — Zod schema validation + cross-source checks on every PR
  2. Deploy — On merge to main: build and deploy API to Workers + Web to Pages in parallel
  3. Daily scrape — Government portal monitoring for updates
  4. Rukyah monitor — Islamic date confirmation tracking

Contributing

See CONTRIBUTING.md for how to:

  • Report a missing holiday or cuti peristiwa
  • Fix data errors
  • Add new features

License

MIT

来源:README.md,提交 975b7a0

工具

0
SourceWeft 尚未在沙箱中启动过该软件包,因此其工具未知。

版本历史

1
  1. v0.1.4最新Sep 16, 2026

评分

已满足适用检查项的 50%

该评分衡量此收录条目的完整程度,依据注册中心条目、端点与公开来源计算得出。它不是对服务器本身的评价,也不表示服务器安全或当前可用:可连通性是带日期的检查结果,评分也不包含安装量或用户评价。

  • 近 30 天内可连通25 分

    请保持端点能够响应 MCP 握手;SourceWeft 每 30 天探测一次。

  • 已声明认证方式10 分

    请在注册中心条目中声明凭据请求头,或保持端点能够响应探测,以便判定其认证方式。

  • 已列出工具15 分

    请让服务器在无凭据时响应 tools/list,或发布可在沙箱中无凭据启动的软件包。

  • 描述必需15 分
  • 图标10 分
  • 文档15 分
  • 许可证10 分