0

这是我的代码:

NSTask *setupTask = [NSTask new];
[setupTask setLaunchPath:@"/bin/sh"];
[setupTask setArguments:[NSArray arrayWithObject:@"/applications/jarvis/brain/server.sh"]];
[setupTask setCurrentDirectoryPath:@"/"];
NSPipe *outputPipeSetup = [NSPipe pipe];
[setupTask setStandardInput:[NSPipe pipe]];
[setupTask setStandardOutput:outputPipeSetup];
[setupTask launch];

NSTask *aliceTask = [NSTask new];
[aliceTask setLaunchPath:@"/usr/bin/java"];
[aliceTask setArguments:[NSArray arrayWithObjects:@"-classpath", @"/applications/jarvis/brain/", @"-Xms64m", @"-Xmx128m", @"org.alicebot.server.net.AliceServer", nil]];

 NSPipe *aliceInputPipe = [NSPipe pipe];
 [aliceTask setStandardInput:aliceInputPipe];
 NSPipe *aliceOutputPipe = [NSPipe pipe];
 [aliceTask setStandardOutput:aliceOutputPipe];

 [aliceTask launch];

NSMutableString *outputString = [NSMutableString string];
while ([outputString rangeOfString:@"Jarvis>"].location == NSNotFound) {
    [outputString appendString:[[[NSString alloc] initWithData:[[aliceOutputPipe fileHandleForReading] readDataToEndOfFile] encoding:NSUTF8StringEncoding] autorelease]];
}

但是, outputString 什么都不返回,它卡在了 while 循环中。这是 server.sh 文件:

echo Starting Jarvis Program D.
ALICE_HOME=.
SERVLET_LIB=lib/servlet.jar
ALICE_LIB=lib/aliceserver.jar
JS_LIB=lib/js.jar

# Set SQL_LIB to the location of your database driver.
SQL_LIB=lib/mysql_comp.jar

# These are for Jetty; you will want to change these if you are using a different http server.
 HTTP_SERVER_LIBS=lib/org.mortbay.jetty.jar

 PROGRAMD_CLASSPATH=$SERVLET_LIB:$ALICE_LIB:$JS_LIB:$SQL_LIB:$HTTP_SERVER_LIBS
 java -classpath $PROGRAMD_CLASSPATH -Xms64m -Xmx128m org.alicebot.server.net.AliceServer $1
4

1 回答 1

0

您可以尝试仅使用一个调用以下命令的 NSTask 来处理 server.sh 输出: sh -c 'source server.sh | sed "/Jarvis>/q"'(参见 shstring)。在这个简化的代码示例中,server.sh (shfile) 只包含一个 cat(1) 命令,用于将 test.file 的内容写入标准输出。也许您也可以将从 Objective-C 调用的 java 命令添加到 shstring 中?

#import <Foundation/Foundation.h>

/*

See:
http://stackoverflow.com/questions/3505942/i-cant-see-the-output-of-nstask-objective-c-java

compile with:
gcc -Wall -O3 -x objective-c -fobjc-exceptions -framework Foundation -o test test.c

./test

# create test.file
n=50
jot -b 'line' $n | nl -w 10 > test.file
echo "Jarvis>" | nl -w 10 -v $((n+1)) >> test.file
jot -b 'line' 19 | nl -w 10 -v $((n+2)) >> test.file

ls -lh test.file
tail -n 100 test.file

# create server.sh
echo '
cat test.file
' > server.sh

sh server.sh

./test

*/


int main(int argc, const char *argv[])
{

    NSAutoreleasePool *pool =  [[NSAutoreleasePool alloc] init];
    NSString *shfile = @"server.sh";

    NSString *shstring = [NSString stringWithFormat:
             @"%@ %@ %@", 
             @"source", 
             shfile, 
             @"| /usr/bin/sed '/Jarvis>/q'"
    ];

    NSTask *sh = [NSTask new];
    NSPipe *pipe = [NSPipe new];
    [sh setLaunchPath:@"/bin/sh"];
    [sh setArguments:[NSArray arrayWithObjects: @"-c", shstring, nil ]];
    [sh setCurrentDirectoryPath:@"."];
    //[sh setStandardInput:[NSFileHandle fileHandleWithNullDevice]];
    [sh setStandardError:[NSFileHandle fileHandleWithNullDevice]];
    [sh setStandardOutput:pipe];
    [sh launch];

    NSData *data = [[[sh standardOutput] fileHandleForReading] readDataToEndOfFile];
    NSString *string = [[[NSString alloc] initWithData:data encoding: NSUTF8StringEncoding] autorelease];

    NSLog(@"\n\n%@\n", string);

    [pool release];

    return 0;

}
于 2010-08-18T22:12:39.200 回答