Source File
prompt.go
Belonging Package
src.elv.sh/pkg/cli/prompt
// Package prompt provides an implementation of the cli.Prompt interface.package promptimport ()// Prompt implements a prompt that is executed asynchronously.type Prompt struct {config Config// Working directory when prompt was last updated.lastWd string// Channel for update requests.updateReq chan struct{}// Channel on which prompt contents are delivered.ch chan struct{}// Last computed prompt content.last ui.Text// Mutex for guarding access to the last field.lastMutex sync.RWMutex}// Config keeps configurations for the prompt.type Config struct {// The function that computes the prompt.Compute func() ui.Text// Function to transform stale prompts.StaleTransform func(ui.Text) ui.Text// Threshold for a prompt to be considered as stale.StaleThreshold func() time.Duration// How eager the prompt should be updated. When >= 5, updated when directory// is changed. When >= 10, always update. Default is 5.Eagerness func() int}func ( ui.Text) ui.Text {return ui.StyleText(, ui.Inverse)}const defaultStaleThreshold = 200 * time.Millisecondconst defaultEagerness = 5var unknownContent = ui.T("???> ")// New makes a new prompt.func ( Config) *Prompt {if .Compute == nil {.Compute = func() ui.Text { return unknownContent }}if .StaleTransform == nil {.StaleTransform = defaultStaleTransform}if .StaleThreshold == nil {.StaleThreshold = func() time.Duration { return defaultStaleThreshold }}if .Eagerness == nil {.Eagerness = func() int { return defaultEagerness }}:= &Prompt{,"", make(chan struct{}, 1), make(chan struct{}, 1),unknownContent, sync.RWMutex{}}// TODO: Don't keep a goroutine running.go .loop()return}func ( *Prompt) () {:= unknownContent:= make(chan ui.Text)for range .updateReq {go func() {<- .config.Compute()}()select {case <-time.After(.config.StaleThreshold()):// The prompt callback did not finish within the threshold. Send the// previous content, marked as stale..update(.config.StaleTransform())= <-select {case <-.updateReq:// If another update is already requested by the time we finish,// keep marking the prompt as stale. This reduces flickering..update(.config.StaleTransform()).queueUpdate()default:.update()}case = <-:.update()}}}// Trigger triggers an update to the prompt.func ( *Prompt) ( bool) {if || .shouldUpdate() {.queueUpdate()}}// Get returns the current content of the prompt.func ( *Prompt) () ui.Text {.lastMutex.RLock()defer .lastMutex.RUnlock()return .last}// LateUpdates returns a channel on which late updates are made available.func ( *Prompt) () <-chan struct{} {return .ch}func ( *Prompt) () {select {case .updateReq <- struct{}{}:default:}}func ( *Prompt) ( ui.Text) {.lastMutex.Lock().last =.lastMutex.Unlock().ch <- struct{}{}}func ( *Prompt) () bool {:= .config.Eagerness()if >= 10 {return true}if >= 5 {, := os.Getwd()if != nil {= "error"}:= .lastWd.lastWd =return !=}return false}
The pages are generated with Golds v0.2.8-preview. (GOOS=darwin GOARCH=arm64)