Кластерный синглтон с использованием Wildfly?

Я пытаюсь создать простой кластер Singleton на Wildfly 8.2. Я настроил 2 экземпляра Wildfly, работающих в автономной кластерной конфигурации. Мое приложение развернуто на обоих устройствах, и я могу без проблем получить к нему доступ.

Мой кластерный EJB выглядит так:

@Named
@Clustered
@Singleton
public class PeekPokeEJB implements PeekPoke {

    /**
     * Logger for this class
     */
    private static final Logger logger = Logger
            .getLogger(PeekPokeEJB.class);

    private static final long serialVersionUID = 2332663907180293111L;

    private int value = -1;

    @Override
    public void poke() {
        if (logger.isDebugEnabled()) {
            logger.debug("poke() - start"); //$NON-NLS-1$
        }

        Random rand = new SecureRandom();
        int newValue = rand.nextInt();
        if (logger.isDebugEnabled()) {
            logger.debug("poke() - int newValue=" + newValue); //$NON-NLS-1$
        }

        this.value = newValue;

        if (logger.isDebugEnabled()) {
            logger.debug("poke() - end"); //$NON-NLS-1$
        }
    }

    @Override
    public void peek() {
        if (logger.isDebugEnabled()) {
            logger.debug("peek() - start"); //$NON-NLS-1$
        }

        if (logger.isDebugEnabled()) {
            logger.debug("peek() - value=" + value); //$NON-NLS-1$
        }

        if (logger.isDebugEnabled()) {
            logger.debug("peek() - end"); //$NON-NLS-1$
        }
    }
}

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

@Path("/test")
@Named
public class TestRS extends AbstractRestService {
    /**
     * Logger for this class
     */
    private static final Logger logger = Logger.getLogger(TestRS.class);

    @Inject
    private PeekPoke ejb = null;

    @GET
    @Path("/poke")
    public void poke() {
        if (logger.isDebugEnabled()) {
            logger.debug("poke() - start"); //$NON-NLS-1$
        }

        this.ejb.poke();

        if (logger.isDebugEnabled()) {
            logger.debug("poke() - end"); //$NON-NLS-1$
        }
    }

    @GET
    @Path("/peek")
    public void peek() {
        if (logger.isDebugEnabled()) {
            logger.debug("peek() - start"); //$NON-NLS-1$
        }

        this.ejb.peek();

        if (logger.isDebugEnabled()) {
            logger.debug("peek() - end"); //$NON-NLS-1$
        }
    }
}

Я могу позвонить как peek а также poke методы из одного экземпляра Wildfly и получить ожидаемое значение. Однако, если я пытаюсь вызвать poke из одного экземпляра и посмотреть из другого, я вижу, что значения не реплицируются по всем EJB-компонентам.

У меня сложилось впечатление, что кластерный синглтон будет повторять значениеvalueна обоих серверах приложений, предоставляя одно и то же значение независимо от того, на каком хосте я сделал peek позвонить с. Это не правильно? Я что-то упускаю, что еще нужно добавить в этот код?

Буду признателен за любую помощь, которую вы можете мне дать! Спасибо!

1 ответ

Решение

Сессионные компоненты Singleton предоставляют формальную программную конструкцию, которая гарантирует, что сессионный компонент будет создан один раз для каждого приложения в конкретной виртуальной машине Java (JVM).

В JSR 318: Enterprise JavaBeans TM версии 3.1 написано:

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

Следовательно, в кластерном приложении каждый член кластера будет иметь свой собственный экземпляр сессионных компонентов синглтона, и данные не будут совместно использоваться экземплярами JVM (в реализации Wildfly).

В Wildfly, если вам нужен только один экземпляр синглтона в области видимости кластера, вы можете использовать SingletonService реализация. Используя SingletonServiceцелевая служба установлена ​​на каждом узле кластера, но запускается только на одном узле в любой момент времени.

Увидеть:

ОБНОВИТЬ:

WildFly 10 добавляет возможность развертывания данного приложения в качестве "одиночного развертывания". Это новая реализация функции, которая существовала в AS 6.0 и более ранних версиях. При развертывании на группе кластерных серверов одноэтапное развертывание будет развертываться только на одном узле в любой момент времени. Если узел, на котором развертывание активно, останавливается или дает сбой, развертывание автоматически запускается на другом узле.

Смотрите: WildFly 10 Final теперь доступен!

Другие вопросы по тегам