亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

Java Testcontainers - 無法連接到公開端口

Java Testcontainers - 無法連接到公開端口

POPMUISE 2023-09-20 14:58:15
我使用 javax.mail 實現了 POP3 服務器和客戶端,只是為了嘗試使用 Docker 進行集成測試。因此,我基于 openjdk:8-jre 映像創建了兩個 Docker 映像,并將我的 jar 復制到其中并啟動它。根據我的配置(見下文),它正在工作。他們正在互相交談。但是,由于想要進行多個集成測試,為每個測試構建一個映像并啟動它們將是一件很乏味的事情。我也不知道如何自動化結果。但后來我偶然發現了 TestContainers,這似乎對實施這些測試有很大幫助。因此,我開始使用 POP3 服務器映像作為 GenericContainer 將這些測試移植到 TestContainers,并在 JUnit 測試方法中啟動我的 POP3 客戶端類。我公開了 POP3 服務器正在偵聽的端口 24999。但是當我嘗試連接到服務器時,出現以下錯誤:com.sun.mail.util.MailConnectException: Couldn't connect to host, port: localhost, 32782; timeout -1;  nested exception is:    java.net.ConnectException: Connection refused...TestContainers 中可能缺少一些設置。請你幫助我好嗎。這是我正在使用的代碼:public class DockerPop3AutocryptKeyProvidingAndReceivingTest {    @Test    public void test() throws InterruptedException {        GenericContainer container = new GenericContainer<>("immerfroehlich/emailfilter:latest")                .withExposedPorts(24999);                container.start();                String host = container.getContainerIpAddress();        String port = container.getFirstMappedPort().toString();        //The following is simplified, but copied from the working jar used in the Docker Client image/container        MyPOP3Client client = new MyPOP3Client(host, port);        client.connect();                container.stop();    }}這就是我創建 Docker 鏡像的方式:FROM openjdk:8-jreADD build/distributions/MyPOP3Server.tar . #This is where I have packed all the needed files to. It gets unpacked by Docker.#EXPOSE 24999 #I tried both with and without this exposeWORKDIR /MyPOP3Server/binENTRYPOINT ["sh","MyPOP3Server"] #Executes the shell script which runs java with my jar這是在 Server Jar 內運行的代碼的簡化版本:MyPOP3Server server = new MyPOP3Server();server.listenToPort(24999);請告訴我我錯過了什么。這里有什么問題嗎?謝謝并致以親切的問候。
查看完整描述

4 回答

?
RISEBY

TA貢獻1856條經驗 獲得超5個贊

其他答案中有一些很好的建議;我將用其他一些技巧來補充這些內容:

正如已經建議的:

  • 絕對要添加,LogConsumer以便您可以看到容器的日志輸出 - 也許現在或將來會出現一些有用的東西。擁有它總是好的。

  • 在容器啟動后、啟動客戶端之前設置斷點。

此外,我希望以下事情能夠有所作為。在斷點處暫停時:

  • docker ps -a在終端中運行

  • 首先,檢查您的容器是否正在運行并且尚未退出。如果它已退出,請從終端查看容器的日志。

  • 其次,檢查輸出中的端口映射docker ps。您應該看到類似的內容0.0.0.0:32768->24999/tcp(盡管第一個端口號是隨機的)。

  • 在您的 IDE 中進行評估container.getFirstMappedPort()并檢查您返回的端口號是否與隨機公開的端口相同。除非您在本地計算機上安裝了非常不尋常的 Docker,否則應該可以通過localhost:+ 此端口訪問此容器。

  • 如果您已經走到這一步,那么容器或客戶端代碼可能有問題。nc您可以嘗試將不同的客戶端連接到正在運行的容器 -如果您手邊沒有另一個 POP3 客戶端,甚至類似的操作也會有所幫助。

另一件可以嘗試的事情是手動運行容器,只是為了減少發生的間接數量。您給出的 Testcontainers 代碼片段相當于:

docker run -p 24999 immerfroehlich/emailfilter:latest

您可能會發現這可以幫助您將問題空間劃分為更小的部分。


查看完整回答
反對 回復 2023-09-20
?
慕妹3242003

TA貢獻1824條經驗 獲得超6個贊

嘗試添加 http 檢查。

 new GenericContainer<>("immerfroehlich/emailfilter:latest")
 .withExposedPorts(24999)
 .waitingFor(new HttpWaitStrategy().forPort(24999)
 .withStartupTimeout(Duration.ofMinutes(5)));

您的容器可能已啟動,但您嘗試在服務器初始化之前進行連接。

另外,注冊一個日志附加程序以查看容器內服務器的運行情況。

 .withLogConsumer(new Slf4jLogConsumer(LoggerFactory.getLogger(
              DockerPop3AutocryptKeyProvidingAndReceivingTest.class)))


查看完整回答
反對 回復 2023-09-20
?
ABOUTYOU

TA貢獻1812條經驗 獲得超5個贊

這引導我找到解決方案。這是缺少 WaitStrategy 和端口映射問題的結合。


這是我所做的:1)在 MyPop3Server.listenToPort(String port) 方法中,我添加了一個 System.out.println:


public class MyPop3Server {

  public void listenToPort(String port) {

     //simplified: do initialization and listenToPort

     System.out.println("Awaiting Connection...");

  }

}

在我的測試中,我添加了一個 LogMessageWaitStrategy 來偵聽“等待連接”


GenericContainer container = new GenericContainer<>("immerfroehlich/emailfilter:latest")

   .waitingFor(Wait.forLogMessage("Awaiting Connection.*", 1))

   .withExposedPorts(24999);

2)我從container.getFirstMappedPort()切換到


container.getMappedPort(24999);

這是整個更改后的工作測試代碼:


public class DockerPop3AutocryptKeyProvidingAndReceivingTest {

    @Test

    public void test() throws InterruptedException {

        GenericContainer container = new GenericContainer<>("immerfroehlich/emailfilter:latest")

                .waitingFor(Wait.forLogMessage("Awaiting Connection.*", 1))

                .withExposedPorts(24999);


        container.start();


        String host = container.getContainerIpAddress();

        String port = container.getMappedPort(24999).toString();


        //The following is simplified, but copied from the working jar used in the Docker Client image/container

        MyPOP3Client client = new MyPOP3Client(host, port);

        client.connect();


        container.stop();

    }

}


查看完整回答
反對 回復 2023-09-20
?
慕容3067478

TA貢獻1773條經驗 獲得超3個贊

試試container.getMappedPort(24999)getFirstMappedPort。可能您的 docker 映像公開了幾個端口。



查看完整回答
反對 回復 2023-09-20
  • 4 回答
  • 0 關注
  • 158 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號