# Events — Real-Time Pub/Sub (/learn/events)



<EventsHero className="w-full max-h-[300px]" />

Think of Events like a PA system in a building — when an announcement is made, everyone currently listening hears it. If you step outside, you miss the announcement. There's no recording, no replay.

KubeMQ Events implement fire-and-forget publish/subscribe with at-most-once delivery. Publishers send messages to a named channel, and all active subscribers receive the message in real time. There is no persistence — if a subscriber is offline, the message is lost for that subscriber.

## The concept it implements [#the-concept-it-implements]

<Callout type="info">
  Events is KubeMQ's implementation of two fundamental ideas. The interaction style is &#x2A;*[pub/sub](/learn/concepts/interaction-styles)*&#x2A; (fan-out) — one publisher, many subscribers, each receiving every message. The delivery guarantee is &#x2A;*[at-most-once](/learn/concepts/delivery-guarantees)** — messages reach only the subscribers connected at publish time and are never persisted or redelivered. New to these terms? Start with the [Fundamentals](/learn/concepts) track.
</Callout>

## Key Properties [#key-properties]

| Property           | This pattern                                  | Learn the concept                                          |
| ------------------ | --------------------------------------------- | ---------------------------------------------------------- |
| Interaction style  | pub/sub (fan-out)                             | [Interaction styles](/learn/concepts/interaction-styles)   |
| Delivery guarantee | at-most-once                                  | [Delivery guarantees](/learn/concepts/delivery-guarantees) |
| Persistence        | None — fire-and-forget                        | [Ordering & replay](/learn/concepts/ordering-and-replay)   |
| Ordering           | Not guaranteed                                | [Ordering & replay](/learn/concepts/ordering-and-replay)   |
| Scaling            | Fan-out, or load-balance with consumer groups | [Scaling & flow](/learn/concepts/scaling-and-flow)         |
| Addressing         | Named channels, wildcards, multicast routing  | [Channels & routing](/learn/concepts/channels-and-routing) |

## Key Features [#key-features]

* **At-most-once delivery** — messages delivered to active subscribers only
* **Lowest latency** — no disk I/O or acknowledgment overhead
* **Multicast delivery** — every subscriber on the channel receives every message (fan-out)
* **Channel groups** — load balance across subscribers in a named group
* **Multicast routing** — publish to multiple channels using routing syntax
* **Stream publishing** — high-throughput batched delivery via bidirectional streaming

## How It Works [#how-it-works]

