empire

package module
v0.10.1 Latest Latest
Warning

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

Go to latest
Published: Jun 14, 2016 License: BSD-2-Clause Imports: 37 Imported by: 0

README

Empire

readthedocs badge Circle CI

Empire

Empire is a control layer on top of Amazon EC2 Container Service (ECS) that provides a Heroku like workflow. It conforms to a subset of the Heroku Platform API, which means you can use the same tools and processes that you use with Heroku, but with all the power of EC2 and Docker.

Empire is targeted at small to medium sized startups that are running a large number of microservices and need more flexibility than what Heroku provides. You can read the original blog post about why we built empire on the Remind engineering blog.

Quickstart

Install

To use Empire, you'll need to have an ECS cluster running. See the quickstart guide for more information.

Architecture

Empire aims to make it trivially easy to deploy a container based microservices architecture, without all of the complexities of managing systems like Mesos or Kubernetes. ECS takes care of much of that work, but Empire attempts to enhance the interface to ECS for deploying and maintaining applications, allowing you to deploy Docker images as easily as:

$ emp deploy remind101/acme-inc:latest
Heroku API compatibility

Empire supports a subset of the Heroku Platform API, which means any tool that uses the Heroku API can probably be used with Empire, if the endpoint is supported.

As an example, you can use the hk CLI with Empire like this:

$ HEROKU_API_URL=<empire_url> hk ...

However, the best user experience will be by using the emp command, which is a fork of hk with Empire specific features.

Routing

Empire's routing layer is backed by internal ELBs. Any application that specifies a web process will get an internal ELB attached to its associated ECS Service. When a new version of the app is deployed, ECS manages spinning up the new versions of the process, waiting for old connections to drain, then killing the old release.

When a new internal ELB is created, an associated CNAME record will be created in Route53 under the internal TLD, which means you can use DNS for service discovery. If we deploy an app named feed then it will be available at http://feed within the ECS cluster.

Apps default to only being exposed internally, unless you add a custom domain to them. Adding a custom domain will create a new external ELB for the ECS service.

Deploying

Any tagged Docker image can be deployed to Empire as an app. Empire doesn't enforce how you tag your Docker images, but we recommend tagging the image with the git sha that it was built from, and deploying that. We have a tool for performing deployments called Tugboat that supports deploying Docker images to Empire.

When you deploy a Docker image to Empire, it will extract a Procfile from the WORKDIR. Like Heroku, you can specify different process types that compose your service (e.g. web and worker), and scale them individually. Each process type in the Procfile maps directly to an ECS Service.

Caveats

Because docker run does not exec commands within a shell, commands specified within the Procfile will also not be exec'd within a shell. This means that you cannot specify environment variables in the Procfile. The following is not valid:

web: acme-inc server -port=$PORT

If you need to specify environment variables as part of the command, we recommend splitting out your Procfile commands into small bash shims instead:

web: ./bin/web
#!/bin/bash

set -e

exec acme-inc server -port=$PORT

Tests

Unit tests live alongside each go file as _test.go.

There is also a tests directory that contains integration and functional tests that tests the system using the heroku-go client and the emp command.

To get started, run:

$ export GO15VENDOREXPERIMENT=1
$ make bootstrap

The bootstrap command assumes you have a running postgres server. It will create a database called empire using the postgres client connection defaults.

To run the tests:

$ make test

Development

If you want to contribute to Empire, you may end up wanting to run a local instance against an ECS cluster. Doing this is relatively easy:

  1. Ensure that you have the AWS CLI installed and configured.

  2. Ensure that you accepted the terms and conditions for the official ECS AMI:

    https://aws.amazon.com/marketplace/ordering?productId=4ce33fd9-63ff-4f35-8d3a-939b641f1931&ref_=dtl_psb_continue&region=us-east-1

    Also check that the offical ECS AMI ID for US East matches with the one in cloudformation.json: https://github.com/remind101/empire/blob/master/docs/cloudformation.json#L20

  3. Run docker-machine and export the environment variables so Empire can connect:

    $ docker-machine start default
    $ eval "$(docker-machine env default)"
    
  4. Run the bootstrap script, which will create a cloudformation stack, ecs cluster and populate a .env file:

    $ ./bin/bootstrap
    
  5. Run Empire with docker-compose:

    $ docker-compose up db # Only need to do this the first time, so that the db can initialize.
    $ docker-compose up
    

    NOTE: You might need to run this twice the first time you start it up, to give the postgres container time to initialize.

  6. Install the emp CLI.

Empire will be available at http://$(docker-machine ip default):8080 and you can point the CLI there.

$ export EMPIRE_API_URL=http://$(docker-machine ip default):8080
$ emp deploy remind101/acme-inc
Vendoring

Empire follows Go's convention of vendoring third party dependencies. We use the Go 1.5+ vendor expirement, and manage the ./vendor/ directory via govendor.

When you add a new dependency, be sure to vendor it with govendor:

$ govendor add <package>
Releasing

Perform the following steps when releasing a new version:

  1. Create a new branch release-VERSION.
  2. Bump the version number with make bump (this will add a commit to the branch).
  3. Change HEAD -> VERSION in CHANGELOG.md.
  4. Open a PR to review.
  5. Once merged into master, wait for the Conveyor build to complete.
  6. Finally, tag the commit with the version as v<VERSION>. This will trigger CircleCI to:
    • Tag the image in Docker Hub with the version.
    • Build Linux and OS X versions of the CLI and Daemon.
    • Create a new GitHub Release and upload the artifacts.
  7. Update the new GitHub Release to be human readable.
  8. Open a PR against Homebrew to update the emp CLI: https://github.com/Homebrew/homebrew-core/blob/master/Formula/emp.rb

Community

We have a google group, empire-dev, where you can ask questions and engage with the Empire community.

Documentation

Index

Constants

View Source
const (
	ExposePrivate = "private"
	ExposePublic  = "public"
)
View Source
const (
	// WebPort is the default PORT to set on web processes.
	WebPort = 8080

	// WebProcessType is the process type we assume are web server processes.
	WebProcessType = "web"
)
View Source
const Version = "0.10.1"

Variables

View Source
var (
	Constraints1X = Constraints{constraints.CPUShare(256), constraints.Memory(512 * MB), constraints.Nproc(256)}
	Constraints2X = Constraints{constraints.CPUShare(512), constraints.Memory(1 * GB), constraints.Nproc(512)}
	ConstraintsPX = Constraints{constraints.CPUShare(1024), constraints.Memory(6 * GB), 0}

	// NamedConstraints maps a heroku dynos size to a Constraints.
	NamedConstraints = map[string]Constraints{
		"1X": Constraints1X,
		"2X": Constraints2X,
		"PX": ConstraintsPX,
	}

	// DefaultConstraints defaults to 1X process size.
	DefaultConstraints = Constraints1X
)
View Source
var (
	ErrDomainInUse        = errors.New("Domain currently in use by another app.")
	ErrDomainAlreadyAdded = errors.New("Domain already added to this app.")
	ErrDomainNotFound     = errors.New("Domain could not be found.")
)
View Source
var All = ScopeFunc(func(db *gorm.DB) *gorm.DB {
	return db
})

