κ°μ μ΄μμ€ν΄νΈ νλ‘μ νΈ λ° μ€ν¬ νλ‘μ νΈ.
νμ΄νμ€ν¬λ¦½νΈ.
MS ν μ±λμμ μ€ν¬μ νλμ μ λ°μ΄νΈνλ €κ³ νλ©΄ κ°μ λμ°λ―Έμ μ€λ₯κ° λ°μν©λλ€.
updateActivity
ν¨μκ° μ 곡λ "SkillHandler"μμ ꡬνλμ§ μκΈ° λλ¬Έμ μ΄λ₯Ό ꡬνν΄μΌ ν¨).onUpdateActivity
: protected async onUpdateActivity(claimsIdentity: ClaimsIdentity, conversationId: string, activityId: string, activity: Activity): Promise<ResourceResponse> {
return await this.updateActivity(claimsIdentity, conversationId, activityId, activity);
}
updateActivity
ν¨μλ λ€μκ³Ό κ°μ΅λλ€.
private async updateActivity(claimsIdentity: ClaimsIdentity, conversationId: string, replyToActivityId: string, activity: Activity): Promise<ResourceResponse> {
let skillConversationReference: SkillConversationReference;
try {
skillConversationReference = await this.conversationIdFactory.getSkillConversationReference(conversationId);
} catch (err) {
// If the factory has overridden getSkillConversationReference, call the deprecated getConversationReference().
// In this scenario, the oAuthScope paired with the ConversationReference can only be used for talking with
// an official channel, not another bot.
if (err.message === 'Not Implemented') {
const conversationReference = await this.conversationIdFactory.getConversationReference(conversationId);
skillConversationReference = {
conversationReference,
oAuthScope: JwtTokenValidation.isGovernment(this.channelService) ?
GovernmentConstants.ToChannelFromBotOAuthScope :
AuthenticationConstants.ToChannelFromBotOAuthScope
};
} else {
// Re-throw all other errors.
throw err;
}
}
if (!skillConversationReference) {
throw new Error('skillConversationReference not found');
}
if (!skillConversationReference.conversationReference) {
throw new Error('conversationReference not found.');
}
const activityConversationReference = TurnContext.getConversationReference(activity);
const callback = async (context: TurnContext): Promise<void> => {
const adapter: BotFrameworkAdapter = (context.adapter as BotFrameworkAdapter);
// Cache the ClaimsIdentity and ConnectorClient on the context so that it's available inside of the bot's logic.
context.turnState.set(adapter.BotIdentityKey, claimsIdentity);
context.turnState.set(this.SkillConversationReferenceKey, activityConversationReference);
activity = TurnContext.applyConversationReference(activity, skillConversationReference.conversationReference) as Activity;
const client = adapter.createConnectorClient(activity.serviceUrl);
context.turnState.set(adapter.ConnectorClientKey, client);
context.activity.id = replyToActivityId;
await context.updateActivity(context.activity);
return;
};
AppCredentials.trustServiceUrl(skillConversationReference.conversationReference.serviceUrl);
await (this.adapter as BotFrameworkAdapter).continueConversation(skillConversationReference.conversationReference, skillConversationReference.oAuthScope, callback);
return { id: uuid() };
}
SkillHandler
μ μΈμ λ³κ²½νμμμ€.// Register the request handler.
const handler: CustomSkillHandler = new CustomSkillHandler(adapter, bot, skillConversationIdFactory, credentialProvider, authenticationConfiguration);
const skillEndpoint = new ChannelServiceRoutes(handler);
skillEndpoint.register(server, '/api/skills');
μΉ΄λκ° νμμ μ λ°μ΄νΈλ©λλ€.
VAκ° μ΄μ μ μ€λͺ
ν onUpdateActivity
ν¨μμμ νλμ μ
λ°μ΄νΈνλ €κ³ ν λ μ€λ₯κ° νμλ©λλ€.
(node:13410) UnhandledPromiseRejectionWarning: Error: Failed to decrypt conversation id
at new RestError (/Users/xxxx/Desktop/repository/xxx/virtual-assistant/node_modules/botframework-connector/node_modules/@azure/ms-rest-js/dist/msRest.node.js:1397:28)
at /Users/xxxx/Desktop/repository/xxx/virtual-assistant/node_modules/botframework-connector/node_modules/@azure/ms-rest-js/dist/msRest.node.js:1849:37
at process._tickCallback (internal/process/next_tick.js:68:7)
(node:13410) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 10)
μ±λ ν
μ΄ λ¬Έμ λ₯Ό λ³΄κ³ ν΄ μ£Όμ μ κ°μ¬ν©λλ€ @tommyJimmy87 . μμ§ κ²ν μ€μ λλ€. μ λ°μ΄νΈλλ λλ‘ λ°λ‘ μ°λ½λλ¦¬κ² μ΅λλ€ π!
@tommyjimmy87λ , μλ νμΈμ, κ·νκ° μ§λ©΄ν λ¬Έμ λ₯Ό μ¬νν μ μμΌλ―λ‘ λ¬΄μμ΄ μλͺ»λμλμ§ νμ νκΈ° μν΄ κ·νκ° νκ³ μλ μμ μ λν μΆκ° μ¬ν λ¨κ³λ₯Ό μ 곡ν΄μΌ ν©λλ€.
The Card is updated in Teams
μ(λ) λ¬΄μ¨ λ»μΈκ°μ?CustomSkillHandler
ν
μ€νΈ λ°©λ²μ μ 곡ν μ μμ΅λκΉ?λ€μμ μ΄ λ¬Έμ λ₯Ό μ¬ννκΈ° μν΄ μνν μ΅μ λ³κ²½ μ¬ν μ΄ μλ λΆκΈ°μ λλ€.
generator-bot-virtualassistant
μ¬μ©νμ¬ VA λ° κΈ°μ λ°°ν¬botskills connect
λͺ
λ Ήμ μ¬μ©νμ¬ VA λ° Skill μ°κ²°CustomSkillHandler
μ onUpdateActivity λ° updateActivity λ©μλ μΆκ°CustomSkillHandler
λ₯Ό μμ νλλ‘ μΈλ±μ€ νμΌ μμ μ°λ¦¬λ λΉμ μ λλ΅μμ£Όμλ₯Ό κΈ°μΈμΌ κ²μ λλ€!
μλ νμΈμ @Batta32λ , κ·νμ μ§λ¬Έμ λ΅λ³ν΄ λλ¦¬κ² μ΅λλ€.
λ΄ λ§μ MS Teams μ±λμμ adaptive card
μ μ
λ°μ΄νΈνλ €κ³ νλλ° κ²°κ³Όλ λ΄κ° μ΄λ€ μμ
μ μνν ν μΉ΄λκ° μ
λ°μ΄νΈλμ΄μΌ νλ€λ κ²μ
λλ€(μΉ΄λλ μ€ν¬ λ΄μ μμΌλ―λ‘ κΈ°λ³Έμ μΌλ‘ ν
μ€νΈλ updateActivity
μ€ν¬μμ VAκΉμ§).
μ, VAμ Skill λͺ¨λ Typescriptμ μμ΅λλ€.
κΈ°μ μμ adaptive card
κ° μμ΅λλ€. μ¬μ©μμ μμ
νμ μ΄ μΉ΄λλ λ€λ₯Έ μ½ν
μΈ λ‘ μ
λ°μ΄νΈλμ΄μΌ ν©λλ€. μ€ν¬μμ updateActivity
.
dc.context.updateActivity(previouslySentActivity);
previouslySentActivity
μ
λ°μ΄νΈνλ €λ μ‘ν°λΉν°μ
λλ€. λμ€μ μ
λ°μ΄νΈν μ μλλ‘ μ‘ν°λΉν°λ₯Ό μνμ μ μ₯ν©λλ€. μ΄ μ¬μ©μ μ΄μ λ²μ μμ μλνμ§λ§ λ΄κ° μ΄ν΄νλ ν μ μ‘ λ° μ
λ°μ΄νΈ νλμ νλ¦μ μ λ²μ μμ λ³κ²½λμμ΅λλ€.
κ·Έλ¬λ©΄ νλμ μ
λ°μ΄νΈν΄μΌ νλ VA λμ (μλ μ€)μ΄ νΈμΆλ©λλ€. νΈμΆμμ μμ CustomSkillHandler
μμ onUpdateActivity
λ°©λ²νμ§λ§ νλμ΄ MS νμ λ³΄λΌ λ λλμ΄ μ€λ₯κ° λ°μν©λλ€.
λ λ§μ 컨ν μ€νΈκ° νμνλ©΄ μλ €μ£Όμμμ€. ννΈ, κ·νμ μ§μ μμλ μ΄κ²μ μλνκ³ λμΌν μ€λ₯κ° μλμ§ νμΈν μ μμ΅λλ€.
μλ
νμΈμ @ Batta32 , ν
μ€νΈμ μ¬μ©νλ μ§μ μμ ν
μ€νΈνμ΅λλ€. μ¬κΈ°μμ ν¬ν¬λ₯Ό λ§λ€μμ΅λλ€. https://github.com/tommyJimmy87/botframework-solutions/tree/feature/southworks/conversationid-issue
λμΌν μ€λ₯λ₯Ό μ¬ννκΈ° μν΄ μ§μ μ λ³κ²½νμ΅λλ€. testSkillHandler
λ΄μμ try-catchλ₯Ό μΆκ°νμ¬ μ€λ₯κ° λ°μνμ΅λλ€.
try{
await context.updateActivity(activity);
}catch(e){
console.log(e);
}
μ΄κ²μ updateActivity
νΈμΆμμ λ°λ μ€μ μ€λ₯μ
λλ€.
{ body: '{"error":{"code":"ServiceError","message":"Unknown"}}',
headers: HttpHeaders { _headersMap: [Object] },
status: 400 },
body: { error: { code: 'ServiceError', message: 'Unknown' } } }
λ΄ νλ‘μ νΈμμ μ»λ κ²κ³Ό λμΌν©λλ€.
μ΄κ²μ λ΄κ° ν ν
μ€νΈμ
λλ€.
sample-skill testUpdateActivityDialog
μμ μ Dialogλ₯Ό λ§λ€μμ΅λλ€. μ¬κΈ°μ beginDialogμμ ν
μ€νΈμ ν¨κ» TestCard
λ₯Ό 보λ
λλ€. onContinueDialog
μμ λμΌν μΉ΄λλ₯Ό 보λ΄μ§λ§ λ€λ₯Έ ν
μ€νΈλ₯Ό μ¬μ©ν©λλ€.
VAλ₯Ό μ€ν¬μ μ°κ²°ν©λλ€.
μ€ν¬μ νΈμΆνκ³ ν μ€νΈ λν μμλ₯Ό μμνκ³ μΉ΄λλ₯Ό νμν μλλ‘ VAλ₯Ό νΈμΆν©λλ€.
Skillκ³Ό Test Dialogμ continueDialog
λ₯Ό νΈμΆν μλλ‘ VAλ₯Ό νΈμΆν©λλ€.
κΈ°μ μ μΉ΄λλ₯Ό μ λ°μ΄νΈνκΈ° μν΄ VAλ₯Ό νΈμΆν λ€μ μ€λ₯κ° λ°μν©λλ€.
λ©μ§λ€ @tommyJimmy87 ! μλ‘μ΄ μ λ³΄λ‘ λ¦¬λ·°ν΄λλ¦¬κ² μ΅λλ€ π μ λ§ κ°μ¬ν©λλ€.
μλ νμΈμ @tommyJimmy87μ λλ€! μ΅μ λ³κ²½ μ¬νκ³Ό μΈκΈλ μ¬ν λ¨κ³λ₯Ό μ¬μ©νμ¬ μλ리μ€λ₯Ό μ±κ³΅μ μΌλ‘ μ¬ν νμ΅λλ€.
μ°λ¦¬λ μ΄ λ¬Έμ μ λν΄ κ³μ μ°κ΅¬ν κ²μ λλ€. μ λ°μ΄νΈλλ λλ‘ λ°λ‘ μ°λ½λλ¦¬κ² μ΅λλ€ π.
_μ€ν¬μ΄ VAμ νλ μ 보λ₯Ό λ³΄λΌ λ λμΌν λ¬Έμ λ₯Ό κ°μ§νλ VAμ Skill λ΄ κ°μ μ°κ²°μ ν
μ€νΈνμ΅λλ€_
μλ νμΈμ @DiegoCardozo94 ,
μ λ°μ΄νΈν΄μ£Όμ μ κ°μ¬ν©λλ€.
μ΄κ±° μΈμ μΆμλ μ§ μμλλΆ κ³μ κ°μ?
17μΌ μ΄μ μ λ°λ§€κ° κ°λ₯ν κΉμ? :)
κ°μ¬ ν΄μ
@tommyJimmy87 μλ νμΈμ,
μ°λ¦¬λ μ΄ λ¬Έμ κ° C#μμλ
λͺ κ°μ§ κ΄λ ¨ λ¬Έμ λ₯Ό μ°Ύμμ΅λλ€.
SkillHandler
κ° κΈ°μ μμ μ±λλ‘ νλμ μ λ¬ν λ κ°μ§ ResourceResponse
μμ±νλ€κ³ μμΈν μ€λͺ
ν©λλ€. μ¦, update
λ° delete
μμ
μ μλνμ§ μμ΅λλ€ .SkillHandler
ν΄λμ€κ° OnUpdateActivityAsync
ꡬννμ§ μλλ€κ³ μμΈν μ€λͺ
ν©λλ€.λ§μ§λ§μΌλ‘ μΈκΈλ λ¨κ³λ₯Ό μ¬μ©νμ¬ λ€μ μλ리μ€λ₯Ό κ²μ¦νμ΅λλ€.
@darrenj , μ°λ¦¬λ C# λ΄λ μ¬μ©νμ¬ μ΄ λ¬Έμ λ₯Ό 볡μ νμ΅λλ€.
μ°λ¦¬μ ν μ€νΈ νκ²½ :
μ°λ¦¬μ μ¬ν λ¨κ³ :
_νλμ μ
λ°μ΄νΈνλ €κ³ ν λ κ°μ λμ°λ―Έμμ μμΈκ° λ°μν©λλ€_
_TypeScript Skillμ΄ Microsoft Teams μ±λμμ μ±κ³΅μ μΌλ‘ μ€ν μ€μ΄λ©° μ΄μ μ λ³΄λΈ μΉ΄λ μ
λ°μ΄νΈ_
μλ νμΈμ, https://github.com/microsoft/botframework-sdk/issues/5919 λ μ§μλλ 3κ° μΈμ΄ λͺ¨λμ λν΄ ν΄κ²°ν΄μΌ ν©λλ€. ν΄λΉ μ루μ μ΄ λ΄μΌλΆν° μμλλ μΌμΌ λΉλ μ€ νλλ₯Ό μ¬μ©νλ λ° λμμ΄ λλ€λ©΄ μλν΄ λ³Ό μ μμ΅λλ€.
@Batta32 λ μλ νμΈμ, λ¨Όμ μ λ°μ΄νΈν΄μΌ ν μ¬νμ λλ€. λ΄κ° μ΄λ―Έ μλ ν μμλ κ²μ΄ μλλλ€?
μλ νμΈμ @tommyJimmy87μ λλ€! μ, @gabog κ° TypeScript λ° C#μ λν΄ μΈκΈν λ΄μ© μ κ²μ¦ν κ²μ λλ€.
λ§μ§λ§ μ λ°μ΄νΈλ₯Ό μΆκ°νκ³ microsoft/botbuilder-js#2489 λ° microsoft/botbuilder-dotnet#4264 κ° ν¬ν¨λ SDKμ botbuilder-v4-js-daily μΌμΌ λΉλλ₯Ό ν΅ν©νμ¬ μ΄ λΆκΈ°λ₯Ό μ λ°μ΄νΈν κ²μ λλ€.
μ λ°μ΄νΈλλ λλ‘ λ°λ‘ μ°λ½λλ¦¬κ² μ΅λλ€ π.
@tommyJimmy87λ , μ΄ λ¬Έμ κ° testSkillHandler
μ microsoft/botbuilder-js#2489μ λ³κ²½ μ¬νμ μ μ©νλ κ²μ μ±κ³΅μ μΌλ‘ νμΈ νμΌλ©° Microsoft Teams μ±λμ μ¬μ©νμ¬ νλμ΄ μ¬λ°λ₯΄κ² μ
λ°μ΄νΈλμμ΅λλ€.
testSkillHandler
, νΉν processActivity
λ©μλμ μ μ©ν΄μΌ νλ λ³κ²½ μ¬νμ μλ³νλ €λ©΄ μ΄ μ»€λ° μ νμΈνμμμ€.
@darrenj & @gabog - C# λ΄μ μ¬μ©νμ¬ microsoft/botbuilder-dotnet#4264μ λ³κ²½ μ¬νλ μ±κ³΅μ μΌλ‘ κ²μ¦νμ΅λλ€.
ν μ€νΈ νκ²½:
μ¬ν λ¨κ³:
_testSkillHandler_μ processActivity λ©μλμ λν λ³κ²½ μ¬ν_
_TypeScript κ°μ λμ°λ―Έκ° Microsoft Teams μ±λμμ μ±κ³΅μ μΌλ‘ μ€ν μ€μ΄λ©° μ΄μ μ λ³΄λΈ μΉ΄λλ₯Ό μ
λ°μ΄νΈνμ΅λλ€_
μ°λ¦¬λ λΉμ μ λλ΅μμ£Όμλ₯Ό κΈ°μΈμΌ κ²μ λλ€!
@Batta32λ , μ λ°μ΄νΈ κ°μ¬ν©λλ€. μ΅λν 빨리 μλν΄ λ³΄κ² μ΅λλ€. λ΄ μͺ½μμ ν κ°μ§ μ§λ¬Έμ΄ μμ΅λλ€. λΌμ΄λΈλ¬λ¦¬ λ²μ μ΄ λ³κ²½λμκ±°λ μμ κ²μν 컀λ°μΌ λΏμ λλ€. κ°μ¬ ν΄μ
@tommyJimmy87 - μμ κ²μν 컀λ°μ λλ€ !
@Batta32 λ μλ νμΈμ :)
@tommyJimmy87 κ°μ¬ν©λλ€! μ΄ λ¬Έμ λ₯Ό νμΈνλ μ¦μ μ΄ λ¬Έμ λ₯Ό μ’ λ£ν μ μμ΅λλ€ π.
μλ νμΈμ @Batta32μ λλ€! μ΄ λ¬Έμ λ₯Ό κΈ°κΊΌμ΄ μ’ λ£ν μ μμ΅λλ€. :)
νμΈν΄μ£Όμ μ κ°μ¬ν©λλ€ @tommyJimmy87 !
@darrenj - SDK νμμ ν΄κ²°
κ°μ₯ μ μ©ν λκΈ
@Batta32 λ μλ νμΈμ :)