Instalación y configuración de Wildfly 11 en alta disponibilidad (clúster) con replicación de sesión.

En este artículo me gustaría explicar cómo instalar y configurar  widlfly en modo dominio en dos servidores distintos llamados master (192.168.1.1) y slave (192.168.1.2)con alta disponibilidad  y replicación de sesión. Los nombres de los servidores no han sido escogidos al azar, al configurar widfly en modo dominio requiere que uno de los servidores sea el maestro (master) y el resto serán los esclavos (slave) que acatarán las órdenes y la configuración del maestro.

Comencemos:

Procedemos a descargar la versión 11 de wildfly desde la web oficial:

http://wildfly.org/downloads/

1.PNG

Se nos descargara el siguiente archivo comprimido wildfly-11.0.0.Final.zip, copiamos dicho archivo en los dos servidores, en este caso lo vamos a copiar en /opt y una vez copiado se procederá a descomprimirlo y  cambiar el nombre al archivo:

unzip wildfly-11.0.0.Final.zip

mv wildfly-11.0.0.Final.zip wildfly

Como ya he indicado anteriormente vamos a configurar wildfly  en modo dominio, servidor master (192.168.1.1) y slave (192.168.1.2), los servidores pueden tener cualquier nombre pero para que sea sencillo elegí estos.

Configuración del servidor maestro 192.168.1.1:

Accedemos a la ruta de configuración “/opt/wildfly/domain/configuration y editamos el fichero host.xml

vi host.xml

Indicamos al servidor que se trata del maestro:

…
<?xml version='1.0' encoding='UTF-8'?>
<host name="master"xmlns="urn:jboss:domain:5.0">
<extensions>
<extension module="org.jboss.as.jmx"/>
<extension module="org.wildfly.extension.core-management"/>
<extension module="org.wildfly.extension.elytron"/>
</extensions>
…

Configuramos la dirección de interfaz de administración y la interfaz pública para que el esclavo pueda conectarse al maestro, sustituimos las IPs 127.0.0.1 que vienen por defecto por la IP del servidor maestro 192.168.1.1

…

<interfaces>
<interface name="management">
<inet-address value="${jboss.bind.address.management:127.0.0.1}"/>
</interface>
<interface name="public">
<inet-address value="${jboss.bind.address:127.0.0.1}"/>
</interface>
</interfaces>
…

…
<interfaces>
<interface name="management">
<inet-address value="192.168.1.1"/>
</interface>
<interface name="public">
<inet-address value="192.168.1.1"/>
</interface>
</interfaces>
…

Procedemos a configurar un  grupo para el dominio,  por defecto vienen varios grupos creados (3), en este ejemplo nos vamos a quedar solo con uno, por lo que el resto los borramos e indicamos a nuestro grupo que se arranque automáticamente.

…
<servers>
<server name="server-one" group="main-server-group">
<!--
~  Remote JPDA debugging for a specific server
~             <jvm name="default">
~               <jvm-options>
~                 <option value="-agentlib:jdwp=transport=dt_socket,address=8787,server=y,suspend=n"/>
~               </jvm-options>
~            </jvm>
-->
</server>
<server name="server-two" group="main-server-group" auto-start="true">
<jvm name="default"/>
<!--
~  server-two avoids port conflicts by incrementing the ports in
~                  the default socket-group declared in the server-group
-->
<socket-bindings port-offset="150"/>
</server>
<server name="server-three" group="other-server-group" auto-start="false">
<jvm name="default"/>
<!--
~  server-three avoids port conflicts by incrementing the ports in
~                  the default socket-group declared in the server-group
-->
<socket-bindings port-offset="250"/>
</server>
</servers>
…

…
<servers>
<server name="MASTER" group="other-server-group" auto-start="true">
<!-- <jvm name="default"/> -->
<system-properties>
<property name="jvmRoute" value="master" boot-time="true"/>
</system-properties>
<!-- <socket-bindings port-offset="250"/>-->
</server>
</servers>
…

Para poder administrar nuestro dominio vía web y para que el servidor esclavo se conecte al maestro es necesario tener un usuario, por lo que procedemos a crearlo:

Cd /opt/wildfly/bin

 sudo ./add-user.sh

What type of user do you wish to add?
a) Management User (mgmt-users.properties)
b) Application User (application-users.properties)
(a): a
Enter the details of the new user to add.
Using realm 'ManagementRealm' as discovered from the existing property files.
Username : prueba

Password recommendations are listed below. To modify these restrictions edit the add-user.properties configuration file.
- The password should be different from the username
- The password should not be one of the following restricted values {root, admin, administrator}
- The password should contain at least 8 characters, 1 alphabetic character(s), 1 digit(s), 1 non-alphanumeric symbol(s)
Password :

WFLYDM0099: Password should have at least 8 characters!
Are you sure you want to use the password entered yes/no? yes
Re-enter Password :
What groups do you want this user to belong to? (Please enter a comma separated list, or leave blank for none)[  ]:
About to add user 'prueba' for realm 'ManagementRealm'
Is this correct yes/no? yes
Added user 'prueba' to file '/opt/wildfly/standalone/configuration/mgmt-users.properties'
Added user 'prueba' to file '/opt/wildfly/domain/configuration/mgmt-users.properties'
Added user 'prueba' with groups  to file '/opt/wildfly/standalone/configuration/mgmt-groups.properties'
Added user 'prueba' with groups  to file '/opt/wildfly/domain/configuration/mgmt-groups.properties'
Is this new user going to be used for one AS process to connect to another AS process?
e.g. for a slave host controller connecting to the master or for a Remoting connection for server to server EJB calls.
yes/no? yes
To represent the user add the following to the server-identities definition <secret value="MTIzNDU=" />

Nos debemos guardar  la clave cifrada <secret value=”MTIzNDU=” />que utilizaremos para que el servidoresclavo se conecte al maestro.

Configuración del servidor esclavo 192.168.1.2:

Accedemos a la ruta de configuración “/opt/wildfly/domain/configuration y editamos el fichero host.xml:

vi host.xml

Indicamos al servidor que se trata del esclavo:

<?xml version='1.0' encoding='UTF-8'?>
<host xmlns="urn:jboss:domain:5.0" name="master">
<extensions>
<extension module="org.jboss.as.jmx"/>
<extension module="org.wildfly.extension.core-management"/>
<extension module="org.wildfly.extension.elytron"/>
…

...
<?xml version='1.0' encoding='UTF-8'?>
<host name="slave" xmlns="urn:jboss:domain:5.0">
<extensions>
<extension module="org.jboss.as.jmx"/>
<extension module="org.wildfly.extension.core-management"/>
<extension module="org.wildfly.extension.elytron"/>
</extensions>
…

Configuramos la dirección de interfaz:

…
<interfaces>
<interface name="management">
<inet-address value="${jboss.bind.address.management:127.0.0.1}"/>
</interface>
<interface name="public">
<inet-address value="${jboss.bind.address:127.0.0.1}"/>
</interface>
</interfaces>
…

   …
<interfaces>
<interface name="management">
<inet-address value="192.138.1.2"/>
</interface>
<interface name="public">
<inet-address value="192.168.1.2"/>
</interface>
</interfaces>
…

Realizamos lo mismo que en el servidor maestro. Procedemos a configurar un  grupo para el dominio,  por defecto vienen varios grupos creados (3), en este ejemplo nos vamos a quedar solo con uno, por lo que el resto los borramos e indicamos a nuestro grupo que se arranque automáticamente.

…
<servers>
<server name="server-one" group="main-server-group">
<!--
              ~  Remote JPDA debugging for a specific server
              ~             <jvm name="default">
              ~               <jvm-options>
              ~                 <option value="-agentlib:jdwp=transport=dt_socket,address=8787,server=y,suspend=n"/>
              ~               </jvm-options>
              ~            </jvm>
              ~
 -->
</server>
<server name="server-two" group="main-server-group" auto-start="true">
<jvm name="default"/>
<!--
 ~ server-two avoids port conflicts by incrementing the ports in
 ~ the default socket-group declared in the server-group
 -->
<socket-bindings port-offset="150"/>
</server>
<server name="server-three" group="other-server-group" auto-start="false">
<jvm name="default"/>
<!--
 ~ server-three avoids port conflicts by incrementing the ports in
 ~ the default socket-group declared in the server-group
 -->
<socket-bindings port-offset="250"/>
</server>
</servers>
…

 …
<servers>
<server name="slave" group="other-server-group" auto-start="true">
<!-- <jvm name="default"/> -->
<system-properties>
<property name="jvmRoute" value="slave" boot-time="true"/>
</system-properties>
<!-- <socket-bindings port-offset="250"/> -->
</server>
</servers>
…

Configuramos la conexión contra el maestro:

…
<security-realms>
<security-realm name="ManagementRealm">
<authentication>
<local default-user="$local" skip-group-loading="true"/>
<properties path="mgmt-users.properties" relative-to="jboss.domain.config.dir"/>
</authentication>
<authorization map-groups-to-roles="false">
<properties path="mgmt-groups.properties" relative-to="jboss.domain.config.dir"/>
</authorization>
</security-realm>
<security-realm name="ApplicationRealm">
<server-identities>
<ssl>
<keystore path="application.keystore" relative-to="jboss.domain.config.dir" keystore-password="password"
 alias="server" key-password="password" generate-self-signed-certificate-host="localhost"/>
</ssl>
</server-identities>
<authentication>
<local default-user="$local" allowed-users="*" skip-group-loading="true"/>
<properties path="application-users.properties" relative-to="jboss.domain.config.dir"/>
</authentication>
<authorization>
<properties path="application-roles.properties" relative-to="jboss.domain.config.dir"/>
</authorization>
</security-realm>
</security-realms>
…

…
<security-realms>
<security-realm name="ManagementRealm">
<server-identities>
<secret value="MTIzNDU=" />
</server-identities>
<authentication>
<properties path="mgmt-users.properties" relative-to="jboss.domain.config.dir"/>
</authentication>
<authorization map-groups-to-roles="false">
<properties path="mgmt-groups.properties" relative-to="jboss.domain.config.dir"/>
</authorization>
</security-realm>
<security-realm name="ApplicationRealm">
<server-identities>
<ssl>
<keystore path="application.keystore" relative-to="jboss.domain.config.dir" keystore-password="password" alias="server" key-password="password" generate-self-signed-certificate-host="localhost"/>
</ssl>
</server-identities>
<authentication>
<local default-user="$local" allowed-users="*" skip-group-loading="true"/>
<properties path="application-users.properties" relative-to="jboss.domain.config.dir"/>
</authentication>
<authorization>
<properties path="application-roles.properties" relative-to="jboss.domain.config.dir"/>
</authorization>
</security-realm>
</security-realms>
…

…
<domain-controller>
<local/>
<!-- Alternative remote domain controller configuration with a host and port -->
<!-- <remote protocol="remote" host="${jboss.domain.master.address}" port="${jboss.domain.master.port:9999}" security-realm="ManagementRealm"/> -->
</domain-controller>
…

…   
<domain-controller>
<!-- Alternative remote domain controller configuration with a host and port -->
<remote protocol="remote" host="192.168.1.1" port="9999" security-realm="ManagementRealm"/>
</domain-controller>
…

Este ejemplo trata sobre un servidor de pruebas por lo que levantaremos los servidores wildfly de manera manual y no como servicio, de la siguiente forma, primero el maestro y segundo el esclavo:

cd /opt/wildfly/bin
./domain.sh

Si todo va bien no debe aparecer algo parecido en los log del sistema, indicando que se ha registrado el servidor esclavo.

[Host Controller] 13:15:37,292 INFO  [org.jboss.as.host.controller] (server-registration-threads - 1) WFLYHC0020: Registering server MASTER
[Host Controller] 13:15:49,198 INFO  [org.jboss.as.domain.controller] (Host Controller Service Threads - 7) WFLYHC0019: Registered remote slave host "slave", JBoss WildFly Full 11.0.0.Final (WildFly 3.0.8.Final)

Para verificar que funciona accedemos a la administración de wildfly, desde el navegador

http://192.168.1.1:9990/console/

2

Verificamos que en el grupo creado se encuentran los dos servidores.

3

Como se puede comprobar el servidor ha registrado al servidor maestro y al servidor esclavo.

Vamos a desplegar una aplicación de prueba llamada clusterjsp.war, para ello accedemos a la pestaña Deployments, server groupsother-server-group   y procedemos con su despliegue:

4

Una vez añadida accedemos a Content Repository y  verificamos que la aplicación se encuentra asignada a nuestro grupo:

5

Probamos su funcionamiento en ambos servidores:

Master                                                                        Slave

6.PNG

Configuración replicación de sesiones entre servidores diferentes.

Ahora vamos a configurar la replicación de sesión entre todos los servidores del domino, en internet no hay muchas información al respecto o por lo menos yo no la he encontrado.

Si no me equivoco, por defecto Wildfly viene configurado para la replicación de sesiones por multidifusión, Si no  tenéis restricciones en la red debería de funcionar sin problemas.

Problema: En las grandes empresas las redes están más cerradas por seguridad y la multidifusión se encuentra cerrada/bloqueada. Este era mi caso.

Solución: Configurar la replicación de sesión mediante tcp, para ello editamos en el servidor master el  fichero domain.xml presente en /opt/wildfly/domain/configuration/.

Original:

<subsystem xmlns="urn:jboss:domain:jdr:1.0"/>
<subsystem xmlns="urn:jboss:domain:jgroups:5.0">
<channels default="ee">
<channel name="ee" stack="udp" cluster="ejb"/>
</channels>
<stacks>
<stack name="udp">
<transport type="UDP" socket-binding="jgroups-udp"/>
<protocol type="PING"/>
<protocol type="MERGE3"/>
<protocol type="FD_SOCK"/>
<protocol type="FD_ALL"/>
<protocol type="VERIFY_SUSPECT"/>
<protocol type="pbcast.NAKACK2"/>
<protocol type="UNICAST3"/>
<protocol type="pbcast.STABLE"/>
<protocol type="pbcast.GMS"/>
<protocol type="UFC"/>
<protocol type="MFC"/>
<protocol type="FRAG2"/>
</stack>
<stack name="tcp">
<transport type="TCP" socket-binding="jgroups-tcp"/>
<socket-protocol type="MPING" socket-binding="jgroups-mping"/>
<protocol type="MERGE3"/>
<protocol type="FD_SOCK"/>
<protocol type="FD_ALL"/>
<protocol type="VERIFY_SUSPECT"/>
<protocol type="pbcast.NAKACK2"/>
<protocol type="UNICAST3"/>
<protocol type="pbcast.STABLE"/>
<protocol type="pbcast.GMS"/>
<protocol type="MFC"/>
<protocol type="FRAG2"/>
</stack>
</stacks>
</subsystem>

Modificado:

<subsystem xmlns="urn:jboss:domain:jdr:1.0"/>
<subsystem xmlns="urn:jboss:domain:jgroups:5.0">
<channels default="ee">
<channel name="ee" stack="tcp" cluster="ejb"/>
</channels>
<stacks>
<stack name="tcp">
<transport type="TCP" socket-binding="jgroups-tcp"/>
<protocol type="org.jgroups.protocols.TCPPING">
<property name="initial_hosts">
                     192.168.1.1[7600], 192.168.1.2[7600]
</property>
<property name="num_initial_members">
                                2
</property>
<property name="timeout">
                                1000
</property>
</protocol>
<protocol type="MERGE3"/>
<protocol type="FD_SOCK" socket-binding="jgroups-tcp-fd"/>
<protocol type="FD_ALL"/>
<protocol type="VERIFY_SUSPECT"/>
<protocol type="pbcast.NAKACK2"/>
<protocol type="UNICAST3"/>
<protocol type="pbcast.STABLE"/>
<protocol type="pbcast.GMS"/>
<protocol type="MFC"/>
<protocol type="FRAG2"/>
</stack>
</stacks>
</subsystem>
<subsystem xmlns="urn:jboss:domain:jmx:1.3">
<expose-resolved-model/>
<expose-expression-model/>
</subsystem>
<subsystem xmlns="urn:jboss:domain:jpa:1.1">
<jpa default-datasource="" default-extended-persistence-inheritance="DEEP"/>
</subsystem>

 

Para finalizar vamos a configurar apache como balanceador en el siguiente enlace:

https://loveyourlinux.com/apache/

 

Anuncios

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión /  Cambiar )

Google photo

Estás comentando usando tu cuenta de Google. Cerrar sesión /  Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión /  Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión /  Cambiar )

Conectando a %s