无法在 Openshift 环境中初始化 hazelcast。服务器套接字绑定失败。没有权限

Could not initiate hazelcast in Open shift environment. Server Socket bind has failed. Permission Denied

我正在尝试在 tomcat 运行 的 openshift 环境中启动一个 hazelcast 实例。我知道 openshift 不允许绑定 15000 - 35530 以外的端口。因此我尝试使用端口 15700 和 public-address as $OPENSHIFT_DIY_IP 来绑定它。但因权限被拒绝而失败。

下面是我使用 spring 的实例配置。

<hz:hazelcast id="instance">
        <hz:config>
            <hz:management-center enabled="false" url="http://localhost:8484/mancenter"></hz:management-center>
            <hz:network public-address="#{systemProperties['publicip']}"
                port="15700" port-auto-increment="true">
                <hz:join>
                    <hz:multicast enabled="false" />
                    <hz:tcp-ip enabled="true">
                        <hz:interface>#{systemProperties['publicip']}</hz:interface>
                    </hz:tcp-ip>
                </hz:join>
            </hz:network>
</hz:hazelcast>

下面是我的命令行参数。这里 public ip 指的是 $OPENSHIFT_DIY_IP 并且 JVM 是使用 openshift start hook 启动的。

 -Djava.util.logging.manager=org.apache.juli.ClassLoaderLogManager
 -Dpublicip=127.12.249.1
 -Dhazelcast.socket.bind.any=false
 -Dhazelcast.socket.server.bind.any=false
 -Dhazelcast.socket.client.bind.any=false
 -Dhazelcast.socket.client.bind=false
 -Xms64m
 -Xmx512m
 -XX:MaxPermSize=256m
 -Xss228k
 -XX:+UseParallelGC
 -XX:MaxGCPauseMillis=1500
 -XX:GCTimeRatio=9
 -XX:+DisableExplicitGC
 -Djava.endorsed.dirs=/var/lib/openshift/558c6acf5004469904000057/app-root/data/tomcat8/apache-tomcat-8.0.23/endorsed
 -Dcatalina.base=/var/lib/openshift/558c6acf5004469904000057/app-root/data/tomcat8/apache-tomcat-8.0.23
 -Dcatalina.home=/var/lib/openshift/558c6acf5004469904000057/app-root/data/tomcat8/apache-tomcat-8.0.23
 -Djava.io.tmpdir=/var/lib/openshift/558c6acf5004469904000057/app-root/data/tomcat8/apache-tomcat-8.0.23/temp

下面是预期轨迹。

timestamp=2015-06-26 14:44:28.954, thread=localhost-startStop-1, level=INFO  location=PropertiesLoaderSupport.java:172 logger=o.s.b.f.c.PropertyPlaceholderConfigurer Loading properties file from class path resource [web-db.properties]
timestamp=2015-06-26 14:44:29.253, thread=localhost-startStop-1, level=INFO  location=PostProcessorRegistrationDelegate.java:309 logger=o.s.c.s.PostProcessorRegistrationDelegate$BeanPostProcessorChecker Bean 'mongo' of type [class org.springframework.data.mongodb.core.MongoFactoryBean] is not eligible for getting processed by all BeanPostProcessors (for example: not eligible for auto-proxying)
timestamp=2015-06-26 14:44:29.376, thread=localhost-startStop-1, level=INFO  location=PostProcessorRegistrationDelegate.java:309 logger=o.s.c.s.PostProcessorRegistrationDelegate$BeanPostProcessorChecker Bean 'org.springframework.scheduling.annotation.SchedulingConfiguration' of type [class org.springframework.scheduling.annotation.SchedulingConfiguration$$EnhancerBySpringCGLIB$dc811d] is not eligible for getting processed by all BeanPostProcessors (for example: not eligible for auto-proxying)
26-Jun-2015 14:44:31.372 INFO [localhost-startStop-1] com.hazelcast.instance.DefaultAddressPicker.null [LOCAL] [dev] [3.4.2] Interfaces is disabled, trying to pick one address from TCP-IP config addresses: [127.12.249.1]
26-Jun-2015 14:44:31.373 INFO [localhost-startStop-1] com.hazelcast.instance.DefaultAddressPicker.null [LOCAL] [dev] [3.4.2] Prefer IPv4 stack is true.
26-Jun-2015 14:44:31.375 WARNING [localhost-startStop-1] com.hazelcast.instance.DefaultAddressPicker.null [LOCAL] [dev] [3.4.2] Could not find a matching address to start with! Picking one of non-loopback addresses.
26-Jun-2015 14:44:31.504 SEVERE [localhost-startStop-1] com.hazelcast.instance.DefaultAddressPicker.null [LOCAL] [dev] [3.4.2] ServerSocket bind has failed. Hazelcast cannot start! config-port: 15700, latest-port: 15800
 com.hazelcast.core.HazelcastException: ServerSocket bind has failed. Hazelcast cannot start! config-port: 15700, latest-port: 15800
        at com.hazelcast.instance.DefaultAddressPicker.pickAddress(DefaultAddressPicker.java:117)
        at com.hazelcast.instance.Node.<init>(Node.java:143)
        at com.hazelcast.instance.HazelcastInstanceImpl.<init>(HazelcastInstanceImpl.java:117)
        at com.hazelcast.instance.HazelcastInstanceFactory.constructHazelcastInstance(HazelcastInstanceFactory.java:153)
        at com.hazelcast.instance.HazelcastInstanceFactory.newHazelcastInstance(HazelcastInstanceFactory.java:136)
        at com.hazelcast.instance.HazelcastInstanceFactory.newHazelcastInstance(HazelcastInstanceFactory.java:112)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.lang.reflect.Method.invoke(Method.java:483)
        at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:166)
        at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:586)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1094)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:989)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:504)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:475)
        at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:304)
        at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:228)
        at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:300)
        at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:195)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1017)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:960)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:858)
        at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:480)
        at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:87)
        at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:289)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1185)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:537)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:475)
        at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:304)
        at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:228)
        at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:300)
        at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:195)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1017)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:960)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:858)
        at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:480)
        at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:87)
        at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:289)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1185)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:537)
        at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:475)
        at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:304)
        at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:228)
        at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:300)
        at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:195)
        at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:703)
        at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:760)
        at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:482)
        at org.springframework.web.context.ContextLoader.configureAndRefreshWebApplicationContext(ContextLoader.java:403)
        at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:306)
        at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:106)
        at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4729)
        at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5167)
        at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150)
        at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:725)
        at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:701)
        at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:717)
        at org.apache.catalina.startup.HostConfig.deployWAR(HostConfig.java:945)
        at org.apache.catalina.startup.HostConfig$DeployWar.run(HostConfig.java:1768)
        at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
        at java.util.concurrent.FutureTask.run(FutureTask.java:266)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
        at java.lang.Thread.run(Thread.java:745)
Caused by: java.net.SocketException: Permission denied
        at sun.nio.ch.Net.bind0(Native Method)
        at sun.nio.ch.Net.bind(Net.java:436)
        at sun.nio.ch.Net.bind(Net.java:428)
        at sun.nio.ch.ServerSocketChannelImpl.bind(ServerSocketChannelImpl.java:214)
        at sun.nio.ch.ServerSocketAdaptor.bind(ServerSocketAdaptor.java:74)
        at com.hazelcast.instance.DefaultAddressPicker.pickAddress(DefaultAddressPicker.java:98)

经过长时间的斗争,我终于弄明白了。我们需要将此变量 hazelcast.local.localAddress 设置为 $OPENSHIFT_DIY_IP

我在节点启动时添加 -Dhazelcast.local.localAddress=$OPENSHIFT_DIY_IP 解决了

在较新版本的 hazelcast 中,可以在配置中这样设置:

config.setProperty("hazelcast.local.localAddress", System.getenv("OPENSHIFT_DIY_IP "));

我正在使用 wildfly,所以对我来说是:

config.setProperty("hazelcast.local.localAddress", System.getenv("OPENSHIFT_WILDFLY_IP"));

我还必须添加这 2 个额外的配置:

config.setProperty("hazelcast.socket.client.bind.any", "false");
config.setProperty("hazelcast.socket.bind.any", "false");