Работают роботы, счастлив человек. Или как получить задачу в DirectumRX из социальной сети ВКонтакте

41 3


Немного истории

Чат-боты это не что-то новое и инновационное, это хорошо забытое старое. Скорее, новый виток древней как IRC технологии. Впервые чат-боты появились еще в 90-х в популярных в то время онлайн чатах. Их задачей было развлекать скучающую публику. Различные розыгрыши, автоматизированные викторины в чате и так далее. В то время чат-боты были уделом гиков и технарей, которым нравилось создавать что-то новое и интересное. Теперь же чат-бот рассматривается как средство замещения человеческого труда машинным.

Напоминает историю парового двигателя, не так ли? Напомню, что впервые паровой двигатель появился в древней Греции и служил средством увеселения гостей.

Новым толчком к развитию чат-ботов послужили получившие признание социальные сети и всевозможные мессенджеры, а благодаря широкому распространению мобильных устройств мессенджеры в настоящее время стали чуть ли не основным средством общения между людьми.

Социальные сети и мессенджеры идут навстречу чат-ботам и предлагают удобные API, которые можно использовать для создания чат-ботов под любые задачи.

В данной статье будет продемонстрирован один из вариантов чат-ботов, а именно автоматизация приема заказов и обработка их в рамках системы документооборота DirectumRX.

Анализ и проектирование

Определимся с целевыми задачами разрабатываемого чат-бота:

  • чат-бот разрабатывается для вымышленного интернет магазина, который размещается в социальной сети,
  • считаем, что подавляющее большинство целевой аудитории магазина сконцентрирована в социальной сети vk.com,
  • использовать кроссплатформенные инструменты и среду разработки,
  • на стороне DirectumRX создается Роль «Ответственный за прием заказов», и при поступлении заказа ответственное лицо получает задачу с ссылкой на пользователя VK и сообщением о заказе.

В процессе анализа возможных вариантов и последующего упрощения удалось получить схему, представленную ниже:

В качестве входа покупателя используется заранее подготовленная страница VK с возможностью отправки сообщения. Для взаимодействия с VK будем использовать VK_API.

Процесс получения данных из социальной сети отделим от процесса отправки данных в DirectumRX. Такое разделения позволит масштабировать решение, можно подключать к работе новые чат-боты для работы с другими социальными сетями, упрощает код и анализ инцидентов.

В случае, если получен запрос от покупателя на товар или услугу, через некоторый интервал времени скрипт обмена получает информацию из БД, и через утилиту DrxUtil выполняется запуск функции с необходимыми параметрами, которая формирует задачу ответственному за обмен.

После чего ответственный консультант сможет связаться с покупателем через социальную сеть для проработки деталей продажи.

Процесс создания

Этап 1. Подготовка сообщества

В первую очередь необходимо подготовить страницу в VK для возможности использования VK-API и получить ключ доступа к сообществу.


В итоге будет сгенерирован ключ, который мы будем использовать на следующих этапах.

А также необходимо включить получение сообщений в сообществе:

Написание робота

Мозг

В качестве «мозга» чат-бота будем использовать SQLite, так как эта СУБД кроссплатформенная и не требует установки и дополнительных настроек.

Выделим основные таблицы, с которыми будет работать наш робот:

1. Таблица синонимов: в полученном сообщении от пользователя социальной сети выполняется поиск ключевых фраз или словосочетаний, фразы и словосочетания соответствуют определенным кодам реакций. В данном случае код реакции – как бот будет реагировать на входящее сообщение

CREATE TABLE synonims (
syn varchar(512),
code varchar(512)
);

2. Таблица кодов реакций: состоит из четырех столбцов:

  • код реакции,
  • ответ на код реакции,
  • параметр ожидания ответа со стороны пользователя,
  • сообщение в случае получения ответа пользователя (если требуется).
CREATE TABLE codes (
code varchar(512),  
synonims text,
welcome text,
correct text,
incorrect text
);

3. Таблица истории общения. Таблица используется роботом для анализа истории общения с покупателем, а также разработчиками для анализа общения робота для дальнейшей доработки.

CREATE TABLE memory (
userid varchar(512),  
code varchar(512),
status int,
ansver text
);

Прочие внутренности робота

Для разработки чат-бота был выбран язык python по следующим причинам:

  1. высокая скорость разработки,
  2. наличие готовых решений,
  3. возможность разместить чат-бота на любом хостинге сайтов (низкая цена владения),
  4. кроссплатформенность.

