Fix restore backup tests (#4407)

Exchange tests inadvertently got disabled since
it wasn't finding path matches for returned
BackupCollections. This switches to using
LocationPath which does allow for matching

Most contacts tests are disabled since restore
doesn't support nested folders

---

#### Does this PR need a docs update or release note?

- [ ]  Yes, it's included
- [ ] 🕐 Yes, but in a later PR
- [ ]  No

#### Type of change

- [ ] 🌻 Feature
- [x] 🐛 Bugfix
- [ ] 🗺️ Documentation
- [x] 🤖 Supportability/Tests
- [ ] 💻 CI/Deployment
- [ ] 🧹 Tech Debt/Cleanup

#### Test Plan

- [x] 💪 Manual
- [ ]  Unit test
- [ ] 💚 E2E
This commit is contained in:
ashmrtn 2023-09-29 11:08:08 -07:00 committed by GitHub
parent 2fe0e8643e
commit 8e080f83b7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 134 additions and 121 deletions

View File

@ -458,9 +458,8 @@ func (suite *SPCollectionIntgSuite) TestCreateSharePointCollection_Lists() {
for item := range collection.Items(ctx, fault.New(true)) { for item := range collection.Items(ctx, fault.New(true)) {
t.Log("File: " + item.ID()) t.Log("File: " + item.ID())
bs, err := io.ReadAll(item.ToReader()) _, err := io.ReadAll(item.ToReader())
require.NoError(t, err, clues.ToCore(err)) require.NoError(t, err, clues.ToCore(err))
t.Log(string(bs))
} }
} }
} }

View File

@ -861,7 +861,7 @@ func (suite *ControllerIntegrationSuite) TestRestoreAndBackup_core() {
}, },
}, },
{ {
name: "MultipleContactsSingleFolder", name: "MultipleContactsInRestoreFolder",
service: path.ExchangeService, service: path.ExchangeService,
collections: []stub.ColInfo{ collections: []stub.ColInfo{
{ {
@ -887,49 +887,77 @@ func (suite *ControllerIntegrationSuite) TestRestoreAndBackup_core() {
}, },
}, },
}, },
{ // TODO(ashmrtn): Re-enable when we can restore contacts to nested folders.
name: "MultipleContactsMultipleFolders", //{
service: path.ExchangeService, // name: "MultipleContactsSingleFolder",
collections: []stub.ColInfo{ // service: path.ExchangeService,
{ // collections: []stub.ColInfo{
PathElements: []string{"Work"}, // {
Category: path.ContactsCategory, // PathElements: []string{"Contacts"},
Items: []stub.ItemInfo{ // Category: path.ContactsCategory,
{ // Items: []stub.ItemInfo{
Name: "someencodeditemID", // {
Data: exchMock.ContactBytes("Ghimley"), // Name: "someencodeditemID",
LookupKey: "Ghimley", // Data: exchMock.ContactBytes("Ghimley"),
}, // LookupKey: "Ghimley",
{ // },
Name: "someencodeditemID2", // {
Data: exchMock.ContactBytes("Irgot"), // Name: "someencodeditemID2",
LookupKey: "Irgot", // Data: exchMock.ContactBytes("Irgot"),
}, // LookupKey: "Irgot",
{ // },
Name: "someencodeditemID3", // {
Data: exchMock.ContactBytes("Jannes"), // Name: "someencodeditemID3",
LookupKey: "Jannes", // Data: exchMock.ContactBytes("Jannes"),
}, // LookupKey: "Jannes",
}, // },
}, // },
{ // },
PathElements: []string{"Personal"}, // },
Category: path.ContactsCategory, //},
Items: []stub.ItemInfo{ //{
{ // name: "MultipleContactsMultipleFolders",
Name: "someencodeditemID4", // service: path.ExchangeService,
Data: exchMock.ContactBytes("Argon"), // collections: []stub.ColInfo{
LookupKey: "Argon", // {
}, // PathElements: []string{"Work"},
{ // Category: path.ContactsCategory,
Name: "someencodeditemID5", // Items: []stub.ItemInfo{
Data: exchMock.ContactBytes("Bernard"), // {
LookupKey: "Bernard", // Name: "someencodeditemID",
}, // Data: exchMock.ContactBytes("Ghimley"),
}, // LookupKey: "Ghimley",
}, // },
}, // {
}, // Name: "someencodeditemID2",
// Data: exchMock.ContactBytes("Irgot"),
// LookupKey: "Irgot",
// },
// {
// Name: "someencodeditemID3",
// Data: exchMock.ContactBytes("Jannes"),
// LookupKey: "Jannes",
// },
// },
// },
// {
// PathElements: []string{"Personal"},
// Category: path.ContactsCategory,
// Items: []stub.ItemInfo{
// {
// Name: "someencodeditemID4",
// Data: exchMock.ContactBytes("Argon"),
// LookupKey: "Argon",
// },
// {
// Name: "someencodeditemID5",
// Data: exchMock.ContactBytes("Bernard"),
// LookupKey: "Bernard",
// },
// },
// },
// },
//},
// { // {
// name: "MultipleEventsSingleCalendar", // name: "MultipleEventsSingleCalendar",
// service: path.ExchangeService, // service: path.ExchangeService,
@ -1017,34 +1045,35 @@ func (suite *ControllerIntegrationSuite) TestRestoreAndBackup_core() {
func (suite *ControllerIntegrationSuite) TestMultiFolderBackupDifferentNames() { func (suite *ControllerIntegrationSuite) TestMultiFolderBackupDifferentNames() {
table := []restoreBackupInfo{ table := []restoreBackupInfo{
{ // TODO(ashmrtn): Re-enable when we can restore contacts to nested folders.
name: "Contacts", //{
service: path.ExchangeService, // name: "Contacts",
collections: []stub.ColInfo{ // service: path.ExchangeService,
{ // collections: []stub.ColInfo{
PathElements: []string{"Work"}, // {
Category: path.ContactsCategory, // PathElements: []string{"Work"},
Items: []stub.ItemInfo{ // Category: path.ContactsCategory,
{ // Items: []stub.ItemInfo{
Name: "someencodeditemID", // {
Data: exchMock.ContactBytes("Ghimley"), // Name: "someencodeditemID",
LookupKey: "Ghimley", // Data: exchMock.ContactBytes("Ghimley"),
}, // LookupKey: "Ghimley",
}, // },
}, // },
{ // },
PathElements: []string{"Personal"}, // {
Category: path.ContactsCategory, // PathElements: []string{"Personal"},
Items: []stub.ItemInfo{ // Category: path.ContactsCategory,
{ // Items: []stub.ItemInfo{
Name: "someencodeditemID2", // {
Data: exchMock.ContactBytes("Irgot"), // Name: "someencodeditemID2",
LookupKey: "Irgot", // Data: exchMock.ContactBytes("Irgot"),
}, // LookupKey: "Irgot",
}, // },
}, // },
}, // },
}, // },
//},
// { // {
// name: "Events", // name: "Events",
// service: path.ExchangeService, // service: path.ExchangeService,

View File

@ -919,30 +919,9 @@ func checkHasCollections(
continue continue
} }
fp := g.FullPath()
loc := g.(data.LocationPather).LocationPath() loc := g.(data.LocationPather).LocationPath()
if fp.Service() == path.OneDriveService || gotNames = append(gotNames, loc.String())
(fp.Service() == path.SharePointService && fp.Category() == path.LibrariesCategory) {
dp, err := path.ToDrivePath(fp)
if !assert.NoError(t, err, clues.ToCore(err)) {
continue
}
loc = path.BuildDriveLocation(dp.DriveID, loc.Elements()...)
}
p, err := loc.ToDataLayerPath(
fp.Tenant(),
fp.ProtectedResource(),
fp.Service(),
fp.Category(),
false)
if !assert.NoError(t, err, clues.ToCore(err)) {
continue
}
gotNames = append(gotNames, p.String())
} }
assert.ElementsMatch(t, expectedNames, gotNames, "returned collections") assert.ElementsMatch(t, expectedNames, gotNames, "returned collections")
@ -963,14 +942,18 @@ func checkCollections(
for _, returned := range got { for _, returned := range got {
var ( var (
hasItems bool expectedColDataByLoc map[string][]byte
service = returned.FullPath().Service() hasItems bool
category = returned.FullPath().Category() service = returned.FullPath().Service()
expectedColData = expected[returned.FullPath().String()] category = returned.FullPath().Category()
folders = returned.FullPath().Elements() folders = returned.FullPath().Elements()
rootDir = folders[len(folders)-1] == mci.RestoreCfg.Location rootDir = folders[len(folders)-1] == mci.RestoreCfg.Location
) )
if p, ok := returned.(data.LocationPather); ok {
expectedColDataByLoc = expected[p.LocationPath().String()]
}
// Need to iterate through all items even if we don't expect to find a match // Need to iterate through all items even if we don't expect to find a match
// because otherwise we'll deadlock waiting for the status. Unexpected or // because otherwise we'll deadlock waiting for the status. Unexpected or
// missing collection paths will be reported by checkHasCollections. // missing collection paths will be reported by checkHasCollections.
@ -990,14 +973,14 @@ func checkCollections(
hasItems = true hasItems = true
gotItems++ gotItems++
if expectedColData == nil { if expectedColDataByLoc == nil {
continue continue
} }
if !compareItem( if !compareItem(
t, t,
returned.FullPath(), returned.FullPath(),
expectedColData, expectedColDataByLoc,
service, service,
category, category,
item, item,

View File

@ -4,6 +4,7 @@ import (
"bytes" "bytes"
"io" "io"
"github.com/alcionai/clues"
"golang.org/x/exp/maps" "golang.org/x/exp/maps"
"github.com/alcionai/corso/src/internal/data" "github.com/alcionai/corso/src/internal/data"
@ -163,28 +164,29 @@ func CollectionsForInfo(
func backupOutputPathFromRestore( func backupOutputPathFromRestore(
restoreCfg control.RestoreConfig, restoreCfg control.RestoreConfig,
inputPath path.Path, inputPath path.Path,
) (path.Path, error) { ) (*path.Builder, error) {
base := []string{restoreCfg.Location} base := []string{restoreCfg.Location}
folders := inputPath.Folders()
switch inputPath.Service() {
// OneDrive has leading information like the drive ID. // OneDrive has leading information like the drive ID.
if inputPath.Service() == path.OneDriveService || inputPath.Service() == path.SharePointService { case path.OneDriveService, path.SharePointService:
folders := inputPath.Folders() p, err := path.ToDrivePath(inputPath)
base = append(append([]string{}, folders[:3]...), restoreCfg.Location) if err != nil {
return nil, clues.Stack(err)
}
if len(folders) > 3 { // Remove driveID, root, etc.
base = append(base, folders[3:]...) folders = p.Folders
// Re-add root, but it needs to be in front of the restore folder.
base = append([]string{p.Root}, base...)
// Currently contacts restore doesn't have nested folders.
case path.ExchangeService:
if inputPath.Category() == path.ContactsCategory {
folders = nil
} }
} }
if inputPath.Service() == path.ExchangeService && inputPath.Category() == path.EmailCategory { return path.Builder{}.Append(append(base, folders...)...), nil
base = append(base, inputPath.Folders()...)
}
return path.Build(
inputPath.Tenant(),
inputPath.ProtectedResource(),
inputPath.Service(),
inputPath.Category(),
false,
base...)
} }