2

I'm using NetShade as a proxy service and thought I could try to automate the switching between the different proxies as a nice start for my first AppleScript script.

The NetShade-app has no AppleScript support, so I have to use UI scripting. After a few tries (and some posts here) I managed to have a script, that switches the proxies via the menu bar item (here is a picture of it, since I can't post it inline due to reputation limit).

Unfortunately my code is extremely slow (≈6sec), which makes it kind of impractical as a script. The first menu opens immediately, but the selection of the sub-menu and the proxy server takes several seconds.

I'm using the following code:

set theProxy to "Netshade US 4"
tell application "System Events" to tell process "NetShade"
    tell menu bar item 1 of menu bar 2
        click
        tell menu item "NetShade Proxy" of menu 1
            click
            tell menu item theProxy of menu 1
                click
            end tell
        end tell
    end tell
end tell

I already tried to add ignoring application responses, like suggested in a different thread (link), but that didn't help.

So finally my questions: Is there a way to speed the process up? Maybe even a way to do all this in the background, without showing the menu items?

P.S.: I'm running OS X 10.9.1

Community
  • 1
  • 1
SBN
  • 21
  • 3
  • Does the NetShade app have any console version... or some way to access its commands from the Terminal? – summea Jan 21 '14 at 22:24
  • @summea Sadly not! It just has the menu bar item and the regular window... – SBN Jan 21 '14 at 23:09
  • Without something like that, and without AppleScript support, it probably just leaves your current UI scripting option (or something similar to it...) at the moment... unless, as you mention, there's a way to simulate GUI events in the background (which would be cool; I just haven't seen that sort of thing in Mac OS X, yet... :) – summea Jan 21 '14 at 23:33
  • @summea Thanks anyway! Does anybody else know a tweak or something to my current script to speed it up? – SBN Jan 22 '14 at 09:49
  • Do you need the *successive* clicks, i.e. is the target menu only populated if you first click the ancestral menus? If not, you can try to use only a *single* click. Large menu structures often cause slow GUI scripting - is that the case here? Perhaps there is a an alternate way to script this, such as via the menu-bar extra icon (or is that what your current code does?). – mklement0 Jan 22 '14 at 15:45
  • @mklement0 My script doesn't work without the successive clicks...and it is referring to the menu-bar extra icon. Here is a picture of the menu (can't post picture, because of reputation limit...): [link](https://db.tt/qwzwrvQQ). I just thought such a small menu shouldn't be a problem... – SBN Jan 22 '14 at 16:45
  • Bummer; indeed strange that it would be so slow. You could consider a radically different approach - don't know if it's feasible at all or, if so, whether it's substantially faster: have your script quit NetShade, modify its preferences on disk (e.g., via `defaults`), then restart it. – mklement0 Jan 22 '14 at 17:24

1 Answers1

9

Summary of the fix

To remove delay you need to do two things:

(I) Identify the click which is causing the delay and enclose only that line in the ignoring application responses block as shown below. In my case, it was click bt after which the execution was going into a wait mode for 5 to 6 seconds.

  ignoring application responses
        click bt
  end ignoring

(II) I then also had to kill System Events to and start it again using the following commands.

  do shell script "killall System\\ Events"
  delay 0.1  
  -- Rest of the code to click stuff or send keycodes

This resolved the delay issue.


Details

I was having the same problem where I created a script to connect/disconnect my bluetooth headset through AppleScript. The script is given below.

tell application "System Events" to tell process "SystemUIServer"
    set bt to (first menu bar item whose description is "bluetooth") of menu bar 1
    click bt
    tell (first menu item whose title is "SBH80") of menu of bt
        click
        tell menu 1
            if exists menu item "Disconnect" then
                click menu item "Disconnect"
            else
                click menu item "Connect"
            end if
        end tell
    end tell
end tell

The script was working fine but had a problem where it would wait for 5 to 6 seconds after executing "click bt" above. I modified the code as follows and it is working absolutely fine now without any delay.

tell application "System Events" to tell process "SystemUIServer"

    set bt to (first menu bar item whose description is "bluetooth") of menu bar 1
    ignoring application responses
        click bt
    end ignoring
end tell

do shell script "killall System\\ Events"
delay 0.1
tell application "System Events" to tell process "SystemUIServer"

    tell (first menu item whose title is "SBH80") of menu of bt
        click
        tell menu 1
            if exists menu item "Disconnect" then
                click menu item "Disconnect"
            else
                click menu item "Connect"
            end if
        end tell
    end tell
end tell
Ashutosh Jindal
  • 18,501
  • 4
  • 62
  • 91
Aviral Bansal
  • 413
  • 6
  • 13
  • 1
    Wow. I added this and it magically got rid of the delay. Any ideas of why? I'm assuming it caches the info from the first System Events call and then future uses are faster? – user336828 Aug 21 '21 at 02:45