@microsoft/agents-hosting 0.1.49 → 0.2.7-gd7a3e9ef95

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (137) hide show
  1. package/dist/src/activityWireCompat.d.ts +19 -0
  2. package/dist/src/activityWireCompat.js +49 -0
  3. package/dist/src/activityWireCompat.js.map +1 -0
  4. package/dist/src/agent-client/agentClient.d.ts +8 -2
  5. package/dist/src/agent-client/agentClient.js +7 -10
  6. package/dist/src/agent-client/agentClient.js.map +1 -1
  7. package/dist/src/agent-client/{expressApi.d.ts → agentResponseHandler.d.ts} +2 -1
  8. package/dist/src/agent-client/{expressApi.js → agentResponseHandler.js} +16 -12
  9. package/dist/src/agent-client/agentResponseHandler.js.map +1 -0
  10. package/dist/src/agent-client/index.d.ts +1 -1
  11. package/dist/src/agent-client/index.js +1 -1
  12. package/dist/src/agent-client/index.js.map +1 -1
  13. package/dist/src/app/agentApplication.d.ts +9 -8
  14. package/dist/src/app/agentApplication.js +17 -8
  15. package/dist/src/app/agentApplication.js.map +1 -1
  16. package/dist/src/app/{applicationBuilder.d.ts → agentApplicationBuilder.d.ts} +6 -6
  17. package/dist/src/app/{applicationBuilder.js → agentApplicationBuilder.js} +4 -4
  18. package/dist/src/app/agentApplicationBuilder.js.map +1 -0
  19. package/dist/src/app/{applicationOptions.d.ts → agentApplicationOptions.d.ts} +3 -3
  20. package/dist/src/app/{applicationOptions.js → agentApplicationOptions.js} +1 -1
  21. package/dist/src/app/agentApplicationOptions.js.map +1 -0
  22. package/dist/src/app/index.d.ts +4 -3
  23. package/dist/src/app/index.js +4 -3
  24. package/dist/src/app/index.js.map +1 -1
  25. package/dist/src/app/oauth/userIdentity.d.ts +43 -0
  26. package/dist/src/app/oauth/userIdentity.js +54 -0
  27. package/dist/src/app/oauth/userIdentity.js.map +1 -0
  28. package/dist/src/app/turnState.d.ts +1 -1
  29. package/dist/src/app/turnState.js +2 -2
  30. package/dist/src/app/turnState.js.map +1 -1
  31. package/dist/src/app/turnStateProperty.d.ts +40 -0
  32. package/dist/src/app/turnStateProperty.js +57 -0
  33. package/dist/src/app/turnStateProperty.js.map +1 -0
  34. package/dist/src/auth/authConfiguration.d.ts +21 -2
  35. package/dist/src/auth/authConfiguration.js +23 -4
  36. package/dist/src/auth/authConfiguration.js.map +1 -1
  37. package/dist/src/auth/jwt-middleware.js +2 -1
  38. package/dist/src/auth/jwt-middleware.js.map +1 -1
  39. package/dist/src/auth/msalTokenProvider.js +1 -1
  40. package/dist/src/auth/msalTokenProvider.js.map +1 -1
  41. package/dist/src/cards/cardFactory.d.ts +8 -0
  42. package/dist/src/cards/cardFactory.js +22 -1
  43. package/dist/src/cards/cardFactory.js.map +1 -1
  44. package/dist/src/cloudAdapter.d.ts +1 -2
  45. package/dist/src/cloudAdapter.js +7 -2
  46. package/dist/src/cloudAdapter.js.map +1 -1
  47. package/dist/src/connector-client/connectorClient.d.ts +3 -2
  48. package/dist/src/connector-client/connectorClient.js +15 -3
  49. package/dist/src/connector-client/connectorClient.js.map +1 -1
  50. package/dist/src/connector-client/index.d.ts +0 -1
  51. package/dist/src/connector-client/index.js +0 -1
  52. package/dist/src/connector-client/index.js.map +1 -1
  53. package/dist/src/getProductInfo.d.ts +1 -0
  54. package/dist/src/getProductInfo.js +11 -0
  55. package/dist/src/getProductInfo.js.map +1 -0
  56. package/dist/src/index.d.ts +2 -1
  57. package/dist/src/index.js +2 -1
  58. package/dist/src/index.js.map +1 -1
  59. package/dist/src/oauth/index.d.ts +3 -4
  60. package/dist/src/oauth/index.js +3 -4
  61. package/dist/src/oauth/index.js.map +1 -1
  62. package/dist/src/oauth/{oauthCard.d.ts → oAuthCard.d.ts} +1 -2
  63. package/dist/src/oauth/{oauthCard.js → oAuthCard.js} +1 -1
  64. package/dist/src/oauth/oAuthCard.js.map +1 -0
  65. package/dist/src/oauth/oAuthFlow.d.ts +47 -0
  66. package/dist/src/oauth/oAuthFlow.js +158 -0
  67. package/dist/src/oauth/oAuthFlow.js.map +1 -0
  68. package/dist/src/oauth/signingResource.d.ts +27 -3
  69. package/dist/src/oauth/tokenResponse.d.ts +29 -0
  70. package/dist/src/oauth/tokenResponse.js +25 -0
  71. package/dist/src/oauth/tokenResponse.js.map +1 -0
  72. package/dist/src/oauth/userTokenClient.d.ts +4 -3
  73. package/dist/src/oauth/userTokenClient.js +23 -13
  74. package/dist/src/oauth/userTokenClient.js.map +1 -1
  75. package/dist/src/state/agentState.d.ts +8 -3
  76. package/dist/src/state/agentState.js +17 -6
  77. package/dist/src/state/agentState.js.map +1 -1
  78. package/dist/src/state/agentStatePropertyAccesor.d.ts +58 -5
  79. package/dist/src/state/agentStatePropertyAccesor.js +6 -6
  80. package/dist/src/state/agentStatePropertyAccesor.js.map +1 -1
  81. package/package.json +3 -6
  82. package/src/activityWireCompat.ts +45 -0
  83. package/src/agent-client/agentClient.ts +21 -13
  84. package/src/agent-client/{expressApi.ts → agentResponseHandler.ts} +20 -12
  85. package/src/agent-client/index.ts +1 -1
  86. package/src/app/agentApplication.ts +24 -15
  87. package/src/app/{applicationBuilder.ts → agentApplicationBuilder.ts} +5 -5
  88. package/src/app/{applicationOptions.ts → agentApplicationOptions.ts} +3 -3
  89. package/src/app/index.ts +4 -3
  90. package/src/app/oauth/userIdentity.ts +78 -0
  91. package/src/app/turnState.ts +2 -2
  92. package/src/app/turnStateProperty.ts +72 -0
  93. package/src/auth/authConfiguration.ts +23 -4
  94. package/src/auth/jwt-middleware.ts +2 -1
  95. package/src/auth/msalTokenProvider.ts +1 -1
  96. package/src/cards/cardFactory.ts +26 -2
  97. package/src/cloudAdapter.ts +8 -4
  98. package/src/connector-client/connectorClient.ts +15 -5
  99. package/src/connector-client/index.ts +0 -1
  100. package/src/getProductInfo.ts +3 -0
  101. package/src/index.ts +2 -2
  102. package/src/oauth/index.ts +3 -4
  103. package/src/oauth/{oauthCard.ts → oAuthCard.ts} +1 -3
  104. package/src/oauth/oAuthFlow.ts +175 -0
  105. package/src/oauth/signingResource.ts +28 -3
  106. package/src/oauth/tokenResponse.ts +43 -0
  107. package/src/oauth/userTokenClient.ts +26 -16
  108. package/src/state/agentState.ts +25 -6
  109. package/src/state/agentStatePropertyAccesor.ts +65 -8
  110. package/dist/src/agent-client/expressApi.js.map +0 -1
  111. package/dist/src/app/applicationBuilder.js.map +0 -1
  112. package/dist/src/app/applicationOptions.js.map +0 -1
  113. package/dist/src/app/oauth/authenticationOptions.d.ts +0 -7
  114. package/dist/src/app/oauth/authenticationOptions.js +0 -7
  115. package/dist/src/app/oauth/authenticationOptions.js.map +0 -1
  116. package/dist/src/app/oauth/webChatOAuthFlowAppStyle.d.ts +0 -11
  117. package/dist/src/app/oauth/webChatOAuthFlowAppStyle.js +0 -85
  118. package/dist/src/app/oauth/webChatOAuthFlowAppStyle.js.map +0 -1
  119. package/dist/src/connector-client/conversationParameters.d.ts +0 -38
  120. package/dist/src/connector-client/conversationParameters.js +0 -7
  121. package/dist/src/connector-client/conversationParameters.js.map +0 -1
  122. package/dist/src/oauth/oauthCard.js.map +0 -1
  123. package/dist/src/oauth/tokenExchangeResource.d.ts +0 -17
  124. package/dist/src/oauth/tokenExchangeResource.js +0 -5
  125. package/dist/src/oauth/tokenExchangeResource.js.map +0 -1
  126. package/dist/src/oauth/tokenPostResource.d.ts +0 -9
  127. package/dist/src/oauth/tokenPostResource.js +0 -5
  128. package/dist/src/oauth/tokenPostResource.js.map +0 -1
  129. package/dist/src/oauth/webChatOAuthFlow.d.ts +0 -41
  130. package/dist/src/oauth/webChatOAuthFlow.js +0 -117
  131. package/dist/src/oauth/webChatOAuthFlow.js.map +0 -1
  132. package/src/app/oauth/authenticationOptions.ts +0 -8
  133. package/src/app/oauth/webChatOAuthFlowAppStyle.ts +0 -90
  134. package/src/connector-client/conversationParameters.ts +0 -40
  135. package/src/oauth/tokenExchangeResource.ts +0 -20
  136. package/src/oauth/tokenPostResource.ts +0 -12
  137. package/src/oauth/webChatOAuthFlow.ts +0 -123
