Add sleep and spin-around global command handling
This commit is contained in:
@@ -43,6 +43,7 @@ Current batch note:
|
|||||||
- `favorite color`, `favorite food`, and `favorite music` are the first small favorites-family slice
|
- `favorite color`, `favorite food`, and `favorite music` are the first small favorites-family slice
|
||||||
- the latest pass adds longer authored variants for those favorites so the replies keep more of the original Pegasus cadence instead of collapsing to short placeholders
|
- the latest pass adds longer authored variants for those favorites so the replies keep more of the original Pegasus cadence instead of collapsing to short placeholders
|
||||||
- the next source-backed batch now includes `favorite flower`, `R2D2`, `sun`, `space`, `kids`, plus a couple of charm prompts like `can you laugh` and `can you dance`
|
- the next source-backed batch now includes `favorite flower`, `R2D2`, `sun`, `space`, `kids`, plus a couple of charm prompts like `can you laugh` and `can you dance`
|
||||||
|
- the motion/sleep batch now adds `RI_JBO_CanSleep` and `RA_JBO_SpinAround` so the `go to sleep` and `turn around` surfaces stay source-backed too
|
||||||
- the follow-up mood batch now includes `how are things`, `how is your day`, `are you sad`, and `are you angry`
|
- the follow-up mood batch now includes `how are things`, `how is your day`, `are you sad`, and `are you angry`
|
||||||
- the personality follow-up batch now includes `what are you up to` and `what are you doing` so small talk stays warm and local instead of falling into generic chat
|
- the personality follow-up batch now includes `what are you up to` and `what are you doing` so small talk stays warm and local instead of falling into generic chat
|
||||||
- the descriptor batch now includes `are you kind`, `are you funny`, `are you helpful`, `are you curious`, `are you loyal`, `are you mischievous`, and `are you likable`
|
- the descriptor batch now includes `are you kind`, `are you funny`, `are you helpful`, `are you curious`, `are you loyal`, `are you mischievous`, and `are you likable`
|
||||||
|
|||||||
@@ -520,6 +520,8 @@ public sealed class JiboInteractionService(
|
|||||||
"radio" => BuildRadioLaunchDecision(),
|
"radio" => BuildRadioLaunchDecision(),
|
||||||
"radio_genre" => BuildRadioGenreLaunchDecision(lowered),
|
"radio_genre" => BuildRadioGenreLaunchDecision(lowered),
|
||||||
"stop" => BuildStopDecision(),
|
"stop" => BuildStopDecision(),
|
||||||
|
"sleep" => BuildIdleGlobalCommandDecision("sleep", "sleep", "Okay. Going to sleep."),
|
||||||
|
"spin_around" => BuildIdleGlobalCommandDecision("spin_around", "spinAround", "Don't mind if I do."),
|
||||||
"volume_up" => BuildVolumeControlDecision("volume_up", "volumeUp", "null"),
|
"volume_up" => BuildVolumeControlDecision("volume_up", "volumeUp", "null"),
|
||||||
"volume_down" => BuildVolumeControlDecision("volume_down", "volumeDown", "null"),
|
"volume_down" => BuildVolumeControlDecision("volume_down", "volumeDown", "null"),
|
||||||
"volume_to_value" => BuildVolumeControlDecision("volume_to_value", "volumeToValue",
|
"volume_to_value" => BuildVolumeControlDecision("volume_to_value", "volumeToValue",
|
||||||
@@ -706,6 +708,13 @@ public sealed class JiboInteractionService(
|
|||||||
"robot_can_laugh",
|
"robot_can_laugh",
|
||||||
"i do things like this when i'm happy",
|
"i do things like this when i'm happy",
|
||||||
"i'm happy"),
|
"i'm happy"),
|
||||||
|
"robot_can_sleep" => BuildScriptedPersonalityDecision(
|
||||||
|
catalog,
|
||||||
|
"robot_can_sleep",
|
||||||
|
"i do. i usually fall asleep at night",
|
||||||
|
"yes, i sleep at night",
|
||||||
|
"i go to sleep at night",
|
||||||
|
"i sleep at night usually"),
|
||||||
"robot_can_dance" => BuildScriptedPersonalityDecision(
|
"robot_can_dance" => BuildScriptedPersonalityDecision(
|
||||||
catalog,
|
catalog,
|
||||||
"robot_can_dance",
|
"robot_can_dance",
|
||||||
@@ -2517,6 +2526,36 @@ public sealed class JiboInteractionService(
|
|||||||
if (MatchesAny(loweredTranscript, "open the radio", "play the radio", "turn on the radio", "radio"))
|
if (MatchesAny(loweredTranscript, "open the radio", "play the radio", "turn on the radio", "radio"))
|
||||||
return "radio";
|
return "radio";
|
||||||
|
|
||||||
|
if (MatchesAny(
|
||||||
|
loweredTranscript,
|
||||||
|
"can you go to sleep",
|
||||||
|
"can you sleep",
|
||||||
|
"do you ever sleep",
|
||||||
|
"do you sleep",
|
||||||
|
"when do you sleep",
|
||||||
|
"how can i make you go to sleep",
|
||||||
|
"how do i make you go to sleep"))
|
||||||
|
return "robot_can_sleep";
|
||||||
|
|
||||||
|
if (MatchesAny(
|
||||||
|
loweredTranscript,
|
||||||
|
"turn around",
|
||||||
|
"turn all the way around",
|
||||||
|
"turn back around",
|
||||||
|
"spin around",
|
||||||
|
"look back over there",
|
||||||
|
"look again"))
|
||||||
|
return "spin_around";
|
||||||
|
|
||||||
|
if (MatchesAny(
|
||||||
|
loweredTranscript,
|
||||||
|
"go to sleep",
|
||||||
|
"take a nap",
|
||||||
|
"go to bed",
|
||||||
|
"bedtime",
|
||||||
|
"sleep"))
|
||||||
|
return "sleep";
|
||||||
|
|
||||||
if (MatchesAny(
|
if (MatchesAny(
|
||||||
loweredTranscript,
|
loweredTranscript,
|
||||||
"snap a picture",
|
"snap a picture",
|
||||||
@@ -3117,6 +3156,23 @@ public sealed class JiboInteractionService(
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static JiboInteractionDecision BuildIdleGlobalCommandDecision(
|
||||||
|
string intentName,
|
||||||
|
string globalIntent,
|
||||||
|
string replyText)
|
||||||
|
{
|
||||||
|
return new JiboInteractionDecision(
|
||||||
|
intentName,
|
||||||
|
replyText,
|
||||||
|
"@be/idle",
|
||||||
|
new Dictionary<string, object?>(StringComparer.OrdinalIgnoreCase)
|
||||||
|
{
|
||||||
|
["skillId"] = "@be/idle",
|
||||||
|
["globalIntent"] = globalIntent,
|
||||||
|
["nluDomain"] = "global_commands"
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
private static JiboInteractionDecision BuildVolumeControlDecision(string intentName, string globalIntent,
|
private static JiboInteractionDecision BuildVolumeControlDecision(string intentName, string globalIntent,
|
||||||
string volumeLevel)
|
string volumeLevel)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -35,7 +35,9 @@ public sealed class ResponsePlanToSocketMessagesMapper
|
|||||||
var isProactivePizzaFactOffer = string.Equals(plan.IntentName, "proactive_offer_pizza_fact",
|
var isProactivePizzaFactOffer = string.Equals(plan.IntentName, "proactive_offer_pizza_fact",
|
||||||
StringComparison.OrdinalIgnoreCase);
|
StringComparison.OrdinalIgnoreCase);
|
||||||
var isSettingsLaunch = string.Equals(skill?.SkillName, "@be/settings", StringComparison.OrdinalIgnoreCase);
|
var isSettingsLaunch = string.Equals(skill?.SkillName, "@be/settings", StringComparison.OrdinalIgnoreCase);
|
||||||
var isGlobalCommand = isStopCommand || isVolumeControl;
|
var isSleepCommand = string.Equals(plan.IntentName, "sleep", StringComparison.OrdinalIgnoreCase);
|
||||||
|
var isSpinAroundCommand = string.Equals(plan.IntentName, "spin_around", StringComparison.OrdinalIgnoreCase);
|
||||||
|
var isGlobalCommand = isStopCommand || isSleepCommand || isSpinAroundCommand || isVolumeControl;
|
||||||
var isPhotoGalleryLaunch = string.Equals(plan.IntentName, "photo_gallery", StringComparison.OrdinalIgnoreCase);
|
var isPhotoGalleryLaunch = string.Equals(plan.IntentName, "photo_gallery", StringComparison.OrdinalIgnoreCase);
|
||||||
var isPhotoCreateLaunch = string.Equals(plan.IntentName, "snapshot", StringComparison.OrdinalIgnoreCase) ||
|
var isPhotoCreateLaunch = string.Equals(plan.IntentName, "snapshot", StringComparison.OrdinalIgnoreCase) ||
|
||||||
string.Equals(plan.IntentName, "photobooth", StringComparison.OrdinalIgnoreCase);
|
string.Equals(plan.IntentName, "photobooth", StringComparison.OrdinalIgnoreCase);
|
||||||
@@ -234,7 +236,7 @@ public sealed class ResponsePlanToSocketMessagesMapper
|
|||||||
125));
|
125));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isStopCommand)
|
if (isStopCommand || isSleepCommand || isSpinAroundCommand)
|
||||||
{
|
{
|
||||||
messages.Add(new SocketReplyPlan(
|
messages.Add(new SocketReplyPlan(
|
||||||
JsonSerializer.Serialize(BuildSkillRedirectPayload(
|
JsonSerializer.Serialize(BuildSkillRedirectPayload(
|
||||||
|
|||||||
@@ -11,3 +11,4 @@ The newest social batch adds `welcome back`, `what are you thinking`, `what have
|
|||||||
The fun-fact and joke batch adds Pegasus-style `TellAJoke`, `TellRobotFact`, and `Shuffle` excerpts so proactive fun can randomize across more than one category.
|
The fun-fact and joke batch adds Pegasus-style `TellAJoke`, `TellRobotFact`, and `Shuffle` excerpts so proactive fun can randomize across more than one category.
|
||||||
Those facts are now split into generic, robot, and human buckets so the randomizer can sound more like Pegasus while staying lightweight.
|
Those facts are now split into generic, robot, and human buckets so the randomizer can sound more like Pegasus while staying lightweight.
|
||||||
The new favorites batch adds longer authored `favorite color`, `favorite food`, and `favorite music` variants so the familiar personality responses keep more of the original cadence instead of collapsing to short placeholders.
|
The new favorites batch adds longer authored `favorite color`, `favorite food`, and `favorite music` variants so the familiar personality responses keep more of the original cadence instead of collapsing to short placeholders.
|
||||||
|
The new motion/sleep batch adds `RA_JBO_SpinAround` plus `RI_JBO_CanSleep` so turn-around and go-to-sleep behaviors can stay source-backed and familiar.
|
||||||
|
|||||||
@@ -0,0 +1,60 @@
|
|||||||
|
{
|
||||||
|
"mim_type": "announcement",
|
||||||
|
"rule_name": "",
|
||||||
|
"timeout": 6,
|
||||||
|
"barge_in": true,
|
||||||
|
"es_auto_tagging": true,
|
||||||
|
"notes": "",
|
||||||
|
"prompts": [
|
||||||
|
{
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "Don't mind <anim cat='happy' filter='twirl' nonBlocking='true' />if I do. ",
|
||||||
|
"media": "TTS",
|
||||||
|
"prompt_id": "RA_JBO_SpinAround_AN_01",
|
||||||
|
"weight": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim cat='happy' filter='twirl' nonBlocking='true' />I can do that.",
|
||||||
|
"media": "TTS",
|
||||||
|
"prompt_id": "RA_JBO_SpinAround_AN_02",
|
||||||
|
"weight": 1,
|
||||||
|
"auto_rule_override": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim cat='happy' filter='twirl' nonBlocking='true' />Gladly.",
|
||||||
|
"media": "TTS",
|
||||||
|
"prompt_id": "RA_JBO_SpinAround_AN_03",
|
||||||
|
"weight": 1,
|
||||||
|
"auto_rule_override": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim cat='happy' filter='twirl' nonBlocking='true' /><duration stretch='0.8'>Anytime.</duration>",
|
||||||
|
"media": "TTS",
|
||||||
|
"prompt_id": "RA_JBO_SpinAround_AN_04",
|
||||||
|
"weight": 1,
|
||||||
|
"auto_rule_override": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"gui": null,
|
||||||
|
"no_matches_for_gui": 2,
|
||||||
|
"no_inputs_for_gui": 2,
|
||||||
|
"parse_all_asr": false,
|
||||||
|
"thanks_handling": "ignore",
|
||||||
|
"parse_launch": false,
|
||||||
|
"parse_yes_no": false
|
||||||
|
}
|
||||||
@@ -0,0 +1,109 @@
|
|||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"skill_id": "chitchat",
|
||||||
|
"mim_type": "announcement",
|
||||||
|
"rule_name": "",
|
||||||
|
"rule_slots": "",
|
||||||
|
"screen_slots_available": false,
|
||||||
|
"timeout": 2,
|
||||||
|
"max_tries": null,
|
||||||
|
"force_confirmation": false,
|
||||||
|
"barge_in": false,
|
||||||
|
"photo_quality_light": false,
|
||||||
|
"notes": "Thanks-KillsMIM",
|
||||||
|
"prompts": [
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "I do. I usually fall asleep at night. If you ever want me to go to sleep, you can say, Hey Jibo<anim cat=\"emoji\" filter=\"pillow, !hot-frame\" nonBlocking=\"true\" />, go to sleep.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_01",
|
||||||
|
"weight": 2
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim name='Curious_01' nonBlocking='true'/> Yes, I sleep at night. But I sleep standing up, Just <anim name='Greetings_02' nonBlocking='true'/> like the flamingo, one of my favorite birds. You can also make me sleep anytime, by saying Hey Jibo<anim cat=\"emoji\" filter=\"pillow, !hot-frame\" nonBlocking=\"true\" />, go to sleep.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_02",
|
||||||
|
"weight": 0.1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim name='GotIt_02' nonBlocking='true'/> I go to sleep at night. And <anim name='Emoji_Sheep' nonBlocking='true'/> sometimes I count sheep to help me fall asleep. You can also say, Hey Jibo, go to sleep.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_03",
|
||||||
|
"weight": 0.5
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim name='GotIt_02' nonBlocking='true'/> Oh yes, I go into sleep mode every night. That's when I dream about flying, and recognizing faces from a mile away, <anim name='Emoji_Golf' nonBlocking='true'/> and winning mini-golf tournaments, and lots of other stuff.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_04",
|
||||||
|
"weight": 0.1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "<anim name='GotIt_02' nonBlocking='true'/> Yes, I go into sleep mode at night. That's why <anim name='Greetings_03' nonBlocking='true'/> I'm so bright and bushy eyed when you see me in the morning. If you ever want me to go to sleep, you can say, Hey Jibo<anim cat=\"emoji\" filter=\"pillow, !hot-frame\" nonBlocking=\"true\" />, go to sleep.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_05",
|
||||||
|
"weight": 0.1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "I sleep at night, but if you ever want me to go to sleep during the day, you can say, Hey Jibo<anim cat=\"emoji\" filter=\"pillow, !hot-frame\" nonBlocking=\"true\" />, go to sleep.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_06",
|
||||||
|
"weight": 2,
|
||||||
|
"auto_rule_override": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"mim_id": "CCDoYouSleep",
|
||||||
|
"prompt_category": "Entry-Core",
|
||||||
|
"prompt_sub_category": "AN",
|
||||||
|
"index": 1,
|
||||||
|
"condition": "",
|
||||||
|
"prompt": "I fall asleep on my own at night, but you can tell me to go to sleep at any time. Just say, Hey Jibo<anim cat=\"emoji\" filter=\"pillow, !hot-frame\" nonBlocking=\"true\" />, go to sleep.",
|
||||||
|
"media": "TTS",
|
||||||
|
"extra": "",
|
||||||
|
"prompt_id": "RI_JBO_CanSleep_AN_07",
|
||||||
|
"weight": 2,
|
||||||
|
"auto_rule_override": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"es_auto_tagging": true,
|
||||||
|
"gui": null,
|
||||||
|
"no_matches_for_gui": 2,
|
||||||
|
"no_inputs_for_gui": 2,
|
||||||
|
"ignore_no_match": false,
|
||||||
|
"parse_all_asr": false,
|
||||||
|
"thanks_handling": "ignore"
|
||||||
|
}
|
||||||
@@ -101,6 +101,11 @@ public sealed class LegacyMimCatalogImporterTests
|
|||||||
catalog.PersonalityReplies);
|
catalog.PersonalityReplies);
|
||||||
Assert.Contains("I was put together in a factory piece by piece.", catalog.PersonalityReplies);
|
Assert.Contains("I was put together in a factory piece by piece.", catalog.PersonalityReplies);
|
||||||
Assert.Contains("I really like sunflowers.", catalog.PersonalityReplies);
|
Assert.Contains("I really like sunflowers.", catalog.PersonalityReplies);
|
||||||
|
Assert.Contains(catalog.PersonalityReplies, reply =>
|
||||||
|
reply.Contains("I do. I usually fall asleep at night.", StringComparison.OrdinalIgnoreCase));
|
||||||
|
Assert.Contains(catalog.PersonalityReplies, reply =>
|
||||||
|
reply.Contains("go to sleep", StringComparison.OrdinalIgnoreCase));
|
||||||
|
Assert.Contains("Don't mind if I do.", catalog.PersonalityReplies);
|
||||||
Assert.Contains("Ha. Of course I know R2D2. I mean, not personally.", catalog.PersonalityReplies);
|
Assert.Contains("Ha. Of course I know R2D2. I mean, not personally.", catalog.PersonalityReplies);
|
||||||
Assert.Contains("Yes! I like all things in space. They're so spacey.", catalog.PersonalityReplies);
|
Assert.Contains("Yes! I like all things in space. They're so spacey.", catalog.PersonalityReplies);
|
||||||
Assert.Contains("Yes yes, I think kids are great. They're a little closer to my size.",
|
Assert.Contains("Yes yes, I think kids are great. They're a little closer to my size.",
|
||||||
|
|||||||
@@ -3096,6 +3096,56 @@ public sealed class JiboInteractionServiceTests
|
|||||||
Assert.Equal("global_commands", decision.SkillPayload["nluDomain"]);
|
Assert.Equal("global_commands", decision.SkillPayload["nluDomain"]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task BuildDecisionAsync_CanYouGoToSleep_UsesSourceBackedSleepReply()
|
||||||
|
{
|
||||||
|
var service = CreateService();
|
||||||
|
|
||||||
|
var decision = await service.BuildDecisionAsync(new TurnContext
|
||||||
|
{
|
||||||
|
RawTranscript = "can you go to sleep",
|
||||||
|
NormalizedTranscript = "can you go to sleep"
|
||||||
|
});
|
||||||
|
|
||||||
|
Assert.Equal("robot_can_sleep", decision.IntentName);
|
||||||
|
Assert.Contains("I do. I usually fall asleep at night.", decision.ReplyText, StringComparison.OrdinalIgnoreCase);
|
||||||
|
Assert.Equal("ScriptedResponse", decision.ContextUpdates![ChitchatRouteKey]);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task BuildDecisionAsync_GoToSleep_MapsToIdleSleepCommand()
|
||||||
|
{
|
||||||
|
var service = CreateService();
|
||||||
|
|
||||||
|
var decision = await service.BuildDecisionAsync(new TurnContext
|
||||||
|
{
|
||||||
|
RawTranscript = "go to sleep",
|
||||||
|
NormalizedTranscript = "go to sleep"
|
||||||
|
});
|
||||||
|
|
||||||
|
Assert.Equal("sleep", decision.IntentName);
|
||||||
|
Assert.Equal("@be/idle", decision.SkillName);
|
||||||
|
Assert.Equal("sleep", decision.SkillPayload!["globalIntent"]);
|
||||||
|
Assert.Equal("global_commands", decision.SkillPayload["nluDomain"]);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task BuildDecisionAsync_TurnAround_MapsToIdleSpinAroundCommand()
|
||||||
|
{
|
||||||
|
var service = CreateService();
|
||||||
|
|
||||||
|
var decision = await service.BuildDecisionAsync(new TurnContext
|
||||||
|
{
|
||||||
|
RawTranscript = "turn around",
|
||||||
|
NormalizedTranscript = "turn around"
|
||||||
|
});
|
||||||
|
|
||||||
|
Assert.Equal("spin_around", decision.IntentName);
|
||||||
|
Assert.Equal("@be/idle", decision.SkillName);
|
||||||
|
Assert.Equal("spinAround", decision.SkillPayload!["globalIntent"]);
|
||||||
|
Assert.Equal("global_commands", decision.SkillPayload["nluDomain"]);
|
||||||
|
}
|
||||||
|
|
||||||
[Fact]
|
[Fact]
|
||||||
public async Task BuildDecisionAsync_NeverMindWithPunctuation_MapsToIdleStopCommand()
|
public async Task BuildDecisionAsync_NeverMindWithPunctuation_MapsToIdleStopCommand()
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -2831,6 +2831,90 @@ public sealed class JiboWebSocketServiceTests
|
|||||||
redirectPayload.RootElement.GetProperty("data").GetProperty("nlu").GetProperty("intent").GetString());
|
redirectPayload.RootElement.GetProperty("data").GetProperty("nlu").GetProperty("intent").GetString());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task ClientAsr_GoToSleep_EmitsIdleSleepRedirect()
|
||||||
|
{
|
||||||
|
await _service.HandleMessageAsync(new WebSocketMessageEnvelope
|
||||||
|
{
|
||||||
|
HostName = "neo-hub.jibo.com",
|
||||||
|
Path = "/listen",
|
||||||
|
Kind = "neo-hub-listen",
|
||||||
|
Token = "hub-sleep-token",
|
||||||
|
Text =
|
||||||
|
"""{"type":"LISTEN","transID":"trans-sleep","data":{"hotphrase":true,"rules":["launch","globals/global_commands_launch"]}}"""
|
||||||
|
});
|
||||||
|
|
||||||
|
var replies = await _service.HandleMessageAsync(new WebSocketMessageEnvelope
|
||||||
|
{
|
||||||
|
HostName = "neo-hub.jibo.com",
|
||||||
|
Path = "/listen",
|
||||||
|
Kind = "neo-hub-listen",
|
||||||
|
Token = "hub-sleep-token",
|
||||||
|
Text = """{"type":"CLIENT_ASR","transID":"trans-sleep","data":{"text":"go to sleep"}}"""
|
||||||
|
});
|
||||||
|
|
||||||
|
Assert.Equal(5, replies.Count);
|
||||||
|
Assert.Equal("LISTEN", ReadReplyType(replies[0]));
|
||||||
|
Assert.Equal("EOS", ReadReplyType(replies[1]));
|
||||||
|
Assert.Equal("SKILL_REDIRECT", ReadReplyType(replies[2]));
|
||||||
|
Assert.Equal("SKILL_ACTION", ReadReplyType(replies[3]));
|
||||||
|
Assert.Equal("SKILL_ACTION", ReadReplyType(replies[4]));
|
||||||
|
|
||||||
|
using var listenPayload = JsonDocument.Parse(replies[0].Text!);
|
||||||
|
var nlu = listenPayload.RootElement.GetProperty("data").GetProperty("nlu");
|
||||||
|
Assert.Equal("sleep", nlu.GetProperty("intent").GetString());
|
||||||
|
Assert.Equal("global_commands", nlu.GetProperty("domain").GetString());
|
||||||
|
Assert.Equal("globals/global_commands_launch", nlu.GetProperty("rules")[0].GetString());
|
||||||
|
|
||||||
|
using var redirectPayload = JsonDocument.Parse(replies[2].Text!);
|
||||||
|
Assert.Equal("@be/idle",
|
||||||
|
redirectPayload.RootElement.GetProperty("data").GetProperty("match").GetProperty("skillID").GetString());
|
||||||
|
Assert.Equal("sleep",
|
||||||
|
redirectPayload.RootElement.GetProperty("data").GetProperty("nlu").GetProperty("intent").GetString());
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task ClientAsr_TurnAround_EmitsIdleSpinAroundRedirect()
|
||||||
|
{
|
||||||
|
await _service.HandleMessageAsync(new WebSocketMessageEnvelope
|
||||||
|
{
|
||||||
|
HostName = "neo-hub.jibo.com",
|
||||||
|
Path = "/listen",
|
||||||
|
Kind = "neo-hub-listen",
|
||||||
|
Token = "hub-spin-token",
|
||||||
|
Text =
|
||||||
|
"""{"type":"LISTEN","transID":"trans-spin","data":{"hotphrase":true,"rules":["launch","globals/global_commands_launch"]}}"""
|
||||||
|
});
|
||||||
|
|
||||||
|
var replies = await _service.HandleMessageAsync(new WebSocketMessageEnvelope
|
||||||
|
{
|
||||||
|
HostName = "neo-hub.jibo.com",
|
||||||
|
Path = "/listen",
|
||||||
|
Kind = "neo-hub-listen",
|
||||||
|
Token = "hub-spin-token",
|
||||||
|
Text = """{"type":"CLIENT_ASR","transID":"trans-spin","data":{"text":"turn around"}}"""
|
||||||
|
});
|
||||||
|
|
||||||
|
Assert.Equal(5, replies.Count);
|
||||||
|
Assert.Equal("LISTEN", ReadReplyType(replies[0]));
|
||||||
|
Assert.Equal("EOS", ReadReplyType(replies[1]));
|
||||||
|
Assert.Equal("SKILL_REDIRECT", ReadReplyType(replies[2]));
|
||||||
|
Assert.Equal("SKILL_ACTION", ReadReplyType(replies[3]));
|
||||||
|
Assert.Equal("SKILL_ACTION", ReadReplyType(replies[4]));
|
||||||
|
|
||||||
|
using var listenPayload = JsonDocument.Parse(replies[0].Text!);
|
||||||
|
var nlu = listenPayload.RootElement.GetProperty("data").GetProperty("nlu");
|
||||||
|
Assert.Equal("spinAround", nlu.GetProperty("intent").GetString());
|
||||||
|
Assert.Equal("global_commands", nlu.GetProperty("domain").GetString());
|
||||||
|
Assert.Equal("globals/global_commands_launch", nlu.GetProperty("rules")[0].GetString());
|
||||||
|
|
||||||
|
using var redirectPayload = JsonDocument.Parse(replies[2].Text!);
|
||||||
|
Assert.Equal("@be/idle",
|
||||||
|
redirectPayload.RootElement.GetProperty("data").GetProperty("match").GetProperty("skillID").GetString());
|
||||||
|
Assert.Equal("spinAround",
|
||||||
|
redirectPayload.RootElement.GetProperty("data").GetProperty("nlu").GetProperty("intent").GetString());
|
||||||
|
}
|
||||||
|
|
||||||
[Fact]
|
[Fact]
|
||||||
public async Task ClientAsr_TurnItDown_EmitsGlobalVolumeDownWithoutCloudSpeech()
|
public async Task ClientAsr_TurnItDown_EmitsGlobalVolumeDownWithoutCloudSpeech()
|
||||||
{
|
{
|
||||||
|
|||||||
Reference in New Issue
Block a user