KubeMQ
Client SDKsNode.jsHow-to guidesConnection

Close a KubeMQ Node.js Client

Properly close a KubeMQ client connection in Node.js, releasing sockets and resources to avoid leaks on application shutdown.

Overview

Closing a client isn't an afterthought — it tells the broker and your own process that this connection is done, so both sides release what they were holding for it. A KubeMQ client is more than a socket: it's a gRPC channel plus whatever subscriptions and in-flight sends it's servicing. Skip the close and those linger — subscriptions keep streaming, the channel stays open — and in short-lived processes (CLI tools, serverless handlers, test suites) you leak connections until the process is killed.

Awaiting client.close() flushes in-flight gRPC calls, cancels active subscriptions, and only then releases the underlying channel. Once it returns, the client transitions to a terminal Closed state — every call after that fails fast with ClientClosedError.

Gotchas: the drain window is bounded ({ timeoutSeconds, callbackTimeoutSeconds }, unbounded by default), not unlimited, so a slow consumer can still lose the tail of a burst if you close mid-stream; a closed client is dead forever — no reconnect on the same instance, construct a new one; and close() belongs in a finally block, not just after the last call, so shutdown runs on every exit path, including thrown errors.

Prerequisites

  • KubeMQ server running on localhost:50000
  • Node.js SDK installed (npm install kubemq-js)

Code

close.ts
import { KubeMQClient, createEventMessage } from 'kubemq-js';

async function main() {
  const client = await KubeMQClient.create({
    address: 'localhost:50000',
    clientId: 'js-connection-close-client',
  });

  try {
    await client.sendEvent(
      createEventMessage({ channel: 'js-connection.close', body: 'hello before close' }),
    );
    console.log('Event sent successfully');
  } finally {
    await client.close();
    console.log('Client closed gracefully');
  }
}

main().catch(console.error);

How It Works

  • client.close() is always called in the finally block — this flushes in-flight gRPC calls, cancels all active subscriptions, and releases the underlying channel.
  • The try/finally pattern ensures the client is closed even if sendEvent() throws, preventing gRPC connection leaks in long-running processes.
  • close() accepts an optional { timeoutSeconds, callbackTimeoutSeconds } object to bound drain time in shutdown-critical paths; the default waits indefinitely.
  • After close() the client state transitions to Closed; any further operation on the same instance throws ClientClosedError.

Was this page helpful?

On this page