All returns a scope that simply returns the db.

View Source
var (
	// DefaultOptions is a default Options instance that can be passed when
	// intializing a new Empire.
	DefaultOptions = Options{}
)
View Source
var DefaultQuantities = map[string]int{
	"web": 1,
}

DefaultQuantities maps a process type to the default number of instances to run.

View Source
var (
	// ErrInvalidName is used to indicate that the app name is not valid.
	ErrInvalidName = &ValidationError{
		errors.New("An app name must be alphanumeric and dashes only, 3-30 chars in length."),
	}
)
View Source
var ErrNoReleases = errors.New("no releases")
View Source
var ErrUserName = errors.New("Name is required")
View Source
var Migrations = []migrate.Migration{
	{
		ID: 1,
		Up: migrate.Queries([]string{
			`CREATE EXTENSION IF NOT EXISTS hstore`,
			`CREATE EXTENSION IF NOT EXISTS "uuid-ossp"`,
			`CREATE TABLE apps (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  name varchar(30) NOT NULL,
  github_repo text,
  docker_repo text,
  created_at timestamp without time zone default (now() at time zone 'utc')
)`,
			`CREATE TABLE configs (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id uuid NOT NULL references apps(id) ON DELETE CASCADE,
  vars hstore,
  created_at timestamp without time zone default (now() at time zone 'utc')
)`,
			`CREATE TABLE slugs (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  image text NOT NULL,
  process_types hstore NOT NULL
)`,
			`CREATE TABLE releases (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id uuid NOT NULL references apps(id) ON DELETE CASCADE,
  config_id uuid NOT NULL references configs(id) ON DELETE CASCADE,
  slug_id uuid NOT NULL references slugs(id) ON DELETE CASCADE,
  version int NOT NULL,
  description text,
  created_at timestamp without time zone default (now() at time zone 'utc')
)`,
			`CREATE TABLE processes (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  release_id uuid NOT NULL references releases(id) ON DELETE CASCADE,
  "type" text NOT NULL,
  quantity int NOT NULL,
  command text NOT NULL
)`,
			`CREATE TABLE jobs (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id uuid NOT NULL references apps(id) ON DELETE CASCADE,
  release_version int NOT NULL,
  process_type text NOT NULL,
  instance int NOT NULL,

  environment hstore NOT NULL,
  image text NOT NULL,
  command text NOT NULL,
  updated_at timestamp without time zone default (now() at time zone 'utc')
)`,
			`CREATE TABLE deployments (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id uuid NOT NULL references apps(id) ON DELETE CASCADE,
  release_id uuid references releases(id),
  image text NOT NULL,
  status text NOT NULL,
  error text,
  created_at timestamp without time zone default (now() at time zone 'utc'),
  finished_at timestamp without time zone
)`,
			`CREATE UNIQUE INDEX index_apps_on_name ON apps USING btree (name)`,
			`CREATE UNIQUE INDEX index_apps_on_github_repo ON apps USING btree (github_repo)`,
			`CREATE UNIQUE INDEX index_apps_on_docker_repo ON apps USING btree (docker_repo)`,
			`CREATE UNIQUE INDEX index_processes_on_release_id_and_type ON processes USING btree (release_id, "type")`,
			`CREATE UNIQUE INDEX index_slugs_on_image ON slugs USING btree (image)`,
			`CREATE UNIQUE INDEX index_releases_on_app_id_and_version ON releases USING btree (app_id, version)`,
			`CREATE UNIQUE INDEX index_jobs_on_app_id_and_release_version_and_process_type_and_instance ON jobs (app_id, release_version, process_type, instance)`,
			`CREATE INDEX index_configs_on_created_at ON configs (created_at)`,
		}),
		Down: migrate.Queries([]string{
			`DROP TABLE apps CASCADE`,
			`DROP TABLE configs CASCADE`,
			`DROP TABLE slugs CASCADE`,
			`DROP TABLE releases CASCADE`,
			`DROP TABLE processes CASCADE`,
			`DROP TABLE jobs CASCADE`,
			`DROP TABLE deployments CASCADE`,
		}),
	},
	{
		ID: 2,
		Up: migrate.Queries([]string{
			`CREATE TABLE domains (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id uuid NOT NULL references apps(id) ON DELETE CASCADE,
  hostname text NOT NULL,
  created_at timestamp without time zone default (now() at time zone 'utc')
)`,
			`CREATE INDEX index_domains_on_app_id ON domains USING btree (app_id)`,
			`CREATE UNIQUE INDEX index_domains_on_hostname ON domains USING btree (hostname)`,
		}),
		Down: migrate.Queries([]string{
			`DROP TABLE domains CASCADE`,
		}),
	},
	{
		ID: 3,
		Up: migrate.Queries([]string{
			`DROP TABLE jobs`,
		}),
		Down: migrate.Queries([]string{
			`CREATE TABLE jobs (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id text NOT NULL references apps(name) ON DELETE CASCADE,
  release_version int NOT NULL,
  process_type text NOT NULL,
  instance int NOT NULL,

  environment hstore NOT NULL,
  image text NOT NULL,
  command text NOT NULL,
  updated_at timestamp without time zone default (now() at time zone 'utc')
)`,
		}),
	},
	{
		ID: 4,
		Up: migrate.Queries([]string{
			`CREATE TABLE ports (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  port integer,
  app_id uuid references apps(id) ON DELETE SET NULL
)`,
			`-- Insert 1000 ports
INSERT INTO ports (port) (SELECT generate_series(9000,10000))`,
		}),
		Down: migrate.Queries([]string{
			`DROP TABLE ports CASCADE`,
		}),
	},
	{
		ID: 5,
		Up: migrate.Queries([]string{
			`ALTER TABLE apps DROP COLUMN docker_repo`,
			`ALTER TABLE apps DROP COLUMN github_repo`,
			`ALTER TABLE apps ADD COLUMN repo text`,
			`DROP TABLE deployments`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE apps DROP COLUMN repo`,
			`ALTER TABLE apps ADD COLUMN docker_repo text`,
			`ALTER TABLE apps ADD COLUMN github_repo text`,
			`CREATE TABLE deployments (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id text NOT NULL references apps(name) ON DELETE CASCADE,
  release_id uuid references releases(id),
  image text NOT NULL,
  status text NOT NULL,
  error text,
  created_at timestamp without time zone default (now() at time zone 'utc'),
  finished_at timestamp without time zone
)`,
		}),
	},
	{
		ID: 6,
		Up: migrate.Queries([]string{
			`DROP INDEX index_slugs_on_image`,
		}),
		Down: migrate.Queries([]string{
			`CREATE UNIQUE INDEX index_slugs_on_image ON slugs USING btree (image)`,
		}),
	},
	{
		ID: 7,
		Up: migrate.Queries([]string{
			`-- Values: private, public
ALTER TABLE apps ADD COLUMN exposure TEXT NOT NULL default 'private'`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE apps DROP COLUMN exposure`,
		}),
	},
	{
		ID: 8,
		Up: migrate.Queries([]string{
			`CREATE TABLE certificates (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  app_id uuid NOT NULL references apps(id) ON DELETE CASCADE,
  name text,
  certificate_chain text,
  created_at timestamp without time zone default (now() at time zone 'utc'),
  updated_at timestamp without time zone default (now() at time zone 'utc')
)`,
			`CREATE UNIQUE INDEX index_certificates_on_app_id ON certificates USING btree (app_id)`,
		}),
		Down: migrate.Queries([]string{
			`DROP TABLE certificates CASCADE`,
		}),
	},
	{
		ID: 9,
		Up: migrate.Queries([]string{
			`ALTER TABLE processes ADD COLUMN cpu_share int`,
			`ALTER TABLE processes ADD COLUMN memory int`,
			`UPDATE processes SET cpu_share = 256, memory = 1073741824`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE processes DROP COLUMN cpu_share`,
			`ALTER TABLE processes DROP COLUMN memory`,
		}),
	},
	{
		ID: 10,
		Up: migrate.Queries([]string{
			`ALTER TABLE processes ALTER COLUMN memory TYPE bigint`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE processes ALTER COLUMN memory TYPE integer`,
		}),
	},
	{
		ID: 11,
		Up: migrate.Queries([]string{
			`ALTER TABLE apps ADD COLUMN cert text`,
			`UPDATE apps SET cert = (select name from certificates where certificates.app_id = apps.id)`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE apps DROP COLUMN cert`,
		}),
	},
	{
		ID: 12,
		Up: migrate.Queries([]string{
			`ALTER TABLE processes ADD COLUMN nproc bigint`,
			`UPDATE processes SET nproc = 0`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE processes DROP COLUMN nproc`,
		}),
	},
	{
		ID: 13,
		Up: migrate.Queries([]string{
			`ALTER TABLE ports ADD COLUMN taken text`,
			`UPDATE ports SET taken = 't' FROM (SELECT port FROM ports WHERE app_id is not NULL) as used_ports WHERE ports.port = used_ports.port`,
		}),
		Down: migrate.Queries([]string{
			`ALTER TABLE ports DROP column taken`,
		}),
	},

	{
		ID: 14,
		Up: func(tx *sql.Tx) error {
			_, err := tx.Exec(`ALTER TABLE slugs ADD COLUMN process_types_json json`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE processes ADD COLUMN command_json json`)
			if err != nil {
				return err
			}

			rows, err := tx.Query(`SELECT id, process_types FROM slugs`)
			if err != nil {
				return err
			}

			slugs := make(map[string]map[string]Command)
			for rows.Next() {
				var id string
				var ptypes hstore.Hstore
				if err := rows.Scan(&id, &ptypes); err != nil {
					return err
				}
				m := make(map[string]Command)
				for k, v := range ptypes.Map {
					command, err := ParseCommand(v.String)
					if err != nil {
						return err
					}
					m[k] = command
				}
				slugs[id] = m
			}

			if err := rows.Err(); err != nil {
				return err
			}

			rows.Close()

			for id, ptypes := range slugs {
				raw, err := json.Marshal(ptypes)
				if err != nil {
					return err
				}

				_, err = tx.Exec(`UPDATE slugs SET process_types_json = $1 WHERE id = $2`, raw, id)
				if err != nil {
					return err
				}
			}

			_, err = tx.Exec(`ALTER TABLE slugs DROP COLUMN process_types`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE slugs RENAME COLUMN process_types_json to process_types`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE slugs ALTER COLUMN process_types SET NOT NULL`)
			if err != nil {
				return err
			}

			rows, err = tx.Query(`SELECT id, command FROM processes`)
			if err != nil {
				return err
			}

			commands := make(map[string]string)
			for rows.Next() {
				var id, command string
				if err := rows.Scan(&id, &command); err != nil {
					return err
				}
				commands[id] = command
			}

			if err := rows.Err(); err != nil {
				return err
			}

			rows.Close()

			for id, command := range commands {
				cmd, err := ParseCommand(command)
				if err != nil {
					return err
				}

				query := `UPDATE processes SET command_json = $1 WHERE id = $2`
				_, err = tx.Exec(query, cmd, id)
				if err != nil {
					return err
				}
			}

			_, err = tx.Exec(`ALTER TABLE processes DROP COLUMN command`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE processes RENAME COLUMN command_json TO command`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE processes ALTER COLUMN command SET NOT NULL`)
			return err
		},
		Down: migrate.Queries([]string{
			`ALTER TABLE processes DROP COLUMN command`,
			`ALTER TABLE processes ADD COLUMN command text not null`,
			`ALTER TABLE slugs DROP COLUMN process_types`,
			`ALTER TABLE slugs ADD COLUMN process_types hstore not null`,
		}),
	},

	{
		ID: 15,
		Up: func(tx *sql.Tx) error {
			_, err := tx.Exec(`ALTER TABLE slugs ADD COLUMN procfile bytea`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE releases ADD COLUMN formation json`)
			if err != nil {
				return err
			}

			rows, err := tx.Query(`SELECT id, process_types FROM slugs`)
			if err != nil {
				return err
			}

			slugs := make(map[string]procfile.Procfile)
			for rows.Next() {
				var id string
				var ptypes []byte
				if err := rows.Scan(&id, &ptypes); err != nil {
					return err
				}
				m := make(map[string][]string)
				if err := json.Unmarshal(ptypes, &m); err != nil {
					return err
				}
				p := make(procfile.ExtendedProcfile)
				for name, command := range m {
					p[name] = procfile.Process{
						Command: command,
					}
				}
				slugs[id] = p
			}

			if err := rows.Err(); err != nil {
				return err
			}

			rows.Close()

			for id, p := range slugs {
				raw, err := procfile.Marshal(p)
				if err != nil {
					return err
				}

				_, err = tx.Exec(`UPDATE slugs SET procfile = $1 WHERE id = $2`, raw, id)
				if err != nil {
					return err
				}
			}

			_, err = tx.Exec(`ALTER TABLE slugs DROP COLUMN process_types`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`ALTER TABLE slugs ALTER COLUMN procfile SET NOT NULL`)
			if err != nil {
				return err
			}

			rows, err = tx.Query(`SELECT release_id, id, type, quantity, command, memory, cpu_share, nproc FROM processes`)
			if err != nil {
				return err
			}

			formations := make(map[string]Formation)
			for rows.Next() {
				var release, id, ptype string
				var command Command
				var quantity, memory, cpu, nproc int
				if err := rows.Scan(&release, &id, &ptype, &quantity, &command, &memory, &cpu, &nproc); err != nil {
					return err
				}
				if formations[release] == nil {
					formations[release] = make(Formation)
				}

				f := formations[release]
				f[ptype] = Process{
					Command:  command,
					Quantity: quantity,
					Memory:   constraints.Memory(memory),
					CPUShare: constraints.CPUShare(cpu),
					Nproc:    constraints.Nproc(nproc),
				}
			}

			if err := rows.Err(); err != nil {
				return err
			}

			rows.Close()

			for id, f := range formations {
				_, err = tx.Exec(`UPDATE releases SET formation = $1 WHERE id = $2`, f, id)
				if err != nil {
					return err
				}
			}

			_, err = tx.Exec(`ALTER TABLE releases ALTER COLUMN formation SET NOT NULL`)
			if err != nil {
				return err
			}

			_, err = tx.Exec(`DROP TABLE processes`)

			return err
		},
		Down: migrate.Queries([]string{
			`ALTER TABLE releases DROP COLUMN formation`,
			`ALTER TABLE slugs DROP COLUMN procfile`,
			`ALTER TABLE slugs ADD COLUMN process_types hstore not null`,
			`CREATE TABLE processes (
  id uuid NOT NULL DEFAULT uuid_generate_v4() primary key,
  release_id uuid NOT NULL references releases(id) ON DELETE CASCADE,
  "type" text NOT NULL,
  quantity int NOT NULL,
  command text NOT NULL,
  cpu_share int,
  memory bigint,
  nproc bigint
)`,
			`CREATE UNIQUE INDEX index_processes_on_release_id_and_type ON processes USING btree (release_id, "type")`,
		}),
	},

	{
		ID: 16,
		Up: migrate.Queries([]string{
			`CREATE TABLE stacks (
  app_id text NOT NULL,
  stack_name text NOT NULL
)`,
			`CREATE UNIQUE INDEX index_stacks_on_app_id ON stacks USING btree (app_id)`,
			`CREATE UNIQUE INDEX index_stacks_on_stack_name ON stacks USING btree (stack_name)`,
		}),
		Down: migrate.Queries([]string{
			`DROP TABLE stacks`,
		}),
	},

	{
		ID: 17,
		Up: migrate.Queries([]string{
			`CREATE TABLE scheduler_migration (app_id text NOT NULL, backend text NOT NULL)`,
			`INSERT INTO scheduler_migration (app_id, backend) SELECT id, 'ecs' FROM apps`,
		}),
		Down: migrate.Queries([]string{
			`DROP TABLE scheduler_migration`,
		}),
	},
}
View Source
var NamePattern = regexp.MustCompile(`^[a-z][a-z0-9-]{2,30}$`)

