MM-45317: global drafts endpoints and ws events (#20614)

* MM-23881: global drafts endpoints and ws events

Adds endpoints:
- create/update drafts
- delete draft
- get drafts

Adds WS events:
- draft_updated
- draft_created
- draft_deleted

* Ordering and WS event name fixes

* Adds PostID to the drafts table

In the future the drafts will include edited posts, this commit adds the
post id in the combined pkey of the table.

* Fixes route for deleting a thread draft

* Fixes failed checks

* Fixes migrations

* Fixes migration

* Extract translation strings

* Removes PostID since we won't sync editing posts

* Fixes tests

* Fixes i18n

* Update migrations for global drafts

* update branch with latest master changes

* Add feature flag for global drafts

* Set global drafts feature flag default to true

* Added support for files in drafts

* Fix failing i18n check

* Added support for deleting files in drafts

* Revert "Added support for deleting files in drafts"

This reverts commit 45dfd04a760359de2e8814d652c9ef46daf994f6.

* Triggering new test server

* Add config setting 'AllowSyncedDrafts' for syncing drafts with server

* Triggering new test server

* Triggering new test server

* Add guard for config setting and add initial tests

* Fix i18n and lint errors

* Triggering new test server

* Add tests for drafts

* fix lint issues

* Add tests for model/draft

* Triggering new test server

* Triggering new test server

* Trigger new test server

* Address PR comments

* Change left join to regular join in GetDraftsForUser

* Fix broken test

Maybe consider adding an inclDeleted field if we want to get deleted drafts in the future

* fix translations

* Add store tests for drafts

* fix test naming

* remove comment

* update migrations

* set feature flag default to false

* update migrations

Co-authored-by: Mylon Suren <mylonsuren@gmail.com>
Co-authored-by: Mattermod <mattermod@users.noreply.github.com>
Этот коммит содержится в:
Kyriakos Z
2022-11-24 05:21:40 +02:00
коммит произвёл GitHub
родитель 27db854089
Коммит 5e5769c4ee
33 изменённых файлов: 2575 добавлений и 0 удалений

13
store/storetest/draft_store.go Обычный файл
Просмотреть файл

@@ -0,0 +1,13 @@
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
package storetest
import (
"testing"
"github.com/mattermost/mattermost-server/v6/store"
)
func TestDraftStore(t *testing.T, ss store.Store, s SqlStore) {
}

121
store/storetest/mocks/DraftStore.go Обычный файл
Просмотреть файл

@@ -0,0 +1,121 @@
// Code generated by mockery v2.10.4. DO NOT EDIT.
// Regenerate this file using `make store-mocks`.
package mocks
import (
model "github.com/mattermost/mattermost-server/v6/model"
mock "github.com/stretchr/testify/mock"
)
// DraftStore is an autogenerated mock type for the DraftStore type
type DraftStore struct {
mock.Mock
}
// Delete provides a mock function with given fields: userID, channelID, rootID
func (_m *DraftStore) Delete(userID string, channelID string, rootID string) error {
ret := _m.Called(userID, channelID, rootID)
var r0 error
if rf, ok := ret.Get(0).(func(string, string, string) error); ok {
r0 = rf(userID, channelID, rootID)
} else {
r0 = ret.Error(0)
}
return r0
}
// Get provides a mock function with given fields: userID, channelID, rootID
func (_m *DraftStore) Get(userID string, channelID string, rootID string) (*model.Draft, error) {
ret := _m.Called(userID, channelID, rootID)
var r0 *model.Draft
if rf, ok := ret.Get(0).(func(string, string, string) *model.Draft); ok {
r0 = rf(userID, channelID, rootID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*model.Draft)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(string, string, string) error); ok {
r1 = rf(userID, channelID, rootID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// GetDraftsForUser provides a mock function with given fields: userID, teamID
func (_m *DraftStore) GetDraftsForUser(userID string, teamID string) ([]*model.Draft, error) {
ret := _m.Called(userID, teamID)
var r0 []*model.Draft
if rf, ok := ret.Get(0).(func(string, string) []*model.Draft); ok {
r0 = rf(userID, teamID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]*model.Draft)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(string, string) error); ok {
r1 = rf(userID, teamID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// Save provides a mock function with given fields: d
func (_m *DraftStore) Save(d *model.Draft) (*model.Draft, error) {
ret := _m.Called(d)
var r0 *model.Draft
if rf, ok := ret.Get(0).(func(*model.Draft) *model.Draft); ok {
r0 = rf(d)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*model.Draft)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(*model.Draft) error); ok {
r1 = rf(d)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// Update provides a mock function with given fields: d
func (_m *DraftStore) Update(d *model.Draft) (*model.Draft, error) {
ret := _m.Called(d)
var r0 *model.Draft
if rf, ok := ret.Get(0).(func(*model.Draft) *model.Draft); ok {
r0 = rf(d)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*model.Draft)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(*model.Draft) error); ok {
r1 = rf(d)
} else {
r1 = ret.Error(1)
}
return r0, r1
}

Просмотреть файл

@@ -187,6 +187,22 @@ func (_m *Store) Context() context.Context {
return r0
}
// Draft provides a mock function with given fields:
func (_m *Store) Draft() store.DraftStore {
ret := _m.Called()
var r0 store.DraftStore
if rf, ok := ret.Get(0).(func() store.DraftStore); ok {
r0 = rf()
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(store.DraftStore)
}
}
return r0
}
// DropAllTables provides a mock function with given fields:
func (_m *Store) DropAllTables() {
_m.Called()

Просмотреть файл

@@ -54,6 +54,7 @@ type Store struct {
LinkMetadataStore mocks.LinkMetadataStore
SharedChannelStore mocks.SharedChannelStore
ProductNoticesStore mocks.ProductNoticesStore
DraftStore mocks.DraftStore
context context.Context
NotifyAdminStore mocks.NotifyAdminStore
PostPriorityStore mocks.PostPriorityStore
@@ -95,6 +96,7 @@ func (s *Store) Role() store.RoleStore { return &s.R
func (s *Store) Scheme() store.SchemeStore { return &s.SchemeStore }
func (s *Store) TermsOfService() store.TermsOfServiceStore { return &s.TermsOfServiceStore }
func (s *Store) UserTermsOfService() store.UserTermsOfServiceStore { return &s.UserTermsOfServiceStore }
func (s *Store) Draft() store.DraftStore { return &s.DraftStore }
func (s *Store) ChannelMemberHistory() store.ChannelMemberHistoryStore {
return &s.ChannelMemberHistoryStore
}
@@ -163,6 +165,7 @@ func (s *Store) AssertExpectations(t mock.TestingT) bool {
&s.ThreadStore,
&s.ProductNoticesStore,
&s.SharedChannelStore,
&s.DraftStore,
&s.NotifyAdminStore,
&s.PostPriorityStore,
&s.PostAcknowledgementStore,