@@ -3,10 +3,10 @@
3
3
  * Licensed under the MIT License.
4
4
  */
5
5
 
6
+ import { Activity, ActivityTypes, ConversationReference } from '@microsoft/agents-activity'
6
7
  import { TurnState } from './turnState'
7
8
  import { BaseAdapter } from '../baseAdapter'
8
- import { Activity, ActivityTypes, ConversationReference } from '@microsoft/agents-activity'
9
- import { ApplicationOptions } from './applicationOptions'
9
+ import { AgentApplicationOptions } from './agentApplicationOptions'
10
10
  import { RouteSelector } from './routeSelector'
11
11
  import { RouteHandler } from './routeHandler'
12
12
  import { ConversationUpdateEvents } from './conversationUpdateEvents'
@@ -15,7 +15,7 @@ import { AppRoute } from './appRoute'
15
15
  import { TurnContext } from '../turnContext'
16
16
  import { ResourceResponse } from '../connector-client'
17
17
  import { debug } from '../logger'
18
- import { WebChatOAuthFlowAppStyle } from './oauth/webChatOAuthFlowAppStyle'
18
+ import { UserIdentity } from './oauth/userIdentity'
19
19
  import { MemoryStorage } from '../storage'
20
20
 
21
21
  const logger = debug('agents:agent-application')
