2

Hoping some one can point out what I am doing wrong. After looking through several threads, plus lots of experimentation, it feels like something simple is wrong. The threads I read include How can I trigger a Notification Center notification from an AppleScript or shell script? and How to get a notification when my commands are done

This script is intended for minimally technical users to perform mounting and un-mounting shares. Right now it only supports SMB, but will handle NFS and other remote mounts later. We have the constraint that the user's system will be the base OS X installation, therefore we cannot install other tools or libraries.

The problem is popping a notification window when an event occurs, with text that includes a space in the argument passed to the function. If the argument is only alpha/numeric, it works fine.

As a starting point, I am using a piece of code from randomor on How to get a notification when my commands are done. The say command makes it much easier to tell when the script works, plus will make for nice voice prompts.

send_notify(){
cmd=$@
local $@ && say 'Completed!' && osascript -e "display notification \"Completed: $2\" with title \"$1\""
}

As long as there isn't whitespace in the argument string being passed from the calling function, both the say and the notification work. When there is white space in the argument string such as "BAR 3" or in a variable being passed, the send_notify() function throws an error.

When called without whitespace, send_notify() works

send_notify "FOO" "BAR2" <<< This works

This fails because of the whitespace

send_notify "FOO" "BAR 3"  <<< This fails

./sharemount.sh: line 138: local: `37': not a valid identifier

Interestingly, the say command also fails to execute.

Part of the problem is my lack of understanding what role “$@" plays in this command. If anyone has an explanation, it would be very welcome.

Below is one of several functions in the script tha call the send_notify() function.

Pre_Mount_Check() {
    Current_Share="$(df -t smbfs --output=source 2>/dev/null | sed '1d' | awk -F/ '{print tolower($NF)}')"
    Current_MountPoint="$(df -t smbfs --output=target 2>/dev/null | sed '1d')"
    logger -p Info "$DebugLog" "Sharemount:Pre_Mount_Check Checking to see if $Share_Path already exists"

    if [[ (-z "$Current_Share") && (-z "$Current_MountPoint") ]]; then 
        logger -p Info "$DebugLog" "Sharemount:Pre_Mount_Check $Share_Path on $Mount_Point is not mounted, we will try to mount it"
        return 0

    elif [[ ( "$Current_Share" = "$Share_Name") && ( "$Current_MountPoint" = *"$Mount_Point"*) ]]; then 
        logger -p Info "$DebugLog" "Sharemount:Pre_Mount_Check $Share_Path already mounted, nothing to do, exiting"
        echo "$Share_Path already mounted, nothing to do, exiting 1"
        exit 0

    elif
     [[ ( "$Current_Share" = "$Share_Name") ]]; then
        logger -p Warning "$DebugLog" "Sharemount:Pre_Mount_Check $Share_Path already mounted, on $Current_MountPoint, exiting"
        echo "$Share_Path already mounted, on $Current_MountPoint, exiting 2"
        send_notify "FOO" "BAR2" <<< This works
        exit 36

    elif [[ ( "$Current_MountPoint" = *"$Mount_Point"*) ]]; then
        logger -p Warning "$DebugLog" "Sharemount:Pre_Mount_Check $Share_Name is already mounted on $Mount_Point exiting"
        echo "$Share_Name is already mounted on $Mount_Point exiting 3"
        send_notify "FOO" "BAR 3"  <<< This fails
        exit 0

    fi
}

send_notify(){
cmd=$@
local $@ && say 'Completed!' && osascript -e "display notification \"Completed: $2\" with title \"$1\""
}
  • In Bash, the $@ expands to the positional parameters. One way to visualize this is if you wanted all the elements in an array, $@ would provide them. That said, I don't see what positional parameters are being set based on the code provided. One way to check is to simply echo $cmd and see what you get (I have a feeling, nothing). That said, there seems to be multiple questions here - can you narrow it down to just one (i.e. the notify problem as described in your title)? – Allan Aug 3 at 22:02
  • 1
    I don't know the purpose of "local $@". I think the intent is to create variables in the local address space. variables cannot have a space in them. What are you trying to do with the local statement? Why is it even there? – historystamp Aug 3 at 22:27
  • 1
    I believe in over-the-top debugging, so I ended up with: pastebin.com/raw/SjVkSnPg – historystamp Aug 3 at 22:40
  • 1
    You still haven't explained the need for the local command at the front of the call to osascript & what you expect the local statement to do. – historystamp Aug 4 at 20:57
  • 1
    Again Kevin this seems like a space delimiting issue. I dropped the 'cmd=$@' and the 'local $@ && ' from the code and it works. $1 and $2 work without any parsing. See tldp.org/LDP/abs/html/localvar.html for more info on passing variables. – Thomas Nelson Aug 5 at 5:23
1

Displaying Notifications Notification Center offers another opportunity for providing feedback during script execution. Use the Standard Additions scripting addition’s display notification command to show notifications, such as status updates as files are processed.

To show a notification, provide the display notification command with a string to display. Optionally, provide values for the with title, subtitle, and sound name parameters to provide additional information and an audible alert when the notification appears, as shown in Listing 24-1 and Listing 24-2.

APPLESCRIPT

Open in Script Editor

Listing 24-1AppleScript: Displaying a notification

display notification "All graphics have been converted." with title "My Graphic Processing Script" subtitle "Processing is complete." sound name "Frog"

JAVASCRIPT

Open in Script Editor

Listing 24-2JavaScript: Displaying a notification

var app = Application.currentApplication()

app.includeStandardAdditions = true

app.displayNotification("All graphics have been converted.", {
    withTitle: "My Graphic Processing Script",
    subtitle: "Processing is complete.",
    soundName: "Frog"
})

NOTE

After using a script to display a notification, the script or Script Editor (if the script is run from within Script Editor) is added to the list of notifying apps in System Preferences > Notifications. There, you can configure options, such as whether to display notifications as alerts or banners.

Clicking the Show button in an alert-style notification opens the app that displayed the notification. For a script app, the action of opening the app again triggers the run handler of the script, potentially causing the script to begin processing a second time. Keep this in mind, and add code to your script to handle this scenario, if appropriate.

From: https://developer.apple.com/library/archive/documentation/LanguagesUtilities/Conceptual/MacAutomationScriptingGuide/DisplayNotifications.html

1

As Thomas Nelson pointed out, I had made this way too complex. Dropping the

cmd=$@
local $@ && 

sequence solved the problem.

Here is the finished function

    #######################
    ##### Send_Notify #####
    #######################

    # Call this and supply the text you want to have spoken ($1) and the notification message ($2)
    # ie: Send_Notify "This is my voice" "This is the message"
    Send_notify(){
    title="FOOScript"
    say "$1" && osascript -e "display notification \"$2\" with title \"$title\""
}

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .