Сервис eltex-papaya предназначен для аутентификации пользователя на Captive Portal посредством услуги Mobile ID операторов связи.
Взаимодействие с Mobile ID осуществляется по протоколу HTTP/HTTPs.
Передаваемые данные кодируются и передаются в формате JSON, в кодировке UTF-8.
Для работы сервиса, его необходимо устанавливать на сервер с публичным IP-адресом и открыть порт 9098.
Алгоритм взаимодействия:
1. Абонент заходит на Captive Portal.
2. Captive Portal в браузере абонента отображает веб-страницу авторизации.
3. Абонент нажимает кнопку "Войти с Mobile Connect".
3.1. Если оператор и номер телефона неизвестны сервису eltex-papaya, то eltex-papaya обращается к Discovery Service для определения оператора и получает данные о Mobile ID.
4. Eltex-papaya отправляет запрос авторизации на Mobile ID.
5. Mobile ID валидирует запрос.
6. Mobile ID возвращает eltex-papaya ответ 200 ОК и ID запроса на авторизацию. Eltex-papaya начинает ожидать ответ на notification endpoint.
7. Mobile ID отправляет интерактивное сообщение абоненту о подтверждении регистрации в сети.
8. Абонент видит на экране телефона интерактивное окно с текстом и кнопками "ОК" и "Отмена".
9. Абонент выбирает "OK".
10. Результат действий абонента отправляется на Mobile ID.
11. Mobile ID формирует ответ для eltex-papaya, ответ содержит: ID Token, Access Token, и, опционально, Refresh Token.
12. Mobile ID отправляет ответ с выданным ранее ID запроса на авторизацию на notification uri eltex-papaya.
13. Eltex-papaya подтверждает получение данных от Mobile ID, отправляя на него http 204 или 200.
14. Captive Portal предоставляет абоненту запрошенный сервис, например - пускает на сайт.
15. Eltex-papaya формирует запрос дополнительной информацции, добавляя в него полученный ранее Access Token, и отправляет его на Mobile ID.
16. Mobile ID валидирует токен и возвращает eltex-papaya запрошенные данные об абоненте.

