2013-06-27 55 views
7

好的。有關堆棧溢出的幾個問題。 This question was the only question與地雷最接近,但它使用通知。NSTask啓動路徑無法訪問。適用於Xcode。顯示出來的錯誤XCode

該代碼非常簡單。創建一個新的空白Mac OSX項目,並將以下代碼粘貼到applicationDidFinishLaunching:方法中。它應該得到任何可執行文件的路徑(在這種情況下爲GIT)。

NSTask *aTask = [[NSTask alloc] init]; 
NSPipe *outputPipe = [NSPipe pipe]; 
NSPipe *errorPipe = [NSPipe pipe]; 

[aTask setStandardOutput: outputPipe]; 
[aTask setStandardError: errorPipe]; 
[aTask setArguments:[NSArray arrayWithObject:@"which"]]; 
[aTask setLaunchPath:@"/usr/bin/git"]; 

NSFileHandle *outputFileHandler = [outputPipe fileHandleForReading]; 
NSFileHandle *errorFileHandler = [errorPipe fileHandleForReading]; 

[aTask launch]; 
[aTask waitUntilExit]; 

// Task launched now just read and print the data 
NSData *data = [outputFileHandler readDataToEndOfFile]; 
NSString *outPutValue = [[NSString alloc] initWithData: data encoding: NSUTF8StringEncoding]; 

NSData *errorData = [errorFileHandler readDataToEndOfFile]; 
NSString *errorValue = [[NSString alloc] initWithData:errorData encoding:NSUTF8StringEncoding]; 

NSLog(@"Error value: %@",errorValue); 
NSLog(@"Output Value: %@",outPutValue); 

此代碼設置兩個讀取管道並運行一個命令:which git

如果我在XCode中運行此我得到這個結果corretly:

Error value: "" 
Output Value: /usr/bin/git 

如果我去我的生成/產品/ Debug文件夾中,雙擊可執行文件,我得到的控制檯應用程序打印此消息:

enter image description here

問:那麼,什麼是真正的問題就在這裏?請不要做出替代解決方案...我也想知道問題是什麼..謝謝。

回答

13

事實證明,答案是堆棧溢出,但其分佈在不同的問題。

的問題在這裏問 - >Commands with NSTask這裏 - >NSTask launch path not accessible以及

但他們爲這一天的答案的arent清楚的問題是什麼。只有在閱讀NSTask not picking up $PATH from the user's environment(問題的標題是誤導性的)以及這兩個答案NSTask not picking up $PATH from the user's environmentFind out location of an executable file in Cocoa之後,我才意識到了解決方案。

看起來這是關於設立或者NS 任務或用戶的shell(如〜/ .bashrc)中,以便正確 環境($ PATH)由NSTask看到。

解決方案:

[task setLaunchPath:@"/bin/bash"]; 
NSArray *args = [NSArray arrayWithObjects:@"-l", 
       @"-c", 
       @"which git", //Assuming git is the launch path you want to run 
       nil]; 
[task setArguments: args]; 

然而,這假定用戶的shell是總是 bash和它將會失敗他人。通過確定殼來解決這個問題。

NSDictionary *environmentDict = [[NSProcessInfo processInfo] environment]; 
NSString *shellString = [environmentDict objectForKey:@"SHELL"];