Skip to content

Commit

Permalink
Ensure EndDialog action within a ForEachElement will end the dialog (#…
Browse files Browse the repository at this point in the history
…6160) (#6164)

* Ensure EndDialog action within a ForEachElement will end the dialog

* EndDialog from a nested ForEach

* Add clarifying comments to ForEachElement
  • Loading branch information
EricDahlvang authored Feb 3, 2022
1 parent 5fd508f commit 5581313
Show file tree
Hide file tree
Showing 4 changed files with 151 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -270,6 +270,11 @@ protected virtual async Task<DialogTurnResult> OnNextActionAsync(DialogContext d
// Recursively call ContinueDialogAsync() to apply changes and continue execution.
return await root.ContinueDialogAsync(cancellationToken).ConfigureAwait(false);
}

if (result is DialogTurnResult dtr && dtr.ParentEnded)
{
return await this.OnEndOfActionsAsync(dc, result, cancellationToken: cancellationToken).ConfigureAwait(false);
}

// Increment our offset into the actions and being the next action
var nextOffset = dc.State.GetIntValue(OFFSETKEY, 0) + 1;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -226,12 +226,34 @@ private async Task<DialogTurnResult> RunItemsAsync(DialogContext dc, bool beginD

beginDialog = true;
UpdateActionScopeState(dc, new DialogState());

// If one of the descendant dialogs ended the parent, then end processing
if (ShouldEndDialog(turnResult, out DialogTurnResult finalResult))
{
return await dc.EndDialogAsync(result: finalResult, cancellationToken: cancellationToken).ConfigureAwait(false);
}
}

// End of list has been reached, or the list is null
return await dc.EndDialogAsync(cancellationToken: cancellationToken).ConfigureAwait(false);
}

private bool ShouldEndDialog(DialogTurnResult turnResult, out DialogTurnResult finalTurnResult)
{
finalTurnResult = turnResult;

// If a descendant dialog multiple levels below this container ended stack processing,
// the result will be nested.
while (finalTurnResult.Result != null
&& finalTurnResult.Result is DialogTurnResult dtr
&& dtr.ParentEnded && dtr.Status == DialogTurnStatus.Complete)
{
finalTurnResult = dtr;
}

return finalTurnResult.ParentEnded && finalTurnResult.Status == DialogTurnStatus.Complete;
}

private void UpdateActionScopeState(DialogContext dc, DialogState state)
{
var activeDialogState = dc.ActiveDialog?.State as Dictionary<string, object>;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -253,7 +253,13 @@ public async Task TestForeachNullItems()
[Fact]
public async Task TestForeachWithPrompt()
{
await TestUtils.RunTestScript(_resourceExplorerFixture.ResourceExplorer);
await TestUtils.RunTestScript(_resourceExplorerFixture.ResourceExplorer);
}

[Fact]
public async Task TestForeachWithEndDialog()
{
await TestUtils.RunTestScript(_resourceExplorerFixture.ResourceExplorer);
}

[Fact]
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
{
"$schema": "../../../tests.schema",
"$kind": "Microsoft.Test.Script",
"dialog": {
"$kind": "Microsoft.AdaptiveDialog",
"id": "AdaptiveDialog",
"generator": {
"$kind": "Microsoft.TemplateEngineLanguageGenerator"
},
"triggers": [
{
"$kind": "Microsoft.OnBeginDialog",
"actions": [
{
"$kind": "Microsoft.SetProperty",
"property": "$loopTwoThenEnd",
"value": "=createArray('one', 'two', 'end')"
},
{
"$kind": "Microsoft.SetProperty",
"property": "$loopTwo",
"value": "=createArray('1', '2')"
},
{
"$kind": "Microsoft.SetProperty",
"property": "$loopTwoAgain",
"value": "=createArray('a', 'b')"
},
{
"$kind": "Microsoft.Foreach",
"itemsProperty": "$loopTwo",
"value": "dialog.foreach0.value",
"index": "dialog.foreach0.index",
"actions": [
{
"$kind": "Microsoft.Foreach",
"itemsProperty": "$loopTwoAgain",
"value": "dialog.foreach1.value",
"index": "dialog.foreach1.index",
"actions": [
{
"$kind": "Microsoft.Foreach",
"value": "dialog.foreach2.value",
"index": "dialog.foreach2.index",
"itemsProperty": "$loopTwoThenEnd",
"actions": [
{
"$kind": "Microsoft.IfCondition",
"condition": "($foreach2.value == 'end')",
"actions": [
{
"$kind": "Microsoft.EndDialog"
}
]
},
{
"$kind": "Microsoft.SendActivity",
"activity": "${$foreach2.value}"
}
]
}
]
},
{
"$kind": "Microsoft.SendActivity",
"activity": "This should never happen2"
}
]
},
{
"$kind": "Microsoft.SendActivity",
"activity": "This should never happen"
}
]
}
],
"autoEndDialog": true,
"defaultResultProperty": "dialog.result"
},
"script": [
{
"$kind": "Microsoft.Test.UserConversationUpdate"
},
{
"$kind": "Microsoft.Test.AssertReply",
"text": "one"
},
{
"$kind": "Microsoft.Test.AssertReply",
"text": "two"
},
{
"$kind": "Microsoft.Test.UserSays",
"text": "hi"
},
{
"$kind": "Microsoft.Test.AssertReply",
"text": "one"
},
{
"$kind": "Microsoft.Test.AssertReply",
"text": "two"
},
{
"$kind": "Microsoft.Test.UserSays",
"text": "hi"
},
{
"$kind": "Microsoft.Test.AssertReply",
"text": "one"
},
{
"$kind": "Microsoft.Test.AssertReply",
"text": "two"
}
]
}

0 comments on commit 5581313

Please sign in to comment.