Exchange multiuser restore and backup tests (#1195)
## Description Basic smoke tests to ensure multi-user restore and backup work properly. Will need updated to add OneDrive tests later on once the OneDrive test pattern is merged ## Type of change <!--- Please check the type of change your PR introduces: ---> - [ ] 🌻 Feature - [ ] 🐛 Bugfix - [ ] 🗺️ Documentation - [x] 🤖 Test - [ ] 💻 CI/Deployment - [ ] 🐹 Trivial/Minor ## Issue(s) * #913 merge after * #1186 ## Test Plan <!-- How will this be tested prior to merging.--> - [ ] 💪 Manual - [x] ⚡ Unit test - [ ] 💚 E2E
This commit is contained in:
parent
7c027564c1
commit
14bd16f978
@ -4,6 +4,7 @@ import (
|
|||||||
"bytes"
|
"bytes"
|
||||||
"context"
|
"context"
|
||||||
"testing"
|
"testing"
|
||||||
|
"time"
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
@ -469,6 +470,89 @@ func (suite *GraphConnectorIntegrationSuite) TestEmptyCollections() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func runRestoreBackupTest(
|
||||||
|
t *testing.T,
|
||||||
|
test restoreBackupInfo,
|
||||||
|
tenant string,
|
||||||
|
users []string,
|
||||||
|
) {
|
||||||
|
var (
|
||||||
|
collections []data.Collection
|
||||||
|
expectedData = map[string]map[string][]byte{}
|
||||||
|
totalItems = 0
|
||||||
|
// Get a dest per test so they're independent.
|
||||||
|
dest = tester.DefaultTestRestoreDestination()
|
||||||
|
)
|
||||||
|
|
||||||
|
ctx, flush := tester.NewContext()
|
||||||
|
defer flush()
|
||||||
|
|
||||||
|
for _, user := range users {
|
||||||
|
numItems, userCollections, userExpectedData := collectionsForInfo(
|
||||||
|
t,
|
||||||
|
test.service,
|
||||||
|
tenant,
|
||||||
|
user,
|
||||||
|
dest,
|
||||||
|
test.collections,
|
||||||
|
)
|
||||||
|
|
||||||
|
collections = append(collections, userCollections...)
|
||||||
|
totalItems += numItems
|
||||||
|
|
||||||
|
for k, v := range userExpectedData {
|
||||||
|
expectedData[k] = v
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
t.Logf(
|
||||||
|
"Restoring collections to %s for user(s) %v\n",
|
||||||
|
dest.ContainerName,
|
||||||
|
users,
|
||||||
|
)
|
||||||
|
|
||||||
|
start := time.Now()
|
||||||
|
|
||||||
|
restoreGC := loadConnector(ctx, t)
|
||||||
|
restoreSel := getSelectorWith(test.service)
|
||||||
|
deets, err := restoreGC.RestoreDataCollections(ctx, restoreSel, dest, collections)
|
||||||
|
require.NoError(t, err)
|
||||||
|
assert.NotNil(t, deets)
|
||||||
|
|
||||||
|
status := restoreGC.AwaitStatus()
|
||||||
|
runTime := time.Now().Sub(start)
|
||||||
|
|
||||||
|
assert.Equal(t, totalItems, status.ObjectCount, "status.ObjectCount")
|
||||||
|
assert.Equal(t, totalItems, status.Successful, "status.Successful")
|
||||||
|
assert.Len(
|
||||||
|
t,
|
||||||
|
deets.Entries,
|
||||||
|
totalItems,
|
||||||
|
"details entries contains same item count as total successful items restored")
|
||||||
|
|
||||||
|
t.Logf("Restore complete in %v\n", runTime)
|
||||||
|
|
||||||
|
// Run a backup and compare its output with what we put in.
|
||||||
|
|
||||||
|
backupGC := loadConnector(ctx, t)
|
||||||
|
backupSel := backupSelectorForExpected(t, expectedData)
|
||||||
|
t.Logf("Selective backup of %s\n", backupSel)
|
||||||
|
|
||||||
|
start = time.Now()
|
||||||
|
dcs, err := backupGC.DataCollections(ctx, backupSel)
|
||||||
|
require.NoError(t, err)
|
||||||
|
|
||||||
|
t.Logf("Backup enumeration complete in %v\n", time.Now().Sub(start))
|
||||||
|
|
||||||
|
// Pull the data prior to waiting for the status as otherwise it will
|
||||||
|
// deadlock.
|
||||||
|
checkCollections(t, totalItems, expectedData, dcs)
|
||||||
|
|
||||||
|
status = backupGC.AwaitStatus()
|
||||||
|
assert.Equal(t, totalItems, status.ObjectCount, "status.ObjectCount")
|
||||||
|
assert.Equal(t, totalItems, status.Successful, "status.Successful")
|
||||||
|
}
|
||||||
|
|
||||||
func (suite *GraphConnectorIntegrationSuite) TestRestoreAndBackup() {
|
func (suite *GraphConnectorIntegrationSuite) TestRestoreAndBackup() {
|
||||||
bodyText := "This email has some text. However, all the text is on the same line."
|
bodyText := "This email has some text. However, all the text is on the same line."
|
||||||
subjectText := "Test message for restore"
|
subjectText := "Test message for restore"
|
||||||
@ -689,56 +773,7 @@ func (suite *GraphConnectorIntegrationSuite) TestRestoreAndBackup() {
|
|||||||
|
|
||||||
for _, test := range table {
|
for _, test := range table {
|
||||||
suite.T().Run(test.name, func(t *testing.T) {
|
suite.T().Run(test.name, func(t *testing.T) {
|
||||||
ctx, flush := tester.NewContext()
|
runRestoreBackupTest(t, test, suite.connector.tenant, []string{suite.user})
|
||||||
defer flush()
|
|
||||||
|
|
||||||
// Get a dest per test so they're independent.
|
|
||||||
dest := tester.DefaultTestRestoreDestination()
|
|
||||||
|
|
||||||
totalItems, collections, expectedData := collectionsForInfo(
|
|
||||||
t,
|
|
||||||
test.service,
|
|
||||||
suite.connector.tenant,
|
|
||||||
suite.user,
|
|
||||||
dest,
|
|
||||||
test.collections,
|
|
||||||
)
|
|
||||||
|
|
||||||
t.Logf("Restoring collections to %s\n", dest.ContainerName)
|
|
||||||
|
|
||||||
restoreGC := loadConnector(ctx, t)
|
|
||||||
restoreSel := getSelectorWith(test.service)
|
|
||||||
deets, err := restoreGC.RestoreDataCollections(ctx, restoreSel, dest, collections)
|
|
||||||
require.NoError(t, err)
|
|
||||||
assert.NotNil(t, deets)
|
|
||||||
|
|
||||||
status := restoreGC.AwaitStatus()
|
|
||||||
assert.Equal(t, totalItems, status.ObjectCount, "status.ObjectCount")
|
|
||||||
assert.Equal(t, totalItems, status.Successful, "status.Successful")
|
|
||||||
assert.Equal(
|
|
||||||
t, totalItems, len(deets.Entries),
|
|
||||||
"details entries contains same item count as total successful items restored")
|
|
||||||
|
|
||||||
t.Logf("Restore complete\n")
|
|
||||||
|
|
||||||
// Run a backup and compare its output with what we put in.
|
|
||||||
|
|
||||||
backupGC := loadConnector(ctx, t)
|
|
||||||
backupSel := backupSelectorForExpected(t, expectedData)
|
|
||||||
t.Logf("Selective backup of %s\n", backupSel)
|
|
||||||
|
|
||||||
dcs, err := backupGC.DataCollections(ctx, backupSel)
|
|
||||||
require.NoError(t, err)
|
|
||||||
|
|
||||||
t.Logf("Backup enumeration complete\n")
|
|
||||||
|
|
||||||
// Pull the data prior to waiting for the status as otherwise it will
|
|
||||||
// deadlock.
|
|
||||||
checkCollections(t, totalItems, expectedData, dcs)
|
|
||||||
|
|
||||||
status = backupGC.AwaitStatus()
|
|
||||||
assert.Equal(t, totalItems, status.ObjectCount, "status.ObjectCount")
|
|
||||||
assert.Equal(t, totalItems, status.Successful, "status.Successful")
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -876,3 +911,113 @@ func (suite *GraphConnectorIntegrationSuite) TestMultiFolderBackupDifferentNames
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (suite *GraphConnectorIntegrationSuite) TestMultiuserRestoreAndBackup() {
|
||||||
|
bodyText := "This email has some text. However, all the text is on the same line."
|
||||||
|
subjectText := "Test message for restore"
|
||||||
|
|
||||||
|
users := []string{
|
||||||
|
suite.user,
|
||||||
|
tester.SecondaryM365UserID(suite.T()),
|
||||||
|
}
|
||||||
|
table := []restoreBackupInfo{
|
||||||
|
{
|
||||||
|
name: "Email",
|
||||||
|
service: path.ExchangeService,
|
||||||
|
collections: []colInfo{
|
||||||
|
{
|
||||||
|
pathElements: []string{"Inbox"},
|
||||||
|
category: path.EmailCategory,
|
||||||
|
items: []itemInfo{
|
||||||
|
{
|
||||||
|
name: "someencodeditemID",
|
||||||
|
data: mockconnector.GetMockMessageWithBodyBytes(
|
||||||
|
subjectText+"-1",
|
||||||
|
bodyText+" 1.",
|
||||||
|
bodyText+" 1.",
|
||||||
|
),
|
||||||
|
lookupKey: subjectText + "-1",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
pathElements: []string{"Archive"},
|
||||||
|
category: path.EmailCategory,
|
||||||
|
items: []itemInfo{
|
||||||
|
{
|
||||||
|
name: "someencodeditemID2",
|
||||||
|
data: mockconnector.GetMockMessageWithBodyBytes(
|
||||||
|
subjectText+"-2",
|
||||||
|
bodyText+" 2.",
|
||||||
|
bodyText+" 2.",
|
||||||
|
),
|
||||||
|
lookupKey: subjectText + "-2",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "Contacts",
|
||||||
|
service: path.ExchangeService,
|
||||||
|
collections: []colInfo{
|
||||||
|
{
|
||||||
|
pathElements: []string{"Work"},
|
||||||
|
category: path.ContactsCategory,
|
||||||
|
items: []itemInfo{
|
||||||
|
{
|
||||||
|
name: "someencodeditemID",
|
||||||
|
data: mockconnector.GetMockContactBytes("Ghimley"),
|
||||||
|
lookupKey: "Ghimley",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
pathElements: []string{"Personal"},
|
||||||
|
category: path.ContactsCategory,
|
||||||
|
items: []itemInfo{
|
||||||
|
{
|
||||||
|
name: "someencodeditemID2",
|
||||||
|
data: mockconnector.GetMockContactBytes("Irgot"),
|
||||||
|
lookupKey: "Irgot",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "Events",
|
||||||
|
service: path.ExchangeService,
|
||||||
|
collections: []colInfo{
|
||||||
|
{
|
||||||
|
pathElements: []string{"Work"},
|
||||||
|
category: path.EventsCategory,
|
||||||
|
items: []itemInfo{
|
||||||
|
{
|
||||||
|
name: "someencodeditemID",
|
||||||
|
data: mockconnector.GetMockEventWithSubjectBytes("Ghimley"),
|
||||||
|
lookupKey: "Ghimley",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
pathElements: []string{"Personal"},
|
||||||
|
category: path.EventsCategory,
|
||||||
|
items: []itemInfo{
|
||||||
|
{
|
||||||
|
name: "someencodeditemID2",
|
||||||
|
data: mockconnector.GetMockEventWithSubjectBytes("Irgot"),
|
||||||
|
lookupKey: "Irgot",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, test := range table {
|
||||||
|
suite.T().Run(test.name, func(t *testing.T) {
|
||||||
|
runRestoreBackupTest(t, test, suite.connector.tenant, users)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user