outlook-mcp
Version:
Comprehensive MCP server for Claude to access Microsoft Outlook and Teams via Microsoft Graph API - including Email, Calendar, Contacts, Tasks, Teams, Chats, and Online Meetings
210 lines (177 loc) • 5.21 kB
JavaScript
/**
* Task lists functionality
*/
const { callGraphAPI } = require('../utils/graph-api');
const { ensureAuthenticated } = require('../auth');
/**
* List task lists handler
* @param {object} args - Tool arguments
* @returns {object} - MCP response
*/
async function handleListTaskLists(args) {
try {
// Ensure user is authenticated
const accessToken = await ensureAuthenticated();
// Build the API path
const apiPath = 'me/todo/lists';
// Build query parameters
const queryParams = {
'$select': 'id,displayName,isOwner,isShared,wellknownListName',
'$orderby': 'displayName asc'
};
console.error('Fetching task lists');
// Make API call
const response = await callGraphAPI(accessToken, 'GET', apiPath, null, queryParams);
const lists = response.value || [];
return {
content: [
{
type: "text",
text: `Found ${lists.length} task lists:\n\n${lists.map(list => {
const isDefault = list.wellknownListName === 'defaultList';
const ownershipStatus = list.isOwner ? 'Owner' : 'Shared';
const sharedStatus = list.isShared ? ' (Shared)' : '';
return `📋 ${list.displayName}${isDefault ? ' (Default)' : ''}${sharedStatus}
ID: ${list.id}
Status: ${ownershipStatus}
${list.wellknownListName ? `Type: ${list.wellknownListName}` : ''}`;
}).join('\n\n')}`
}
]
};
} catch (error) {
console.error('Error in handleListTaskLists:', error);
return {
error: {
code: -32603,
message: `Failed to list task lists: ${error.message}`
}
};
}
}
/**
* Create task list handler
* @param {object} args - Tool arguments
* @returns {object} - MCP response
*/
async function handleCreateTaskList(args) {
try {
const { displayName } = args;
if (!displayName) {
return {
error: {
code: -32602,
message: "displayName is required"
}
};
}
// Ensure user is authenticated
const accessToken = await ensureAuthenticated();
// Build the list object
const listData = {
displayName
};
// Build the API path
const apiPath = 'me/todo/lists';
console.error(`Creating task list: ${displayName}`);
// Make API call
const newList = await callGraphAPI(accessToken, 'POST', apiPath, listData);
return {
content: [
{
type: "text",
text: `✅ Task list created successfully!
**Name:** ${newList.displayName}
**List ID:** ${newList.id}
**Owner:** ${newList.isOwner ? 'Yes' : 'No'}
**Shared:** ${newList.isShared ? 'Yes' : 'No'}
The task list has been created and is ready to use.`
}
]
};
} catch (error) {
console.error('Error in handleCreateTaskList:', error);
return {
error: {
code: -32603,
message: `Failed to create task list: ${error.message}`
}
};
}
}
/**
* Delete task list handler
* @param {object} args - Tool arguments
* @returns {object} - MCP response
*/
async function handleDeleteTaskList(args) {
try {
const { listId } = args;
if (!listId) {
return {
error: {
code: -32602,
message: "listId is required"
}
};
}
// Ensure user is authenticated
const accessToken = await ensureAuthenticated();
// First, get the list details for confirmation
const listPath = `me/todo/lists/${listId}`;
let listName = 'Unknown';
try {
const list = await callGraphAPI(accessToken, 'GET', listPath, null, { '$select': 'displayName,wellknownListName' });
listName = list.displayName || 'Unknown';
// Prevent deletion of default list
if (list.wellknownListName === 'defaultList') {
return {
error: {
code: -32603,
message: "Cannot delete the default task list"
}
};
}
} catch (error) {
console.error('Could not retrieve task list for deletion:', error);
}
// Build the API path
const apiPath = `me/todo/lists/${listId}`;
console.error(`Deleting task list: ${listId} (${listName})`);
// Make API call to delete the list
await callGraphAPI(accessToken, 'DELETE', apiPath);
return {
content: [
{
type: "text",
text: `✅ Task list deleted successfully!
**List:** ${listName}
**List ID:** ${listId}
The task list and all its tasks have been permanently removed.`
}
]
};
} catch (error) {
console.error('Error in handleDeleteTaskList:', error);
// Handle specific error cases
if (error.message.includes('404') || error.message.includes('Not Found')) {
return {
error: {
code: -32603,
message: `Task list not found: ${listId}`
}
};
}
return {
error: {
code: -32603,
message: `Failed to delete task list: ${error.message}`
}
};
}
}
module.exports = {
handleListTaskLists,
handleCreateTaskList,
handleDeleteTaskList
};