{"record":{"id":"b15aaf3b8a998e2c","repo":"quarkusio/quarkus","slug":"no-virtual-channel-available","errorCode":null,"errorMessage":"No virtual channel available","messagePattern":"No virtual channel available","errorType":"exception","errorClass":"RuntimeException","httpStatus":null,"severity":"error","filePath":"extensions/netty/runtime/src/main/java/io/quarkus/netty/runtime/virtual/VirtualClientConnection.java","lineNumber":117,"sourceCode":"    public static VirtualClientConnection connect(VirtualResponseHandler handler, VirtualAddress remoteAddress) {\n        return connect(handler, remoteAddress, remoteAddress);\n    }\n\n    /**\n     * Establish a virtual intra-JVM connection\n     *\n     * @param remoteAddress\n     * @param clientAddress\n     * @return\n     */\n    public static VirtualClientConnection connect(VirtualResponseHandler handler, VirtualAddress remoteAddress,\n            SocketAddress clientAddress) {\n        if (clientAddress == null)\n            clientAddress = remoteAddress;\n\n        Channel boundChannel = VirtualChannelRegistry.get(remoteAddress);\n        if (boundChannel == null) {\n            throw new RuntimeException(\"No virtual channel available\");\n        }\n        if (!(boundChannel instanceof VirtualServerChannel)) {\n            throw new RuntimeException(\"Should be virtual server channel: \" + boundChannel.getClass().getName());\n        }\n\n        VirtualServerChannel serverChannel = (VirtualServerChannel) boundChannel;\n        VirtualClientConnection conn = new VirtualClientConnection(clientAddress, handler);\n        conn.peer = serverChannel.serve(conn);\n        return conn;\n    }\n}\n","sourceCodeStart":99,"sourceCodeEnd":129,"githubUrl":"https://github.com/quarkusio/quarkus/blob/e1c734241f34c7919086ceb4c9262b4a58f6de44/extensions/netty/runtime/src/main/java/io/quarkus/netty/runtime/virtual/VirtualClientConnection.java#L99-L129","documentation":"VirtualClientConnection.connect looks up the remote address in VirtualChannelRegistry to find a bound server channel. If no virtual channel is registered under that remote address, a RuntimeException(\"No virtual channel available\") is thrown — the virtual-transport equivalent of 'connection refused': nothing is listening at that address.","triggerScenarios":"Connecting a virtual client to a remote VirtualAddress that no server channel has bound; connecting before the server finished binding; address typo/mismatch between the bound VirtualAddress and the connect target; server channel closed (unregistered) before the client connects.","commonSituations":"In-memory client/server test setups where the client connect races the server bind; tests restarted without rebinding; using raw SocketAddress values that don't match the registered VirtualAddress instance; teardown ordering shutting down the server first.","solutions":["Ensure the virtual server channel is bound and still active before the client connects (await bind().sync() and check registry).","Use the exact VirtualAddress instance returned by the server's bind for the client's remote address.","Close connections before shutting the server down; keep server lifetime scoped around client usage.","Add retry/await logic (e.g. Awaitility) for the registry entry to appear in concurrent tests."],"exampleFix":"// before\nVirtualClientConnection.connect(channel, peer, remoteAddress); // server not bound yet -> throws\n// after\nserverChannel.bind(localAddr).syncUninterruptibly(); // guarantee bound first\nawait().atMost(2, SECONDS).until(() -> VirtualChannelRegistry.get(localAddr) != null);\nVirtualClientConnection.connect(channel, peer, localAddr);","handlingStrategy":"retry","validationCode":"if (VirtualChannelRegistry.get(remoteAddress) == null) {\n    throw new IllegalStateException(\"no virtual server bound at \" + remoteAddress + \"; bind the server first\");\n}","typeGuard":null,"tryCatchPattern":"try {\n    VirtualClientConnection.connect(channel, peer, remoteAddress);\n} catch (RuntimeException e) {\n    if (\"No virtual channel available\".equals(e.getMessage())) {\n        await().atMost(2, SECONDS).until(() -> VirtualChannelRegistry.get(remoteAddress) != null);\n        VirtualClientConnection.connect(channel, peer, remoteAddress);\n    } else { throw e; }\n}","preventionTips":["Always await the server's bind completion before clients connect","Reuse the exact VirtualAddress instance returned from the bind for the client's remote address","Order shutdown: close client connections before the server channel","In tests, poll the registry (Awaitility) instead of connecting immediately"],"tags":["netty","virtual-channel","connect","connection-refused"],"backgroundTag":"virtual-connection-no-server-bound","analyzedSha":"e1c734241f34c7919086ceb4c9262b4a58f6de44","analyzedAt":"2026-09-05T17:01:29.979Z","contentChangedAt":"2026-09-05T17:01:29.979Z","schemaVersion":2},"datasetVersion":"2026-09-12T22:17:10.623Z"}