<Mermaid
  chart="graph LR
  PUB[&#x22;Publisher&#x22;]
  EV{{&#x22;Events channel<br/>order-notifications&#x22;}}
  S1[&#x22;Subscriber A&#x22;]
  S2[&#x22;Subscriber B&#x22;]
  S3[&#x22;Subscriber C<br/>(offline)&#x22;]

  PUB -- publish --> EV
  EV -- &#x22;at-most-once&#x22; --> S1
  EV -- &#x22;at-most-once&#x22; --> S2
  EV -. &#x22;missed&#x22; .-> S3

  class EV events
  class PUB,S1,S2 client
  class S3 external"
/>

*Fan-out: a publisher broadcasts to the channel, every connected subscriber receives the message, and offline subscribers miss it.*

## Quick Example [#quick-example]

<Tabs groupId="language" items="['Go', 'Python', 'Node.js', 'Java', 'C#', 'Kotlin', 'C++', 'Rust', 'Ruby', 'Elixir']">
  <Tab value="Go">
    ```go title="publish.go"
    package main

    import (
        "context"
        "log"

        "github.com/kubemq-io/kubemq-go/v2"
    )

    func main() {
        ctx := context.Background()
        client, err := kubemq.NewClient(ctx,
            kubemq.WithAddress("localhost", 50000),
        )
        if err != nil {
            log.Fatal(err)
        }
        defer client.Close()

        err = client.SendEvent(ctx, kubemq.NewEvent().
            SetChannel("order-notifications").
            SetMetadata("order.created").
            SetBody([]byte(`{"orderId":"ORD-1234","status":"created"}`)),
        )
        if err != nil {
            log.Fatal(err)
        }
        log.Println("Event sent successfully")
    }
    ```
  </Tab>

  <Tab value="Python">
    ```python title="publish.py"
    from kubemq.pubsub import Client as PubSubClient
    from kubemq.pubsub import EventMessage

    client = PubSubClient(address="localhost:50000")
    client.send_event(
        EventMessage(
            channel="order-notifications",
            metadata="order.created",
            body=b'{"orderId":"ORD-1234","status":"created"}',
        )
    )
    print("Event sent successfully")
    client.close()
    ```
  </Tab>

  <Tab value="Node.js">
    ```javascript title="publish.js"
    import { KubeMQClient } from 'kubemq-js';

    const client = await KubeMQClient.create({ address: 'localhost:50000' });
    await client.sendEvent({
      channel: "order-notifications",
      metadata: "order.created",
      body: Buffer.from(JSON.stringify({ orderId: "ORD-1234", status: "created" })),
    });

    console.log("Event sent successfully");
    ```
  </Tab>

  <Tab value="Java">
    ```java title="Publish.java"
    PubSubClient client = PubSubClient.builder()
        .address("localhost:50000")
        .clientId("order-publisher")
        .build();

    client.sendEventsMessage(EventMessage.builder()
        .channel("order-notifications")
        .metadata("order.created")
        .body("{\"orderId\":\"ORD-1234\",\"status\":\"created\"}".getBytes())
        .build());

    System.out.println("Event sent successfully");
    client.close();
    ```
  </Tab>

  <Tab value="C#">
    ```csharp title="Publish.cs"
    using KubeMQ.Sdk.Client;

    await using var client = new KubeMQClient(new KubeMQClientOptions());
    await client.ConnectAsync();

    await client.SendEventAsync(new EventMessage
    {
        Channel = "order-notifications",
        Metadata = "order.created",
        Body = Encoding.UTF8.GetBytes("{\"orderId\":\"ORD-1234\",\"status\":\"created\"}")
    });

    Console.WriteLine("Event sent successfully");
    ```
  </Tab>

  <Tab value="Kotlin">
    ```kotlin title="Publish.kt"
    val client = PubSubClient("localhost:50000")

    client.sendEvent(EventMessage(
        channel = "order-notifications",
        metadata = "order.created",
        body = """{"orderId":"ORD-1234","status":"created"}""".toByteArray()
    ))

    println("Event sent successfully")
    client.close()
    ```
  </Tab>

  <Tab value="C++">
    ```cpp title="publish.cpp"
    #include <kubemq/client.h>

    auto client = kubemq::PubSubClient("localhost:50000");

    kubemq::EventMessage event;
    event.channel = "order-notifications";
    event.metadata = "order.created";
    event.body = R"({"orderId":"ORD-1234","status":"created"})";

    client.sendEvent(event);
    std::cout << "Event sent successfully" << std::endl;
    ```
  </Tab>

  <Tab value="Rust">
    ```rust title="publish.rs"
    use kubemq::prelude::*;
    use kubemq::EventBuilder;

    #[tokio::main]
    async fn main() -> kubemq::Result<()> {
        let client = KubemqClient::builder()
            .host("localhost")
            .port(50000)
            .build()
            .await?;

        let event = EventBuilder::new()
            .channel("order-notifications")
            .metadata("order.created")
            .body(br#"{"orderId":"ORD-1234","status":"created"}"#.to_vec())
            .build();

        client.send_event(event).await?;
        println!("Event sent successfully");

        client.close().await?;
        Ok(())
    }
    ```
  </Tab>

  <Tab value="Ruby">
    ```ruby title="publish.rb"
    require 'kubemq'

    client = KubeMQ::PubSubClient.new(address: "localhost:50000", client_id: "order-publisher")

    client.send_event(KubeMQ::PubSub::EventMessage.new(
      channel: "order-notifications",
      metadata: "order.created",
      body: '{"orderId":"ORD-1234","status":"created"}'
    ))

    puts "Event sent successfully"
    client.close
    ```
  </Tab>

  <Tab value="Elixir">
    ```elixir title="publish.exs"
    {:ok, client} = KubeMQ.Client.start_link(address: "localhost:50000", client_id: "order-publisher")

    event = KubeMQ.Event.new(
      channel: "order-notifications",
      metadata: "order.created",
      body: ~s({"orderId":"ORD-1234","status":"created"})
    )

    :ok = KubeMQ.Client.send_event(client, event)
    IO.puts("Event sent successfully")

    KubeMQ.Client.close(client)
    ```
  </Tab>
</Tabs>

## When to Use Events [#when-to-use-events]

| Scenario                | Events                 | Events Store                  |
| ----------------------- | ---------------------- | ----------------------------- |
| Real-time notifications | ✅ Best choice          | Overkill                      |
| Log/metric streaming    | ✅ Best choice          | Use if logs must not be lost  |
| Live dashboards         | ✅ Best choice          | Use if historical data needed |
| Cache invalidation      | ✅ Best choice          | Not needed                    |
| Audit trails            | ❌ Messages can be lost | ✅ Use Events Store            |
| Event sourcing          | ❌ No persistence       | ✅ Use Events Store            |

<Callout type="info">
  Need guaranteed delivery or replay capability? Use [Events Store](/learn/events-store) instead.
</Callout>

<Callout type="info">
  Events are also available via the [CloudEvents protocol](/connectors/cloudevents/how-to/events) — use any language with a CloudEvents SDK, no KubeMQ client library needed.
</Callout>

## Learn More [#learn-more]

<Cards>
  <Card title="Getting Started" href="/learn/events/getting-started" description="Publish and subscribe to your first event in 5 minutes." />

  <Card title="Publish & Subscribe" href="/learn/events/tutorials/publish-subscribe" description="Learn the basic pub/sub pattern with multiple subscribers." />

  <Card title="Consumer Groups" href="/learn/events/tutorials/consumer-groups" description="Distribute event processing across a group." />

  <Card title="Wildcard Subscriptions" href="/learn/events/tutorials/wildcard-subscriptions" description="Subscribe to multiple channels with patterns." />

  <Card title="Multicast Events" href="/learn/events/tutorials/multicast" description="Publish to multiple channels simultaneously." />

  <Card title="Stream Publishing" href="/learn/events/tutorials/stream-publishing" description="High-throughput batched event delivery." />

  <Card title="Events Reference" href="/learn/events/reference" description="Message structure, validation rules, and error codes." />
</Cards>
