MM-43956: Adds post counts by duration. (#20131)
* MM-43956: Adds post counts by day. * MM-43956: Test data cleanup. Switch from Unix to UnixMilli. * MM-43956: Changes from selecting date data types to strings in SQL. * MM-43956: Fixes date format key. * MM-43956: Adds missing user id scope for 'my' top channels graph. * MM-43956: Adds the ability to group post counts by hour. * MM-43956: Require enterprise or professional license. Reject guests. * MM-43956: Adds license for tests. * MM-43956: Renames function. * MM-43956: Omits future hours from post counts by hour. * MM-43956: Adjust API response grouping to users timezone. * MM-43956: Adds translation. * MM-43956: Adds user's timezone to the data tier for the grouping by day and hour. * MM-43956: Fixes layers. * MM-43956: Lint fix. * MM-43956: Fix store layers. * MM-43956: Switches to default name for time package; changes parameter names to avoid naming conflict. * MM-43956: Updates mocks. Co-authored-by: Mattermod <mattermod@users.noreply.github.com>
Этот коммит содержится в:
коммит произвёл
GitHub
родитель
c03eb778c8
Коммит
182ae1234a
@@ -4297,3 +4297,53 @@ func (s SqlChannelStore) GetTopChannelsForUserSince(userID string, teamID string
|
||||
|
||||
return model.GetTopChannelListWithPagination(channels, limit), nil
|
||||
}
|
||||
|
||||
func (s SqlChannelStore) PostCountsByDuration(channelIDs []string, sinceUnixMillis int64, userID *string, duration model.PostCountGrouping, atLocation *time.Location) ([]*model.DurationPostCount, error) {
|
||||
var unixSelect string
|
||||
var propsQuery string
|
||||
loc := atLocation.String()
|
||||
if loc == "Local" {
|
||||
loc = "UTC"
|
||||
}
|
||||
if s.DriverName() == model.DatabaseDriverMysql {
|
||||
if duration == model.PostsByDay {
|
||||
unixSelect = `DATE_FORMAT(CONVERT_TZ(FROM_UNIXTIME(Posts.CreateAt / 1000), 'GMT', '` + loc + `'),'%Y-%m-%d') AS duration`
|
||||
} else {
|
||||
unixSelect = `DATE_FORMAT(CONVERT_TZ(FROM_UNIXTIME(Posts.CreateAt / 1000), 'GMT', '` + loc + `'),'%Y-%m-%dT%H') AS duration`
|
||||
}
|
||||
propsQuery = `(JSON_EXTRACT(Posts.Props, '$.from_bot') IS NULL OR JSON_EXTRACT(Posts.Props, '$.from_bot') = 'false')`
|
||||
} else if s.DriverName() == model.DatabaseDriverPostgres {
|
||||
if duration == model.PostsByDay {
|
||||
unixSelect = fmt.Sprintf(`TO_CHAR(TO_TIMESTAMP(Posts.CreateAt / 1000) AT TIME ZONE '%s', 'YYYY-MM-DD') AS duration`, loc)
|
||||
} else {
|
||||
unixSelect = fmt.Sprintf(`TO_CHAR(TO_TIMESTAMP(Posts.CreateAt / 1000) AT TIME ZONE '%s', 'YYYY-MM-DD"T"HH24') AS duration`, loc)
|
||||
}
|
||||
propsQuery = `(Posts.Props ->> 'from_bot' IS NULL OR Posts.Props ->> 'from_bot' = 'false')`
|
||||
}
|
||||
query := sq.
|
||||
Select("Posts.ChannelId AS channelid", unixSelect, "count(Posts.Id) AS postcount").
|
||||
From("Posts").
|
||||
LeftJoin("Channels ON Posts.ChannelId = Channels.Id").
|
||||
Where(sq.And{
|
||||
sq.Eq{"Posts.DeleteAt": 0},
|
||||
sq.Gt{"Posts.CreateAt": sinceUnixMillis},
|
||||
sq.Eq{"Posts.Type": ""},
|
||||
sq.Eq{"Channels.Id": channelIDs},
|
||||
}).
|
||||
Where(propsQuery).
|
||||
GroupBy("channelid", "duration").
|
||||
OrderBy("channelid", "duration")
|
||||
if userID != nil && model.IsValidId(*userID) {
|
||||
query = query.Where(sq.And{sq.Eq{"Posts.UserId": *userID}})
|
||||
}
|
||||
queryString, args, err := query.ToSql()
|
||||
if err != nil {
|
||||
return nil, errors.Wrap(err, "failed to parse query")
|
||||
}
|
||||
dailyPostCounts := make([]*model.DurationPostCount, 0)
|
||||
if err := s.GetReplicaX().Select(&dailyPostCounts, queryString, args...); err != nil {
|
||||
return nil, errors.Wrap(err, "failed to get post counts by duration")
|
||||
}
|
||||
|
||||
return dailyPostCounts, nil
|
||||
}
|
||||
|
||||
Ссылка в новой задаче
Block a user