NamePattern is a regex pattern that app names must conform to.

View Source
var NullEventStream = EventStreamFunc(func(event Event) error {
	return nil
})

NullEventStream an events service that does nothing.

View Source
var (
	// ProcfileName is the name of the Procfile file.
	ProcfileName = "Procfile"
)

Functions

func AppID

func AppID(id string) func(*gorm.DB) *gorm.DB

AppID returns a scope to find an app by id.

func AppNameFromRepo

func AppNameFromRepo(repo string) string

AppNameFromRepo generates a name from a Repo

remind101/r101-api => r101-api

func SignToken

func SignToken(secret []byte, token *AccessToken) (string, error)

SignToken jwt signs the token and adds the signature to the Token field.

Types

type AccessToken

type AccessToken struct {
	Token string
	User  *User
}

AccessToken represents a token that allow access to the api.

func ParseToken

func ParseToken(secret []byte, token string) (*AccessToken, error)

ParseToken parses a string token, verifies it, and returns an AccessToken instance.

func (*AccessToken) IsValid added in v0.10.1

func (t *AccessToken) IsValid() error

IsValid returns nil if the AccessToken is valid.

type App

type App struct {
	ID string

	Name string

	Repo *string

	// Valid values are empire.ExposePrivate and empire.ExposePublic.
	Exposure string

	// The name of an SSL cert for the web process of this app.
	Cert string

	CreatedAt *time.Time
}

