Example #1
0
File: auth.go Project: nedmax/tsuru
func addUserToTeam(email, teamName string, u *auth.User) error {
	conn, err := db.Conn()
	if err != nil {
		return err
	}
	defer conn.Close()
	team, user := new(auth.Team), new(auth.User)
	selector := bson.M{"_id": teamName}
	if err := conn.Teams().Find(selector).One(team); err != nil {
		return &errors.Http{Code: http.StatusNotFound, Message: "Team not found"}
	}
	if !team.ContainsUser(u) {
		msg := fmt.Sprintf("You are not authorized to add new users to the team %s", team.Name)
		return &errors.Http{Code: http.StatusUnauthorized, Message: msg}
	}
	if err := conn.Users().Find(bson.M{"email": email}).One(user); err != nil {
		return &errors.Http{Code: http.StatusNotFound, Message: "User not found"}
	}
	actions := []*action.Action{
		&addUserToTeamInGandalfAction,
		&addUserToTeamInDatabaseAction,
	}
	pipeline := action.NewPipeline(actions...)
	return pipeline.Execute(user.Email, u, team)
}
Example #2
0
File: app.go Project: nemx/tsuru
// CreateApp creates a new app.
//
// Creating a new app is a process composed of four steps:
//
//       1. Save the app in the database
//       2. Create IAM credentials for the app
//       3. Create S3 bucket for the app (if the bucket support is enabled)
//       4. Create the git repository using gandalf
//       5. Provision units within the provisioner
func CreateApp(app *App, user *auth.User) error {
	teams, err := user.Teams()
	if err != nil {
		return err
	}
	if len(teams) == 0 {
		return NoTeamsError{}
	}
	if _, err := getPlatform(app.Platform); err != nil {
		return err
	}
	app.SetTeams(teams)
	app.Owner = user.Email
	if !app.isValid() {
		msg := "Invalid app name, your app should have at most 63 " +
			"characters, containing only lower case letters, numbers or dashes, " +
			"starting with a letter."
		return &errors.ValidationError{Message: msg}
	}
	actions := []*action.Action{&reserveUserApp, &createAppQuota, &insertApp}
	useS3, _ := config.GetBool("bucket-support")
	if useS3 {
		actions = append(actions, &createIAMUserAction,
			&createIAMAccessKeyAction,
			&createBucketAction, &createUserPolicyAction)
	}
	actions = append(actions, &exportEnvironmentsAction,
		&createRepository, &provisionApp)
	pipeline := action.NewPipeline(actions...)
	err = pipeline.Execute(app, user)
	if err != nil {
		return &AppCreationError{app: app.Name, Err: err}
	}
	return nil
}
Example #3
0
// CreateApp creates a new app.
//
// Creating a new app is a process composed of four steps:
//
//       1. Save the app in the database
//       2. Create IAM credentials for the app
//       3. Create S3 bucket for the app (if the bucket support is enabled)
//       4. Create the git repository using gandalf
//       5. Provision units within the provisioner
func CreateApp(app *App, units uint, teams []auth.Team) error {
	if units == 0 {
		return &errors.ValidationError{Message: "Cannot create app with 0 units."}
	}
	if len(teams) == 0 {
		return NoTeamsError{}
	}
	app.SetTeams(teams)
	if !app.isValid() {
		msg := "Invalid app name, your app should have at most 63 " +
			"characters, containing only lower case letters or numbers, " +
			"starting with a letter."
		return &errors.ValidationError{Message: msg}
	}
	actions := []*action.Action{&insertApp}
	useS3, _ := config.GetBool("bucket-support")
	if useS3 {
		actions = append(actions, &createIAMUserAction,
			&createIAMAccessKeyAction,
			&createBucketAction, &createUserPolicyAction)
	}
	actions = append(actions, &exportEnvironmentsAction,
		&createRepository, &provisionApp, &provisionAddUnits)
	pipeline := action.NewPipeline(actions...)
	err := pipeline.Execute(app, units)
	if err != nil {
		return &appCreationError{app: app.Name, err: err}
	}
	return nil
}
Example #4
0
func CreateServiceInstance(name string, service *Service, plan *Plan, user *auth.User) error {
	err := validateServiceInstanceName(name)
	if err != nil {
		return err
	}
	instance := ServiceInstance{
		Name:        name,
		ServiceName: service.Name,
	}
	if plan != nil {
		instance.PlanName = plan.Name
	}
	teams, err := user.Teams()
	if err != nil {
		return err
	}
	instance.Teams = make([]string, 0, len(teams))
	for _, team := range teams {
		if service.HasTeam(&team) || !service.IsRestricted {
			instance.Teams = append(instance.Teams, team.Name)
		}
	}
	actions := []*action.Action{&createServiceInstance, &insertServiceInstance}
	pipeline := action.NewPipeline(actions...)
	return pipeline.Execute(*service, instance)
}
Example #5
0
func addUserToTeam(w http.ResponseWriter, r *http.Request, t *auth.Token) error {
	teamName := r.URL.Query().Get(":team")
	email := r.URL.Query().Get(":user")
	u, err := t.User()
	if err != nil {
		return err
	}
	rec.Log(u.Email, "add-user-to-team", "team="+teamName, "user="******"Team not found"}
	}
	if !team.ContainsUser(u) {
		msg := fmt.Sprintf("You are not authorized to add new users to the team %s", team.Name)
		return &errors.HTTP{Code: http.StatusUnauthorized, Message: msg}
	}
	user, err := auth.GetUserByEmail(email)
	if err != nil {
		return &errors.HTTP{Code: http.StatusNotFound, Message: "User not found"}
	}
	actions := []*action.Action{
		&addUserToTeamInGandalfAction,
		&addUserToTeamInDatabaseAction,
	}
	pipeline := action.NewPipeline(actions...)
	return pipeline.Execute(user.Email, u, team)
}
Example #6
0
func deploy(app provision.App, version string, w io.Writer) (string, error) {
	commands, err := deployCmds(app, version)
	if err != nil {
		return "", err
	}
	imageId := getImage(app)
	actions := []*action.Action{&createContainer, &startContainer, &insertContainer}
	pipeline := action.NewPipeline(actions...)
	err = pipeline.Execute(app, imageId, commands)
	if err != nil {
		log.Errorf("error on execute deploy pipeline for app %s - %s", app.GetName(), err)
		return "", err
	}
	c := pipeline.Result().(container)
	err = c.logs(w)
	if err != nil {
		log.Errorf("error on get logs for container %s - %s", c.ID, err)
		return "", err
	}
	_, err = dockerCluster().WaitContainer(c.ID)
	if err != nil {
		log.Errorf("Process failed for container %q: %s", c.ID, err)
		return "", err
	}
	imageId, err = c.commit()
	if err != nil {
		log.Errorf("error on commit container %s - %s", c.ID, err)
		return "", err
	}
	c.remove()
	return imageId, nil
}
Example #7
0
// BindApp makes the bind between the service instance and an app.
func (si *ServiceInstance) BindApp(app bind.App) error {
	actions := []*action.Action{
		&addAppToServiceInstance,
		&setEnvironVariablesToApp,
	}
	pipeline := action.NewPipeline(actions...)
	return pipeline.Execute(app, *si)
}
Example #8
0
File: app.go Project: nemx/tsuru
// DeployApp calls the Provisioner.Deploy
func DeployApp(app *App, version string, writer io.Writer) error {
	pipeline := Provisioner.DeployPipeline()
	if pipeline == nil {
		actions := []*action.Action{&ProvisionerDeploy, &IncrementDeploy}
		pipeline = action.NewPipeline(actions...)
	}
	logWriter := LogWriter{App: app, Writer: writer}
	return pipeline.Execute(app, version, &logWriter)
}
Example #9
0
File: app.go Project: nemx/tsuru
// AddUnits creates n new units within the provisioner, saves new units in the
// database and enqueues the apprc serialization.
func (app *App) AddUnits(n uint) error {
	if n == 0 {
		return stderr.New("Cannot add zero units.")
	}
	return action.NewPipeline(
		&reserveUnitsToAdd,
		&provisionAddUnits,
		&saveNewUnitsInDatabase,
	).Execute(app, n)
}
Example #10
0
func (p *dockerProvisioner) DeployPipeline() *action.Pipeline {
	actions := []*action.Action{
		&app.ProvisionerDeploy,
		&app.IncrementDeploy,
		&saveUnits,
		&injectEnvirons,
		&bindService,
	}
	pipeline := action.NewPipeline(actions...)
	return pipeline
}
Example #11
0
// CreateApp creates a new app.
//
// Creating a new app is a process composed of four steps:
//
//       1. Save the app in the database
//       2. Create IAM credentials for the app
//       3. Create S3 bucket for the app (if the bucket support is enabled)
//       4. Create the git repository using gandalf
//       5. Provision units within the provisioner
func CreateApp(app *App, user *auth.User) error {
	teams, err := user.Teams()
	if err != nil {
		return err
	}
	if len(teams) == 0 {
		return NoTeamsError{}
	}
	if _, err := getPlatform(app.Platform); err != nil {
		return err
	}
	// app.Memory is empty, no custom memory passed from CLI
	if app.Memory < 1 {
		// get default memory limit from tsuru config
		configMemory, err := config.GetInt("docker:memory")
		if err != nil {
			// no default memory set in config (or error when reading), set it as unlimited (0)
			app.Memory = 0
		} else {
			// default memory set in config, use that.
			app.Memory = configMemory
		}
	}
	if err := app.setTeamOwner(teams); err != nil {
		return err
	}
	app.SetTeams(teams)
	app.Owner = user.Email
	if !app.isValid() {
		msg := "Invalid app name, your app should have at most 63 " +
			"characters, containing only lower case letters, numbers or dashes, " +
			"starting with a letter."
		return &errors.ValidationError{Message: msg}
	}
	actions := []*action.Action{&reserveUserApp, &insertApp}
	useS3, _ := config.GetBool("bucket-support")
	if useS3 {
		actions = append(actions, &createIAMUserAction,
			&createIAMAccessKeyAction,
			&createBucketAction, &createUserPolicyAction)
	}
	actions = append(actions, &exportEnvironmentsAction,
		&createRepository, &provisionApp)
	pipeline := action.NewPipeline(actions...)
	err = pipeline.Execute(app, user)
	if err != nil {
		return &AppCreationError{app: app.Name, Err: err}
	}
	return nil
}
Example #12
0
File: app.go Project: janqii/tsuru
// DeployApp calls the Provisioner.Deploy
func DeployApp(app *App, version, commit string, writer io.Writer) error {
	start := time.Now()
	pipeline := Provisioner.DeployPipeline()
	if pipeline == nil {
		actions := []*action.Action{&ProvisionerDeploy, &IncrementDeploy}
		pipeline = action.NewPipeline(actions...)
	}
	logWriter := LogWriter{App: app, Writer: writer}
	err := pipeline.Execute(app, version, &logWriter)
	if err != nil {
		return err
	}
	elapsed := time.Since(start)
	return saveDeployData(app.Name, commit, elapsed)
}
Example #13
0
File: auth.go Project: nedmax/tsuru
// addKeyToUser adds a key to a user in mongodb and send the key to the git server
// in order to allow ssh-ing into git server.
func addKeyToUser(content string, u *auth.User) error {
	key := auth.Key{Content: content}
	if u.HasKey(key) {
		return &errors.Http{Code: http.StatusConflict, Message: "User already has this key"}
	}
	actions := []*action.Action{
		&addKeyInGandalfAction,
		&addKeyInDatabaseAction,
	}
	pipeline := action.NewPipeline(actions...)
	err := pipeline.Execute(&key, u)
	if err != nil {
		return err
	}
	return nil
}
Example #14
0
func (p *FakeProvisioner) DeployPipeline() *action.Pipeline {
	if p.CustomPipeline {
		act := action.Action{
			Name: "change-executed-pipeline",
			Forward: func(ctx action.FWContext) (action.Result, error) {
				p.executedPipeline = true
				return nil, nil
			},
			Backward: func(ctx action.BWContext) {
			},
		}
		actions := []*action.Action{&act}
		pipeline := action.NewPipeline(actions...)
		return pipeline
	}
	return nil
}
Example #15
0
// AddKeyToUser adds a key to a user.
//
// This function is just an http wrapper around addKeyToUser. The latter function
// exists to be used in other places in the package without the http stuff (request and
// response).
func addKeyToUser(w http.ResponseWriter, r *http.Request, t *auth.Token) error {
	content, err := getKeyFromBody(r.Body)
	if err != nil {
		return err
	}
	u, err := t.User()
	if err != nil {
		return err
	}
	rec.Log(u.Email, "add-key", content)
	key := auth.Key{Content: content}
	if u.HasKey(key) {
		return &errors.HTTP{Code: http.StatusConflict, Message: "User already has this key"}
	}
	actions := []*action.Action{
		&addKeyInGandalfAction,
		&addKeyInDatabaseAction,
	}
	pipeline := action.NewPipeline(actions...)
	return pipeline.Execute(&key, u)
}
Example #16
0
func deploy(app provision.App, version string, w io.Writer) (string, error) {
	commands, err := deployCmds(app, version)
	if err != nil {
		return "", err
	}
	imageId := getImage(app)
	actions := []*action.Action{&createContainer, &startContainer, &insertContainer}
	pipeline := action.NewPipeline(actions...)
	err = pipeline.Execute(app, imageId, commands)
	if err != nil {
		log.Printf("error on execute deploy pipeline for app %s - %s", app.GetName(), err.Error())
		return "", err
	}
	c := pipeline.Result().(container)
	for {
		result, err := c.stopped()
		if err != nil {
			log.Printf("error on stopped for container %s - %s", c.ID, err.Error())
			return "", err
		}
		if result {
			break
		}
	}
	err = c.logs(w)
	if err != nil {
		log.Printf("error on get logs for container %s - %s", c.ID, err.Error())
		return "", err
	}
	imageId, err = c.commit()
	if err != nil {
		log.Printf("error on commit container %s - %s", c.ID, err.Error())
		return "", err
	}
	c.remove()
	// if err != nil {
	// 	return "", err
	// }
	return imageId, nil
}
Example #17
0
func start(app provision.App, imageId string, w io.Writer) (*container, error) {
	commands, err := runCmds()
	if err != nil {
		return nil, err
	}
	actions := []*action.Action{&createContainer, &startContainer, &setNetworkInfo, &insertContainer, &addRoute}
	pipeline := action.NewPipeline(actions...)
	err = pipeline.Execute(app, imageId, commands)
	if err != nil {
		return nil, err
	}
	c := pipeline.Result().(container)
	err = c.setImage(imageId)
	if err != nil {
		return nil, err
	}
	err = c.setStatus("running")
	if err != nil {
		return nil, err
	}
	return &c, nil
}