Для работы мы будем использовать Python третьей версии и модуль VK_API для работы c api ВКонтакте. Установить модуль можно через pip (одна из утилит python):

pip3 install vk_api

Подключаем необходимые библиотеки:

import vk_api # подключаемый модуль для работы с VK
import time # модуль для работы с датой и временем
import sqltools # функции для работы с базой робота

Используем токен, полученный при настройке сообщества:

session = vk_api.VkApi(token='xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx')

Для удобства создаем функцию, которая будет отправлять сообщение в ВК:

def print_msg(user_id,msg):
    session.method('messages.send', {'user_id':user_id,'message':msg})

Зададим параметры работы с ВКонтакте: будем получаем 100 новых сообщений за последние 60 минут

values = {'out':0,'count':100,'time_offset':60}

Подключаем файл БД:

db = 'src\\mind.db'

Получаем список кодов реакций и словарь синонимов:

codes = sqltools.get_codes(db)
synonims = sqltools.get_synonims(db)

Зацикливаем работу чат-бота. В дальнейшем роботу можно будет давать секретную команду на отключения через ВКонтакте:

working = True
while working:
    resp = session.method('messages.get',values) # получаем сообщение
    if resp['items']:
        values['last_message_id'] = resp['items'][0]['id'] # сдвигаем каретку указывающую на последнее новое сообщение (чтобы повторно не обрабатывать другие сообщения)
    for item in resp['items']:
        body = item['body']	# получаем сообщение покупателя
        body = body.lower()	# будем обрабатывать слова в нижнем регистре
        code = ""
        last = sqltools.get_last_remember(db, item['user_id']) # робот вспоминает, о чем общались с данным пользователем в последний раз
        # если мы ждали ответ на вопрос о заказе
        if (last[2] == 1):
            for c in codes:
                if c[0] == last[1]:
                    # ищем соответствующий код реакции и получаем текст закрывающего сообщения
                    print_msg(item['user_id'],c[2]) # отправляем покупателю текст сообщения
                    sqltools.in_memory(db, item['user_id'], c[0], 3, body, 0) # запоминаем взаимодействие
                    # формируем заказ
                    sqltools.set_order(db, item['user_id'], c[0], body, 'VK', 'https://vk.com/' + str(item['user_id']), 'wait')
        else:
            # если мы не ждем какого-то конкретного ответа
            for syn in synonims:
                if (syn[0] in body): # ищем подходящую реакцию на сообщение покупателя
                    code = syn[1]
            if code != '':  
                for c in codes:
                    if c[0] == code:
                        print_msg(item['user_id'],c[1]) # выводим ответную реакцию на сообщение
                        sqltools.in_memory(db, item['user_id'], code, c[4], body, 0) # запоминаем взаимодействие
            else: # если не нашли подходящий ответ
                for c in codes:
                    if c[0] == 'error':
                        print_msg(item['user_id'],c[1]) # выводим сообщение об ошибке
                        sqltools.in_memory(db, item['user_id'], 'error', c[4], body, 0) # запоминаем взаимодействие

Процесс взаимодействия с RX

Подключаем необходимые библиотеки.

import time 		# модуль для работы с датой и временем
import sqltools 	# функции для работы с базой робота
import rxsynctools	# инструменты для работы с DrxUtil

Задаем константы:

db = 'src\\mind.db'
drxutilpath = 'C:\\Program Files\\Directum Company\\Sungero Development Studio\\Utilities\\DrxUtil'
# зададим пароли, которые будут использоваться для создания задачи в DirecutmRX
drxuser = "Administrator"
drxpass = "11111"

Зацикливаем процесс работы средства синхронизации:

working = True
while working:
    # получаем все заказы, которые еще не были обработаны
    orders = sqltools.get_order_for_sync(db)
    for order in orders:
        print(order)
        # отправляем сообщения в DirectumRX и обрабатываем результат
        result = rxsynctools.chatbot_sync(drxutilpath, drxuser, drxpass, order[5], order[2], order[6], order[4])
        if result == 0:
            # если все успешно, то повторная обработка не требуется
            sqltools.update_order_syncstatus(db, order[0], 'success')
        else:
            # если импорт произошел неуспешно, попытка будет повторяться
            sqltools.update_order_syncstatus(db, order[0], 'error')
    time.sleep(10) # ожидание 10 секунд

Рассмотрим подробнее инструмент для создания новой задачи в DirectumRX (rxsynctools)

