0.0.5 • Published 1 year ago

@leighton-digital/eventnet v0.0.5

Weekly downloads
-
License
ISC
Repository
github
Last release
1 year ago

EventNet

Several tools for working with AWS EventBridge and the events published through it.

CDK Event Extension

A CDK construct that allows you to connect a WebSocket to an EventBridge instance and make the events published to it visible to a client.

Test Client

Event Producers - Perform and Action and Collect Events

The Test Client connects to the WebSocket and collects the events for Jest assertions.

Event Consumers - Validating and Sending Events

The Test Client validates the event you will send to ensure it matches the Schema; if it is valid, it will send the events. You can then check that the events sent trigger the correct response from your application, such as saving the record to DynamoDb.

Jest Schema Assertion - Assert Events Match the Prescibed Schema

Test that your captured events match a published JSON Schema specification.

COMING SOON: Event Monitoring Client - Collect Events to a WebUI in realtime

A web application that can connect to your WebSocket, allowing you to inspect, save and copy the published events. Useful when developing for instant feedback without adding lots of console logs to your Jest tests or logging out through compute.


Using the EventNet CDK Construct

Install:

yarn add @leighton-digitial/eventnet

& Import the construct:

import { EventNet } from "@leighton-digital/eventnet/lib/construct/";

Set up the EventNet instance with the EventBridge instance.

const eventNet = new EventNet(
    this,
    "EventNet",
    {
        prefix: stackName,
        eventBusName: eventBusName,
        includeOutput: true, // optional, default is false
        includeLogs: true // optional, default is false
    }
);
  • prefix: usually your stackname, used to namespace the event net resources. Usually, your stackName. If you want to monitor multiple buses in the same application, you can construct an individual reference such as ${stackName}-1 and ${stackName}-2, as long as you can reproduce this when creating the connection in your test suite
  • eventBusName: name of an existing EventBridge bus you want to subscribe too
  • includeOutput: prints out the WebSocket URL for easy access for the WebClient

Note: Wrap this construct in a conditional that omits it from PRODUCTION; this is for test use only and exposes your events through a WebSocket.


Using the Test Client

  • For testing Event Producers, you will want to perform an action that will trigger your application to generate an event. For instance, writing a record to the DynamoDb table.

  • The test harness then collects all events produced and sends them to a web socket connection.

  • The Test Client collects the events from the WebSocket.

import { EventNetClient } from "@leighton-digital/eventnet";

The EventNet client expects your prefix from the CDK construct to be passed in as '--stack=my-service-dev'. This corresponds to the Cloud Formation stack name produced by CDK. i.e.:

yarn test:int --stack=my-stack-name-dev --all --runInBand

Why did we choose this? Because we also heavily use sls-test-tools in our test suites, we didn't want to create another mechanism for bootstrapping our test suite.

If you are using multiple Event Buses, we strongly recommend basing the names from the stackName as it is easier to reproduce.

Event Producer Example - Perform Action and Collect Events

import { EventNetClient, stackName } from "@leighton-digital/eventnet";


describe("Test Producer > ", () => {
  test("basic request produces event", async () => {
    // Following can be added to beforeEach/beforeAll
    eventNet = await EventNetClient.create();
    // If you have used the stack name eventNet
    // will automatically use the target stack
    await eventNet.waitForOpenSocket();

    // You can also override it:
    // await eventNet.waitForOpenSocket(`${stackName}-1`);
    // OR
    // await eventNet.waitForOpenSocket(`${stackName}-2`);

    const payload = { some: "something"};
    const resp = await axios.post(url, payload);

    // Matches any * source
    // Matches any * detailtype
    // Returns when ONE record have been found
    // Or waits for 10 secs
    const events = await eventNet.matchEnvelope("*", "*", 1, 100000);

    await eventNet.waitForClosedSocket()

    // Use the Jest assertion to check
    // the event against the JSONSchema,
    // more on this below
    expect(events[0]).toMatchJsonSchema(EventSpec);

    expect(resp.data.body).toBeDefined();
    expect(events).toHaveLength(2);

    // Following can be added to afterEach/afterAll
    await eventNet.closeClient();

  });
});

Event Consumer Example - Validating and Sending Events

import { EventNetClient } from "@leighton-digital/eventnet";
import * as EventSpec from "../../jsonSpecs/someSchema-v1.json";

describe("Test Consumer > ", () => {
  test("basic request produces event", async () => {
    eventNet = await EventNetClient.create();
    await eventNet.waitForOpenSocket();

    const Event {
        EventBusName: 'your-event-bus-name',
        Source: "some.source",
        DetailType: "some.detail.type",
        Detail: {
          some: "value"
        },
      },

    // Use the Jest assertion to check
    // the event against the JSONSchema,
    // more on this below
    expect(Event).toMatchJsonSchema(EventSpec);

    // send the event to the EventBrdge instance
    const sendEvents = await eventNet.sendEvent(Event, EventBusName)
    await eventNet.waitForClosedSocket()

    // Check DynamoDb Table or S3 that events have been stored or modified
    // ...
    // Following can be added to afterEach/afterAll
    await eventNet.closeClient();

  });
});

Using the Jest Schema Matcher

When installed, the Jest JSONschema matcher will be available to use.

import * as EventSpec from "../../jsonSpecs/someSchema-v1.json";

Importantly, this can be from a shared/published NPM module.

import * as EventSpec from "../../node_modules/@something/event-catalogue/events/orderCreated/someSchema-v1.json";

Then, use the schema to assert against a captured event.

expect(singleMessage).toMatchJsonSchema(EventSpec);

COMING SOON: Using the EventNet Web Client

First, you need to run the client:

eventnet start

This will open a web client on url: http://localhost:3000

From the output in CDK, you will have a WebSocket URL.

wss://xxxxx.execute-api.eu-west-2.amazonaws.com/dev

You need to paste it into eventnet client and press connect.

Once connected, we can inspect events, save them locally or copy/paste them into your IDE.