From 0ec21a4ed61da5b0f883eaba34a14f915c16a468 Mon Sep 17 00:00:00 2001 From: J Guerreiro Date: Fri, 18 Feb 2022 12:08:00 +0000 Subject: [PATCH] Service accounts: make is_service_account nullable (#45541) * add base nullable migration to is_service_account Co-authored-by: Jeremy Price * fix postgres migration * ServiceAccounts: ensure SA is set to false when creating a user Co-authored-by: Jeremy Price --- pkg/services/sqlstore/migrations/user_mig.go | 14 +++++++++++ pkg/services/sqlstore/org_test.go | 1 + pkg/services/sqlstore/user.go | 26 +++++++++++--------- 3 files changed, 29 insertions(+), 12 deletions(-) diff --git a/pkg/services/sqlstore/migrations/user_mig.go b/pkg/services/sqlstore/migrations/user_mig.go index 0dfd3063f48..6c33849621c 100644 --- a/pkg/services/sqlstore/migrations/user_mig.go +++ b/pkg/services/sqlstore/migrations/user_mig.go @@ -127,11 +127,25 @@ func addUserMigrations(mg *Migrator) { Cols: []string{"login", "email"}, })) + //Service accounts are lightweight users with restricted permissions. They support API keys + //and provisioning and tasks like alarms and reports. + // Issues in this migration: is_service_account should be nullable mg.AddMigration("Add is_service_account column to user", NewAddColumnMigration(userV2, &Column{ Name: "is_service_account", Type: DB_Bool, Nullable: false, Default: "0", })) + + mg.AddMigration("Update is_service_account column to nullable", + NewRawSQLMigration(""). + SQLite(migSQLITEisServiceAccountNullable). + Postgres("ALTER TABLE `user` ALTER COLUMN is_service_account DROP NOT NULL;"). + Mysql("ALTER TABLE user MODIFY is_service_account BOOLEAN DEFAULT 0;")) } +const migSQLITEisServiceAccountNullable = `ALTER TABLE user ADD COLUMN tmp_service_account BOOLEAN DEFAULT 0; +UPDATE user SET tmp_service_account = is_service_account; +ALTER TABLE user DROP COLUMN is_service_account; +ALTER TABLE user RENAME COLUMN tmp_service_account TO is_service_account;` + type AddMissingUserSaltAndRandsMigration struct { MigrationBase } diff --git a/pkg/services/sqlstore/org_test.go b/pkg/services/sqlstore/org_test.go index 10b46601ecb..6565e1eefc2 100644 --- a/pkg/services/sqlstore/org_test.go +++ b/pkg/services/sqlstore/org_test.go @@ -167,6 +167,7 @@ func TestAccountDataAccess(t *testing.T) { err := SearchUsers(context.Background(), &query) require.NoError(t, err) + require.Len(t, query.Result.Users, 2) require.Equal(t, query.Result.Users[0].Email, "ac1@test.com") require.Equal(t, query.Result.Users[1].Email, "ac2@test.com") }) diff --git a/pkg/services/sqlstore/user.go b/pkg/services/sqlstore/user.go index 67a08cdcb02..47da1eafb4a 100644 --- a/pkg/services/sqlstore/user.go +++ b/pkg/services/sqlstore/user.go @@ -113,17 +113,18 @@ func (ss *SQLStore) createUser(ctx context.Context, sess *DBSession, args userCr // create user user = models.User{ - Email: args.Email, - Name: args.Name, - Login: args.Login, - Company: args.Company, - IsAdmin: args.IsAdmin, - IsDisabled: args.IsDisabled, - OrgId: orgID, - EmailVerified: args.EmailVerified, - Created: time.Now(), - Updated: time.Now(), - LastSeenAt: time.Now().AddDate(-10, 0, 0), + Email: args.Email, + Name: args.Name, + Login: args.Login, + Company: args.Company, + IsAdmin: args.IsAdmin, + IsDisabled: args.IsDisabled, + OrgId: orgID, + EmailVerified: args.EmailVerified, + Created: time.Now(), + Updated: time.Now(), + LastSeenAt: time.Now().AddDate(-10, 0, 0), + IsServiceAccount: false, } salt, err := util.GetRandomString(10) @@ -630,7 +631,8 @@ func SearchUsers(ctx context.Context, query *models.SearchUsersQuery) error { // TODO: add to chore, for cleaning up after we have created // service accounts table in the modelling - whereConditions = append(whereConditions, "u.is_service_account = false") + whereConditions = append(whereConditions, "u.is_service_account = ?") + whereParams = append(whereParams, dialect.BooleanStr(false)) // Join with only most recent auth module joinCondition := `(