github.com/coincircle/mattermost-server@v4.8.1-0.20180321182714-9d701c704416+incompatible/app/user_test.go (about)

     1  // Copyright (c) 2016-present Mattermost, Inc. All Rights Reserved.
     2  // See License.txt for license information.
     3  
     4  package app
     5  
     6  import (
     7  	"bytes"
     8  	"encoding/json"
     9  	"image"
    10  	"image/color"
    11  	"math/rand"
    12  	"strings"
    13  	"testing"
    14  	"time"
    15  
    16  	"github.com/stretchr/testify/assert"
    17  
    18  	"github.com/mattermost/mattermost-server/einterfaces"
    19  	"github.com/mattermost/mattermost-server/model"
    20  	"github.com/mattermost/mattermost-server/model/gitlab"
    21  )
    22  
    23  func TestIsUsernameTaken(t *testing.T) {
    24  	th := Setup().InitBasic()
    25  	defer th.TearDown()
    26  
    27  	user := th.BasicUser
    28  	taken := th.App.IsUsernameTaken(user.Username)
    29  
    30  	if !taken {
    31  		t.Logf("the username '%v' should be taken", user.Username)
    32  		t.FailNow()
    33  	}
    34  
    35  	newUsername := "randomUsername"
    36  	taken = th.App.IsUsernameTaken(newUsername)
    37  
    38  	if taken {
    39  		t.Logf("the username '%v' should not be taken", newUsername)
    40  		t.FailNow()
    41  	}
    42  }
    43  
    44  func TestCheckUserDomain(t *testing.T) {
    45  	th := Setup().InitBasic()
    46  	defer th.TearDown()
    47  
    48  	user := th.BasicUser
    49  
    50  	cases := []struct {
    51  		domains string
    52  		matched bool
    53  	}{
    54  		{"simulator.amazonses.com", true},
    55  		{"gmail.com", false},
    56  		{"", true},
    57  		{"gmail.com simulator.amazonses.com", true},
    58  	}
    59  	for _, c := range cases {
    60  		matched := CheckUserDomain(user, c.domains)
    61  		if matched != c.matched {
    62  			if c.matched {
    63  				t.Logf("'%v' should have matched '%v'", user.Email, c.domains)
    64  			} else {
    65  				t.Logf("'%v' should not have matched '%v'", user.Email, c.domains)
    66  			}
    67  			t.FailNow()
    68  		}
    69  	}
    70  }
    71  
    72  func TestCreateOAuthUser(t *testing.T) {
    73  	th := Setup().InitBasic()
    74  	defer th.TearDown()
    75  
    76  	r := rand.New(rand.NewSource(time.Now().UnixNano()))
    77  	glUser := oauthgitlab.GitLabUser{Id: int64(r.Intn(1000)) + 1, Username: "o" + model.NewId(), Email: model.NewId() + "@simulator.amazonses.com", Name: "Joram Wilander"}
    78  
    79  	json := glUser.ToJson()
    80  	user, err := th.App.CreateOAuthUser(model.USER_AUTH_SERVICE_GITLAB, strings.NewReader(json), th.BasicTeam.Id)
    81  	if err != nil {
    82  		t.Fatal(err)
    83  	}
    84  
    85  	if user.Username != glUser.Username {
    86  		t.Fatal("usernames didn't match")
    87  	}
    88  
    89  	th.App.PermanentDeleteUser(user)
    90  
    91  	th.App.Config().TeamSettings.EnableUserCreation = false
    92  
    93  	_, err = th.App.CreateOAuthUser(model.USER_AUTH_SERVICE_GITLAB, strings.NewReader(json), th.BasicTeam.Id)
    94  	if err == nil {
    95  		t.Fatal("should have failed - user creation disabled")
    96  	}
    97  }
    98  
    99  func TestDeactivateSSOUser(t *testing.T) {
   100  	th := Setup().InitBasic()
   101  	defer th.TearDown()
   102  
   103  	r := rand.New(rand.NewSource(time.Now().UnixNano()))
   104  	glUser := oauthgitlab.GitLabUser{Id: int64(r.Intn(1000)) + 1, Username: "o" + model.NewId(), Email: model.NewId() + "@simulator.amazonses.com", Name: "Joram Wilander"}
   105  
   106  	json := glUser.ToJson()
   107  	user, err := th.App.CreateOAuthUser(model.USER_AUTH_SERVICE_GITLAB, strings.NewReader(json), th.BasicTeam.Id)
   108  	if err != nil {
   109  		t.Fatal(err)
   110  	}
   111  	defer th.App.PermanentDeleteUser(user)
   112  
   113  	_, err = th.App.UpdateNonSSOUserActive(user.Id, false)
   114  	assert.Equal(t, "api.user.update_active.no_deactivate_sso.app_error", err.Id)
   115  }
   116  
   117  func TestCreateProfileImage(t *testing.T) {
   118  	b, err := CreateProfileImage("Corey Hulen", "eo1zkdr96pdj98pjmq8zy35wba", "luximbi.ttf")
   119  	if err != nil {
   120  		t.Fatal(err)
   121  	}
   122  
   123  	rdr := bytes.NewReader(b)
   124  	img, _, err2 := image.Decode(rdr)
   125  	if err2 != nil {
   126  		t.Fatal(err)
   127  	}
   128  
   129  	colorful := color.RGBA{116, 49, 196, 255}
   130  
   131  	if img.At(1, 1) != colorful {
   132  		t.Fatal("Failed to create correct color")
   133  	}
   134  }
   135  
   136  func TestUpdateUserToRestrictedDomain(t *testing.T) {
   137  	th := Setup()
   138  	defer th.TearDown()
   139  
   140  	user := th.CreateUser()
   141  	defer th.App.PermanentDeleteUser(user)
   142  
   143  	th.App.UpdateConfig(func(cfg *model.Config) {
   144  		cfg.TeamSettings.RestrictCreationToDomains = "foo.com"
   145  	})
   146  
   147  	_, err := th.App.UpdateUser(user, false)
   148  	assert.True(t, err == nil)
   149  
   150  	user.Email = "asdf@ghjk.l"
   151  	_, err = th.App.UpdateUser(user, false)
   152  	assert.False(t, err == nil)
   153  }
   154  
   155  func TestUpdateOAuthUserAttrs(t *testing.T) {
   156  	th := Setup()
   157  	defer th.TearDown()
   158  
   159  	id := model.NewId()
   160  	id2 := model.NewId()
   161  	gitlabProvider := einterfaces.GetOauthProvider("gitlab")
   162  
   163  	username := "user" + id
   164  	username2 := "user" + id2
   165  
   166  	email := "user" + id + "@nowhere.com"
   167  	email2 := "user" + id2 + "@nowhere.com"
   168  
   169  	var user, user2 *model.User
   170  	var gitlabUserObj oauthgitlab.GitLabUser
   171  	user, gitlabUserObj = createGitlabUser(t, th.App, username, email)
   172  	user2, _ = createGitlabUser(t, th.App, username2, email2)
   173  
   174  	t.Run("UpdateUsername", func(t *testing.T) {
   175  		t.Run("NoExistingUserWithSameUsername", func(t *testing.T) {
   176  			gitlabUserObj.Username = "updateduser" + model.NewId()
   177  			gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   178  			data := bytes.NewReader(gitlabUser)
   179  
   180  			user = getUserFromDB(th.App, user.Id, t)
   181  			th.App.UpdateOAuthUserAttrs(data, user, gitlabProvider, "gitlab")
   182  			user = getUserFromDB(th.App, user.Id, t)
   183  
   184  			if user.Username != gitlabUserObj.Username {
   185  				t.Fatal("user's username is not updated")
   186  			}
   187  		})
   188  
   189  		t.Run("ExistinguserWithSameUsername", func(t *testing.T) {
   190  			gitlabUserObj.Username = user2.Username
   191  
   192  			gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   193  			data := bytes.NewReader(gitlabUser)
   194  
   195  			user = getUserFromDB(th.App, user.Id, t)
   196  			th.App.UpdateOAuthUserAttrs(data, user, gitlabProvider, "gitlab")
   197  			user = getUserFromDB(th.App, user.Id, t)
   198  
   199  			if user.Username == gitlabUserObj.Username {
   200  				t.Fatal("user's username is updated though there already exists another user with the same username")
   201  			}
   202  		})
   203  	})
   204  
   205  	t.Run("UpdateEmail", func(t *testing.T) {
   206  		t.Run("NoExistingUserWithSameEmail", func(t *testing.T) {
   207  			gitlabUserObj.Email = "newuser" + model.NewId() + "@nowhere.com"
   208  			gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   209  			data := bytes.NewReader(gitlabUser)
   210  
   211  			user = getUserFromDB(th.App, user.Id, t)
   212  			th.App.UpdateOAuthUserAttrs(data, user, gitlabProvider, "gitlab")
   213  			user = getUserFromDB(th.App, user.Id, t)
   214  
   215  			if user.Email != gitlabUserObj.Email {
   216  				t.Fatal("user's email is not updated")
   217  			}
   218  
   219  			if !user.EmailVerified {
   220  				t.Fatal("user's email should have been verified")
   221  			}
   222  		})
   223  
   224  		t.Run("ExistingUserWithSameEmail", func(t *testing.T) {
   225  			gitlabUserObj.Email = user2.Email
   226  
   227  			gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   228  			data := bytes.NewReader(gitlabUser)
   229  
   230  			user = getUserFromDB(th.App, user.Id, t)
   231  			th.App.UpdateOAuthUserAttrs(data, user, gitlabProvider, "gitlab")
   232  			user = getUserFromDB(th.App, user.Id, t)
   233  
   234  			if user.Email == gitlabUserObj.Email {
   235  				t.Fatal("user's email is updated though there already exists another user with the same email")
   236  			}
   237  		})
   238  	})
   239  
   240  	t.Run("UpdateFirstName", func(t *testing.T) {
   241  		gitlabUserObj.Name = "Updated User"
   242  		gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   243  		data := bytes.NewReader(gitlabUser)
   244  
   245  		user = getUserFromDB(th.App, user.Id, t)
   246  		th.App.UpdateOAuthUserAttrs(data, user, gitlabProvider, "gitlab")
   247  		user = getUserFromDB(th.App, user.Id, t)
   248  
   249  		if user.FirstName != "Updated" {
   250  			t.Fatal("user's first name is not updated")
   251  		}
   252  	})
   253  
   254  	t.Run("UpdateLastName", func(t *testing.T) {
   255  		gitlabUserObj.Name = "Updated Lastname"
   256  		gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   257  		data := bytes.NewReader(gitlabUser)
   258  
   259  		user = getUserFromDB(th.App, user.Id, t)
   260  		th.App.UpdateOAuthUserAttrs(data, user, gitlabProvider, "gitlab")
   261  		user = getUserFromDB(th.App, user.Id, t)
   262  
   263  		if user.LastName != "Lastname" {
   264  			t.Fatal("user's last name is not updated")
   265  		}
   266  	})
   267  }
   268  
   269  func getUserFromDB(a *App, id string, t *testing.T) *model.User {
   270  	if user, err := a.GetUser(id); err != nil {
   271  		t.Fatal("user is not found")
   272  		return nil
   273  	} else {
   274  		return user
   275  	}
   276  }
   277  
   278  func getGitlabUserPayload(gitlabUser oauthgitlab.GitLabUser, t *testing.T) []byte {
   279  	var payload []byte
   280  	var err error
   281  	if payload, err = json.Marshal(gitlabUser); err != nil {
   282  		t.Fatal("Serialization of gitlab user to json failed")
   283  	}
   284  
   285  	return payload
   286  }
   287  
   288  func createGitlabUser(t *testing.T, a *App, email string, username string) (*model.User, oauthgitlab.GitLabUser) {
   289  	r := rand.New(rand.NewSource(time.Now().UnixNano()))
   290  	gitlabUserObj := oauthgitlab.GitLabUser{Id: int64(r.Intn(1000)) + 1, Username: username, Login: "user1", Email: email, Name: "Test User"}
   291  	gitlabUser := getGitlabUserPayload(gitlabUserObj, t)
   292  
   293  	var user *model.User
   294  	var err *model.AppError
   295  
   296  	if user, err = a.CreateOAuthUser("gitlab", bytes.NewReader(gitlabUser), ""); err != nil {
   297  		t.Fatal("unable to create the user")
   298  	}
   299  
   300  	return user, gitlabUserObj
   301  }
   302  
   303  func TestGetUsersByStatus(t *testing.T) {
   304  	th := Setup()
   305  	defer th.TearDown()
   306  
   307  	team := th.CreateTeam()
   308  	channel, err := th.App.CreateChannel(&model.Channel{
   309  		DisplayName: "dn_" + model.NewId(),
   310  		Name:        "name_" + model.NewId(),
   311  		Type:        model.CHANNEL_OPEN,
   312  		TeamId:      team.Id,
   313  		CreatorId:   model.NewId(),
   314  	}, false)
   315  	if err != nil {
   316  		t.Fatalf("failed to create channel: %v", err)
   317  	}
   318  
   319  	createUserWithStatus := func(username string, status string) *model.User {
   320  		id := model.NewId()
   321  
   322  		user, err := th.App.CreateUser(&model.User{
   323  			Email:    "success+" + id + "@simulator.amazonses.com",
   324  			Username: "un_" + username + "_" + id,
   325  			Nickname: "nn_" + id,
   326  			Password: "Password1",
   327  		})
   328  		if err != nil {
   329  			t.Fatalf("failed to create user: %v", err)
   330  		}
   331  
   332  		th.LinkUserToTeam(user, team)
   333  		th.AddUserToChannel(user, channel)
   334  
   335  		th.App.SaveAndBroadcastStatus(&model.Status{
   336  			UserId: user.Id,
   337  			Status: status,
   338  			Manual: true,
   339  		})
   340  
   341  		return user
   342  	}
   343  
   344  	// Creating these out of order in case that affects results
   345  	awayUser1 := createUserWithStatus("away1", model.STATUS_AWAY)
   346  	awayUser2 := createUserWithStatus("away2", model.STATUS_AWAY)
   347  	dndUser1 := createUserWithStatus("dnd1", model.STATUS_DND)
   348  	dndUser2 := createUserWithStatus("dnd2", model.STATUS_DND)
   349  	offlineUser1 := createUserWithStatus("offline1", model.STATUS_OFFLINE)
   350  	offlineUser2 := createUserWithStatus("offline2", model.STATUS_OFFLINE)
   351  	onlineUser1 := createUserWithStatus("online1", model.STATUS_ONLINE)
   352  	onlineUser2 := createUserWithStatus("online2", model.STATUS_ONLINE)
   353  
   354  	t.Run("sorting by status then alphabetical", func(t *testing.T) {
   355  		usersByStatus, err := th.App.GetUsersInChannelPageByStatus(channel.Id, 0, 8, true)
   356  		if err != nil {
   357  			t.Fatal(err)
   358  		}
   359  
   360  		expectedUsersByStatus := []*model.User{
   361  			onlineUser1,
   362  			onlineUser2,
   363  			awayUser1,
   364  			awayUser2,
   365  			dndUser1,
   366  			dndUser2,
   367  			offlineUser1,
   368  			offlineUser2,
   369  		}
   370  
   371  		if len(usersByStatus) != len(expectedUsersByStatus) {
   372  			t.Fatalf("received only %v users, expected %v", len(usersByStatus), len(expectedUsersByStatus))
   373  		}
   374  
   375  		for i := range usersByStatus {
   376  			if usersByStatus[i].Id != expectedUsersByStatus[i].Id {
   377  				t.Fatalf("received user %v at index %v, expected %v", usersByStatus[i].Username, i, expectedUsersByStatus[i].Username)
   378  			}
   379  		}
   380  	})
   381  
   382  	t.Run("paging", func(t *testing.T) {
   383  		usersByStatus, err := th.App.GetUsersInChannelPageByStatus(channel.Id, 0, 3, true)
   384  		if err != nil {
   385  			t.Fatal(err)
   386  		}
   387  
   388  		if len(usersByStatus) != 3 {
   389  			t.Fatal("received too many users")
   390  		}
   391  
   392  		if usersByStatus[0].Id != onlineUser1.Id && usersByStatus[1].Id != onlineUser2.Id {
   393  			t.Fatal("expected to receive online users first")
   394  		}
   395  
   396  		if usersByStatus[2].Id != awayUser1.Id {
   397  			t.Fatal("expected to receive away users second")
   398  		}
   399  
   400  		usersByStatus, err = th.App.GetUsersInChannelPageByStatus(channel.Id, 1, 3, true)
   401  		if err != nil {
   402  			t.Fatal(err)
   403  		}
   404  
   405  		if usersByStatus[0].Id != awayUser2.Id {
   406  			t.Fatal("expected to receive away users second")
   407  		}
   408  
   409  		if usersByStatus[1].Id != dndUser1.Id && usersByStatus[2].Id != dndUser2.Id {
   410  			t.Fatal("expected to receive dnd users third")
   411  		}
   412  
   413  		usersByStatus, err = th.App.GetUsersInChannelPageByStatus(channel.Id, 1, 4, true)
   414  		if err != nil {
   415  			t.Fatal(err)
   416  		}
   417  
   418  		if len(usersByStatus) != 4 {
   419  			t.Fatal("received too many users")
   420  		}
   421  
   422  		if usersByStatus[0].Id != dndUser1.Id && usersByStatus[1].Id != dndUser2.Id {
   423  			t.Fatal("expected to receive dnd users third")
   424  		}
   425  
   426  		if usersByStatus[2].Id != offlineUser1.Id && usersByStatus[3].Id != offlineUser2.Id {
   427  			t.Fatal("expected to receive offline users last")
   428  		}
   429  	})
   430  }