通过Finder和Applescript复制项目:如何获取“项目存在 - 替换?” Finder中的对话框?

时间:2012-05-03 11:32:40

标签: macos applescript finder

在我的应用中,我喜欢让OSX Finder复制文件或文件夹。

注意:我有充分的理由使用Finder而不是使用shell cmds,NSWorkspace或其他方法,所以不需要那个方向的建议。

我目前依靠Applescript要求Finder执行复制操作。这是一个用于测试的示例脚本:

tell application "Finder"
    try
        copy file POSIX file "/etc/bashrc" to folder POSIX file "/private/tmp"
        -- alternative with same behavior:
        --duplicate POSIX file "/etc/bashrc" to POSIX file "/private/tmp"
    on error errmesg number errn
        display dialog "Error thrown: " & errmesg
    end try
end tell

现在的问题是:如果目标项已经存在,脚本会抛出错误并取消复制操作。

然而,我宁愿让Finder显示“项目存在”对话框,它在交互式Finder中执行此类复制操作时会显示,如下所示:

Finder "item already exists" warning

现在,这是事情: 如果我从第三方应用脚本调试器运行此脚本,则会出现此对话框!

所以,显然有一种方法可以让Finder显示对话框而不是抛出异常。但是怎么样?谁知道这个的秘密?

3 个答案:

答案 0 :(得分:1)

嗯,根据我自己的需要,我找到了一个解决方案:我不需要使用AppleScript,而是需要直接使用AppleEvents API。

在那里,我可以提供值kAEAlwaysInteract | kAECanSwitchLayerAESend的SendMode参数。这使得对话框出现在Finder中(在这种情况下也会将Finder放在前面)。

对于依赖AppleScript的人来说,遗憾的是,这不是一个解决方案。

答案 1 :(得分:0)

在使用AppleScript 时,似乎没有办法让Finder显示对话框 - 至少在脚本在常规环境中运行时。在我的测试中,当目标已经存在时, Finder 系统事件'文件move命令始终错误输出 - 唯一的区别是,除了语义,Finder提供replacing开关以使用true来抑制此行为,这意味着目标文件将被覆盖而不会提示,但没有选项将其设置为ask(请参阅this MacScripter thread }讨论完全相同的问题)。

如果不了解其内部工作原理,我只会冒险猜测Script Debugger处理这种情况的方式不同,很可能是因为在正常环境中运行脚本。很难想象如何在不创建自己的脚本执行层的情况下将脚本作为调试器工作的内部工作方式。这样的中间层可以解释为什么命令以不同的方式转发给应用程序 - 在Finder和move的情况下,转发到低级Finder复制例程,这将显示对话框。

这让您自己重新实现该功能,as suggested by Paul R或转移到AppleScript-ObjectiveC(而不是我的专业领域,我担心)。

答案 2 :(得分:-1)

这可能会迟到,但如果您在复制之前删除该文件,则与替换文件相同:

tell application "System Events"
    if exists file ("NewFilePath") then
        delete file ("NewFilePath")
            -- NewFilePath Is where the file will end up or already is
    end if
end tell
tell application "Finder"
    try
        copy file POSIX file "FilePath" to folder POSIX file "FolderPath"
        -- FilePath is where it is now
        -- FolderPath is the path of the folder you want the file in
    on error errmesg number errn
        display dialog "Error thrown: " & errmesg
    end try
end tell

并且因为在替换或停止查找器之间没有选择不应该提出这样的窗口