自动保存邮件附件的 AppleScript - 适用于新邮件但不适用于旧邮件

AppleScript to automatically save mail attachments - works for new but not old emails

感谢大家迄今为止的帮助。抱歉,我在上一个问题的 'answer' 部分问过这个问题,我现在明白我不应该这样做......所以我在这里开始了一个新问题。

所以,我想编写一个脚本来在电子邮件到达时将附件保存在电子邮件中 ​​- 每个电子邮件发件人都有一个不同的文件夹。我从这个网站上的人那里得到了很多帮助。

有点用..... 对于新收到的电子邮件,它工作得很好,但是当我 运行 它针对我邮箱中的旧电子邮件时,它会保存一些附件而不是其他附件。

我认为问题是在查找重复项时出错(我认为这不太可能,因为我已将时间戳记连同电子邮件的数据戳记一起添加到文件名中。)所以我添加了 delFile 删除过程检查同名文件,如果找到则将其删除。

当我执行脚本时,它处理的附件比以前多了一些,但不是全部......有趣的是,没有任何东西被放入垃圾箱。

我现在难住了!!作为 AppleScript 的新手,我还不知道如何调试或处理错误。

有人可以帮忙吗?

use scripting additions

using terms from application "Mail"
    on perform mail action with messages messageList for rule aRule
        set destinationPath to (POSIX file "/volumes/Data/Dropbox/WORK ITEMS/Email Attachments/") as string
        tell application "Mail"
            repeat with aMessage in messageList
                repeat with anAttachment in mail attachments of aMessage
                    set senderName to (extract name from sender of aMessage)
                    set {year:y, month:m, day:d, hours:h, minutes:min} to date received of aMessage
                    set timeStamp to (d & "/" & (m as integer) & "/" & y & " " & h & "." & min) as string
                    set attachmentName to timeStamp & " - " & name of anAttachment
                    
                    set doSave to true
                    set originalName to name of anAttachment
                    if originalName contains "jpg" then
                        set doSave to false
                    else if originalName contains "jpeg" then
                        set doSave to false
                    else if originalName contains "gif" then
                        set doSave to false
                    else if originalName contains "png" then
                        set doSave to false
                    else if originalName contains "html" then
                        set doSave to false
                    else if originalName contains "ics" then
                        set doSave to false
                    end if
                    
                    if doSave is true then
                        tell application "System Events"
                            if not (exists folder (destinationPath & senderName)) then
                                make new folder at end of alias destinationPath with properties {name:senderName}
                            end if
                        end tell
                    end if
                    
                    if doSave is true then
                        set delFile to destinationPath & senderName & ":" & attachmentName
                        tell application "System Events" to if (exists file delFile) then delete file delFile
                    end if
                    
                    if doSave is true then save anAttachment in file (destinationPath & senderName & ":" & attachmentName) with replacing
                    
                    
                    
                end repeat
            end repeat
        end tell
        
    end perform mail action with messages
end using terms from

谢谢

我不确定我能否帮助您找出脚本失败的确切原因,但我或许可以帮助您了解它失败的地方。

首先,我将用您希望排除的文件扩展名列表代替长 if...else if 块。类似于:

set ignore list to {".jpg", ".jpeg", ".gif", ".png", ".html", ".ics"} 在脚本的顶部,set fileExtension to rich text (offset of "." in originalName) thru end of originalName 在循环中。

然后你可以测试:

if fileExtension is not in ignoreList then

并将其包装在保存代码周围(您不需要多次执行相同的测试)。

我认为您的删除文件块是多余的,因为它应该与以下 save...with replacing 相同(如果文件已经存在)。 (如果文件存在,您可能希望删除该文件,在这种情况下,稍后删除 with replacing。)

要开始调试,首先删除顶部处理传入消息的代码并将其替换为 set messageList to selection。尝试在您不确定发生了什么的地方插入一些 display dialog <varname>。例如,您知道 anAttachment 是什么,但您确定 destinationPath & senderName & ":" & attachmentName 是什么吗?

