6. Способы интеграции

Существует два основных подхода для интеграции с Synergy:

  • Прямая интеграция — интеграционные модули разрабатываются с использованием API Synergy и интегрируемых систем. Синхронизация данных между системами и координация обмена между ними остаётся за разработчиком интеграционного модуля
  • Событийная интеграция — когда какая-либо из подсистем Synergy генерирует различные события, связанные с какими-либо данными. Обработчики этих событий (на стороне Synergy) при необходимости преобразовывают данные событий и передают их интегрируемой системе через какой-либо транспортный уровень

6.1. Прямая интеграция

ARTA Synergy предоставляет API для доступа к своим функциям с помощью rest сервисов. Описание методов REST API можно найти в данном разделе.

Авторизация для всех методов API — Basic HTTP.

6.2. Событийная интеграция

Под «событием» мы будем подразумевать сообщение о каком-либо изменении в ARTA Synergy, содержащее тип события и минимально необходимые для получения связанной с событием информации либо воздействия на Synergy данные. Обработчик события (или событий) — программный модуль, читающий сообщения о событиях из JMS Queue или JMS Topic и осуществляющий, при необходимости, доступ к экземпляру Synergy, сгенерировавшему сообщение, с помощью API Synergy.

Обработчик событий является отдельным от ARTA Synergy приложением, которое может работать как на том же сервере приложений, что и ARTA Synergy, так и на удалённом.

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

Обработчик событий может обрабатывать как конкретное событие (например, event.registers.formdata.add), так и класс событий (например, event.registers.*).

Обработка события может происходить в 3 этапа:

  1. Получение события
  2. Получение и преобразование необходимых обработчику данных
  3. Передача сформированного пакета данных далее (опционально)

ARTA Synergy генерирует событие в случае, если для этого события настроены обработчики. Обработчики событий настраиваются в конфигурационном файле ${jboss.home}/standalone/configuration/arta/api-observation-configuration.xml.

Примечание

При установке Synergy файл {$jboss.home}/standalone/configuration/arta/api-observation-configuration.xml по умолчанию не создается. Создаете файл api-observation-configuration.xml в директории {$jboss.home}/standalone/configuration/arta/ с содержимым:

<?xml version="1.0"?>
<configuration>
<!-->список листенеров<-->
</configuration>

Указываете владельца файла:

chown -R jboss:synergy /opt/synergy/jboss/standalone/configuration/arta/api-observation-configuration.xml

Затем можете добавлять листенеры в файл.

Сообщение, помещаемое в очередь JMS, представляет собой экземпляр javax.jms.TextMessage. Тело сообщения зависит от типа события, его описание можно посмотреть ниже среди описаний типов событий. Каждое событие содержит свойство api_event, указывающее на тип события, вызвавшего его (содержимое тега <event>event.registers.formdata.add</event> в конфигурационном файле).

Например:

<configuration>
    <listener>
        <queue>java:jboss/queues/Synergy/UsersQueue</queue>
        <event>event.users.*</event>
    </listener>
    <listener>
        <queue>java:jboss/queues/Synergy/RegisterCreateDocQueue</queue>
        <event>event.registers.formdata.add</event>
    </listener>
</configuration>

В этом примере настроены обработчики:

  1. java:jboss/queues/Synergy/UsersQueue для всех событий класса event.users.*, т.е. всех событий, связанных с пользователями: event.users.account.change, event.users.formdata.change, event.users.account.add и т.д.
  2. java:jboss/queues/Synergy/RegisterCreateDocQueue для события добавления записи реестра event.registers.formdata.add.

Рассмотрим, например, код обработчика очереди UsersQueue:

@MessageDriven(name = "UsersQueue", activationConfig = {
    @ActivationConfigProperty(propertyName = "destinationType", propertyValue = "javax.jms.Queue"),
    @ActivationConfigProperty(propertyName = "destination", propertyValue = "java:jboss/queues/Synergy/UsersQueue"),
    @ActivationConfigProperty(propertyName = "reconnectAttempts", propertyValue = "32"),
    @ActivationConfigProperty(propertyName = "reconnectInterval", propertyValue = "4000"),
    @ActivationConfigProperty(propertyName = "acknowledgeMode", propertyValue = "Auto-acknowledge") })
