harness

package
v0.30.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Nov 2, 2022 License: Apache-2.0 Imports: 48 Imported by: 0

Documentation

Index

Constants

View Source
const DefaultGraphQLAdminUserID = "00000000-0000-0000-0000-000000000002"

DefaultGraphQLAdminUserID is the UserID created & used for GraphQL calls by default.

View Source
const (
	SlackTestSigningSecret = "secret"
)

Variables

This section is empty.

Functions

func DBURL

func DBURL(name string) string

func ExecSQL

func ExecSQL(ctx context.Context, url string, query string) error

ExecSQL will execute all queries one-by-one.

func ExecSQLBatch

func ExecSQLBatch(ctx context.Context, url string, query string) error

ExecSQLBatch will execute all queries in a transaction by sending them all at once.

func GenPhoneCC

func GenPhoneCC(cc string) string

GenPhoneCC will return a random phone number with supplied country code

func GenUUID

func GenUUID() string

GenUUID will return a random UUID.

Types

type DataGen

type DataGen struct {
	// contains filtered or unexported fields
}

DataGen handles generating random data for tests. It ties arbitrary ids to generated values so they can be re-used during a test.

func NewDataGen

func NewDataGen(t *testing.T, name string, g Generator) *DataGen

NewDataGen will create a new data generator. fn should return a new/unique string each time

func (*DataGen) Get

func (d *DataGen) Get(id string) string

Get returns the value associated with id. The first time an id is provided, a new value is generated. If id is empty, a new value will always be returned.

func (*DataGen) GetWithArg

func (d *DataGen) GetWithArg(arg, id string) string

GetWithArg returns the value associated with id. The first time an id is provided, a new value is generated. If id is empty, a new value will always be returned.

type DataGenArgFunc

type DataGenArgFunc func(string) string

func (DataGenArgFunc) Generate

func (d DataGenArgFunc) Generate(a string) string

type DataGenFunc

type DataGenFunc func() string

func (DataGenFunc) Generate

func (d DataGenFunc) Generate(string) string

type EmailServer

type EmailServer interface {
	ExpectMessage(address string, keywords ...string)

	WaitAndAssert()
}

type ExpectedCall

type ExpectedCall interface {
	// ThenPress imitates a user entering a key on the phone.
	ThenPress(digits string) ExpectedCall

	// ThenExpect asserts that the message matches ALL keywords (case-insensitive).
	//
	// Generally used as ThenPress().ThenExpect()
	ThenExpect(keywords ...string) ExpectedCall

	// Body will return the last full spoken message as text. Separate stanzas (e.g. multiple `<Say>`) are
	// separated by newline.
	Body() string

	// Hangup will hangup the active call.
	Hangup()
}

ExpectedCall represents a phone call.

type ExpectedSMS

type ExpectedSMS interface {

	// ThenReply will respond with an SMS with the given body.
	ThenReply(body string) SMSReply

	// Body is the text of the SMS message.
	Body() string

	// From is the source number of the SMS message.
	From() string
}

ExpectedSMS represents an SMS message.

type Generator

type Generator interface {
	Generate(string) string
}

type Harness

type Harness struct {
	// contains filtered or unexported fields
}

Harness is a helper for smoketests. It deals with assertions, database management, and backend monitoring during tests.

func NewHarness

func NewHarness(t *testing.T, initSQL, migrationName string) *Harness

NewHarness will create a new database, perform `migrateSteps` migrations, inject `initSQL` and return a new Harness bound to the result. It starts a backend process pre-configured to a mock twilio server for monitoring notifications as well.

func NewHarnessDebugDB

func NewHarnessDebugDB(t *testing.T, initSQL, migrationName string) *Harness

NewHarnessDebugDB works like NewHarness, but fails the test immediately after migrations have been run. It is used to debug data & queries from a smoketest.

Note that the now() function will be locked to the init timestamp for inspection.

func NewHarnessWithData

func NewHarnessWithData(t *testing.T, initSQL string, sqlData interface{}, migrationName string) *Harness

func NewStoppedHarness

func NewStoppedHarness(t *testing.T, initSQL string, sqlData interface{}, migrationName string) *Harness

NewStoppedHarness will create a NewHarness, but will not call Start.

func (*Harness) AddNotificationRule

