Documentation
¶
Overview ¶
Package flyte is where you find the main public api for the flyte client. Almost all of your interactions with the client will occur here.
Index ¶
Examples ¶
Constants ¶
This section is empty.
Variables ¶
var StartHealthCheckServer = true // this is only overridden for testing purposes
Functions ¶
This section is empty.
Types ¶
type Command ¶
type Command struct {
Name string // the name of the command
OutputEvents []EventDef // the events a pack can output
Handler CommandHandler // the handler is where the functionality of a pack is implemented when a command is called
HelpURL *url.URL // optional
}
Defines a command - its name, the events it can output and a handler for incoming actions. The help URL is optional.
Example ¶
package main
import (
"encoding/json"
"fmt"
"github.com/HotelsDotCom/flyte-client/flyte"
"net/url"
)
type CreateIssueInput struct {
Project string `json:"project"`
TicketText string `json:"ticketText"`
}
type IssueCreatedPayload struct {
Project string `json:"project"`
IssueId string `json:"issueId"`
Location *url.URL `json:"location"`
}
func createURL(u string) *url.URL {
url, _ := url.Parse(u)
return url
}
func main() {
// to create a command, we need to create and populate at least one output event. often, these will represent
// a success or failure case
issueCreatedEventDef := flyte.EventDef{
Name: "IssueCreated",
}
issueCreationErrorEventDef := flyte.EventDef{
Name: "IssueCreationError",
}
// we also need a command handler. this is where the functionality of the command will be implemented
createIssueHandler := func(input json.RawMessage) flyte.Event {
// deserialize the raw JSON into our domain struct
var createIssueInput CreateIssueInput
json.Unmarshal(input, &createIssueInput)
// call some ticket creation code...
// ...
// if it succeeds then return something like the following. The payload will be serialised to JSON and sent to the Flyte api server.
return flyte.Event{
EventDef: issueCreatedEventDef,
Payload: IssueCreatedPayload{
Project: "FOO",
IssueId: "123",
Location: createURL("http://jira/FOO/123"),
},
}
}
// you can also provide an optional help URL. this will help document your command to your end users
helpUrl, _ := url.Parse("http://jirapack/help#create-issue-command")
// you can now give the command a name. it is now ready to be passed into the pack definition
createIssueCommand := flyte.Command{
Name: "createIssue",
OutputEvents: []flyte.EventDef{
issueCreatedEventDef,
issueCreationErrorEventDef,
},
Handler: createIssueHandler,
HelpURL: helpUrl,
}
fmt.Printf("%+v", createIssueCommand)
}
type CommandHandler ¶
type CommandHandler func(input json.RawMessage) Event
Command handlers will be invoked with the input JSON when they are invoked from a flow step in the flyte server.
Example ¶
package main
import (
"encoding/json"
"fmt"
"github.com/HotelsDotCom/flyte-client/flyte"
)
func main() {
// In this example the client will call this handler every time it receives a "createIssue" action from the Flyte api. The handler will take the input JSON from the action
// and must return a flyte.Event. Handlers are where the functionality of the pack is implemented so will likely form the bulk of most packs.
// the JSON input passed into the handler will be deserialized into this struct
type CreateIssueInput struct {
Project string `json:"project"`
TicketText string `json:"ticketText"`
}
// this event definition will be passed into the returned flyte.Event below
issueCreatedEventDef := flyte.EventDef{
Name: "IssueCreated",
}
// this payload struct will used in the returned flyte.Event below
type IssueCreatedPayload struct {
Project string `json:"project"`
IssueId string `json:"issueId"`
}
// the handler once created, can now be used in a flyte.Command struct
createIssueHandler := func(input json.RawMessage) flyte.Event {
// deserialize the raw JSON into our domain struct
var createIssueInput CreateIssueInput
json.Unmarshal(input, &createIssueInput)
// call some ticket creation code...
// ...
// if it succeeds then return something like the following. The payload will be serialised to JSON and sent to the Flyte api server.
return flyte.Event{
EventDef: issueCreatedEventDef,
Payload: IssueCreatedPayload{
Project: "FOO",
IssueId: "123",
},
}
}
fmt.Printf("%+v", createIssueHandler(json.RawMessage{}))
}
type Event ¶
type Event struct {
EventDef EventDef
Payload interface{}
}
The event data the pack can send for events it observes (using SendEvent()) or from commands that have been called. The payload will be marshalled into JSON, so should be annotated appropriately.
Example ¶
package main
import (
"fmt"
"github.com/HotelsDotCom/flyte-client/flyte"
"net/url"
)
func main() {
// to create an event, you first need to create a named event definition
// to help document your event to your end users, you can provide an optional help URL
helpUrl, _ := url.Parse("http://jirapack/help#create-issue-command")
issueCreatedEventDef := flyte.EventDef{
Name: "IssueCreated",
HelpURL: helpUrl, // optional
}
// you will also need to provide a payload containing the relevant data for the event.
// the payload will be marshalled into JSON, so should be annotated appropriately
type IssueCreatedPayload struct {
Project string `json:"project"`
IssueId string `json:"issueId"`
}
// then simply pass in the event definition and a populated payload struct to create the event
event := flyte.Event{
EventDef: issueCreatedEventDef,
Payload: IssueCreatedPayload{
Project: "FOO",
IssueId: "123",
},
}
fmt.Printf("%+v", event)
}
func NewFatalEvent ¶
func NewFatalEvent(payload interface{}) Event
This is the preferred way for packs to handle serious errors within the handler.
Example ¶
package main
import (
"fmt"
"github.com/HotelsDotCom/flyte-client/flyte"
)
func main() {
payload := fmt.Errorf("some error").Error()
fmt.Printf("%v", flyte.NewFatalEvent(payload))
}
type EventDef ¶
Defines an event. The help URL is optional.
Example ¶
package main
import (
"fmt"
"github.com/HotelsDotCom/flyte-client/flyte"
"net/url"
)
func main() {
// an event definition defines an event. to help the end user, you can provide an optional help URL
helpUrl, _ := url.Parse("http://jirapack/help#issue-created-event-def")
// once created, the event definition is ready to be passed into a flyte.Event struct
issueCreatedEventDef := flyte.EventDef{
Name: "IssueCreated",
HelpURL: helpUrl,
}
fmt.Printf("%+v", issueCreatedEventDef)
}
type Pack ¶
type Pack interface {
// Start will register the pack with the flyte server and will begin handling actions and invoking commands.
// The pack will also be available to send observed events.
Start()
// SendEvent spontaneously sends an event that the pack has observed to the flyte server.
SendEvent(Event) error
}
func NewPack ¶
func NewPack(packDef PackDef, client client.Client, healthChecks ...healthcheck.HealthCheck) Pack
Creates a Pack struct with the details from the pack definition and a connection to the flyte api through the client. Optionally, you can also pass in pack health checks
Example ¶
package main
import (
"encoding/json"
"github.com/HotelsDotCom/flyte-client/client"
"github.com/HotelsDotCom/flyte-client/flyte"
"net/url"
"time"
)
func main() {
// First we create event definitions that describe what events our pack can raise.
// An EventDef contains the name of the event (mandatory) and a help URL (optional)
issueCreatedEventDef := flyte.EventDef{
Name: "IssueCreated",
}
issueCreationErrorEventDef := flyte.EventDef{
Name: "IssueCreationError",
}
// This pack has a single "createIssue" command. To implement a command we must provide a "CommandHandler" function matching the signature below.
// The client will call this handler every time it receives a "createIssue" action from the Flyte api. The handler will take the input JSON from the action
// and must return a flyte.Event. Handlers are where the functionality of the pack is implemented so will likely form the bulk of most packs.
createIssueHandler := func(input json.RawMessage) flyte.Event {
// deserialize the raw JSON into our domain struct
var createIssueInput CreateIssueInput
json.Unmarshal(input, &createIssueInput)
// call some ticket creation code...
// ...
// if it succeeds then return something like the following. The payload will be serialised to JSON and sent to the Flyte api server.
return flyte.Event{
EventDef: issueCreatedEventDef,
Payload: IssueCreatedPayload{
Project: "FOO",
IssueId: "123",
Location: createURL("http://jira/FOO/123"),
},
}
}
// Next we create a struct that defines the "createIssue" command. Note the handler above is passed to it.
// Also note that we specify what events the command can output.
// The help URL is optional
createIssueCommand := flyte.Command{
Name: "createIssue",
OutputEvents: []flyte.EventDef{
issueCreatedEventDef,
issueCreationErrorEventDef,
},
HelpURL: createURL("http://jirapack/help#create-issue-command"),
Handler: createIssueHandler,
}
// The final struct we must define is the PackDef struct which pulls together the above structs to give the full definition of the pack.
packDef := flyte.PackDef{
Name: "JiraPack",
Commands: []flyte.Command{createIssueCommand},
HelpURL: createURL("http://jirapack/help#create-issue-command"),
}
// Finally we call NewPack() to create a pack struct. This can then be started by calling Start()
p := flyte.NewPack(packDef, client.NewClient(createURL("http://example.com"), 10*time.Second))
// p.Start() is not blocking, it is user's responsibility to make sure that the program does not exit immediately
p.Start()
}
type CreateIssueInput struct {
Project string `json:"project"`
TicketText string `json:"ticketText"`
}
type IssueCreatedPayload struct {
Project string `json:"project"`
IssueId string `json:"issueId"`
Location *url.URL `json:"location"`
}
func createURL(u string) *url.URL {
url, _ := url.Parse(u)
return url
}
type PackDef ¶
type PackDef struct {
Name string // the pack name
Labels map[string]string // the pack labels. These act as a filter that determines when the pack will execute against a flow
EventDefs []EventDef // the event definitions of a pack. These can be events a pack observes and sends spontaneously
Commands []Command // the commands a pack exposes
HelpURL *url.URL // a help url to a page that describes what the pack does and how it is used
}
The main configuration struct for defining a pack.
Example ¶
package main
import (
"encoding/json"
"fmt"
"github.com/HotelsDotCom/flyte-client/flyte"
"net/url"
)
type CreateIssueInput struct {
Project string `json:"project"`
TicketText string `json:"ticketText"`
}
type IssueCreatedPayload struct {
Project string `json:"project"`
IssueId string `json:"issueId"`
Location *url.URL `json:"location"`
}
func main() {
// First we create event definitions that describe what events our pack can raise.
// An event definition contains the name of the event (mandatory) and a help URL (optional)
issueCreatedEventDef := flyte.EventDef{
Name: "IssueCreated",
}
issueCreationErrorEventDef := flyte.EventDef{
Name: "IssueCreationError",
}
// This pack has a single "createIssue" command. To implement a command we must provide a "CommandHandler" function matching the signature below.
// The client will call this handler every time it receives a "createIssue" action from the Flyte api. The handler will take the input JSON from the action
// and must return a flyte.Event. Handlers are where the functionality of the pack is implemented so will likely form the bulk of most packs.
createIssueHandler := func(input json.RawMessage) flyte.Event {
// deserialize the raw JSON into our domain struct
var createIssueInput CreateIssueInput
json.Unmarshal(input, &createIssueInput)
// call some ticket creation code...
// ...
// if it succeeds then return something like the following. The payload will be serialised to JSON and sent to the Flyte api server.
return flyte.Event{
EventDef: issueCreatedEventDef,
Payload: IssueCreatedPayload{
Project: "FOO",
IssueId: "123",
},
}
}
// Next we create a struct that defines the "createIssue" command. Note the handler above is passed to it.
// Also note that we specify what events the command can output.
createIssueCommand := flyte.Command{
Name: "createIssue",
OutputEvents: []flyte.EventDef{
issueCreatedEventDef,
issueCreationErrorEventDef,
},
Handler: createIssueHandler,
}
// you can add (optional) labels that act as a filter that determines when the pack will execute against a flow
// in this example the pack will only run in a 'production' environment
labels := make(map[string]string)
labels["env"] = "prod"
// you can provide a help URL that describes what the pack does and is used for
helpUrl, _ := url.Parse("http://jirapack/help#create-issue-command")
// now we are ready to create the PackDef struct which pulls together the above structs to give the full definition of the pack.
packDef := flyte.PackDef{
Name: "JiraPack",
Labels: labels,
EventDefs: []flyte.EventDef{
issueCreatedEventDef,
issueCreationErrorEventDef,
},
Commands: []flyte.Command{createIssueCommand},
HelpURL: helpUrl,
}
fmt.Printf("%+v", packDef)
}