public class UsersMessagesListener implements MessageListener {

    public void onMessage(Message message) {
        //Получаем идентификатор пользователя, для которого
        //сгенерировано событие
        String userID = ((TextMessage) message).getText();
        //Получаем тип события
        String eventType = message.getStringProperty("api_event");

        //Выполнение действия по получению дополнительных данных через API
        //и прочих операций, зависящих от условий решаемой задачи
    }
}

В проекте blocking-process-template реализован пример обработчика очереди.

Ниже описаны типы событий, которые могут быть сгенерированы ARTA Synergy.

Для события [event.orgstructure.department.formdata.change] - идентификатор подразделения, для события [event.orgstructure.position.formdata.change] - идентификатор должности, для события [event.users.formdata.change] - идентификатор пользователя будет передаваться как основной параметр, остальные как свойства. Получить их можно следующим образом:

public void onMessage(Message message) {
    //Получение идентификатора пользователя/должности/подразделения (В зависимости от события на которое подписаны)
    String userID = ((TextMessage) message).getText();
    //Получаем идентификатор формы
    String formUUID = message.getStringProperty("formUUID");
}

6.3. Блокирующий процесс

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

  • при использовании блокирующего процесса маршрут реестра дожидается ответа о результате выполнения операции внешним модулем
  • блокирующий процесс может завершиться положительно или отрицательно, что повлияет на дальнейшую работу маршрута (Если блокирующий процесс завершится отрицательно — процесс остановится, если положительно — то продолжит работу дальше)

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

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

6.3.1. Конфигурация блокирующего процесса

Для того, чтобы добавить блокирующий процесс, необходимо выполнить следующие действия:

  1. Добавить процесс с в маршрут реестра в конфигураторе:

    _images/blocking-add.png

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

  2. Создать очередь JMS для блокирующего процесса. Для этого необходимо в конфигурационный файл (в стандартной установке это /opt/synergy/jboss/standalone/configuration/standalone-onesynergy.xml) в секцию <subsystem xmlns="urn:jboss:domain:messaging:1.2"> добавить:

    <jms-queue name="ExampleQueue">
        <entry name="java:jboss/queues/Integration/ExampleQueue"/>
        <durable>true</durable>
    </jms-queue>
    
  3. Связать очередь и процесс через конфигурационный файл {$jboss.home}/standalone/configuration/arta/api-observation-configuration.xml, добавив в него следующее:

    <listener>
         <queue>java:jboss/queues/Integration/ExampleQueue</queue>
         <event>event.blocking.example</event>
    </listener>
    

Обратите внимание, что название блокирующего процесса, указанное в маршруте в конфигураторе должно быть равно значению тега в конфигурационном файле api-observation-configuration.xml (в данном примере: event.blocking.example) и название очереди должно совпадать со значением тега queue конфигурационного файла api-observation-configuration.xml (в данном примере: java:jboss/queues/Integration/ExampleQueue)

Сообщение, передаваемое в очередь, является экземпляром TextMessage. Содержимым сообщения является объект JSON с полями:

  1. dataUUID — идентификатор данных по форме записи реестра
  2. executionID — идентификатор блокирующего процесса
  3. documentID — идентификатор документа реестра

После того, как модуль обратится к внешней системе и выполнит необходимые действия, он должен вызвать метод API Synergy для того, чтобы возвратить результат выполнения процесса и продолжить работу маршрута. Для того, чтобы это сделать, необходимо вызвать метод API rest/api/processes/signal.

Примечание

Сигнал блокирующему процессу для его разблокировки/блокировки нужно отправлять после того, как этот процесс был запущен, то есть после того как транзакция с запуском процесса была завершена. Для этого, перед отправкой сигнала, проверяйте на наличие такого процесса в БД. В противном случае, блокирующий процесс может завершиться в транзакции, но в маршруте нет.

В примере кода ниже разблокировка маршрута осуществляется в методе onMessage. Если время выполнения действия значительно или зависит от внешних факторов (например, доступность интегрируемой системы, или необходимость ввода пользователем данных в интегрируемой системе), то разблокировка маршрута может произойти позже, в любой другой момент времени из другого метода, а сам метод onMessage должен завершиться без ошибок, «запомнив» переданные параметры.

package kz.arta.synergy.samples.processes.blocking;

import com.sun.org.apache.xerces.internal.impl.dv.util.Base64;
import org.codehaus.jackson.JsonFactory;
import org.codehaus.jackson.JsonParser;
import org.codehaus.jackson.JsonToken;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.jms.Message;
import javax.jms.MessageListener;
import javax.jms.TextMessage;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;

/**
 * <p><Пример блокирующего процесса</p>
 */
@MessageDriven(name = "ExampleQueue", activationConfig = {
    @ActivationConfigProperty(propertyName = "destinationType", propertyValue = "javax.jms.Queue"),
    @ActivationConfigProperty(propertyName = "destination", propertyValue = "java:jboss/queues/Integration/ExampleQueue"),
    @ActivationConfigProperty(propertyName = "reconnectAttempts", propertyValue = "32"),
    @ActivationConfigProperty(propertyName = "reconnectInterval", propertyValue = "4000"),
    @ActivationConfigProperty(propertyName = "acknowledgeMode", propertyValue = "Auto-acknowledge") })
public class BlockingQueueListener implements MessageListener {

    public void onMessage(Message message) {

        String dataUUID = null;
        String executionID = null;
        String documentID = null;

        if (!(message instanceof TextMessage)){
            return;
        }

        try {

            JsonFactory factory = new JsonFactory();
            JsonParser parser = factory.createJsonParser(((TextMessage) message).getText());
            JsonToken token = null;

            while ((token = parser.nextToken()) != null) {
                if (token == JsonToken.FIELD_NAME) {
                    String fieldName = parser.getText();
                    parser.nextToken();
                    String value = parser.getText();
                    if (fieldName.equals("dataUUID")){
                        dataUUID = value;
                    } else if (fieldName.equals("executionID")){
                        executionID = value;
                    } else if (fieldName.equals("documentID")){
                        documentID = value;
                    }
                }
            }

         //Выполнение каких-либо действий
         ….......

            //Разблокировка маршрута

            String address = "http://127.0.0.1:8080/Synergy";
            String login = "1";
            String password = "1";
            String signal = "got_agree";
            boolean isSuccess = false;

            try {
                URL url = new URL(address + "/rest/api/processes/signal?signal=" + signal + "&executionID=" + executionID + "&param1=resolution&value1=signal_is_" + signal);

                HttpURLConnection conn = (HttpURLConnection) url.openConnection();
                conn.setRequestMethod("GET");
                conn.setRequestProperty("Accept", "application/json; charset=utf-8");

                String encoded = Base64.encode((login + ":" + password).getBytes());
                conn.setRequestProperty("Authorization", "Basic " + encoded);

                String output;
                StringBuffer result = new StringBuffer();

                BufferedReader br = new BufferedReader(new InputStreamReader((conn.getInputStream())));

                while ((output = br.readLine()) != null) {
                    result.append(output);
                }

                conn.disconnect();

                JsonFactory factory = new JsonFactory();
                JsonParser parser = factory.createJsonParser(result.toString());
                JsonToken token = null;

                while ((token = parser.nextToken()) != null) {
                    if (token == JsonToken.FIELD_NAME) {
                        String fieldName = parser.getText();
                        token = parser.nextToken();
                        if (fieldName.equals("errorCode") && parser.getText().equals("0")){
                            isSuccess = true;
                        }
                    }
                }
            } catch (Exception exc){
                logger.error(exc.getMessage(), exc);
            }

        } catch (Exception exc){
            logger.error(exc.getMessage(), exc);
        }
    }
}

6.4. Дополнительный обработчик для стандартного процесса

Цель данного вида интеграции — дать возможность повлиять на запуск стандартного процесса и, при необходимости, прервать его.

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

Обработчик может быть применён к процессам:

  • «работа» (assignment-single)
  • «согласование» (agreement-single)
  • «утверждение» (approval-single)
  • «ознакомление» (acquaintance-single)
  • «отправка документа» (send-document)
  • «общий процесс при запуске по формам» (common-process-by-form)
  • «отправка документа по форме» (send-document-by-form)

Обработчик представляет собой Java-класс, реализующий интерфейс

kz.arta.synergy.integration.api.bp.StartHandlerIF

Данный интерфейс находится в библиотеке integration-api.jar, которую можно найти в установленном экземпляре ARTA Synergy в директории /opt/synergy/jboss/standalone/deployments/Synergy.ear/lib.

Интерфейс содержит два метода:

  • makeDecision() — проверяет возможно ли выполнение процесса
  • getResolution() — возвращает текст, который должен быть записан в ход исполнения

Более подробную информацию о полях методов можно посмотреть в javadoc к этим методам, которые доступны в integration-api.jar (библиотека содержит и скомпилированные классы, и исходный код).

Установка обработчика для процесса осуществляется с помощью конфигурационного файла ${jboss.server.config.dir}/arta/process-handlers-configuration.xml, имеющего следующий формат:

<?xml version="1.0" encoding="UTF-8"?>
<process-handlers-configuration
  xmlns="http://www.arta.kz/xml/ns/ai"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://www.arta.kz/xml/ns/arta
  http://www.arta.kz/xml/ns/ai/process-handlers-configuration .xsd">
 <handlers>
     <handler>
         <process>assignment-single</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
     <handler>
         <process>agreement-single</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
     <handler>
         <process>approval-single</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
     <handler>
         <process>acquaintance-single</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
     <handler>
         <process>send-document</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
 </handlers>
</process-handlers-configuration>

Обработчики выполняются последовательно до тех пор, пока метод makeDecision() одного из них не вернет false, после этого процесс прерывается.

Библиотеку, содержащую обработчик необходимо скопировать в папку /opt/synergy/jboss/standalone/deployments/Synergy.ear/lib.

После копирования библиотеки обработчика и изменения файла process-handlers-configuration.xml необходимо перезапустить JBoss.

Внимание

Процесс common-process-by-form запускает процессы agreement-single, approval-single, acquaintance-single, assignment-single (подпроцессы). Поэтому, если обработчик будет запрещать выполнение подпроцесса и при этом разрешать выполнение процесса common-process-by-form, то подпроцессы все равно будут прерваны. Аналогично, если выполнение common-process-by-form разрешено, а выполнение подпроцесса запрещено, подпроцессы будут прерваны.

6.4.1. Пример использования

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

Для установки внешнего модуля из репозитория необходимо установить пакет arta-synergy-ext-sendcontrol.

Далее на остановленном JBoss в конфигурационном файле ${jboss.server.config.dir}/arta/process-handlers-configuration.xml необходимо прописать следующие обработчики процесса:

<?xml version="1.0" encoding="UTF-8"?>
<process-handlers-configuration
  xmlns="http://www.arta.kz/xml/ns/ai"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://www.arta.kz/xml/ns/arta
  http://www.arta.kz/xml/ns/ai/process-handlers-configuration .xsd">
 <handlers>
     <handler>
         <process>assignment-single</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
     <handler>
         <process>agreement-single</process>
         <handler-providers>kz.arta.synergy.ext.blocking.SendControlHandler</handler-providers>
     </handler>
 </handlers>
</process-handlers-configuration>

Установка групп (каким группам пользователей Synergy) разрешать либо блокировать процессы осуществляется с помощью конфигурационного файла ${jboss.server.config.dir}/arta/ext/send-control.xml. Пример настройки:

<?xml version="1.0" encoding="UTF-8"?>
<send-control>

    <!--
        Идентификаторы групп, членам которых разрешено отправлять
        что-либо из блоков `deny`
    -->
    <from>
        <allow>35</allow>
    </from>

    <!--
        Идентификаторы групп, членам которых могут отправлять что-либо
        только пользователи групп из блоков `allow`, если таковые есть.
        В противном случае, никто ничего этим пользователям отправить
        не сможет.
    -->
    <to>
        <deny comment="Вы не можете отправлять что-либо на согласование данному пользователю">111</deny>
    </to>
</send-control>

6.5. Способы авторизации в ARTA Synergy

REST API ARTA Synergy доступно только авторизованным пользователям. Тип авторизации — BASIC HTTP. Методы API выполняются от имени того пользователя, который авторизован. Имеются следующие типы авторизации:

6.5.1. Авторизация по логину и паролю

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

  • Приложение предоставляет альтернативный интерфейс к некоторым модулям Synergy (мобильное приложение, десктопный клиент для хранилища)
  • Приложение представляет собой server-side утилиту для синхронизации, для которого создан выделенный пользователь, и его логин и пароль хранятся в конфигурационном файле на сервере.

Для реализации данного типа авторизации надо передать в запросе заголовок Authorization со значением:

"Basic " + Base64("login" + ":" + "password")

Например:

Логин Administrator
Пароль 123456
Значение заголовка Basic QWRtaW5pc3RyYXRvcjoxMjM0NTY=

Пример кода на JAVA:

String login = "Administrator";
String password = "123456";

HttpResponse<String> response = Unirest.get("http://demo.arta.kz/Synergy/rest/api/admin/db/current_version")
.header("authorization", Base64.getEncoder().encodeToString((login + ":" + password).getBytes(‌"UTF‌​-8"​)))
.asString();

Пример кода на JavaScript (jQuery):

var login = "Administrator";
var password = "123456";

var settings = {
  "async": true,
  "crossDomain": true,
  "url": "http://demo.arta.kz/Synergy/rest/api/admin/db/current_version",
  "method": "GET",
  "headers": {
    "authorization": ("Basic " + btoa(login + ":" + password))
  }
}

$.ajax(settings).done(function (response) {
  console.log(response);
});

Пример кода на PHP:

<?php

$login = "Administrator";
$password = "123456";

$request = new HttpRequest();
$request->setUrl('http://demo.arta.kz/Synergy/rest/api/admin/db/current_version');
$request->setMethod(HTTP_METH_GET);

$request->setHeaders(array(
  'authorization' => "Basic " . base64_encode("$login:$password")
));

try {
  $response = $request->send();

  echo $response->getBody();
} catch (HttpException $ex) {
  echo $ex;
}

6.5.2. Сессионная авторизация

Сессионная авторизации используется для встроенных WEB-модулей. При cессионной авторизации также используется тип — BASIC HTTP, но в качестве логина пользователя необходимо использовать значение $session и в качестве пароля — полученное значение sso_hash.

Таким образом заголовок Authorization должен иметь значение:

"Basic " + Base64("$session" + ":" + "sso_hash")

Например:

Значение sso_hash D3RONfC52dtJO5XgDyn5qUMv
Значение заголовка Basic JHNlc3Npb246RDNST05mQzUyZHRKTzVYZ0R5bjVxVU12

