下面是我的代码:
task = [[NSTask alloc] init];
[task setCurrentDirectoryPath:@"/applications/jarvis/brain/"];
[task setLaunchPath:@"/applications/jarvis/brain/server.sh"];
NSPipe * out = [NSPipe pipe];
[task setStandardOutput:out];
[task launch];
[task waitUntilExit];
[task release];
NSFileHandle * read = [out fileHandleForReading];
NSData * dataRead = [read readDataToEndOfFile];
NSString * stringRead = [[[NSString alloc] initWithData:dataRead encoding:NSUTF8StringEncoding] autorelease];所以我试着复制这个:
cd /applications/jarvis/brain/
./server.sh但在objective-c中使用NSTask。
但是,由于某些原因,当我运行这段代码时,stringRead什么也不返回。当我启动.sh文件时,它应该返回终端返回的内容。对,是这样?
有什么想法吗?
以利亚
发布于 2010-08-13 03:52:31
Xcode错误
Xcode中有一个bug,在使用标准输出的新任务启动后,它停止打印任何输出(它收集所有输出,但不再打印任何输出)。您必须调用[task setStandardInput:[NSPipe pipe]]让它再次显示输出(或者,让任务打印到stderr而不是stdout)。
最终代码的建议:
NSTask *server = [NSTask new];
[server setLaunchPath:@"/bin/sh"];
[server setArguments:[NSArray arrayWithObject:@"/path/to/server.sh"]];
[server setCurrentDirectoryPath:@"/path/to/current/directory/"];
NSPipe *outputPipe = [NSPipe pipe];
[server setStandardInput:[NSPipe pipe]];
[server setStandardOutput:outputPipe];
[server launch];
[server waitUntilExit]; // Alternatively, make it asynchronous.
[server release];
NSData *outputData = [[outputPipe fileHandleForReading] readDataToEndOfFile];
NSString *outputString = [[[NSString alloc] initWithData:outputData encoding:NSUTF8StringEncoding] autorelease]; // Autorelease optional, depending on usage.发布于 2013-04-29 17:06:39
上面的解决方案是冻结的,因为它是同步的。调用[server waitUntilExit]会阻止运行循环,直到任务完成。
下面是获取任务输出的异步解决方案。
task.standardOutput = [NSPipe pipe];
[[task.standardOutput fileHandleForReading] setReadabilityHandler:^(NSFileHandle *file) {
NSData *data = [file availableData]; // this will read to EOF, so call only once
NSLog(@"Task output! %@", [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
// if you're collecting the whole output of a task, you may store it on a property
[self.taskOutput appendData:data];
}];您可能希望对task.standardError重复上述操作。
重要信息:
当您的任务终止时,您必须将readabilityHandler块设置为空;否则,您将遇到高CPU使用率,因为读取永远不会停止。
[task setTerminationHandler:^(NSTask *task) {
// do your stuff on completion
[task.standardOutput fileHandleForReading].readabilityHandler = nil;
[task.standardError fileHandleForReading].readabilityHandler = nil;
}];这都是异步的(你应该异步地做),所以你的方法应该有一个^完成块。
https://stackoverflow.com/questions/3444178
复制相似问题