¿Cómo puedo activar una notificación del Centro de notificaciones desde un AppleScript o un script de shell?

Me encantaría poder aprovechar las funciones del Centro de notificaciones de 10.8 en AppleScripts y scripts de shell que escribo.

¿Hay un comando incorporado o una biblioteca de terceros que pueda usar desde un AppleScript o un script de shell?

Idealmente, se podría controlar el tipo y el ícono de la notificación, pero incluso se agradecería la capacidad de activar un banner básico con un ícono de acciones (pero con texto personalizado).

Respuestas (13)

Con Mavericks y posteriores, puede hacer esto usando la 'notificación de visualización' de AppleScript:

display notification "Lorem ipsum dolor sit amet" with title "Title"

                          

Eso es, ¡literalmente así de simple! No se requieren bibliotecas o aplicaciones de terceros y es completamente portátil para usar en otros sistemas. Notificación 10.9 en la parte superior, 10.10 DP en el medio, 10.10 en la parte inferior.

AppleScript se puede ejecutar desde el shell usando /usr/bin/osascript:

osascript -e 'display notification "Lorem ipsum dolor sit amet" with title "Title"'

También puede personalizar aún más la alerta agregando...

  • un subtitulo

    Agregue 'subtítulo' seguido de la cadena o variable que contiene el subtítulo.

    display notification "message" with title "title" subtitle "subtitle"
    

    El ejemplo anterior produce la siguiente notificación:

  • sonar

    Agregue 'nombre de sonido' seguido del nombre de un sonido que se reproducirá junto con la notificación.

    display notification "message" sound name "Sound Name"
    

    Los nombres de sonido válidos son los nombres de los sonidos ubicados en...

    • ~/Library/Sounds
    • /System/Library/Sounds

Las notificaciones de publicación se pueden envolver como un script de línea de comandos. El siguiente código se puede ejecutar en Terminal y agregará un script a /usr/local/bin (debe existir, agregar a $PATH) llamado notify.

cd /usr/local/bin && echo -e "#!/bin/bash\n/usr/bin/osascript -e \"display notification \\\"\$*\\\"\"" > notify && chmod +x notify;cd -

Este es el script que agregará lo anterior para notificar.

#!/bin/bash
/usr/bin/osascript -e "display notification \"$*\""

Ahora para mostrar una notificación:

