gpt4 book ai didi

java - 如何使用 ScriptEngine 将 Javascript 的输出转换为 Java

转载 作者:搜寻专家 更新时间:2023-10-31 20:28:55 25 4
gpt4 key购买 nike

通过这个简单的 applescript,我可以列出 iTunes 中所有歌曲的名称

tell application "iTunes"
set mainLibrary to library playlist 1
repeat with nexttrack in (get every track of mainLibrary)
try
name of nexttrack
end try
end repeat
end tell

然后我使用 ScriptEngine 将它作为 Java 7 代码运行,但是很明显如何获得脚本的结果,在这种情况下,它只是最后一首轨道的名称。

    StringBuilder script =new StringBuilder();
script.append("tell application \"iTunes\"\n");
script.append("set mainLibrary to library playlist 1\n");
script.append("repeat with nexttrack in (get every track of mainLibrary)\n");
script.append("try\n");
script.append("name of nexttrack\n");
script.append("end try\n");
script.append("end repeat\n");
script.append("end tell\n");
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine engine = mgr.getEngineByName("AppleScript");
System.out.println(engine.eval(script.toString()));

How do can I capture the name of all tracks , i.e all output from the script. I assume I have to redirect standard out to a Reader, but cannot see how to do it.

更新:

I found this article 

http://www.informit.com/articles/article.aspx?p=696621&seqNum=6

但是通过代码更新为

StringBuilder script =new StringBuilder();
script.append("tell application \"iTunes\"\n");
script.append("set mainLibrary to library playlist 1\n");
script.append("repeat with nexttrack in (get every track of mainLibrary)\n");
script.append("try\n");
script.append("name of nexttrack\n");
script.append("end try\n");
script.append("end repeat\n");
script.append("end tell\n");
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine engine = mgr.getEngineByName("AppleScript");
StringWriter sw = new StringWriter();
PrintWriter pw = new PrintWriter(sw);
StringWriter swError = new StringWriter();
PrintWriter pwError = new PrintWriter(swError);
engine.getContext().setWriter(pw);
engine.getContext().setErrorWriter(pwError);

System.out.println(engine.eval(script.toString()));
System.out.println("************* engine:"+sw.getBuffer());
System.out.println("************* engine error:"+swError.getBuffer());

只是输出

See You on the Other Side (short)
************* engine:
************* engine error:

因此您可以清楚地看到脚本在运行,因为 eval 显示了最后一首轨道的名称,但我没有从重定向的作者那里得到任何回复。想知道这是否真的适用于 applescript?

更新 2我用 Javascript 编写了一个测试,发现设置编写器确实有效,所以我认为要么

  1. OSX 上 Java 7 早期访问版本的 Applescript(我使用的是最新版本 1.7.0_40-ea-b29)的脚本引擎出现问题
  2. 我的 Applescript 是错误的,即不仅仅是 nexttrack 的名称 我应该做一些像 echo name of nexttrack 这样的事情来真正让它转到标准输出。

我认为 (2) 是问题所在,但我找不到任何关于在 Applescript 中输出文本的引用,echo 不是有效命令,print 命令确实尝试打印到打印机,而不是像在 Java 或 C 中那样打印到标准输出。

更新 3所以我无法让它工作,现在想知道 Applescript 是否只写返回值。我找到了一个使用 stdout 的示例(或者我认为如此),但我认为这只是一个命名约定,事实上它所做的只是不断地将数据附加到一个变量,并最终返回它。

所以我通过使用存储在文件中的以下脚本,然后在 Java 中使用了 engine.eval(new java.io.FileReader("filename")

tell application "iTunes"
set output to ""
set mainLibrary to library playlist 1
repeat with nexttrack in (get every track of mainLibrary)
if (class of nexttrack is file track) then
try
set trackname to name of nexttrack
set loc to location of nexttrack
set locpath to POSIX path of loc
set persistid to persistent ID of nexttrack
set nextline to trackname & "::" & locpath & "::" & persistid
set output to output & "\n" & nextline
end try
end if
end repeat
copy output to stdout
end tell

但这实际上并没有解决最初的问题,它的一个问题是如果有任何错误,我将不会得到任何回复,而如果它在读取我的 iTunes 库的过程中失败并且我正在使用 stdout 我至少会取回一半数据。

最佳答案

为了回答您最初的问题,您将取回您在脚本末尾“返回”的任何内容。如果您没有特定的“return”语句,那么默认情况下您会返回上次操作的结果(在您的情况下是重复循环的最后一次迭代)。因此,如果您需要的不仅仅是返回的最后一个操作,您必须在脚本中创建返回值,然后在最后返回它。

but this doesnt actually resolve the original question, and the one problem with it is that if there is any error then I wont get anything back, whereas if it failed halfway through reading my iTuneslibrary and I was using stdout I would at least get half the data back. This is incorrect. The try block around your code will make applescript ignore the errors and continue, so anything you collect that doesn't error will still get returned.

请注意,您最新的 applescript 代码中存在一些错误。特别是这一行毫无意义,因为 applescript 不知道标准输出是什么。所以你的评论是不正确的。

copy output to stdout

这是您需要做的。如前所述,您使用“return”来返回某些东西。所以我清理了你的代码。这会将重复循环的每一行放在输出变量的单独一行上,您在代码末尾返回该行,然后在将其带入 javascript 代码后可以对其进行解析。试试这个...

tell application "iTunes"
set output to ""
set mainLibrary to library playlist 1
repeat with nexttrack in (get every track of mainLibrary)
if (class of nexttrack is file track) then
try
set trackname to name of nexttrack
set loc to location of nexttrack
set locpath to POSIX path of loc
set persistid to (persistent ID of nexttrack) as text
set nextline to trackname & "::" & locpath & "::" & persistid & return
set output to output & nextline
end try
end if
end repeat
end tell
return output

关于java - 如何使用 ScriptEngine 将 Javascript 的输出转换为 Java,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18183758/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com