Получить значение sso_hash авторизованного пользователя можно следующими способами:

  1. В случае если приложение представляет собой Внешний WEB-модуль, получить значение sso_hash можно из строки запроса.

    Пример кода на JavaScript (jQuery):

    function getURLParameter(name) {
      return decodeURIComponent((new RegExp('[?|&]' + name + '=' + '([^&;]+?)(&|#|;|$)')
      .exec(location.search) || [null, ''])[1]
      .replace(/\+/g, '%20')) || null;
    }
    
    var settings = {
      "async": true,
      "crossDomain": true,
      "url": "http://demo.arta.kz/Synergy/rest/api/admin/db/current_version",
      "method": "GET",
      "headers": {
        "authorization": ("Basic " + btoa("$session" + ":" + getURLParameter('sso_hash')))
      }
    }
    
    $.ajax(settings).done(function (response) {
      console.log(response);
    });
    
  2. С помощью переменной окружения $CURRENT_USER основного WEB-приложения Synergy, которая представляет собой JSON-объект следующего вида:

    {
      "id": "Идентификатор текущего пользователя",
      "sso_hash": "hash-сумма для идентификации пользователя",
      "surname": "Фамилия текущего пользователя",
      "name": "Имя текущего пользователя",
      "patronymic": "Отчество текущего пользователя"
    }
    

    Пример кода на JavaScript (jQuery):

    var settings = {
      "async": true,
      "crossDomain": true,
      "url": "http://demo.arta.kz/Synergy/rest/api/admin/db/current_version",
      "method": "GET",
      "headers": {
        "authorization": ("Basic " + btoa("$session" + ":" + $CURRENT_USER.sso_hash))
      }
    }
    
    $.ajax(settings).done(function (response) {
      console.log(response);
    });
    

    Примечание

    Данный способ можно использовать только если код исполняется в основном приложении Synergy. Например, приложение представляет собой Внешний модуль-компонент .

6.5.3. Авторизация по ключам

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

rest/api/person/generate_auth_key

Этот вызов назначает ключ тому пользователю, от имени которого выполняется.

Параметр user_token_expire_interval регулирует интервал устаревания ключей авторизации. Пример настройки интервала:

insert into options (id, value) values ('user_token_expire_interval', '5256000'); -- 10 лет

Примечание

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

Создать ключ можно только для существующего WEB-модуля, так как для этого требуется идентификатор приложения.

Совет

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

Использование этого ключа для авторизации аналогично использованию сессионного ключа. Тип авторизации Basic HTTP, в качестве логина пользователя надо использовать строку $key, в качестве пароля — полученный с помощью API ключ.

Таким образом заголовок Authorization должен иметь значение:

"Basic " + Base64("$key" + ":" + "значение_ключа")

Например:

Значение ключа MS03Y2Q0ZGU3YS0zYjRkLTQ2NjgtYWIyOC0zZDI1YzgxZGNmOGZfMjAxMy0xMC0zMSAxNzo0Mg==
Значение заголовка Basic JGtleTpNUzAzWTJRMFpHVTNZUzB6WWpSa0xUUTJOamd0WVdJeU9DMHpaREkxWXpneFpHTm1PR1pmTWpBeE15MHhNQzB6TVNBeE56bzBNZz09

6.6. Внешний WEB-модуль

Web-приложение внешнего модуля открывается в iframe в окне основного приложения. При этом рабочая область внешнего модуля занимает всю область страницы, кроме панели меню и панели задач:

_images/web-module.png

Внешний WEB-модуль

Для добавления нового модуля нужно перейти в

Конфигуратор ‣ Настройки системы ‣ Управление модулями ‣ Внешние модули

и нажать на кнопку «Добавить».

_images/web-modules.png

Внешние модули

В открывшемся окне нужно заполнить следующие поля:

  • «Название» - название модуля в соответствующем интерфейсе.

  • «Код» - поле должно содержать уникальное значение.

  • «Адрес приложения» - поле для ввода URL.

  • «Описание модуля» - поле для описания данного модуля.

  • «Иконка» - задает иконку модуля в пользовательской подсистеме (по умолчанию внешний модуль имеет стандартную иконку). Для того, чтобы изменить стандартную иконку, нужно кликнуть по кнопке «Выберите файл» и в диалоге выбора файла указать файл формата PNG, размер которого не превышает 28х26.

    _images/web-module-add.png

    Добавление нового внешнего модуля

Подсказка

Добавить внешний web-модуль можно с помощью SQL-запроса в БД synergy.outer_modules, вставив запись со следующими полями:

  • id — идентификатор модуля, должен совпадать с идентификатором
    вашего проекта в репозитории проектов
  • nameru, namekz, nameen — название модуля на русском, казахском и английском языках соответственно
  • url — адрес приложения
  • description — описание модуля
  • active — активен ли модуль, 1/0.

