v1.0.1: Fix accept-event registration, edit-rule-sequence import, timezone config
Bug fixes (non-breaking): - Register accept-event tool in calendar module (was dead code) - Add missing callGraphAPI + ensureAuthenticated imports to rules/index.js (edit-rule-sequence would throw ReferenceError at runtime) - Make calendar event timezone configurable via MS_TIMEZONE env var (was hardcoded to UTC; default is now Eastern Standard Time) Version bump: 1.0.0 → 1.0.1 README updated: 21 tools, MS_TIMEZONE in config table, known issues pruned
This commit is contained in:
parent
a7886b5b2b
commit
ba45f57b39
7 changed files with 43 additions and 16 deletions
|
|
@ -11,3 +11,8 @@ USE_TEST_MODE=false
|
||||||
|
|
||||||
# Optional: Enable verbose debug logging
|
# Optional: Enable verbose debug logging
|
||||||
DEBUG_MODE=false
|
DEBUG_MODE=false
|
||||||
|
|
||||||
|
# Optional: Default timezone for calendar event creation (IANA tz name).
|
||||||
|
# Examples: 'America/New_York', 'Europe/London', 'Australia/Sydney'
|
||||||
|
# Defaults to Eastern Standard Time if not set.
|
||||||
|
# MS_TIMEZONE=America/New_York
|
||||||
|
|
|
||||||
18
README.md
18
README.md
|
|
@ -91,6 +91,7 @@ All configuration is via environment variables:
|
||||||
| `USE_TEST_MODE` | No | `false` | Use mock data instead of real API calls |
|
| `USE_TEST_MODE` | No | `false` | Use mock data instead of real API calls |
|
||||||
| `DEBUG_MODE` | No | `false` | Verbose logging (MSAL, API calls, working directory) |
|
| `DEBUG_MODE` | No | `false` | Verbose logging (MSAL, API calls, working directory) |
|
||||||
| `OUTLOOK_TOKEN_STORE_PATH` | No | `~/.outlook-mcp-tokens.json` | Token cache file path (override for multi-instance setups) |
|
| `OUTLOOK_TOKEN_STORE_PATH` | No | `~/.outlook-mcp-tokens.json` | Token cache file path (override for multi-instance setups) |
|
||||||
|
| `MS_TIMEZONE` | No | `Eastern Standard Time` | Default timezone for calendar event creation (IANA or Windows timezone name) |
|
||||||
|
|
||||||
## MCP Client Configuration
|
## MCP Client Configuration
|
||||||
|
|
||||||
|
|
@ -149,7 +150,7 @@ Each instance gets its own MSAL cache — no account-selection conflicts.
|
||||||
|
|
||||||
## Tools Reference
|
## Tools Reference
|
||||||
|
|
||||||
The server exposes **20 tools** across five categories.
|
The server exposes **21 tools** across five categories.
|
||||||
|
|
||||||
### Authentication (3 tools)
|
### Authentication (3 tools)
|
||||||
|
|
||||||
|
|
@ -174,12 +175,13 @@ The server exposes **20 tools** across five categories.
|
||||||
|
|
||||||
**Search strategy**: The server uses a progressive fallback approach because Graph API doesn't allow `$search` with `$orderby` or `$filter`. It tries: (1) combined KQL search with client-side boolean filtering, (2) individual term searches, (3) boolean-filter-only with `$filter` + `$orderby`, (4) fallback to recent emails.
|
**Search strategy**: The server uses a progressive fallback approach because Graph API doesn't allow `$search` with `$orderby` or `$filter`. It tries: (1) combined KQL search with client-side boolean filtering, (2) individual term searches, (3) boolean-filter-only with `$filter` + `$orderby`, (4) fallback to recent emails.
|
||||||
|
|
||||||
### Calendar (5 tools)
|
### Calendar (6 tools)
|
||||||
|
|
||||||
| Tool | Key Parameters | Description |
|
| Tool | Key Parameters | Description |
|
||||||
|---|---|---|
|
|---|---|---|
|
||||||
| `list-events` | `count`, `startDate`, `endDate` | Lists events in a date range (defaults to upcoming from now) |
|
| `list-events` | `count`, `startDate`, `endDate` | Lists events in a date range (defaults to upcoming from now) |
|
||||||
| `create-event` | `subject`, `start`, `end`, `attendees`, `body` | Creates a calendar event (times in ISO 8601, UTC timezone) |
|
| `create-event` | `subject`, `start`, `end`, `attendees`, `body` | Creates a calendar event (times in ISO 8601, timezone configurable via `MS_TIMEZONE`) |
|
||||||
|
| `accept-event` | `eventId`, `comment` | Accepts a meeting invitation |
|
||||||
| `decline-event` | `eventId`, `comment` | Declines a meeting invitation |
|
| `decline-event` | `eventId`, `comment` | Declines a meeting invitation |
|
||||||
| `cancel-event` | `eventId`, `comment` | Cancels an event you organized |
|
| `cancel-event` | `eventId`, `comment` | Cancels an event you organized |
|
||||||
| `delete-event` | `eventId` | Deletes an event from your calendar |
|
| `delete-event` | `eventId` | Deletes an event from your calendar |
|
||||||
|
|
@ -228,7 +230,7 @@ calendar/
|
||||||
decline.js # decline-event handler
|
decline.js # decline-event handler
|
||||||
cancel.js # cancel-event handler
|
cancel.js # cancel-event handler
|
||||||
delete.js # delete-event handler
|
delete.js # delete-event handler
|
||||||
accept.js # ⚠️ Dead file — not registered (see Known Issues)
|
accept.js # accept-event handler
|
||||||
|
|
||||||
folder/
|
folder/
|
||||||
index.js # Tool definitions for folder tools
|
index.js # Tool definitions for folder tools
|
||||||
|
|
@ -291,13 +293,7 @@ Launches the [MCP Inspector](https://modelcontextprotocol.io/docs/tools/inspecto
|
||||||
|
|
||||||
## Known Issues
|
## Known Issues
|
||||||
|
|
||||||
1. **`calendar/accept.js` is not registered** — The `accept-event` handler exists in `calendar/accept.js` but is not imported or registered in `calendar/index.js`. The tool is unavailable to MCP clients. To fix: import and add it to `calendarTools`.
|
1. **`authenticate` `force` parameter is a no-op** — The `force` parameter is declared in the tool schema but never read by the handler. Calling `authenticate(force=false)` will still start a fresh device code flow. Use `check-auth-status` to check auth state without side effects.
|
||||||
|
|
||||||
2. **`rules/index.js` missing `callGraphAPI` import** — `handleEditRuleSequence` calls `callGraphAPI()` but the function is never imported at the top of the file. This will throw a `ReferenceError` at runtime when `edit-rule-sequence` is invoked. To fix: add `const { callGraphAPI } = require('../utils/graph-api');` to `rules/index.js`.
|
|
||||||
|
|
||||||
3. **Calendar events are created in UTC** — `create-event` hardcodes `timeZone: "UTC"` for both start and end. Events created through the server will be in UTC regardless of the user's local timezone.
|
|
||||||
|
|
||||||
4. **`authenticate` `force` parameter is a no-op** — The `force` parameter is declared in the tool schema but never read by the handler. Calling `authenticate(force=false)` will still start a fresh device code flow. Use `check-auth-status` to check auth state without side effects.
|
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@
|
||||||
*/
|
*/
|
||||||
const { callGraphAPI } = require('../utils/graph-api');
|
const { callGraphAPI } = require('../utils/graph-api');
|
||||||
const { ensureAuthenticated } = require('../auth');
|
const { ensureAuthenticated } = require('../auth');
|
||||||
|
const config = require('../config');
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create event handler
|
* Create event handler
|
||||||
|
|
@ -31,8 +32,8 @@ async function handleCreateEvent(args) {
|
||||||
// Request body
|
// Request body
|
||||||
const bodyContent = {
|
const bodyContent = {
|
||||||
subject,
|
subject,
|
||||||
start: { dateTime: start, timeZone: "UTC" },
|
start: { dateTime: start, timeZone: config.DEFAULT_TIMEZONE },
|
||||||
end: { dateTime: end, timeZone: "UTC" },
|
end: { dateTime: end, timeZone: config.DEFAULT_TIMEZONE },
|
||||||
attendees: attendees?.map(email => ({ emailAddress: { address: email }, type: "required" })),
|
attendees: attendees?.map(email => ({ emailAddress: { address: email }, type: "required" })),
|
||||||
body: { contentType: "HTML", content: body || "" }
|
body: { contentType: "HTML", content: body || "" }
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@
|
||||||
*/
|
*/
|
||||||
const handleListEvents = require('./list');
|
const handleListEvents = require('./list');
|
||||||
const handleDeclineEvent = require('./decline');
|
const handleDeclineEvent = require('./decline');
|
||||||
|
const handleAcceptEvent = require('./accept');
|
||||||
const handleCreateEvent = require('./create');
|
const handleCreateEvent = require('./create');
|
||||||
const handleCancelEvent = require('./cancel');
|
const handleCancelEvent = require('./cancel');
|
||||||
const handleDeleteEvent = require('./delete');
|
const handleDeleteEvent = require('./delete');
|
||||||
|
|
@ -32,6 +33,25 @@ const calendarTools = [
|
||||||
},
|
},
|
||||||
handler: handleListEvents
|
handler: handleListEvents
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "accept-event",
|
||||||
|
description: "Accepts a calendar event",
|
||||||
|
inputSchema: {
|
||||||
|
type: "object",
|
||||||
|
properties: {
|
||||||
|
eventId: {
|
||||||
|
type: "string",
|
||||||
|
description: "The ID of the event to accept"
|
||||||
|
},
|
||||||
|
comment: {
|
||||||
|
type: "string",
|
||||||
|
description: "Optional comment for accepting the event"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
required: ["eventId"]
|
||||||
|
},
|
||||||
|
handler: handleAcceptEvent
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "decline-event",
|
name: "decline-event",
|
||||||
description: "Declines a calendar event",
|
description: "Declines a calendar event",
|
||||||
|
|
@ -124,6 +144,7 @@ const calendarTools = [
|
||||||
module.exports = {
|
module.exports = {
|
||||||
calendarTools,
|
calendarTools,
|
||||||
handleListEvents,
|
handleListEvents,
|
||||||
|
handleAcceptEvent,
|
||||||
handleDeclineEvent,
|
handleDeclineEvent,
|
||||||
handleCreateEvent,
|
handleCreateEvent,
|
||||||
handleCancelEvent,
|
handleCancelEvent,
|
||||||
|
|
|
||||||
|
|
@ -10,7 +10,7 @@ const homeDir = process.env.HOME || process.env.USERPROFILE || os.homedir() || '
|
||||||
module.exports = {
|
module.exports = {
|
||||||
// Server information
|
// Server information
|
||||||
SERVER_NAME: "outlook-assistant-main",
|
SERVER_NAME: "outlook-assistant-main",
|
||||||
SERVER_VERSION: "1.0.0",
|
SERVER_VERSION: "1.0.1",
|
||||||
|
|
||||||
// Test mode setting
|
// Test mode setting
|
||||||
USE_TEST_MODE: process.env.USE_TEST_MODE === 'true',
|
USE_TEST_MODE: process.env.USE_TEST_MODE === 'true',
|
||||||
|
|
@ -43,7 +43,9 @@ module.exports = {
|
||||||
// Calendar constants
|
// Calendar constants
|
||||||
CALENDAR_SELECT_FIELDS: 'id,subject,bodyPreview,start,end,location,organizer,attendees,isAllDay,isCancelled',
|
CALENDAR_SELECT_FIELDS: 'id,subject,bodyPreview,start,end,location,organizer,attendees,isAllDay,isCancelled',
|
||||||
|
|
||||||
// Pagination
|
// Default timezone for calendar event creation (IANA tz name, e.g. 'America/New_York').
|
||||||
|
// Override via MS_TIMEZONE env var. Graph API accepts IANA timezone identifiers.
|
||||||
|
DEFAULT_TIMEZONE: process.env.MS_TIMEZONE || 'Eastern Standard Time',
|
||||||
DEFAULT_PAGE_SIZE: 25,
|
DEFAULT_PAGE_SIZE: 25,
|
||||||
MAX_RESULT_COUNT: 500
|
MAX_RESULT_COUNT: 500
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
{
|
{
|
||||||
"name": "outlook-mcp",
|
"name": "outlook-mcp",
|
||||||
"version": "1.0.0",
|
"version": "1.0.1",
|
||||||
"description": "MCP server for Claude to access Outlook data via Microsoft Graph API",
|
"description": "MCP server for Claude to access Outlook data via Microsoft Graph API",
|
||||||
"main": "index.js",
|
"main": "index.js",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,8 @@
|
||||||
*/
|
*/
|
||||||
const handleListRules = require('./list');
|
const handleListRules = require('./list');
|
||||||
const handleCreateRule = require('./create');
|
const handleCreateRule = require('./create');
|
||||||
|
const { callGraphAPI } = require('../utils/graph-api');
|
||||||
|
const { ensureAuthenticated } = require('../auth');
|
||||||
|
|
||||||
// Import getInboxRules for the edit sequence tool
|
// Import getInboxRules for the edit sequence tool
|
||||||
const { getInboxRules } = require('./list');
|
const { getInboxRules } = require('./list');
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue