通过 Web 应用程序发起的 Java 套接字连接,在服务器重新启动时重新打开

发布于 2024-12-03 03:57:31 字数 2326 浏览 2 评论 0原文

我有一个在 Tomcat 6 上运行的 Web 应用程序,安装在 Windows Server 2003 上。该应用程序打开与不同服务器的套接字连接以检索一些数据。该应用程序已经运行了几个月。但有两次由于某种原因 Web 应用程序停止工作。在这两次事件中,运行 netstat 命令(使用 -ano)显示 Web 应用程序通过套接字连接连接的端口上大约有 4.000 个 tcp 连接(处于 TIME_WAIT 状态)。

奇怪的事情从这里开始:我停止了 tomcat,过了一会儿这些连接就断开了(再次运行 netstat)。我重新启动tomcat,这些连接都回到TIME_WAIT状态!

我不知道为什么这些连接会重新打开。我可能缺少一些非常明显的东西。有什么想法吗?

谢谢。

编辑:

这是进行套接字管理的代码:

    public void openSocketConnection() throws Exception {
    socket = createSingleSocket();
    socket.setSoTimeout(5000);
    out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream(), "UTF8")), true);
    in = new BufferedReader(new InputStreamReader(socket.getInputStream(), "UTF8"));
}

/**
 * Closes socket and output input streams.
 */
public void closeSocketConnection() throws IOException {
    socket.close();
    out.close();
    in.close();
}

/**
 * Writes the input to the socket and returns the output response
 * 
 * @param input
 *            a String to write on the socket
 * @return output a String that the socket returns
 * @throws Exception
 */
public String writeReadSocket(String input) throws Exception {
    openSocketConnection();
    out.println(input);
    logger.debug("Socket Input:" + input);
    String output = in.readLine();
    logger.debug("Socket output:" + output);
    closeSocketConnection();
    return output;
}

/**
 * Method overiden by Spring. We use the method injection technique, so that we have a new socket instance in every call to openSocketConnection()
 * method
 */
public abstract Socket createSingleSocket();

调用的方法是 writeReadSocket。

最后一个方法(createSingleSocket)由spring使用,因此我可以为每次调用openConnection()方法创建一个新的Socket实例(顺便说一句,我不确定为每个请求创建一个新的Socket是否正确)。在 Spring 配置文件中我有这个:

<!--  prototype scope is used to instantiate a new socket instance in every createSingleSocket() method call. -->
<bean id="socket" class="java.net.Socket"  scope="prototype">
    <constructor-arg type="String" value="${socket.url}"/>
    <constructor-arg type="int" value="${socket.port}"/>
</bean>

<bean id="socketConnector" class="gr.diassa.dsjsonrpcsuite.socket.SocketConnector">
    <lookup-method name="createSingleSocket" bean="socket"/>
</bean>

I have a web application running on a Tomcat 6, installed on a Windows Server 2003. This application opens socket connections with at different server to retrieve some data. This application has been working for months. But in two occurrences for some reason the web application stopped working. In both occurrences running the netstat command (with -ano) showed about 4.000 tcp connections (on TIME_WAIT state) on the port that the web app is connecting through the socket connection.

The strange thing starts here: I stop tomcat, after a while those connections drop (running netstat again). I restart tomcat and these connections are all back on TIME_WAIT state!!!

I have no clue why these connections are reopened. It might be something very obvious that I am missing. Any ideas?

Thank you.

EDIT:

Here is the code that does the socket management:

    public void openSocketConnection() throws Exception {
    socket = createSingleSocket();
    socket.setSoTimeout(5000);
    out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream(), "UTF8")), true);
    in = new BufferedReader(new InputStreamReader(socket.getInputStream(), "UTF8"));
}

/**
 * Closes socket and output input streams.
 */
public void closeSocketConnection() throws IOException {
    socket.close();
    out.close();
    in.close();
}

/**
 * Writes the input to the socket and returns the output response
 * 
 * @param input
 *            a String to write on the socket
 * @return output a String that the socket returns
 * @throws Exception
 */
public String writeReadSocket(String input) throws Exception {
    openSocketConnection();
    out.println(input);
    logger.debug("Socket Input:" + input);
    String output = in.readLine();
    logger.debug("Socket output:" + output);
    closeSocketConnection();
    return output;
}

/**
 * Method overiden by Spring. We use the method injection technique, so that we have a new socket instance in every call to openSocketConnection()
 * method
 */
public abstract Socket createSingleSocket();

The method that is called is writeReadSocket.

The last method (createSingleSocket) is used by spring, so I can have a new Socket instance for every call to openConnection() method (by the way, I am not sure if this is correct to have a new Socket for every request). In a Spring configuration file I have this:

<!--  prototype scope is used to instantiate a new socket instance in every createSingleSocket() method call. -->
<bean id="socket" class="java.net.Socket"  scope="prototype">
    <constructor-arg type="String" value="${socket.url}"/>
    <constructor-arg type="int" value="${socket.port}"/>
</bean>

<bean id="socketConnector" class="gr.diassa.dsjsonrpcsuite.socket.SocketConnector">
    <lookup-method name="createSingleSocket" bean="socket"/>
</bean>

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

半城柳色半声笛 2024-12-10 03:57:31

请检查几件事

  1. 请确保在使用完客户端套接字后已将其关闭。
  2. 创建套接字时,指定适当的超时。

Please check couple of things

  1. Please make sure you have closed the client socket after you have finished using it.
  2. When you create a socket, specify a proper timeout.
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文