Apache cxf не смог отправить сообщение и время ожидания чтения
Что может быть причиной:
org.apache.cxf.interceptor.Fault: Could not send Message.
Caused by: java.net.SocketTimeoutException: SocketTimeoutException invoking https://xxx.xxx.xxx.xxx:8443/services/test: Read timed out
Обычно это происходит после отправки запроса на мыло к ws
. Я использую apache cxf
. Я полностью уверен, что ws
запущен, так как до истечения тайм-аута клиент отправит еще 2 запроса. Тайм-аут происходит в третьем запросе мыла.
Ответы
Ответ 1
Я тоже столкнулся с этой ошибкой для моего клиента webservice. Решение, которое сработало для меня, - это настроить клиент http в конфигурационном файле CXF (cxf.xml).
Как описано в документе Apache CXF:
1. Добавьте пространство имен http-conduit и xsd:
<beans ...
xmlns:http-conf="http://cxf.apache.org/transports/http/configuration
...
xsi:schemaLocation="...
http://cxf.apache.org/transports/http/configuration
http://cxf.apache.org/schemas/configuration/http-conf.xsd
...">
2. Добавьте тег/элемент http-conduit и установите для параметра RecieveTimeout/ConnectionTimeout значение 180000ms:
<http-conf:conduit name="*.http-conduit">
<http-conf:client
ConnectionTimeout="300000"
ReceiveTimeout="300000"/>
</http-conf:conduit>
Ответ 2
Сообщение об ошибке означает, что клиент веб-службы пытался получать данные из удаленной веб-службы по сети, но никаких данных не было получено в течение определенного периода времени, поэтому клиент веб-службы остановил ожидание данных получен.
Одна из возможных причин может заключаться в том, что свойство timeout
слишком низкое. По умолчанию установлены значения cxf по умолчанию 30000 и 60000 мс соответственно. Они могут быть изменены в зависимости от того, как вы создаете своего клиента.
Если вы создаете клиента с помощью java-кода, вы можете использовать:
//1 minute for connection
((BindingProvider) wsPort).getRequestContext().put("com.sun.xml.ws.connect.timeout", 1 * 60 * 1000);
//3 minutes for request
((BindingProvider) wsPort).getRequestContext().put("com.sun.xml.ws.request.timeout", 3 * 60 * 1000);
Если вы используете Spring, вы можете использовать такую карту:
<util:map id="jaxwsProperties">
<entry key="com.sun.xml.internal.ws.request.timeout">
<value type="java.lang.Integer">120000</value>
</entry>
<entry key="com.sun.xml.internal.ws.connect.timeout">
<value type="java.lang.Integer">60000</value>
</entry>
</util:map>
Затем установите это отображение в конфигурацию <jaxws:client.../>
.
Ответ 3
Другой вариант для тайм-аутов конфигурации (программно):
JaxWsProxyFactoryBean factory = new JaxWsProxyFactoryBean();
Object serviceClass = factory.create();
defineTimeouts(serviceClass);
static void defineTimeouts(Object serviceClass) {
Client cxfClient = ClientProxy.getClient(serviceClass);
HTTPConduit httpConduit = (HTTPConduit) cxfClient.getConduit();
HTTPClientPolicy httpClientPolicy = new HTTPClientPolicy();
httpClientPolicy.setConnectionTimeout(DEFAULT_CLIENT_CONNECTION_TIMEOUT);
httpClientPolicy.setReceiveTimeout(DEFAULT_CLIENT_RECEIVE_TIMEOUT);
httpConduit.setClient(httpClientPolicy);
}
Ответ 4
Возможно, вы захотите изменить параметр receiveTimeout из Apache CXF src и заменить существующий cxf-rt-transports-http-version.jar на своем сервере.
Краткие инструкции: (Получил инструкции из Wildfly 8.2/время ожидания отладки)
- Загрузить CXF2.7.16 src из apache
- Добавить maven/bin в PATH
- Экспортировать файл MAVEN_OPTS = -Xmx512m для исправления ошибок перм
- Откройте. /rt/transports/http/src/main/resources/schemas/wsdl/http -conf.xsd и измените ReceiveTimeout с 60000 на все, что необходимо, например. 600000 (10 минут)
- Запустить mvn -Pfastinstall
- Получите "исправленный" cxf-rt-transports-http-2.7.16.jar из папки. /rt/transports/http/target.
- Замените cxf-rt-transports-http-2.7.16.jar на своем сервере. Например, с wildfly8.2 он находится в папке. //modules/system/layers/base/org/apache/cxf/impl/main и не забудьте обновить module.xml внутри той же папки, чтобы использовать этот исправленный cxf-rt -transports-HTTP-2.7.16.jar.
Это должно устранить исключение SocketTimeoutException, вызванное базовым Apache CXF, используемым на сервере.