Beispiel #1
0
func TestFetchAdminAccounts(t *testing.T) {
	db := modeltesthelper.NewMongoDB(t)
	defer db.Close()

	acc1 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc1.Id)

	acc2 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc2.Id)

	group, err := createGroup()
	if err != nil {
		t.Error(err)
	}

	accounts, err := modelhelper.FetchAdminAccounts(group.Slug)
	if err != nil {
		t.Error(err)
	}

	if len(accounts) != 0 {
		t.Errorf("accounts count should be 0, got: %d", len(accounts))
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc1.Id,
		TargetName: "JAccount",
		SourceId:   group.Id,
		SourceName: "JGroup",
		As:         "admin",
	}); err != nil {
		t.Error(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc2.Id,
		TargetName: "JAccount",
		SourceId:   group.Id,
		SourceName: "JGroup",
		As:         "admin",
	}); err != nil {
		t.Error(err)
	}

	accounts, err = modelhelper.FetchAdminAccounts(group.Slug)
	if err != nil {
		t.Error(err)
	}

	if len(accounts) != 2 {
		t.Errorf("accounts count should be 2, got: %d", len(accounts))
	}
}
Beispiel #2
0
func TestUserLoginSessionCreation(t *testing.T) {
	db := modeltesthelper.NewMongoDB(t)
	defer db.Close()

	acc2 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc2.Id)

	group, err := createGroup()
	if err != nil {
		t.Error(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc2.Id,
		TargetName: "JAccount",
		SourceId:   group.Id,
		SourceName: "JGroup",
		As:         "member",
	}); err != nil {
		t.Error(err)
	}

	ses, err := modelhelper.UserLogin(acc2.Profile.Nickname, group.Slug)
	if err != nil {
		t.Errorf("expected nil error, but got %q!", err)
	}

	if ses == nil || ses.ClientId == "" {
		t.Error("expected ses.ClientId to be set, but got empty!")
	}
}
Beispiel #3
0
func (m *Migrate) Action(args []string) error {
	if err := m.Valid(); err != nil {
		return err
	}

	c, err := kloudClient()
	if err != nil {
		return err
	}
	defer c.Close()

	modelhelper.Initialize(*m.MongoURL)
	defer modelhelper.Close()

	account, err := modelhelper.GetAccount(*m.User)
	if err != nil {
		return err
	}

	if *m.Credential == "" {
		*m.Credential = bson.NewObjectId().Hex()

		cred := &models.Credential{
			Id:         bson.NewObjectId(),
			Provider:   "aws",
			Identifier: *m.Credential,
			OriginId:   account.Id,
		}

		credData := &models.CredentialData{
			Id:         bson.NewObjectId(),
			Identifier: *m.Credential,
			OriginId:   account.Id,
			Meta: bson.M{
				"access_key": *m.Key,
				"secret_key": *m.Secret,
				"region":     *m.Region,
			},
		}

		if err := modelhelper.InsertCredential(cred, credData); err != nil {
			return err
		}

		credRelationship := &models.Relationship{
			Id:         bson.NewObjectId(),
			TargetId:   cred.Id,
			TargetName: "JCredential",
			SourceId:   account.Id,
			SourceName: "JAccount",
			As:         "owner",
		}

		if err := modelhelper.AddRelationship(credRelationship); err != nil {
			return err
		}
	}

	req := &MigrateRequest{
		Provider:    "aws",
		Machines:    m.Machines,
		Identifier:  *m.Credential,
		GroupName:   *m.Team,
		StackName:   "Migrated Stack",
		Impersonate: *m.User,
	}

	_, err = c.Tell("migrate", req)

	return err
}
Beispiel #4
0
func TestUserLogin(t *testing.T) {
	db := modeltesthelper.NewMongoDB(t)
	defer db.Close()

	acc1 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc1.Id)

	acc2 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc2.Id)

	group, err := createGroup()
	if err != nil {
		t.Error(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc1.Id,
		TargetName: "JAccount",
		SourceId:   group.Id,
		SourceName: "JGroup",
		As:         "member",
	}); err != nil {
		t.Error(err)
	}

	ses, err := modelhelper.CreateSessionForAccount(acc1.Profile.Nickname, group.Slug)
	if err != nil {
		t.Error(err)
	}

	tests := []struct {
		Title    string
		Nick     string
		Slug     string
		ClientID string
		Err      error
	}{
		{
			Title:    "Member account",
			Nick:     acc1.Profile.Nickname,
			Slug:     group.Slug,
			ClientID: ses.ClientId,
			Err:      nil,
		},
		{
			Title:    "Re-testing with Member account",
			Nick:     acc1.Profile.Nickname,
			Slug:     group.Slug,
			ClientID: ses.ClientId,
			Err:      nil,
		},
		{
			Title:    "Non-member account",
			Nick:     acc2.Profile.Nickname,
			Slug:     group.Slug,
			ClientID: "",
			Err:      modelhelper.ErrNotParticipant,
		},
	}

	for _, test := range tests {
		t.Run(test.Title, func(t *testing.T) {
			ses, err := modelhelper.UserLogin(test.Nick, test.Slug)
			if err != test.Err {
				t.Errorf("expected Err equal to %q, but got %q!", test.Err, err)
			}

			if ses != nil && ses.ClientId != test.ClientID {
				t.Errorf("expected ClientID equal to %q, but got %q!", test.ClientID, ses.ClientId)
			}
		})
	}
}
Beispiel #5
0
func TestFetchAccountGroups(t *testing.T) {
	db := modeltesthelper.NewMongoDB(t)
	defer db.Close()

	acc1 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc1.Id)

	groups, err := modelhelper.FetchAccountGroups(acc1.Profile.Nickname)
	if err != mgo.ErrNotFound {
		t.Fatalf("want err = %v; got %v", mgo.ErrNotFound, err)
	}

	if len(groups) != 0 {
		t.Fatalf("expected len(groups) to be 0, got groups: %+v", groups)
	}

	group1, err := createGroup()
	if err != nil {
		t.Fatal(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc1.Id,
		TargetName: "JAccount",
		SourceId:   group1.Id,
		SourceName: "JGroup",
		As:         "member",
	}); err != nil {
		t.Error(err)
	}

	groups, err = modelhelper.FetchAccountGroups(acc1.Profile.Nickname)
	if err != nil {
		t.Fatal(err)
	}

	if len(groups) != 1 {
		t.Fatalf("expected len(groups) to be 1, got groups: %+v", groups)
	}

	// test having 2 relationsips in one group
	group2, err := createGroup()
	if err != nil {
		t.Error(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc1.Id,
		TargetName: "JAccount",
		SourceId:   group2.Id,
		SourceName: "JGroup",
		As:         "admin",
	}); err != nil {
		t.Error(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc1.Id,
		TargetName: "JAccount",
		SourceId:   group2.Id,
		SourceName: "JGroup",
		As:         "member",
	}); err != nil {
		t.Fatal(err)
	}

	groups, err = modelhelper.FetchAccountGroups(acc1.Profile.Nickname)
	if err != nil {
		t.Fatal(err)
	}

	if len(groups) != 2 {
		t.Fatalf("expected len(groups) to be 2, got groups: %+v", groups)
	}
}
Beispiel #6
0
func TestHasRole(t *testing.T) {
	db := modeltesthelper.NewMongoDB(t)
	defer db.Close()

	acc1 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc1.Id)

	acc2 := createTestAccount(t)
	defer modelhelper.RemoveAccount(acc2.Id)

	group, err := createGroup()
	if err != nil {
		t.Error(err)
	}

	if err := modelhelper.AddRelationship(&models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   acc1.Id,
		TargetName: "JAccount",
		SourceId:   group.Id,
		SourceName: "JGroup",
		As:         "member",
	}); err != nil {
		t.Error(err)
	}

	tests := []struct {
		Title string
		Nick  string
		Slug  string
		Roles []string
		Has   bool
	}{
		{
			Title: "Member account",
			Nick:  acc1.Profile.Nickname,
			Slug:  group.Slug,
			Roles: []string{"member"},
			Has:   true,
		},
		{
			Title: "Member account with multi role",
			Nick:  acc1.Profile.Nickname,
			Slug:  group.Slug,
			Roles: []string{"member", "admin"},
			Has:   true,
		},
		{
			Title: "Member account with default roles",
			Nick:  acc1.Profile.Nickname,
			Slug:  group.Slug,
			Roles: modelhelper.DefaultRoles,
			Has:   true,
		},
		{
			Title: "Non-member account",
			Nick:  acc2.Profile.Nickname,
			Slug:  group.Slug,
			Roles: []string{"member"},
			Has:   false,
		},
		{
			Title: "Invalid role correct account",
			Nick:  acc1.Profile.Nickname,
			Slug:  group.Slug,
			Roles: []string{"admin"},
			Has:   false,
		},
		{
			Title: "Invalid role in-correct account",
			Nick:  acc2.Profile.Nickname,
			Slug:  group.Slug,
			Roles: []string{"admin"},
			Has:   false,
		},
	}

	for _, test := range tests {
		has, err := modelhelper.HasAnyRole(test.Nick, test.Slug, test.Roles...)
		if err != nil {
			t.Error(err)
		}
		if has != test.Has {
			t.Errorf("expected %q's \"has\" equal to %t, but it wasnt!", test.Title, test.Has)
		}
	}
}
Beispiel #7
0
func (db *mongoDatabase) SetCred(c *Cred) error {
	f, ok := c.Perm.(*Filter)
	if !ok {
		return errors.New("invalid credential permission")
	}

	perm, err := db.Validate(f, c)
	if err == nil {
		c.Perm = perm
		return nil
	}

	if !models.IsNotFound(err, "jCredential") {
		return err
	}

	mPerm, ok := perm.(*MongoPerm)
	if !ok {
		return fmt.Errorf("unable to create credential: %s", err)
	}

	if mPerm.AccModel == nil {
		return fmt.Errorf("unable to create credential: missing %q account", f.Username)
	}

	now := time.Now().UTC()

	if c.Title == "" {
		c.Title = mPerm.UserModel.Name + " " + now.String()
	}

	mPerm.CredModel = &models.Credential{
		Id:          bson.NewObjectId(),
		Provider:    c.Provider,
		Identifier:  c.Ident,
		Title:       c.Title,
		OriginId:    mPerm.AccModel.Id,
		Verified:    false,
		AccessLevel: "private",
		Meta: &models.CredentialMeta{
			CreatedAt:  now,
			ModifiedAt: now,
		},
	}

	db.Log.Debug("creating credential: %#v", mPerm.CredModel)

	if err := modelhelper.CreateCredential(mPerm.CredModel); err != nil {
		return err
	}

	rel := &models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   mPerm.CredModel.Id,
		TargetName: "JCredential",
		SourceId:   mPerm.AccModel.Id,
		SourceName: "JAccount",
		As:         "owner",
		TimeStamp:  now,
	}

	if err := modelhelper.AddRelationship(rel); err != nil {
		return err
	}

	c.Perm = mPerm

	return nil
}
Beispiel #8
0
func CreateUser(opts *UserOptions) (*User, error) {
	username := opts.Username
	groupname := opts.Groupname
	provider := opts.Provider
	template := opts.Template

	privateKey, publicKey, err := sshutil.TemporaryKey()
	if err != nil {
		return nil, err
	}

	labels, err := machineLabels([]byte(template))
	if err != nil {
		return nil, err
	}

	relationExists := true

	// jAccounts
	account, err := modelhelper.GetAccount(username)
	if err == mgo.ErrNotFound {
		relationExists = false

		account = &models.Account{
			Id: bson.NewObjectId(),
			Profile: models.AccountProfile{
				Nickname: username,
			},
		}

		err = modelhelper.CreateAccount(account)
	}
	if err != nil {
		return nil, errors.New("failure looking up jAccounts: " + err.Error())
	}

	// jGroups
	group, err := modelhelper.GetGroup(groupname)
	if err == mgo.ErrNotFound {
		relationExists = false

		group = &models.Group{
			Id:    bson.NewObjectId(),
			Title: groupname,
			Slug:  groupname,
		}

		err = modelhelper.CreateGroup(group)
	}
	if err != nil {
		return nil, errors.New("failure looking up jGroups: " + err.Error())
	}

	if !relationExists {
		// add relation between use and group
		relationship := &models.Relationship{
			Id:         bson.NewObjectId(),
			TargetId:   account.Id,
			TargetName: "JAccount",
			SourceId:   group.Id,
			SourceName: "JGroup",
			As:         "member",
		}

		err := modelhelper.AddRelationship(relationship)
		if err != nil {
			return nil, errors.New("failure insering relationship: " + err.Error())
		}
	}

	// jUsers
	user, err := modelhelper.GetUser(username)
	if err == nil && len(user.SshKeys) != 0 {
		publicKey = user.SshKeys[0].Key
	}
	if err == mgo.ErrNotFound {
		user = &models.User{
			ObjectId:      bson.NewObjectId(),
			Email:         username + "@" + username + ".com",
			LastLoginDate: time.Now().UTC(),
			RegisteredAt:  time.Now().UTC(),
			Name:          username, // bson equivelant is username
			Password:      "******",
			Status:        "confirmed",
			SshKeys: []struct {
				Title string `bson:"title"`
				Key   string `bson:"key"`
			}{
				{Key: publicKey},
			},
		}

		err = modelhelper.CreateUser(user)
	}
	if err != nil {
		return nil, errors.New("failure looking up jUsers: " + err.Error())
	}

	queryString := protocol.Kite{ID: opts.KlientID}.String()

	cred := &models.Credential{
		Id:         bson.NewObjectId(),
		Provider:   opts.Provider,
		Identifier: bson.NewObjectId().Hex(),
		OriginId:   account.Id,
	}

	credData := &models.CredentialData{
		Id:         bson.NewObjectId(),
		Identifier: cred.Identifier,
		OriginId:   account.Id,
		Meta: bson.M{
			"queryString": queryString,
			"memory":      0,
			"cpu":         0,
			"box":         "",
		},
	}

	if err := modelhelper.InsertCredential(cred, credData); err != nil {
		return nil, err
	}

	relationship := &models.Relationship{
		Id:         bson.NewObjectId(),
		TargetId:   cred.Id,
		TargetName: "JCredential",
		SourceId:   account.Id,
		SourceName: "JAccount",
		As:         "owner",
	}

	if err := modelhelper.AddRelationship(relationship); err != nil {
		return nil, err
	}

	// jComputeStack and jStackTemplates
	stackTemplateId := bson.NewObjectId()
	stackTemplate := &models.StackTemplate{
		Id: stackTemplateId,
		Credentials: map[string][]string{
			"vagrant": {cred.Identifier},
		},
	}
	stackTemplate.Template.Content = template

	if err := modelhelper.CreateStackTemplate(stackTemplate); err != nil {
		return nil, err
	}

	// later we can add more users with "Owner:false" to test sharing capabilities
	users := []models.MachineUser{
		{Id: user.ObjectId, Sudo: true, Owner: true},
	}

	machineIds := make([]bson.ObjectId, len(labels))

	for i, label := range labels {
		machineId := bson.NewObjectId()
		machine := &models.Machine{
			ObjectId:   machineId,
			Label:      label,
			Domain:     username + ".dev.koding.io",
			Provider:   provider,
			CreatedAt:  time.Now().UTC(),
			Users:      users,
			Meta:       make(bson.M, 0),
			Groups:     make([]models.MachineGroup, 0),
			Credential: username,
		}

		machine.Assignee.InProgress = false
		machine.Assignee.AssignedAt = time.Now().UTC()
		machine.Status.State = machinestate.NotInitialized.String()
		machine.Status.ModifiedAt = time.Now().UTC()

		machineIds[i] = machine.ObjectId

		if err := modelhelper.CreateMachine(machine); err != nil {
			return nil, err
		}
	}

	computeStackID := bson.NewObjectId()
	computeStack := &models.ComputeStack{
		Id:          computeStackID,
		BaseStackId: stackTemplateId,
		Machines:    machineIds,
	}

	if err := modelhelper.CreateComputeStack(computeStack); err != nil {
		return nil, err
	}

	return &User{
		MachineIDs:      machineIds,
		MachineLabels:   labels,
		StackID:         computeStackID.Hex(),
		StackTemplateID: stackTemplate.Id.Hex(),
		AccountID:       account.Id,
		CredID:          cred.Id.Hex(),
		CredDataID:      credData.Id.Hex(),
		PrivateKey:      privateKey,
		PublicKey:       publicKey,
		Identifiers:     []string{cred.Identifier},
	}, nil
}