MM-64531: [Shared Channels] Users on different remote servers should not communicate unless the remotes have established secure connection. (#30985) (#33434)
Automatic Merge
Этот коммит содержится в:
коммит произвёл
GitHub
родитель
3a6aeee57e
Коммит
07a34f02b6
@@ -28,6 +28,7 @@ type SharedChannelServiceIFace interface {
|
||||
CheckChannelIsShared(channelID string) error
|
||||
CheckCanInviteToSharedChannel(channelId string) error
|
||||
HandleMembershipChange(channelID, userID string, isAdd bool, remoteID string)
|
||||
IsRemoteClusterDirectlyConnected(remoteId string) bool
|
||||
TransformMentionsOnReceiveForTesting(ctx request.CTX, post *model.Post, targetChannel *model.Channel, rc *model.RemoteCluster, mentionTransforms map[string]string)
|
||||
}
|
||||
|
||||
@@ -100,3 +101,11 @@ func (mrcs *mockSharedChannelService) HandleMembershipChange(channelID, userID s
|
||||
mrcs.SharedChannelServiceIFace.HandleMembershipChange(channelID, userID, isAdd, remoteID)
|
||||
}
|
||||
}
|
||||
|
||||
func (mrcs *mockSharedChannelService) IsRemoteClusterDirectlyConnected(remoteId string) bool {
|
||||
if mrcs.SharedChannelServiceIFace != nil {
|
||||
return mrcs.SharedChannelServiceIFace.IsRemoteClusterDirectlyConnected(remoteId)
|
||||
}
|
||||
// Default behavior for mock: Local server is always connected
|
||||
return remoteId == ""
|
||||
}
|
||||
|
||||
@@ -9,6 +9,7 @@ import (
|
||||
"database/sql"
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"testing"
|
||||
@@ -26,6 +27,7 @@ import (
|
||||
"github.com/mattermost/mattermost/server/v8/channels/utils/testutils"
|
||||
"github.com/mattermost/mattermost/server/v8/einterfaces"
|
||||
"github.com/mattermost/mattermost/server/v8/einterfaces/mocks"
|
||||
"github.com/mattermost/mattermost/server/v8/platform/services/sharedchannel"
|
||||
)
|
||||
|
||||
func TestCreateOAuthUser(t *testing.T) {
|
||||
@@ -2411,3 +2413,74 @@ func TestGetUsersForReporting(t *testing.T) {
|
||||
require.NotNil(t, userReports)
|
||||
})
|
||||
}
|
||||
|
||||
// Helper functions for remote user testing
|
||||
func setupRemoteClusterTest(t *testing.T) (*TestHelper, store.Store) {
|
||||
os.Setenv("MM_FEATUREFLAGS_ENABLESHAREDCHANNELSDMS", "true")
|
||||
t.Cleanup(func() { os.Unsetenv("MM_FEATUREFLAGS_ENABLESHAREDCHANNELSDMS") })
|
||||
th := setupSharedChannels(t).InitBasic()
|
||||
t.Cleanup(th.TearDown)
|
||||
return th, th.App.Srv().Store()
|
||||
}
|
||||
|
||||
func createTestRemoteCluster(t *testing.T, th *TestHelper, ss store.Store, name, siteURL string, confirmed bool) *model.RemoteCluster {
|
||||
cluster := &model.RemoteCluster{
|
||||
RemoteId: model.NewId(),
|
||||
Name: name,
|
||||
SiteURL: siteURL,
|
||||
CreateAt: model.GetMillis(),
|
||||
LastPingAt: model.GetMillis(),
|
||||
Token: model.NewId(),
|
||||
CreatorId: th.BasicUser.Id,
|
||||
}
|
||||
if confirmed {
|
||||
cluster.RemoteToken = model.NewId()
|
||||
}
|
||||
savedCluster, err := ss.RemoteCluster().Save(cluster)
|
||||
require.NoError(t, err)
|
||||
return savedCluster
|
||||
}
|
||||
|
||||
func createRemoteUser(t *testing.T, th *TestHelper, remoteCluster *model.RemoteCluster) *model.User {
|
||||
user := th.CreateUser()
|
||||
user.RemoteId = &remoteCluster.RemoteId
|
||||
updatedUser, appErr := th.App.UpdateUser(th.Context, user, false)
|
||||
require.Nil(t, appErr)
|
||||
return updatedUser
|
||||
}
|
||||
|
||||
func ensureRemoteClusterConnected(t *testing.T, ss store.Store, cluster *model.RemoteCluster, connected bool) {
|
||||
if connected {
|
||||
cluster.SiteURL = "https://example.com"
|
||||
cluster.RemoteToken = model.NewId()
|
||||
cluster.LastPingAt = model.GetMillis()
|
||||
} else {
|
||||
cluster.SiteURL = model.SiteURLPending + "example.com"
|
||||
cluster.RemoteToken = ""
|
||||
}
|
||||
_, err := ss.RemoteCluster().Update(cluster)
|
||||
require.NoError(t, err)
|
||||
}
|
||||
|
||||
// TestRemoteUserDirectChannelCreation tests direct channel creation with remote users
|
||||
func TestRemoteUserDirectChannelCreation(t *testing.T) {
|
||||
th, ss := setupRemoteClusterTest(t)
|
||||
|
||||
connectedRC := createTestRemoteCluster(t, th, ss, "connected-cluster", "https://example-connected.com", true)
|
||||
|
||||
user1 := createRemoteUser(t, th, connectedRC)
|
||||
|
||||
t.Run("Can create DM with user from connected remote", func(t *testing.T) {
|
||||
ensureRemoteClusterConnected(t, ss, connectedRC, true)
|
||||
|
||||
scs := th.App.Srv().GetSharedChannelSyncService()
|
||||
service, ok := scs.(*sharedchannel.Service)
|
||||
require.True(t, ok)
|
||||
require.True(t, service.IsRemoteClusterDirectlyConnected(connectedRC.RemoteId))
|
||||
|
||||
channel, appErr := th.App.GetOrCreateDirectChannel(th.Context, th.BasicUser.Id, user1.Id)
|
||||
assert.NotNil(t, channel)
|
||||
assert.Nil(t, appErr)
|
||||
assert.Equal(t, model.ChannelTypeDirect, channel.Type)
|
||||
})
|
||||
}
|
||||
|
||||
Ссылка в новой задаче
Block a user