I have written a Unix shell script to call Growl -- here's the source. My script is named growl, and I keep a copy in $HOME/bin. I generally use my Growl script to notify me when a long-running Unix script finishes. If you are imaginative, you could have a cron job that calls Growl when disk space is low:
#!/bin/sh
df -m / | awk '
/Filesystem/ { next }
200 > $4 { system("growl root only has " $4 "MB available") }
'
Or if a critical system has gone off-line:
#!/bin/sh
if ! ping -c 1 -t 10 critical.system.com; then
growl critical.system.com is off-line
fi
If you have a multicore processor in your Mac, then instead of doing the traditional compile and install steps for a *nix program...
$ ./configure
$ make
$ make install
...use this version instead:
$ ./configure
$ make -j n
$ make install
The n in the second line is the number of jobs you want make to start. So to reduce compile time, replace n with the total number of cores in your Mac.
[robg adds: At some point, I'd like to test this with a large compile, but I haven't had the time as of yet. If you've done any testing on compile time reductions versus cores used, please post your results in the comments. I think this should work on multi-core G5s and all the Intel Macs...]
This hint is based on this previous hint, and alluded to in this comment to that hint. I went ahead and created a DVD-spanning script using tar. Copy and paste this code into your favorite pure text editor, and save it as tar2dvd.sh. In Terminal, make it executable (chmod 755 tar2dvd.sh), and store it somewhere on your path for easy access.
To use it, just type tar2dvd.sh folder_to_backup in Terminal. For example, you could do this:
$ cd ~/Documents
$ tar2dvd.sh MyBigFolder
When the processing is done, you'll find a new folder called MyBigFolder.backup, which will contain numbered subdirectories, one per DVD.
[robg adds: This worked well in my testing, even on folders with spaces in their names. Note that if you use Apple's Backup app, you'll probably want to change the line that reads TARDIR=$BACKUPDIR.backup -- the .backup extension will make it appear as though the end result is a Backup package bundle. I changed the extension to simply .bkup, and then the end result is a folder, as expected.]
I see many hints here on Mac OS X Hints that use the grep utility to filter text. However, many of these hints use grep to search for a plain string, rather than a regular expression. There's nothing wrong with that goal, but using grep for that is inefficient (you're invoking the full power of the regex engine just for a plain string), and requires that you escape any regex characters in the pattern:
grep 'Price: $' partslist.txt
# Incorrect: Only matches "Price: " at the end of a line
grep 'Price: $' partslist.txt
# Correct: Matches "Price: " followed by a dollar sign
There's a better way. grep also exists under the name fgrep, which searches for a fixed (hence the 'f') string -- that is, a plain string; no characters are special. You can search for any string this way, with no escaping needed (see note below):
fgrep 'Price: $' partslist.txt
# Correct: Matches "Price: " followed by a dollar sign
You can also do this with grep -F, but fgrep is shorter. fgrep and grep are the same program, just with different behavior, so all the other options (-n, -o, -H, etc.) are supported by both.
Note: Of course, you may need to escape quotes or backslashes according to the rules of your shell, but you would have to do this anyway. My point is that fgrep does not require quoting where grep itself would.
This tip will work on almost any *nix OS with curl installed. Create a text file called dfltpwd on your Desktop. Copy and paste the following into the text file:
After doing the above, test the script with something like dfltpwd "belkin". The results should be a listing of default passwords for any Belkin devices from the phenoelit.de site.
[robg adds: I don't tend to save things to /usr/bin, for fear that I overwrite something someday if I ever reinstall the OS. Instead, I have a local user bin folder on my path where such files reside.
And before the comments start, this script is not a way to "hack" networked devices. The script merely makes it easier to find the default password for a given networked device. Speaking as someone who has looked up too many of these in manuals (can you say "AirPort Express?"), this is a handy timesaver. There are quite a few sites that provide such lists, and this little shell script merely makes it easier to view the data from one such site. Also, if you happen to have any network devices that still have their default passwords, this is a good time to mention that you really should change them, because they are about as far from secure as I am from a good golfer...]
Yesterday I had the need to run a cron process more than once a minute -- I wanted to grab a still frame from a web camera every 15 seconds, in order to create a time-lapse movie. The standard cron syntax lets you specify the minute(s) at which a task runs, but you cannot (to my knowledge) specify an interval less than once a minute (using */1).
After much Googling, I finally found the solution, posted in some newsgroup somewhere (sorry, I didn't mark the page): create a simple shell script that repeatedly runs the task, with a sleep command between each call to the job. In my case, my shell script looked like this:
#!/bin/sh
open /path/to/getpic.app
sleep 15
open /path/to/getpic.app
sleep 15
open /path/to/getpic.app
sleep 15
open /path/to/getpic.app
sleep 15
This will run the task four times over the course of a minute (not allowing for processing time). I then created my cron entry to call the above script, with the minute interval set to "every minute" (*/1), and sat back to see what would happen (not for the full twelve hours, of course!). The final result? Not too bad, but not perfect -- I captured a frame about every 25 seconds, instead of every 15. I think I need to reduce the sleep value to allow for the processing time of the getpic.app, so I'll try that later today. As for exactly what it was I was capturing for 12 hours, well, that too is for another day. (It will probably show up on my blog, not here -- though I may write up the 'acquire image' bit as a separate hint, as it was a little tricky.)
In summary, if you need a cron task to run more than once a minute, create a simple shell script using sleep, and have it call your other task the required number of times per minute, then tell cron to run that shell script. I'd love to hear if there are better ways to do this (via cron, launchd, or any other mechanism...).
I really don't know what I'm doing here (my experience in shell scripting amounts to about two hours), but I put together this little script that will print out a random message each time you open a new bash window. Just copy this into your user's .bash_profile file, located in your user's home directory:
fn=/path/to/quotes.txt
cnt=$(wc -l $fn)
lns=${cnt:6:2}
if [ "$lns" = 0 ]; then
rnd=1
else
let "lns += 1"
rnd=$(expr $RANDOM % $lns)
let "rnd += 1"
fi
sed -n ${rnd}p $fn
Set the fn variable in the first line to the path and name of your quotes file. Each quote should be on its own line, with no extra lines between the quotes.
[robg adds: This worked for me -- note that this will not replace Terminal's welcome message (Welcome to Darwin!) with the quote -- it shows up after the welcome message. If you want to change the welcome message, you need to edit /etc/motd. Replacing the welcome message with a random quotation is left as an exercise for the reader (i.e. I don't have a clue...), but this hint might get you started.]
This is a simple Folder Action Script that will set the executable bit on any file saved within the folder to which the script is attached. Copy and paste the following into a Script Editor document, and save it as a script into your Folder Action Scripts directory.
on adding folder items to thisFolder after receiving theItem
set fileName to POSIX path of theItem
do shell script "chmod +x " & fileName
end adding folder items to
Remember to call your shell (#!/bin/bash) or application (#!/usr/local/bin/ruby -w) in the first line of your script. Then save to, or drag your file to, the folder with the action script attached.
X11.app preferences allow you to set it to 256 colors for the occasional x-windows programs requiring this setting, but you may then find other x-windows applications don't function at all, or at least look terrible. There is a simple way to have it both ways, simultaneously. The trick is to create a wrapper shell script that looks something like this:
This essentially forces a second X11 session to be started on a different (randomly determined) DISPLAY, so it can peacefully coexist with X11.app running in default mode (usually on DISPLAY :0.0, unless multiple users have X11 running with Fast User Switching). By randomly assigning the DISPLAY, multiple instances of the program invoked from the wrapper script can be run simultaneously. This works on Intel powered Macs now, too.
I like to keep the home directories on my work (PC) and home (Mac) machines more-or-less in sync using a hard drive that I tote back and forth every few weeks. In addition to rsync, one useful tool is the unix diff command.
As mentioned in otherhints, diff can not only compare two files, it can, by using the -r option, walk entire directory trees, recursively checking differences between subdirectories and files that occur at comparable points in each tree. The trick is to use the -q option to suppress line-by-line comparisons in files that differ:
diff -rq dirA dirB
This command will provide a nice list of files that occur in dirA but not in dirB, files that occur in dirB, but not in dirA, and files that differ between dirA and dirB. Pipe the output through grep to remove mention of uninteresting files, and sort to tidy it up, e.g.:
This list gives me a good feel for the big picture before I start overwriting things: which files or subdirectories can be deleted, which can be synced (and in which direction) using rsync, and which should be carefully checked before replacing, in case changes need to be merged.
To forestall some obvious comments, Unison would seem to be the ideal tool, but it lists hundreds of files that only differ in their permissions metadata (not important to me). Although Unison appears to have an option to turn off permission checking (-perms 0, or -perms=0), I couldn't get it to work. There are, of course, a number of GUI apps that would do the job, too (e.g., FileMerge), many of them shareware.