notify Lorem ipsum dolor sit amet
sleep 5; notify Slow command finished
¿Cuál es el camino de display? Tengo Mavericks pero no puedo ver para encontrarlo. ¡Gracias!
@ceilingcat ¿Podría aclarar lo que quiere decir? ¿Qué no funciona?
Sin embargo, tengo -bash: display: command not foundMi camino es un poco complicado, por lo que sería bueno saber exactamente dónde displayse encuentra.
@ceilingcat Esto es AppleScript. Para ejecutarlo en Terminal, use osascript (ver respuesta).
El único problema display notificationes que cuando hace clic en él, aparece el cuadro de diálogo Abrir archivo.
¿Es posible hacer que la ventana emergente de notificación exista para siempre (no se oculte automáticamente después de N segundos) hasta que el usuario haga clic explícitamente?
¿Cómo agrego un límite de tiempo para que exista la notificación en la pantalla?
Un par de preguntas: 1. ¿Puedo agregar ciertas acciones al hacer clic en la notificación? Digamos que quiero ejecutar un determinado script de shell. Estoy en Yosemite y se inicia el explorador de archivos. 2. ¿Cómo personalizo la notificación con más opciones, como mostrar un botón al costado al pasar el mouse sobre él, como lo que sucede cuando la próxima canción de iTunes se reproduce automáticamente y aparece una notificación que muestra esa canción, o cuando hace clic en la notificación cuando tiene un mensaje nuevo, aparecen dos opciones: ¿Enviar y Cancelar?
Nada de lo que he encontrado indica que hay una forma de controlar la acción (lo que sucede cuando haces clic en la notificación). macosxautomation.com/mavericks/notifications/01.html es útil, FYI.
Damas y caballeros, después de una hora de investigación en Internet, descubrí cómo dejar que la ventana de notificación permanezca hasta que el usuario la descarte. En realidad, estaba controlado por una configuración en Preferencias del sistema, en lugar de algún parámetro en el script escrito. Estas dos imágenes deberían explicarlo todo i.imgur.com/cNOqFyX.jpg i.imgur.com/i8oyoan.jpg Diviértanse muchachos y gracias @grgarside por la excelente respuesta.
Tenga en cuenta que el texto debe estar entre comillas dobles. Las comillas simples no funcionan. Entonces, si necesita una variable en el texto, no puede escribir "display ... '$mytext' ...", pero necesita comillas dobles con escape: "display notification \"$mytext\" ...".
display notificationno funciona para mí en El Capitan, aunque display alertfunciona bien. La documentación afirma que ambos funcionan. ¿Alguna idea de esto?
Como Vic Jang mencionó pero no explicó claramente, puede cambiar la configuración de cómo se muestran las notificaciones a través de Preferencias del sistema> Notificaciones> Editor de secuencias de comandos> cambiar de "Banners" a "Alertas". De esa manera, al menos puede hacer clic en "Cerrar" en lugar de ver el cuadro de diálogo Abrir archivo cuando descarta la notificación.
@Dan Hacer clic en una notificación nunca es una acción de descartar, razón por la cual se inicia el Editor de secuencias de comandos al hacer clic. Puede descartar una pancarta con un deslizamiento de dos dedos mientras se desplaza sobre ella. Puedo buscar alternativas si tengo tiempo en algún momento.
imagen personalizada para la notificación?
Parece que sound nameya no te permite reproducir sonidos personalizados ~/Library/Sounds. ¿Alguien sabe una solución? Usando macOS 10.13.2.
En Mac 11.2.3:zsh: command not found: display
@Alik Lea la respuesta, específicamente: 'AppleScript se puede ejecutar desde el shell usando /usr/bin/osascript'
Tuve que eliminar el proceso del "Centro de notificaciones" que se reinicia automáticamente, antes de que la notificación comenzara a aparecer.

notificador de terminal

Del LÉAME:

terminal-notifier es una herramienta de línea de comandos para enviar notificaciones de usuario de Mac OS X, que están disponibles en Mac OS X 10.8.

Actualmente está empaquetado como un paquete de aplicaciones, porque NSUserNotificationno funciona desde una 'herramienta de base'. radar://11956694

Kicker utilizará esta herramienta para mostrar el estado de los comandos que se ejecutan debido a cambios en el sistema de archivos. (v3.0.0)

Descargar

Los binarios preconstruidos, que están firmados con código y listos para usar, están disponibles en la sección de descargas .

Uso

$ ./terminal-notifier.app/Contents/MacOS/terminal-notifier group-ID sender-name message [bundle-ID]

Para usar el notificador de terminal, debe llamar al binario dentro del paquete de la aplicación.

El primer argumento especifica el 'grupo' al que pertenece una notificación. Para cualquier 'grupo', solo se mostrará una notificación, reemplazando las notificaciones publicadas anteriormente. Algunos ejemplos son: el ID del proceso del remitente para definir el alcance de las notificaciones por un proceso único, o el directorio de trabajo actual para determinar el alcance de las notificaciones por un proyecto.

Los argumentos segundo y tercero describen la notificación en sí y son su 'título' y 'mensaje' respectivamente. Por ejemplo, para comunicar el remitente de una notificación al usuario, puede especificar el nombre del remitente como título.

El cuarto y último argumento es opcional. Especifica qué aplicación debe activarse cuando el usuario hace clic en la notificación. De manera predeterminada, esto activará Terminal.app, para iniciar otra aplicación en su lugar, especifique el identificador del paquete de la aplicación. Por ejemplo, para iniciar Safari.app use: com.apple.Safari.

