Lock updating info in lazyItem (#4401)
Don't allow concurrent reads/writes to info in lazyItem so we can make stronger assumptions about state --- #### Does this PR need a docs update or release note? - [ ] ✅ Yes, it's included - [ ] 🕐 Yes, but in a later PR - [x] ⛔ No #### Type of change - [ ] 🌻 Feature - [ ] 🐛 Bugfix - [ ] 🗺️ Documentation - [ ] 🤖 Supportability/Tests - [ ] 💻 CI/Deployment - [x] 🧹 Tech Debt/Cleanup #### Test Plan - [ ] 💪 Manual - [x] ⚡ Unit test - [x] 💚 E2E
This commit is contained in:
parent
5258ef0f36
commit
d5cdf37369
@ -4,6 +4,7 @@ import (
|
|||||||
"bytes"
|
"bytes"
|
||||||
"context"
|
"context"
|
||||||
"io"
|
"io"
|
||||||
|
"sync"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/alcionai/clues"
|
"github.com/alcionai/clues"
|
||||||
@ -110,6 +111,7 @@ func NewLazyItem(
|
|||||||
// made.
|
// made.
|
||||||
type lazyItem struct {
|
type lazyItem struct {
|
||||||
ctx context.Context
|
ctx context.Context
|
||||||
|
mu sync.Mutex
|
||||||
id string
|
id string
|
||||||
errs *fault.Bus
|
errs *fault.Bus
|
||||||
itemGetter ItemDataGetter
|
itemGetter ItemDataGetter
|
||||||
@ -127,12 +129,18 @@ type lazyItem struct {
|
|||||||
delInFlight bool
|
delInFlight bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i lazyItem) ID() string {
|
func (i *lazyItem) ID() string {
|
||||||
return i.id
|
return i.id
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i *lazyItem) ToReader() io.ReadCloser {
|
func (i *lazyItem) ToReader() io.ReadCloser {
|
||||||
return lazy.NewLazyReadCloser(func() (io.ReadCloser, error) {
|
return lazy.NewLazyReadCloser(func() (io.ReadCloser, error) {
|
||||||
|
// Don't allow getting Item info while trying to initialize said info.
|
||||||
|
// GetData could be a long running call, but in theory nothing should happen
|
||||||
|
// with the item until a reader is returned anyway.
|
||||||
|
i.mu.Lock()
|
||||||
|
defer i.mu.Unlock()
|
||||||
|
|
||||||
reader, info, delInFlight, err := i.itemGetter.GetData(i.ctx, i.errs)
|
reader, info, delInFlight, err := i.itemGetter.GetData(i.ctx, i.errs)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, clues.Stack(err)
|
return nil, clues.Stack(err)
|
||||||
@ -159,11 +167,14 @@ func (i *lazyItem) ToReader() io.ReadCloser {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i lazyItem) Deleted() bool {
|
func (i *lazyItem) Deleted() bool {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i lazyItem) Info() (details.ItemInfo, error) {
|
func (i *lazyItem) Info() (details.ItemInfo, error) {
|
||||||
|
i.mu.Lock()
|
||||||
|
defer i.mu.Unlock()
|
||||||
|
|
||||||
if i.delInFlight {
|
if i.delInFlight {
|
||||||
return details.ItemInfo{}, clues.Stack(ErrNotFound).WithClues(i.ctx)
|
return details.ItemInfo{}, clues.Stack(ErrNotFound).WithClues(i.ctx)
|
||||||
} else if i.info == nil {
|
} else if i.info == nil {
|
||||||
@ -174,6 +185,6 @@ func (i lazyItem) Info() (details.ItemInfo, error) {
|
|||||||
return *i.info, nil
|
return *i.info, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i lazyItem) ModTime() time.Time {
|
func (i *lazyItem) ModTime() time.Time {
|
||||||
return i.modTime
|
return i.modTime
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user