Tip_Make_common_emerges_easier_with_an_update_script
Contents |
Usages
Every once in a while I run into an emerge that I tend to run often. These emerges are simple, usually they involve simply updating a few svn, bzr, or git packages. To make this easier, and also ease rebuilding an entire system, I wrote this script.
Script: rebuild
#!/bin/bash
packagedir="/home/mozes/scripts/package_lists"
total=-1
builtcorrect=0
triedtobuild=0
function count(){
if [ "$total" -lt "1" ]
then
for p in $list; do
total=$(( $total + 1 ))
done
if [ "$total" -ge "30" ]
then
NEEDLESS=yes
else
CUSTOM=custom
NEEDLESS=no
fi
else
tbroken=0
for p in $broken; do
tbroken=$(( $tbroken + 1 ))
done
if [ "$tbroken" -ge "30" ]
then
NEEDLESS=yes
else
NEEDLESS=no
fi
fi
}
function list_updates(){
if [ -n "$plist" ]
then
prettylist="\n${plist}"
else
for x in $list; do
prettylist="${prettylist}\n ${GOOD}\0452${NORMAL} ${x}"
done
fi
if [ "$NEEDLESS" == "yes" ]
then
echo -e "This is the list of packages to emerge:${prettylist}" | less
else
echo -e "This is the list of packages to emerge:${prettylist}"
fi
}
function build(){
for x in $list; do
buildcount=0
echo -e " ${GOOD}\0452${NORMAL} (${currentpackage} of ${total}) Building ${x}"
if [ "$triedtobuild" != "$builtcorrect" ]
then
echo -e " ${BAD}\0452${NORMAL} Only $builtcorrect out of the $triedtobuild packages have been built correctly"
fi
triedtobuild=$(( $triedtobuild + 1 ))
PORTAGE_ELOG_SYSTEM="save $CUSTOM" FEATURES="${features}" emerge -v1 ${x} && buildcount=1 && builtcorrect=$(( $builtcorrect + 1 ))
if [ "$buildcount" == "0" ]
then
echo -e " ${GOOD}\0452${NORMAL} (${currentpackage} of ${total}) Trying to build ${x} again"
PORTAGE_ELOG_SYSTEM="save $CUSTOM" FEATURES="${features}" emerge -v1 ${x} && buildcount=1 && builtcorrect=$(( $builtcorrect + 1 ))
fi
if [ "$buildcount" == "0" ]
then
echo "Couldn't successfully build ${x}"
broken="${broken}\n ${GOOD}\0452${NORMAL} ${x}"
fi
currentpackage=$(( $currentpackage + 1 ))
done
}
function question(){
echo "Do you want to continue with the emerge? (Y/n)"
read x
if [ "${x}" == "n" ]
then
exit 0
elif [ "${x}" == "" ] || [ "${x}" == "Y" ] || [ "${x}" == "y" ] || [ "${x}" == "yes" ] || [ "${x}" == "YES" ] || [ "${x}" == "Yes" ]
# This does multiple matchings, i want it to continue by default if nothing is entered
then
continue_script
else
echo "Sorry, response '${x}' not understood."
question
fi
}
function continue_script(){
build
if [ -e ${packagedir}/$brokenname ]
then
rm ${packagedir}/$brokenname
fi
if [ -n "${broken}" ]
then
count
echo -e "${broken}" | sed -e 's/\*//g' -e 's/\ //g' -e 's/^............//g' | grep '\.' > ${packagedir}/${brokenname}
if [ "$NEEDLESS" == "yes" ]
then
echo -e " ${BAD}\0452${NORMAL} Only $builtcorrect out of the $triedtobuild packages have been built correctly\nThese are the packages that are broken:${broken}\nThese can be retried with '`basename $0` $brokenname'" | less
else
echo -e " ${BAD}\0452${NORMAL} Only $builtcorrect out of the $triedtobuild packages have been built correctly\nThese are the packages that are broken:${broken}\nThese can be retried with '`basename $0` $brokenname'"
fi
else
echo -e "All packages built correctly."
fi
}
currentpackage=1
total=0
GOOD=$'\e[32;01m'
BAD=$'\e[31;01m'
NORMAL=$'\e[0m'
case "$1" in
world)
echo "Getting a list of packages to be upgraded"
plist=`emerge -pvuDN world | grep ebuild`
list=`echo "${plist}" | sed -e 's/^................/=/g' | awk '{ print $1 }'`
listupdates=yes
brokenname=broken.world
;;
system)
echo "Getting a list of packages to be upgraded"
plist=`emerge -pvuDN system | grep ebuild`
list=`echo "${plist}" | sed -e 's/^................/=/g' | awk '{ print $1 }'`
listupdates=yes
brokenname=broken.system
;;
*)
recheck=yes
esac
if [ "$recheck" == "yes" ]
then
case "$2" in
world)
echo "Getting a list of packages to rebuild"
plist=`emerge -pveuDN world | grep ebuild | grep -v open-office`
list=`echo "${plist}" | sed -e 's/^................/=/g' | awk '{ print $1 }'`
listupdates=yes
brokenname=broken.e.world
;;
system)
echo "Getting a list of packages to rebuild"
plist=`emerge -pveuDN system | grep ebuild`
list=`echo "${plist}" | sed -e 's/^................/=/g' | awk '{ print $1 }'`
listupdates=yes
brokenname=broken.e.system
;;
*)
if [ -n "$1" ] && [ -e "${packagedir}/$1" ]
then
if [ -n "`cat ${packagedir}/$1 | sed -n '1p' | grep 'FEATURES'`" ]
then
features=`cat ${packagedir}/$1 | sed -n '1p' | awk -F "\"" '{ print $2 }'`
lc=`cat ${packagedir}/$1 | wc -l`
list=`cat ${packagedir}/$1 | sed -n 2,${lc}p `
listupdates=yes
else
list=`cat ${packagedir}/$1`
listupdates=yes
fi
if [ "`echo "$1" | head -c 6`" == "broken" ]
then
brokenname=$1
else
brokenname=broken.$1
fi
else
for x in `ls -1 ${packagedir}`
do
packagelist="${packagelist}|${x}"
done
echo "`basename $0` {e} {world|system${packagelist}}"
echo "e stands for 'emptytree'"
fi
esac
fi
if [ -n "${list}" ]
then
count
if [ "$listupdates" == "yes" ]
then
list_updates
fi
question
else
echo "Nothing to do... exiting"
fi
How to set up
In order to use this script, you simply need to modify the variable "packagedir" (the second line of the script) Change it to point at an empty directory, we will put something in it later (if you want it to take care of -9999 packages) In its current state, it will be more than happy to function. You can run
- ./rebuild world
and it will output a list of <world> updates, if the list is longer 30 packages, it will output it in `less` so that you can view all of them. As the script continues, it will ask you if you want to perform the action (update). If you answer yes it will update those packages, 1 emerge at a time. If it fails on one it will retry it. If it fails a second time it simply moves on.
When the script has finished the emerge, it will tell you which packages it failed on, and outputs those failed packages to $packagedir/broken.$1 (or if it is an empty tree merge to $packagedir/broken.e.$1)
As soon as a file is within the $packagedir folder, it can be specified as an argument to rebuild
Package File Syntax
This syntax is very simple, as anything you can pass directly to emerge will get sent on directly to emerge
- Packages should be 1 per line
- You can specify versions with =${packagename}-$version
- You CAN specify special FEATURES for a package group.
- Must be done on the first line, and must be done with FEATURES="$whatever"
Sample Package File
compiz-fusion
x11-wm/compiz x11-libs/compiz-bcop x11-plugins/compiz-fusion-plugins-main x11-plugins/compiz-fusion-plugins-extra x11-plugins/compiz-fusion-plugins-unsupported x11-plugins/compiz-fusion-plugins-wallpaper x11-plugins/compiz-plugins-screensaver x11-wm/emerald x11-themes/emerald-themes x11-libs/libcompizconfig dev-python/compizconfig-python x11-apps/ccsm x11-apps/fusion-icon
Bugs
Ignores issues with compatibility
It doesn't care if a package is Fetch restricted, or if it Blocks another package. It will still try to emerge it.
Created by NickStallman.net, Luxury Homes Australia
Real estate agents should be using interactive floor plans and list their apartments, townhouses and units.