App represents an app.

func (*App) BeforeCreate

func (a *App) BeforeCreate() error

func (*App) IsValid

func (a *App) IsValid() error

IsValid returns an error if the app isn't valid.

type AppEvent added in v0.10.1

type AppEvent interface {
	Event
	GetApp() *App
}

AppEvent is an Event that relates to a specific App.

type AppsQuery

type AppsQuery struct {
	// If provided, an App ID to find.
	ID *string

	// If provided, finds apps matching the given name.
	Name *string

	// If provided, finds apps with the given repo attached.
	Repo *string
}

AppsQuery is a Scope implementation for common things to filter releases by.

func (AppsQuery) Scope

func (q AppsQuery) Scope(db *gorm.DB) *gorm.DB

Scope implements the Scope interface.

type AsyncEventStream added in v0.10.0

type AsyncEventStream struct {
	EventStream
	// contains filtered or unexported fields
}

AsyncEventStream wraps an array of EventStreams to publish events asynchronously in a goroutine

func AsyncEvents added in v0.10.0

func AsyncEvents(e EventStream) *AsyncEventStream

AsyncEvents returns a new AsyncEventStream that will buffer upto 100 events before applying backpressure.

func (*AsyncEventStream) PublishEvent added in v0.10.0

func (e *AsyncEventStream) PublishEvent(event Event) error

type CMDExtractor added in v0.10.1

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

CommandExtractor is an Extractor implementation that returns a Procfile based on the CMD directive in the Dockerfile. It makes the assumption that the cmd is a "web" process.

func NewCMDExtractor added in v0.10.1

func NewCMDExtractor(c *docker.Client) *CMDExtractor

func (*CMDExtractor) Extract added in v0.10.1

func (e *CMDExtractor) Extract(_ context.Context, img image.Image, _ io.Writer) ([]byte, error)

type Command

type Command []string

Command represents the actual shell command that gets executed for a given ProcessType.

func MustParseCommand added in v0.10.1

func MustParseCommand(command string) Command

MustParseCommand parses the string into a Command, panicing if there's an error. This method should only be used in tests for convenience.

func ParseCommand added in v0.10.1

func ParseCommand(command string) (Command, error)

ParseCommand parses a string into a Command, taking quotes and other shell words into account.

func (*Command) Scan

func (c *Command) Scan(src interface{}) error

Scan implements the sql.Scanner interface.

func (Command) String added in v0.10.1

func (c Command) String() string

String returns the string reprsentation of the command.

func (Command) Value

func (c Command) Value() (driver.Value, error)

Value implements the driver.Value interface.

type ComposedScope

type ComposedScope []Scope

ComposedScope is an implementation of the Scope interface that chains the scopes together.

func (ComposedScope) Scope

func (s ComposedScope) Scope(db *gorm.DB) *gorm.DB

Scope implements the Scope interface.

type Config

type Config struct {
	ID   string
	Vars Vars

	AppID string
	App   *App
}

Config represents a collection of environment variables.

func NewConfig

func NewConfig(old *Config, vars Vars) *Config

NewConfig initializes a new config based on the old config, with the new variables provided.

type ConfigsQuery

type ConfigsQuery struct {
	// If provided, returns finds the config with the given id.
	ID *string

	// If provided, filters configs for the given app.
	App *App
}

ConfigsQuery is a Scope implementation for common things to filter releases by.

func (ConfigsQuery) Scope

func (q ConfigsQuery) Scope(db *gorm.DB) *gorm.DB

Scope implements the Scope interface.

type Constraints

type Constraints constraints.Constraints

Constraints aliases empire.Constraints type to implement the json.Unmarshaller interface.

func (Constraints) String

func (c Constraints) String() string

func (*Constraints) UnmarshalJSON

func (c *Constraints) UnmarshalJSON(b []byte) error

type CreateEvent added in v0.10.0

type CreateEvent struct {
	User    string
	Name    string
	Message string
}

CreateEvent is triggered when a user creates a new application.

func (CreateEvent) Event added in v0.10.0

func (e CreateEvent) Event() string

func (CreateEvent) String added in v0.10.0

func (e CreateEvent) String() string

type CreateOpts added in v0.10.0

type CreateOpts struct {
	// User performing the action.
	User *User

	// Name of the application.
	Name string

	// Commit message
	Message string
}

CreateOpts are options that are provided when creating a new application.

func (CreateOpts) Event added in v0.10.0

func (opts CreateOpts) Event() CreateEvent

func (CreateOpts) Validate added in v0.10.1

func (opts CreateOpts) Validate(e *Empire) error

type DB added in v0.10.0

type DB struct {
	*gorm.DB
	// contains filtered or unexported fields
}

DB wraps a gorm.DB and provides the datastore layer for Empire.

func OpenDB added in v0.10.0

func OpenDB(uri string) (*DB, error)

OpenDB returns a new gorm.DB instance.

func (*DB) Debug added in v0.10.0

func (db *DB) Debug()

Debug puts the db in debug mode, which logs all queries.

func (*DB) IsHealthy added in v0.10.0

func (db *DB) IsHealthy() bool

IsHealthy checks that we can connect to the database.

func (*DB) MigrateUp added in v0.10.0

func (db *DB) MigrateUp() error

MigrateUp migrates the database to the latest version of the schema.

func (*DB) Reset added in v0.10.0

func (db *DB) Reset() error

Reset resets the database to a pristine state.

type DeployEvent added in v0.10.0

type DeployEvent struct {
	User        string
	App         string
	Image       string
	Environment string
	Release     int
	Message     string
	// contains filtered or unexported fields
}

DeployEvent is triggered when a user deploys a new image to an app.

func (DeployEvent) Event added in v0.10.0

func (e DeployEvent) Event() string

func (DeployEvent) GetApp added in v0.10.1

func (e DeployEvent) GetApp() *App

func (DeployEvent) String added in v0.10.0

func (e DeployEvent) String() string

type DeploymentsCreateOpts

type DeploymentsCreateOpts struct {
	// User the user that is triggering the deployment.
	User *User

	// App is the app that is being deployed to.
	App *App

	// Image is the image that's being deployed.
	Image image.Image

	// Environment is the environment where the image is being deployed
	Environment string

	// Output is an io.Writer where deployment output and events will be
	// streamed in jsonmessage format.
	Output io.Writer

	// Commit message
	Message string
}

DeploymentsCreateOpts represents options that can be passed when deploying to an application.

func (DeploymentsCreateOpts) Event added in v0.10.0

func (opts DeploymentsCreateOpts) Event() DeployEvent

func (DeploymentsCreateOpts) Validate added in v0.10.1

func (opts DeploymentsCreateOpts) Validate(e *Empire) error

type DestroyEvent added in v0.10.0

type DestroyEvent struct {
	User    string
	App     string
	Message string
}

DestroyEvent is triggered when a user destroys an application.

func (DestroyEvent) Event added in v0.10.0

func (e DestroyEvent) Event() string

func (DestroyEvent) String added in v0.10.0

func (e DestroyEvent) String() string

type DestroyOpts added in v0.10.0

type DestroyOpts struct {
	// User performing the action.
	User *User

	// The associated app.
	App *App

	// Commit message
	Message string
}

DestroyOpts are options provided when destroying an application.

func (DestroyOpts) Event added in v0.10.0

func (opts DestroyOpts) Event() DestroyEvent

func (DestroyOpts) Validate added in v0.10.1

func (opts DestroyOpts) Validate(e *Empire) error

type Domain

type Domain struct {
	ID        string
	Hostname  string
	CreatedAt *time.Time

	AppID string
	App   *App
}

func (*Domain) BeforeCreate

func (d *Domain) BeforeCreate() error

type DomainsQuery

type DomainsQuery struct {
	// If provided, finds domains matching the given hostname.
	Hostname *string

	// If provided, filters domains belonging to the given app.
	App *App
}

DomainsQuery is a Scope implementation for common things to filter releases by.

func (DomainsQuery) Scope

func (q DomainsQuery) Scope(db *gorm.DB) *gorm.DB

Scope implements the Scope interface.

type Empire

type Empire struct {
	DB *DB

	// Scheduler is the backend scheduler used to run applications.
	Scheduler scheduler.Scheduler

	// LogsStreamer is the backend used to stream application logs.
	LogsStreamer LogsStreamer

	// ProcfileExtractor is called during deployments to extract the
	// Formation from the Procfile in the newly deployed image.
	ProcfileExtractor ProcfileExtractor

	// Environment represents the environment this Empire server is responsible for
	Environment string

	// EventStream service for publishing Empire events.
	EventStream

	// RunRecorder is used to record the logs from interactive runs.
	RunRecorder RunRecorder

	// MessagesRequired is a boolean used to determine if messages should be required for events.
	MessagesRequired bool
	// contains filtered or unexported fields
}

Empire is a context object that contains a collection of services.

func New

func New(db *DB, options Options) *Empire

New returns a new Empire instance.

func (*Empire) AccessTokensCreate

func (e *Empire) AccessTokensCreate(accessToken *AccessToken) (*AccessToken, error)

AccessTokensCreate creates a new AccessToken.

func (*Empire) AccessTokensFind

func (e *Empire) AccessTokensFind(token string) (*AccessToken, error)

AccessTokensFind finds an access token.

func (*Empire) Apps

func (e *Empire) Apps(q AppsQuery) ([]*App, error)

Apps returns all Apps.

func (*Empire) AppsFind added in v0.10.0

func (e *Empire) AppsFind(q AppsQuery) (*App, error)

AppsFind finds the first app matching the query.

func (*Empire) CertsAttach added in v0.10.0

func (e *Empire) CertsAttach(ctx context.Context, app *App, cert string) error

CertsAttach attaches an SSL certificate to the app.

func (*Empire) Config added in v0.10.0

func (e *Empire) Config(app *App) (*Config, error)

Config returns the current Config for a given app.

func (*Empire) Create added in v0.10.0

func (e *Empire) Create(ctx context.Context, opts CreateOpts) (*App, error)

Create creates a new app.

func (*Empire) Deploy

func (e *Empire) Deploy(ctx context.Context, opts DeploymentsCreateOpts) (*Release, error)

Deploy deploys an image and streams the output to w.

func (*Empire) Destroy added in v0.10.0

func (e *Empire) Destroy(ctx context.Context, opts DestroyOpts) error

Destroy destroys an app.

func (*Empire) Domains

func (e *Empire) Domains(q DomainsQuery) ([]*Domain, error)

Domains returns all domains matching the query.

func (*Empire) DomainsCreate

func (e *Empire) DomainsCreate(ctx context.Context, domain *Domain) (*Domain, error)

DomainsCreate adds a new Domain for an App.

func (*Empire) DomainsDestroy

func (e *Empire) DomainsDestroy(ctx context.Context, domain *Domain) error

DomainsDestroy removes a Domain for an App.

func (*Empire) DomainsFind added in v0.10.0

func (e *Empire) DomainsFind(q DomainsQuery) (*Domain, error)

DomainsFind returns the first domain matching the query.

func (*Empire) IsHealthy

func (e *Empire) IsHealthy() bool

IsHealthy returns true if Empire is healthy, which means it can connect to the services it depends on.

func (*Empire) ListScale added in v0.10.1

func (e *Empire) ListScale(ctx context.Context, app *App) (Formation, error)

ListScale lists the current scale settings for a given App

func (*Empire) Releases

func (e *Empire) Releases(q ReleasesQuery) ([]*Release, error)

Releases returns all Releases for a given App.

func (*Empire) ReleasesFind added in v0.10.0

func (e *Empire) ReleasesFind(q ReleasesQuery) (*Release, error)

ReleasesFind returns the first releases for a given App.

func (*Empire) Reset

func (e *Empire) Reset() error

Reset resets empire.

func (*Empire) Restart added in v0.10.0

func (e *Empire) Restart(ctx context.Context, opts RestartOpts) error

Restart restarts processes matching the given prefix for the given Release. If the prefix is empty, it will match all processes for the release.

func (*Empire) Rollback added in v0.10.0

func (e *Empire) Rollback(ctx context.Context, opts RollbackOpts) (*Release, error)

Rollback rolls an app back to a specific release version. Returns a new release.

func (*Empire) Run added in v0.10.0

func (e *Empire) Run(ctx context.Context, opts RunOpts) error

Run runs a one-off process for a given App and command.

func (*Empire) Scale added in v0.10.0

func (e *Empire) Scale(ctx context.Context, opts ScaleOpts) (*Process, error)

Scale scales an apps process.

func (*Empire) Set added in v0.10.0

func (e *Empire) Set(ctx context.Context, opts SetOpts) (*Config, error)

Set applies the new config vars to the apps current Config, returning the new Config. If the app has a running release, a new release will be created and run.

func (*Empire) StreamLogs added in v0.9.2

func (e *Empire) StreamLogs(app *App, w io.Writer, duration time.Duration) error

Streamlogs streams logs from an app.

func (*Empire) Tasks added in v0.10.0

func (e *Empire) Tasks(ctx context.Context, app *App) ([]*Task, error)

Tasks returns the Tasks for the given app.

type Event added in v0.10.0

type Event interface {
	// Returns the name of the event.
	Event() string

	// Returns a human readable string about the event.
	String() string
}

Event represents an event triggered within Empire.

type EventStream added in v0.10.0

type EventStream interface {
	PublishEvent(Event) error
}

EventStream is an interface for publishing events that happen within Empire.

type EventStreamFunc added in v0.10.0

type EventStreamFunc func(Event) error

EventStreamFunc is a function that implements the Events interface.

func (EventStreamFunc) PublishEvent added in v0.10.0

func (fn EventStreamFunc) PublishEvent(event Event) error

type FileExtractor added in v0.10.1

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

FileExtractor is an implementation of the Extractor interface that extracts the Procfile from the images WORKDIR.

func NewFileExtractor added in v0.10.1

func NewFileExtractor(c *docker.Client) *FileExtractor

func (*FileExtractor) Extract added in v0.10.1

func (e *FileExtractor) Extract(_ context.Context, img image.Image, w io.Writer) ([]byte, error)

Extract implements Extractor Extract.

type Formation

type Formation map[string]Process

Formation represents a collection of named processes and their configuration.

func (Formation) Merge added in v0.10.1

func (f Formation) Merge(other Formation) Formation

Merge merges in the existing quantity and constraints from the old Formation into this Formation.

func (*Formation) Scan added in v0.10.1

func (f *Formation) Scan(src interface{}) error

Scan implements the sql.Scanner interface.

func (Formation) Value added in v0.10.1

func (f Formation) Value() (driver.Value, error)

Value implements the driver.Value interface.

type KinesisLogsStreamer added in v0.10.0

type KinesisLogsStreamer struct{}

func NewKinesisLogsStreamer added in v0.10.0

func NewKinesisLogsStreamer() *KinesisLogsStreamer

func (*KinesisLogsStreamer) StreamLogs added in v0.10.0

func (s *KinesisLogsStreamer) StreamLogs(app *App, w io.Writer, duration time.Duration) error

type LogsStreamer added in v0.9.2

type LogsStreamer interface {
	StreamLogs(*App, io.Writer, time.Duration) error
}

type MessageRequiredError added in v0.10.1

type MessageRequiredError struct{}

func (*MessageRequiredError) Error added in v0.10.1

func (e *MessageRequiredError) Error() string

type MultiEventStream added in v0.10.1

type MultiEventStream []EventStream

MultiEventStream is an EventStream implementation that publishes the event to multiple EventStreams, returning any errors after publishing to all streams.

func (MultiEventStream) PublishEvent added in v0.10.1

func (streams MultiEventStream) PublishEvent(e Event) error

type Options

type Options struct {
	Secret string
}

Options is provided to New to configure the Empire services.

type Process

type Process struct {
	Command  Command              `json:"Command,omitempty"`
	Quantity int                  `json:"Quantity,omitempty"`
	Memory   constraints.Memory   `json:"Memory,omitempty"`
	CPUShare constraints.CPUShare `json:"CPUShare,omitempty"`
	Nproc    constraints.Nproc    `json:"Nproc,omitempty"`
}

Process holds configuration information about a Process.

func (*Process) Constraints added in v0.10.1

func (p *Process) Constraints() Constraints

Constraints returns a constraints.Constraints from this Process definition.

func (*Process) SetConstraints added in v0.10.1

func (p *Process) SetConstraints(c Constraints)

