Export From Evernote to Yojimbo

Description

Version 3.3 of the Evernote Client may have errors which prevent this AppleScript from working -- Click here for the latest update on the situation.

Originally published here as a blog post, this script exports a copy of all the selected entries in an Evernote notebook and saves them into Yojimbo while providing a Growl notification of its progress.

Currently, links to audio clips from Evernote will appear to import into Yojimbo. However, the links are non-functional. I'll look at what can be done about this in future revisions (and based on popular consensus). If you don't have Growl installed, you may also receive an error when running the script. If this is happening to you, please let me know via the Bug Report Link below.

Change Log:

  • 1.02 (October 19, 2009) BUGFIX FOR ADDITIONAL CASE OF "Can’t get item 1 of {}" ERROR ("find notes"/quotation issue)
  • 1.01 (October 18, 2009) BUG FIXES ("Can’t get item 1 of {}" ERROR, UPDATED/FIXED GROWL NOTIFICATIONS)
  • 1.00 (October 2, 2009) INITIAL RELEASE OF SCRIPT

The Code

(*
http://veritrope.com
Evernote to Yojimbo Exporter
Version 1.02
October 19, 2009

Project Status, Latest Updates, and Comments Collected at:
http://veritrope.com/tips/evernote-yojimbo-export
           
Installation: Just double-click on the script!

FastScripts Installation (Optional, but recommended):
--Download and Install FastScripts from http://www.red-sweater.com/fastscripts/index.html
--Copy script or an Alias to ~/Library/Scripts/Applications/Evernote
--Set up your keyboard shortcut

CHANGELOG:
1.02    BUGFIX FOR ADDITIONAL CASE OF "Can’t get item 1 of {}" ERROR ("find notes"/quotation issue)
1.01       BUG FIXES ("Can’t get item 1 of {}" ERROR, UPDATED/FIXED GROWL NOTIFICATIONS)
1.00    INITIAL RELEASE
*)

property theKind : "Evernote"
property theNum : "0"
property CleanTitle : ""
property itemexists : ""
property noteToExport : ""
property theString : ""
(* CHECK FOR GROWL *)
if appIsRunning("GrowlHelperApp") then
    set isRunning to true
    tell application "GrowlHelperApp"
        set allNotificationsList to {"Success Notification", "Failure Notification"}
        set enabledNotificationsList to {"Success Notification", "Failure Notification"}
        register as application ¬
            "Evernote to Yojimbo" all notifications allNotificationsList ¬
            default notifications enabledNotificationsList ¬
            icon of application "Evernote"
    end tell
end if

(*MAIN PROGRAM *)
set myPath to (path to home folder)
tell application "Evernote"
    try
        (* EVERNOTE NOTEBOOK SELECTION SUBROUTINE *)
        set listOfNotebooks to {}
        set EVNotebooks to every notebook --GET THE NOTEBOOK LIST
        repeat with currentNotebook in EVNotebooks
            set currentNotebookName to (the name of currentNotebook)
            copy currentNotebookName to the end of listOfNotebooks
        end repeat
       
        (*SORT THE FOLDER LIST *)
        set Folders_sorted to my simple_sort(listOfNotebooks)
       
        (*USER SELECTION FROM NOTEBOOK LIST *)
        set SelNotebook to choose from list of Folders_sorted with title "Select Notebook For Export" with prompt ¬
            "Available Evernote Notebooks" OK button name "OK"
        set EVnotebook to item 1 of SelNotebook
        set listofNotes to {} (*PREPARE TO GET EVERNOTE'S LIST OF NOTES *)
        set allNotes to (find notes "notebook:\"" & EVnotebook & "\" ")
        repeat with currentNote in allNotes
            set currentNoteName to (the title of currentNote)
            copy currentNoteName to the end of listofNotes
        end repeat
       
        (*SORT THE NOTEBOOK LIST *)
        set Notes_sorted to my simple_sort(listofNotes)
       
        (*PICK THE NOTES FROM THE LIST *)
        set SelNotes to ¬
            choose from list of Notes_sorted with title ¬
                "Select Notes" with prompt "Multiple Selections Allowed" OK button name "Export Notes" cancel button name "Cancel" with multiple selections allowed
        -- NOTE: ALL UNTITLED NOTES MAY SHOW UP AS SINGLE "UNTITLED" ENTRY
       
        if (SelNotes is not false) then
           
            (*TEMP FILES PROCESSED ON THE DESKTOP*)
            tell application "Finder"
                if (the folder "Temp Export From Evernote" exists) then set SaveLoc to (the folder "Temp Export From Evernote")
                if not (the folder "Temp Export From Evernote" exists) then
                    set SaveLoc to (make new folder at (path to desktop folder) with properties {name:"Temp Export From Evernote"})
                end if
            end tell
           
            (*DO THE CONVERSION*)
            my ENExport(EVnotebook, SelNotes, SaveLoc)
        end if
        (*GROWL *)
        my GrowlNotify(theNum, theKind)
        set TotalNum to 0
        (* ERROR HANDLING *)
    on error errText number errNum
        if isRunning is true then
            if errNum is -128 then
                tell application "GrowlHelperApp" -- GROWL FAILURE FOR ERROR
                    notify with name ¬
                        "Failure Notification" title ¬
                        "User Cancelled" description ¬
                        "Failed to export!" application name "Evernote to Yojimbo"
                end tell
            else -- IF NOT CANCELLED
                tell application "GrowlHelperApp" -- GROWL FAILURE FOR ERROR
                    notify with name ¬
                        "Failure Notification" title ¬
                        "Import Failure" description "Failed to export " & theKind & " item due to the following error:  " & errNum & " (" & errText & ¬
                        ")" application name "Evernote to Yojimbo"
                end tell
            end if -- ENDING GROWL ERROR NOTIFY
        else if isRunning is false then -- NON-GROWL ERROR MSG. FOR ERROR
            display dialog "Item Failed to Import: " & errNum & return & errText with icon 0
        end if
       
    end try
end tell

(* SUBROUTINES *)
on appIsRunning(appName)
    tell application "System Events" to (name of processes) contains appName
end appIsRunning

on ENExport(EVnotebook, SelNotes, SaveLoc)
    (*FIND FOLDER FOR NOTE*)
    tell application "Evernote"
        set theNum to 0
        repeat with SelNote in SelNotes
            set theString to SelNote
            set theOriginalString to "\""
            set theNewString to ""
            set StripQuotes to my replaceString(theString, theOriginalString, theNewString)
            set noteToExport to (find notes "notebook:\"" & EVnotebook & "\" intitle:\"" & StripQuotes & "\"")
            set noteID to (local id of item 1 of noteToExport)
            set noteName to (title of item 1 of noteToExport)
            (*PREPARE HTML FOLDER *)
            tell application "Finder"
                --activate
                set SingQuote to "-e s/'//g"
                set CleanTitle to do shell script ("echo " & quoted form of SelNote & "  | sed -e 's/:/ /g' -e 's/\"//g' -e 's/—/ /g' " & (quoted form of SingQuote)) --CLEAN OUT COLONS FOR FILE PATH (SOUNDS GROSSER THAN IT IS)
                set ArchiveInput to ((SaveLoc as Unicode text) & CleanTitle)
                (*NEW HTML EXPORT *)
                tell application "Evernote"
                    export noteToExport ¬
                        to ArchiveInput ¬
                        format HTML
                end tell
               
                tell application "Finder"
                    (*LOOK FOR RESOURCE FOLDER *)
                    try
                        set EVNote to (every file of folder ArchiveInput whose ¬
                            name extension is "html")
                        set name of (item 1 of EVNote) to (CleanTitle & ".html")
                        set ResourceFolder to ((ArchiveInput & ":" & CleanTitle & ".resources") as string)
                        set theFile to (every document file of folder ResourceFolder whose ¬
                            name extension is "PDF")
                        set thePDF to POSIX path of (theFile as alias)
                        (*LOOK FOR PDF *)
                        set itemexists to my PDFDetect(theFile)
                    end try
                end tell
               
                (*IMPORT PDF IF PRESENT... *)
                tell application "Yojimbo" (*PREPARE YOJIMBO*)
                    if itemexists is true then
                        set resultRecord to import thePDF ¬
                           
                        (*.. OR CONVERT TO WEBARCHIVE FILE*)
                    else
                        tell application "Finder"
                            set ExportedNote to POSIX path of ((ArchiveInput & ":" & CleanTitle & ".html") as string)
                            do shell script ("textutil -convert webarchive " & (quoted form of ExportedNote))
                            set Make_Archive to POSIX path of ((ArchiveInput & ":" & CleanTitle & ".webarchive") as string)
                        end tell
                        set resultRecord to import Make_Archive
                    end if
                end tell
            end tell --Finder
            set theNum to theNum + 1
            set itemexists to ""
        end repeat --SelNotes
       
        (*DELETE THE TEMP FILE/FOLDER *)
        tell application "Finder" to delete SaveLoc
    end tell --EV
end ENExport

--PDF CHECK
on PDFDetect(theFile)
    try
        set PDFalias to theFile as alias
        return true
    on error
        return false
    end try
end PDFDetect

--REPLACE SUBROUTINE
on replaceString(theString, theOriginalString, theNewString)
    set {od, AppleScript's text item delimiters} to {AppleScript's text item delimiters, theOriginalString}
    set theStringParts to text items of theString
    if (count of theStringParts) is greater than 1 then
        set theString to text item 1 of theStringParts as string
        repeat with eachPart in items 2 thru -1 of theStringParts
            set theString to theString & theNewString & eachPart as string
        end repeat
    end if
    set AppleScript's text item delimiters to od
    return theString
end replaceString

--SORT SUBROUTINE
on simple_sort(my_list)
    set the index_list to {}
    set the sorted_list to {}
    repeat (the number of items in my_list) times
        set the low_item to ""
        repeat with i from 1 to (number of items in my_list)
            if i is not in the index_list then
                set this_item to item i of my_list as text
                if the low_item is "" then
                    set the low_item to this_item
                    set the low_item_index to i
                else if this_item comes before the low_item then
                    set the low_item to this_item
                    set the low_item_index to i
                end if
            end if
        end repeat
        set the end of sorted_list to the low_item
        set the end of the index_list to the low_item_index
    end repeat
    return the sorted_list
end simple_sort
--GROWL
on GrowlNotify(theNum, theKind)
    tell application "GrowlHelperApp" -- GROWL SUCCESS
        set Plural_Test to (theNum) as number
        if Plural_Test is greater than 1 then
            notify with name ¬
                "Success Notification" title ¬
                "Import Success" description "Successfully exported " & theNum & " " & theKind & ¬
                " items to Yojimbo" application name ¬
                "Evernote to Yojimbo"
           
        else if Plural_Test is equal to 1 then
            notify with name ¬
                "Success Notification" title ¬
                "Import Success" description "Successfully exported " & theNum & " " & theKind & ¬
                " item to Yojimbo" application name ¬
                "Evernote to Yojimbo"
        end if
    end tell
end GrowlNotify