Dulce, una gran biblioteca! Me encantaría verlo actualizado con control sobre el ícono y la alerta frente al banner, pero definitivamente útil. Gracias por el enlace! i.imgur.com/tsCeK.png
Gran pequeña aplicación, creé un iniciador y puse /usr/local/bin para poder usarlo en cualquier lugar desde una terminal, etc. Script del iniciador: #!/bin/bash cd /Applications/terminal-notifier.app/Contents/ MacOS ./terminal-notificador $*
El iniciador es útil, si lo cambia un poco, funciona con texto entrecomillado con espacios: #!/bin/bash cd /Applications/terminal-notifier.app/Contents/MacOS ./terminal-notifier "$@"
Fácil de usar. Pero no funciona en cronjobs por alguna razón. estoy obteniendosh: terminal-notifier: command not found
@Nabin, ¿el usuario que ejecuta el cron tiene un brewdirectorio bin en la variable `$PATH? Por defecto no...

Solo quiero agregar una nota a la respuesta de @grgarside, porque sé que muchas personas quieren tener una ventana emergente de notificación que solo se puede descartar haciendo clic en un botón.

Comparación

He encontrado la solución para ti:

En realidad, estaba controlado por una configuración en Preferencias del sistema, en lugar de algún parámetro en el script escrito. Estas dos imágenes deberían explicarlo todo.

Gracias @grgarside por la gran respuesta.

Preferencia del sistema

Tenga en cuenta que la aplicación específica variará. Script Editores solo para Script Editor.appy osascript. En un flujo de trabajo de servicio, es Automator Runner. Cuando está adentro Automator.app, es Automator.
Me resulta molesto que si hago clic en el Banner, aparece la aplicación Editor de secuencias de comandos. Me gustaría que simplemente desaparezca al hacer clic, pero esta publicación señala que puede pasar el cursor sobre él y deslizar el trackpad hacia la derecha para que desaparezca en silencio: osxdaily.com/2012/09/05/…
@JoshuaGoldberg ¡Gracias por agregar eso! Descubrí eso intuitivamente un día, que es una cosa que me gusta de Mac OS X, funciona de la manera que esperas que funcione :)
¡ Intentar usar el osascriptcomando de repente no funcionaba, ni en iTerm ni en Terminal, hasta que fui a la configuración de Notificaciones para el Editor de secuencias de comandos y lo cambié de "Ninguno" a "Banners"!
Tuve problemas intermitentes para que el display notificationprograma funcionara correctamente; a veces funcionaba, otras veces simplemente estaba en silencio. Después de meses de este comportamiento frustrante, finalmente descubrí que era causado por No molestar , que había programado para activarse después de las 8:00 p. m. 🤦‍♂️
Esto ya no parece funcionar (Big Sur de todos modos)...

Ahora puede hacer esto con Growl2 ( disponible en la App Store ). Instale Growl y habilite las "Notificaciones de OS X" (captura de pantalla)

ingrese la descripción de la imagen aquí

Además, deberá instalar GrowlNotify para que una herramienta de línea de comandos envíe notificaciones de Growl. Puede descargar esta herramienta de forma gratuita en la página de descargas .

Ahora puede generar notificaciones de Growl desde la línea de comandos, que se reenviarán al Centro de notificaciones. Por ejemplo:

growlnotify -n "My App" -m "Hello world"

ingrese la descripción de la imagen aquí

Tenga en cuenta que actualmente no parece posible cambiar el icono de la aplicación.

Buen enfoque, especialmente si el gruñido ya está instalado.
Creo que podrías usar la opción --icon path/to/icon.pngpara íconos.
¿Obsoleto/ya no se mantiene? La última actualización fue para macos 10.9 mavericks

Recientemente bifurqué terminal-notifier para crear una herramienta de línea de comandos para mostrar alertas de notificación (con acciones) y alertas de tipo de respuesta.

Lo uso con mis scripts de shell y aplicaciones golang para obtener respuestas interactivas de los usuarios.

https://github.com/vjeantet/alerter

ingrese la descripción de la imagen aquí

También aparentemente obsoleto/abandonado.
Parece vivo y bien ahora.

La solución de @grgarside es buena, pero es vulnerable a la inyección de secuencias de comandos, lo que puede ser un problema de seguridad importante cuando se usa, por ejemplo, para mostrar el contenido del archivo de registro o algo similar.

Esto debería ser más seguro:

#!/bin/bash
X="$*" /usr/bin/osascript -e 'display notification system attribute "X"'
esto es interesante, pero ¿puede describir un escenario en el que un script que ejecuto en mi sistema que solo es ejecutable por el usuario es vulnerable a la inyección de script?
Si muestra contenido de usuario que no es suyo, es vulnerable. Por ejemplo, si ejecuta esto en un sistema con un servidor web público, o cuando alguna aplicación registra cadenas que obtuvo de la red que lee y muestra, por ejemplo, un navegador, un programa de correo o un cliente de Twitter. Podría tener un " para finalizar la cadena y la declaración, luego tener código y luego reiniciar una cadena.
bien, eso es verdad. es difícil para mí imaginar alguna vez poner contenido de formularios web en mis notificaciones, pero se acepta su punto.
Bueno, tal vez le gustaría decir algo como I have a "laser""citar" sus "palabras" sin que le digan que tiene un error de sintaxis. Con escapar, puede:script 'I have a "laser"'
Vota a favor porque siempre es bueno tener en cuenta la seguridad. Alguien podría copiar soluciones de pasta y usarlas de maneras que la persona que publicó la solución no había considerado.
Acabo de jugar con él; ese idioma parece escapar solo de una cita. ¿Hay una versión "global"?
@EdwardFalk a la sustitución le faltaba una barra. Debería funcionar ahora.
Si desea usar el escape, debe escapar \ -> \\ también, de lo contrario, \" se convierte en \\" y puede salir. Cambié el ejemplo para usar una variable de entorno en su lugar.

(Esta es una implementación alternativa basada en la excelente respuesta de @grgarside).

AppleScript se puede interpretar directamente colocando osascriptla línea shebang.

#!/usr/bin/osascript

on run argv
    if length of argv = 1 then
        display notification (item 1 of argv) with title "Notification"
    else if length of argv > 1 then
        display notification (item 1 of argv) with title (item 2 of argv)
    else
        return "<message> is required\nUsage: notify <message> [<title>]"
    end if
end run

Guárdelo notifyen algún lugar de su ruta, por ejemplo, /usr/local/bin/notifyy hágalo ejecutable ( chmod +x notify). Acepta un mensaje y un título opcional. Si alguno tiene espacios en blanco, envuélvalo entre comillas para que el shell lo interprete como un solo argumento.

$ notify "Lorem ipsum dolor sit amet" "Testing Notifications"
Esto evita los ataques de inyección a los que todas las demás respuestas son vulnerables.
Buen guión, gracias! Tenga en cuenta que "notificar" es un comando de shell incorporado en algunos comandos (como el mío, tcsh), por lo que es posible que deba usar un nombre diferente, como lo hice yo.
¿Hay alguna manera de hacer que la notificación sea fija, por lo que requiere un clic para descartar?
@CraigS.Anderson: una de las otras respuestas (de Vic Jang) indica que esto está determinado por las Preferencias del sistema del usuario (en Notificaciones> Editor de secuencias de comandos). No estoy al tanto de una forma con guión de hacer uno u otro.

Como Growl no es gratuito y terminal-notifier no está disponible en sistemas anteriores a 10.8, tiendo a usar cocoaDialog . Es gratuito y de código abierto, por lo que probablemente también pueda distribuirlo junto con sus scripts.

Si no necesita mucha personalización, también puede usar AppleScript, display notificationque también puede llamar desde el shell, como ya han mencionado otros.

Pero tenga en cuenta que AppleScript parece requerir comillas dobles. Entonces, si necesita variables, esto no funcionará :

osascript -e "display notification '$text' with title '$title'" #WRONG

Tendrá que usar comillas dobles escapadas. Esto es feo pero funciona :

osascript -e "display notification \"$text\" with title \"$title\""
Esto también funciona:osascript -e 'display notification "Lorem ipsum dolor sit amet" with title "Title"'
También en desuso. El enlace muestra "No hay un sitio de Páginas de GitHub aquí".

Aquí hay uno genial que uso en un script Ruby en OS X (para que pueda iniciar un script y obtener una actualización incluso después de salir de la ventana):

cmd = %Q|osascript -e 'display notification "Server was reset" with title "Posted Update"'|
system ( cmd )
guau... entonces la cadena es algo así como Usuario -> Ruby -> Shell -> AppleScript -> Objective-C -> Asamblea -> CPU?
Llegando tan tarde, pero para que conste, por conveniencia, escribí un contenedor LISP para el comando Ruby, y lo escribí con los brazos mecánicos de uno de esos exoesqueletos mecánicos gigantes P-5000 Powered Work Loader como Ripley usó en Aliens .
@JohnSmith Es precisamente por eso que leo todos los comentarios en las publicaciones de SE.
@johnsmith buen punto. Obviamente, deberíamos envolver esto en un contenedor docker y luego implementarlo con Kubernetes usando una canalización de CI/CD. :)

Una alternativa:

en .bash_profile:

function _sys_notify() {
    local notification_command="display notification \"$2\" with title \"$1\""
    osascript -e "$notification_command"
}
alias sys-notify="_sys_notify $1 $2"

Usar comando:sys-notify "title" "message"

Documentación oficial

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

Copiando el texto aquí, en caso de que el documento sea movido o eliminado.

Para mostrar una notificación, proporcione el comando de notificación de visualización con una cadena para mostrar. Opcionalmente, proporcione valores para los parámetros con título, subtítulo y nombre de sonido para proporcionar información adicional y una alerta audible cuando aparezca la notificación.

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

NOTA

Después de usar una secuencia de comandos para mostrar una notificación, la secuencia de comandos o el Editor de secuencias de comandos (si la secuencia de comandos se ejecuta desde el Editor de secuencias de comandos) se agrega a la lista de aplicaciones de notificación en Preferencias del sistema > Notificaciones. Allí, puede configurar opciones, como mostrar las notificaciones como alertas o pancartas.

Al hacer clic en el botón Mostrar en una notificación de estilo de alerta, se abre la aplicación que muestra la notificación. Para una aplicación de secuencia de comandos, la acción de volver a abrir la aplicación activa el controlador de ejecución de la secuencia de comandos, lo que puede causar que la secuencia de comandos comience a procesarse por segunda vez. Tenga esto en cuenta y agregue código a su secuencia de comandos para manejar este escenario, si corresponde.

Gracias, esto era justo lo que necesitaba para algunos scripts de usuario. Hice una ligera modificación para agregar un subtítulo y sonido. Si no se proporciona un valor, se ignora.

function _sys_notify() {
local notification_command="display notification \"$2\" with title \"$1\" subtitle \"$3\" sound name \"$4\""
osascript -e "$notification_command"
}

alias sys-notify="_sys_notify $1 $2 $3 $4"

Para el sonido, use un nombre de archivo de sonido sin la extensión de /System/Library/Sounds. Por ejemplo, para usar el archivo Ping.aiff, use Ping por $4

Si desea notificaciones adhesivas (el comentario de Vic Jang parece que ya no funciona, al menos en Big Sur), aquí hay una forma de usar el diálogo en lugar de la notificación:

osascript -e 'display dialog "Lorem ipsum dolor sit amet" with title "Title"'

Entonces podría hacer uno display notificationy luego seguirlo con el diálogo.

También alerter hace pegajoso.

$ brew install alerter
$ alerter -message "hi"
Buena solución, y puede evitar que dialogbloquee su terminal ejecutando en 'fondo':osascript -e 'display dialog "Lorem ipsum dolor sit amet" with title "Title"' &