1

I am testing the use of an NSTask because I want to try to run a bunch of commands within my Cocoa application written in Swift that I usually run in Terminal.

In viewDidLoad I have the following code:

    let task = NSTask()
    let pipe = NSPipe()
    task.standardOutput = pipe

    task.launchPath = "/usr/bash"
    task.currentDirectoryPath = dir
    task.arguments = ["ls"]

    let file:NSFileHandle = pipe.fileHandleForReading

    task.launch()
    task.waitUntilExit()

    let data =  file.readDataToEndOfFile()
    let datastring = NSString(data: data, encoding: NSUTF8StringEncoding)
    print("datastring = \(datastring)")

The app runs but I am getting the following error:

Failed to set (contentViewController) user defined inspected property on (NSWindow): launch path not accessible

Can somebody help me understand what I am doing wrong? What I am trying to do now is to run the ls command and then store the result into an array of strings...

Thanks

zumzum
  • 17,984
  • 26
  • 111
  • 172
  • 1
    if `ls` is a real example consider using the native Foundation class `NSFileManager` instead. – vadian Aug 16 '15 at 17:41

1 Answers1

3

Well, for starters, /usr/bash is not the path to the bash executable. You want /bin/bash.

Next, it does not work to invoke /bin/bash ls, which is the equivalent of what you're doing. At a shell, if you want to give a command for bash to process and execute, you would do /bin/bash -c ls. So, you want to set the tasks's arguments to ["-c", "ls"].

However, why are you involving a shell interpreter here, at all? Why not just set the task's launchPath to "/bin/ls" and run the ls command directly? You would either leave the arguments unset, if you just want to list the current working directory's contents, or set it to arguments that you would pass to ls, such as options or a path (e.g. ["-l", "/Applications"]).

Ken Thomases
  • 88,520
  • 7
  • 116
  • 154
  • task.launchPath = "/bin/bash", task.currentDirectoryPath = dir, task.arguments = ["-c","ls"] got rid of the error. Can you explain why I need to use the -c ? – zumzum Aug 16 '15 at 17:57
  • 1
    Because that's how `bash` works. If you supply a direct argument, it tries to use it as a path to a script file. You were trying to make `bash` interpret `"ls"` as a command string. It only does that when you specify `-c` followed by a command string. See the [`bash` man page](https://developer.apple.com/library/mac/documentation/Darwin/Reference/ManPages/man1/bash.1.html). – Ken Thomases Aug 16 '15 at 18:09