func (h *Harness) AddNotificationRule(userID, cmID string, delayMinutes int)

AddNotificationRule will add a notification rule to the database.

func (*Harness) App

func (h *Harness) App() *app.App

func (*Harness) Close

func (h *Harness) Close() error

Close terminates any background processes, and drops the testing database. It should be called at the end of all tests (usually with `defer h.Close()`).

func (*Harness) Config

func (h *Harness) Config() config.Config

func (*Harness) CreateAlert

func (h *Harness) CreateAlert(serviceID string, summary string) TestAlert

CreateAlerts will create one or more unacknowledged alerts for a service.

func (*Harness) CreateAlertWithDetails

func (h *Harness) CreateAlertWithDetails(serviceID, summary, details string) TestAlert

CreateAlertWithDetails will create a single alert with summary and detailss.

func (*Harness) CreateManyAlert

func (h *Harness) CreateManyAlert(serviceID, summary string)

CreateManyAlert will create multiple new unacknowledged alerts for a given service.

func (*Harness) CreateUser

func (h *Harness) CreateUser() (u *user.User)

CreateUser generates a random user.

func (*Harness) Email

func (h *Harness) Email(id string) string

func (*Harness) Escalate

func (h *Harness) Escalate(alertID, level int)

Escalate will escalate an alert in the database, when 'level' matches.

func (*Harness) FastForward

func (h *Harness) FastForward(d time.Duration)

func (*Harness) GraphQLQuery2

func (h *Harness) GraphQLQuery2(query string) *QLResponse

GraphQLQuery2 will perform a GraphQL2 query against the backend, internally handling authentication. Queries are performed with Admin role.

func (*Harness) GraphQLQueryT

func (h *Harness) GraphQLQueryT(t *testing.T, query string) *QLResponse

GraphQLQueryT will perform a GraphQL query against the backend, internally handling authentication. Queries are performed with Admin role.

func (*Harness) GraphQLQueryUserT

func (h *Harness) GraphQLQueryUserT(t *testing.T, userID, query string) *QLResponse

GraphQLQueryUserT will perform a GraphQL query against the backend, internally handling authentication. Queries are performed with the provided UserID.

func (*Harness) IgnoreErrorsWith

func (h *Harness) IgnoreErrorsWith(substr string)

IgnoreErrorsWith will cause the Harness to ignore backend errors containing the specified substring.

func (*Harness) LinkSlackUser

func (h *Harness) LinkSlackUser()

LinkSlackUser creates a link between the GraphQL user and the smoketest Slack user.

func (*Harness) Migrate

func (h *Harness) Migrate(migrationName string)

Migrate will perform `steps` number of migrations.

func (*Harness) Phone

func (h *Harness) Phone(id string) string

Phone will return the generated phone number for the id provided.

func (*Harness) PhoneCC

func (h *Harness) PhoneCC(cc, id string) string

PhoneCC will return the generated phone number for the id provided.

func (*Harness) SMTP

func (h *Harness) SMTP() EmailServer

func (*Harness) SetCarrierName

func (h *Harness) SetCarrierName(number, name string)

SetCarrierName will set the carrier name for the given phone number.

func (*Harness) SetConfigValue

func (h *Harness) SetConfigValue(id, value string)

SetConfigValue will update the config value id (e.g. `General.PublicURL`) to the provided value.

func (*Harness) SetSystemLimit

func (h *Harness) SetSystemLimit(id limit.ID, value int)

SetSystemLimit will update the value of a system limit given an id (e.g. `RulesPerSchedule`). TODO repalce SetSystemLimit with new mutation (work anticipated to be done with Admin Config view)

func (*Harness) Slack

func (h *Harness) Slack() SlackServer

func (*Harness) Start

func (h *Harness) Start()

func (*Harness) Trigger

func (h *Harness) Trigger()

Trigger will trigger, and wait for, an engine cycle.

func (*Harness) Twilio

func (h *Harness) Twilio(t *testing.T) PhoneAssertions

Twilio will return PhoneAssertions for the given testing context.

func (*Harness) TwilioMessagingService

func (h *Harness) TwilioMessagingService() string

TwilioMessagingService will return the id and phone numbers for the mock messaging service.

func (*Harness) TwilioNumber

func (h *Harness) TwilioNumber(id string) string

TwilioNumber will return a registered (or register if missing) Twilio number for the given ID. The default FromNumber will always be the empty ID.

func (*Harness) URL

func (h *Harness) URL() string

URL returns the backend server's URL

func (*Harness) UUID

func (h *Harness) UUID(id string) string

UUID will return the generated UUID for the id provided.

func (*Harness) WaitAndAssertOnCallUsers

func (h *Harness) WaitAndAssertOnCallUsers(serviceID string, userIDs ...string)

WaitAndAssertOnCallUsers will ensure the correct set of users as on-call for the given serviceID.

type PhoneAssertions

type PhoneAssertions interface {

	// Device returns a TwilioDevice for the given number.
	//
	// It is safe to call multiple times for the same device.
	Device(number string) PhoneDevice

	// WaitAndAssert will fail the test if there are any unexpected messages received within the timeout interval.
	WaitAndAssert()
}

PhoneAssertions is used to assert voice and SMS behavior.

type PhoneDevice

type PhoneDevice interface {
	// SendSMS will send a message to GoAlert from the device.
	SendSMS(body string)

	// ExpectSMS will match against an SMS that matches ALL provided keywords (case-insensitive).
	// Each call to ExpectSMS results in the requirement that an additional SMS is received.
	ExpectSMS(keywords ...string) ExpectedSMS

	// RejectSMS will match against an SMS that matches ALL provided keywords (case-insensitive) and tell the server that delivery failed.
	RejectSMS(keywords ...string)

	// ExpectVoice will match against a voice call where the spoken text matches ALL provided keywords (case-insensitive).
	ExpectVoice(keywords ...string) ExpectedCall

	// RejectVoice will match against a voice call where the spoken text matches ALL provided keywords (case-insensitive) and tell the server that delivery failed.
	RejectVoice(keywords ...string)

	// IgnoreUnexpectedSMS will cause any extra SMS messages (after processing ExpectSMS calls) that match
	// ALL keywords (case-insensitive) to not fail the test.
	IgnoreUnexpectedSMS(keywords ...string)

	// IgnoreUnexpectedVoice will cause any extra voice calls (after processing ExpectVoice) that match
	// ALL keywords (case-insensitive) to not fail the test.
	IgnoreUnexpectedVoice(keywords ...string)
}

A PhoneDevice immitates a device (i.e. a phone) for testing interactions.

type QLResponse

type QLResponse struct {
	Data   json.RawMessage
	Errors []struct{ Message string }
}

QLResponse is a generic GraphQL response.

type SMSReply

type SMSReply interface {
	// ThenExpect will match against an SMS that matches ALL provided keywords (case-insensitive).
	// The message must be received AFTER the reply is sent or the assertion will fail.
	ThenExpect(keywords ...string) ExpectedSMS
}

SMSReply represents a reply to a received SMS message.

type SlackAction

type SlackAction interface {
	Click()
	URL() string
}

type SlackChannel

type SlackChannel interface {
	ID() string
	Name() string

	ExpectMessage(keywords ...string) SlackMessage
	ExpectEphemeralMessage(keywords ...string) SlackMessage
}

type SlackMessage

type SlackMessage interface {
	SlackMessageState

	ExpectUpdate() SlackMessageState

	// ExpectThreadReply waits and asserts that a non-broadcast thread reply is received.
	ExpectThreadReply(keywords ...string)

	// ExpectBroadcastReply waits and asserts that a broadcast thread reply is received.
	ExpectBroadcastReply(keywords ...string)
}

type SlackMessageState

type SlackMessageState interface {
	// AssertText asserts that the message contains the given keywords.
	AssertText(keywords ...string)

	// AssertNotText asserts that the message does not contain the given keywords.
	AssertNotText(keywords ...string)

	// AssertColor asserts that the message has the given color bar value.
	AssertColor(color string)

	// AssertActions asserts that the message includes the given action buttons.
	AssertActions(labels ...string)

	// Action returns the action with the given label.
	Action(label string) SlackAction
}

type SlackServer

type SlackServer interface {
	Channel(string) SlackChannel

	WaitAndAssert()
}

type TestAlert

type TestAlert interface {
	ID() int
	Ack()
	Escalate()
	Close()
}

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL