With onedrive storage file names being changed from the file display name to the file id, we need a more granular form of indentification when using selectors to choose which values count as matchable fields. This change modifies the selector PathValues to return slices of strings for each category instead of a single string, and the reducer matches on any. This will allow each service to decide what values are considered equivalent (id, shortRef, a value inside the info, etc) for each property. --- #### Does this PR need a docs update or release note? - [x] ⛔ No #### Type of change - [x] 🌻 Feature #### Issue(s) * #2708 #### Test Plan - [x] ⚡ Unit test
200 lines
4.8 KiB
Go
200 lines
4.8 KiB
Go
package selectors
|
|
|
|
import (
|
|
"strings"
|
|
"testing"
|
|
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/require"
|
|
|
|
"github.com/alcionai/corso/src/pkg/backup/details"
|
|
"github.com/alcionai/corso/src/pkg/filters"
|
|
"github.com/alcionai/corso/src/pkg/path"
|
|
)
|
|
|
|
// ---------------------------------------------------------------------------
|
|
// categorizers
|
|
// ---------------------------------------------------------------------------
|
|
|
|
// categorizer
|
|
type mockCategorizer string
|
|
|
|
const (
|
|
unknownCatStub mockCategorizer = ""
|
|
// wrap Exchange data here to get around path pkg assertions about path content.
|
|
rootCatStub mockCategorizer = mockCategorizer(ExchangeUser)
|
|
leafCatStub mockCategorizer = mockCategorizer(ExchangeEvent)
|
|
|
|
pathServiceStub = path.ExchangeService
|
|
pathCatStub = path.EmailCategory
|
|
)
|
|
|
|
var _ categorizer = unknownCatStub
|
|
|
|
func (mc mockCategorizer) String() string {
|
|
return string(mc)
|
|
}
|
|
|
|
func (mc mockCategorizer) leafCat() categorizer {
|
|
return mc
|
|
}
|
|
|
|
func (mc mockCategorizer) rootCat() categorizer {
|
|
return rootCatStub
|
|
}
|
|
|
|
func (mc mockCategorizer) unknownCat() categorizer {
|
|
return unknownCatStub
|
|
}
|
|
|
|
func (mc mockCategorizer) isUnion() bool {
|
|
return mc == rootCatStub
|
|
}
|
|
|
|
func (mc mockCategorizer) isLeaf() bool {
|
|
return mc == leafCatStub
|
|
}
|
|
|
|
func (mc mockCategorizer) pathValues(repo path.Path, ent details.DetailsEntry) map[categorizer][]string {
|
|
return map[categorizer][]string{
|
|
rootCatStub: {"root"},
|
|
leafCatStub: {"leaf"},
|
|
}
|
|
}
|
|
|
|
func (mc mockCategorizer) pathKeys() []categorizer {
|
|
return []categorizer{rootCatStub, leafCatStub}
|
|
}
|
|
|
|
func (mc mockCategorizer) PathType() path.CategoryType {
|
|
switch mc {
|
|
case leafCatStub:
|
|
return path.EventsCategory
|
|
default:
|
|
return path.UnknownCategory
|
|
}
|
|
}
|
|
|
|
func stubPathValues() map[categorizer][]string {
|
|
return map[categorizer][]string{
|
|
rootCatStub: {rootCatStub.String()},
|
|
leafCatStub: {leafCatStub.String()},
|
|
}
|
|
}
|
|
|
|
// ---------------------------------------------------------------------------
|
|
// scopers
|
|
// ---------------------------------------------------------------------------
|
|
|
|
// scoper
|
|
type mockScope scope
|
|
|
|
var _ scoper = &mockScope{}
|
|
|
|
func (ms mockScope) categorizer() categorizer {
|
|
switch ms[scopeKeyCategory].Target {
|
|
case rootCatStub.String():
|
|
return rootCatStub
|
|
case leafCatStub.String():
|
|
return leafCatStub
|
|
}
|
|
|
|
return unknownCatStub
|
|
}
|
|
|
|
func (ms mockScope) matchesInfo(dii details.ItemInfo) bool {
|
|
return ms[shouldMatch].Target == "true"
|
|
}
|
|
|
|
func (ms mockScope) setDefaults() {}
|
|
|
|
const (
|
|
shouldMatch = "should-match-entry"
|
|
)
|
|
|
|
// helper funcs
|
|
func stubScope(match string) mockScope {
|
|
sm := "true"
|
|
if len(match) > 0 {
|
|
sm = match
|
|
}
|
|
|
|
filt := passAny
|
|
if match == "none" {
|
|
filt = failAny
|
|
}
|
|
|
|
return mockScope{
|
|
rootCatStub.String(): filt,
|
|
leafCatStub.String(): filt,
|
|
scopeKeyCategory: filters.Identity(rootCatStub.String()),
|
|
scopeKeyDataType: filters.Identity(rootCatStub.String()),
|
|
shouldMatch: filters.Identity(sm),
|
|
}
|
|
}
|
|
|
|
func stubInfoScope(match string) mockScope {
|
|
sc := stubScope(match)
|
|
sc[scopeKeyInfoFilter] = filters.Identity("true")
|
|
|
|
return sc
|
|
}
|
|
|
|
// ---------------------------------------------------------------------------
|
|
// selectors
|
|
// ---------------------------------------------------------------------------
|
|
|
|
type mockSel struct {
|
|
Selector
|
|
}
|
|
|
|
func stubSelector(resourceOwners []string) mockSel {
|
|
return mockSel{
|
|
Selector: Selector{
|
|
ResourceOwners: filterize(scopeConfig{}, resourceOwners...),
|
|
Service: ServiceExchange,
|
|
Excludes: []scope{scope(stubScope(""))},
|
|
Filters: []scope{scope(stubScope(""))},
|
|
Includes: []scope{scope(stubScope(""))},
|
|
},
|
|
}
|
|
}
|
|
|
|
// ---------------------------------------------------------------------------
|
|
// helper funcs
|
|
// ---------------------------------------------------------------------------
|
|
|
|
func setScopesToDefault[T scopeT](ts []T) []T {
|
|
for _, s := range ts {
|
|
s.setDefaults()
|
|
}
|
|
|
|
return ts
|
|
}
|
|
|
|
// calls assert.Equal(t, v, getCatValue(sc, k)[0]) on each k:v pair in the map
|
|
func scopeMustHave[T scopeT](t *testing.T, sc T, m map[categorizer]string) {
|
|
for k, v := range m {
|
|
t.Run(k.String(), func(t *testing.T) {
|
|
assert.Equal(t, split(v), getCatValue(sc, k), "Key: %s", k)
|
|
})
|
|
}
|
|
}
|
|
|
|
// stubPath ensures test path production matches that of fullPath design,
|
|
// stubbing out static values where necessary.
|
|
func stubPath(t *testing.T, user string, s []string, cat path.CategoryType) path.Path {
|
|
pth, err := path.Builder{}.
|
|
Append(s...).
|
|
ToDataLayerExchangePathForCategory("tid", user, cat, true)
|
|
require.NoError(t, err)
|
|
|
|
return pth
|
|
}
|
|
|
|
// stubRepoRef ensures test path production matches that of repoRef design,
|
|
// stubbing out static values where necessary.
|
|
func stubRepoRef(service path.ServiceType, data path.CategoryType, resourceOwner, folders, item string) string {
|
|
return strings.Join([]string{"tid", service.String(), resourceOwner, data.String(), folders, item}, "/")
|
|
}
|