Инструмент содержит две функции:

import os
import subprocess
# метод для вызова функции DirectumRX через DrxUtil
def execute_dirrx_function(dirrxpath, user, password, functionname, params):
    if (dirrxpath == "") or (functionname == "") or (user != "") or (password != ""):
        return
    scriptdir = os.getcwd()
    os.chdir(dirrxpath)
    # формируем строку запуска DrxUtil:
    comstr = "drxutil.exe -n %(user)s -p %(password)s --call %(functionname)s %(params)s " % {'user': user,
                                                                                                  'password': password,
                                                                                                  'functionname': functionname,
                                                                                                  'params': params}
   # выполняем строку
    proc = subprocess.Popen(comstr, shell=True, stdout=subprocess.PIPE)
    out = proc.stdout.readlines()
    array = [row.strip() for row in out]
    os.chdir(scriptdir)
    # вывод результатов работы DrxUtil для дальнейшей обработки
    return array

# метод формирования задачи в DirectumRX
def chatbot_sync(dirrxpath, user, password, SocialNetwork, UserID, UserURI, Request):
    # используем решение ARD.ChatBotSolution и функцию  ARD.ChatBot.Module.ProcessingData
    functionname = "ARD.ChatBot.Module.ProcessingData"
    # задаем параметры
    params = " %(SocialNetwork)s %(UserID)s \"%(UserURI)s\" \"%(Request)s\" " % {'SocialNetwork':SocialNetwork,'UserID':UserID,'UserURI':UserURI,'Request':Request}
    # выполняем функцию и обрабатываем результат
    result = execute_dirrx_function(dirrxpath, user, password, functionname, params)
    print(result[1])
    if ("success" in result[1].decode(encoding='windows-1252')):
        return 0
    else:
        return 1    

execute_dirrx_function — реализует процедуру вызова необходимой функции в DirectumRX с параметрами.

chatbot_sync — подготовка параметров и вызов необходимой функции DirectumRX.

Доработки на стороне DirectumRX

Для формирования задачи на стороне DirectumRX создано специализированное решение ARD.ChatBotSolution с модулем ChatBot.

Для автоматизации процесса создания задач созданы ряд клиентских и серверных функций.

Клиентские функции (выполняются на стороне DrxUtil)

    /// <summary>
    /// Обрабатывает поступающие данные от чат-бота.
    /// </summary>
    /// <param name="SocialNetwork">Идентификатор социальной сети.</param>
    /// <param name="UserID">ИД пользователя социальной сети.</param>
    /// <param name="UserURI">Ссылка на пользователя социальной сети.</param>
    /// <param name="Request">Запрос, который должен обработать ответственный.</param>
    /// <param name="Theme">Тема сообщения.</param>
    public static void ProcessingData(string SocialNetwork, string UserID, string UserURI, string Request, string Theme)
    {
	// выполняется вызов серверной функции  GetProcessingData
    	ChatBot.Functions.Module.Remote.GetProcessingData(SocialNetwork, UserID, UserURI, Request);
    }
    
    /// <summary>
    /// Создает предопределенные данные модуля.
    /// </summary>
    public virtual void Initialize()
    {      
      // Создание роли специалиста сервисного подразделения.
      Logger.Debug("Init: Create roles.");
      // создаем необходимую роль, которую будем впоследствии использовать для назначени ответственного за получение сообщений из ВК
      Functions.Module.Remote.CreateRoles();
    }

Серверные функции (выполняются на стороне сервера DirectumRX)

Обрабатываем запрос поступивший от чат-бота:

    /// <summary>
    /// Обрабатывает запрос поступивший от чат-бота. 
    /// </summary>
    /// <returns>.</returns>
    [Remote]
    public static int GetProcessingData(string SocialNetwork, string UserID, string UserURI, string Request, string Theme)
    {
      string Text = "";
      Text = "Социальная сеть: " + SocialNetwork + "\n" + 
      	     "Идентификатор пользователя: " + UserID + "\n" +
      	     "Ссылка на пользователя: " + UserURI + "\n" +
      	     "Тема: " + Theme + "\n" +
      		 "Сообщение: " + "\n" +
      		 Request;
      return SendSimpleTask(Text);
    }

