在熟悉Go和goroutine的过程中,我遇到了执行命令的障碍。这些命令的格式为:
sudo find /folder -type f | while read i; do sudo -S chmod 644 "$i"; done
使用从如何在Golang中执行系统命令的代码中获取未知参数的代码,我试图执行此命令,但是我相信由于第一个参数为sudo,该命令未执行,这可能是错误的。我只有两个问题。
当这些命令无法运行时,我将返回“退出状态1”,是否有办法比我正在执行的操作得到更详细的错误?问题二,为什么我使用此脚本会获得“退出状态1”?那到底是怎么回事?
package main import ( "bufio" "fmt" "os" "os/exec" "strings" "sync" ) func ExeCmd(cmd string, wg *sync.WaitGroup) { parts := strings.Fields(cmd) head := parts[0] // Head at this point is "sudo" parts = parts[1:len(parts)] out, err := exec.Command(head,parts...).Output() if err != nil { fmt.Printf("%s\n", err) } fmt.Printf("%s\n", out) wg.Done() // Signal to WaitGroup goroutine finished } func InArray(a []string, e string) bool { for _, x := range a { if x == e { return true fmt.Print("True") } } return false } func main() { exec.Command("sudo ls > /dev/null") // Get sudo password just once, doesn't seem to work with Go wg := new(sync.WaitGroup) reader := bufio.NewReader(os.Stdin) fdbslices := []string{"f", "d", "b", "files", "directories", "both"} commands := []string{} fdb := "" filep := "" dirp := "" // Grab Path fmt.Print("Path: ") findpath, _ := reader.ReadString('\n') findpath = strings.ToLower(strings.Trim(findpath, "\n")) // Grab Files, Directories, or Both for { fmt.Print("Files, Directories, or Both: ") fdb, _ = reader.ReadString('\n') fdb = strings.ToLower(strings.Trim(fdb, "\n")) if InArray(fdbslices, fdb) == true { break } } // Build commands string, these come out as they should for { if fdb == "f" || fdb == "files" { fmt.Print("Permissions for Files: ") filep, _ = reader.ReadString('\n') filep = strings.Trim(filep, "\n") commands = append(commands, "sudo find " + findpath + " -type f | while read i; do sudo -S chmod " + filep + " \"$i\"; done") } if fdb == "d" || fdb == "directories" { fmt.Print("Permissions for Directories: ") dirp, _ = reader.ReadString('\n') dirp = strings.Trim(dirp, "\n") commands = append(commands, "sudo find " + findpath + " -type d | while read i; do sudo -S chmod " + dirp + " \"$i\"; done") } if fdb == "b" || fdb == "both" { fmt.Print("Permissions for Files: ") filep, _ = reader.ReadString('\n') filep = strings.Trim(filep, "\n") commands = append(commands, "sudo find " + findpath + " -type f | while read i; do sudo -S chmod " + filep + " \"$i\"; done") fmt.Print("Permissions for Directories: ") dirp, _ = reader.ReadString('\n') dirp = strings.Trim(dirp, "\n") commands = append(commands, "sudo find " + findpath + " -type d | while read i; do sudo -S chmod " + dirp + " \"$i\"; done") } break } // Execute Commands for _, str := range commands { wg.Add(1) fmt.Print("Doing: " + str + "\r\n") go ExeCmd(str, wg) } wg.Wait() }
终端输出示例:
Path: test Files, Directories, or Both: b Permissions for Files: 644 Permissions for Directories: 755 Doing: find test -type f | while read i; do sudo -S chmod 644 "$i"; done Doing: find test -type d | while read i; do sudo -S chmod 755 "$i"; done exit status 1 exit status 1
感谢您的时间。
exec.Command()将要求内核直接执行给定的进程。但是,您传递的命令是由外壳程序脚本链接在一起的多个程序的字符串。
exec.Command()
如果要执行Shell脚本,则应使用以下内容:
cmd := exec.Command("/bin/sh", "-c", "sudo find ...")