diff options
Diffstat (limited to 'store')
-rw-r--r-- | store/sql_audit_store.go | 4 | ||||
-rw-r--r-- | store/sql_channel_store.go | 45 | ||||
-rw-r--r-- | store/sql_channel_store_test.go | 18 | ||||
-rw-r--r-- | store/sql_oauth_store.go | 10 | ||||
-rw-r--r-- | store/sql_post_store.go | 210 | ||||
-rw-r--r-- | store/sql_post_store_test.go | 144 | ||||
-rw-r--r-- | store/sql_preference_store.go | 6 | ||||
-rw-r--r-- | store/sql_session_store.go | 8 | ||||
-rw-r--r-- | store/sql_store.go | 53 | ||||
-rw-r--r-- | store/sql_system_store.go | 6 | ||||
-rw-r--r-- | store/sql_team_store.go | 100 | ||||
-rw-r--r-- | store/sql_team_store_test.go | 77 | ||||
-rw-r--r-- | store/sql_user_store.go | 14 | ||||
-rw-r--r-- | store/store.go | 6 |
14 files changed, 618 insertions, 83 deletions
diff --git a/store/sql_audit_store.go b/store/sql_audit_store.go index 898cf8f78..b3e2daea0 100644 --- a/store/sql_audit_store.go +++ b/store/sql_audit_store.go @@ -46,7 +46,7 @@ func (s SqlAuditStore) Save(audit *model.Audit) StoreChannel { if err := s.GetMaster().Insert(audit); err != nil { result.Err = model.NewAppError("SqlAuditStore.Save", - "We encounted an error saving the audit", "user_id="+ + "We encountered an error saving the audit", "user_id="+ audit.UserId+" action="+audit.Action) } @@ -75,7 +75,7 @@ func (s SqlAuditStore) Get(user_id string, limit int) StoreChannel { var audits model.Audits if _, err := s.GetReplica().Select(&audits, "SELECT * FROM Audits WHERE UserId = :user_id ORDER BY CreateAt DESC LIMIT :limit", map[string]interface{}{"user_id": user_id, "limit": limit}); err != nil { - result.Err = model.NewAppError("SqlAuditStore.Get", "We encounted an error finding the audits", "user_id="+user_id) + result.Err = model.NewAppError("SqlAuditStore.Get", "We encountered an error finding the audits", "user_id="+user_id) } else { result.Data = audits } diff --git a/store/sql_channel_store.go b/store/sql_channel_store.go index 8bedf0632..2d62b8614 100644 --- a/store/sql_channel_store.go +++ b/store/sql_channel_store.go @@ -25,7 +25,8 @@ func NewSqlChannelStore(sqlStore *SqlStore) ChannelStore { table.ColMap("DisplayName").SetMaxSize(64) table.ColMap("Name").SetMaxSize(64) table.SetUniqueTogether("Name", "TeamId") - table.ColMap("Description").SetMaxSize(1024) + table.ColMap("Header").SetMaxSize(1024) + table.ColMap("Purpose").SetMaxSize(128) table.ColMap("CreatorId").SetMaxSize(26) tablem := db.AddTableWithName(model.ChannelMember{}, "ChannelMembers").SetKeys(false, "ChannelId", "UserId") @@ -40,7 +41,7 @@ func NewSqlChannelStore(sqlStore *SqlStore) ChannelStore { func (s SqlChannelStore) UpgradeSchemaIfNeeded() { - // BEGIN REMOVE AFTER 1.1.0 + // REMOVE AFTER 1.2 SHIP see PLT-828 if s.CreateColumnIfNotExists("ChannelMembers", "NotifyProps", "varchar(2000)", "varchar(2000)", "{}") { // populate NotifyProps from existing NotifyLevel field @@ -83,7 +84,11 @@ func (s SqlChannelStore) UpgradeSchemaIfNeeded() { s.RemoveColumnIfExists("ChannelMembers", "NotifyLevel") } - // END REMOVE AFTER 1.1.0 + + // BEGIN REMOVE AFTER 1.2.0 + s.RenameColumnIfExists("Channels", "Description", "Header", "varchar(1024)") + s.CreateColumnIfNotExists("Channels", "Purpose", "varchar(1024)", "varchar(1024)", "") + // END REMOVE AFTER 1.2.0 } func (s SqlChannelStore) CreateIndexesIfNotExists() { @@ -242,7 +247,7 @@ func (s SqlChannelStore) Update(channel *model.Channel) StoreChannel { result.Err = model.NewAppError("SqlChannelStore.Update", "A channel with that handle already exists", "id="+channel.Id+", "+err.Error()) } } else { - result.Err = model.NewAppError("SqlChannelStore.Update", "We encounted an error updating the channel", "id="+channel.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlChannelStore.Update", "We encountered an error updating the channel", "id="+channel.Id+", "+err.Error()) } } else if count != 1 { result.Err = model.NewAppError("SqlChannelStore.Update", "We couldn't update the channel", "id="+channel.Id) @@ -292,7 +297,7 @@ func (s SqlChannelStore) Get(id string) StoreChannel { result := StoreResult{} if obj, err := s.GetReplica().Get(model.Channel{}, id); err != nil { - result.Err = model.NewAppError("SqlChannelStore.Get", "We encounted an error finding the channel", "id="+id+", "+err.Error()) + result.Err = model.NewAppError("SqlChannelStore.Get", "We encountered an error finding the channel", "id="+id+", "+err.Error()) } else if obj == nil { result.Err = model.NewAppError("SqlChannelStore.Get", "We couldn't find the existing channel", "id="+id) } else { @@ -532,7 +537,7 @@ func (s SqlChannelStore) UpdateMember(member *model.ChannelMember) StoreChannel } if _, err := s.GetMaster().Update(member); err != nil { - result.Err = model.NewAppError("SqlChannelStore.UpdateMember", "We encounted an error updating the channel member", + result.Err = model.NewAppError("SqlChannelStore.UpdateMember", "We encountered an error updating the channel member", "channel_id="+member.ChannelId+", "+"user_id="+member.UserId+", "+err.Error()) } else { result.Data = member @@ -829,3 +834,31 @@ func (s SqlChannelStore) GetForExport(teamId string) StoreChannel { return storeChannel } + +func (s SqlChannelStore) AnalyticsTypeCount(teamId string, channelType string) StoreChannel { + storeChannel := make(StoreChannel) + + go func() { + result := StoreResult{} + + v, err := s.GetReplica().SelectInt( + `SELECT + COUNT(Id) AS Value + FROM + Channels + WHERE + TeamId = :TeamId + AND Type = :ChannelType`, + map[string]interface{}{"TeamId": teamId, "ChannelType": channelType}) + if err != nil { + result.Err = model.NewAppError("SqlChannelStore.AnalyticsTypeCount", "We couldn't get channel type counts", err.Error()) + } else { + result.Data = v + } + + storeChannel <- result + close(storeChannel) + }() + + return storeChannel +} diff --git a/store/sql_channel_store_test.go b/store/sql_channel_store_test.go index 60d3de56a..f6a0fb713 100644 --- a/store/sql_channel_store_test.go +++ b/store/sql_channel_store_test.go @@ -561,6 +561,24 @@ func TestChannelStoreGetMoreChannels(t *testing.T) { if list.Channels[0].Name != o3.Name { t.Fatal("missing channel") } + + if r1 := <-store.Channel().AnalyticsTypeCount(o1.TeamId, model.CHANNEL_OPEN); r1.Err != nil { + t.Fatal(r1.Err) + } else { + if r1.Data.(int64) != 2 { + t.Log(r1.Data) + t.Fatal("wrong value") + } + } + + if r1 := <-store.Channel().AnalyticsTypeCount(o1.TeamId, model.CHANNEL_PRIVATE); r1.Err != nil { + t.Fatal(r1.Err) + } else { + if r1.Data.(int64) != 2 { + t.Log(r1.Data) + t.Fatal("wrong value") + } + } } func TestChannelStoreGetChannelCounts(t *testing.T) { diff --git a/store/sql_oauth_store.go b/store/sql_oauth_store.go index db52e379b..751207b85 100644 --- a/store/sql_oauth_store.go +++ b/store/sql_oauth_store.go @@ -102,7 +102,7 @@ func (as SqlOAuthStore) UpdateApp(app *model.OAuthApp) StoreChannel { } if oldAppResult, err := as.GetMaster().Get(model.OAuthApp{}, app.Id); err != nil { - result.Err = model.NewAppError("SqlOAuthStore.UpdateApp", "We encounted an error finding the app", "app_id="+app.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlOAuthStore.UpdateApp", "We encountered an error finding the app", "app_id="+app.Id+", "+err.Error()) } else if oldAppResult == nil { result.Err = model.NewAppError("SqlOAuthStore.UpdateApp", "We couldn't find the existing app to update", "app_id="+app.Id) } else { @@ -112,7 +112,7 @@ func (as SqlOAuthStore) UpdateApp(app *model.OAuthApp) StoreChannel { app.CreatorId = oldApp.CreatorId if count, err := as.GetMaster().Update(app); err != nil { - result.Err = model.NewAppError("SqlOAuthStore.UpdateApp", "We encounted an error updating the app", "app_id="+app.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlOAuthStore.UpdateApp", "We encountered an error updating the app", "app_id="+app.Id+", "+err.Error()) } else if count != 1 { result.Err = model.NewAppError("SqlOAuthStore.UpdateApp", "We couldn't update the app", "app_id="+app.Id) } else { @@ -135,7 +135,7 @@ func (as SqlOAuthStore) GetApp(id string) StoreChannel { result := StoreResult{} if obj, err := as.GetReplica().Get(model.OAuthApp{}, id); err != nil { - result.Err = model.NewAppError("SqlOAuthStore.GetApp", "We encounted an error finding the app", "app_id="+id+", "+err.Error()) + result.Err = model.NewAppError("SqlOAuthStore.GetApp", "We encountered an error finding the app", "app_id="+id+", "+err.Error()) } else if obj == nil { result.Err = model.NewAppError("SqlOAuthStore.GetApp", "We couldn't find the existing app", "app_id="+id) } else { @@ -208,7 +208,7 @@ func (as SqlOAuthStore) GetAccessData(token string) StoreChannel { accessData := model.AccessData{} if err := as.GetReplica().SelectOne(&accessData, "SELECT * FROM OAuthAccessData WHERE Token = :Token", map[string]interface{}{"Token": token}); err != nil { - result.Err = model.NewAppError("SqlOAuthStore.GetAccessData", "We encounted an error finding the access token", err.Error()) + result.Err = model.NewAppError("SqlOAuthStore.GetAccessData", "We encountered an error finding the access token", err.Error()) } else { result.Data = &accessData } @@ -300,7 +300,7 @@ func (as SqlOAuthStore) GetAuthData(code string) StoreChannel { result := StoreResult{} if obj, err := as.GetReplica().Get(model.AuthData{}, code); err != nil { - result.Err = model.NewAppError("SqlOAuthStore.GetAuthData", "We encounted an error finding the authorization code", err.Error()) + result.Err = model.NewAppError("SqlOAuthStore.GetAuthData", "We encountered an error finding the authorization code", err.Error()) } else if obj == nil { result.Err = model.NewAppError("SqlOAuthStore.GetAuthData", "We couldn't find the existing authorization code", "") } else { diff --git a/store/sql_post_store.go b/store/sql_post_store.go index 6971de9d7..de8c4f356 100644 --- a/store/sql_post_store.go +++ b/store/sql_post_store.go @@ -6,6 +6,7 @@ package store import ( "fmt" "regexp" + "strconv" "strings" "github.com/mattermost/platform/model" @@ -413,10 +414,15 @@ func (s SqlPostStore) Search(teamId string, userId string, params *model.SearchP go func() { result := StoreResult{} + queryParams := map[string]interface{}{ + "TeamId": teamId, + "UserId": userId, + } + termMap := map[string]bool{} terms := params.Terms - if terms == "" && params.InChannel == "" && params.FromUser == "" { + if terms == "" && len(params.InChannels) == 0 && len(params.FromUsers) == 0 { result.Data = []*model.Post{} storeChannel <- result return @@ -437,13 +443,6 @@ func (s SqlPostStore) Search(teamId string, userId string, params *model.SearchP var posts []*model.Post - if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_POSTGRES { - // Parse text for wildcards - if wildcard, err := regexp.Compile("\\*($| )"); err == nil { - terms = wildcard.ReplaceAllLiteralString(terms, "* ") - } - } - searchQuery := ` SELECT * @@ -468,13 +467,45 @@ func (s SqlPostStore) Search(teamId string, userId string, params *model.SearchP ORDER BY CreateAt DESC LIMIT 100` - if params.InChannel != "" { + if len(params.InChannels) > 1 { + inClause := ":InChannel0" + queryParams["InChannel0"] = params.InChannels[0] + + for i := 1; i < len(params.InChannels); i++ { + paramName := "InChannel" + strconv.FormatInt(int64(i), 10) + inClause += ", :" + paramName + queryParams[paramName] = params.InChannels[i] + } + + searchQuery = strings.Replace(searchQuery, "CHANNEL_FILTER", "AND Name IN ("+inClause+")", 1) + } else if len(params.InChannels) == 1 { + queryParams["InChannel"] = params.InChannels[0] searchQuery = strings.Replace(searchQuery, "CHANNEL_FILTER", "AND Name = :InChannel", 1) } else { searchQuery = strings.Replace(searchQuery, "CHANNEL_FILTER", "", 1) } - if params.FromUser != "" { + if len(params.FromUsers) > 1 { + inClause := ":FromUser0" + queryParams["FromUser0"] = params.FromUsers[0] + + for i := 1; i < len(params.FromUsers); i++ { + paramName := "FromUser" + strconv.FormatInt(int64(i), 10) + inClause += ", :" + paramName + queryParams[paramName] = params.FromUsers[i] + } + + searchQuery = strings.Replace(searchQuery, "POST_FILTER", ` + AND UserId IN ( + SELECT + Id + FROM + Users + WHERE + TeamId = :TeamId + AND Username IN (`+inClause+`))`, 1) + } else if len(params.FromUsers) == 1 { + queryParams["FromUser"] = params.FromUsers[0] searchQuery = strings.Replace(searchQuery, "POST_FILTER", ` AND UserId IN ( SELECT @@ -506,17 +537,11 @@ func (s SqlPostStore) Search(teamId string, userId string, params *model.SearchP searchQuery = strings.Replace(searchQuery, "SEARCH_CLAUSE", searchClause, 1) } - queryParams := map[string]interface{}{ - "TeamId": teamId, - "UserId": userId, - "Terms": terms, - "InChannel": params.InChannel, - "FromUser": params.FromUser, - } + queryParams["Terms"] = terms _, err := s.GetReplica().Select(&posts, searchQuery, queryParams) if err != nil { - result.Err = model.NewAppError("SqlPostStore.Search", "We encounted an error while searching for posts", "teamId="+teamId+", err="+err.Error()) + result.Err = model.NewAppError("SqlPostStore.Search", "We encountered an error while searching for posts", "teamId="+teamId+", err="+err.Error()) } list := &model.PostList{Order: make([]string, 0, len(posts))} @@ -571,3 +596,152 @@ func (s SqlPostStore) GetForExport(channelId string) StoreChannel { return storeChannel } + +func (s SqlPostStore) AnalyticsUserCountsWithPostsByDay(teamId string) StoreChannel { + storeChannel := make(StoreChannel) + + go func() { + result := StoreResult{} + + query := + `SELECT + t1.Name, COUNT(t1.UserId) AS Value + FROM + (SELECT DISTINCT + DATE(FROM_UNIXTIME(Posts.CreateAt / 1000)) AS Name, + Posts.UserId + FROM + Posts, Channels + WHERE + Posts.ChannelId = Channels.Id + AND Channels.TeamId = :TeamId + ORDER BY Name DESC) AS t1 + GROUP BY Name + ORDER BY Name DESC + LIMIT 30` + + if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_POSTGRES { + query = + `SELECT + TO_CHAR(t1.Name, 'YYYY-MM-DD') AS Name, COUNT(t1.UserId) AS Value + FROM + (SELECT DISTINCT + DATE(TO_TIMESTAMP(Posts.CreateAt / 1000)) AS Name, + Posts.UserId + FROM + Posts, Channels + WHERE + Posts.ChannelId = Channels.Id + AND Channels.TeamId = :TeamId + ORDER BY Name DESC) AS t1 + GROUP BY Name + ORDER BY Name DESC + LIMIT 30` + } + + var rows model.AnalyticsRows + _, err := s.GetReplica().Select( + &rows, + query, + map[string]interface{}{"TeamId": teamId, "Time": model.GetMillis() - 1000*60*60*24*31}) + if err != nil { + result.Err = model.NewAppError("SqlPostStore.AnalyticsUserCountsWithPostsByDay", "We couldn't get user counts with posts", err.Error()) + } else { + result.Data = rows + } + + storeChannel <- result + close(storeChannel) + }() + + return storeChannel +} + +func (s SqlPostStore) AnalyticsPostCountsByDay(teamId string) StoreChannel { + storeChannel := make(StoreChannel) + + go func() { + result := StoreResult{} + + query := + `SELECT + Name, COUNT(Value) AS Value + FROM + (SELECT + DATE(FROM_UNIXTIME(Posts.CreateAt / 1000)) AS Name, + '1' AS Value + FROM + Posts, Channels + WHERE + Posts.ChannelId = Channels.Id + AND Channels.TeamId = :TeamId + AND Posts.CreateAt >:Time) AS t1 + GROUP BY Name + ORDER BY Name DESC + LIMIT 30` + + if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_POSTGRES { + query = + `SELECT + Name, COUNT(Value) AS Value + FROM + (SELECT + TO_CHAR(DATE(TO_TIMESTAMP(Posts.CreateAt / 1000)), 'YYYY-MM-DD') AS Name, + '1' AS Value + FROM + Posts, Channels + WHERE + Posts.ChannelId = Channels.Id + AND Channels.TeamId = :TeamId + AND Posts.CreateAt > :Time) AS t1 + GROUP BY Name + ORDER BY Name DESC + LIMIT 30` + } + + var rows model.AnalyticsRows + _, err := s.GetReplica().Select( + &rows, + query, + map[string]interface{}{"TeamId": teamId, "Time": model.GetMillis() - 1000*60*60*24*31}) + if err != nil { + result.Err = model.NewAppError("SqlPostStore.AnalyticsPostCountsByDay", "We couldn't get post counts by day", err.Error()) + } else { + result.Data = rows + } + + storeChannel <- result + close(storeChannel) + }() + + return storeChannel +} + +func (s SqlPostStore) AnalyticsPostCount(teamId string) StoreChannel { + storeChannel := make(StoreChannel) + + go func() { + result := StoreResult{} + + v, err := s.GetReplica().SelectInt( + `SELECT + COUNT(Posts.Id) AS Value + FROM + Posts, + Channels + WHERE + Posts.ChannelId = Channels.Id + AND Channels.TeamId = :TeamId`, + map[string]interface{}{"TeamId": teamId}) + if err != nil { + result.Err = model.NewAppError("SqlPostStore.AnalyticsPostCount", "We couldn't get post counts", err.Error()) + } else { + result.Data = v + } + + storeChannel <- result + close(storeChannel) + }() + + return storeChannel +} diff --git a/store/sql_post_store_test.go b/store/sql_post_store_test.go index b2256417e..0980b1a11 100644 --- a/store/sql_post_store_test.go +++ b/store/sql_post_store_test.go @@ -526,32 +526,32 @@ func TestPostStoreSearch(t *testing.T) { o5 = (<-store.Post().Save(o5)).Data.(*model.Post) r1 := (<-store.Post().Search(teamId, userId, &model.SearchParams{Terms: "corey", IsHashtag: false})).Data.(*model.PostList) - if len(r1.Order) != 1 && r1.Order[0] != o1.Id { + if len(r1.Order) != 1 || r1.Order[0] != o1.Id { t.Fatal("returned wrong search result") } r3 := (<-store.Post().Search(teamId, userId, &model.SearchParams{Terms: "new", IsHashtag: false})).Data.(*model.PostList) - if len(r3.Order) != 2 && r3.Order[0] != o1.Id { + if len(r3.Order) != 2 || (r3.Order[0] != o1.Id && r3.Order[1] != o1.Id) { t.Fatal("returned wrong search result") } r4 := (<-store.Post().Search(teamId, userId, &model.SearchParams{Terms: "john", IsHashtag: false})).Data.(*model.PostList) - if len(r4.Order) != 1 && r4.Order[0] != o2.Id { + if len(r4.Order) != 1 || r4.Order[0] != o2.Id { t.Fatal("returned wrong search result") } r5 := (<-store.Post().Search(teamId, userId, &model.SearchParams{Terms: "matter*", IsHashtag: false})).Data.(*model.PostList) - if len(r5.Order) != 1 && r5.Order[0] != o1.Id { + if len(r5.Order) != 1 || r5.Order[0] != o1.Id { t.Fatal("returned wrong search result") } r6 := (<-store.Post().Search(teamId, userId, &model.SearchParams{Terms: "#hashtag", IsHashtag: true})).Data.(*model.PostList) - if len(r6.Order) != 1 && r6.Order[0] != o4.Id { + if len(r6.Order) != 1 || r6.Order[0] != o4.Id { t.Fatal("returned wrong search result") } r7 := (<-store.Post().Search(teamId, userId, &model.SearchParams{Terms: "#secret", IsHashtag: true})).Data.(*model.PostList) - if len(r7.Order) != 1 && r7.Order[0] != o5.Id { + if len(r7.Order) != 1 || r7.Order[0] != o5.Id { t.Fatal("returned wrong search result") } @@ -580,3 +580,135 @@ func TestPostStoreSearch(t *testing.T) { t.Fatal("returned wrong search result") } } + +func TestUserCountsWithPostsByDay(t *testing.T) { + Setup() + + t1 := &model.Team{} + t1.DisplayName = "DisplayName" + t1.Name = "a" + model.NewId() + "b" + t1.Email = model.NewId() + "@nowhere.com" + t1.Type = model.TEAM_OPEN + t1 = Must(store.Team().Save(t1)).(*model.Team) + + c1 := &model.Channel{} + c1.TeamId = t1.Id + c1.DisplayName = "Channel2" + c1.Name = "a" + model.NewId() + "b" + c1.Type = model.CHANNEL_OPEN + c1 = Must(store.Channel().Save(c1)).(*model.Channel) + + o1 := &model.Post{} + o1.ChannelId = c1.Id + o1.UserId = model.NewId() + o1.CreateAt = model.GetMillis() + o1.Message = "a" + model.NewId() + "b" + o1 = Must(store.Post().Save(o1)).(*model.Post) + + o1a := &model.Post{} + o1a.ChannelId = c1.Id + o1a.UserId = model.NewId() + o1a.CreateAt = o1.CreateAt + o1a.Message = "a" + model.NewId() + "b" + o1a = Must(store.Post().Save(o1a)).(*model.Post) + + o2 := &model.Post{} + o2.ChannelId = c1.Id + o2.UserId = model.NewId() + o2.CreateAt = o1.CreateAt - (1000 * 60 * 60 * 24) + o2.Message = "a" + model.NewId() + "b" + o2 = Must(store.Post().Save(o2)).(*model.Post) + + o2a := &model.Post{} + o2a.ChannelId = c1.Id + o2a.UserId = o2.UserId + o2a.CreateAt = o1.CreateAt - (1000 * 60 * 60 * 24) + o2a.Message = "a" + model.NewId() + "b" + o2a = Must(store.Post().Save(o2a)).(*model.Post) + + if r1 := <-store.Post().AnalyticsUserCountsWithPostsByDay(t1.Id); r1.Err != nil { + t.Fatal(r1.Err) + } else { + row1 := r1.Data.(model.AnalyticsRows)[0] + if row1.Value != 2 { + t.Fatal("wrong value") + } + + row2 := r1.Data.(model.AnalyticsRows)[1] + if row2.Value != 1 { + t.Fatal("wrong value") + } + } +} + +func TestPostCountsByDay(t *testing.T) { + Setup() + + t1 := &model.Team{} + t1.DisplayName = "DisplayName" + t1.Name = "a" + model.NewId() + "b" + t1.Email = model.NewId() + "@nowhere.com" + t1.Type = model.TEAM_OPEN + t1 = Must(store.Team().Save(t1)).(*model.Team) + + c1 := &model.Channel{} + c1.TeamId = t1.Id + c1.DisplayName = "Channel2" + c1.Name = "a" + model.NewId() + "b" + c1.Type = model.CHANNEL_OPEN + c1 = Must(store.Channel().Save(c1)).(*model.Channel) + + o1 := &model.Post{} + o1.ChannelId = c1.Id + o1.UserId = model.NewId() + o1.CreateAt = model.GetMillis() + o1.Message = "a" + model.NewId() + "b" + o1 = Must(store.Post().Save(o1)).(*model.Post) + + o1a := &model.Post{} + o1a.ChannelId = c1.Id + o1a.UserId = model.NewId() + o1a.CreateAt = o1.CreateAt + o1a.Message = "a" + model.NewId() + "b" + o1a = Must(store.Post().Save(o1a)).(*model.Post) + + o2 := &model.Post{} + o2.ChannelId = c1.Id + o2.UserId = model.NewId() + o2.CreateAt = o1.CreateAt - (1000 * 60 * 60 * 24 * 2) + o2.Message = "a" + model.NewId() + "b" + o2 = Must(store.Post().Save(o2)).(*model.Post) + + o2a := &model.Post{} + o2a.ChannelId = c1.Id + o2a.UserId = o2.UserId + o2a.CreateAt = o1.CreateAt - (1000 * 60 * 60 * 24 * 2) + o2a.Message = "a" + model.NewId() + "b" + o2a = Must(store.Post().Save(o2a)).(*model.Post) + + time.Sleep(1 * time.Second) + t.Log(t1.Id) + + if r1 := <-store.Post().AnalyticsPostCountsByDay(t1.Id); r1.Err != nil { + t.Fatal(r1.Err) + } else { + row1 := r1.Data.(model.AnalyticsRows)[0] + if row1.Value != 2 { + t.Log(row1) + t.Fatal("wrong value") + } + + row2 := r1.Data.(model.AnalyticsRows)[1] + if row2.Value != 2 { + t.Fatal("wrong value") + } + } + + if r1 := <-store.Post().AnalyticsPostCount(t1.Id); r1.Err != nil { + t.Fatal(r1.Err) + } else { + if r1.Data.(int64) != 4 { + t.Fatal("wrong value") + } + } +} diff --git a/store/sql_preference_store.go b/store/sql_preference_store.go index bf6e030bf..f9f38b747 100644 --- a/store/sql_preference_store.go +++ b/store/sql_preference_store.go @@ -173,7 +173,7 @@ func (s SqlPreferenceStore) Get(userId string, category string, name string) Sto UserId = :UserId AND Category = :Category AND Name = :Name`, map[string]interface{}{"UserId": userId, "Category": category, "Name": name}); err != nil { - result.Err = model.NewAppError("SqlPreferenceStore.Get", "We encounted an error while finding preferences", err.Error()) + result.Err = model.NewAppError("SqlPreferenceStore.Get", "We encountered an error while finding preferences", err.Error()) } else { result.Data = preference } @@ -201,7 +201,7 @@ func (s SqlPreferenceStore) GetCategory(userId string, category string) StoreCha WHERE UserId = :UserId AND Category = :Category`, map[string]interface{}{"UserId": userId, "Category": category}); err != nil { - result.Err = model.NewAppError("SqlPreferenceStore.GetCategory", "We encounted an error while finding preferences", err.Error()) + result.Err = model.NewAppError("SqlPreferenceStore.GetCategory", "We encountered an error while finding preferences", err.Error()) } else { result.Data = preferences } @@ -228,7 +228,7 @@ func (s SqlPreferenceStore) GetAll(userId string) StoreChannel { Preferences WHERE UserId = :UserId`, map[string]interface{}{"UserId": userId}); err != nil { - result.Err = model.NewAppError("SqlPreferenceStore.GetAll", "We encounted an error while finding preferences", err.Error()) + result.Err = model.NewAppError("SqlPreferenceStore.GetAll", "We encountered an error while finding preferences", err.Error()) } else { result.Data = preferences } diff --git a/store/sql_session_store.go b/store/sql_session_store.go index 15ec6924b..27b34ee39 100644 --- a/store/sql_session_store.go +++ b/store/sql_session_store.go @@ -80,9 +80,9 @@ func (me SqlSessionStore) Get(sessionIdOrToken string) StoreChannel { var sessions []*model.Session if _, err := me.GetReplica().Select(&sessions, "SELECT * FROM Sessions WHERE Token = :Token OR Id = :Id LIMIT 1", map[string]interface{}{"Token": sessionIdOrToken, "Id": sessionIdOrToken}); err != nil { - result.Err = model.NewAppError("SqlSessionStore.Get", "We encounted an error finding the session", "sessionIdOrToken="+sessionIdOrToken+", "+err.Error()) + result.Err = model.NewAppError("SqlSessionStore.Get", "We encountered an error finding the session", "sessionIdOrToken="+sessionIdOrToken+", "+err.Error()) } else if sessions == nil || len(sessions) == 0 { - result.Err = model.NewAppError("SqlSessionStore.Get", "We encounted an error finding the session", "sessionIdOrToken="+sessionIdOrToken) + result.Err = model.NewAppError("SqlSessionStore.Get", "We encountered an error finding the session", "sessionIdOrToken="+sessionIdOrToken) } else { result.Data = sessions[0] } @@ -109,7 +109,7 @@ func (me SqlSessionStore) GetSessions(userId string) StoreChannel { var sessions []*model.Session if _, err := me.GetReplica().Select(&sessions, "SELECT * FROM Sessions WHERE UserId = :UserId ORDER BY LastActivityAt DESC", map[string]interface{}{"UserId": userId}); err != nil { - result.Err = model.NewAppError("SqlSessionStore.GetSessions", "We encounted an error while finding user sessions", err.Error()) + result.Err = model.NewAppError("SqlSessionStore.GetSessions", "We encountered an error while finding user sessions", err.Error()) } else { result.Data = sessions @@ -165,7 +165,7 @@ func (me SqlSessionStore) CleanUpExpiredSessions(userId string) StoreChannel { result := StoreResult{} if _, err := me.GetMaster().Exec("DELETE FROM Sessions WHERE UserId = :UserId AND ExpiresAt != 0 AND :ExpiresAt > ExpiresAt", map[string]interface{}{"UserId": userId, "ExpiresAt": model.GetMillis()}); err != nil { - result.Err = model.NewAppError("SqlSessionStore.CleanUpExpiredSessions", "We encounted an error while deleting expired user sessions", err.Error()) + result.Err = model.NewAppError("SqlSessionStore.CleanUpExpiredSessions", "We encountered an error while deleting expired user sessions", err.Error()) } else { result.Data = userId } diff --git a/store/sql_store.go b/store/sql_store.go index 0d1bfe41b..e5c540e06 100644 --- a/store/sql_store.go +++ b/store/sql_store.go @@ -73,7 +73,8 @@ func NewSqlStore() Store { } schemaVersion := sqlStore.GetCurrentSchemaVersion() - isSchemaVersion07 := false + isSchemaVersion07 := false // REMOVE AFTER 1.2 SHIP see PLT-828 + isSchemaVersion10 := false // REMOVE AFTER 1.2 SHIP see PLT-828 // If the version is already set then we are potentially in an 'upgrade needed' state if schemaVersion != "" { @@ -86,7 +87,11 @@ func NewSqlStore() Store { isSchemaVersion07 = true } - if model.IsPreviousVersion(schemaVersion) || isSchemaVersion07 { + if schemaVersion == "1.0.0" { + isSchemaVersion10 = true + } + + if model.IsPreviousVersion(schemaVersion) || isSchemaVersion07 || isSchemaVersion10 { l4g.Warn("The database schema version of " + schemaVersion + " appears to be out of date") l4g.Warn("Attempting to upgrade the database schema version to " + model.CurrentVersion) } else { @@ -98,7 +103,7 @@ func NewSqlStore() Store { } } - // REMOVE in 1.2 + // REMOVE AFTER 1.2 SHIP see PLT-828 if sqlStore.DoesTableExist("Sessions") { if sqlStore.DoesColumnExist("Sessions", "AltId") { sqlStore.GetMaster().Exec("DROP TABLE IF EXISTS Sessions") @@ -116,7 +121,10 @@ func NewSqlStore() Store { sqlStore.webhook = NewSqlWebhookStore(sqlStore) sqlStore.preference = NewSqlPreferenceStore(sqlStore) - sqlStore.master.CreateTablesIfNotExists() + err := sqlStore.master.CreateTablesIfNotExists() + if err != nil { + l4g.Critical("Error creating database tables: %v", err) + } sqlStore.team.(*SqlTeamStore).UpgradeSchemaIfNeeded() sqlStore.channel.(*SqlChannelStore).UpgradeSchemaIfNeeded() @@ -140,7 +148,7 @@ func NewSqlStore() Store { sqlStore.webhook.(*SqlWebhookStore).CreateIndexesIfNotExists() sqlStore.preference.(*SqlPreferenceStore).CreateIndexesIfNotExists() - if model.IsPreviousVersion(schemaVersion) || isSchemaVersion07 { + if model.IsPreviousVersion(schemaVersion) || isSchemaVersion07 || isSchemaVersion10 { sqlStore.system.Update(&model.System{Name: "Version", Value: model.CurrentVersion}) l4g.Warn("The database schema has been upgraded to version " + model.CurrentVersion) } @@ -359,27 +367,26 @@ func (ss SqlStore) RemoveColumnIfExists(tableName string, columnName string) boo return true } -// func (ss SqlStore) RenameColumnIfExists(tableName string, oldColumnName string, newColumnName string, colType string) bool { - -// // XXX TODO FIXME this should be removed after 0.6.0 -// if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_POSTGRES { -// return false -// } - -// if !ss.DoesColumnExist(tableName, oldColumnName) { -// return false -// } +func (ss SqlStore) RenameColumnIfExists(tableName string, oldColumnName string, newColumnName string, colType string) bool { + if !ss.DoesColumnExist(tableName, oldColumnName) { + return false + } -// _, err := ss.GetMaster().Exec("ALTER TABLE " + tableName + " CHANGE " + oldColumnName + " " + newColumnName + " " + colType) + var err error + if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_MYSQL { + _, err = ss.GetMaster().Exec("ALTER TABLE " + tableName + " CHANGE " + oldColumnName + " " + newColumnName + " " + colType) + } else if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_POSTGRES { + _, err = ss.GetMaster().Exec("ALTER TABLE " + tableName + " RENAME COLUMN " + oldColumnName + " TO " + newColumnName) + } -// if err != nil { -// l4g.Critical("Failed to rename column %v", err) -// time.Sleep(time.Second) -// panic("Failed to drop column " + err.Error()) -// } + if err != nil { + l4g.Critical("Failed to rename column %v", err) + time.Sleep(time.Second) + panic("Failed to drop column " + err.Error()) + } -// return true -// } + return true +} func (ss SqlStore) CreateIndexIfNotExists(indexName string, tableName string, columnName string) { ss.createIndexIfNotExists(indexName, tableName, columnName, INDEX_TYPE_DEFAULT) diff --git a/store/sql_system_store.go b/store/sql_system_store.go index a4cb52d4d..1fbdfb333 100644 --- a/store/sql_system_store.go +++ b/store/sql_system_store.go @@ -37,7 +37,7 @@ func (s SqlSystemStore) Save(system *model.System) StoreChannel { result := StoreResult{} if err := s.GetMaster().Insert(system); err != nil { - result.Err = model.NewAppError("SqlSystemStore.Save", "We encounted an error saving the system property", "") + result.Err = model.NewAppError("SqlSystemStore.Save", "We encountered an error saving the system property", "") } storeChannel <- result @@ -55,7 +55,7 @@ func (s SqlSystemStore) Update(system *model.System) StoreChannel { result := StoreResult{} if _, err := s.GetMaster().Update(system); err != nil { - result.Err = model.NewAppError("SqlSystemStore.Save", "We encounted an error updating the system property", "") + result.Err = model.NewAppError("SqlSystemStore.Save", "We encountered an error updating the system property", "") } storeChannel <- result @@ -75,7 +75,7 @@ func (s SqlSystemStore) Get() StoreChannel { var systems []model.System props := make(model.StringMap) if _, err := s.GetReplica().Select(&systems, "SELECT * FROM Systems"); err != nil { - result.Err = model.NewAppError("SqlSystemStore.Get", "We encounted an error finding the system properties", "") + result.Err = model.NewAppError("SqlSystemStore.Get", "We encountered an error finding the system properties", "") } else { for _, prop := range systems { props[prop.Name] = prop.Value diff --git a/store/sql_team_store.go b/store/sql_team_store.go index 380d979bd..e0f95fa7e 100644 --- a/store/sql_team_store.go +++ b/store/sql_team_store.go @@ -23,18 +23,23 @@ func NewSqlTeamStore(sqlStore *SqlStore) TeamStore { table.ColMap("Email").SetMaxSize(128) table.ColMap("CompanyName").SetMaxSize(64) table.ColMap("AllowedDomains").SetMaxSize(500) + table.ColMap("InviteId").SetMaxSize(32) } return s } func (s SqlTeamStore) UpgradeSchemaIfNeeded() { - // REMOVE in 1.2 + // REMOVE AFTER 1.2 SHIP see PLT-828 s.RemoveColumnIfExists("Teams", "AllowValet") + s.CreateColumnIfNotExists("Teams", "InviteId", "varchar(32)", "varchar(32)", "") + s.CreateColumnIfNotExists("Teams", "AllowOpenInvite", "tinyint(1)", "boolean", "0") + s.CreateColumnIfNotExists("Teams", "AllowTeamListing", "tinyint(1)", "boolean", "0") } func (s SqlTeamStore) CreateIndexesIfNotExists() { s.CreateIndexIfNotExists("idx_teams_name", "Teams", "Name") + s.CreateIndexIfNotExists("idx_teams_invite_id", "Teams", "InviteId") } func (s SqlTeamStore) Save(team *model.Team) StoreChannel { @@ -92,16 +97,17 @@ func (s SqlTeamStore) Update(team *model.Team) StoreChannel { } if oldResult, err := s.GetMaster().Get(model.Team{}, team.Id); err != nil { - result.Err = model.NewAppError("SqlTeamStore.Update", "We encounted an error finding the team", "id="+team.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlTeamStore.Update", "We encountered an error finding the team", "id="+team.Id+", "+err.Error()) } else if oldResult == nil { result.Err = model.NewAppError("SqlTeamStore.Update", "We couldn't find the existing team to update", "id="+team.Id) } else { oldTeam := oldResult.(*model.Team) team.CreateAt = oldTeam.CreateAt + team.UpdateAt = model.GetMillis() team.Name = oldTeam.Name if count, err := s.GetMaster().Update(team); err != nil { - result.Err = model.NewAppError("SqlTeamStore.Update", "We encounted an error updating the team", "id="+team.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlTeamStore.Update", "We encountered an error updating the team", "id="+team.Id+", "+err.Error()) } else if count != 1 { result.Err = model.NewAppError("SqlTeamStore.Update", "We couldn't update the team", "id="+team.Id) } else { @@ -143,11 +149,16 @@ func (s SqlTeamStore) Get(id string) StoreChannel { result := StoreResult{} if obj, err := s.GetReplica().Get(model.Team{}, id); err != nil { - result.Err = model.NewAppError("SqlTeamStore.Get", "We encounted an error finding the team", "id="+id+", "+err.Error()) + result.Err = model.NewAppError("SqlTeamStore.Get", "We encountered an error finding the team", "id="+id+", "+err.Error()) } else if obj == nil { result.Err = model.NewAppError("SqlTeamStore.Get", "We couldn't find the existing team", "id="+id) } else { - result.Data = obj.(*model.Team) + team := obj.(*model.Team) + if len(team.InviteId) == 0 { + team.InviteId = team.Id + } + + result.Data = team } storeChannel <- result @@ -157,6 +168,35 @@ func (s SqlTeamStore) Get(id string) StoreChannel { return storeChannel } +func (s SqlTeamStore) GetByInviteId(inviteId string) StoreChannel { + storeChannel := make(StoreChannel) + + go func() { + result := StoreResult{} + + team := model.Team{} + + if err := s.GetReplica().SelectOne(&team, "SELECT * FROM Teams WHERE Id = :InviteId OR InviteId = :InviteId", map[string]interface{}{"InviteId": inviteId}); err != nil { + result.Err = model.NewAppError("SqlTeamStore.GetByInviteId", "We couldn't find the existing team", "inviteId="+inviteId+", "+err.Error()) + } + + if len(team.InviteId) == 0 { + team.InviteId = team.Id + } + + if len(inviteId) == 0 || team.InviteId != inviteId { + result.Err = model.NewAppError("SqlTeamStore.GetByInviteId", "We couldn't find the existing team", "inviteId="+inviteId) + } + + result.Data = &team + + storeChannel <- result + close(storeChannel) + }() + + return storeChannel +} + func (s SqlTeamStore) GetByName(name string) StoreChannel { storeChannel := make(StoreChannel) @@ -169,6 +209,10 @@ func (s SqlTeamStore) GetByName(name string) StoreChannel { result.Err = model.NewAppError("SqlTeamStore.GetByName", "We couldn't find the existing team", "name="+name+", "+err.Error()) } + if len(team.InviteId) == 0 { + team.InviteId = team.Id + } + result.Data = &team storeChannel <- result @@ -186,7 +230,13 @@ func (s SqlTeamStore) GetTeamsForEmail(email string) StoreChannel { var data []*model.Team if _, err := s.GetReplica().Select(&data, "SELECT Teams.* FROM Teams, Users WHERE Teams.Id = Users.TeamId AND Users.Email = :Email", map[string]interface{}{"Email": email}); err != nil { - result.Err = model.NewAppError("SqlTeamStore.GetTeamsForEmail", "We encounted a problem when looking up teams", "email="+email+", "+err.Error()) + result.Err = model.NewAppError("SqlTeamStore.GetTeamsForEmail", "We encountered a problem when looking up teams", "email="+email+", "+err.Error()) + } + + for _, team := range data { + if len(team.InviteId) == 0 { + team.InviteId = team.Id + } } result.Data = data @@ -209,6 +259,44 @@ func (s SqlTeamStore) GetAll() StoreChannel { result.Err = model.NewAppError("SqlTeamStore.GetAllTeams", "We could not get all teams", err.Error()) } + for _, team := range data { + if len(team.InviteId) == 0 { + team.InviteId = team.Id + } + } + + result.Data = data + + storeChannel <- result + close(storeChannel) + }() + + return storeChannel +} + +func (s SqlTeamStore) GetAllTeamListing() StoreChannel { + storeChannel := make(StoreChannel) + + go func() { + result := StoreResult{} + + query := "SELECT * FROM Teams WHERE AllowTeamListing = 1" + + if utils.Cfg.SqlSettings.DriverName == model.DATABASE_DRIVER_POSTGRES { + query = "SELECT * FROM Teams WHERE AllowTeamListing = true" + } + + var data []*model.Team + if _, err := s.GetReplica().Select(&data, query); err != nil { + result.Err = model.NewAppError("SqlTeamStore.GetAllTeams", "We could not get all teams", err.Error()) + } + + for _, team := range data { + if len(team.InviteId) == 0 { + team.InviteId = team.Id + } + } + result.Data = data storeChannel <- result diff --git a/store/sql_team_store_test.go b/store/sql_team_store_test.go index 3d9b4d435..71740f7e7 100644 --- a/store/sql_team_store_test.go +++ b/store/sql_team_store_test.go @@ -132,6 +132,54 @@ func TestTeamStoreGetByName(t *testing.T) { } } +func TestTeamStoreGetByIniviteId(t *testing.T) { + Setup() + + o1 := model.Team{} + o1.DisplayName = "DisplayName" + o1.Name = "a" + model.NewId() + "b" + o1.Email = model.NewId() + "@nowhere.com" + o1.Type = model.TEAM_OPEN + o1.InviteId = model.NewId() + + if err := (<-store.Team().Save(&o1)).Err; err != nil { + t.Fatal(err) + } + + o2 := model.Team{} + o2.DisplayName = "DisplayName" + o2.Name = "a" + model.NewId() + "b" + o2.Email = model.NewId() + "@nowhere.com" + o2.Type = model.TEAM_OPEN + + if err := (<-store.Team().Save(&o2)).Err; err != nil { + t.Fatal(err) + } + + if r1 := <-store.Team().GetByInviteId(o1.InviteId); r1.Err != nil { + t.Fatal(r1.Err) + } else { + if r1.Data.(*model.Team).ToJson() != o1.ToJson() { + t.Fatal("invalid returned team") + } + } + + o2.InviteId = "" + <-store.Team().Update(&o2) + + if r1 := <-store.Team().GetByInviteId(o2.Id); r1.Err != nil { + t.Fatal(r1.Err) + } else { + if r1.Data.(*model.Team).Id != o2.Id { + t.Fatal("invalid returned team") + } + } + + if err := (<-store.Team().GetByInviteId("")).Err; err == nil { + t.Fatal("Missing id should have failed") + } +} + func TestTeamStoreGetForEmail(t *testing.T) { Setup() @@ -161,3 +209,32 @@ func TestTeamStoreGetForEmail(t *testing.T) { t.Fatal(r1.Err) } } + +func TestAllTeamListing(t *testing.T) { + Setup() + + o1 := model.Team{} + o1.DisplayName = "DisplayName" + o1.Name = "a" + model.NewId() + "b" + o1.Email = model.NewId() + "@nowhere.com" + o1.Type = model.TEAM_OPEN + o1.AllowTeamListing = true + Must(store.Team().Save(&o1)) + + o2 := model.Team{} + o2.DisplayName = "DisplayName" + o2.Name = "a" + model.NewId() + "b" + o2.Email = model.NewId() + "@nowhere.com" + o2.Type = model.TEAM_OPEN + Must(store.Team().Save(&o2)) + + if r1 := <-store.Team().GetAllTeamListing(); r1.Err != nil { + t.Fatal(r1.Err) + } else { + teams := r1.Data.([]*model.Team) + + if len(teams) == 0 { + t.Fatal("failed team listing") + } + } +} diff --git a/store/sql_user_store.go b/store/sql_user_store.go index 5fab38ace..3347df08b 100644 --- a/store/sql_user_store.go +++ b/store/sql_user_store.go @@ -41,7 +41,7 @@ func NewSqlUserStore(sqlStore *SqlStore) UserStore { } func (us SqlUserStore) UpgradeSchemaIfNeeded() { - // REMOVE in 1.2 + // REMOVE AFTER 1.2 SHIP see PLT-828 us.CreateColumnIfNotExists("Users", "ThemeProps", "varchar(2000)", "character varying(2000)", "{}") } @@ -118,7 +118,7 @@ func (us SqlUserStore) Update(user *model.User, allowActiveUpdate bool) StoreCha } if oldUserResult, err := us.GetMaster().Get(model.User{}, user.Id); err != nil { - result.Err = model.NewAppError("SqlUserStore.Update", "We encounted an error finding the account", "user_id="+user.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlUserStore.Update", "We encountered an error finding the account", "user_id="+user.Id+", "+err.Error()) } else if oldUserResult == nil { result.Err = model.NewAppError("SqlUserStore.Update", "We couldn't find the existing account to update", "user_id="+user.Id) } else { @@ -161,7 +161,7 @@ func (us SqlUserStore) Update(user *model.User, allowActiveUpdate bool) StoreCha } else if IsUniqueConstraintError(err.Error(), "Username", "users_username_teamid_key") { result.Err = model.NewAppError("SqlUserStore.Update", "This username is already taken. Please choose another.", "user_id="+user.Id+", "+err.Error()) } else { - result.Err = model.NewAppError("SqlUserStore.Update", "We encounted an error updating the account", "user_id="+user.Id+", "+err.Error()) + result.Err = model.NewAppError("SqlUserStore.Update", "We encountered an error updating the account", "user_id="+user.Id+", "+err.Error()) } } else if count != 1 { result.Err = model.NewAppError("SqlUserStore.Update", "We couldn't update the account", fmt.Sprintf("user_id=%v, count=%v", user.Id, count)) @@ -306,7 +306,7 @@ func (us SqlUserStore) Get(id string) StoreChannel { result := StoreResult{} if obj, err := us.GetReplica().Get(model.User{}, id); err != nil { - result.Err = model.NewAppError("SqlUserStore.Get", "We encounted an error finding the account", "user_id="+id+", "+err.Error()) + result.Err = model.NewAppError("SqlUserStore.Get", "We encountered an error finding the account", "user_id="+id+", "+err.Error()) } else if obj == nil { result.Err = model.NewAppError("SqlUserStore.Get", "We couldn't find the existing account", "user_id="+id) } else { @@ -351,7 +351,7 @@ func (us SqlUserStore) GetProfiles(teamId string) StoreChannel { var users []*model.User if _, err := us.GetReplica().Select(&users, "SELECT * FROM Users WHERE TeamId = :TeamId", map[string]interface{}{"TeamId": teamId}); err != nil { - result.Err = model.NewAppError("SqlUserStore.GetProfiles", "We encounted an error while finding user profiles", err.Error()) + result.Err = model.NewAppError("SqlUserStore.GetProfiles", "We encountered an error while finding user profiles", err.Error()) } else { userMap := make(map[string]*model.User) @@ -382,7 +382,7 @@ func (us SqlUserStore) GetSystemAdminProfiles() StoreChannel { var users []*model.User if _, err := us.GetReplica().Select(&users, "SELECT * FROM Users WHERE Roles = :Roles", map[string]interface{}{"Roles": "system_admin"}); err != nil { - result.Err = model.NewAppError("SqlUserStore.GetSystemAdminProfiles", "We encounted an error while finding user profiles", err.Error()) + result.Err = model.NewAppError("SqlUserStore.GetSystemAdminProfiles", "We encountered an error while finding user profiles", err.Error()) } else { userMap := make(map[string]*model.User) @@ -498,7 +498,7 @@ func (us SqlUserStore) GetForExport(teamId string) StoreChannel { var users []*model.User if _, err := us.GetReplica().Select(&users, "SELECT * FROM Users WHERE TeamId = :TeamId", map[string]interface{}{"TeamId": teamId}); err != nil { - result.Err = model.NewAppError("SqlUserStore.GetProfiles", "We encounted an error while finding user profiles", err.Error()) + result.Err = model.NewAppError("SqlUserStore.GetProfiles", "We encountered an error while finding user profiles", err.Error()) } else { for _, u := range users { u.Password = "" diff --git a/store/store.go b/store/store.go index bd2c3681e..53a6e053b 100644 --- a/store/store.go +++ b/store/store.go @@ -50,6 +50,8 @@ type TeamStore interface { GetByName(name string) StoreChannel GetTeamsForEmail(domain string) StoreChannel GetAll() StoreChannel + GetAllTeamListing() StoreChannel + GetByInviteId(inviteId string) StoreChannel } type ChannelStore interface { @@ -75,6 +77,7 @@ type ChannelStore interface { CheckPermissionsToByName(teamId string, channelName string, userId string) StoreChannel UpdateLastViewedAt(channelId string, userId string) StoreChannel IncrementMentionCount(channelId string, userId string) StoreChannel + AnalyticsTypeCount(teamId string, channelType string) StoreChannel } type PostStore interface { @@ -87,6 +90,9 @@ type PostStore interface { GetEtag(channelId string) StoreChannel Search(teamId string, userId string, params *model.SearchParams) StoreChannel GetForExport(channelId string) StoreChannel + AnalyticsUserCountsWithPostsByDay(teamId string) StoreChannel + AnalyticsPostCountsByDay(teamId string) StoreChannel + AnalyticsPostCount(teamId string) StoreChannel } type UserStore interface { |