1

I'm working on a Ruby script that requires some variables from Applescript. Right now I'm having success grabbing them one at a time, but it seems inelegant and possibly slow. For example:

note = %x{ osascript <<APPLESCRIPT
    tell application "Evernote"
        if selection is not {} then
            set the_selection to selection
            if notebook of item 1 of the_selection is (notebook named "Writing") then
                return HTML content of item 1 of the_selection
            end if
        else
            return ""
        end if
    end tell
APPLESCRIPT}

title = %x{ osascript <<APPLESCRIPT
  tell application "Evernote"
        if selection is not {} then
            set the_selection to selection
            if notebook of item 1 of the_selection is (notebook named "Writing") then
                return title of item 1 of the_selection
            end if
        else
            return ""
        end if
    end tell
APPLESCRIPT}

I know I'm probably overlooking something obvious, but is there an easy way I can do this with just a single snippet of Applescript that returns both variables into Ruby (note, title)?

1 Answer 1

2

Getting multiple values out of AppleScript is the easy part. Instead of returning a single value, return a list:

result = %x{ osascript <<APPLESCRIPT
  tell application "Evernote"
      if selection is not {} then
          set the_selection to selection
          if notebook of item 1 of the_selection is (notebook named "Writing") then
              set title to title of item 1 of the_selection
              set html to HTML content of item 1 of the_selection
              return { title, html }
          end if
      else
          return ""
      end if
  end tell
APPLESCRIPT}

The hard part is parsing the output. Supposing your title is This is a note and html is <h1>Hello World</h1>, osascript will return this:

This is a note, <h1>Hello World</h1>

You could split it on the , but if title happens to contain a comma, you've got a problem. You can also pass the -ss option to osascript, which makes it return formatted AppleScript objects, but you don't want to have to write your own AppleScript parser in Ruby.

An alternative, if you know title will never contain a line break, is to put a line break after the title:

result = %x{ osascript <<APPLESCRIPT
  ...
  if notebook of item 1 of the_selection is (notebook named "Writing") then
      set title to title of item 1 of the_selection
      set html to HTML content of item 1 of the_selection
      return title & "\n" & html
  end if
  ...
APPLESCRIPT}.chomp

Now the output (result) will look like this:

This is a note
<h1>Hello World</h1>

...and you can get the title and HTML like this:

title, html = result.split("\n", 2)
puts title
# => This is a note
puts html
# => <h1>Hello World</h1>

Now, if you have line breaks in any of your titles (I can't remember if Evernote allows that or not), or if you want to return more than two values, this will be problematic as well. The next simplest solution would be to choose some kind of delimiter that's unlikely to appear in any part of the output, for example %!%:

DELIMITER = '%!%'

result = %x{ osascript <<APPLESCRIPT
  ...
  if notebook of item 1 of the_selection is (notebook named "Writing") then
      set title to title of item 1 of the_selection
      set html to HTML content of item 1 of the_selection
      return title & "#{DELIMITER}" & html
  end if
  ...
APPLESCRIPT}.chomp
# =>This is a note%!%<h1>Hello World</h1>

title, html = result.split(DELIMITER, 2)

If all else fails, you could use an addon to make osascript output a known format that Ruby knows how to parse. Just now I found this free JSON Helper that looks pretty handy.

Sign up to request clarification or add additional context in comments.

1 Comment

This is great, with one syntax change: Applescript interprets "/n" literally, so when you compile the script in the editor it actually adds a line there. In Applescript, "linefeed" is the equivalent. I used that, then split by "/n" in my Ruby script, and everything is working perfectly.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.