Отправляем простую задачу соответствующей роли:

    /// <summary>
    /// Отправляет простую задачу в соответствии с настроенными параметрами отправки.
    /// </summary>
    public static int SendSimpleTask(string Text)
    {
   	  var role = Roles.GetAll().FirstOrDefault(r => r.Sid == Constants.Module.RoleGuid.ChatBotRole);
      if (role == null)
        return 0;
      var performer = role.RecipientLinks.FirstOrDefault().Member;
      if (performer == null)
      	return 0;
      
      // Создание простой задачи.  
      var task = Sungero.Workflow.SimpleTasks.Create("Обработать сообщение из социальной сети",performer);
      task.Deadline = Calendar.Now.AddDays(1);  
      task.ActiveText = Text;
      task.Start();
      return task.Id;
    }

Создаем предопределенные роли (ответственный по обработке сообщений от робота):

    /// <summary>
    /// Создать предопределенные роли.
    /// </summary>
    [Remote]
    public static void CreateRoles()
    {
      Logger.Debug("Init: Create Default Roles");
      
      Sungero.Docflow.PublicFunctions.Module.CreateRole("Обработчик сообщений чат-бота", "Обработчик сообщений чат-бота", Constants.Module.RoleGuid.ChatBotRole);
    }

Пример использования робота

Прежде чем запустить разработанные скрипты, необходимо заполнить «мозг» нашего робот необходимой информацией. Для наполнения БД будем использовать инструмент SQLiteStudio.

В зависимости от наполнения таблицы с кодами реакций можно применять робота для любых задач.

Допустим наша мнимая организация продает красные и синие коробки, а также может подготовить коробку на заказ.

Заполним коды реакций и текст.

В поле Code будут находиться коды реакций, в поле welcome будут находиться текстовые сообщения, которые выводятся при получении кода реакции. В поле correct будут находиться сообщения, в случае получения ответа на вопрос робота (если реакция является вопросом).

Является реакция вопросом или ответом – за это отвечает параметр WaitAnsw. 1 – вопрос, робот ждет ответа. 0 – робот не ждет ответ.


Затем наполняем справочник синонимов:


База данных готова к работе.

Для тестирования робота было создано специальное закрытое сообщество «Мой робот». Ниже привожу текст беседы с роботом.

Кейс 1: покупатель решил заказать синие коробки, робот будет предлагать акцию и получать заказ.


После отработки скриптов на стороне DirectumRX ответственному лицу формируется задача:


Кейс 2: покупатель решил заказать услугу оформления коробки


После отработки скриптов на стороне DirectumRX ответственному лицу формируется задача:


В итоге получили робота, который может рекламировать услуги компании 24х7 и собирать заказы для дальнейшей обработки.

Итоги

Мессенджеры и социальные сети — это новый канал коммуникации бизнеса с клиентом, а боты это средство автоматизации части этих коммуникаций.

Как видим из представленного выше исследования, за короткий срок можно создать простого бота и интегрировать его с существующими системами автоматизации.

Робот должен быть универсальным, так как заказчики находятся в различных социальных сетях. Подобный робот может автоматизировать работу со всеми социальными сетями одновременно, потребуется только создать скрипт для работы с API какой-либо другой социальной сети или мессенджера.

В следующей статье рассмотрим другие кейсы, в которых можно использовать данного робота с небольшой доработкой.

Исходные коды разработанного робота можно получить на gitlab по ссылке https://gitlab.com/ardashev/ChatBotRX.git. Для получения исходных кодов необходимо быть авторизованным пользователем на сервисе gitlab.

41
Авторизуйтесь, чтобы оценить материал.
8
Андрей Полкачев

Здорово!

Для WhatsApp кто-нибудь делал чат-боты?

Андрей Ардашев

Андрей, для WhatsApp есть api https://blog.cloudrail.com/whatsapp-api-how-to-use-the-whatsapp-chat-api/.
По всей видимости, сделать бота можно сделать аналогичным способом.

Денис Евграфов

Андрей, отличное решение, в каких бизнес-процессах используете? Недавно тоже написал бота, для создания эл. документов в системе, есть одна проблема! Может вы мне подскажете, как вы решили проблему с "прощанием пользователя", как я вижу по скринам последнее сообщение отправляет бот, в котором говорится о результате выполнения запрошенной операции, но если пользователь начинает отвечать, что то вроде "спасибо" или "пока". Ведь всех пользователей не научишь работать по четкому алгоритму, может какие то переменные для хранения информации о пользователе хранить? Но тоже не всегда верно, так как пользователь может повторить операцию или выполнить другую, если бот многофункционален. Дай те совет, пожалуйста, в какую сторону копать?

Авторизуйтесь, чтобы написать комментарий