You are not logged in.
Offline
It's a variable expansion on $1, and it means that if $1 is unset, put in a literal 1 (the bit after ":-"). ":" is the general expansion action that does things in the value is unset, and "-" is a specific subaction of it. There are others like := which sets it if unset. I forget them all, but man bash will get you there
[git] | [AURpkgs] | [arch-games]
Offline
It's a variable expansion on $1, and it means that if $1 is unset, put in a literal 1 (the bit after ":-"). ":" is the general expansion action that does things in the value is unset, and "-" is a specific subaction of it. There are others like := which sets it if unset. I forget them all, but man bash will get you there
Ahh, thank you for the information. It now makes a lot more sense.
Offline
Now that's a lot cleaner.
Although with "robust"ness i meant 1) more or less than 1 argument, 2) a non-integer $1, which will make seq err.
The source you've given has a nice one, here's a simpler version:
up ()
{
test $# -eq 0 && { cd ..; return; }
test $# -eq 1 && test "$1" -ge 0 2> /dev/null || { echo error; return 1; }
for i in $(seq $1); do cd ..; done
}
The greater-than/equal-to 0 test with '2> /dev/null' also ensures that the variable holds an integer. The fact that it allows 0 and 1 means you can use `up 0` to do nothing (!) and `up 1` as a longer version for `up`. `seq` returns nothing when given a single negative number, but i prohibited negatives anyway since they're illogical unlike say 0.
``Common sense is nothing more than a deposit of prejudices laid down by the mind before you reach eighteen.''
~ Albert Einstein
Offline
You can also do "for updirs in {1..${1:-1}};" which is nicer than seq
[git] | [AURpkgs] | [arch-games]
Offline
Can you? I've never had any success nesting variables inside a brace expansion...
$ foo=5
$ echo {1..${foo}}
{1..5}
The guys in #bash recommend just using a for/while loop:
for ((i=1;i<${1:-1};i++); do...done
i=1
while [[ $i -lt ${1:-1} ]]; do...i=$(($i + 1));done
Offline
Ah, I hadn't tried it. Just assumed it would work.
[git] | [AURpkgs] | [arch-games]
Offline
Hi, after forgetting time and time again to write sudo in front of nano, editing a root-owned text file, then trying to save it and failing, I finally broke down and wrote a script which automates everything. I added in the -u flag (which allows you to edit as the owner of the file instead of as root when you are not the owner), the -g flag (which allows you to edit using your _graphical_ editor of choice), and the -gu flag (combines both -g and -u). It requires gksu, the $EDITOR variable to be set to your CLI editor of choice, and the $GUIEDITOR variable to your GUI editor of choice. This can be easily edited to use su instead of sudo if you so prefer.
edit() {
case $1 in
-u)
if [ -w $2 ]; then
$EDITOR $2
else
_fileUid=`stat ~ | grep uid | cut -d" " -f6`
_uidName=`getent passwd $_fileUID | head -n 1 | cut -d":" -f1`
if [ $_uidName = 'root' ]; then
sudo $EDITOR $2
else
sudo -u $_uidName $EDITOR $2
fi
fi
;;
-g)
if [ -w $2 ]; then
$GUIEDITOR $2
else
gksu $GUIEDITOR $2
fi
;;
-gu)
if [ -w $2 ]; then
$GUIEDITOR $2
else
_fileUid=`stat ~ | grep uid | cut -d" " -f6`
_uidName=`getent passwd $_fileUID | cut -d":" -f1`
if [ $_uidName = 'root' ]; then
gksu $GUIEDITOR $2
else
gksu -u $_uidName $GUIEDITOR $2
fi
fi
;;
*)
if [ -w $1 ]; then
$EDITOR $1
else
sudo $EDITOR $1
fi ;;
esac
}
Offline
hehe, all that when a little
cmap w!! w !sudo tee % >/dev/null<CR>:e!<CR><CR>
works for vim
Not everyone likes vim. I barely know enough about vim to browse through text files with it, i still can't remember how to insert text, and will probably forget again. ;P
Offline
find . -type d -name .git | while read gitdir; do
pushd $gitdir
git remote update
popd
done
Last edited by Daenyth (2010-06-24 16:08:42)
[git] | [AURpkgs] | [arch-games]
Offline
Here is a function I wrote for my ~/.bashrc
function makescript()
{
[ $# -eq 0 ] || [ $# -gt 2 ] && echo '
Usage: makescript <FILENAME> <INTERPRETER>
FILENAME - if no path is specified, just a filename, this will occur in the working
directory
INTERPRETER - Supported interpreters are bash, perl, python, ruby, sh' && return 1
interp=''
if [ $# -eq 2 ]; then
case $2 in
py | python) interp='#!/usr/bin/python' ;;
b | bash) interp='#!/bin/bash' ;;
pl | perl) interp='#!/usr/bin/perl' ;;
sh) interp='#!/bin/sh' ;;
ru | ruby) interp='#!/usr/bin/ruby' ;;
*) echo "$2 isnt a known interpreter"; exit $? ;;
esac
else
interp='#!/bin/bash'
fi
if [ -f "$1" ]; then
echo "makescript: do you wish to over-write $1? (Y/n) "
read answer
case $answer in
y | Y | yes | YES) > $1; echo "makescript: file cleared for new script." ;;
n | N | no | NO) echo "makescript: operation aborted."; exit $? ;;
*) echo "makescript: not a correct response. aborting."; exit $? ;;
esac
else
> $1
fi
echo $interp > $1
chmod +x ./$1
echo "makescript: $1 has been created and chmodded."
}
I know, seems lazy but I was bored at the time so I wrote that.
For the noobs, this script creates empty script templates and chmods them executable.
You could also make defaults if no second argument is specified, which I am thinking about doing, to default to a bash script.
EDIT: I went ahead and modified it. If no arguments are provided, or more than 2 then the usage is printed. if you provide only a filename then bash is defaulted.
Last edited by evil (2010-06-26 22:50:53)
Offline
Can you? I've never had any success nesting variables inside a brace expansion...
$ foo=5 $ echo {1..${foo}} {1..5}
The guys in #bash recommend just using a for/while loop:
for ((i=1;i<${1:-1};i++); do...done
i=1 while [[ $i -lt ${1:-1} ]]; do...i=$(($i + 1));done
until recently, i was unaware that you could use C style for statements. i like that a lot
Offline
Heh, feels like im taking over the thread. Here is yet another script. To use it, you will either have to run it as root or chmod 744 /var/log/* so the average user can read the logs, just not modify/move/delete.
#!/bin/bash
usage()
{
echo "
Usage: logviewer [OPTIONS] log
Options:
-f: Follow the log
-l: Number of lines to tail log (default 10)
-h: This help message
-v: Verbose
Programmed Logs:
all, ao, archftw, auth, crond, dmn, dmesg, err,
faillog, kdm, kern, last, msg, pac, slim, sys,
user, uucp, wtmp, and xorg
Example(s):
logviewer err - views the error log
logviewer -fvl 5 kern - displays last 5 lines of the
kernel.log and continues to follow it as text is
added to the log with verbose switched on"
}
[ $# -eq 0 ] && echo "logviewer: no arguments specified" && usage && exit $?
logdir="/var/log/ /home/$USER/.weechat/logs/"
follow=0
lines=10
mylog=''
verbose=0
while getopts "fhvl:" options ; do
case $options in
f) follow=1; ;;
l) lines=$OPTARG; ;;
v) verbose=1; ;;
h) usage; exit $?; ;;
esac
done
shift $(($OPTIND - 1))
case $1 in
all) mylog='everything.log' ;;
ao) mylog='irc.freenode.#archlinux-offtopic.weechatlog' ;;
archftw) mylog='irc.freenode.##arch-ftw.weechatlog' ;;
auth) mylog='auth.log' ;;
crond) mylog='crond.log' ;;
dmn) mylog='daemon.log' ;;
dmesg) mylog='dmesg.log' ;;
err) mylog='errors.log' ;;
faillog) mylog='faillog' ;;
kdm) mylog='kdm.log' ;;
kern) mylog='kernel.log' ;;
last) mylog='lastlog' ;;
msg) mylog='messages.log' ;;
pac) mylog='pacman.log' ;;
slim) mylog='slim.log' ;;
sys) mylog='syslog.log' ;;
user) mylog='user.log' ;;
uucp) mylog='uucp.log' ;;
wtmp) mylog='wtmp' ;;
xorg) mylog='Xorg.0.log' ;;
*) echo "logviewer: the log you specified isnt available"; exit 1 ;;
esac
tries=0
for i in $logdir ; do
if [ -f $i$mylog ] && [ $follow == 0 ]; then
[ $verbose -eq 1 ] && echo "logviewer: now showing the last $lines line(s) of $logdir$mylog"
tail -n $lines $i$mylog
elif [ -f $i$mylog ] && [ $follow == 1 ]; then
[ $verbose -eq 1 ] && echo "logviewer: now displaying the last $lines line(s) of $logdir$mylog in follow mode"
tail -fn $lines $i$mylog
elif [ ! -f $i$mylog ]; then
[ $tries -eq 1 ] && echo "logviewer: the log you have requested does not currently exist."
fi
tries=$(($tries + 1))
done
I wrote this for practice because I had never used getopts before.
EDIT: I am actually finding this script useful when I ssh in to a computer and need to quickly check logs for something.
Last edited by evil (2010-06-27 15:11:11)
Offline
you will either have to run it as root or chmod 744 /var/log/* so the average user can read the logs, just not modify/move/delete.
Better solution:
sudo gpasswd -a $USER log
I'll contribute... a password generator:
#!/bin/bash
ALLOWEDCHARS='[:alnum:][:punct:]'
if [[ $# -eq 0 ]]; then
echo "Usage: ${0##*/} <string length> [output quantity]" >&2
exit 1
fi
[[ -z $2 ]] && set $1 1
cat /dev/urandom | tr -dc $ALLOWEDCHARS | fold -w $1 | head -n $2
Offline
Far from a tool, but it just came in handy to convert a folder full of .vcf files (as Nokia's N900 exports it's Contacts) into one giant .vcf file as Evolution likes them.
In principle it's a simple cat *.vcf >> all.vcf but then one misses newlines between the files so here is my hacky solution:
#!/usr/bin/zsh
touch all.vcf;
rm all.vcf;
find -name '*.vcf' | while read filename;
do;
cat $filename >> all.vcf;
echo "\n" >> all.vcf;
done;
Offline
#!/bin/sh
cd /srv/http/stream || exit 1
mkdir -p /tmp/fifos
if [ -e /tmp/fifos/mplayer ]
then
test -p /tmp/fifos/mplayer || exit 1
else
rm -f /tmp/fifos/mplayer # Might have been a dangling symlink; just remove it
mkfifo /tmp/fifos/mplayer
fi
mplayer tv:// -slave -input file=/tmp/fifos/mplayer -vf screenshot -vo null < /dev/null > /dev/null 2>&1 &
trap "kill $! 2> /dev/null; exit" INT TERM EXIT
sleep 3 # Give MPlayer time to initialize
rm -f shot????.png # Initial cleanup
while true
do
echo screenshot 0 > /tmp/fifos/mplayer
sleep 2 # Here's our FPS setting (this would be 0.5 FPS)
mv shot????.png current_frame.png
done
Put a screenshot to /srv/http/stream/current_frame.png (change to whatever you want) every N seconds.
Clients may create their own frontends. (View http://foobar/stream/current_frame.png and refresh every N seconds.)
A default frontend with once per 2.5 seconds refresh (totally simple HTML+JavaScript) is present as index.html in the directory 'stream'.
There you've got cheap and dirty streaming from your webcam.
---
I had shared some older, crappy version of this:
#!/bin/dash
#
# screenrec.sh: POSIX sh based screen recorder that relies on scrot and mencoder.
# You also need bc.
#
. "$HOME"/bin/common_stuff.sh
if [ $# -gt 1 ]
then
echo >&2 "usage:"
echo >&2 "$z [filename]"
echo >&2
echo >&2 "'filename' defaults to 'out' and will be appended '.avi'"
echo >&2 "send a SIGINT (e.g. press ^C) to stop recording"
fi
file=${1:-out}
make_tmp_dirs imgdir || exit 2
trapEXIT "rm -rf '$imgdir'"
breaker=${TMPDIR:-/tmp}/$z-$$-breaker
trapEXIT "rm '$breaker'"
trap "touch '$breaker'" INT
start=$(date +%s)
for i in $(seq -w 1 999999)
do
scrot "$imgdir"/$i.png
test -e "$breaker" && break
done
dur=$(( $(date +%s) - start ))
fps=$(echo "scale=3; $(ls "$imgdir" | wc -l)/$dur" | bc)
mencoder "mf://$imgdir/*" -mf fps=$fps -o "$file".avi -ovc lavc -lavcopts vcodec=mpeg4 > /dev/null 2>&1
Something like 1 FPS, and the mouse isn't visible, and it lags the OS like hell while it's running, but hey it works! xD
``Common sense is nothing more than a deposit of prejudices laid down by the mind before you reach eighteen.''
~ Albert Einstein
Offline
Run xstart after login to select your WM. BEFORE USING make a backup of your $HOME/.xinitrc file.
#!/bin/bash
# Name: Evil (Arch forum nick / registered nick on Freenode)
# Script: Start-up WM Selector
# Scriptname: xstart
# Date: July 4th 2010
wm=''
choice=''
dialog --title "Select your Window Manager" --menu "Choose one of the following or press <Cancel> to exit." 11 40 3 "1" "KDE" "2" "Openbox" "3" "Rat Poison" "4" "Awesome" "5" "Enlightenment" 2> ./.ans
choice=$(cat ./.ans)
case $choice in
1) wm='startkde'
;;
2) wm='dbus-launch --exit-with-session openbox-session'
;;
3) wm='dbus-launch --exit-with-session ratpoison'
;;
4) wm='dbus-launch --exit-with-session awesome'
;;
5) wm='dbus-launch --exit-with-session enlightenment_start'
;;
*) exit 1
;;
esac
clear
cd ~
echo 'xman: configuring .xinitrc'
setheader='#!/bin/bash'
echo "$setheader
exec $wm" > .xinitrc
echo 'xman: .xinitrc configured'
echo 'xman: launching X'
startx
Last edited by evil (2010-07-05 19:54:39)
Offline
~/.xinitrc is a bash script. Don't overwrite it, put your selection stuff in it.
[git] | [AURpkgs] | [arch-games]
Offline
~/.xinitrc is a bash script. Don't overwrite it, put your selection stuff in it.
I did. I put the script in there minus the parts of overwriting .xinitrc of course then typed startx and didn't work. It wont even show the dialog.
Offline
I'm a bit of an amateur at scripting and such, but I love customization. GDM >=2.8 is bloody irritating to customize.
I know one should be able to run something like "sudo -u gdm gconftool-2 --set --type string /desktop/gnome/background/picture_filename /path/to/your/background/here.jpg" to change the background for the GDM login.
I couldn't get that to work at all, however.
So I wrote this.
#!/bin/sh
echo "Enter your username (e.g.,[hwkiller] without the brackets)"
read USER
bkrnd=`sudo -u $USER gconftool-2 --get /desktop/gnome/background/picture_filename`
echo "Using $bkrnd"
if [ ! -e /usr/share/pixmaps/backgrounds/gnome/nature/gnome-background-default.jpg ]; then sudo cp /usr/share/pixmaps/backgrounds/gnome/background-default.jpg /usr/share/pixmaps/backgrounds/gnome/nature/gnome-background-default.jpg
fi
sudo cp $bkrnd /usr/share/pixmaps/backgrounds/gnome/background-default.jpg
echo "Finished."
You just run it as root and type in which user's background you want to use for the login screen. If you've never run it before, it will backup the original default background picture and replace it with your preferred one.
Offline
#!/bin/bash
################################################### CONFIGURATION ######
PKGBUILDSPATH=/data/etc/PKGBUILDS
REPOPATH=/data/WWW/pozitpoh.is-a-geek.org/repo/i686
REPONAME=pozitpoh
########################################################################
################################################### Variables ##########
PKGNAME=1
########################################################################
################################################### Main code ##########
################################################### Rebuild all packages
buildpkg_done () {
echo -e "\033[1;36m===>\033[0m \033[1;32mJob completed. Check ~/reporebuild Logs/reporebuild-PKGNAME.log for details.\033[0m"
exit
}
buildpkg () {
for PKGNAME in $(cat ~/.reporebuild | awk '{ print $PKGNAME }'); do
# END in package list detected?
if [ "$PKGNAME" == "END" ]; then
buildpkg_done
fi
echo -e "\033[1;36m===>\033[0m Rebuild package: \033[1;31m$PKGNAME\033[0m"
cd $PKGBUILDSPATH/$PKGNAME
makepkg $3 &> ~/reporebuild\ Logs/reporebuild-$PKGNAME.log
echo -e "\033[1;36m===>\033[0m \033[1;33mRebuild complete. Moving package\033[0m \033[1;31m$PKGNAME\033[0m \033[1;33mto repository dir and update repo database...\033[0m "
rm $REPOPATH/$PKGNAME-*.pkg.tar.* &> /dev/null
mv $PKGBUILDSPATH/$PKGNAME/$PKGNAME-*.pkg.tar.* $REPOPATH &> /dev/null
cd $REPOPATH && rm $REPONAME.db.tar.gz && repo-add $REPONAME.db.tar.gz *.pkg.tar.gz *.pkg.tar.xz &> /dev/null
PKGNAME=PKGNAME+1
done
################################################### Make some cycle :>
buildpkg
}
all () {
echo -e "\033[1;36m=====>\033[0m Rebuild all packages.\033[0m Output redirected to ~/reporebuild Logs/reporebuild-PKGNAME.log"
buildpkg
}
################################################### Some help :>
help () {
clear
echo "=================================================================================="
echo -e "\033[1;32mLocal repository rebuild script\033[0m version 0.3"
echo -e "\033[1;33mUsage:\033[0m"
echo "reporebuild.sh [OPTION] -f"
echo
echo "Options:"
echo " all rebuild all packages specified in ~/.localrepo"
echo " build pkgname build specified package from AUR (PKGBUILD will be saved"
echo " in PKGBUILDS directory for later usage with localbuild"
echo " command)"
echo " localbuild pkgname rebuild only specific package from local PKGBUILD"
echo " -f force rebuild (for localbuild only)"
echo
echo "You must verify CONFIGURATION section in this script."
echo "PKGBUILDs must be placed in <pkgname> folder (for example, for PSI-PLUS package:"
echo "psi-plus/PKGBUILD)"
echo
echo
echo "List of packages in your local repository must be placed in ~/.localrepo"
echo "Example contents of ~/.reporebuild:"
echo
echo "packagename1 packagename2 ... packagenameN END"
echo
echo -e "\033[1;31mREMEMBER!\033[0m Word 'END' in the end of package list is mandatory!"
echo
echo
echo "If you want to build package from AUR (option 'build pkgname') - you need yaourt to"
echo "be installed"
echo "=================================================================================="
}
case "$1" in
all)
all
;;
build)
################################################### Save PKGBUILD from AUR and build it
echo -e "\033[1;36m===>\033[0m Rebuild package: \033[1;31m$2\033[0m"
echo -e "\033[1;31m===> WARNING:\033[0m \033[1;33mPKGBUILD for package $2 will be saved in $PKGBUILDSPATH/$2 directory. Want to proceed [Y/N]?\033[0m"
read pkgbuildsaverequest
if [ $pkgbuildsaverequest = y -o $pkgbuildsaverequest = Y ]; then
mkdir -p $PKGBUILDSPATH/$2
cd $PKGBUILDSPATH/$2 && yaourt -G aur/$2
echo -e "\033[1;32m===> Fetching Complete.\033[0m \033[1;33mBuilding package...\033[0m"
makepkg &> ~/reporebuild\ Logs/reporebuild-$PKGNAME.log
echo -e "\033[1;36m===>\033[0m \033[1;33mRebuild complete. Moving package\033[0m \033[1;31m$2\033[0m \033[1;33mto repository dir and update repo database...\033[0m "
rm $REPOPATH/$2-*.pkg.tar.* &> /dev/null
mv $PKGBUILDSPATH/$2/$2-*.pkg.tar.* $REPOPATH &> /dev/null
cd $REPOPATH && rm $REPONAME.db.tar.gz && repo-add $REPONAME.db.tar.gz *.pkg.tar.gz *.pkg.tar.xz &> /dev/null
echo -e "\033[1;36m===>\033[0m \033[1;32mJob completed.\033[0m"
fi
if [ $pkgbuildsaverequest = n -o $pkgbuildsaverequest = N ]; then
mkdir -p /tmp/reporebuild/$2
cd /tmp/reporebuild/$2 && yaourt -G aur/$2 &> /dev/null
echo -e "\033[1;32m===> Fetching Complete.\033[0m \033[1;33mBuilding package...\033[0m"
makepkg &> ~/reporebuild\ Logs/reporebuild-$PKGNAME.log
echo -e "\033[1;36m===>\033[0m \033[1;33mRebuild complete. Moving package\033[0m \033[1;31m$2\033[0m \033[1;33mto repository dir and update repo database...\033[0m "
rm $REPOPATH/$2-*.pkg.tar.* &> /dev/null
mv $PKGBUILDSPATH/$2/$2-*.pkg.tar.* $REPOPATH &> /dev/null
cd $REPOPATH && rm $REPONAME.db.tar.gz && repo-add $REPONAME.db.tar.gz *.pkg.tar.gz *.pkg.tar.xz &> /dev/null
rm -rf /tmp/reporebuild/$2
echo -e "\033[1;36m===>\033[0m \033[1;32mJob completed.\033[0m"
exit 0
fi
;;
localbuild)
################################################### I cant make it run from function =\
echo -e "\033[1;36m===>\033[0m Rebuild package: \033[1;31m$2\033[0m"
cd $PKGBUILDSPATH/$2
makepkg $3 &> ~/reporebuild\ Logs/reporebuild-$2.log
echo -e "\033[1;36m===>\033[0m \033[1;33mRebuild complete. Moving package\033[0m \033[1;31m$2\033[0m \033[1;33mto repository dir and update repo database...\033[0m "
rm $REPOPATH/$2-*.pkg.tar.* &> /dev/null
mv $PKGBUILDSPATH/$2/$2-*.pkg.tar.* $REPOPATH &> /dev/null
cd $REPOPATH && rm $REPONAME.db.tar.gz && repo-add $REPONAME.db.tar.gz *.pkg.tar.gz *.pkg.tar.xz &> /dev/null
echo -e "\033[1;36m===>\033[0m \033[1;32mJob completed.\033[0m"
;;
*)
help
;;
esac
exit
########################################################################
General script purpose: keeping local repository up-to-date. Im using CRON for launch it. Also script can fetch pkgbuilds in local folder for later rebuild :>
Offline
Here is the scripts I use to run wine in my chroot32:
wine.sh
#!/bin/sh
#
if [ ! -e /var/run/daemons/arch32 ]; then
echo "Chroot environment not started. Starting now"
sudo /etc/rc.d/arch32 start
fi
ROOT="/media/disk/chroot32"
if [ "$WINE" ]; then
linux32 chroot $ROOT wine "$WINE" $*
else
linux32 chroot $ROOT wine $*
fi
It's kind of hackish, since when I run the command linux32 chroot $ROOT wine "$WINE" in a shell it doesn't need the quotes, but a soon as I put it in a script it stops working without them. Anyone know why this is?
Anyway. Then I have a script for each program like so, ie Spotify:
#!/bin/sh
#
export WINE="C:\\Program Files\Spotify\spotify.exe"
export WINEDEBUG=-all
~/scripts/wine.sh $*
Offline
A utility to launch various command line applications in screen sessions by their name. It either resumes a session with the running application in it or starts a new session for it. Screen has build-in functionality for that. I'm just wrapping it up:
#!/bin/bash
#
# screen-launch: Execute command in a screen session
#
[[ ${STY} ]] && echo \
Please quit or detach from current session first >&2 && exit 1
COMMAND=$(basename ${0})
XTERM="urxvt -T ${COMMAND} -e"
SCREEN=screen
[[ ${DISPLAY} && ${TERM} == linux ]] && SCREEN="${XTERM} ${SCREEN}"
exec ${SCREEN} -d -R ${COMMAND} /usr/bin/${COMMAND}
I make use of it by creating symlinks to it, placing the symlinks in some $PATH and executing them with dmenu:
canto -> utils/screen-launch
irssi -> utils/screen-launch
ncmpc -> utils/screen-launch
rtorrent -> utils/screen-launch
slrn -> utils/screen-launch
Last edited by Lars Stokholm (2010-07-14 07:22:09)
Offline
Here's another one. I use it along with flashgot to open pdf's using google docs.
Pass it a url, it encodes it and opens the link with firefox.
#!/bin/sh
#
URI=$(echo -n "$*" | perl -MURI::Escape -le 'print uri_escape <STDIN>')
firefox "http://docs.google.com/viewer?url=$URI"
Offline