@microsoft/agents-hosting-teams
Version:
Microsoft 365 Agents SDK for JavaScript
423 lines • 23.7 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.MessageExtensions = void 0;
/**
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License.
*/
const agents_activity_1 = require("@microsoft/agents-activity");
const agents_hosting_1 = require("@microsoft/agents-hosting");
const messageExtensionsInvokeNames_1 = require("./messageExtensionsInvokeNames");
const parsers_1 = require("../../parsers");
/**
* The MessageExtensions class provides methods to handle various messaging extension scenarios in a Teams application.
* It allows developers to define handlers for different invoke activities such as queries, task fetches, and message previews.
* @template TState - The type of the TurnState used in the application.
*/
class MessageExtensions {
/**
* Creates an instance of MessageExtensions.
* @param app - The TeamsApplication instance to associate with this MessageExtensions instance.
*/
constructor(app) {
this._app = app;
}
/**
* Registers a handler for the anonymous query link invoke activity.
* @param handler - A function to handle the anonymous query link.
* @returns The TeamsApplication instance.
*/
anonymousQueryLink(handler) {
const { ANONYMOUS_QUERY_LINK_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
const selector = (context) => {
var _a;
return Promise.resolve(((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke &&
(context === null || context === void 0 ? void 0 : context.activity.name) === ANONYMOUS_QUERY_LINK_INVOKE);
};
this._app.addRoute(selector, async (context, state) => {
var _a;
const activityValueUrl = (0, parsers_1.parseValueQuery)(context.activity.value);
const result = await handler(context, state, (_a = activityValueUrl.url) !== null && _a !== void 0 ? _a : '');
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
const response = {
composeExtension: result
};
await context.sendActivity({
value: { body: response, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
return this._app;
}
/**
* Registers a handler for editing a message preview.
* @param commandId - The command ID(s) or selector(s) to match the activity.
* @param handler - A function to handle the message preview edit.
* @returns The TeamsApplication instance.
*/
messagePreviewEdit(commandId, handler) {
const { SUBMIT_ACTION_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
(Array.isArray(commandId) ? commandId : [commandId]).forEach((cid) => {
const selector = createTaskSelector(cid, SUBMIT_ACTION_INVOKE, 'edit');
this._app.addRoute(selector, async (context, state) => {
var _a, _b, _c, _d;
const activityValue = (0, parsers_1.parseValueAgentMessagePreviewAction)(context.activity.value);
if (((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) !== agents_activity_1.ActivityTypes.Invoke ||
((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.name) !== SUBMIT_ACTION_INVOKE ||
activityValue.botMessagePreviewAction !== 'edit') {
throw new Error(`Unexpected MessageExtensions.messagePreviewEdit() triggered for activity type: ${(_c = context === null || context === void 0 ? void 0 : context.activity) === null || _c === void 0 ? void 0 : _c.type}`);
}
const activityActivityPreview = (0, parsers_1.parseValueAgentActivityPreview)(context.activity.value);
const result = await handler(context, state, (_d = activityActivityPreview.botActivityPreview[0]) !== null && _d !== void 0 ? _d : {});
await this.returnSubmitActionResponse(context, result);
}, true);
});
return this._app;
}
/**
* Registers a handler for sending a message preview.
* @param commandId - The command ID(s) or selector(s) to match the activity.
* @param handler - A function to handle the message preview send.
* @returns The TeamsApplication instance.
*/
messagePreviewSend(commandId, handler) {
const { SUBMIT_ACTION_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
(Array.isArray(commandId) ? commandId : [commandId]).forEach((cid) => {
const selector = createTaskSelector(cid, SUBMIT_ACTION_INVOKE, 'send');
this._app.addRoute(selector, async (context, state) => {
var _a, _b, _c, _d;
const activityMessagePreviewAction = (0, parsers_1.parseValueAgentMessagePreviewAction)(context.activity.value);
if (((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) !== agents_activity_1.ActivityTypes.Invoke ||
((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.name) !== SUBMIT_ACTION_INVOKE ||
activityMessagePreviewAction.botMessagePreviewAction !== 'send') {
throw new Error(`Unexpected MessageExtensions.messagePreviewSend() triggered for activity type: ${(_c = context === null || context === void 0 ? void 0 : context.activity) === null || _c === void 0 ? void 0 : _c.type}`);
}
const activityActivityPreview = (0, parsers_1.parseValueAgentActivityPreview)(context.activity.value);
await handler(context, state, (_d = activityActivityPreview.botActivityPreview[0]) !== null && _d !== void 0 ? _d : {});
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
await context.sendActivity({
value: { body: {}, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
});
return this._app;
}
/**
* Registers a handler for fetching a task module.
* @param commandId - The command ID(s) or selector(s) to match the activity.
* @param handler - A function to handle the task fetch.
* @returns The TeamsApplication instance.
*/
fetchTask(commandId, handler) {
const { FETCH_TASK_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
(Array.isArray(commandId) ? commandId : [commandId]).forEach((cid) => {
const selector = createTaskSelector(cid, FETCH_TASK_INVOKE);
this._app.addRoute(selector, async (context, state) => {
var _a, _b, _c;
if (((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) !== agents_activity_1.ActivityTypes.Invoke ||
((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.name) !== FETCH_TASK_INVOKE) {
throw new Error(`Unexpected MessageExtensions.fetchTask() triggered for activity type: ${(_c = context === null || context === void 0 ? void 0 : context.activity) === null || _c === void 0 ? void 0 : _c.type}`);
}
const result = await handler(context, state);
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
let response;
if (typeof result === 'string') {
response = {
task: {
type: 'message',
value: result
}
};
}
else {
response = {
task: {
type: 'continue',
value: result
}
};
}
await context.sendActivity({
value: { body: response, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
});
return this._app;
}
/**
* Registers a handler for a query invoke activity.
* @param commandId - The command ID(s) or selector(s) to match the activity.
* @param handler - A function to handle the query.
* @returns The TeamsApplication instance.
*/
query(commandId, handler) {
const { QUERY_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
(Array.isArray(commandId) ? commandId : [commandId]).forEach((cid) => {
const selector = createTaskSelector(cid, QUERY_INVOKE);
this._app.addRoute(selector, async (context, state) => {
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k;
if (((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) !== agents_activity_1.ActivityTypes.Invoke || ((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.name) !== QUERY_INVOKE) {
throw new Error(`Unexpected MessageExtensions.query() triggered for activity type: ${(_c = context === null || context === void 0 ? void 0 : context.activity) === null || _c === void 0 ? void 0 : _c.type}`);
}
const meQuery = (_e = (_d = context === null || context === void 0 ? void 0 : context.activity) === null || _d === void 0 ? void 0 : _d.value) !== null && _e !== void 0 ? _e : {};
const query = {
count: (_g = (_f = meQuery === null || meQuery === void 0 ? void 0 : meQuery.queryOptions) === null || _f === void 0 ? void 0 : _f.count) !== null && _g !== void 0 ? _g : 25,
skip: (_j = (_h = meQuery === null || meQuery === void 0 ? void 0 : meQuery.queryOptions) === null || _h === void 0 ? void 0 : _h.skip) !== null && _j !== void 0 ? _j : 0,
parameters: {}
};
((_k = meQuery.parameters) !== null && _k !== void 0 ? _k : []).forEach((param) => {
if (param.name) {
query.parameters[param.name] = param.value;
}
});
const result = await handler(context, state, query);
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
const response = {
composeExtension: result
};
await context.sendActivity({
value: { body: response, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
});
return this._app;
}
/**
* Registers a handler for a query link invoke activity.
* @param handler - A function to handle the query link.
* @returns The TeamsApplication instance.
*/
queryLink(handler) {
const { QUERY_LINK_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
const selector = (context) => {
var _a;
return Promise.resolve(((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke && (context === null || context === void 0 ? void 0 : context.activity.name) === QUERY_LINK_INVOKE);
};
this._app.addRoute(selector, async (context, state) => {
const activityValueUrl = (0, parsers_1.parseValueQuery)(context.activity.value);
const result = await handler(context, state, activityValueUrl.url);
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
const response = {
composeExtension: result
};
await context.sendActivity({
value: { body: response, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
return this._app;
}
/**
* Registers a handler for selecting an item in a messaging extension.
* @param handler - A function to handle the item selection.
* @returns The TeamsApplication instance.
*/
selectItem(handler) {
const { SELECT_ITEM_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
const selector = (context) => {
var _a;
return Promise.resolve(((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke && (context === null || context === void 0 ? void 0 : context.activity.name) === SELECT_ITEM_INVOKE);
};
this._app.addRoute(selector, async (context, state) => {
var _a, _b;
const result = await handler(context, state, (_b = (_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.value) !== null && _b !== void 0 ? _b : {});
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
const response = {
composeExtension: result
};
await context.sendActivity({
value: { body: response, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
return this._app;
}
/**
* Registers a handler for submitting an action in a messaging extension.
* @param commandId - The command ID(s) or selector(s) to match the activity.
* @param handler - A function to handle the action submission.
* @returns The TeamsApplication instance.
*/
submitAction(commandId, handler) {
const { SUBMIT_ACTION_INVOKE } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
(Array.isArray(commandId) ? commandId : [commandId]).forEach((cid) => {
const selector = createTaskSelector(cid, SUBMIT_ACTION_INVOKE);
this._app.addRoute(selector, async (context, state) => {
var _a, _b, _c, _d, _e;
if (((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) !== agents_activity_1.ActivityTypes.Invoke ||
((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.name) !== SUBMIT_ACTION_INVOKE) {
throw new Error(`Unexpected MessageExtensions.submitAction() triggered for activity type: ${(_c = context === null || context === void 0 ? void 0 : context.activity) === null || _c === void 0 ? void 0 : _c.type}`);
}
const result = await handler(context, state, (_e = (_d = context.activity.value) === null || _d === void 0 ? void 0 : _d.data) !== null && _e !== void 0 ? _e : {});
await this.returnSubmitActionResponse(context, result);
}, true);
});
return this._app;
}
/**
* Sends a response for a submit action invoke activity.
* @param context - The TurnContext of the activity.
* @param result - The result to send in the response.
*/
async returnSubmitActionResponse(context, result) {
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
let response;
if (typeof result === 'string') {
response = {
task: {
type: 'message',
value: result
}
};
}
else if (typeof result === 'object' && result != null) {
if (result.card) {
response = {
task: {
type: 'continue',
value: result
}
};
}
else {
response = {
composeExtension: result
};
}
}
else {
response = {
composeExtension: undefined
};
}
await context.sendActivity({
value: { body: response, status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}
/**
* Registers a handler for querying a URL setting in a messaging extension.
* @param handler - A function to handle the URL setting query.
* @returns The TeamsApplication instance.
*/
queryUrlSetting(handler) {
const { QUERY_SETTING_URL } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
const selector = (context) => {
var _a;
return Promise.resolve(((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke && (context === null || context === void 0 ? void 0 : context.activity.name) === QUERY_SETTING_URL);
};
this._app.addRoute(selector, async (context, state) => {
const result = await handler(context, state);
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
const response = {
composeExtension: result
};
await context.sendActivity({
value: { status: 200, body: response },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
return this._app;
}
/**
* Registers a handler for configuring settings in a messaging extension.
* @param handler - A function to handle the settings configuration.
* @returns The TeamsApplication instance.
*/
configureSettings(handler) {
const { CONFIGURE_SETTINGS } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
const selector = (context) => {
var _a;
return Promise.resolve(((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke && (context === null || context === void 0 ? void 0 : context.activity.name) === CONFIGURE_SETTINGS);
};
this._app.addRoute(selector, async (context, state) => {
var _a;
await handler(context, state, (_a = context.activity.value) !== null && _a !== void 0 ? _a : {});
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
await context.sendActivity({
value: { status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
return this._app;
}
/**
* Registers a handler for handling button clicks in a messaging extension card.
* @param handler - A function to handle the button click.
* @returns The TeamsApplication instance.
*/
handleOnButtonClicked(handler) {
const { QUERY_CARD_BUTTON_CLICKED } = messageExtensionsInvokeNames_1.MessageExtensionsInvokeNames;
const selector = (context) => {
var _a;
return Promise.resolve(((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke && (context === null || context === void 0 ? void 0 : context.activity.name) === QUERY_CARD_BUTTON_CLICKED);
};
this._app.addRoute(selector, async (context, state) => {
var _a;
await handler(context, state, (_a = context.activity.value) !== null && _a !== void 0 ? _a : {});
if (!context.turnState.get(agents_hosting_1.INVOKE_RESPONSE_KEY)) {
await context.sendActivity({
value: { status: 200 },
type: agents_activity_1.ActivityTypes.InvokeResponse
});
}
}, true);
return this._app;
}
}
exports.MessageExtensions = MessageExtensions;
function createTaskSelector(commandId, invokeName, messagePreviewAction) {
if (typeof commandId === 'function') {
return commandId;
}
else if (commandId instanceof RegExp) {
return (context) => {
var _a, _b;
const activityValue = (0, parsers_1.parseValueCommandId)(context.activity.value);
const isInvoke = ((_a = context === null || context === void 0 ? void 0 : context.activity) === null || _a === void 0 ? void 0 : _a.type) === agents_activity_1.ActivityTypes.Invoke && ((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.name) === invokeName;
if (isInvoke &&
typeof activityValue.commandId === 'string' &&
matchesPreviewAction(context.activity, messagePreviewAction)) {
return Promise.resolve(commandId.test(activityValue.commandId));
}
else {
return Promise.resolve(false);
}
};
}
else {
return (context) => {
var _a, _b, _c;
if (!((_a = context.activity.name) === null || _a === void 0 ? void 0 : _a.includes('task'))) {
const activityValue = (0, parsers_1.parseValueCommandId)(context.activity.value);
const isInvoke = ((_b = context === null || context === void 0 ? void 0 : context.activity) === null || _b === void 0 ? void 0 : _b.type) === agents_activity_1.ActivityTypes.Invoke && ((_c = context === null || context === void 0 ? void 0 : context.activity) === null || _c === void 0 ? void 0 : _c.name) === invokeName;
return Promise.resolve(isInvoke &&
activityValue.commandId === commandId &&
matchesPreviewAction(context.activity, messagePreviewAction));
}
return Promise.resolve(false);
};
}
}
function matchesPreviewAction(activity, messagePreviewAction) {
if ('botMessagePreviewAction' in (activity === null || activity === void 0 ? void 0 : activity.value)) {
const activityValue = (0, parsers_1.parseValueAgentMessagePreviewAction)(activity.value);
return activityValue.botMessagePreviewAction === messagePreviewAction;
}
else {
return messagePreviewAction === undefined;
}
}
//# sourceMappingURL=messageExtensions.js.map