Easy way to execute shell script

I want to be able to search in Spotlight for a shell script (or something that calls a shell script) and that such shell script opens a Terminal window so the output is shown live (and I can interrupt with ctrl + C).

Right now, I have a backup.sh

#!/bin/bash
caffeinate -s \
  rsync -hva --progress --stats --delete "/path/to/source/" "/path/to/destination"

that I've renamed to backup.command so I can doubleclick in Finder and it works perfectly. But I cannot search for it in Spolight because I want Spotlight to only search for Applications, System Preferences and Contacts, and if I mark Developer then it shows backup.command but also a lot of unwanted files that are just unnecessary.

What can I do?

I tried to appify it but then it runs on the background, and doesn't open a new Terminal window so I can't see the progress of how is it going, and also I can't stop the progress with ctrl + C. Any suggestion?


Solution 1:

Appifying with Platypus:

Download Platypus and create an app from the shell script.

Example:

enter image description here

The settings above create an app with a progress bar (including details) and it can be quitted - the rsync process has to be canceled (killed) manually though.

enter image description here

The app itself can be found with Spotlight.


Simple AppleScript solution:

In Mavericks (and probably later) you have to allow the AppleScript app to control the computer in "System Preferences -> Security & Privacy -> Privacy -> Accessibility"

Open ScriptEditor, enter the code snippet below and export it as an application with a unique name:

tell application "Terminal"
    delay 2
    set newWindow to do script "caffeinate -s rsync -hva --progress --stats --delete /path/to/folder /path/to/folder2"
    activate
end tell

If you need root permissions prepend sudo -> "sudo caffeinate -s ...."

You can refine the AppleScript app by checking if Terminal already has open windows and create a new one to run the shell script:

set myScript to "caffeinate -s rsync -hva --progress --stats --delete /path/to/folder /path/to/folder2"
tell application "System Events"
    if exists (window 1 of process "Terminal") then
        tell application "Terminal"
            set newWindow to do script myScript
            activate
        end tell
    else
        tell application "Terminal"
            delay 2
            set Window1 to do script myScript
            activate
        end tell
    end if
end tell

The AppleScript app can be found with Spotlight.


In Mountain Lion you have to enable "System Preferences -> Accessibility -> Enable access for assistive device" and change it a little bit to get the AppleScript app solutions running properly:

set myScript to "caffeinate -s rsync -hva --progress --stats --delete /path/to/folder /path/to/folder2"
tell application "System Events"
    if exists (window 1 of process "Terminal") then
        tell application "Terminal"
            reopen
            activate
            set newWindow to do script myScript
        end tell
    else
        tell application "Terminal"
            reopen
            activate
            do script myScript in window 1
        end tell
    end if
end tell

AppleScript with "external" shell script (backup.sh):

This is the final approach the OP is using. Taken from here. In Mavericks (and probably later) you have to allow the AppleScript app to control the computer in "System Preferences -> Security & Privacy -> Privacy -> Accessibility". One can load the full .sh (placed inside the app in Contents/Resources/backup.sh) with:

set bashFile to path to resource "backup.sh"
tell application "Terminal"
    delay 1
    activate
    set newWindow to do script "bash " & quoted form of (POSIX path of bashFile)
end tell

You can refine the AppleScript app by checking if Terminal already has open windows and create a new one to run the shell script:

set bashFile to path to resource "backup.sh"
tell application "System Events"
    if exists (window 1 of process "Terminal") then
        tell application "Terminal"
            delay 1
            set newWindow to do script "bash " & quoted form of (POSIX path of bashFile)
            activate
        end tell
    else
        tell application "Terminal"
            delay 2
            set Window1 to do script "bash " & quoted form of (POSIX path of bashFile)
            activate
        end tell
    end if
end tell