On macOs Catalina have problems with making screenshots over cron.
When manually run do_screenshot.sh script then all fine.
But when it run auto over cron - probs, only menu correct, instead window content shown macOs background(see pic)
do_screenshot.sh:
#!/bin/bash
DATEFULL=`date '+%Y%m%d%H%M%S'`
FILENAME="/Users/yak/Documents/screenshots/"$DATEFULL.png
/usr/sbin/screencapture -x $FILENAME
Ran into this problem after the update too. Spent hours learning the details, here is the why and how. Credit goes to big-circle. The original question and answer here.
The problem is the cron doesn't have screen access.
Here's the solution
close SIP (System Integrity Protection).
Make sure your SIP is disabled. To check if SIP is disabled. To to terminal and type csrutil status. It should say SIP status: enabled/disabled.
To disable it:
Powerdown Mac, start up again and hold down cmd+r until OS X Utilities window shows up. Open terminal type csrutil disable. Restart again, boot into normal mac os.
grant write permission to TCC
sudo chmod 664 /Library/Application\ Support/com.apple.TCC
grant screencapure privilege to cron and screencapture
a) CRON:
`sudo sqlite3 "/Library/Application Support/com.apple.TCC/TCC.db" 'insert into access values ("kTCCServiceScreenCapture", "/usr/sbin/cron", 1, 1, 1, "", "", "", "UNUSED", "", 0,"")'`
b) screencapture:
Pre Big Sur:
`sudo sqlite3 "/Library/Application Support/com.apple.TCC/TCC.db" 'insert into access values ("kTCCServiceScreenCapture", "/usr/sbin/screencapture", 1, 1, 1, "", "", "", "UNUSED", "", 0,"")'`
--------------------------------------------------------------------------
Big Sur and later:
`sudo sqlite3 "/Library/Application Support/com.apple.TCC/TCC.db" 'insert into access values ("kTCCServiceScreenCapture", "/usr/sbin/screencapture", 1,2,4,1, "", "", "", "UNUSED", "", 0,"")'`
It's probably a good idea to turn SIP back on at this stage. To enable it, follow step 1, and instead of csrutil disable just type csrutil enable.
Edit # 2021-12-09T11:58:00+1000: Added in commands for Big Sur and later per comment from Silvan Mühlemann
You should allow your script to use the "Screen Recording" in the "Security & Privacy" system preferences.
You may start your app in a background from a terminal with a long loop (you need start it manually, that is not good):
#!/bin/bash
for value in {1..980}
do
/Users/<username>/record_activity_with_screen_capture.bash
sleep 60
done
echo All done
OR
use launchd (instead of cron) for running this script.
There are two examples:
how to start bash script in launchd
How to add timing
calendar example
Instead of playing with SIP (System Integrity Protection), which is dangerous, but suggested anyways but the top answer, simply give Screen Recording permissions to /usr/sbin/cron (or /sbin/cron in some MacOS versions I think).
In order to do that:
Open System Settings
Open Security & Privacy
Go to the Privacy tab
Go to Screen Recording
Click the lock in the bottom left corner and authenticate in order to enable editing the list
Now, if cron is listed there and unchecked, check it and the job is done. Likely is not listed there at all and you need to add it manually
Click on + below the list of programs
In the file picker hit a magic command Cmd+Shift+G, which will show a Go To Folder popup
Type: /usr/sbin and hit Enter (if you can't find cron in the next steps, try /sbin here instead)
You should see a list of files, all with an icon of a black terminal
Find cron on the list and hit Open
Check the checkbox next to cron
Wait for your cron to run the command again.
Voila, it should be capturing screenshots now.
You can try to change shebang to #!/bin/sh, or change screencapture to exec screencapture
Related
Inside my ~/Pictures/wallpapers/ folder I have a shell script that changes the wallpaper using a while true each time the sleep function terminates:
feh-auto.sh
#!/bin/bash
while true; do
feh /home/maruko/Pictures/wallpapers --randomize --bg-fill
sleep 1800
done
this script is automatically run each time the laptop powers up, or the i3 configuration is reloaded in place using the shortcut Win+Shift+R:
~/.config/i3/config
...
### CHANGE WALLPAPER RANDOMLY
# https://www.linuxandubuntu.com/home/set-background-wallpapers-on-i3wm
exec_always --no-startup-id ~/Pictures/wallpapers/feh-auto.sh
...
Making changes to the i3 configuration is usually accompanied with a reload in place, so that said changes take place.
The problem is that each time a reload occurs, a new instance of feh-auto.sh is also created, meaning that now instead of 1 timer, I have multiple timers of 1800, that will change the wallpaper x times where x is the number of times I reloaded the configuration.
I would like a more appropriate behavior as I reload: check if feh-auto.sh is already running and if it is, do not create a new instance.
Could you please guide me to the best solution?
Thank you.
EDIT
As #balki suggested in the comments, I have created a cron job
(sudo crontab -e)
#reboot /home/maruko/Documents/program-files/shell/feh-auto.sh
to run the following script
feh-auto.sh
#!/bin/bash
export DISPLAY=0:0
feh /home/maruko/Pictures/wallpapers/ --randomize --bg-fill
However, when booting up or rebooting the system, the wallpaper is blank as if nothing really happened. The command sudo systemctl status cronie.service reports the following:
crond[3300]: pam_unix(crond:session): session opened for user root(uid=0) by (uid=0)
CROND[3307]: (root) CMD (/home/maruko/Documents/program-files/shell/feh-auto.sh)
CROND[3300]: (root) CMDOUT (feh ERROR: Can't open X display. It *is* running, yeah?)
CROND[3300]: (root) CMDEND (/home/maruko/Documents/program-files/shell/feh-auto.sh)
CROND[3300]: pam_unix(crond:session): session closed for user root
I don't know what to do next.
The answer to this post is to read documentation:
i3 config comes with the exec and exec_always commands:
exec will execute the command once at boot,
exec_always will execute the command on reloads too.
The solution is to substitute the above call to feh-auto.sh:
~/.config/i3/config
### START FEH WALLPAPER
# note: exec_always will run the script on each reload, not ideal
# --no-startup-id will eliminate the problem of loading icon on boot
exec --no-startup-id /home/maruko/Pictures/wallpapers/feh-auto.sh
I've looked for ages, but I can't seem to find the right answer that will work. I want to run launchd every timestep (e.g. every minute) when I'm logged out or when the screen is locked (I'm happy if I can do it in one or both ways).
What I've done:
Create a .plist file with a simple command that has text output.
The .plist has stdout and stderr output to log files.
I load it with `sudo launchctl -w /Library/LaunchDaemons/mydaemon.plist
I create the file via cp ~/mydaemon.plist /Library/LaunchDaemons
Put the energy saver to "never sleep" (including the disks), both on battery and when the power adapter is on.
As long as I'm logged in and have an unlocked screen, it works, the daemon runs.
I've tried both:
Option key + command key + power button (screen lock)
Shift + command key + Q (logout)
After copying myexentension#me.com folder to .../gnome-shell/extensions/ I'm executing this command on the terminal:
gnome-shell-extension-tool -e myexentension#me.com
Then, I restart my session with Alt + F2 and execute r, and everything works fine.
But can I start my extension only through the command line? Without Alt+F2+r? Without restarting my gnome-shell session?
According to some answers around the internet, sending SIGHUP to the gnome-shell process restarts it (i. e. killall -HUP gnome-shell), but I haven’t been able to find a clear source on this and couldn’t find the signal handling in the code. What I do know is that this should be exactly equivalent to Alt+F2 r:
busctl --user call org.gnome.Shell /org/gnome/Shell org.gnome.Shell Eval s 'Meta.restart("Restarting…")'
Because apart from a gettext call on the message, this is exactly what Alt+F2 r is bound to (see runDialog.js – search for _restart).
January 2022 update: Since Gnome 41, calling Eval is restricted and requires “unsafe mode” to be enabled, so by default this will no longer work. I’m not currently aware of a replacement for this particular usage.
Personally, I prefer a solid Alt+F2, r+Enter but maybe try disabling and enabling:
gnome-shell-extension-tool -d myexentension#me.com && gnome-shell-extension-tool -e myexentension#me.com
or
gnome-shell-extension-tool -r myexentension#me.com
Which may do the same thing. There's also gnome-shell-extension-prefs which you can use to do the same thing (and is typically hidden in Gnome for some reason).
A notification center notification would be ideal but growl, bounce dock, sound, etc would be fine, too (or if this can only be done in Terminal.app I'd be willing to switch back). Is there an option somewhere in iTerm to turn on notifications or is it something I'm supposed to type at the end of a command in the terminal? If the latter, is it possible to add an alert once process has started (for example if I realize it's going to take longer than I initially expected, I'm bad at guessing).
Notify on an already running process:
Edit → Marks and Annotations → Alerts → Alert on next mark
or Shortcut: ⌥⌘A
: iTerm will literally keep an eye (on top right corner) of your terminal. Once the command is finished, it will issue a notification.
Requirement: Shell Integration:
iTerm2 → Install Shell Integration
NOTE: integration will not issue notifications until iTerm2 is restarted.
Example Use Case:
We launched a command, underestimated completion time, and we don't want to cancel or just wait for completion.
And you can always use the say command.
Usually when you are running a long process inside the terminal and want to get updated you can simply use this command to speak out things like done or error or bazinga.
mvn clean install; say done
This command builds a java spring app, and takes a long long time, and it will speak out done after the process is complete.
You can add any one of the following after any command, with a semi-colon in between the command and it:
afplay /System/Library/Sounds/Ping.aiff -v 2
osascript -e 'beep 3'
tput bel
or, if you like Notification Centre
osascript -e 'display notification "Lorem ipsum dolor sit amet" with title "Title"'
You can also make an alias in your profile, called notify and add that at the end of your command. So, in your login profile
alias notify="tput bel"
then
sleep 10; notify
Or, if you started your command and it is "hanging", just type notify and hit Enter and it will run your notify alias at the end, whne the command has finished, e.g.
sleep 20
# wait 5 seconds before realising this will take 20 seconds
notify<Enter>
iTerm2 supports Growl notifications. You can turn it on in each profile settings.
Select a profile in Preferences…->Profiles.
Then in Terminal tab there is an option Enable Growl Notifications.
Remember to also enable iTerm notifications in Growl preferences.
If you want to get notification for a given process you could try to experiment with Triggers. You define triggers in Advanced tab in a profile settings. In this way you may assign a Growl notification to a particular output of your process (regexp).
You could for example do:
$ mycommand; echo "end-of-my-process"
And connect trigger to "end-of-my-process" message.
Update
Read more about triggers on iTerm2.com.
There is an OSS tool called noti.
You can easily install it with brew install noti and start using it just by prefixing your command with noti like noti sleep 3.
Install the iTerm2 shell integration
curl -L https://iterm2.com/shell_integration/install_shell_integration_and_utilities.sh | bash
Execute your command and concatenate the attention app, e.g.
./task && ~/.iterm2/it2attention once
It'll cause the iTerm app to bounce it's icon once the job is complete.
You also have other attention options:
$ .iterm2/it2attention -h
Usage:
it2attention start
Begin bouncing the dock icon if another app is active
it2attention stop
Stop bouncing the dock icon if another app is active
it2attention once
Bounce the dock icon once if another app is active
it2attention fireworks
Show an explosion animation at the cursor
You can also use terminal-notifier which use mac os system notifications. To install it via Home brew just:
$ brew install terminal-notifier
Then if you want to display notification when your job/process is done use something like this
$ <your job/process command> && echo 'Completed' | terminal-notifier -sound default
And this display like this:
You can also change sound and icon of notifications. More info in github repo: https://github.com/julienXX/terminal-notifier
I have an OSX application providing a service menu to other applications. This works fine so far, the menu is activated and available after a user installed the app and logged out and back in. (see similiar post)
I know the log-out-and-back-in is obsolete when triggering the service menu agent (pbs) to scan for changed services by opening a terminal and running
/System/Library/CoreServices/pbs
(this also works without having the new application launched even once)
So I´d like to provide an installer (.pkg) which runs "pbs" as post-install script. Suprisingly, running "bps" as post-install only works if the application was launched before e.g.:
#! /bin/sh
sleep 3
open /Applications/MyApp.app
sleep 3
/System/Library/CoreServices/pbs
exit 0
Unfortunately, (due to application specific reasons) I do not want to start my application directly from the installer. Does anyone know why the post-install-scrips behaves different than the Terminal?
Depending on the rights the Installer requires the post-install scripts maybe runs as root user. Try:
sleep 3
su -l "${USER}" -c "open /Applications/MyApp.app"
sleep 3
su -l "${USER}" -c "/System/Library/CoreServices/pbs"
exit 0
Eventually, as a workarround, I am going to start my application hidden and stopping it again before running pbs. Still looking forward for a better solution.