fzf

package
v0.0.0-...-a67dd81 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Feb 18, 2016 License: MIT, MIT Imports: 23 Imported by: 0

README

fzf in Go

fzf in go

This directory contains the source code for the new fzf implementation in Go.

Upgrade from Ruby version

The install script has been updated to download the right binary for your system. If you already have installed fzf, simply git-pull the repository and rerun the install script.

cd ~/.fzf
git pull
./install

Otherwise, follow the instruction as before. You can also install fzf using Homebrew if you prefer that way.

Motivations

No Ruby dependency

There have always been complaints about fzf being a Ruby script. To make matters worse, Ruby 2.1 removed ncurses binding from its standard libary. Because of the change, users running Ruby 2.1 or above are forced to build C extensions of curses gem to meet the requirement of fzf. The new Go version will be distributed as an executable binary so it will be much more accessible and should be easier to setup.

Performance

Many people have been surprised to see how fast fzf is even when it was written in Ruby. It stays quite responsive even for 100k+ lines, which is well above the size of the usual input.

The new Go version, of course, is significantly faster than that. It has all the performance optimization techniques used in Ruby implementation and more. It also doesn't suffer from GIL, so the search performance scales proportional to the number of CPU cores. On my MacBook Pro (Mid 2012), the new version was shown to be an order of magnitude faster on certain cases. It also starts much faster though the difference may not be noticeable.

Differences with Ruby version

The Go version is designed to be perfectly compatible with the previous Ruby version. The only behavioral difference is that the new version ignores the numeric argument to --sort=N option and always sorts the result regardless of the number of matches. The value was introduced to limit the response time of the query, but the Go version is blazingly fast (almost instant response even for 1M+ items) so I decided that it's no longer required.

System requirements

Currently, prebuilt binaries are provided only for OS X and Linux. The install script will fall back to the legacy Ruby version on the other systems, but if you have Go 1.4 installed, you can try building it yourself.

However, as pointed out in golang.org/doc/install, the Go version may not run on CentOS/RHEL 5.x, and if that's the case, the install script will choose the Ruby version instead.

The Go version depends on ncurses and some Unix system calls, so it shouldn't run natively on Windows at the moment. But it won't be impossible to support Windows by falling back to a cross-platform alternative such as termbox only on Windows. If you're interested in making fzf work on Windows, please let me know.

Build

# Build fzf executables and tarballs
make

# Install the executable to ../bin directory
make install

# Build executables and tarballs for Linux using Docker
make linux

Contribution

For the time being, I will not add or accept any new features until we can be sure that the implementation is stable and we have a sufficient number of test cases. However, fixes for obvious bugs and new test cases are welcome.

I also care much about the performance of the implementation, so please make sure that your change does not result in performance regression. And please be noted that we don't have a quantitative measure of the performance yet.

Third-party libraries used

License

MIT

Documentation

Overview

Package fzf implements fzf, a command-line fuzzy finder.

The MIT License (MIT)

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

Index

Constants

View Source
const (
	EvtReadNew util.EventType = iota
	EvtReadFin
	EvtSearchNew
	EvtSearchProgress
	EvtSearchFin
	EvtHeader
	EvtClose
)

fzf events

Variables

View Source
var EmptyMerger = NewMerger([][]*Item{}, false, false)

Merger with no data

Functions

func CountItems

func CountItems(cs []*Chunk) int

CountItems returns the total number of Items

func Run

func Run(opts *Options)

Run starts fzf

Types

type ByOrder

type ByOrder []Offset

ByOrder is for sorting substring offsets

func (ByOrder) Len

func (a ByOrder) Len() int

func (ByOrder) Less

func (a ByOrder) Less(i, j int) bool

func (ByOrder) Swap

func (a ByOrder) Swap(i, j int)

type ByRelevance

type ByRelevance []*Item

ByRelevance is for sorting Items

func (ByRelevance) Len

func (a ByRelevance) Len() int

func (ByRelevance) Less

func (a ByRelevance) Less(i, j int) bool

func (ByRelevance) Swap

func (a ByRelevance) Swap(i, j int)

