mirror of
https://github.com/junegunn/fzf.git
synced 2025-07-31 04:02:01 -07:00
Less aggressive chunk cache invalidation for --tail
This commit is contained in:
@@ -1,6 +1,10 @@
|
||||
CHANGELOG
|
||||
=========
|
||||
|
||||
0.53.1
|
||||
------
|
||||
- Bug fixes and minor improvements
|
||||
|
||||
0.53.0
|
||||
------
|
||||
- Multi-line display
|
||||
|
@@ -22,6 +22,14 @@ func (cc *ChunkCache) Clear() {
|
||||
cc.mutex.Unlock()
|
||||
}
|
||||
|
||||
func (cc *ChunkCache) retire(chunk ...*Chunk) {
|
||||
cc.mutex.Lock()
|
||||
for _, c := range chunk {
|
||||
delete(cc.cache, c)
|
||||
}
|
||||
cc.mutex.Unlock()
|
||||
}
|
||||
|
||||
// Add adds the list to the cache
|
||||
func (cc *ChunkCache) Add(chunk *Chunk, key string, list []Result) {
|
||||
if len(key) == 0 || !chunk.IsFull() || len(list) > queryCacheMax {
|
||||
|
@@ -16,14 +16,16 @@ type ChunkList struct {
|
||||
chunks []*Chunk
|
||||
mutex sync.Mutex
|
||||
trans ItemBuilder
|
||||
cache *ChunkCache
|
||||
}
|
||||
|
||||
// NewChunkList returns a new ChunkList
|
||||
func NewChunkList(trans ItemBuilder) *ChunkList {
|
||||
func NewChunkList(cache *ChunkCache, trans ItemBuilder) *ChunkList {
|
||||
return &ChunkList{
|
||||
chunks: []*Chunk{},
|
||||
mutex: sync.Mutex{},
|
||||
trans: trans}
|
||||
trans: trans,
|
||||
cache: cache}
|
||||
}
|
||||
|
||||
func (c *Chunk) push(trans ItemBuilder, data []byte) bool {
|
||||
@@ -92,7 +94,9 @@ func (cl *ChunkList) Snapshot(tail int) ([]*Chunk, int, bool) {
|
||||
|
||||
// Copy the chunks to keep
|
||||
ret := make([]*Chunk, numChunks)
|
||||
copy(ret, cl.chunks[len(cl.chunks)-numChunks:])
|
||||
minIndex := len(cl.chunks) - numChunks
|
||||
cl.cache.retire(cl.chunks[:minIndex]...)
|
||||
copy(ret, cl.chunks[minIndex:])
|
||||
|
||||
for left, i := tail, len(ret)-1; i >= 0; i-- {
|
||||
chunk := ret[i]
|
||||
@@ -104,6 +108,7 @@ func (cl *ChunkList) Snapshot(tail int) ([]*Chunk, int, bool) {
|
||||
newChunk.items[i] = chunk.items[oldCount-left+i]
|
||||
}
|
||||
ret[i] = &newChunk
|
||||
cl.cache.retire(chunk)
|
||||
break
|
||||
}
|
||||
left -= chunk.count
|
||||
|
@@ -11,7 +11,7 @@ func TestChunkList(t *testing.T) {
|
||||
// FIXME global
|
||||
sortCriteria = []criterion{byScore, byLength}
|
||||
|
||||
cl := NewChunkList(func(item *Item, s []byte) bool {
|
||||
cl := NewChunkList(NewChunkCache(), func(item *Item, s []byte) bool {
|
||||
item.text = util.ToChars(s)
|
||||
return true
|
||||
})
|
||||
@@ -80,7 +80,7 @@ func TestChunkList(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestChunkListTail(t *testing.T) {
|
||||
cl := NewChunkList(func(item *Item, s []byte) bool {
|
||||
cl := NewChunkList(NewChunkCache(), func(item *Item, s []byte) bool {
|
||||
item.text = util.ToChars(s)
|
||||
return true
|
||||
})
|
||||
|
10
src/core.go
10
src/core.go
@@ -32,10 +32,6 @@ func (r *revision) bumpMinor() {
|
||||
r.minor++
|
||||
}
|
||||
|
||||
func (r revision) equals(other revision) bool {
|
||||
return r.major == other.major && r.minor == other.minor
|
||||
}
|
||||
|
||||
func (r revision) compatible(other revision) bool {
|
||||
return r.major == other.major
|
||||
}
|
||||
@@ -94,11 +90,12 @@ func Run(opts *Options) (int, error) {
|
||||
}
|
||||
|
||||
// Chunk list
|
||||
cache := NewChunkCache()
|
||||
var chunkList *ChunkList
|
||||
var itemIndex int32
|
||||
header := make([]string, 0, opts.HeaderLines)
|
||||
if len(opts.WithNth) == 0 {
|
||||
chunkList = NewChunkList(func(item *Item, data []byte) bool {
|
||||
chunkList = NewChunkList(cache, func(item *Item, data []byte) bool {
|
||||
if len(header) < opts.HeaderLines {
|
||||
header = append(header, byteString(data))
|
||||
eventBox.Set(EvtHeader, header)
|
||||
@@ -110,7 +107,7 @@ func Run(opts *Options) (int, error) {
|
||||
return true
|
||||
})
|
||||
} else {
|
||||
chunkList = NewChunkList(func(item *Item, data []byte) bool {
|
||||
chunkList = NewChunkList(cache, func(item *Item, data []byte) bool {
|
||||
tokens := Tokenize(byteString(data), opts.Delimiter)
|
||||
if opts.Ansi && opts.Theme.Colored && len(tokens) > 1 {
|
||||
var ansiState *ansiState
|
||||
@@ -170,7 +167,6 @@ func Run(opts *Options) (int, error) {
|
||||
forward = true
|
||||
}
|
||||
}
|
||||
cache := NewChunkCache()
|
||||
patternCache := make(map[string]*Pattern)
|
||||
patternBuilder := func(runes []rune) *Pattern {
|
||||
return BuildPattern(cache, patternCache,
|
||||
|
@@ -87,7 +87,9 @@ func (m *Matcher) Loop() {
|
||||
m.sort = request.sort
|
||||
m.revision = request.revision
|
||||
m.mergerCache = make(map[string]*Merger)
|
||||
m.cache.Clear()
|
||||
if !request.revision.compatible(m.revision) {
|
||||
m.cache.Clear()
|
||||
}
|
||||
cacheCleared = true
|
||||
}
|
||||
|
||||
@@ -193,7 +195,7 @@ func (m *Matcher) scan(request MatchRequest) (*Merger, bool) {
|
||||
for _, matches := range allMatches {
|
||||
sliceMatches = append(sliceMatches, matches...)
|
||||
}
|
||||
if m.sort {
|
||||
if m.sort && request.pattern.sortable {
|
||||
if m.tac {
|
||||
sort.Sort(ByRelevanceTac(sliceMatches))
|
||||
} else {
|
||||
@@ -234,7 +236,7 @@ func (m *Matcher) scan(request MatchRequest) (*Merger, bool) {
|
||||
partialResult := <-resultChan
|
||||
partialResults[partialResult.index] = partialResult.matches
|
||||
}
|
||||
return NewMerger(pattern, partialResults, m.sort, m.tac, request.revision, minIndex), false
|
||||
return NewMerger(pattern, partialResults, m.sort && request.pattern.sortable, m.tac, request.revision, minIndex), false
|
||||
}
|
||||
|
||||
// Reset is called to interrupt/signal the ongoing search
|
||||
@@ -247,7 +249,7 @@ func (m *Matcher) Reset(chunks []*Chunk, patternRunes []rune, cancel bool, final
|
||||
} else {
|
||||
event = reqRetry
|
||||
}
|
||||
m.reqBox.Set(event, MatchRequest{chunks, pattern, final, sort && pattern.sortable, revision})
|
||||
m.reqBox.Set(event, MatchRequest{chunks, pattern, final, sort, revision})
|
||||
}
|
||||
|
||||
func (m *Matcher) Stop() {
|
||||
|
@@ -1174,7 +1174,7 @@ func (t *Terminal) UpdateList(merger *Merger, triggerResultEvent bool) {
|
||||
}
|
||||
t.progress = 100
|
||||
t.merger = merger
|
||||
if !t.revision.equals(newRevision) {
|
||||
if t.revision != newRevision {
|
||||
if !t.revision.compatible(newRevision) {
|
||||
// Reloaded: clear selection
|
||||
t.selected = make(map[int32]selectedItem)
|
||||
|
Reference in New Issue
Block a user