Разработка сценария
На этом этапе мы напишем сценарий для бота, рассмотрим использование слот-филлинга и разные варианты обработки случайных значений.
Создание сценария
Создайте файл main.sc
в папке src
. В нем будет сценарий работы бота:
require: slotfilling/slotFilling.sc
module = sys.zb-common
require: common.js
module = sys.zb-common
theme: /
state: Правила
q!: $regex</start>
intent!: /Давай поиграем
a: Игра больше-меньше. Загадаю число от 0 до 100, ты будешь отгадывать. Начнём?
go!: /Правила/Согласен?
state: Согласен?
state: Да
intent: /Согласие
go!: /Игра
state: Нет
intent: /Несогласие
a: Ну и ладно! Если передумаешь — скажи "давай поиграем"
state: Игра
# сгенерируем случайное число и перейдем в стейт /Проверка
script:
$session.number = $jsapi.random(100) + 1;
# $reactions.answer("Загадано {{$session.number}}");
$reactions.transition("/Проверка");
state: Проверка
intent: /Число
script:
# сохраняем введенное пользователем число
var num = $parseTree._Number;
# проверяем угадал ли пользователь загаданное число и выводим соответствующую реакцию
if (num == $session.number) {
$reactions.answer("Ты выиграл! Хочешь еще раз?");
$reactions.transition("/Правила/Согласен?");
}
else
if (num < $session.number)
$reactions.answer(selectRandomArg(["Мое число больше!", "Бер и выше", "Попробуй число больше"]));
else $reactions.answer(selectRandomArg(["Мое число меньше!", "Подсказка: число меньше", "Дам тебе еще одну попытку! Мое число меньше."]));
state: NoMatch || noContext = true
event!: noMatch
random:
a: Я не понял.
a: Что вы имеете в виду?
a: Ничего не пойму
В начале сценария под тегом require
подключаем дополнительные модули slotFilling
и common.js
. Их использование мы рассмотрим в разделе Структура сценария.
Сценарий бота состоит из следующих основных стейтов:
Правила
— начало работы. Бот приветствует пользователя, предлагает сыграть в игру и объясняет правила.Игра
— начало игры. Здесь бот загадывает случайное число.Проверка
— стейт содержит логику проверки введенного пользователем числа и вывода сообщения в зависимости от результата проверки.NoMatch
— стейт, предусмотренный для случаев, когда сообщение пользователя не подходит ни под один установленный стейт.
Структура сценария
Правила
В стейте Правила
запускается сценарий. Бот посылает приветственное сообщение и предлагает сыграть в игру.
state: Правила
q!: $regex</start>
intent!: /Давай поиграем
a: Игра больше-меньше. Загадаю число от 0 до 100, ты будешь отгадывать. Начнём?
go!: /Правила/Согласен?
state: Согласен?
state: Да
intent: /Согласие
go!: /Игра
state: Нет
intent: /Несогласие
a: Ну и ладно! Если передумаешь — скажи "давай поиграем"
Предусмотрим переход в стейт Правила
из любого другого стейта по фразе давай поиграем
. Для этого создадим интент /Давай поиграем
.
Перейдите на вкладку NLU > Интенты, расположенную в боковом меню. Создайте интент и добавьте в поле Тренировочные фразы следующие фразы: хочу играть
, давай поиграем
, играть
.
Далее с помощью тега go!
осуществляется переход во вложенный стейт Согласен?
. Затем в зависимости от ответа пользователя бот переходит в следующие стейты /Согласие
или Несогласие
.
Несогласие
Отрицательный ответ обрабатывается в интенте /Несогласие
. Создайте интент и добавьте в поле Тренировочные фразы фразы, несущие отрицательную окраску. Например: не буду
, не хочу
, нет
. Тогда, если бот получит одно из таких сообщений от пользователя, сработает интент /Несогласие
.
Дополните тренировочные фразы своими вариантами. Чем больше вариаций фраз, тем больше вероятность того, что ваш бот сможет правильно среагировать на сообщения пользователя.
Согласие
Если ответ пользователя оказался положительным, выполняется переход в стейт Да
. Создайте интент /Согласие
и добавьте как можно больше тренировочных фраз, выражающих согласие. Например: да
, согласен
, начнем
, хочу
. Теперь, если бот получит одно из таких сообщений от пользователя, сработает интент /Согласие
.
Число
Для перехода в следующий стейт нам важно получить от пользователя число. Если он не введет его, то бот отправит сообщение с просьбой ввести число. Для этого воспользуемся слот-филлингом и создадим слот Number
. Слот-филлинг используется в том случае, когда боту необходимо получить какую-то конкретную информацию от пользователя, без которой он не может дальше работать. В нашем случае, это число.
Настроим параметры слота. Каждый слот имеет поле Сущность. Оно определяет тип данных, которые попадут в слот. Будем использовать системную сущность @duckling.number
с помощью сервиса Duckling.
Чтобы подключить системную сущность Duckling
, перейдите на вкладку NLU > Сущности > Системные, расположенную в боковом меню. Найдите в списке доступных сущностей @duckling.number
и переведите переключатель в активное положение.
Вернитесь к настройке интента /Согласие
. В поле Сущность установите @duckling.number
. Переведите переключатель Обязательно в активное положение и заполните поле Вопросы уточняющими вопросами. Например, Я загадал число. Твоя догадка?
, Предположи число
.
Уточняющий вопрос будет отправлен ботом в случае, когда в сообщении пользователя не был распознан обязательный слот. Пока бот не получит число, он будет продолжать отправлять по очереди уточняющие вопросы столько, скол ько мы указали при настройке конфигурационного файла.
Заполненный слот будет передан в переменную $parseTree._Number
в стейт Проверка
.
Игра
По правилам бот случайно загадывает число. Для этого напишем скрипт, который сначала загадает случайное число, а затем вызовет переход в следующий стейт Проверка
.
state: Игра
script:
# сгенерируем случайное число
$session.number = $jsapi.random(100) + 1;
# перейдем в стейт /Проверка
$reactions.transition("/Проверка");
Случайный выбор числа
Как уже было сказано ранее, по правилам бот случайно загадывает число от 0 до 100. Для этого воспользуемся генератором случайных чисел с помощью встроенного сервиса $jsapi.random()
. Метод возвращает целочисленные значения от 0
до max
(не включая max
), поэтому в качестве параметра укажем 100
и прибавим к получившемуся случайному значению 1
. Запишем в тег script
команду:
$session.number = $jsapi.random(100) + 1;
В JS API переменная $session
является объектом для сохранения сессионных данных. Присвоим переменной $session.number
функцию случайного выбора числа. В дальнейшем будем сравнивать число, хранящееся в $session.number
, с числом, введенным пользователем.
Чтобы убедиться, что бот действительно загадывает числа в случайном порядке, выведем загаданное число на экран в виде сообщения Загадано *число*
. Вставьте в скрипт следующую строку:
$reactions.answer("Загадано {{$session.number}}");