Skip to content

Event Listeners

SDM supported events

In an SDM, there are several built-in events that you can take action on. You can also make a custom event subscription.

Most of these work only in team mode; the local SDM only hears about push events. Goal-related listeners do work in local mode.

To respond to these events, register a listener with a function to run in response. Each listener function receives a ListenerInvocation containing general context and specific information about that event.

This page shows you how to:

  • write a listener function for many different events
  • register that listener with your SDM

Generally, you’ll configure listeners inside your machine function.

Repository Creation

(team mode only) This fires when a repository is first created in your version control manager. The repository might not have code yet! If you want to respond to a repository with code in it, register a first push listener.

This is a good time to add standard labels to the repository, give read-only access to your whole organization, or announce its existence in chat.

Create a function that accepts a RepoCreationListenerInvocation. In addition to the standard RepoContext, this invocation has a repo field with owner and name. (You could also use the standard id field.) The addressChannels method won’t do anything, as the repository is not yet linked to any chat channels.

Pass this function to sdm.addRepoCreationListener.

First Push

(team mode only) This fires the first time code is pushed to a new repository.

This is a good time to look at the code in the repository, and send messages to chat that offer to upgrade it or add a deployment spec. Note that sometimes the repository has not been linked to a channel yet, so addressChannels won’t have anywhere to go.

Create a function that accepts a PushListenerInvocation. In addition to the standard RepoContext, this invocation has push and project.

If you want to check whether there are any channels linked, you could look in pushListenerInvocation.push.repo.channels. If that is empty, there are no channels linked yet. You might consider implementing a Channel Link listener to send messages about a new repository.

Pass this function to sdm.addFirstPushListener.

Repo Onboarding

(team mode only) This fires when a repository formerly not watched by Atomist is brought into our purvey, like when we add a webhook to a new organization. You might want to do similar things to a FirstPushListener.

Create a function that accepts a ProjectListenerInvocation. In addition to the standard RepoContext project, giving you access to the code in the repository.

Pass this function to sdm.addRepoOnboardingListener.

Goal Events

These work in local mode as well as team mode, since they happen around Goals.

Goals Set

Once per push, the goals are chosen. This subscription fires after that happens.

Create a function that accepts a GoalsSetListenerInvocation. In addition to the standard RepoContext, this invocation has push and fields about the goals that were set: goalSet, goalSetId, and goalSetName.

Pass this function to sdm.addGoalsSetListener.

Goal Execution

This fires for every goal, before and after execution in your SDM. You can notify a person when a goal completes, or send a message to a logging system, for instance.

Create a function that accepts a GoalExecutionListenerInvocation. In addition to the standard RepoContext, this invocation has goalEvent property. Check its state to see whether the goal is in_process, successful, or failed.

Pass this function to sdm.addGoalExecutionListener.

Goal Completion

(team mode only) This fires when a goal created by your SDM is completed, even if the goal is implemented in another SDM. In most cases, you probably want a goal execution listener instead.

Create a function that accepts a GoalCompletionListenerInvocation. In addition to the standard RepoContext, this invocation has [completedGoal] field, which is an SdmGoalEvent. Check its state to see whether the goal completed successfully.

Pass this function to sdm.addGoalCompletionListener.

Channels

A repository can be linked to a chat channel. Then, the addressChannel method in the invocation object passed to listeners will post messages to all channels linked to the repository in the event. There are also some events around chat channels that you can subscribe to in your SDM.

(team mode only) This fires when a repository is linked to a chat channel.

Create a function that accepts a ChannelLinkListenerInvocation. In addition to the standard SdmContext, this invocation has project and newlyLinkedChannelName. There is also a handy method to send messages: addressNewlyLinkedChannel.

Pass this function to sdm.addChannelLinkListener.

User Joined Channel

(team mode only) When a user joins a channel that is linked to at least one repository, your SDM can respond to it.

Create a function that accepts a UserJoiningChannelListenerInvocation. In addition to an SdmContext, this invocation has joinEvent, which contains data about the user and channel, and repos, an array of identifiers for all the linked repositories.

Pass this function to sdm.addUserJoiningChannelListener.

Issues

Currently, these events fire for GitHub issues. They work with GitHub.com and GitHub Enterprise.

New Issue

(team mode only) When a new issue is created, you might want to capitalize its title, or complain if it doesn’t have a description. You might want to add labels to it. This is a good place to action some organizational policies.

Create a function that accepts a NewIssueListenerInvocation. In addition to the standard RepoContext, this invocation has issue, with fields selected in this GraphQL.

Pass this function to sdm.addNewIssueListener.

Issue Updated

(team mode only) When an issue changes, you might want to update some other system.

Create a function that accepts a UpdatedIssueListenerInvocation. In addition to the standard RepoContext, this invocation has issue, with fields selected in this GraphQL.

Pass this function to sdm.addUpdatedIssueListener.

Issue Closed

(team mode only) When an issue closes, you might want to congratulate someone.

Create a function that accepts a ClosedIssueListenerInvocation. In addition to the standard RepoContext, this invocation has issue, with fields selected in this GraphQL.

Pass this function to sdm.addClosedIssueListener.

Fingerprint Difference

(team mode only) When a fingerprint is added to a push, and that fingerprint differs in value from the same fingerprint before the push, this listener gets to respond.

Create a function that accepts a FingerprintDifferenceListenerInvocation. In addition to the standard RepoContext, this invocation has diffs, an array of FingerprintDifference objects containing the old and new value of each changed fingerprint.

Pass this function to sdm.addFingerprintDifferenceListener.

Startup

(team mode only) When your SDM has completed startup, these listeners are called. This is handy for sending notifications to logging systems or to chat.

Create a function that accepts a StartupListenerInvocation. This is different from most of the listener invocations. It is an AdminCommunicationContext, which has an addressAdmin method and the sdm itself as a property.

Pass this function to sdm.addStartupListener.

Tag

(team mode only) When a tag is added to a repository, you have the opportunity to respond.

Create a function that accepts a TagListenerInvocation. In addition to the standard RepoContext, this invocation has a tag

Pass this function to sdm.addTagListener.

Triggered

This one is different: you can make a listener that is invoked at time intervals while your SDM is running.

Create a function that accepts a TriggeredListenerInvocation. It is an AdminCommunicationContext, which has an addressAdmin method and the sdm itself as a property.

Include this in a TriggeredListenerRegistration, along with a trigger which contains either a cron expression or an interval in milliseconds.

Pass the registration to sdm.addTriggeredListener.