Для реализации механизма SSO приложений, ARTA Synergy при загрузке внешнего web-модуля будет в строку URL добавлять три параметра:

  1. locale — локаль авторизованного пользователя
  2. sso_hash — hash-сумма для идентификации пользователя.
  3. host — адрес, с которого загружено приложение Synergy

Например, если URL приложения

http://host:port/plans_module,

то при обращении к модулю будет вызываться

http://host:port/plans_module?locale=locale_value&sso_hash=sso_hash_value

Интегрированный модуль должен будет будет получить из URL параметр sso_hash и запросить по REST API у ARTA Synergy информацию об авторизованном пользователе (идентификатор, имя). Если метод REST API возвращает информацию о пользователе, это подтверждает, что данный пользователь действительно авторизован с данного хоста, в данном браузере.

Далее строка sso_hash может быть использована для Сессионная авторизация и вызова REST API Arta Synergy.

В ARTA Synergy реализована возможность обращения к ее модулям по относительной ссылке. Такая же возможность существует для внешних web-модулей. Переход по ссылке вида:

#submodule=outer&outerModuleID='код_модуля'&прочие_параметры_по_желанию_модуля

активирует в Synergy заданный модуль и передаст ему заданные в url-e параметры (параметры locale, sso_hash, host также будут переданы, несмотря на то, что они отсутствуют в ссылке).

Часто возникает необходимость в этой ссылке передать ссылку на текущий документ. Для этого можно добавить в ссылку параметр, значение которого будет равно ${docID} — эта строка в web-интерфейсе проигрывателя форм Synergy будет заменена на идентификатор данного документа.

6.7. Внешний проигрыватель форм

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

Проигрыватель форм - это инструмент, который даёт возможность работать с формами, созданными и используемыми в Synergy, а также выполняет скрипты. При использовании во внешней системе проигрыватель позволяет:

  • отображать и редактировать формы Synergy;
  • настраивать произвольный вид формы и ее компонентов, создавать новые компоненты;
  • автоматически заполнять поля формы данными из внешней системы;
  • обеспечивать обратную связь от проигрывателя к серверу, используя механизм событий;
  • обрабатывать наступившие события.

Примечание

Проигрыватель форм запускается на стороне клиента, поэтому все события и скрипты срабатывают только при открытом проигрывателе.

6.7.1. Подключение проигрывателя форм

  1. Для подключения проигрывателя на страницу необходимо добавить код в раздел head:

    <script>
     FORM_PLAYER_URL_PREFIX = "http://127.0.0.1:8080/Synergy/"; <!--служебная переменная для корректной работы компонента "HTD-редактор"-->
    </script>
    <link rel="stylesheet" href="http://127.0.0.1:8080/Synergy/js/form.player.css"/> <!--стандартный стиль компонентов формы-->
    <script src="http://127.0.0.1:8080/Synergy/js/vendor.js" type="text/javascript"></script> <!--ссылка на сторонние библиотеки-->
    <script src="http://127.0.0.1:8080/Synergy/js/form.player.js" type="text/javascript"></script> <!--ссылка на проигрыватель форм-->
    

    и вставить элемент для размещения проигрывателя в тело страницы:

    <div id="form_player_container">
        <div id="form_player_div"></div>
    </div>
    
  2. Код скрипта, который использует проигрыватель, должен содержать ссылку на Synergy:

    AS.OPTIONS.coreUrl = "http://127.0.0.1:8080/Synergy/"; //ссылка на экземпляр Synergy
    

    Создание объекта проигрывателя выглядит следующим образом:

    'use strict';
    
     AS.OPTIONS.locale = "ru";
     AS.OPTIONS.coreUrl = "http://127.0.0.1:8080/Synergy/";
    
    
     var portal = {
         player : null,
    
         /**
          * очистить текущий проигрыватель форм
          */
         clearPlayer : function() {
             if(portal.player) {
                 portal.player.destroy();
             }
         },
         /**
          * добавить новый проигрыватель форм
          */
         createPlayer : function(formCode){
    
             portal.clearPlayer();
             portal.player = AS.FORMS.createPlayer();
    
             portal.player.showFormByCode(formCode);
    
             portal.player.view.appendTo($('#form_player_div'));
    
         }
    
     };
    
     $(document).ready(function(){
    
         AS.OPTIONS.login = "login";
         AS.OPTIONS.password = "password";
         portal.createPlayer("formCode");
    
     });
    

См. также документацию по Скриптинг в формах.

6.7.2. Варианты использования внешнего проигрывателя форм

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

  • описание примера;
  • реализованный пример внешнего проигрывателя форм, встроенного во внешний портал (в данном случае - в портал документации);
  • а также исходные коды JavaScript и CSS этих примеров.

Примеры использования внешнего проигрывателя форм:

6.8. Ссылки на модули системы и их внутренние элементы

Ссылки на модули и различные объекты Synergy можно использовать как внутри основного web-приложения (в этом случае предпочтительно использовать относительные ссылки, чтобы не перезагружать страницу), так и во внешних системах.

Общий вид ссылок:

http[s]://host***[:port]*/**Application?*param1*=*value1*&*param2*=*value2*#*param3*=*value3*&*param4*=*value4*

где

  • host - доменное имя или ip-адрес сервера Synergy
  • port - порт
  • Application:
    • Synergy - основное приложение
    • Configurator - Конфигуратор
    • SynergyAdmin - административное приложение
  • param1, param2 - параметры абсолютной ссылки
  • param3, param4 - параметры относительной ссылки

Параметры абсолютной ссылки - это, как правило:

  • locale - локаль загружаемой системы
  • nocache - специальный параметр, предотвращающий случайное кэширование

остальные параметры можно передавать как параметры относительной ссылки.

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

6.8.1. Ссылка на модуль системы

#submodule=module_id

где module_id:

  • workflow - Потоки работ
  • calendar - Ежедневник
  • repository - Хранилище
  • plans - Проекты
  • pointers - Цели и показатели
  • employees - Сотрудники

При переходе по ссылке откроется указанный модуль.

6.8.2. Ссылка на документ и файл в нём

#submodule=common&file_identifier=some_file_id&action=open_document&document_identifier=some_doc_id

При переходе по такой ссылке откроется указанный документ с основным файлом, а если указан file_identifier - то откроется документ с этим файлом.

6.8.3. Ссылка на проект и мероприятие в нем

#submodule=plans&action=open_action&action_identifier=some_action_id&project_identifier=some_project_id

При переходе по такой ссылке откроется указанный проект, а если указан action_identifier - то в проекте будет выделено это мероприятие.

6.8.4. Ссылка на профиль пользователя

#submodule=employees&innermodule=structure&action=open_user&user_identifier=some_user_id

При переходе по такой ссылке будет открыт модуль «Сотрудники», а в нем - профиль указанного пользователя

6.8.5. Отключение всего пользовательского клиентского скриптинга

Если в абсолютной ссылке указать параметр noCustomScripting, то все пользовательские ВМК, скрипты в формах и пользовательских компонентах будут отключены. Это можно использовать для отладки пользовательских компонентов, ВМК и скриптов на форме.

6.9. Как задеплоить интеграционное приложение

ARTA Synergy работает на сервере приложений JBoss AS7. Интеграционное приложение может представлять собой jar-файл либо war-файл либо их комбинацию.

Если приложение является одиночным файлом, его можно задеплоить, скопировав в директорию ${jboss.home}/standalone/deployments. Если приложение состоит из нескольких файлов, необходимо создать *.ear приложение.

Если приложение имеет зависимости на внешние библиотеки и они находятся в модулях JBoss-а (${jboss.home}/modules), необходимо использовать их, прочие зависимости — помещать внутрь приложения.

Опасно

В целях безопасности работы приложения Synergy и сервера приложений категорически запрещается помещать артефакты интеграционного модуля в приложение Synergy.ear и изменять состав модулей (${jboss.home}/modules).