SetConstraints sets the memory/cpu/nproc for this Process to the given constraints.

type ProcfileError

type ProcfileError struct {
	Err error
}

Example instance: Procfile doesn't exist

func (*ProcfileError) Error

func (e *ProcfileError) Error() string

type ProcfileExtractor added in v0.10.0

type ProcfileExtractor interface {
	Extract(context.Context, image.Image, io.Writer) ([]byte, error)
}

ProcfileExtractor represents something that can extract a Procfile from an image.

func MultiExtractor added in v0.10.1

func MultiExtractor(extractors ...ProcfileExtractor) ProcfileExtractor

MultiExtractor is an Extractor implementation that tries multiple Extractors in succession until one succeeds.

func PullAndExtract added in v0.10.0

func PullAndExtract(c *dockerutil.Client) ProcfileExtractor

PullAndExtract returns a ProcfileExtractor that will pull the image using the docker client, then attempt to extract the the Procfile, or fallback to the CMD directive in the Dockerfile.

type ProcfileExtractorFunc added in v0.10.1

type ProcfileExtractorFunc func(context.Context, image.Image, io.Writer) ([]byte, error)

func (ProcfileExtractorFunc) Extract added in v0.10.1

func (fn ProcfileExtractorFunc) Extract(ctx context.Context, image image.Image, w io.Writer) ([]byte, error)

type Release

type Release struct {
	ID      string
	Version int

	AppID string
	App   *App

	ConfigID string
	Config   *Config

	SlugID string
	Slug   *Slug

	Formation Formation

	Description string
	CreatedAt   *time.Time
}

Release is a combination of a Config and a Slug, which form a deployable release.

func (*Release) BeforeCreate

func (r *Release) BeforeCreate() error

BeforeCreate sets created_at before inserting.

type ReleasesQuery

type ReleasesQuery struct {
	// If provided, an app to filter by.
	App *App

	// If provided, a version to filter by.
	Version *int

	// If provided, uses the limit and sorting parameters specified in the range.
	Range headerutil.Range
}

ReleasesQuery is a Scope implementation for common things to filter releases by.

func (ReleasesQuery) DefaultRange

func (q ReleasesQuery) DefaultRange() headerutil.Range

DefaultRange returns the default headerutil.Range used if values aren't provided.

func (ReleasesQuery) Scope

func (q ReleasesQuery) Scope(db *gorm.DB) *gorm.DB

Scope implements the Scope interface.

type RestartEvent added in v0.10.0

type RestartEvent struct {
	User    string
	App     string
	PID     string
	Message string
	// contains filtered or unexported fields
}

RestartEvent is triggered when a user restarts an application.

func (RestartEvent) Event added in v0.10.0

func (e RestartEvent) Event() string

func (RestartEvent) GetApp added in v0.10.1

func (e RestartEvent) GetApp() *App

func (RestartEvent) String added in v0.10.0

func (e RestartEvent) String() string

type RestartOpts added in v0.10.0

type RestartOpts struct {
	// User performing the action.
	User *User

	// The associated app.
	App *App

	// If provided, a PID that will be killed. Generally used for killing
	// detached processes.
	PID string

	// Commit message
	Message string
}

RestartOpts are options provided when restarting an app.

func (RestartOpts) Event added in v0.10.0

func (opts RestartOpts) Event() RestartEvent

func (RestartOpts) Validate added in v0.10.1

func (opts RestartOpts) Validate(e *Empire) error

type RollbackEvent added in v0.10.0

type RollbackEvent struct {
	User    string
	App     string
	Version int
	Message string
	// contains filtered or unexported fields
}

RollbackEvent is triggered when a user rolls back to an old version.

func (RollbackEvent) Event added in v0.10.0

func (e RollbackEvent) Event() string

func (RollbackEvent) GetApp added in v0.10.1

func (e RollbackEvent) GetApp() *App

func (RollbackEvent) String added in v0.10.0

func (e RollbackEvent) String() string

type RollbackOpts added in v0.10.0

type RollbackOpts struct {
	// The user performing the action.
	User *User

	// The associated app.
	App *App

	// The release version to rollback to.
	Version int

	// Commit message
	Message string
}

RollbackOpts are options provided when rolling back to an old release.

func (RollbackOpts) Event added in v0.10.0

func (opts RollbackOpts) Event() RollbackEvent

func (RollbackOpts) Validate added in v0.10.1

func (opts RollbackOpts) Validate(e *Empire) error

type RunEvent added in v0.10.0

type RunEvent struct {
	User     string
	App      string
	Command  Command
	URL      string
	Attached bool
	Message  string
	// contains filtered or unexported fields
}

RunEvent is triggered when a user starts a one off process.

func (RunEvent) Event added in v0.10.0

func (e RunEvent) Event() string

func (RunEvent) GetApp added in v0.10.1

func (e RunEvent) GetApp() *App

func (RunEvent) String added in v0.10.0

func (e RunEvent) String() string

type RunOpts added in v0.10.0

type RunOpts struct {
	// User performing this action.
	User *User

	// Related app.
	App *App

	// The command to run.
	Command Command

	// Commit message
	Message string

	// If provided, input will be read from this.
	Input io.Reader

	// If provided, output will be written to this.
	Output io.Writer

	// Extra environment variables to set.
	Env map[string]string

	// Optional memory/cpu/nproc constraints.
	Constraints *Constraints
}

RunOpts are options provided when running an attached/detached process.

func (RunOpts) Event added in v0.10.0

func (opts RunOpts) Event() RunEvent

func (RunOpts) Validate added in v0.10.1

func (opts RunOpts) Validate(e *Empire) error

type RunRecorder added in v0.10.1

type RunRecorder func() (io.Writer, error)

RunRecorder is a function that returns an io.Writer that will be written to to record Stdout and Stdin of interactive runs.

func RecordTo added in v0.10.1

func RecordTo(w io.Writer) RunRecorder

RecordTo returns a RunRecorder that writes the log record to the io.Writer

func RecordToCloudWatch added in v0.10.1

func RecordToCloudWatch(group string, config client.ConfigProvider) RunRecorder

RecordToCloudWatch returns a RunRecorder that writes the log record to CloudWatch Logs.

type ScaleEvent added in v0.10.0

type ScaleEvent struct {
	User                string
	App                 string
	Process             string
	Quantity            int
	PreviousQuantity    int
	Constraints         Constraints
	PreviousConstraints Constraints
	Message             string
	// contains filtered or unexported fields
}

ScaleEvent is triggered when a manual scaling event happens.

func (ScaleEvent) Event added in v0.10.0

func (e ScaleEvent) Event() string

func (ScaleEvent) GetApp added in v0.10.1

func (e ScaleEvent) GetApp() *App

func (ScaleEvent) String added in v0.10.0

func (e ScaleEvent) String() string

type ScaleOpts added in v0.10.0

type ScaleOpts struct {
	// User that's performing the action.
	User *User

	// The associated app.
	App *App

	// The process to scale.
	Process string

	// The desired quantity of processes.
	Quantity int

	// If provided, new memory and CPU constraints for the process.
	Constraints *Constraints

	// Commit message
	Message string
}

ScaleOpts are options provided when scaling a process.

func (ScaleOpts) Event added in v0.10.0

func (opts ScaleOpts) Event() ScaleEvent

func (ScaleOpts) Validate added in v0.10.1

func (opts ScaleOpts) Validate(e *Empire) error

type Scope

type Scope interface {
	Scope(*gorm.DB) *gorm.DB
}

Scope is an interface that scopes a gorm.DB. Scopes are used in ThingsFirst and ThingsAll methods on the store for filtering/querying.

func FieldEquals

func FieldEquals(field string, v interface{}) Scope

FieldEquals returns a Scope that filters on a field.

func ForApp

func ForApp(app *App) Scope

ForApp returns a Scope that will filter items belonging the the given app.

func ID

func ID(id string) Scope

ID returns a Scope that will find the item by id.

func Limit

func Limit(limit int) Scope

Limit returns a Scope that limits the results.

func Order

func Order(order string) Scope

Order returns a Scope that orders the results.

func Preload

func Preload(associations ...string) Scope

Preload returns a Scope that preloads the associations.

func Range

func Range(r headerutil.Range) Scope

Range returns a Scope that limits and orders the results.

type ScopeFunc

type ScopeFunc func(*gorm.DB) *gorm.DB

ScopeFunc implements the Scope interface for functions.

func (ScopeFunc) Scope

func (f ScopeFunc) Scope(db *gorm.DB) *gorm.DB

Scope implements the Scope interface.

type SetEvent added in v0.10.0

type SetEvent struct {
	User    string
	App     string
	Changed []string
	Message string
	// contains filtered or unexported fields
}

SetEvent is triggered when environment variables are changed on an application.

func (SetEvent) Event added in v0.10.0

func (e SetEvent) Event() string

func (SetEvent) GetApp added in v0.10.1

func (e SetEvent) GetApp() *App

func (SetEvent) String added in v0.10.0

func (e SetEvent) String() string

type SetOpts added in v0.10.0

type SetOpts struct {
	// User performing the action.
	User *User

	// The associated app.
	App *App

	// The new vars to merge into the old config.
	Vars Vars

	// Commit message
	Message string
}

SetOpts are options provided when setting new config vars on an app.

func (SetOpts) Event added in v0.10.0

func (opts SetOpts) Event() SetEvent

func (SetOpts) Validate added in v0.10.1

func (opts SetOpts) Validate(e *Empire) error

type Slug

type Slug struct {
	ID       string
	Image    image.Image
	Procfile []byte
}

Slug represents a container image with the extracted ProcessType.

func (*Slug) Formation added in v0.10.1

func (s *Slug) Formation() (Formation, error)

Formation returns a new Formation built from the extracted Procfile.

type Task added in v0.10.0

type Task struct {
	Name        string
	Type        string
	Command     Command
	State       string
	UpdatedAt   time.Time
	Constraints Constraints
}

Task represents a running process.

type User

type User struct {
	Name        string `json:"name"`
	GitHubToken string `json:"-"`
}

User represents a user of Empire.

func (*User) IsValid added in v0.10.1

func (u *User) IsValid() error

IsValid returns nil if the User is valid.

type ValidationError

type ValidationError struct {
	Err error
}

ValidationError is returned when a model is not valid.

func (*ValidationError) Error

func (e *ValidationError) Error() string

type Variable

type Variable string

Variable represents the name of an environment variable.

type Vars

type Vars map[Variable]*string

Vars represents a variable -> value mapping.

func (*Vars) Scan

func (v *Vars) Scan(src interface{}) error

Scan implements the sql.Scanner interface.

func (Vars) Value

func (v Vars) Value() (driver.Value, error)

Value implements the driver.Value interface.

Directories

Path Synopsis
cmd
emp
events
app
Package app provides an empire.EventStream implementation that publishs events to the app's kinesis stream if available.
Package app provides an empire.EventStream implementation that publishs events to the app's kinesis stream if available.
sns
Package sns provides an empire.EventStream implementation that publishes events to SNS.
Package sns provides an empire.EventStream implementation that publishes events to SNS.
stdout
Package stdout provides an empire.EventStream implementation that publishes events to stdout.
Package stdout provides an empire.EventStream implementation that publishes events to stdout.
pkg
arn
package arn is a Go package for parsing Amazon Resource Names.
package arn is a Go package for parsing Amazon Resource Names.
bytesize
package bytesize contains constants for easily switching between different byte sizes.
package bytesize contains constants for easily switching between different byte sizes.
constraints
package constraints contains methods for decoding a compact CPU and Memory constraints format.
package constraints contains methods for decoding a compact CPU and Memory constraints format.
ecsutil
Package ecsutil is a layer on top of Amazon ECS to provide an app aware ECS client.
Package ecsutil is a layer on top of Amazon ECS to provide an app aware ECS client.
heroku
Package heroku is a client interface to the Heroku API.
Package heroku is a client interface to the Heroku API.
image
Package image contains methods and helpers for parsing the docker image format.
Package image contains methods and helpers for parsing the docker image format.
runner
package runner provides a simple interface for running docker containers.
package runner provides a simple interface for running docker containers.
stream
Package stream provides types that make it easier to perform streaming.
Package stream provides types that make it easier to perform streaming.
stream/http
Package http provides streaming implementations of various net/http types.
Package http provides streaming implementations of various net/http types.
Package scheduler provides the core interface that Empire uses when interacting with a cluster of machines to run tasks.
Package scheduler provides the core interface that Empire uses when interacting with a cluster of machines to run tasks.
cloudformation
Package cloudformation implements the Scheduler interface for ECS by using CloudFormation to provision and update resources.
Package cloudformation implements the Scheduler interface for ECS by using CloudFormation to provision and update resources.
docker
Package docker implements the Scheduler interface backed by the Docker API.
Package docker implements the Scheduler interface backed by the Docker API.
ecs
Pacakge ecs provides an implementation of the Scheduler interface that uses Amazon EC2 Container Service.
Pacakge ecs provides an implementation of the Scheduler interface that uses Amazon EC2 Container Service.
ecs/lb
package lb provides an abstraction around creating load balancers.
package lb provides an abstraction around creating load balancers.
kubernetes
Package kubernetes implements the Scheduler interface backed by Kubernetes.
Package kubernetes implements the Scheduler interface backed by Kubernetes.
auth
Package auth contains types for authenticating and authorizing requests.
Package auth contains types for authenticating and authorizing requests.
auth/github
Package github provides auth.Authentication and auth.Authorizer implementations backed by GitHub users, orgs and teams.
Package github provides auth.Authentication and auth.Authorizer implementations backed by GitHub users, orgs and teams.

Jump to

Keyboard shortcuts

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