127 lines
2.6 KiB
Go
127 lines
2.6 KiB
Go
package shell
|
|
|
|
import (
|
|
"errors"
|
|
"fmt"
|
|
"os"
|
|
"os/exec"
|
|
"syscall"
|
|
|
|
"go.wit.com/log"
|
|
)
|
|
|
|
func Exec(args []string) error {
|
|
if len(args) == 0 {
|
|
return errors.New("Error: Command slice is empty.")
|
|
}
|
|
|
|
// Start a long-running process, capture stdout and stderr
|
|
a, b := RemoveFirstElement(args)
|
|
|
|
process := exec.Command(a, b...)
|
|
process.Stderr = os.Stderr
|
|
process.Stdin = os.Stdin
|
|
process.Stdout = os.Stdout
|
|
process.Start()
|
|
err := process.Wait()
|
|
log.Log(INFO, "shell.Exec() err =", err)
|
|
return nil
|
|
}
|
|
|
|
func ExecCheck(args []string) error {
|
|
if len(args) == 0 {
|
|
return errors.New("Error: Command slice is empty.")
|
|
}
|
|
|
|
// Start a long-running process, capture stdout and stderr
|
|
a, b := RemoveFirstElement(args)
|
|
|
|
process := exec.Command(a, b...)
|
|
process.Stderr = os.Stderr
|
|
process.Stdin = os.Stdin
|
|
process.Stdout = os.Stdout
|
|
err := process.Run()
|
|
if err != nil {
|
|
log.Info("ExecCheck() err", err)
|
|
return err
|
|
}
|
|
// log.Info("ExecCheck() nil")
|
|
return nil
|
|
}
|
|
|
|
func PathExecVerbose(path string, args []string) error {
|
|
if len(args) == 0 {
|
|
return errors.New("Error: Command slice is empty.")
|
|
}
|
|
|
|
// Start a long-running process, capture stdout and stderr
|
|
a, b := RemoveFirstElement(args)
|
|
|
|
process := exec.Command(a, b...)
|
|
process.Dir = path
|
|
process.Stderr = os.Stderr
|
|
process.Stdin = os.Stdin
|
|
process.Stdout = os.Stdout
|
|
err := process.Run()
|
|
if err != nil {
|
|
log.Info("ExecCheck() err", err)
|
|
return err
|
|
}
|
|
// log.Info("ExecCheck() nil")
|
|
return nil
|
|
}
|
|
|
|
func SudoRaw(c []string) {
|
|
args := []string{"-S"}
|
|
args = append(args, c...)
|
|
cmd := exec.Command("sudo", args...)
|
|
|
|
// Assign the current process's standard input, output, and error
|
|
cmd.Stderr = os.Stderr
|
|
cmd.Stdout = os.Stdout
|
|
cmd.Stdin = os.Stdin
|
|
|
|
// Ensure the process has a terminal session
|
|
cmd.SysProcAttr = &syscall.SysProcAttr{
|
|
Setsid: true, // Start a new session
|
|
}
|
|
|
|
err := cmd.Run()
|
|
if err != nil {
|
|
fmt.Println("Command execution failed:", err)
|
|
}
|
|
}
|
|
|
|
func Sudo(c []string) error {
|
|
args := []string{"-S"}
|
|
// args := []string{}
|
|
args = append(args, c...)
|
|
cmd := exec.Command("sudo", args...)
|
|
|
|
// Open the terminal device directly to preserve input/output control
|
|
tty, err := os.OpenFile("/dev/tty", os.O_RDWR, 0)
|
|
if err != nil {
|
|
fmt.Println("Failed to open /dev/tty:", err)
|
|
return err
|
|
}
|
|
defer tty.Close()
|
|
|
|
// Assign the TTY explicitly
|
|
cmd.Stdin = tty
|
|
cmd.Stdout = tty
|
|
cmd.Stderr = tty
|
|
|
|
// Ensure the new process gets its own session
|
|
cmd.SysProcAttr = &syscall.SysProcAttr{
|
|
Setsid: true, // Start a new session
|
|
}
|
|
|
|
// Run the command
|
|
if err := cmd.Run(); err != nil {
|
|
fmt.Println("Command execution failed:", err)
|
|
}
|
|
|
|
fmt.Println("\nProcess finished. TTY restored.")
|
|
return nil
|
|
}
|