Documentation

APIs, event services and consumers

A service is one of three kinds. The kind decides how it is started, what a line into it means, and what a request for it looks like.

The three kinds

When a service first goes on a canvas, Debugt asks What kind of service is this?

Kind What it is A line into it A request for it
API Listens on a port and answers requests. A redirect An HTTP request
Event A handler Debugt invokes once per event — a Lambda, a scheduled function, an SQS or SNS handler. A trigger An event: a JSON payload
Consumer Stays running and takes its work off something it connects to itself — a queue, a topic. Not allowed A message

Debugt suggests a kind where it can — from a serverless.yml, or from a broker’s client library in the service’s dependencies — and says why. It is only a suggestion. Change the kind later from the service’s details, or by clicking its icon in Services.

API services

The ordinary case. An API needs a Host, such as http://localhost:3000: where its requests are sent and where a redirect into it points. Tick It has no port for one that listens on nothing.

Everything on Canvases and running services and Requests, history and traces describes an API service.

Event services

An event service is run the way a warm Lambda runs: its handler is loaded once, then called for each event, so the process stays up under the debugger and a breakpoint in the handler stays set.

The handler

In the service’s details, Handler names the file and then the function it exports — index.lambdaHandler, src/jobs/clean.handler — as serverless.yml writes it. It is filled in from the serverless.yml beside the launch configuration when there is one.

Running an event service does not run its launch configuration’s program. Debugt starts its own runner in that place, in Node or Python to match, and keeps the configuration’s cwd, env and interpreter. Async, callback-style and ES module handlers work in Node, and async def handlers in Python.

The runner sets IS_LOCAL=true, as serverless offline does, unless the configuration’s env or envFile sets it. Libraries that check it — chrome-aws-lambda, for one — then use what is on your machine instead of the binaries they would bring to Lambda.

Invoking by hand

A request under an event service is an event: a JSON payload and an Invoke button. The handler receives the payload as event; what it returned, or its error with type and stack, shows beside it. A breakpoint in the handler holds the answer until you continue.

Each invocation opens its trace and is kept in Request History as an EVT row.

Schedules

A schedule declared in serverless.yml is listed under Triggers in the service’s details, with Trigger now: it sends what the rule would send when it fires.

Triggers: SQS and SNS

Draw a line from a service into an event service and the New trigger dialog asks which queue or topic: SQS by URL, ARN or name, or SNS by ARN or name. They are matched by the name at the end.

When the source service then sends a message to that queue or topic, Debugt answers it as AWS would and hands the message to the event service’s handler, wrapped in the event Lambda would build: event.Records[0].body for SQS, event.Records[0].Sns.Message for SNS. The message does not reach AWS, and the handler’s work joins the trace under the call that sent it.

Things to know:

  • Calls to any other queue or topic go on to AWS exactly as they were sent.
  • A message for an event service that is not running is dropped, and the trace shows an error where its handler would have been.
  • Untick Trigger active to let the message go to AWS as usual while keeping the rule.
  • Triggers are delivered from Node and Python services.

Consumers

A consumer is the launch configuration’s own program, left running. It has no port to send a request to, and it is not a handler Debugt calls.

  • No host. It is not asked for one and is handed no PORT.
  • Green as soon as it starts, or when its output matches a Ready pattern set in its details.
  • Nothing is drawn into it. Its node has no input to draw a line to. Lines out of it are redirects of its own calls, as for any service.
  • Its Protocol — what it takes its messages off — is asked for with its kind. Today that is RabbitMQ (AMQP) or Something else.

A consumer on Something else still runs, turns green and has its own calls traced; there is just no message to write for it yet.

Publishing a test message

A request under a RabbitMQ consumer is a message, listed as MSG: an Exchange, a Routing key, headers, a body and a Publish button. Leave the exchange empty for the default exchange, which delivers to the queue the routing key names.

Which broker is the project’s to say, once. Click the chip at the start of the line — No broker set, to begin with — and give the address your services connect with, such as amqp://guest:guest@localhost:5672. It is saved under ~/.debugt, not in your repository, since it has a password in it.

The message goes with a trace header, so a consumer Debugt started hangs its delivery under the send: the trace is the send, the delivery, and everything the consumer then did.

Things to know:

  • A message nobody would get is an error. A routing key no queue is bound for comes back as dropped — a typo there is the commonest way for a test message to do nothing.
  • A broker on this machine only: localhost or 127.0.0.1.
  • There is no response. The panel says Published once the broker has the message.
  • The body is sent as text. Other message properties cannot be set yet.

Messages between services

When a traced service publishes to RabbitMQ, the publish is a hop, and the delivery to a consumer Debugt started is a hop under it, with nothing configured. Which client libraries are covered is on Language support and limits.