@@ -24,15 +24,15 @@ const TYPING_TIMER_DELAY = 1000
24
24
  type ApplicationEventHandler<TState extends TurnState> = (context: TurnContext, state: TState) => Promise<boolean>
25
25
 
26
26
  export class AgentApplication<TState extends TurnState> {
27
- protected readonly _options: ApplicationOptions<TState>
27
+ protected readonly _options: AgentApplicationOptions<TState>
28
28
  protected readonly _routes: AppRoute<TState>[] = []
29
29
  protected readonly _beforeTurn: ApplicationEventHandler<TState>[] = []
30
30
  protected readonly _afterTurn: ApplicationEventHandler<TState>[] = []
31
31
  private readonly _adapter?: BaseAdapter
32
32
  private _typingTimer: any
33
- private readonly _authManager?: WebChatOAuthFlowAppStyle
33
+ private readonly _userIdentity?: UserIdentity
34
34
 
35
- public constructor (options?: Partial<ApplicationOptions<TState>>) {
35
+ public constructor (options?: Partial<AgentApplicationOptions<TState>>) {
36
36
  this._options = {
37
37
  ...options,
38
38
  turnStateFactory: options?.turnStateFactory || (() => new TurnState() as TState),
@@ -44,8 +44,8 @@ export class AgentApplication<TState extends TurnState> {
44
44
  this._adapter = this._options.adapter
45
45
  }
46
46
 
47
- if (this._options.authentication && this._options.authentication.enableSSO) {
48
- this._authManager = new WebChatOAuthFlowAppStyle(this._options.storage ?? new MemoryStorage())
47
+ if (this._options.authentication && this._options.authentication.enableSSO && this._options.authentication.ssoConnectionName) {
48
+ this._userIdentity = new UserIdentity(this._options.storage ?? new MemoryStorage(), this._options.authentication.ssoConnectionName)
49
49
  }
50
50
 
51
51
  if (this._options.longRunningMessages && !this._adapter && !this._options.agentAppId) {
@@ -65,17 +65,17 @@ export class AgentApplication<TState extends TurnState> {
65
65
  return this._adapter
66
66
  }
67
67
 
68
- public get authManager (): WebChatOAuthFlowAppStyle {
69
- if (!this._authManager) {
68
+ public get userIdentity (): UserIdentity {
69
+ if (!this._userIdentity) {
70
70
  throw new Error(
71
71
  'The Application.authentication property is unavailable because no authentication options were configured.'
72
72
  )
73
73
  }
74
74
 
75
- return this._authManager
75
+ return this._userIdentity
76
76
  }
77
77
 
78
- public get options (): ApplicationOptions<TState> {
78
+ public get options (): AgentApplicationOptions<TState> {
79
79
  return this._options
80
80
  }
81
81
 
@@ -129,9 +129,7 @@ export class AgentApplication<TState extends TurnState> {
129
129
  }
130
130
 
131
131
  if (!this.options.agentAppId) {
132
- console.warn(
133
- "Calling Application.continueConversationAsync() without a configured 'agentAppId'. In production environments, a 'agentAppId' is required."
134
- )
132
+ logger.warn("Calling Application.continueConversationAsync() without a configured 'agentAppId'. In production environments, a 'agentAppId' is required.")
135
133
  }
136
134
 
137
135
  let reference: ConversationReference
@@ -156,6 +154,17 @@ export class AgentApplication<TState extends TurnState> {
156
154
  return this
157
155
  }
158
156
 
157
+ public onSignInSuccess (handler: (context: TurnContext, state: TurnState) => void): this {
158
+ if (this._userIdentity) {
159
+ this._userIdentity.onSignInSuccess(handler)
160
+ } else {
161
+ throw new Error(
162
+ 'The Application.authentication property is unavailable because no authentication options were configured.'
163
+ )
164
+ }
165
+ return this
166
+ }
167
+
159
168
  public async run (turnContext: TurnContext): Promise<boolean> {
160
169
  return await this.startLongRunningCall(turnContext, async (context) => {
161
170
  this.startTypingTimer(context)
@@ -4,13 +4,13 @@
4
4
  */
5
5
 
6
6
  import { AgentApplication } from './agentApplication'
7
- import { ApplicationOptions } from './applicationOptions'
7
+ import { AgentApplicationOptions } from './agentApplicationOptions'
8
8
  import { TurnState } from './turnState'
9
9
  import { Storage } from '../storage'
10
- import { AuthenticationOptions } from './oauth/authenticationOptions'
10
+ import { UserIdentityOptions } from './oauth/userIdentity'
11
11
 
12
- export class ApplicationBuilder<TState extends TurnState = TurnState> {
13
- protected _options: Partial<ApplicationOptions<TState>> = {}
12
+ export class AgentApplicationBuilder<TState extends TurnState = TurnState> {
13
+ protected _options: Partial<AgentApplicationOptions<TState>> = {}
14
14
 
15
15
  protected get options () {
16
16
  return this._options
@@ -31,7 +31,7 @@ export class ApplicationBuilder<TState extends TurnState = TurnState> {
31
31
  return this
32
32
  }
33
33
 
34
- public withAuthentication (authenticationOptions: AuthenticationOptions): this {
34
+ public withAuthentication (authenticationOptions: UserIdentityOptions): this {
35
35
  this._options.authentication = authenticationOptions
36
36
  return this
37
37
  }
@@ -7,9 +7,9 @@ import { CloudAdapter } from '../cloudAdapter'
7
7
  import { InputFileDownloader } from './inputFileDownloader'
8
8
  import { TurnState } from './turnState'
9
9
  import { Storage } from '../storage'
10
- import { AuthenticationOptions } from './oauth/authenticationOptions'
10
+ import { UserIdentityOptions } from './oauth/userIdentity'
11
11
 
12
- export interface ApplicationOptions<TState extends TurnState> {
12
+ export interface AgentApplicationOptions<TState extends TurnState> {
13
13
  adapter?: CloudAdapter;
14
14
  agentAppId?: string;
15
15
  storage?: Storage;
@@ -17,5 +17,5 @@ export interface ApplicationOptions<TState extends TurnState> {
17
17
  longRunningMessages: boolean;
18
18
  turnStateFactory: () => TState;
19
19
  fileDownloaders?: InputFileDownloader<TState>[];
20
- authentication?: AuthenticationOptions;
20
+ authentication?: UserIdentityOptions;
21
21
  }
package/src/app/index.ts CHANGED
@@ -1,10 +1,11 @@
1
1
  export * from './agentApplication'
2
- export * from './applicationBuilder'
3
- export * from './applicationOptions'
2
+ export * from './agentApplicationBuilder'
3
+ export * from './agentApplicationOptions'
4
4
  export * from './appRoute'
5
5
  export * from './attachmentDownloader'
6
- export * from './oauth/webChatOAuthFlowAppStyle'
6
+ export * from './oauth/userIdentity'
7
7
  export * from './conversationUpdateEvents'
8
8
  export * from './routeHandler'
9
9
  export * from './routeSelector'
10
10
  export * from './turnState'
11
+ export * from './inputFileDownloader'
@@ -0,0 +1,78 @@
1
+ /**
2
+ * Copyright (c) Microsoft Corporation. All rights reserved.
3
+ * Licensed under the MIT License.
4
+ */
5
+
6
+ import { TurnContext } from '../../turnContext'
7
+ // import { debug } from '../../logger'
8
+ import { TurnState } from '../turnState'
9
+ import { Storage } from '../../storage'
10
+ import { OAuthFlow, TokenRequestStatus, TokenResponse } from '../../oauth'
11
+ import { UserState } from '../../state'
12
+
13
+ // const logger = debug('agents:user-identity')
14
+
15
+ /**
16
+ * Options for configuring user identity.
17
+ * Contains settings related to Single Sign-On (SSO) authentication.
18
+ */
19
+ export interface UserIdentityOptions {
20
+ /**
21
+ * Determines whether Single Sign-On (SSO) is enabled for user authentication.
22
+ */
23
+ enableSSO: boolean;
24
+
25
+ /**
26
+ * The name of the SSO connection to use when SSO is enabled.
27
+ * Only applicable when enableSSO is set to true.
28
+ */
29
+ ssoConnectionName?: string;
30
+ }
31
+
32
+ export class UserIdentity {
33
+ oAuthFlow: OAuthFlow
34
+
35
+ /**
36
+ * Creates a new instance of UserAuthorization.
37
+ * @param {Storage} storage - The storage system to use for state management.
38
+ */
39
+ constructor (storage: Storage, connectionName: string) {
40
+ const userState = new UserState(storage)
41
+ this.oAuthFlow = new OAuthFlow(userState, connectionName)
42
+ }
43
+
44
+ public async getToken (context: TurnContext): Promise<TokenResponse> {
45
+ return await this.oAuthFlow.getUserToken(context)
46
+ }
47
+
48
+ public async authenticate (context: TurnContext, state: TurnState) : Promise<TokenResponse> {
49
+ let tokenResponse: TokenResponse
50
+ if (this.oAuthFlow.state?.flowStarted === false) {
51
+ tokenResponse = await this.oAuthFlow.beginFlow(context)
52
+ } else {
53
+ tokenResponse = await this.oAuthFlow.continueFlow(context)
54
+ if (tokenResponse.status === TokenRequestStatus.Success) {
55
+ if (this._signInHandler) {
56
+ await this._signInHandler(context, state)
57
+ }
58
+ }
59
+ }
60
+ return tokenResponse
61
+ }
62
+
63
+ /**
64
+ * Signs out the current user.
65
+ * This method clears the user's token and resets the SSO state.
66
+ *
67
+ * @param {TurnContext} context - The context object for the current turn.
68
+ * @param {TurnState} state - The state object for the current turn.
69
+ */
70
+ async signOut (context: TurnContext, state: TurnState) {
71
+ await this.oAuthFlow.signOut(context)
72
+ }
73
+
74
+ _signInHandler: ((context: TurnContext, state: TurnState) => void) | null = null
75
+ public onSignInSuccess (handler: (context: TurnContext, state: TurnState) => void) {
76
+ this._signInHandler = handler
77
+ }
78
+ }
@@ -198,8 +198,8 @@ export class TurnState<
198
198
  scope.value[name] = value
199
199
  }
200
200
 
201
- public load (context: TurnContext, storage?: Storage): Promise<boolean> {
202
- if (this._isLoaded) {
201
+ public load (context: TurnContext, storage?: Storage, force: boolean = false): Promise<boolean> {
202
+ if (this._isLoaded && !force) {
203
203
  return Promise.resolve(false)
204
204
  }
205
205
 
@@ -0,0 +1,72 @@
1
+ /**
2
+ * Copyright (c) Microsoft Corporation. All rights reserved.
3
+ * Licensed under the MIT License.
4
+ */
5
+
6
+ import { TurnContext } from '../turnContext'
7
+ import { StatePropertyAccessor } from '../state'
8
+ import { TurnStateEntry } from './turnStateEntry'
9
+ import { TurnState } from './turnState'
10
+
11
+ /**
12
+ * Maps an application's Turn State property to a State property.
13
+ * @template T Optional. Type of the property being mapped. Defaults to any.
14
+ */
15
+ export class TurnStateProperty<T = any> implements StatePropertyAccessor<T> {
16
+ private readonly _state: TurnStateEntry
17
+ private readonly _propertyName: string
18
+
19
+ /**
20
+ * Creates a new instance of the `TurnStateProperty` class.
21
+ * @param {TurnState} state Current application turn state.
22
+ * @param {string} scopeName Name of properties the memory scope to use.
23
+ * @param {string} propertyName Name of the property to use.
24
+ */
25
+ public constructor (state: TurnState, scopeName: string, propertyName: string) {
26
+ this._propertyName = propertyName
27
+
28
+ const scope = state.getScope(scopeName)
29
+ if (!scope) {
30
+ throw new Error(`TurnStateProperty: TurnState missing state scope named "${scope}".`)
31
+ }
32
+
33
+ this._state = scope
34
+ if (!this._state) {
35
+ throw new Error(`TurnStateProperty: TurnState missing state scope named "${scope}".`)
36
+ }
37
+ }
38
+
39
+ /**
40
+ * Deletes the state property.
41
+ * @returns {Promise<void>} A promise that represents the work queued to execute.
42
+ */
43
+ public delete (): Promise<void> {
44
+ this._state.value[this._propertyName] = undefined
45
+ return Promise.resolve()
46
+ }
47
+
48
+ /**
49
+ * Returns the state property value.
50
+ */
51
+ public get (context: TurnContext): Promise<T | undefined>
52
+ public get (context: TurnContext, defaultValue: T): Promise<T>
53
+ public get (defaultValue?: unknown): Promise<T | undefined> | Promise<T> {
54
+ if (this._state.value[this._propertyName] === undefined) {
55
+ this._state.value[this._propertyName] = defaultValue
56
+ }
57
+
58
+ return Promise.resolve(this._state.value[this._propertyName] as T)
59
+ }
60
+
61
+ /**
62
+ * Replace's the state property value.
63
+ * @template T
64
+ * @param {TurnContext} context The context object for the turn.
65
+ * @param {T} value The value to assign to the state property.
66
+ * @returns {Promise<void>} A promise that represents the work queued to execute.
67
+ */
68
+ public set (context: TurnContext, value: T): Promise<void> {
69
+ this._state.value[this._propertyName] = value
70
+ return Promise.resolve()
71
+ }
72
+ }
@@ -19,6 +19,20 @@ export interface AuthConfiguration {
19
19
 
20
20
  /**
21
21
  * Loads the authentication configuration from environment variables.
22
+ * ```
23
+ * tenantId=your-tenant-id
24
+ * clientId=your-client-id
25
+ * clientSecret=your-client-secret
26
+ *
27
+ * certPemFile=your-cert-pem-file
28
+ * certKeyFile=your-cert-key-file
29
+ *
30
+ * FICClientId=your-FIC-client-id
31
+ *
32
+ * connectionName=your-connection-name
33
+ * ```
34
+ * @remarks
35
+ * - `clientId` is required
22
36
  * @returns The authentication configuration.
23
37
  * @throws Will throw an error if clientId is not provided in production.
24
38
  */
@@ -43,11 +57,16 @@ export const loadAuthConfigFromEnv: () => AuthConfiguration = () => {
43
57
  }
44
58
 
45
59
  /**
46
- * Loads the agent authentication configuration from environment variables.
60
+ * Loads the agent authentication configuration from previous version environment variables.
61
+ * ```
62
+ * MicrosoftAppId=your-client-id
63
+ * MicrosoftAppPassword=your-client-secret
64
+ * MicrosoftAppTenantId=your-tenant-id
65
+ * ```
47
66
  * @returns The agent authentication configuration.
48
67
  * @throws Will throw an error if MicrosoftAppId is not provided in production.
49
68
  */
50
- export const loadBotAuthConfigFromEnv: () => AuthConfiguration = () => {
69
+ export const loadPrevAuthConfigFromEnv: () => AuthConfiguration = () => {
51
70
  if (process.env.MicrosoftAppId === undefined && process.env.NODE_ENV === 'production') {
52
71
  throw new Error('ClientId required in production')
53
72
  }
@@ -61,8 +80,8 @@ export const loadBotAuthConfigFromEnv: () => AuthConfiguration = () => {
61
80
  FICClientId: process.env.MicrosoftAppClientId,
62
81
  issuers: [
63
82
  'https://api.botframework.com',
64
- `https://sts.windows.net/${process.env.MicrosoftAppTenantId}/`,
65
- `https://login.microsoftonline.com/${process.env.MicrosoftAppTenantId}/v2.0`
83
+ `https://sts.windows.net/${process.env.MicrosoftAppTenantId}/`,
84
+ `https://login.microsoftonline.com/${process.env.MicrosoftAppTenantId}/v2.0`
66
85
  ]
67
86
  }
68
87
  }
@@ -46,7 +46,8 @@ const verifyToken = async (raw: string, config: AuthConfiguration): Promise<JwtP
46
46
  issuer: config.issuers,
47
47
  audience: [config.clientId!, 'https://api.botframework.com'],
48
48
  ignoreExpiration: false,
49
- algorithms: ['RS256']
49
+ algorithms: ['RS256'],
50
+ clockTolerance: 300
50
51
  }
51
52
 
52
53
  jwt.verify(raw, getKey, verifyOptions, (err, user) => {
@@ -13,7 +13,7 @@ import fs from 'fs'
13
13
  import crypto from 'crypto'
14
14
 
15
15
  const audience = 'api://AzureADTokenExchange'
16
- const logger = debug('agents:msal-token-provider')
16
+ const logger = debug('agents:msal')
17
17
 
18
18
  /**
19
19
  * Provides tokens using MSAL.
@@ -13,8 +13,9 @@ import { O365ConnectorCard } from './o365ConnectorCard'
13
13
  import { ThumbnailCard } from './thumbnailCard'
14
14
  import { VideoCard } from './videoCard'
15
15
  import { CardImage } from './cardImage'
16
- import { OAuthCard } from '../oauth/oauthCard'
16
+ import { OAuthCard } from '../oauth/oAuthCard'
17
17
  import { SigningResource } from '../oauth/signingResource'
18
+ import { SigninCard } from './signinCard'
18
19
 
19
20
  /**
20
21
  * Factory class for creating various types of cards.
@@ -216,7 +217,12 @@ export class CardFactory {
216
217
  */
217
218
  static oauthCard (connectionName: string, title: string, text: string, signingResource: SigningResource) : Attachment {
218
219
  const card: Partial<OAuthCard> = {
219
- buttons: [{ type: ActionTypes.Signin, title, value: signingResource.singingLink, channelData: undefined }],
220
+ buttons: [{
221
+ type: ActionTypes.Signin,
222
+ title,
223
+ value: signingResource.signInLink,
224
+ channelData: undefined
225
+ }],
220
226
  connectionName,
221
227
  tokenExchangeResource: signingResource.tokenExchangeResource,
222
228
  tokenPostResource: signingResource.tokenPostResource,
@@ -228,6 +234,24 @@ export class CardFactory {
228
234
  return { contentType: CardFactory.contentTypes.oauthCard, content: card }
229
235
  }
230
236
 
237
+ /**
238
+ * Creates a sign-in card attachment.
239
+ * @param title The title of the card.
240
+ * @param url The URL for the sign-in button.
241
+ * @param text The optional text for the card.
242
+ * @returns The sign-in card attachment.
243
+ */
244
+ static signinCard (title: string, url: string, text?: string): Attachment {
245
+ const card: SigninCard = {
246
+ buttons: [{ type: ActionTypes.Signin, title, value: url, channelData: undefined }],
247
+ }
248
+ if (text) {
249
+ card.text = text
250
+ }
251
+
252
+ return { contentType: CardFactory.contentTypes.signinCard, content: card }
253
+ }
254
+
231
255
  /**
232
256
  * Converts an array of media URLs or objects to an array of MediaUrl objects.
233
257
  * @param links The media URLs or objects.
@@ -11,16 +11,16 @@ import { Request } from './auth/request'
11
11
  import { ConnectorClient } from './connector-client/connectorClient'
12
12
  import { AuthConfiguration } from './auth/authConfiguration'
13
13
  import { AuthProvider } from './auth/authProvider'
14
- import { Activity, ActivityEventNames, ActivityTypes, Channels, ConversationReference, DeliveryModes } from '@microsoft/agents-activity'
14
+ import { Activity, ActivityEventNames, ActivityTypes, Channels, ConversationReference, DeliveryModes, ConversationParameters } from '@microsoft/agents-activity'
15
15
  import { ResourceResponse } from './connector-client/resourceResponse'
16
16
  import { MsalTokenProvider } from './auth/msalTokenProvider'
17
- import { ConversationParameters } from './connector-client/conversationParameters'
18
17
  import * as uuid from 'uuid'
19
18
  import { debug } from './logger'
20
19
  import { StatusCodes } from './statusCodes'
21
20
  import { InvokeResponse } from './invoke/invokeResponse'
22
21
  import { AttachmentInfo } from './connector-client/attachmentInfo'
23
22
  import { AttachmentData } from './connector-client/attachmentData'
23
+ import { normalizeIncomingActivity } from './activityWireCompat'
24
24
 
25
25
  const logger = debug('agents:cloud-adapter')
26
26
 
@@ -164,8 +164,10 @@ export class CloudAdapter extends BaseAdapter {
164
164
  }
165
165
  res.end()
166
166
  }
167
+ const incoming = normalizeIncomingActivity(request.body!)
168
+ const activity = Activity.fromObject(incoming)
169
+ logger.info(`--> Processing incoming activity, type:${activity.type} channel:${activity.channelId}`)
167
170
 
168
- const activity = Activity.fromObject(request.body!)
169
171
  if (!this.isValidChannelActivity(activity)) {
170
172
  return end(StatusCodes.BAD_REQUEST)
171
173
  }
@@ -180,6 +182,7 @@ export class CloudAdapter extends BaseAdapter {
180
182
  const context = this.createTurnContext(activity, logic)
181
183
  await this.runMiddleware(context, logic)
182
184
  const invokeResponse = this.processTurnResults(context)
185
+ logger.debug('Activity Response (invoke/expect replies): ', invokeResponse)
183
186
  return end(invokeResponse?.status ?? StatusCodes.OK, JSON.stringify(invokeResponse?.body), true)
184
187
  }
185
188
 
@@ -286,6 +289,7 @@ export class CloudAdapter extends BaseAdapter {
286
289
  * @returns The InvokeResponse if applicable, otherwise undefined.
287
290
  */
288
291
  protected processTurnResults (context: TurnContext): InvokeResponse | undefined {
292
+ logger.info('<--Sending back turn results')
289
293
  // Handle ExpectedReplies scenarios where all activities have been buffered and sent back at once in an invoke response.
290
294
  if (context.activity.deliveryMode === DeliveryModes.ExpectReplies) {
291
295
  return {
@@ -339,7 +343,7 @@ export class CloudAdapter extends BaseAdapter {
339
343
  tenantId: conversationParameters.tenantId,
340
344
  }
341
345
  activity.channelData = conversationParameters.channelData
342
- activity.recipient = conversationParameters.bot
346
+ activity.recipient = conversationParameters.agent
343
347
 
344
348
  return activity
345
349
  }
@@ -3,16 +3,18 @@ import axios, { AxiosInstance, AxiosRequestConfig, AxiosResponse } from 'axios'
3
3
  import { AuthConfiguration } from '../auth/authConfiguration'
4
4
  import { AuthProvider } from '../auth/authProvider'
5
5
  import { debug } from '../logger'
6
- import { Activity } from '@microsoft/agents-activity'
6
+ import { Activity, ConversationParameters } from '@microsoft/agents-activity'
7
7
  import { ConversationsResult } from './conversationsResult'
8
- import { ConversationParameters } from './conversationParameters'
9
8
  import { ConversationResourceResponse } from './conversationResourceResponse'
10
9
  import { ResourceResponse } from './resourceResponse'
11
10
  import { AttachmentInfo } from './attachmentInfo'
12
11
  import { AttachmentData } from './attachmentData'
13
-
12
+ import { normalizeOutgoingActivity } from '../activityWireCompat'
13
+ import { getProductInfo } from '../getProductInfo'
14
14
  const logger = debug('agents:connector-client')
15
15
 
16
+ export { getProductInfo }
17
+
16
18
  /**
17
19
  * ConnectorClient is a client for interacting with the Microsoft Connector API.
18
20
  */
@@ -71,8 +73,13 @@ export class ConnectorClient {
71
73
  const axiosInstance = axios.create({
72
74
  baseURL,
73
75
  headers: {
74
- Accept: 'application/json'
75
- }
76
+ Accept: 'application/json',
77
+ 'User-Agent': getProductInfo(),
78
+ },
79
+ transformRequest: [
80
+ (data, headers) => {
81
+ return JSON.stringify(normalizeOutgoingActivity(data))
82
+ }]
76
83
  })
77
84
 
78
85
  const token = await authProvider.getAccessToken(authConfig, scope)
@@ -103,6 +110,7 @@ export class ConnectorClient {
103
110
  * @returns The conversation resource response.
104
111
  */
105
112
  public async createConversationAsync (body: ConversationParameters): Promise<ConversationResourceResponse> {
113
+ // const payload = normalizeOutgoingConvoParams(body)
106
114
  const config: AxiosRequestConfig = {
107
115
  method: 'post',
108
116
  url: '/v3/conversations',
@@ -127,6 +135,7 @@ export class ConnectorClient {
127
135
  activityId: string,
128
136
  body: Activity
129
137
  ): Promise<ResourceResponse> {
138
+ logger.debug(`Replying to activity: ${activityId} in conversation: ${conversationId}`)
130
139
  if (!conversationId || !activityId) {
131
140
  throw new Error('conversationId and activityId are required')
132
141
  }
@@ -153,6 +162,7 @@ export class ConnectorClient {
153
162
  conversationId: string,
154
163
  body: Activity
155
164
  ): Promise<ResourceResponse> {
165
+ logger.debug(`Send to conversation: ${conversationId} activity: ${body.id}`)
156
166
  if (!conversationId) {
157
167
  throw new Error('conversationId is required')
158
168
  }
@@ -3,7 +3,6 @@ export * from './attachmentInfo'
3
3
  export * from './attachmentView'
4
4
  export * from './connectorClient'
5
5
  export * from './conversationMembers'
6
- export * from './conversationParameters'
7
6
  export * from './conversationResourceResponse'
8
7
  export * from './conversationsResult'
9
8
  export * from './resourceResponse'
@@ -0,0 +1,3 @@
1
+ import pjson from '@microsoft/agents-hosting/package.json'
2
+ import os from 'os'
3
+ export const getProductInfo = () : string => `agents-sdk-js/${pjson.version} nodejs/${process.version} ${os.platform()}-${os.arch()}/${os.release()}`
package/src/index.ts CHANGED
@@ -16,7 +16,9 @@ export * from './storage'
16
16
  export * from './transcript'
17
17
 
18
18
  export * from './activityHandler'
19
+ export * from './baseAdapter'
19
20
  export * from './cloudAdapter'
21
+ export * from './middlewareSet'
20
22
  export * from './claimsIdentity'
21
23
  export * from './logger'
22
24
  export * from './messageFactory'
@@ -27,5 +29,3 @@ export * from './logger'
27
29
  export * from './storage/storage'
28
30
 
29
31
  export * from './agent-client'
30
-
31
- export * from '@microsoft/agents-activity'
@@ -1,7 +1,6 @@
1
- export * from './oauthCard'
1
+ export * from './oAuthCard'
2
2
  export * from './signingResource'
3
- export * from './tokenExchangeResource'
4
- export * from './tokenPostResource'
5
3
  export * from './userTokenClient'
6
- export * from './webChatOAuthFlow'
7
4
  export * from './tokenExchangeRequest'
5
+ export * from './oAuthFlow'
6
+ export * from './tokenResponse'
@@ -2,9 +2,7 @@
2
2
  // Licensed under the MIT License.
3
3
 
4
4
  import { CardAction } from '@microsoft/agents-activity'
5
- import { TokenExchangeResource } from './tokenExchangeResource'
6
- import { TokenPostResource } from './tokenPostResource'
7
-
5
+ import { TokenExchangeResource, TokenPostResource } from './signingResource'
8
6
  /**
9
7
  * Represents an OAuth card.
10
8
  */