oscommands

package
v0.0.0-...-00ab8b8 Latest Latest
Warning

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

Go to latest
Published: Mar 15, 2024 License: MIT Imports: 26 Imported by: 0

Documentation

Index

Constants

View Source
const CHARS_REQUIRING_QUOTES = "\"\\$` "

Variables

This section is empty.

Functions

func CopyDir

func CopyDir(src string, dst string) (err error)

CopyDir recursively copies a directory tree, attempting to preserve permissions. Source directory must exist. If destination already exists we'll clobber it. Symlinks are ignored and skipped.

func CopyFile

func CopyFile(src, dst string) (err error)

CopyFile copies the contents of the file named src to the file named by dst. The file will be created if it does not already exist. If the destination file exists, all it's contents will be replaced by the contents of the source file. The file mode will be copied from the source and the copied data is synced/flushed to stable storage.

func FileType

func FileType(path string) string

FileType tells us if the file is a file, directory or other

func GetLazygitPath

func GetLazygitPath() string

GetLazygitPath returns the path of the currently executed file

func Kill

func Kill(cmd *exec.Cmd) error

Kill kills a process. If the process has Setpgid == true, then we have anticipated that it might spawn its own child processes, so we've given it a process group ID (PGID) equal to its process id (PID) and given its child processes will inherit the PGID, we can kill that group, rather than killing the process itself.

func NewGuiIO

func NewGuiIO(
	log *logrus.Entry,
	logCommandFn func(string, bool),
	newCmdWriterFn func() io.Writer,
	promptForCredentialFn func(CredentialType) <-chan string,
) *guiIO

func NewNullGuiIO

func NewNullGuiIO(log *logrus.Entry) *guiIO

we use this function when we want to access the functionality of our OS struct but we don't have anywhere to log things, or request input from the user.

func PrepareForChildren

func PrepareForChildren(cmd *exec.Cmd)

PrepareForChildren sets Setpgid to true on the cmd, so that when we run it as a subprocess, we can kill its group rather than the process itself. This is because some commands, like `docker-compose logs` spawn multiple children processes, and killing the parent process isn't sufficient for killing those child processes. We set the group id here, and then in subprocess.go we check if the group id is set and if so, we kill the whole group rather than just the one process.

Types

type CmdObj

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

func (*CmdObj) AddEnvVars

func (self *CmdObj) AddEnvVars(vars ...string) ICmdObj

func (*CmdObj) Args

func (self *CmdObj) Args() []string

func (*CmdObj) Clone

func (self *CmdObj) Clone() ICmdObj

func (*CmdObj) DontLog

func (self *CmdObj) DontLog() ICmdObj

func (*CmdObj) FailOnCredentialRequest

func (self *CmdObj) FailOnCredentialRequest() ICmdObj

func (*CmdObj) GetCmd

func (self *CmdObj) GetCmd() *exec.Cmd

func (*CmdObj) GetCredentialStrategy

func (self *CmdObj) GetCredentialStrategy() CredentialStrategy

func (*CmdObj) GetEnvVars

func (self *CmdObj) GetEnvVars() []string

func (*CmdObj) GetTask

func (self *CmdObj) GetTask() gocui.Task

func (*CmdObj) IgnoreEmptyError

func (self *CmdObj) IgnoreEmptyError() ICmdObj

func (*CmdObj) Mutex

func (self *CmdObj) Mutex() *deadlock.Mutex

func (*CmdObj) PromptOnCredentialRequest

func (self *CmdObj) PromptOnCredentialRequest(task gocui.Task) ICmdObj

func (*CmdObj) Run

func (self *CmdObj) Run() error

func (*CmdObj) RunAndProcessLines

func (self *CmdObj) RunAndProcessLines(onLine func(line string) (bool, error)) error

func (*CmdObj) RunWithOutput

func (self *CmdObj) RunWithOutput() (string, error)

func (*CmdObj) RunWithOutputs

func (self *CmdObj) RunWithOutputs() (string, string, error)

func (*CmdObj) SetWd

func (self *CmdObj) SetWd(wd string) ICmdObj

func (*CmdObj) ShouldIgnoreEmptyError

func (self *CmdObj) ShouldIgnoreEmptyError() bool

func (*CmdObj) ShouldLog

func (self *CmdObj) ShouldLog() bool

func (*CmdObj) ShouldStreamOutput

func (self *CmdObj) ShouldStreamOutput() bool

func (*CmdObj) StreamOutput

func (self *CmdObj) StreamOutput() ICmdObj

func (*CmdObj) ToString

func (self *CmdObj) ToString() string

func (*CmdObj) WithMutex

func (self *CmdObj) WithMutex(mutex *deadlock.Mutex) ICmdObj

type CmdObjBuilder

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

func NewDummyCmdObjBuilder

func NewDummyCmdObjBuilder(runner ICmdObjRunner) *CmdObjBuilder

func (*CmdObjBuilder) CloneWithNewRunner

func (self *CmdObjBuilder) CloneWithNewRunner(decorate func(ICmdObjRunner) ICmdObjRunner) *CmdObjBuilder

func (*CmdObjBuilder) New

func (self *CmdObjBuilder) New(args []string) ICmdObj

func (*CmdObjBuilder) NewShell

func (self *CmdObjBuilder) NewShell(commandStr string) ICmdObj

func (*CmdObjBuilder) NewWithEnviron

func (self *CmdObjBuilder) NewWithEnviron(args []string, env []string) ICmdObj

A command with explicit environment from env

func (*CmdObjBuilder) Quote

func (self *CmdObjBuilder) Quote(message string) string

If you update this method, be sure to update CHARS_REQUIRING_QUOTES

type CmdObjMatcher

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

type CredentialStrategy

type CredentialStrategy int
const (
	// do not expect a credential request. If we end up getting one
	// we'll be in trouble because the command will hang indefinitely
	NONE CredentialStrategy = iota
	// expect a credential request and if we get one, prompt the user to enter their username/password
	PROMPT
	// in this case we will check for a credential request (i.e. the command pauses to ask for
	// username/password) and if we get one, we just submit a newline, forcing the
	// command to fail. We use this e.g. for a background `git fetch` to prevent it
	// from hanging indefinitely.
	FAIL
)

type CredentialType

type CredentialType int
const (
	Password CredentialType = iota
	Username
	Passphrase
	PIN
)

type FakeCmdObjRunner

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

func NewFakeRunner

func NewFakeRunner(t *testing.T) *FakeCmdObjRunner

func (*FakeCmdObjRunner) CheckForMissingCalls

func (self *FakeCmdObjRunner) CheckForMissingCalls()

func (*FakeCmdObjRunner) ExpectArgs

func (self *FakeCmdObjRunner) ExpectArgs(expectedArgs []string, output string, err error) *FakeCmdObjRunner

func (*FakeCmdObjRunner) ExpectFunc

func (self *FakeCmdObjRunner) ExpectFunc(description string, fn func(cmdObj ICmdObj) bool, output string, err error) *FakeCmdObjRunner

func (*FakeCmdObjRunner) ExpectGitArgs

func (self *FakeCmdObjRunner) ExpectGitArgs(expectedArgs []string, output string, err error) *FakeCmdObjRunner

func (*FakeCmdObjRunner) Run

func (self *FakeCmdObjRunner) Run(cmdObj ICmdObj) error

func (*FakeCmdObjRunner) RunAndProcessLines

func (self *FakeCmdObjRunner) RunAndProcessLines(cmdObj ICmdObj, onLine func(line string) (bool, error)) error

func (*FakeCmdObjRunner) RunWithOutput

func (self *FakeCmdObjRunner) RunWithOutput(cmdObj ICmdObj) (string, error)

func (*FakeCmdObjRunner) RunWithOutputs

func (self *FakeCmdObjRunner) RunWithOutputs(cmdObj ICmdObj) (string, string, error)

type ICmdObj

type ICmdObj interface {
	GetCmd() *exec.Cmd
	// outputs string representation of command. Note that if the command was built
	// using NewFromArgs, the output won't be quite the same as what you would type
	// into a terminal e.g. 'sh -c git commit' as opposed to 'sh -c "git commit"'
	ToString() string

	// outputs args vector e.g. ["git", "commit", "-m", "my message"]
	Args() []string

	AddEnvVars(...string) ICmdObj
	GetEnvVars() []string

	// sets the working directory
	SetWd(string) ICmdObj

	// runs the command and returns an error if any
	Run() error
	// runs the command and returns the output as a string, and an error if any
	RunWithOutput() (string, error)
	// runs the command and returns stdout and stderr as a string, and an error if any
	RunWithOutputs() (string, string, error)
	// runs the command and runs a callback function on each line of the output. If the callback returns true for the boolean value, we kill the process and return.
	RunAndProcessLines(onLine func(line string) (bool, error)) error

	// Be calling DontLog(), we're saying that once we call Run(), we don't want to
	// log the command in the UI (it'll still be logged in the log file). The general rule
	// is that if a command doesn't change the git state (e.g. read commands like `git diff`)
	// then we don't want to log it. If we are changing something (e.g. `git add .`) then
	// we do. The only exception is if we're running a command in the background periodically
	// like `git fetch`, which technically does mutate stuff but isn't something we need
	// to notify the user about.
	DontLog() ICmdObj

	// This returns false if DontLog() was called
	ShouldLog() bool

	// when you call this, then call Run(), we'll stream the output to the cmdWriter (i.e. the command log panel)
	StreamOutput() ICmdObj
	// returns true if StreamOutput() was called
	ShouldStreamOutput() bool

	// if you call this before ShouldStreamOutput we'll consider an error with no
	// stderr content as a non-error. Not yet supported for Run or RunWithOutput (
	// but adding support is trivial)
	IgnoreEmptyError() ICmdObj
	// returns true if IgnoreEmptyError() was called
	ShouldIgnoreEmptyError() bool

	PromptOnCredentialRequest(task gocui.Task) ICmdObj
	FailOnCredentialRequest() ICmdObj

	WithMutex(mutex *deadlock.Mutex) ICmdObj
	Mutex() *deadlock.Mutex

	GetCredentialStrategy() CredentialStrategy
	GetTask() gocui.Task

	Clone() ICmdObj
}

A command object is a general way to represent a command to be run on the command line.

type ICmdObjBuilder

type ICmdObjBuilder interface {
	// NewFromArgs takes a slice of strings like []string{"git", "commit"} and returns a new command object.
	New(args []string) ICmdObj
	// NewShell takes a string like `git commit` and returns an executable shell command for it e.g. `sh -c 'git commit'`
	NewShell(commandStr string) ICmdObj
	// Quote wraps a string in quotes with any necessary escaping applied. The reason for bundling this up with the other methods in this interface is that we basically always need to make use of this when creating new command objects.
	Quote(str string) string
}

type ICmdObjRunner

type ICmdObjRunner interface {
	Run(cmdObj ICmdObj) error
	RunWithOutput(cmdObj ICmdObj) (string, error)
	RunWithOutputs(cmdObj ICmdObj) (string, string, error)
	RunAndProcessLines(cmdObj ICmdObj, onLine func(line string) (bool, error)) error
}

type OSCommand

type OSCommand struct {
	*common.Common
	Platform *Platform

	Cmd *CmdObjBuilder
	// contains filtered or unexported fields
}

OSCommand holds all the os commands

func NewDummyOSCommand

func NewDummyOSCommand() *OSCommand

NewDummyOSCommand creates a new dummy OSCommand for testing

func NewDummyOSCommandWithDeps

func NewDummyOSCommandWithDeps(deps OSCommandDeps) *OSCommand

func NewDummyOSCommandWithRunner

func NewDummyOSCommandWithRunner(runner *FakeCmdObjRunner) *OSCommand

func NewOSCommand

func NewOSCommand(common *common.Common, config config.AppConfigurer, platform *Platform, guiIO *guiIO) *OSCommand

NewOSCommand os command runner

func (*OSCommand) AppendLineToFile

func (c *OSCommand) AppendLineToFile(filename, line string) error

AppendLineToFile adds a new line in file

func (*OSCommand) CopyToClipboard

func (c *OSCommand) CopyToClipboard(str string) error

func (*OSCommand) CreateFileWithContent

func (c *OSCommand) CreateFileWithContent(path string, content string) error

CreateFileWithContent creates a file with the given content

func (*OSCommand) FileExists

func (c *OSCommand) FileExists(path string) (bool, error)

FileExists checks whether a file exists at the specified path

func (*OSCommand) GetTempDir

func (c *OSCommand) GetTempDir() string

func (*OSCommand) Getenv

func (c *OSCommand) Getenv(key string) string

func (*OSCommand) LogCommand

func (c *OSCommand) LogCommand(cmdStr string, commandLine bool)

func (*OSCommand) OpenFile

func (c *OSCommand) OpenFile(filename string) error
func (c *OSCommand) OpenLink(link string) error

func (*OSCommand) PipeCommands

func (c *OSCommand) PipeCommands(cmdObjs ...ICmdObj) error

PipeCommands runs a heap of commands and pipes their inputs/outputs together like A | B | C

func (*OSCommand) Quote

func (c *OSCommand) Quote(message string) string

Quote wraps a message in platform-specific quotation marks

func (*OSCommand) Remove

func (c *OSCommand) Remove(filename string) error

Remove removes a file or directory at the specified path

func (*OSCommand) RemoveFile

func (c *OSCommand) RemoveFile(path string) error

func (*OSCommand) UpdateWindowTitle

func (c *OSCommand) UpdateWindowTitle() error

type OSCommandDeps

type OSCommandDeps struct {
	Common       *common.Common
	Platform     *Platform
	GetenvFn     func(string) string
	RemoveFileFn func(string) error
	Cmd          *CmdObjBuilder
	TempDir      string
}

type Platform

type Platform struct {
	OS              string
	Shell           string
	ShellArg        string
	OpenCommand     string
	OpenLinkCommand string
}

Platform stores the os state

func GetPlatform

func GetPlatform() *Platform

Jump to

Keyboard shortcuts

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