最后,请注意我没有 运行 你的数据,所以一定要做好备份。它不应该破坏任何东西,但安全总比后悔好!

有任何问题请回来。祝你好运!

编辑:

我在顶部添加了一个函数(on getExtension(fileName) 块。这是由 set fileExtension to my getExtension(originalName)

行调用的

这是为了通过反转名称字符串来优化扩展名的获取,因此只有第一个“.”。被发现。一旦得到扩展名就被逆转了。

另一个关键部分是它包含try ... on error ... end try。这就是 AppleScript 处理错误的方式。如果没有 '/' 则抛出错误。这被 on error which returns 'skip' 捕获。 (此时主程序中未使用它,但可用于将所有输出集中到一个 catchall 文件夹中。)

最后的变化是我把保存的部分包裹在了If originalName does not contain "/" then ... end if中。这是为了捕获那些包含 '/' 的文件并 'jump over' 它们而不做任何事情。

我不需要添加 delay,所以一开始不要添加。这可能是一条红鲱鱼!

set ignoreList to {".jpg", ".jpeg", ".gif", ".png", ".html", ".ics"}
set destinationPath to (POSIX file "/volumes/Data/Dropbox/WORK ITEMS/Email Attachments/") as string

on getExtension(fileName)
    try
        set fileName to (reverse of every character of fileName) as string
        set extension to text 1 thru (offset of "." in fileName) of fileName
        set extension to (reverse of every character of extension) as string
        return extension
    on error
        return "skip"
    end try
end getExtension


tell application "Mail"
    set messageList to selection
    
    repeat with aMessage in messageList
        repeat with anAttachment in mail attachments of aMessage
            set senderName to (extract name from sender of aMessage)
            set {year:y, month:m, day:d, hours:h, minutes:min} to date received of aMessage
            set timeStamp to (d & "/" & (m as integer) & "/" & y & " " & h & "." & min) as string
            set attachmentName to timeStamp & " - " & name of anAttachment
            set originalName to name of anAttachment
            if originalName does not contain "/" then
                set fileExtension to my getExtension(originalName)
                if fileExtension is not in ignoreList then
                    
                    tell application "System Events"
                        if not (exists folder (destinationPath & senderName)) then
                            make new folder at end of alias destinationPath with properties {name:senderName}
                        end if
                    end tell
                    
                    save anAttachment in file (destinationPath & senderName & ":" & attachmentName) with replacing
                end if
            end if
        end repeat
    end repeat
    
end tell

从邮件规则调用:

use scripting additions

set ignoreList to {".jpg", ".jpeg", ".gif", ".png", ".html", ".ics"}
set destinationPath to (POSIX file "/Users/bernardharte/test/") as string

on getExtension(fileName)
    try
        set fileName to (reverse of every character of fileName) as string
        set extension to text 1 thru (offset of "." in fileName) of fileName
        set extension to (reverse of every character of extension) as string
        return extension
    on error
        return "skip"
    end try
end getExtension

using terms from application "Mail"
    on perform mail action with messages messageList for rule aRule
        
        tell application "Mail"
            
            repeat with aMessage in messageList
                repeat with anAttachment in mail attachments of aMessage
                    set senderName to (extract name from sender of aMessage)
                    set {year:y, month:m, day:d, hours:h, minutes:min} to date received of aMessage
                    set timeStamp to (d & "/" & (m as integer) & "/" & y & " " & h & "." & min) as string
                    set attachmentName to timeStamp & " - " & name of anAttachment
                    set originalName to name of anAttachment
                    if originalName does not contain "/" then
                        set fileExtension to my getExtension(originalName)
                        if fileExtension is not in ignoreList then
                            
                            tell application "System Events"
                                if not (exists folder (destinationPath & senderName)) then
                                    make new folder at end of alias destinationPath with properties {name:senderName}
                                end if
                            end tell
                            
                            save anAttachment in file (destinationPath & senderName & ":" & attachmentName) with replacing
                        end if
                    end if
                end repeat
            end repeat
            
        end tell
        
    end perform mail action with messages
end using terms from