From 597e689417082164f0b0f0d99b9f415474e35ec1 Mon Sep 17 00:00:00 2001 From: Danny Date: Fri, 21 Oct 2022 18:11:29 -0400 Subject: [PATCH] GC: Update Error Messages (#1252) ## Description ## Type of change - [x] :world_map: Documentation ## Issue(s) *Related to #1225 ## Test Plan - [x] :muscle: Manual --- .../exchange/contact_folder_cache.go | 10 ++++--- .../exchange/event_calendar_cache.go | 16 ++++++----- .../connector/exchange/service_functions.go | 10 +++---- .../connector/exchange/service_iterators.go | 27 +++++++++++-------- .../connector/exchange/service_restore.go | 14 +++++----- .../connector/graph/service_helper.go | 5 ++-- src/internal/connector/graph_connector.go | 14 +++++----- src/internal/connector/support/m365Support.go | 11 ++++---- .../connector/support/m365Transform.go | 8 +++--- 9 files changed, 65 insertions(+), 50 deletions(-) diff --git a/src/internal/connector/exchange/contact_folder_cache.go b/src/internal/connector/exchange/contact_folder_cache.go index 1c115d904..a9e7f93a2 100644 --- a/src/internal/connector/exchange/contact_folder_cache.go +++ b/src/internal/connector/exchange/contact_folder_cache.go @@ -39,7 +39,9 @@ func (cfc *contactFolderCache) populateContactRoot( ContactFoldersById(directoryID). Get(ctx, opts) if err != nil { - return errors.Wrapf(err, "fetching root contact folder") + return errors.Wrapf( + err, + "fetching root contact folder: "+support.ConnectorStackErrorTrace(err)) } idPtr := f.GetId() @@ -92,14 +94,14 @@ func (cfc *contactFolderCache) Populate( iter, err := msgraphgocore.NewPageIterator(query, cfc.gs.Adapter(), models.CreateContactFolderCollectionResponseFromDiscriminatorValue) if err != nil { - return err + return errors.Wrap(err, support.ConnectorStackErrorTrace(err)) } cb := IterativeCollectContactContainers(containers, "", errUpdater) if err := iter.Iterate(ctx, cb); err != nil { - return err + return errors.Wrap(err, support.ConnectorStackErrorTrace(err)) } if errs != nil { @@ -141,7 +143,7 @@ func (cfc *contactFolderCache) IDToPath( ) (*path.Builder, error) { c, ok := cfc.cache[folderID] if !ok { - return nil, errors.Errorf("folder %s not cached", folderID) + return nil, errors.Errorf("contact folder %s not cached", folderID) } p := c.Path() diff --git a/src/internal/connector/exchange/event_calendar_cache.go b/src/internal/connector/exchange/event_calendar_cache.go index eaf21207c..3999cf8e7 100644 --- a/src/internal/connector/exchange/event_calendar_cache.go +++ b/src/internal/connector/exchange/event_calendar_cache.go @@ -37,10 +37,13 @@ func (ecc *eventCalendarCache) Populate( return err } - directories := make(map[string]graph.Container) - errUpdater := func(s string, e error) { - err = support.WrapAndAppend(s, e, err) - } + var ( + asyncError error + directories = make(map[string]graph.Container) + errUpdater = func(s string, e error) { + asyncError = support.WrapAndAppend(s, e, err) + } + ) query, err := ecc.gs.Client().UsersById(ecc.userID).Calendars().Get(ctx, options) if err != nil { @@ -64,10 +67,11 @@ func (ecc *eventCalendarCache) Populate( iterateErr := iter.Iterate(ctx, cb) if iterateErr != nil { - return iterateErr + return errors.Wrap(iterateErr, support.ConnectorStackErrorTrace(iterateErr)) } - if err != nil { + // check for errors created during iteration + if asyncError != nil { return err } diff --git a/src/internal/connector/exchange/service_functions.go b/src/internal/connector/exchange/service_functions.go index 5fd99448b..6e7a39dce 100644 --- a/src/internal/connector/exchange/service_functions.go +++ b/src/internal/connector/exchange/service_functions.go @@ -48,7 +48,7 @@ func createService(credentials account.M365Config, shouldFailFast bool) (*exchan credentials.AzureClientSecret, ) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating microsoft graph service for exchange") } service := exchangeService{ @@ -58,7 +58,7 @@ func createService(credentials account.M365Config, shouldFailFast bool) (*exchan credentials: credentials, } - return &service, err + return &service, nil } // CreateMailFolder makes a mail folder iff a folder of the same name does not exist @@ -142,7 +142,7 @@ func GetAllMailFolders( resolver, err := PopulateExchangeContainerResolver(ctx, qp, path.EmailCategory) if err != nil { - return nil, err + return nil, errors.Wrap(err, "building directory resolver in GetAllMailFolders") } for _, c := range resolver.Items() { @@ -171,7 +171,7 @@ func GetAllCalendars( resolver, err := PopulateExchangeContainerResolver(ctx, qp, path.EventsCategory) if err != nil { - return nil, err + return nil, errors.Wrap(err, "building calendar resolver in GetAllCalendars") } for _, c := range resolver.Items() { @@ -200,7 +200,7 @@ func GetAllContactFolders( resolver, err := PopulateExchangeContainerResolver(ctx, qp, path.ContactsCategory) if err != nil { - return nil, err + return nil, errors.Wrap(err, "building directory resolver in GetAllContactFolders") } for _, c := range resolver.Items() { diff --git a/src/internal/connector/exchange/service_iterators.go b/src/internal/connector/exchange/service_iterators.go index 4371135b7..dbd29a948 100644 --- a/src/internal/connector/exchange/service_iterators.go +++ b/src/internal/connector/exchange/service_iterators.go @@ -40,7 +40,7 @@ func FilterContainersAndFillCollections( service, err := createService(qp.Credentials, qp.FailFast) if err != nil { errs = support.WrapAndAppend( - qp.User+" failed to create service during FilterContainerAndFillCollection", + qp.User+" FilterContainerAndFillCollection", err, errs) @@ -98,7 +98,8 @@ func IterativeCollectContactContainers( return func(entry any) bool { folder, ok := entry.(models.ContactFolderable) if !ok { - errUpdater("", errors.New("casting item to models.ContactFolderable")) + errUpdater("iterateCollectContactContainers", + errors.New("casting item to models.ContactFolderable")) return false } @@ -121,7 +122,7 @@ func IterativeCollectCalendarContainers( return func(entry any) bool { cal, ok := entry.(models.Calendarable) if !ok { - errUpdater("failure during IterativeCollectCalendarContainers", + errUpdater("iterativeCollectCalendarContainers", errors.New("casting item to models.Calendarable")) return false } @@ -190,6 +191,7 @@ func FetchEventIDsFromCalendar( if entry.GetId() == nil { errs = multierror.Append(errs, errors.New("item with nil ID")) + return true } ids = append(ids, *entry.GetId()) @@ -201,7 +203,7 @@ func FetchEventIDsFromCalendar( return nil, errors.Wrap( err, support.ConnectorStackErrorTrace(err)+ - " :iterateFailure for fetching events from calendar "+calendarID, + " :fetching events from calendar "+calendarID, ) } @@ -233,7 +235,7 @@ func FetchContactIDsFromDirectory(ctx context.Context, gs graph.Service, user, d models.CreateContactCollectionResponseFromDiscriminatorValue, ) if err != nil { - return nil, errors.Wrap(err, "failure to create iterator during FecthContactIDs") + return nil, errors.Wrap(err, "iterator creation during FetchContactIDs") } var errs *multierror.Error @@ -249,6 +251,11 @@ func FetchContactIDsFromDirectory(ctx context.Context, gs graph.Service, user, d return true } + if entry.GetId() == nil { + errs = multierror.Append(errs, errors.New("item with nil ID")) + return true + } + ids = append(ids, *entry.GetId()) return true @@ -259,7 +266,7 @@ func FetchContactIDsFromDirectory(ctx context.Context, gs graph.Service, user, d errors.Wrap( err, support.ConnectorStackErrorTrace(err)+ - " :iterate failure during fetching contactIDs from directory "+directoryID, + " :fetching contactIDs from directory "+directoryID, ) } @@ -286,10 +293,8 @@ func FetchMessageIDsFromDirectory( Messages(). Get(ctx, options) if err != nil { - return nil, errors.Wrap( - errors.Wrap(err, support.ConnectorStackErrorTrace(err)), - "initial folder query", - ) + return nil, + errors.Wrap(err, support.ConnectorStackErrorTrace(err)) } pageIter, err := msgraphgocore.NewPageIterator( @@ -324,7 +329,7 @@ func FetchMessageIDsFromDirectory( return nil, errors.Wrap( err, support.ConnectorStackErrorTrace(err)+ - " :iterateFailure for fetching messages from directory "+directoryID, + " :fetching messages from directory "+directoryID, ) } diff --git a/src/internal/connector/exchange/service_restore.go b/src/internal/connector/exchange/service_restore.go index a57546344..23e90936c 100644 --- a/src/internal/connector/exchange/service_restore.go +++ b/src/internal/connector/exchange/service_restore.go @@ -65,7 +65,7 @@ func RestoreExchangeContact( ) (*details.ExchangeInfo, error) { contact, err := support.CreateContactFromBytes(bits) if err != nil { - return nil, errors.Wrap(err, "failure to create contact from bytes: RestoreExchangeContact") + return nil, errors.Wrap(err, "creating contact from bytes: RestoreExchangeContact") } response, err := service.Client().UsersById(user).ContactFoldersById(destination).Contacts().Post(ctx, contact, nil) @@ -74,7 +74,7 @@ func RestoreExchangeContact( return nil, errors.Wrap( err, - "failure to create Contact during RestoreExchangeContact: "+name+" "+ + "uploading Contact during RestoreExchangeContact: "+name+" "+ support.ConnectorStackErrorTrace(err), ) } @@ -101,7 +101,7 @@ func RestoreExchangeEvent( ) (*details.ExchangeInfo, error) { event, err := support.CreateEventFromBytes(bits) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating event from bytes: RestoreExchangeEvent") } transformedEvent := support.ToEventSimplified(event) @@ -110,7 +110,7 @@ func RestoreExchangeEvent( if err != nil { return nil, errors.Wrap(err, fmt.Sprintf( - "failure to event creation failure during RestoreExchangeEvent: %s", + "uploading event during RestoreExchangeEvent: %s", support.ConnectorStackErrorTrace(err)), ) } @@ -138,7 +138,7 @@ func RestoreMailMessage( // Creates messageable object from original bytes originalMessage, err := support.CreateMessageFromBytes(bits) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating email from bytes: RestoreMailMessage") } // Sets fields from original message from storage clone := support.ToMessage(originalMessage) @@ -226,7 +226,9 @@ func SendMailToBackStore( for _, attachment := range attached { err := uploadAttachment(ctx, service, user, destination, id, attachment) if err != nil { - errs = support.WrapAndAppend(fmt.Sprintf("uploading attachment for message %s", id), + errs = support.WrapAndAppend( + fmt.Sprintf("uploading attachment for message %s: %s", + id, support.ConnectorStackErrorTrace(err)), err, errs, ) diff --git a/src/internal/connector/graph/service_helper.go b/src/internal/connector/graph/service_helper.go index ecd292f59..32c5b05e5 100644 --- a/src/internal/connector/graph/service_helper.go +++ b/src/internal/connector/graph/service_helper.go @@ -12,6 +12,7 @@ import ( khttp "github.com/microsoft/kiota-http-go" msgraphsdk "github.com/microsoftgraph/msgraph-sdk-go" msgraphgocore "github.com/microsoftgraph/msgraph-sdk-go-core" + "github.com/pkg/errors" "github.com/alcionai/corso/src/pkg/logger" "github.com/alcionai/corso/src/pkg/path" @@ -29,7 +30,7 @@ func CreateAdapter(tenant, client, secret string) (*msgraphsdk.GraphRequestAdapt // Client Provider: Uses Secret for access to tenant-level data cred, err := az.NewClientSecretCredential(tenant, client, secret, nil) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating m365 client secret credentials") } auth, err := ka.NewAzureIdentityAuthenticationProviderWithScopes( @@ -37,7 +38,7 @@ func CreateAdapter(tenant, client, secret string) (*msgraphsdk.GraphRequestAdapt []string{"https://graph.microsoft.com/.default"}, ) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating new AzureIdentityAuthentication") } clientOptions := msgraphsdk.GetDefaultClientOptions() diff --git a/src/internal/connector/graph_connector.go b/src/internal/connector/graph_connector.go index 0411ca333..7c57f0606 100644 --- a/src/internal/connector/graph_connector.go +++ b/src/internal/connector/graph_connector.go @@ -84,14 +84,14 @@ func NewGraphConnector(ctx context.Context, acct account.Account) (*GraphConnect aService, err := gc.createService(false) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating service connection") } gc.graphService = *aService err = gc.setTenantUsers(ctx) if err != nil { - return nil, err + return nil, errors.Wrap(err, "retrieving tenant user list") } return &gc, nil @@ -114,7 +114,7 @@ func (gc *GraphConnector) createService(shouldFailFast bool) (*graphService, err failFast: shouldFailFast, } - return &connector, err + return &connector, nil } func (gs *graphService) EnableFailFast() { @@ -149,7 +149,7 @@ func (gc *GraphConnector) setTenantUsers(ctx context.Context) error { callbackFunc := func(userItem interface{}) bool { user, ok := userItem.(models.Userable) if !ok { - err = support.WrapAndAppend(gc.graphService.adapter.GetBaseUrl(), errors.New("user iteration failure"), err) + err = support.WrapAndAppend(gc.graphService.adapter.GetBaseUrl(), errors.New("received non-User on iteration"), err) return true } @@ -216,7 +216,7 @@ func (gc *GraphConnector) ExchangeDataCollection( ) ([]data.Collection, error) { eb, err := selector.ToExchangeBackup() if err != nil { - return nil, errors.Wrap(err, "exchangeDataCollection: unable to parse selector") + return nil, errors.Wrap(err, "exchangeDataCollection: parsing selector") } var ( @@ -386,7 +386,7 @@ func (gc *GraphConnector) DataCollections(ctx context.Context, sels selectors.Se case selectors.ServiceOneDrive: return gc.OneDriveDataCollections(ctx, sels) default: - return nil, errors.Errorf("Service %s not supported", sels) + return nil, errors.Errorf("service %s not supported", sels) } } @@ -398,7 +398,7 @@ func (gc *GraphConnector) OneDriveDataCollections( ) ([]data.Collection, error) { odb, err := selector.ToOneDriveBackup() if err != nil { - return nil, errors.Wrap(err, "collecting onedrive data") + return nil, errors.Wrap(err, "oneDriveDataCollection: parsing selector") } collections := []data.Collection{} diff --git a/src/internal/connector/support/m365Support.go b/src/internal/connector/support/m365Support.go index 94b75ece9..fb2f50747 100644 --- a/src/internal/connector/support/m365Support.go +++ b/src/internal/connector/support/m365Support.go @@ -4,6 +4,7 @@ import ( absser "github.com/microsoft/kiota-abstractions-go/serialization" js "github.com/microsoft/kiota-serialization-json-go" "github.com/microsoftgraph/msgraph-sdk-go/models" + "github.com/pkg/errors" ) // CreateFromBytes helper function to initialize m365 object form bytes. @@ -11,12 +12,12 @@ import ( func CreateFromBytes(bytes []byte, createFunc absser.ParsableFactory) (absser.Parsable, error) { parseNode, err := js.NewJsonParseNodeFactory().GetRootParseNode("application/json", bytes) if err != nil { - return nil, err + return nil, errors.Wrap(err, "parsing byte array into m365 object") } anObject, err := parseNode.GetObjectValue(createFunc) if err != nil { - return nil, err + return nil, errors.Wrap(err, "parsing m365 object factory") } return anObject, nil @@ -26,7 +27,7 @@ func CreateFromBytes(bytes []byte, createFunc absser.ParsableFactory) (absser.Pa func CreateMessageFromBytes(bytes []byte) (models.Messageable, error) { aMessage, err := CreateFromBytes(bytes, models.CreateMessageFromDiscriminatorValue) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating m365 exchange.Mail object from provided bytes") } message := aMessage.(models.Messageable) @@ -39,7 +40,7 @@ func CreateMessageFromBytes(bytes []byte) (models.Messageable, error) { func CreateContactFromBytes(bytes []byte) (models.Contactable, error) { parsable, err := CreateFromBytes(bytes, models.CreateContactFromDiscriminatorValue) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating m365 exchange.Contact object from provided bytes") } contact := parsable.(models.Contactable) @@ -51,7 +52,7 @@ func CreateContactFromBytes(bytes []byte) (models.Contactable, error) { func CreateEventFromBytes(bytes []byte) (models.Eventable, error) { parsable, err := CreateFromBytes(bytes, models.CreateEventFromDiscriminatorValue) if err != nil { - return nil, err + return nil, errors.Wrap(err, "creating m365 exchange.Event object from provided bytes") } event := parsable.(models.Eventable) diff --git a/src/internal/connector/support/m365Transform.go b/src/internal/connector/support/m365Transform.go index 082626713..11044d072 100644 --- a/src/internal/connector/support/m365Transform.go +++ b/src/internal/connector/support/m365Transform.go @@ -90,7 +90,7 @@ func SetEventMessageRequest(orig models.Messageable, adtl map[string]any) (model eventMessage, err := setEventRequestableFields(message, additional) if err != nil { - return nil, err + return nil, errors.Wrap(err, "unable to set all fields for eventMessageRequestable") } return eventMessage, nil @@ -275,7 +275,7 @@ func SetAdditionalDataToEventMessage( value, err := node.GetStringValue() if err != nil { - return nil, err + return nil, errors.Wrapf(err, "could not parse string value for %s", key) } switch key { @@ -304,7 +304,7 @@ func SetAdditionalDataToEventMessage( value, err := node.GetStringValue() if err != nil { - return nil, err + return nil, errors.Wrapf(err, "could not parse string value for %s", key) } switch key { @@ -333,7 +333,7 @@ func SetAdditionalDataToEventMessage( value, err := node.GetStringValue() if err != nil { - return nil, errors.New("map[string]*JsonParseNode conversion failure") + return nil, errors.Wrapf(err, "could not parse string value for key %s", key) } switch key {