[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M69BV7ABFQ0N5VYE1R4MP20Z":3,"skill-same:01M69BV7ABFQ0N5VYE1R4MP20Z":67},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":16,"categories":17,"keywords":18,"publishedAt":37,"linkOnly":38,"markdownContent":39,"markdownBody":40,"frontMatter":41,"refName":43,"commitSha":44,"skillDirectory":45,"forksCount":46,"repositoryHtmlUrl":47,"repositoryHomepageUrl":48,"ownerHtmlUrl":49,"ownerBlogUrl":50,"ownerDescription":51,"updatedAt":52,"install":53,"resources":66},"01M69BV7ABFQ0N5VYE1R4MP20Z","add-office365",null,"Adds Office 365 Outlook by delegating to `\u002Fadd-data-source` with `api-id=shared_office365` and action mode. Use when integrating Outlook mail\u002Fcalendar.","microsoft\u002Fmanaged-apps","microsoft","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F6154722?v=4","01M698VYDXZ6JW5WH3CRV650R8","Microsoft","01M69BTSR13CCGCPK40C03N7CN",36,"MIT","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fadd-office365\u002FSKILL.md",[],[19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36],"Office365","add","add office365","mail","source","mode","action","data-source","with","id","shared","calendar","use","read","api","outlook","data","office","2026-11-10 10:12:30",false,"---\nname: add-office365\ndescription: Adds Office 365 Outlook by delegating to `\u002Fadd-data-source` with `api-id=shared_office365` and action mode. Use when integrating Outlook mail\u002Fcalendar.\nallowed-tools: Read AskUserQuestion Skill\n---\n\n**? Shared Instructions: [shared-instructions.md](..\u002F..\u002Fshared\u002Fshared-instructions.md)** — Cross-cutting concerns.\n\n# Add Office 365 Outlook (Wrapper)\n\nThis skill is a thin wrapper. Use `\u002Fadd-data-source` as the single implementation path.\n\n## Delegation contract\n\nInvoke `\u002Fadd-data-source` with:\n\n- `api-id`: `shared_office365`\n- `mode`: `action`\n\n---\n\n# Office 365 Connector: Method Selection Guide\n\nAfter the connector is added, you'll have access to `Office365OutlookService` with 20+ methods. **Use this guide to select the right method for your use case.**\n\n## Calendar Operations\n\n### For Fetching Events in a Date Range: `GetEventsCalendarViewV2`\n\n**Best for:** Meeting lists, calendar views, event queries between two dates (e.g., \"past 7 days\", \"next 30 days\").\n\n**Key Parameters:**\n- `calendarId` (string) — Always discover using `CalendarGetTables()` first\n- `startDateTimeOffset` (ISO 8601 string) — Use `.toISOString()`\n- `endDateTimeOffset` (ISO 8601 string) — Use `.toISOString()`\n- `top`, `skip` (optional) — For pagination (200-1000 range typical)\n\n**Pattern:**\n\n```typescript\nimport { Office365OutlookService } from '..\u002F..\u002Fgenerated\u002Fservices\u002FOffice365OutlookService'\n\n\u002F\u002F Step 1: Discover calendar ID (validate and prefer primary calendar)\nconst calendarsResult = await Office365OutlookService.CalendarGetTables()\nif (!calendarsResult.success) {\n  throw new Error(calendarsResult.error?.message ?? 'Failed to list calendars')\n}\n\nconst calendars = calendarsResult.data?.value ?? []\nif (calendars.length === 0) {\n  throw new Error('No calendars found in Office 365 connection')\n}\n\n\u002F\u002F Prefer primary 'calendar' (by DisplayName), fall back to first\nconst defaultCalendar =\n  calendars.find((c: any) => (c.DisplayName ?? '').toLowerCase() === 'calendar') \n  ?? calendars[0]\nconst calendarId = defaultCalendar?.Name ?? calendars[0]?.Name\n\nif (!calendarId) {\n  throw new Error('Could not determine calendar ID from response')\n}\n\n\u002F\u002F Step 2: Query events with pagination\nconst eventsResult = await Office365OutlookService.GetEventsCalendarViewV2(\n  calendarId,\n  startDate.toISOString(),\n  endDate.toISOString(),\n  undefined,        \u002F\u002F filter (optional)\n  undefined,        \u002F\u002F select (optional)\n  200,              \u002F\u002F top - results per page\n  0                 \u002F\u002F skip - pagination offset\n)\n\nif (!eventsResult.success) {\n  throw new Error(eventsResult.error?.message ?? 'Failed to fetch events')\n}\n\nconst meetings = eventsResult.data?.value ?? []\n```\n\n**Response Structure:**\n- Array of `CalendarEventClientReceiveStringEnums` (access via `.data.value`)\n- Contains: `Subject`, `Start`, `End`, `Id`, `Organizer`, `RequiredAttendees`, `OptionalAttendees`\n\n### For Immediate Upcoming Events: `OnUpcomingEventsV3`\n\n**Best for:** \"Show me my next meeting\" queries using a minutes-based time window.\n\n**Key Parameters:**\n- `table` (string) — Calendar ID\n- `minutesWindow` (number) — Time window in minutes (e.g., 60 for next hour, 1440 for next 24 hours)\n\n### For Creating Events: `V3CalendarPostItem`\n\n**Parameters:**\n- `table` — Calendar ID\n- `item` — `CalendarEventHtmlClient` object with `Subject`, `Start`, `End` (required)\n\n### For Updating Events: `CalendarPatchItem`\n\n**Parameters:**\n- `table` — Calendar ID\n- `id` — Event ID\n- `item` — Updated event properties\n\n### For Deleting Events: `CalendarDeleteItem`\n\n**Parameters:**\n- `table` — Calendar ID\n- `id` — Event ID\n\n### Discovery: `CalendarGetTables`\n\n**Purpose:** List available calendars to discover correct calendar IDs (required before using other calendar methods)\n\n## Email Operations\n\n### For Sending Emails: `SendEmailV2`\n\n**Best for:** Sending notifications, alerts, summaries.\n\n**Pattern:**\n\n```typescript\nconst result = await Office365OutlookService.SendEmailV2({\n  To: 'recipient@example.com',\n  Subject: 'Meeting Summary',\n  Body: '\u003Cp>Here is your meeting summary...\u003C\u002Fp>',\n  Importance: 'Normal'\n})\n```\n\n### For Fetching Inbox: `GetEmails`\n\n**Parameters:**\n- `folderPath` (string) — E.g., \"Inbox\", \"Drafts\"\n- `fetchOnlyUnread` (boolean) — Filter for unread emails\n- `top` (number) — Limit\n\n### For Reading Single Email: `GetEmail`\n\n**Parameters:**\n- `messageId` (string) — Email ID\n\n### For Marking as Read: `MarkAsRead`\n\n**Parameters:**\n- `messageId` (string) — Email ID\n\n### For Replying to Email: `ReplyToV3`\n\n**Parameters:**\n- `messageId` (string) — Email ID to reply to\n- `body` (string) — Reply text\n\n---\n\n## Key Patterns\n\n**? Generic connector response handling:** [shared-instructions.md](..\u002F..\u002Fshared\u002Fshared-instructions.md#connector-response-handling) — Error handling, array access (`.data.value`), empty results, and response structure patterns apply to all connectors, including Office 365.\n\n**1. Always discover calendar ID first using `CalendarGetTables()`**\n\nThis ensures you have the correct calendar ID for the user (don't hardcode \"Calendar\").\n\n**2. Use ISO date strings for date parameters**\n\nUse `.toISOString()` when passing dates to Office 365 methods.\n\n**3. Calendar ID Discovery - CRITICAL**\n\n**⚠️ NEVER use hardcoded `'Calendar'` as calendar ID.** Always discover from the user's actual calendars.\n\n```typescript\n\u002F\u002F ❌ BROKEN - Will fail for users whose primary calendar isn't named 'Calendar'\nconst calendarId = 'Calendar'\n\n\u002F\u002F ✅ CORRECT - Discover actual calendar IDs\nconst calendarsResult = await Office365OutlookService.CalendarGetTables()\nconst calendars = calendarsResult.data?.value ?? []\n\n\u002F\u002F Validate calendars exist\nif (calendars.length === 0) {\n  throw new Error('No calendars found')\n}\n\n\u002F\u002F Prefer primary calendar by DisplayName, otherwise use first\nconst primaryCalendar =\n  calendars.find((c: any) => (c.DisplayName ?? '').toLowerCase() === 'calendar')\n  ?? calendars[0]\n\n\u002F\u002F Extract the actual calendar ID from response\nconst calendarId = primaryCalendar?.Name\n\nif (!calendarId) {\n  throw new Error('Could not extract calendar ID from Office 365 response')\n}\n```\n\n**Why this matters:**\n- Users may have multiple calendars (shared calendars, project calendars, etc.)\n- The primary calendar's internal ID is not always the string `\"Calendar\"`\n- Hardcoding causes failures for any user without a calendar literally named `\"Calendar\"`\n- Must validate response contains valid data before proceeding\n","**? Shared Instructions: [shared-instructions.md](..\u002F..\u002Fshared\u002Fshared-instructions.md)** — Cross-cutting concerns.\n\n# Add Office 365 Outlook (Wrapper)\n\nThis skill is a thin wrapper. Use `\u002Fadd-data-source` as the single implementation path.\n\n## Delegation contract\n\nInvoke `\u002Fadd-data-source` with:\n\n- `api-id`: `shared_office365`\n- `mode`: `action`\n\n---\n\n# Office 365 Connector: Method Selection Guide\n\nAfter the connector is added, you'll have access to `Office365OutlookService` with 20+ methods. **Use this guide to select the right method for your use case.**\n\n## Calendar Operations\n\n### For Fetching Events in a Date Range: `GetEventsCalendarViewV2`\n\n**Best for:** Meeting lists, calendar views, event queries between two dates (e.g., \"past 7 days\", \"next 30 days\").\n\n**Key Parameters:**\n- `calendarId` (string) — Always discover using `CalendarGetTables()` first\n- `startDateTimeOffset` (ISO 8601 string) — Use `.toISOString()`\n- `endDateTimeOffset` (ISO 8601 string) — Use `.toISOString()`\n- `top`, `skip` (optional) — For pagination (200-1000 range typical)\n\n**Pattern:**\n\n```typescript\nimport { Office365OutlookService } from '..\u002F..\u002Fgenerated\u002Fservices\u002FOffice365OutlookService'\n\n\u002F\u002F Step 1: Discover calendar ID (validate and prefer primary calendar)\nconst calendarsResult = await Office365OutlookService.CalendarGetTables()\nif (!calendarsResult.success) {\n  throw new Error(calendarsResult.error?.message ?? 'Failed to list calendars')\n}\n\nconst calendars = calendarsResult.data?.value ?? []\nif (calendars.length === 0) {\n  throw new Error('No calendars found in Office 365 connection')\n}\n\n\u002F\u002F Prefer primary 'calendar' (by DisplayName), fall back to first\nconst defaultCalendar =\n  calendars.find((c: any) => (c.DisplayName ?? '').toLowerCase() === 'calendar') \n  ?? calendars[0]\nconst calendarId = defaultCalendar?.Name ?? calendars[0]?.Name\n\nif (!calendarId) {\n  throw new Error('Could not determine calendar ID from response')\n}\n\n\u002F\u002F Step 2: Query events with pagination\nconst eventsResult = await Office365OutlookService.GetEventsCalendarViewV2(\n  calendarId,\n  startDate.toISOString(),\n  endDate.toISOString(),\n  undefined,        \u002F\u002F filter (optional)\n  undefined,        \u002F\u002F select (optional)\n  200,              \u002F\u002F top - results per page\n  0                 \u002F\u002F skip - pagination offset\n)\n\nif (!eventsResult.success) {\n  throw new Error(eventsResult.error?.message ?? 'Failed to fetch events')\n}\n\nconst meetings = eventsResult.data?.value ?? []\n```\n\n**Response Structure:**\n- Array of `CalendarEventClientReceiveStringEnums` (access via `.data.value`)\n- Contains: `Subject`, `Start`, `End`, `Id`, `Organizer`, `RequiredAttendees`, `OptionalAttendees`\n\n### For Immediate Upcoming Events: `OnUpcomingEventsV3`\n\n**Best for:** \"Show me my next meeting\" queries using a minutes-based time window.\n\n**Key Parameters:**\n- `table` (string) — Calendar ID\n- `minutesWindow` (number) — Time window in minutes (e.g., 60 for next hour, 1440 for next 24 hours)\n\n### For Creating Events: `V3CalendarPostItem`\n\n**Parameters:**\n- `table` — Calendar ID\n- `item` — `CalendarEventHtmlClient` object with `Subject`, `Start`, `End` (required)\n\n### For Updating Events: `CalendarPatchItem`\n\n**Parameters:**\n- `table` — Calendar ID\n- `id` — Event ID\n- `item` — Updated event properties\n\n### For Deleting Events: `CalendarDeleteItem`\n\n**Parameters:**\n- `table` — Calendar ID\n- `id` — Event ID\n\n### Discovery: `CalendarGetTables`\n\n**Purpose:** List available calendars to discover correct calendar IDs (required before using other calendar methods)\n\n## Email Operations\n\n### For Sending Emails: `SendEmailV2`\n\n**Best for:** Sending notifications, alerts, summaries.\n\n**Pattern:**\n\n```typescript\nconst result = await Office365OutlookService.SendEmailV2({\n  To: 'recipient@example.com',\n  Subject: 'Meeting Summary',\n  Body: '\u003Cp>Here is your meeting summary...\u003C\u002Fp>',\n  Importance: 'Normal'\n})\n```\n\n### For Fetching Inbox: `GetEmails`\n\n**Parameters:**\n- `folderPath` (string) — E.g., \"Inbox\", \"Drafts\"\n- `fetchOnlyUnread` (boolean) — Filter for unread emails\n- `top` (number) — Limit\n\n### For Reading Single Email: `GetEmail`\n\n**Parameters:**\n- `messageId` (string) — Email ID\n\n### For Marking as Read: `MarkAsRead`\n\n**Parameters:**\n- `messageId` (string) — Email ID\n\n### For Replying to Email: `ReplyToV3`\n\n**Parameters:**\n- `messageId` (string) — Email ID to reply to\n- `body` (string) — Reply text\n\n---\n\n## Key Patterns\n\n**? Generic connector response handling:** [shared-instructions.md](..\u002F..\u002Fshared\u002Fshared-instructions.md#connector-response-handling) — Error handling, array access (`.data.value`), empty results, and response structure patterns apply to all connectors, including Office 365.\n\n**1. Always discover calendar ID first using `CalendarGetTables()`**\n\nThis ensures you have the correct calendar ID for the user (don't hardcode \"Calendar\").\n\n**2. Use ISO date strings for date parameters**\n\nUse `.toISOString()` when passing dates to Office 365 methods.\n\n**3. Calendar ID Discovery - CRITICAL**\n\n**⚠️ NEVER use hardcoded `'Calendar'` as calendar ID.** Always discover from the user's actual calendars.\n\n```typescript\n\u002F\u002F ❌ BROKEN - Will fail for users whose primary calendar isn't named 'Calendar'\nconst calendarId = 'Calendar'\n\n\u002F\u002F ✅ CORRECT - Discover actual calendar IDs\nconst calendarsResult = await Office365OutlookService.CalendarGetTables()\nconst calendars = calendarsResult.data?.value ?? []\n\n\u002F\u002F Validate calendars exist\nif (calendars.length === 0) {\n  throw new Error('No calendars found')\n}\n\n\u002F\u002F Prefer primary calendar by DisplayName, otherwise use first\nconst primaryCalendar =\n  calendars.find((c: any) => (c.DisplayName ?? '').toLowerCase() === 'calendar')\n  ?? calendars[0]\n\n\u002F\u002F Extract the actual calendar ID from response\nconst calendarId = primaryCalendar?.Name\n\nif (!calendarId) {\n  throw new Error('Could not extract calendar ID from Office 365 response')\n}\n```\n\n**Why this matters:**\n- Users may have multiple calendars (shared calendars, project calendars, etc.)\n- The primary calendar's internal ID is not always the string `\"Calendar\"`\n- Hardcoding causes failures for any user without a calendar literally named `\"Calendar\"`\n- Must validate response contains valid data before proceeding\n",{"name":5,"description":7,"allowed-tools":42},"Read AskUserQuestion Skill","main","5e4bd47de38c9ae0327efb7c0003d250afff31b6","plugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fadd-office365",11,"https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002FCopilot-Managed-Runtime","https:\u002F\u002Fgithub.com\u002Fmicrosoft","https:\u002F\u002Fopensource.microsoft.com","Open source projects and samples from Microsoft","2026-11-06 04:02:23",{"source":8,"skillName":5,"commands":54,"prompt":64,"zipAvailable":65},[55,58,61],{"tool":56,"command":57},"npx","npx skills add microsoft\u002Fmanaged-apps --skill add-office365",{"tool":59,"command":60},"bunx","bunx skills add microsoft\u002Fmanaged-apps --skill add-office365",{"tool":62,"command":63},"pnpm","pnpm dlx skills add microsoft\u002Fmanaged-apps --skill add-office365","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fadd-office365\u002FSKILL.md",true,[],[68,91,104,121,138,154],{"skillNo":69,"name":70,"nameZh":6,"description":71,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":72,"categories":73,"keywords":74,"publishedAt":37},"01M69BW0D2HDW3YFJJX4QEYJF2","state","Store and query a Microsoft Managed App's built-in state and file attachments with `ms project state` CLI schema commands and generated TypeScript clients. First, with the user signed in to the CLI, run `ms feature status --name state --json`; if `feature.enabled` is not `true`, recommend an alternative connector or data source.","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fstate\u002FSKILL.md",[],[70,75,76,77,78,79,80,81,82,83,84,85,32,86,87,88,89,35,23,90],"status","cli","run","typescript","app","ms","project","generated","query","Bash","Connector","write","edit","recommend","commands","feature",{"skillNo":92,"name":93,"nameZh":6,"description":94,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":95,"categories":96,"keywords":97,"publishedAt":37},"01M69BVYVZ0YYRMDY1WPVJ98VV","share","Shares (or unshares) a Microsoft App with users via `ms app share` \u002F `ms app unshare`. Use when updating app access control.","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fshare\u002FSKILL.md",[],[93,9,79,98,80,31,99,84,100,27,101,102,32,103],"Access Control","access","users","control","via","grep",{"skillNo":105,"name":106,"nameZh":6,"description":107,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":108,"categories":109,"keywords":110,"publishedAt":37},"01M69BVX6TTS1A17ZA2BDP13KP","share-link","Manages tenant-wide share links for a Microsoft App via `ms app share link create`, `ms app share link list`, and `ms app share link revoke`. Use when you want to distribute app access via a URL instead of named principals.","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fshare-link\u002FSKILL.md",[],[111,93,112,113,9,79,114,80,115,31,99,116,117,84,102,118,32,103,119,120],"share link","link","create","links","for","URL","you","distribute","wide","list",{"skillNo":122,"name":123,"nameZh":6,"description":124,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":125,"categories":126,"keywords":127,"publishedAt":37},"01M69BVVFK3WFDMJW2R5CYCRD4","play","Opens a Microsoft App in the browser via `ms app play`. Use when opening the live deployed version or a cloud-hosted preview (main branch or specific commit SHA) without starting a local dev server.","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Fplay\u002FSKILL.md",[],[123,128,129,9,130,79,131,80,132,43,31,133,84,134,135,136,137,102,32,103],"dev","commit","local dev","branch","local","version","preview","local dev server","browser","server",{"skillNo":139,"name":140,"nameZh":6,"description":141,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":142,"categories":143,"keywords":144,"publishedAt":37},"01M69BVSSESTPDA4Z5WP8WEN01","list-connectors","Lists connectors available in the active environment — including whether each is allowed or blocked by your organization's policy — plus the connection-bound data sources already wired into a Microsoft App. Use when discovering connectors and their operations before adding data sources.","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Flist-connectors\u002FSKILL.md",[],[145,146,120,9,147,79,148,149,31,84,150,151,152,32,35,153],"list connectors","connectors","policy","sources","environment","organization","operations","active","connection",{"skillNo":155,"name":156,"nameZh":6,"description":157,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":158,"categories":159,"keywords":160,"publishedAt":37},"01M69BVRDCYENNS8XXM1E5RBYQ","list-apps","Discovers managed apps in the active environment via `ms app list --json` and optional `ms app show --json`. Use when listing or locating apps.","https:\u002F\u002Fgithub.com\u002Fmicrosoft\u002Fmanaged-apps\u002Fblob\u002Fmain\u002Fplugins\u002Fmicrosoft-managed-apps\u002Fskills\u002Flist-apps\u002FSKILL.md",[],[161,162,120,79,163,80,149,31,84,102,152,164,32,103],"list apps","apps","show","json"]