Внутренняя документация сервиса доступна по адресу: http://<IP-address>:9098/doc
root@ubuntu:~# apt-get install eltex-papaya |
| Действие | Команды | Ответ | ||
|---|---|---|---|---|
| Проверка состояния | service eltex-papaya status systemctl status eltex-papaya.service | Сервис запущен
Cервис не запущен
| ||
| Запуск сервиса | service eltex-papaya start systemctl start eltex-papaya.service | Сервис успешно запущен
| ||
| Остановка сервиса | service eltex-papaya stop systemctl stop eltex-papaya.service | Сервис успешно остановлен
| ||
| Перезапуск сервиса | service eltex-papaya restart systemctl restart eltex-papaya.service | Сервис успешно перезапущен
|
Eltex-papaya предоставляет следующие методы:
root@ubuntu:~# curl -X GET http://<IP-address>:9098/getversion 1.23-182 (23.06.22 17:47:26) |
root@ubuntu:~# curl -X GET http://<IP-address>:9098/jwt/refresh |
root@ubuntu:~# curl -X GET http://<IP-address>:9098/.well-known/jwks.json | json_pp
{
"keys" : [
{
"e" : "AQAB",
"kid" : "92547494-19b8-4e78-b083-a630c6f5ac8e",
"alg" : "RS256",
"n" : "1Jeumh33o1...",
"use" : "sig",
"kty" : "RSA"
},
{
"kty" : "RSA",
"use" : "sig",
"n" : "hmeZwCaSQ...",
"alg" : "RS256",
"kid" : "81123458-3763-4972-a0ab-d0042e4a284a",
"e" : "AQAB"
}
]
}
|
root@ubuntu:~# curl -X GET http://<IP-address>:9098/actuator | json_pp |
{
"_links" : {
"beans" : {
"href" : "http://100.110.1.201:9098/actuator/beans",
"templated" : false
},
"configprops-prefix" : {
"templated" : true,
"href" : "http://100.110.1.201:9098/actuator/configprops/{prefix}"
},
"env-toMatch" : {
"href" : "http://100.110.1.201:9098/actuator/env/{toMatch}",
"templated" : true
},
"health-path" : {
"href" : "http://100.110.1.201:9098/actuator/health/{*path}",
"templated" : true
},
"caches" : {
"templated" : false,
"href" : "http://100.110.1.201:9098/actuator/caches"
},
"info" : {
"templated" : false,
"href" : "http://100.110.1.201:9098/actuator/info"
},
"httptrace" : {
"href" : "http://100.110.1.201:9098/actuator/httptrace",
"templated" : false
},
"self" : {
"templated" : false,
"href" : "http://100.110.1.201:9098/actuator"
},
"env" : {
"href" : "http://100.110.1.201:9098/actuator/env",
"templated" : false
},
"configprops" : {
"templated" : false,
"href" : "http://100.110.1.201:9098/actuator/configprops"
},
"health" : {
"templated" : false,
"href" : "http://100.110.1.201:9098/actuator/health"
},
"threaddump" : {
"href" : "http://100.110.1.201:9098/actuator/threaddump",
"templated" : false
},
"heapdump" : {
"href" : "http://100.110.1.201:9098/actuator/heapdump",
"templated" : false
},
"caches-cache" : {
"href" : "http://100.110.1.201:9098/actuator/caches/{cache}",
"templated" : true
}
}
}
|
server:
port: 9098
portal:
baseUrl: http://<IP-address_portal>:9000/eltex_portal/
connectionTimeoutMs: 1000
totalConnections: 1
jwt:
configuration:
algorithm: RS256
keyLength: 2048
privateKeyFilePath: "/etc/eltex-papaya/keys/private.key"
publicKeyFilePath: "/etc/eltex-papaya/keys/public.key"
keyIdFilePath: "/etc/eltex-papaya/keys/keyId.txt"
discovery:
cacheTtlSeconds: 600
url: "<URL_Discovery>"
clientSecret: "<Client_Secret>"
clientId: "<Client_ID>"
redirectUrl: "<URL_Redirect>"
openid:
configCacheTtlSeconds: 600
authCacheTtlSeconds: 600
otpAuthCacheTtlSeconds: 600
notificationUri: "<URL_Notify>"
acrValue: "2"
version: "mc_si_r2_v1.0"
caching:
# We use this if we want replication. If it's disabled we don't need any network configuration
replicationEnabled: false
# The address outside of the NAT network of a Docker Container, for example
# Leave this section empty and hazelcast chooses it's itself
publicAddress: ""
# Port of the public node
port: 5703
# Do we need to propagate to further ports
portAutoIncrement: false
# Count of ports to propagate if portAutoIncrement is true
portCount: 1
# Available methods are:
# HOSTNAME - you need to specify the HOSTNAME environment variable inside your container that contains host and
# can be resolved to an IP Address
# IP_ADDRESS - you need to specify interfaceIp variable in this configuration or INTERFACE_IP variable in docker
# environment
# BIND_TO_ALL - hazelcast tries to bind itself to all known interfaces
# By Default IP_ADDRESS is used in Deb package and HOSTNAME in Docker environment
interfaceBindingMethod: "IP_ADDRESS"
# The IP Address by which we select binding interface in hazelcast.
# Works only if interfaceBindingMethods is INTERFACE_IP
interfaceIp: "<IP-address>"
# List of the member servers of this cache cluster. You can list comma-separated IPv4, IPv6 addresses
# and resolvable hosts with ports separated by colon. If port not configured - port from configuration parameter below
# will be used as default for all cluster nodes.
# Not resolvable hosts will be logged in error log.
servers:
# List hosts, ips here
[]
spring:
cloud:
discovery:
client:
composite-indicator:
enabled: false
management:
health:
defaults:
enabled: false
trace:
http:
enabled: true
endpoint:
health:
show-details: always
endpoints:
web:
exposure:
# Actuator info
# Useful for inspecting deployed beans, watching metrics, watching caches info
# Also we can use it to create heapdump, threaddump, shutdown application and etc.
include: health, beans, info, caches, prometheus, env, threaddump, heapdump, configprops, httptrace
|
server: port: 9098 |
portal: baseUrl: http://<IP-address_portal>:9000/eltex_portal/ # URL сервиса Captive Portal, на котором будет происходить аутентификация пользователей connectionTimeoutMs: 1000 # Время ожидания подключения в милисекундах totalConnections: 1 # Максимальное количество одновременных подключений |
jwt:
configuration:
algorithm: RS256 # Алгоритм генерации ключей:RS256, RS384, RS512, PS256, PS384, PS512 (рекомендуется RS256)
keyLength: 2048 # Длина ключа в битах
privateKeyFilePath: "/etc/eltex-papaya/keys/private.key" # Путь к приватному ключу
publicKeyFilePath: "/etc/eltex-papaya/keys/public.key" # Путь к публичному ключу
keyIdFilePath: "/etc/eltex-papaya/keys/keyId.txt # Путь к файлу, содержащему keyId ключа
|
discovery: url: "<URL_Discovery>" # URL Discovery-сервиса cacheTtlSeconds: 600 # Время хранения кэша в секундах clientSecret: "<Client_Secret>" # Ключ подключения clientId: "<Client_ID>" # ID подключения redirectUrl: "<URL_Redirect>" # URL перенапрвления |
openid: cacheTtlSeconds: 600 # Время хранения кэша в секундах authCacheTtlSeconds: 600 # Время жизни записи в кэше авторизаций MobileID otpAuthCacheTtlSeconds: 600 # Время жизни записи в кэше авторизаций по MobileID OTP notificationUri: "http://<PUBLIC_IP>:9098/notify/" # Адрес для обратных уведомлений от IDGW acrValue: "2" # Список запрашиваемых LoA version: "mc_si_r2_v1.0" # Версия приложения MobileID |
caching:
replicationEnabled: false # Статус активации репликации
multicastEnabled: false # Статус активации мультикаста
autoDetectionEnabled: false # Cтатус активации автообнаружение нод
publicAddress: "" # Публичный адрес текущей ноды
port: 5703 # Порт доступа к ноде
portAutoIncrement: false # Автоинкремент портов
portCount: 1 # Максимум портов для автоинкремента;
interfaceBindingMethod: "IP_ADDRESS" # Метод биндинга. Доступные методы:
## HOSTNAME — для этого режима необходимо задать переменную окружения HOSTNAME, которая может зарезолвиться в IP-адрес
## IP_ADDRESS — для этого режима необходимо задать значение переменной CACHING_INTERFACEIP
## BIND_TO_ALL — в этом режиме Hazelcast попытается использовать все доступные интерфейсы
## IP_ADDRESS используется для Deb пакетов, HOSTNAME используется в Docker environment
interfaceIp: "127.0.0.1" # IP-адрес интерфейса для биндинга
servers:
[] # Cписок членов кластера в виде IPv4, IPv6
|
management:
health:
defaults:
enabled: false
trace:
http:
enabled: true
endpoint:
health:
show-details: always
endpoints:
web:
exposure:
# Actuator info
# Useful for inspecting deployed beans, watching metrics, watching caches info
# Also we can use it to create heapdump, threaddump, shutdown application and etc.
include: health, beans, info, caches, prometheus, env, threaddump, heapdump, configprops, httptrace
|
<?xml version="1.0" encoding="UTF-8"?>
<Configuration>
<Properties>
<Property name="maxSize" value="10MB"/>
<Property name="maxCount" value="10"/>
<Property name="logDir" value="/var/log/eltex-papaya"/>
<Property name="defaultPattern" value="%d{ISO8601} [%t] %-5p %logger{1} %C{1}.%M(line:%L). %m%n"/>
<Property name="gelfHost" value="udp:localhost"/>
<Property name="gelfPort" value="12201"/>
<Property name="gelfLevel" value="OFF"/>
<Property name="filenamePrefix" value="eltex-papaya"/>
</Properties>
<Appenders>
<RollingFile name="SPRING-INFO"
fileName="${logDir}/${filenamePrefix}-spring.log"
filePattern="${logDir}/spring/%d{yyyyMMdd}.%i.log">
<ThresholdFilter level="INFO" onMatch="ACCEPT" onMismatch="DENY"/>
<PatternLayout>
<pattern>${defaultPattern}</pattern>
</PatternLayout>
<Policies>
<SizeBasedTriggeringPolicy size="${maxSize}"/>
</Policies>
<DefaultRolloverStrategy max="${maxCount}"/>
</RollingFile>
<RollingFile name="SERVICE"
fileName="${logDir}/${filenamePrefix}.log"
filePattern="${logDir}/service/%d{yyyyMMdd}.%i.log">
<PatternLayout>
<pattern>${defaultPattern}</pattern>
</PatternLayout>
<Policies>
<SizeBasedTriggeringPolicy size="${maxSize}"/>
</Policies>
<DefaultRolloverStrategy max="${maxCount}"/>
</RollingFile>
<RollingFile name="HAZELCAST"
fileName="${logDir}/${filenamePrefix}-hazelcast.log"
filePattern="${logDir}/hazelcast/%d{yyyyMMdd}.%i.log">
<PatternLayout>
<pattern>${defaultPattern}</pattern>
</PatternLayout>
<Policies>
<SizeBasedTriggeringPolicy size="${maxSize}"/>
</Policies>
<DefaultRolloverStrategy max="${maxCount}"/>
</RollingFile>
<Gelf name="Gelf"
host="${gelfHost}"
port="${gelfPort}"
version="1.1"
facility="${filenamePrefix}"
extractStackTrace="true"
originHost="%host{fqdn}"
maximumMessageSize="8192">
<Field name="thread" pattern="%t"/>
<Field name="level" pattern="%level"/>
<Field name="severity" pattern="%-5level"/>
<Field name="logger" pattern="%logger{1}"/>
<Field name="location" pattern="%C{1}.%M(line:%L)"/>
</Gelf>
</Appenders>
<Loggers>
<Root level="info">
<AppenderRef ref="Gelf" level="${gelfLevel}"/>
</Root>
<Logger name="org.springframework" level="info">
<AppenderRef ref="SPRING-INFO"/>
</Logger>
<Logger name="org.eltex.softwlc.papaya" level="info">
<AppenderRef ref="SERVICE"/>
</Logger>
<Logger name="com.hazelcast" level="info">
<AppenderRef ref="HAZELCAST"/>
</Logger>
</Loggers>
</Configuration>
|
<Property name="maxSize" value="5MB"/> |
<Property name="maxCount" value="7"/> |
<Property name="logDir" value="/var/log/eltex-papaya"/> |
<Property name="defaultPattern" value="%d{ISO8601} [%t] %-5p %logger{1} %C{1}.%M(line:%L). %m%n"/> |
<Property name="gelfHost" value="udp:localhost"/> <Property name="gelfPort" value="12201"/> <Property name="gelfLevel" value="OFF"/> |
<Property name="filenamePrefix" value="eltex-papaya"/> |
<Loggers>
<Root level="info"> |
# Papaya service # Initial size of Java heap JAVA_INIT_HEAP=256m # Maximum size of Java heap JAVA_MAX_HEAP=512m # JVM debug port DEBUG_PORT= # Options for Java Garbage Collector GC_OPTS="-XX:+UseG1GC \ -XX:+UseStringDeduplication \ -XX:+PrintGCDateStamps \ -XX:+PrintGCDetails \ -XX:+UseGCLogFileRotation \ -XX:NumberOfGCLogFiles=7 \ -XX:GCLogFileSize=5M \ -Xloggc:/var/log/eltex-papaya/gc.log" # Additional arguments to pass to java JAVA_OPTS="$GC_OPTS -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/var/log/eltex-papaya" |
JAVA_INIT_HEAP=256m |
JAVA_MAX_HEAP=512m |
DEBUG_PORT= |
GC_OPTS="-XX:+UseG1GC \ -XX:+PrintGCDateStamps \ -XX:+PrintGCDetails \ -XX:+UseGCLogFileRotation \ -XX:NumberOfGCLogFiles=7 \ -XX:GCLogFileSize=5M \ -Xloggc:/var/log/eltex-papaya/gc.log" |
JAVA_OPTS="$GC_OPTS -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/var/log/eltex-papaya" |
Сервис может быть запущен в docker-контейнере. Для этого необходимо подготовить файл с переменными окружения .env и docker-compose.yml.
version: "3"
services:
eltex-papaya:
ports:
- "${PAPAYA_SERVER_PORT}:${PAPAYA_SERVER_PORT}"
- "${CACHING_PORT}:${CACHING_PORT}"
#- "${PAPAYA_DEBUG_PORT}:${PAPAYA_DEBUG_PORT}"
container_name: eltex-papaya
image: ${ELTEX_HUB}/eltex-papaya:${SWLC_VERSION}
volumes:
- ${PAPAYA_CONFIG_DIR}/keys/:${PAPAYA_CONFIG_DIR}/keys/
environment:
# Порт внутри контейнера. По умолчанию 9098
- SERVER_PORT=${PAPAYA_SERVER_PORT}
# Порт удаленного дебага
- PAPAYA_DEBUG_PORT=${PAPAYA_DEBUG_PORT}
# URL сервиса Captive Portal, на котором будет происходить аутентификация пользователей
- PORTAL_BASEURL=${PORTAL_BASEURL}
# Таймаут подключения к Captive Portal
- PORTAL_CONNECTIONTIMEOUTMS=${PORTAL_CONNECTIONTIMEOUTMS}
# Число одновременных подключений к Captive Portal
- PORTAL_TOTALCONNECTIONS=${PORTAL_TOTALCONNECTIONS}
# Алгоритм генерации ключей
- JWT_CONFIGURATION_ALGORITHM=${JWT_CONFIGURATION_ALGORITHM}
# Длина ключа в битах
- JWT_CONFIGURATION_KEYLENGTH=${JWT_CONFIGURATION_KEYLENGTH}
# Путь к приватному ключу
- JWT_CONFIGURATION_PRIVATEKEYFILEPATH=${JWT_CONFIGURATION_PRIVATEKEYFILEPATH}
# Путь к публичному ключу
- JWT_CONFIGURATION_PUBLICKEYFILEPATH=${JWT_CONFIGURATION_PUBLICKEYFILEPATH}
# Путь к файлу, содержащему keyId ключа
- JWT_CONFIGURATION_KEYIDFILEPATH=${JWT_CONFIGURATION_KEYIDFILEPATH}
# Discovery
# Время жизни записи в кэше запросов Discovery
- DISCOVERY_CACHETTLSECONDS=${DISCOVERY_CACHETTLSECONDS}
# Адрес сервиса Discovery
- DISCOVERY_URL=${DISCOVERY_URL}
# Секрет для авторизации
- DISCOVERY_CLIENTSECRET=${DISCOVERY_CLIENTSECRET}
# Идентификатор клиента для авторизации
- DISCOVERY_CLIENTID=${DISCOVERY_CLIENTID}
# Зарегистрированный URL для перенаправления
- DISCOVERY_REDIRECTURL=${DISCOVERY_REDIRECTURL}
# Open ID
# Время жизни записи в кэше конфигураций MobileID
- OPENID_CONFIGCACHETTLSECONDS=${OPENID_CONFIGCACHETTLSECONDS}
# Время жизни записи в кэше авторизаций MobileID
- OPENID_AUTHCACHETTLSECONDS=${OPENID_AUTHCACHETTLSECONDS}
# Время жизни записи в кэше авторизаций по MobileID OTP
- OPENID_OTPAUTHCACHETTLSECONDS=${OPENID_OTPAUTHCACHETTLSECONDS}
# Адрес для обратных уведомлений от IDGW
- OPENID_NOTIFICATIONURI=${OPENID_NOTIFICATIONURI}
# Список запрашиваемых LoA
- OPENID_ACRVALUE=${OPENID_ACRVALUE}
# Версия приложения MobileID
- OPENID_VERSION=${OPENID_VERSION}
# Настройки Hazelcast
# Репликация
- CACHING_REPLICATIONENABLED=${CACHING_REPLICATIONENABLED}
# Публичный адрес текущей ноды
- CACHING_PUBLICADDRESS=${CACHING_PUBLICADDRESS}
# Порт доступа к ноде
- CACHING_PORT=${CACHING_PORT}
# Автоинкремент портов
- CACHING_PORTAUTOINCREMENT=${CACHING_PORTAUTOINCREMENT}
# Максимум портов для автоинкремента
- CACHING_PORTCOUNT=${CACHING_PORTCOUNT}
# Доступные методы биндинга:
# HOSTNAME - для этого режима необходимо задать переменную окружения HOSTNAME которая может зарезолвиться в IP адрес
# IP_ADDRESS - для этого режима необходимо задать значение переменной CACHING_INTERFACEIP
# BIND_TO_ALL - в этом режиме Hazelcast попытается использовать все доступные интерфейсы
# IP_ADDRESS используется для Deb пакетов, HOSTNAME используется в Docker environment
- CACHING_INTERFACEBINDINGMETHOD=${CACHING_INTERFACEBINDINGMETHOD}
- CACHING_INTERFACEIP=${CACHING_INTERFACEIP}
# список членов кластера в виде IPv4, IPv6 или hostname
- CACHING_SERVERS=${CACHING_SERVERS}
# - CACHING_SERVERS_0=${CACHING_SERVERS_0}
# - CACHING_SERVERS_1=${CACHING_SERVERS_1}
# Изначальный размер хипа
- PAPAYA_JAVA_INIT_HEAP=${PAPAYA_JAVA_INIT_HEAP}
# Максимальный размер хипа
- PAPAYA_JAVA_MAX_HEAP=${PAPAYA_JAVA_MAX_HEAP}
# Путь, куда нужно складывать heap-dump в случае падения приложения
- PAPAYA_HEAP_DUMP_PATH=${PAPAYA_HEAP_DUMP_PATH}
# Внутренний путь до конфигурации сервиса
- PAPAYA_CONFIG_DIR=${PAPAYA_CONFIG_DIR}
# Настройки логирования
- PAPAYA_LOG_LEVEL=${PAPAYA_LOG_LEVEL}
- PAPAYA_CONSOLE_LEVEL=${PAPAYA_CONSOLE_LEVEL}
# Настройки Graylog
- GELF_LEVEL=${GELF_LEVEL}
- GELF_HOST=${GELF_HOST}
- GELF_PORT=${GELF_PORT}
#Настройка часового пояса
- TZ=${TZ}
|
# Docker-репозиторий, где находится образ eltex-papaya. # Для разработки: lab3.eltex.loc:5000 # Публичный: hub.eltex-co.ru/softwlc ELTEX_HUB=hub.eltex-co.ru/softwlc # Версия сервиса, которую нужно развернуть # На feature-ветке — вида 1.23-<название_ветки> SWLC_VERSION=1.23-<tag> # Внешний порт контейнера eltex-papaya PAPAYA_SERVER_PORT=9098 # Порт для удаленного дебага PAPAYA_DEBUG_PORT=5015 # URL сервиса Captive Portal, на котором будет происходить аутентификация пользователей PORTAL_BASEURL=http://<IP-address_portal>:9000/eltex_portal/ # Таймаут подключения к Captive Portal PORTAL_CONNECTIONTIMEOUTMS=1000 # Число одновременных подключений к Captive Portal PORTAL_TOTALCONNECTIONS=1 # Алгоритм генерации ключей JWT_CONFIGURATION_ALGORITHM=RS256 # Длина ключа в битах JWT_CONFIGURATION_KEYLENGTH=2048 # Путь к приватному ключу JWT_CONFIGURATION_PRIVATEKEYFILEPATH=/etc/eltex-papaya/keys/private.key # Путь к публичному ключу JWT_CONFIGURATION_PUBLICKEYFILEPATH=/etc/eltex-papaya/keys/public.key # Путь к файлу, содержащему keyId ключа JWT_CONFIGURATION_KEYIDFILEPATH=/etc/eltex-papaya/keys/keyId.txt # Discovery # Время жизни записи в кэше запросов Discovery DISCOVERY_CACHETTLSECONDS=600 # Адрес сервиса Discovery DISCOVERY_URL=<URL_Discovery> # Секрет для авторизации DISCOVERY_CLIENTSECRET="<Client_Secret>" # Идентификатор клиента для авторизации DISCOVERY_CLIENTID="<Client_ID>" # Зарегистрированный URL для перенаправления DISCOVERY_REDIRECTURL="<URL_Redirect>" # Open ID # Время жизни записи в кэше конфигураций MobileID OPENID_CONFIGCACHETTLSECONDS=600 # Время жизни записи в кэше авторизаций MobileID OPENID_AUTHCACHETTLSECONDS=600 # Время жизни записи в кэше авторизаций по MobileID OTP OPENID_OTPAUTHCACHETTLSECONDS=600 # Адрес для обратных уведомлений от IDGW OPENID_NOTIFICATIONURI=http://<PUBLIC_IP>:9098/notify # Список запрашиваемых LoA OPENID_ACRVALUE=2 # Версия приложения MobileID OPENID_VERSION=mc_si_r2_v1.0 # Настройки Hazelcast # Репликация CACHING_REPLICATIONENABLED=false # Публичный адрес текущей ноды CACHING_PUBLICADDRESS= # Порт доступа к ноде CACHING_PORT=5703 # Автоинкремент портов CACHING_PORTAUTOINCREMENT=false # Максимум портов для автоинкремента CACHING_PORTCOUNT=1 # Доступные методы биндинга: # HOSTNAME - для этого режима необходимо задать переменную окружения HOSTNAME которая может зарезолвиться в IP адрес # IP_ADDRESS - для этого режима необходимо задать значение переменной CACHING_INTERFACEIP # BIND_TO_ALL - в этом режиме Hazelcast попытается использовать все доступные интерфейсы # IP_ADDRESS используется для Deb пакетов, HOSTNAME используется в Docker environment CACHING_INTERFACEBINDINGMETHOD= CACHING_INTERFACEIP= # список членов кластера в виде IPv4, IPv6 или hostname CACHING_SERVERS= # Изначальный размер хипа PAPAYA_JAVA_INIT_HEAP=8m # Максимальный размер хипа PAPAYA_JAVA_MAX_HEAP=64m # Путь, куда нужно складывать heap-dump в случае падения приложения PAPAYA_HEAP_DUMP_PATH=/var/log/eltex-papaya # Внутренний путь до конфигурации сервиса PAPAYA_CONFIG_DIR=/etc/eltex-papaya # Настройки логирования PAPAYA_LOG_LEVEL=INFO PAPAYA_CONSOLE_LEVEL=INFO # Настройки Graylog # Вместо <graylog_server_ip> нужно указать настоящий адрес сервера Graylog или localhost GELF_LEVEL=OFF GELF_HOST=udp:localhost GELF_PORT=12201 #Настройка часового пояса TZ=Asia/Novosibirsk |
PORTAL_BASEURL — URL сервиса Captive Portal, на котором будет происходить аутентификация пользователей;
PORTAL_CONNECTIONTIMEOUTMS — таймаут подключения к Captive Portal;
PORTAL_TOTALCONNECTIONS — число одновременных подключений к Captive Portal.
Для просмотра справочной информации по настройке hazelcast можно перейти по ссылке http://<IP адрес хоста papaya>:9098/doc в браузере и перейти в соответсвующий раздел.
Настройка часового пояса
Файлы .env и docker-compose.yml должны находиться в одной папке. Контейнер запускается командой:
root@ubuntu:~# docker-compose up -d |
Для просмотра справочной информации о метриках сервиса можно перейти по ссылке http://<IP адрес хоста papaya>:9098/doc в браузере.
| Название | Описание | Тип | Тэги |
|---|---|---|---|
papaya_authentication_request | Общее количество запросов на аутентификацию пользователя по Mobile ID от портала к Papaya. Поможет оценить нагрузку на сервис | Счетчик | - |
papaya_authentication_request_processing_status | Количество ответов от Papaya со статусом обработки запроса на аутентификацию пользователя | Счетчик | status: статус обработки запроса {success, failed} |
papaya_authentication_status | Количество ответов от Papaya порталу с итоговым статусом аутентификации пользователя | Счетчик | status: статус аутентификации пользователя {authenticated, failed} |
papaya_discovery_request | Количество discovery запросов от Papaya к Discovery | Счетчик | - |
papaya_discovery_response | Количество ответов на запрос от Discovery к Papaya | Счетчик | http_code: HTTP-статус ответа |
papaya_configuration_request | Количество запросов на получение OpenID конфигурации от Papaya к IDGW | Счетчик | - |
papaya_configuration_response | Количество ответов от IDGW к Papaya на запрос конфигурации | Счетчик | http_code: HTTP-статус ответа |
papaya_idgw_request | Общее количество запросов от Papaya к IDGW: через PUSH и OTP | Счетчик | - |
papaya_idgw_response | Количество ответов от IDGW на запрос аутентификации пользователя | Счетчик | http_code: HTTP-статус ответа |
papaya_idgw_otp_request | Количество запросов от Papaya к IDGW на аутентификацию пользователя по OTP. Выполняется дополнительно в случае если Mobile ID не поддерживается | Счетчик | http_code: HTTP-статус ответа |
Spring Actuator предоставляет несколько готовых конечных точек (endpoint) для мониторинга метрик:
/actuator/prometheus |
Отображает пользовательские метрики в формате, который может быть обработан сервером Prometheus.
Пример URL: http://localhost:9098/actuator/prometheus.
/actuator/metrics |
Показывает список всех метрик, которые можно отслеживать для приложения.
Пример URL: http://localhost:9098/actuator/metrics.
Посмотреть информацию по отдельной метрике можно передав её в URL-адресе после /metrics, как показано в примере ниже:
http://localhost:9098/actuator/metrics/papaya_authentication_request.
Настройка интеграции | ||||||
| Конструкор порталов | Поключение к сервису eltex-papaya |
|
2. Проверить значения параметров модуля mobileID
| |||
| Включение нового типа авторизации |
| Проверить, что новая настройка сохранилавь в БД:
2. По ID портала найти ID его группы конфигураций:
3. Проверить, что авторизация по Mobile ID включена:
| ||||
Проверка авторизации через MobileID | ||||||
| Портал | Авторизация с телефонным номером Теле2 с поддержкой Mobile ID. |
|
2. Перейти на страницу Портала. 3. Выбрать авторизацию по номеру телефона. 4. Ввести телефонный номер Теле2 и нажать кнопку "MobileID". 5. Должно появиться системное уведомление о подключении к сети. 6. Нажать "ок" - должен появиться доступ в сеть. 7. Нажать "отмена" либо ничего не нажимать - редирект на выбор способа авторизации. | |||
| Авторизация с телефонным номером Теле2 без поддержки Mobile ID. |
| Старые сим-карты Теле2 могут не поддерживать Mobile D, для такого случая предусмотрен сценарий, при котором пользователю Mobile ID присылает смс-сообщение с кодом.
2. Перейти на страницу Портала. 3. Выбрать авторизацию по номеру телефона. 4. Ввести телефонный номер Теле2 и нажать кнопку "MobileID". 5. Придет SMS-сообщение с кодом для авторизации. 6. Если код авторизации не пришел, его можно запросить повторно. 7. В случае превышения числа попыток ввода кода, будет редирект на страницу выбора способа авторизации. | ||||
| Авторизация с телефонным номером других операторов |
|
2. Перейти на страницу Портала. 3. Выбрать авторизацию по номеру телефона. 4. Ввести телефонный номер любого другого и нажать кнопку "MobileID". 5. На портале должна появиться ошибка и предложение использовать другой способ авторизации. | ||||
Расшифровка логов портала | |
|---|---|
| Неуспешная авторизация, papaya не отвечает MobailID (подробнее в логах papaya). | ERROR org.eltex.portal.service.PapayaServiceImpl PapayaServiceImpl.postMobileIdAuthentication(line:56). Papaya not answered success to MobileID auth request. Details: Code: 500. Message: Internal Server Error |
| Успешная авторизация. | DEBUG org.eltex.portal.controller.MobileIdController MobileIdController.setMobileIdStatus(line:51). MobileID user with id 44189e91-45bc-430a-ad01-66baccc4233d successfully authenticated |
| Успешная авторизация по SMS-коду. | DEBUG org.eltex.portal.controller.MobileIdController MobileIdController.getSmsCodeStatus(line:121). MobileID user with MAC a4:45:19:0b:8c:2e successfully authenticated |
| Начало OTP-сессии для устройства с mac-адресом. | DEBUG org.eltex.portal.controller.MobileIdController MobileIdController.getAuthenticationStatus(line:206). For user 00:00:00:ff:dd:dd started an MobileID OTP Session. Showing code enter form |
| Неуспешная авторизация, подробнее в логах papaya. | ERROR org.eltex.portal.controller.MobileIdController MobileIdController.setMobileIdStatus(line:60). Authentication failed for authReqId: 3fcea8a7-b9a6-4118-9e01-5de02795c7cd. Status: FAILED |
| Сессия пользователя не найдена для проверки SMS-кода - сессия истекла на стороне MobileID. | ERROR org.eltex.portal.service.PapayaServiceImpl PapayaServiceImpl.checkSmsStatus(line:154). Cannot check SMS status for device: null |
| Пользователь не подтвердил свою личность, статус аутентификации - не подтверждён (не нажал "ОК", не ввёл пин-код). | DEBUG org.eltex.portal.controller.MobileIdController MobileIdController.getAuthenticationStatus(line:223). User a4:45:19:0b:8c:2e is not authenticated due some unknown error of MobileID. Redirecting to index and showing error |
| Нельзя начать OTP-сессию для пользователя. Он либо давно ушёл с портала, попал на OTP очень поздно, либо запросил новую сессию в MobileID. | ERROR org.eltex.portal.service.PapayaServiceImpl PapayaServiceImpl.requireSmsCodeFromUser(line:124). Can't start OTP session for authReqId a37c6178-1502-486c-b0a4-012e94145314. User MAC not found. |
| Не удалось проставить статус FAILED, так как пользователь уже ушёл с портала, либо получил новую сессию в MobileID. | ERROR org.eltex.portal.service.PapayaServiceImpl PapayaServiceImpl.authenticationFail(line:107). Can't fail MobileID user authentication. Mac not found by 18d0c694-9bdf-42ad-851e-a30cd4d430a0. Current status is: FAILED |
Расшифровка логов papaya | |
|---|---|
| Пользователь отклонил системное уведомление о входе на портал, либо оператор не смог его прислать. | OpenIdAuthorizationService.processNotifyRequest$suspendImpl(line:145). User not authorized because of: authorization_error:user denies the request or authentication fails |
| Слишком долго ждали нажатия "ОК", либо вовсе его не нажали. Неуспешная авторизация. | OpenIdAuthorizationService.processNotifyRequest$suspendImpl(line:145). User not authorized because of: authorization_error:Subscriber consent waiting time expired |
| Получено уведомление о статусе авторизации пользователя MobileID. Внутри ID сессии и номер телефона, если пользователь находится в кэше. | OpenIdAuthorizationService.processNotifyRequest$suspendImpl(line:143). Received notify with request id 3485f838-9f7c-4349-9f54-a35d6f8ab49f. Phone 79585150889 |
| Успешно отправили запрос на авторизацию пользователя с номером телефона в MobileID. Ждём уведомления от MobileID. | OpenIdAuthorizationService.processMobileIdAuth$suspendImpl(line:198). Auth success for 79585150889. Waiting for auth notification |
Получили от портала запрос на авторизацию с представленным номером телефона. Замечание: нельзя одновременно авторизоваться с одним номером телефона на двух устройствах. MobileID держит только одну сессию за время, так что на одном из устройств будет неуспех. | OpenIdAuthorizationService.processMobileIdAuth$suspendImpl(line:184). Received auth request for phone 79585150889 |
| Ответ на запрос проверки SMS-кода по схеме Пользователь -> Портал -> Папайа -> MobileID. В данном случае введённый SMS-код верный. | OpenIdAuthorizationService.processMobileIdOtpAuth$suspendImpl(line:241). SMS status is correct for c8f4e1a4-0a71-4eaf-bae5-74491c2076cd : 79930086782 |
| Получен SMS-код от портала на проверку в MobileID. | OpenIdAuthorizationService.processMobileIdOtpAuth$suspendImpl(line:222). Received sms code from portal service. Phone 79930086782 |
| Статус проверки SMS - введённый код неверный. | penIdAuthorizationService.processMobileIdOtpAuth$suspendImpl(line:241). SMS status is incorrect for c8f4e1a4-0a71-4eaf-bae5-74491c2076cd : 79930086782 |
| Код из SMS неверный. Оставшееся количество попыток: 2. Это сообщение, которое приходит в папаю из MobileID. | penIdAuthorizationService$performOtpAuthRequest$2.invokeSuspend(line:128). Error while sending auth request to MobileID platform 5135:FORBIDDEN: remaining attempts: 2 |
| Сообщение от MobileID - превышено число попыток проверки SMS-кода. | OpenIdAuthorizationService$performOtpAuthRequest$2.invokeSuspend(line:128). Error while sending auth request to MobileID platform 5136:LIMIT_REACHED |
| MobileID открыл сессию OTP для пользователя с представленным номером. Ожидаем ввода пользователя на портале, после этого проверяем SMS-код. | OpenIdAuthorizationService.processOtpNotifyRequest$suspendImpl(line:162). Received OTP notify with request id c8f4e1a4-0a71-4eaf-bae5-74491c2076cd. Phone 79930086782 |
| Не можем отправить запрос на авторизацию пользователя с таким номером, так как его оператор не подключен к MobileID, либо не подключен в профиле С-П на Discovery. | OpenIdDiscoveryService$sendDiscoveryRequest$2.invokeSuspend(line:61). Can't perform discovery with specified phone 79293810070. Details: 404 NOT_FOUND "Not_Found_Entity:There is no organization with the specified MSISDN" |
| Превысили число проверок SMS-кода на MobileID. OTP-сессия завершилась неуспешно. | OpenIdAuthorizationService.processNotifyRequest$suspendImpl(line:145). User not authorized because of: authorization_error:OTP authentication failed |
| Исчерпали число попыток для проверки СМС. OTP-сессия после этого закрывается и получаем ошибку авторизации. | OpenIdAuthorizationService.processMobileIdOtpAuth$suspendImpl(line:241). SMS status is limit_reached for 185de01e-6637-46d3-92ab-6b4905e13a71 : 79930086782 |
| Не верно настроены параметры - DISCOVERY_CLIENTSECRET - DISCOVERY_CLIENTID | [DefaultDispatcher-worker-2] ERROR KClassImpl OpenIdDiscoveryService$sendDiscoveryRequest$2.invokeSuspend(line:67). Can't perform discovery with specified phone 79509219031. Details: 401 UNAUTHORIZED |
За конфигурацию сервиса отвечают свойства с префиксом caching. из файла application.properties при работе в Deb или CACHING_ в случае настройки через .env файл и работе в Docker. Переменные окружения для .env файла указываются с префиксом и в верхнем регистре. Описание свойств конфигурации актуально для обоих способов запуска. Описание и особенности настройки для обеих сред указаны ниже:
replicationEnabled - отвечает за включение/выключение репликации кэша;
publicAddress - публичный IP адрес текущей ноды, используемый для обнаружения другими нодами. Должен быть доступен для других нод;
port - порт, на котором нода работает и слушает входящие подключения от других нод. В случае настройки репликации в Docker необходимо также прокинуть этот порт наружу с помощью директивы ports в docker-compose.yml файле;
portAutoIncrement - включение режима автоинкремента портов начиная с port, если port занят другим процессом;
portCount - количество портов для свойства portAutoIncrement, которое текущей ноде позволено перебрать по порядку начиная с port если port занят;
interfaceBindingMethod - свойство, отвечающее за выбор метода определения интерфейса, на котором будет доступна нода; Возможные значения:
IP_ADDRESS - в этом режиме необходимо указать адрес к которому нода попробует привязаться установив его значение в переменную interfaceIp
HOSTNAME - режим, используемый для запуска в Docker контейнерах объединенных общей сетью. При указании директивы hostname для сервиса в файле docker-compose.yml нода попробует привязаться к адресу в который зарезолвится hostname.
BIND_TO_ALL - в этом режиме нода попробует привязаться ко всем доступным интерфейсам.
interfaceIp - значение адреса ноды для interfaceBindingMethod=IP_ADDRESS.
servers - список адресов(IPv4, IPv6, hostname) нод, которые входят в кластер. Адреса могут быть указаны с портом, через двоеточие. Если порт не указан - используется значение свойства port. В случае настройки в файле application.properties список адресов указывается как массив:
servers: [address1:port1, address2:port2]При настройке для Docker в файле .env массив указывается через название переменной и индекс элемента массива:
CACHING_SERVERS_0=address1:port1
CACHING_SERVERS_1=address2:port2Что будет в итоге преобразовано в массив аналогичный массиву servers в application.properties.
Настройка выполняется в файле /etc/eltex-papaya/config/application.yml в разделе "caching".
Алгоритм минимальной настройки:
replicationEnabled: true |
2. Указать тип привязки:
interfaceBindingMethod: "IP_ADDRESS" |
3. Указать IP-адрес интерфейса привязки:
interfaceIp: "100.110.1.201" |
4. Перечислить участников кластера:
servers:
[100.110.1.201:5703, 100.110.2.50:5703] |
Параметры необходимо настроить на всех нодах и перезапустить сервис на всех серверах-участниках.
Настройка параметров выполняется в файле переменных окружения .env.
Алгоритм минимальной настройки:
CACHING_REPLICATIONENABLED=true |
2. Указать публичный адрес сервера:
CACHING_PUBLICADDRESS=100.110.1.201 |
3. Указать тип привязки:
CACHING_INTERFACEBINDINGMETHOD=HOSTNAME |
4. Указать IP-адрес второй ноды
CACHING_SERVERS=100.110.2.50 |
Параметры необходимо настроить на всех нодах и перезапустить контейнер на всех серверах-участниках.
Настройка параметров выполняется в файле переменных окружения .env.
Алгоритм минимальной настройки:
CACHING_REPLICATIONENABLED=true |
2. Указать публичный адрес сервера:
CACHING_PUBLICADDRESS=100.110.1.201 |
3. Указать тип привязки:
CACHING_INTERFACEBINDINGMETHOD=HOSTNAME |
4. Указать IP-адрес текущей ноды
CACHING_SERVERS_0=100.110.1.201 |
5. Указать IP-адрес второй ноды
CACHING_SERVERS_1=100.110.2.50 |
6. Указать IP-адрес третей ноды
CACHING_SERVERS_2=100.110.2.56 |
7. Добавить в docker-compose.yml новые переменные и удалить старую:
# - CACHING_SERVERS=${CACHING_SERVERS}
- CACHING_SERVERS_0=${CACHING_SERVERS_0}
- CACHING_SERVERS_1=${CACHING_SERVERS_1}
- CACHING_SERVERS_2=${CACHING_SERVERS_2} |
Параметры необходимо настроить на всех нодах и перезапустить контейнер на всех серверах-участниках.
Проверить состояние кластера можно командой:
root@ubuntu:~/papaya# curl -X GET http://100.110.1.201:9098/actuator/health/hazelcast | json_pp
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 415 100 415 0 0 25937 0 --:--:-- --:--:-- --:--:-- 25937
{
"details" : {
"members" : [
{
"uuid" : "15e43aae-fe31-4804-bd57-b8a46bcf1bf1",
"localMember" : false,
"address" : "[100.110.2.50]:5703",
"liteMember" : false,
"memberVersion" : "4.2.5"
},
{
"localMember" : true,
"uuid" : "739d7ea4-d6e4-46c3-a86c-080ec2d0fc69",
"address" : "[100.110.1.201]:5703",
"memberVersion" : "4.2.5",
"liteMember" : false
}
],
"uuid" : "739d7ea4-d6e4-46c3-a86c-080ec2d0fc69",
"state" : "ACTIVE",
"name" : "competent_hermann"
},
"status" : "UP"
} |
Команда является единой для всех видов запуска.