type ByRelevanceTac

type ByRelevanceTac []*Item

ByRelevanceTac is for sorting Items

func (ByRelevanceTac) Len

func (a ByRelevanceTac) Len() int

func (ByRelevanceTac) Less

func (a ByRelevanceTac) Less(i, j int) bool

func (ByRelevanceTac) Swap

func (a ByRelevanceTac) Swap(i, j int)

type Case

type Case int

Case denotes case-sensitivity of search

const (
	CaseSmart Case = iota
	CaseIgnore
	CaseRespect
)

Case-sensitivities

type Chunk

type Chunk []*Item // >>> []Item

Chunk is a list of Item pointers whose size has the upper limit of chunkSize

func (*Chunk) IsFull

func (c *Chunk) IsFull() bool

IsFull returns true if the Chunk is full

type ChunkCache

type ChunkCache struct {
	// contains filtered or unexported fields
}

ChunkCache associates Chunk and query string to lists of items

func NewChunkCache

func NewChunkCache() ChunkCache

NewChunkCache returns a new ChunkCache

func (*ChunkCache) Add

func (cc *ChunkCache) Add(chunk *Chunk, key string, list []*Item)

Add adds the list to the cache

func (*ChunkCache) Find

func (cc *ChunkCache) Find(chunk *Chunk, key string) ([]*Item, bool)

Find is called to lookup ChunkCache

type ChunkList

type ChunkList struct {
	// contains filtered or unexported fields
}

ChunkList is a list of Chunks

func NewChunkList

func NewChunkList(trans ItemBuilder) *ChunkList

NewChunkList returns a new ChunkList

func (*ChunkList) Push

func (cl *ChunkList) Push(data []byte) bool

Push adds the item to the list

func (*ChunkList) Snapshot

func (cl *ChunkList) Snapshot() ([]*Chunk, int)

Snapshot returns immutable snapshot of the ChunkList

type Delimiter

type Delimiter struct {
	// contains filtered or unexported fields
}

Delimiter for tokenizing the input

type History

type History struct {
	// contains filtered or unexported fields
}

History struct represents input history

func NewHistory

func NewHistory(path string, maxSize int) (*History, error)

NewHistory returns the pointer to a new History struct

type Item

type Item struct {
	// contains filtered or unexported fields
}

Item represents each input line

func (*Item) AsString

func (item *Item) AsString(stripAnsi bool) string

AsString returns the original string

func (*Item) Index

func (item *Item) Index() int32

func (*Item) Rank

func (item *Item) Rank(cache bool) [5]int32

Rank calculates rank of the Item

func (*Item) StringPtr

func (item *Item) StringPtr(stripAnsi bool) *string

StringPtr returns the pointer to the original string

type ItemBuilder

type ItemBuilder func([]byte, int) *Item

ItemBuilder is a closure type that builds Item object from a pointer to a string and an integer

type MatchRequest

type MatchRequest struct {
	// contains filtered or unexported fields
}

MatchRequest represents a search request

type Matcher

type Matcher struct {
	// contains filtered or unexported fields
}

Matcher is responsible for performing search

func NewMatcher

func NewMatcher(patternBuilder func([]rune) *Pattern,
	sort bool, tac bool, eventBox *util.EventBox) *Matcher

NewMatcher returns a new Matcher

func (*Matcher) Loop

func (m *Matcher) Loop()

Loop puts Matcher in action

func (*Matcher) Reset

func (m *Matcher) Reset(chunks []*Chunk, patternRunes []rune, cancel bool, final bool, sort bool)

Reset is called to interrupt/signal the ongoing search

type Merger

type Merger struct {
	// contains filtered or unexported fields
}

Merger holds a set of locally sorted lists of items and provides the view of a single, globally-sorted list

func NewMerger

func NewMerger(lists [][]*Item, sorted bool, tac bool) *Merger

NewMerger returns a new Merger

func PassMerger

func PassMerger(chunks *[]*Chunk, tac bool) *Merger

PassMerger returns a new Merger that simply returns the items in the original order

func (*Merger) Get

func (mg *Merger) Get(idx int) *Item

Get returns the pointer to the Item object indexed by the given integer

func (*Merger) Length

func (mg *Merger) Length() int

Length returns the number of items

type Offset

type Offset [3]int32

Offset holds three 32-bit integers denoting the offsets of a matched substring

type Options

type Options struct {
	Fuzzy       bool
	Extended    bool
	Case        Case
	Nth         []Range
	WithNth     []Range
	Delimiter   Delimiter
	Sort        int
	Tac         bool
	Criteria    []criterion
	Multi       bool
	Ansi        bool
	Mouse       bool
	Theme       *curses.ColorTheme
	Black       bool
	Reverse     bool
	Cycle       bool
	Hscroll     bool
	InlineInfo  bool
	Prompt      string
	Query       string
	Select1     bool
	Exit0       bool
	Filter      *string
	ToggleSort  bool
	Expect      map[int]string
	Keymap      map[int]actionType
	Execmap     map[int]string
	PrintQuery  bool
	ReadZero    bool
	Sync        bool
	History     *History
	Header      []string
	HeaderLines int
	Margin      [4]string
	Tabstop     int
	Version     bool
}

Options stores the values of command-line options

func ParseOptions

func ParseOptions() *Options

ParseOptions parses command-line options

type Pattern

type Pattern struct {
	// contains filtered or unexported fields
}

Pattern represents search pattern

func BuildPattern

func BuildPattern(fuzzy bool, extended bool, caseMode Case, forward bool,
	nth []Range, delimiter Delimiter, runes []rune) *Pattern

BuildPattern builds Pattern object from the given arguments

func (*Pattern) AsString

func (p *Pattern) AsString() string

AsString returns the search query in string type

func (*Pattern) CacheKey

func (p *Pattern) CacheKey() string

CacheKey is used to build string to be used as the key of result cache

func (*Pattern) IsEmpty

func (p *Pattern) IsEmpty() bool

IsEmpty returns true if the pattern is effectively empty

func (*Pattern) Match

func (p *Pattern) Match(chunk *Chunk) []*Item

Match returns the list of matches Items in the given Chunk

func (*Pattern) MatchItem

func (p *Pattern) MatchItem(item *Item) bool

MatchItem returns true if the Item is a match

type Range

type Range struct {
	// contains filtered or unexported fields
}

Range represents nth-expression

func ParseRange

func ParseRange(str *string) (Range, bool)

ParseRange parses nth-expression and returns the corresponding Range object

type Reader

type Reader struct {
	// contains filtered or unexported fields
}

Reader reads from command or standard input

func (*Reader) ReadSource

func (r *Reader) ReadSource()

ReadSource reads data from the default command or from standard input

type Terminal

type Terminal struct {
	// contains filtered or unexported fields
}

Terminal represents terminal input/output

func NewTerminal

func NewTerminal(opts *Options, eventBox *util.EventBox) *Terminal

NewTerminal returns new Terminal object

func (*Terminal) Input

func (t *Terminal) Input() []rune

Input returns current query string

func (*Terminal) Loop

func (t *Terminal) Loop()

Loop is called to start Terminal I/O

func (*Terminal) UpdateCount

func (t *Terminal) UpdateCount(cnt int, final bool)

UpdateCount updates the count information

func (*Terminal) UpdateHeader

func (t *Terminal) UpdateHeader(header []string)

UpdateHeader updates the header

func (*Terminal) UpdateList

func (t *Terminal) UpdateList(merger *Merger)

UpdateList updates Merger to display the list

func (*Terminal) UpdateProgress

func (t *Terminal) UpdateProgress(progress float32)

UpdateProgress updates the search progress

type Token

type Token struct {
	// contains filtered or unexported fields
}

Token contains the tokenized part of the strings and its prefix length

func Tokenize

func Tokenize(runes []rune, delimiter Delimiter) []Token

Tokenize tokenizes the given string with the delimiter

func Transform

func Transform(tokens []Token, withNth []Range) []Token

Transform is used to transform the input when --with-nth option is given

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL