tazpkg view modules/remove @ rev 898

Module 'get': fix temp dir; module 'find-depends': faster search, add debug messages
author Aleksej Bobylev <al.bobylev@gmail.com>
date Tue Dec 29 22:00:47 2015 +0200 (2015-12-29)
parents 1362693564d1
children 92509572ed28
line source
1 #!/bin/sh
2 # TazPkg - Tiny autonomous zone packages manager, hg.slitaz.org/tazpkg
3 # remove - TazPkg module
4 # Remove packages
7 # Connect function libraries
8 . /lib/libtaz.sh
10 # Get TazPkg working environment
11 . @@MODULES@@/getenv
16 # Log activity
18 log_pkg() {
19 [ -w "$LOG" ] &&
20 echo "$(date +'%F %T') - $1 - $PACKAGE ($VERSION$EXTRAVERSION)" >> "$LOG"
21 }
24 # Interactive mode
26 im() { tty -s; }
29 # Block of receipt function callers
30 # Why? "Bad" receipt sourcing can redefine some vital TazPkg variables.
31 # Few receipts function should be patched now.
33 # Input: $1 = path to the receipt to be processed
35 call_pre_remove() {
36 local tmp
37 if grep -q '^pre_remove()' "$1"; then
38 action 'Execute pre-remove commands...'
39 tmp="$(mktemp)"
40 cp "$1" "$tmp"
41 sed -i 's|$1/*$INSTALLED|$INSTALLED|g' "$tmp"
42 ( . "$tmp"; pre_remove "$root" )
43 status
44 rm "$tmp"
45 fi
46 }
48 call_post_remove() {
49 local tmp
50 if grep -q '^post_remove()' "$1"; then
51 action 'Execute post-remove commands...'
52 tmp="$(mktemp)"
53 cp "$1" "$tmp"
54 sed -i 's|$1/*$INSTALLED|$INSTALLED|g' "$tmp"
55 ( . "$tmp"; post_remove "$root" )
56 status
57 rm "$tmp"
58 fi
59 }
62 # return possible name for a virtual package name
64 virtual_pkg() {
65 # input: $1 virtual package name
66 # $2 repository db directory
67 # output: display possible package name
69 debug "\nvirtual_pkg('$1', '$2')"
70 local i
71 unset IFS
72 for i in $(grep -hs "^$1=" "$2/packages.equiv" | sed "s/^$1=//"); do
73 if echo $i | fgrep -q : ; then
74 # format 'alternative:newname'
75 # if alternative is installed then substitute newname
76 if [ -f $INSTALLED/${i%:*}/receipt ]; then
77 # substitute package dependency
78 echo ${i#*:}
79 return
80 fi
81 elif ! grep -q "^$1 " "$2/packages.info" || [ -f "$INSTALLED/$i/receipt" ]; then
82 # unconditional substitution
83 echo $i
84 return
85 fi
86 done
87 # the real package name
88 echo $1
89 }
94 for rep in $PRIORITY; do
95 [ ! -f "$rep/packages.info" ] && continue
96 PACKAGE="$(virtual_pkg "$1" "$rep")"
97 [ "$PACKAGE" != "$1" ] && break
98 done
100 if [ ! -f "$INSTALLED/$PACKAGE/receipt" ]; then
101 newline; _ 'Package "%s" is not installed.' "$PACKAGE"
102 exit 1
103 fi
105 . "$INSTALLED/$PACKAGE/receipt"
107 # Info #1: dependent packages (to be processed later)
108 ALTERED="$(awk -F$'\t' -vp=" $PACKAGE " 'index(" " $8 " ", p) { printf " %s\n", $1 }' "$PKGS_DB/installed.info")"
110 if [ -n "$ALTERED" ]; then
111 _ 'The following packages depend on package "%s":' "$PACKAGE"
112 echo "$ALTERED"
113 fi
115 # Info #2: changed packages (to be processed later)
116 REFRESH=$(cd "$INSTALLED"; grep -sl "^$PACKAGE$" */modifiers)
118 if [ -n "$REFRESH" ]; then
119 _ 'The following packages have been modified by package "%s":' "$PACKAGE"
120 for i in $REFRESH; do
121 echo " ${i%/modifiers}"
122 done
123 fi
125 # Confirmation
126 if im && [ -z "$auto" ]; then
127 confirm "$(_ 'Remove package "%s" (%s)? (y/N)' "$PACKAGE" "$VERSION$EXTRAVERSION")"
128 if [ "$?" -ne 0 ]; then
129 newline; _ 'Uninstallation of package "%s" cancelled.' "$PACKAGE"
130 exit 0
131 fi
132 fi
133 # We are here: non-interactive mode, or --auto, or answer 'y'
135 # Removing package
136 title 'Removing package "%s"' "$PACKAGE"
138 # [1/5] Pre-remove commands
139 call_pre_remove "$INSTALLED/$PACKAGE/receipt"
142 # [2/5] Removing files
143 action 'Removing all files installed...'
145 # NOTE: package 'faenza-icon-theme' install time: 12s; removing time ~ 11min on my system o_O
146 # After optimization: 3s! (Long) for-loops are (big) evil ;)
148 # NOTE: many packages contains filenames with spaces:
149 # lzcat /var/lib/tazpkg/files.list.lzma | awk -F" " '{if(NF>2)print $1}' | sed 's|:$||' | uniq
150 # Redefine IFS to only-new-line field separator:
151 IFS=$'\n'
153 files2remove="$(mktemp)"
155 debug '\nDetermine which files to remove...'
156 if [ -f "$INSTALLED/$PACKAGE/modifiers" ]; then
157 debug ' (modifiers detected)'
159 mods="$(mktemp)"
160 for mod in $(cat "$INSTALLED/$PACKAGE/modifiers"); do
161 cat "$INSTALLED/$mod/files.list" >> "$mods" 2>/dev/null
162 done
164 awk -vroot="$root" -vfl="$INSTALLED/$PACKAGE/files.list" '
165 {
166 if (FILENAME == fl)
167 f[$0] = 1;
168 else
169 f[$0] = "";
170 }
171 END {
172 for (i in f) {
173 if (f[i] == 1) printf "%s%s\n", root, i;
174 }
175 }' "$INSTALLED/$PACKAGE/files.list" "$mods" > "$files2remove"
176 rm "$mods"
177 else
178 debug ' (modifiers not detected)'
180 awk -vroot="$root" '{ printf "%s%s\n", root, $0; }' \
181 "$INSTALLED/$PACKAGE/files.list" > "$files2remove"
182 fi
184 debug 'Removing files...'
185 xargs rm -f < "$files2remove"
187 debug 'Removing folders...'
188 awk '
189 BEGIN {
190 FS = "/"; OFS = "/";
191 }
192 {
193 # removing filename beyond the last "/"
194 $NF = "";
195 if (! a[$0]) {
196 a[$0] = 1; print;
197 }
198 }' "$files2remove" | xargs rmdir -p 2>/dev/null
200 rm "$files2remove"
201 unset IFS
203 status
205 # [3/5] Post-remove commands
206 call_post_remove "$INSTALLED/$PACKAGE/receipt"
208 # [4/5] Update system databases
209 local fl="$INSTALLED/$PACKAGE/files.list" upd=0 udesk umime uicon uschm ukrnl
211 fgrep /usr/share/applications/ "$fl" | fgrep -q .desktop && udesk='yes'
212 fgrep -q /usr/share/mime "$fl" && umime='yes'
213 fgrep -q /usr/share/icon/hicolor "$fl" && uicon='yes'
214 fgrep -q /usr/share/glib-2.0/schemas "$fl" && uschm='yes'
215 fgrep /usr/lib/gdk-pixbuf "$fl" | fgrep -q .so && upixb='yes'
216 fgrep -q /lib/modules "$fl" && ukrnl='yes'
218 if [ -n "$udesk$umime$uicon$uschm$upixb$ukrnl" ]; then
219 action 'Update system databases...'
220 upd=1
221 fi
223 # package 'desktop-file-utils'
224 [ -n "$udesk" ] && chroot "$root/" /usr/bin/update-desktop-database /usr/share/applications 2>/dev/null
225 # package 'shared-mime-info'
226 [ -n "$umime" ] && chroot "$root/" /usr/bin/update-mime-database /usr/share/mime
227 # packages 'gtk+', 'gtk+3'
228 [ -n "$uicon" ] && chroot "$root/" /usr/bin/gtk-update-icon-cache /usr/share/icons/hicolor
229 # package 'glib'
230 # hide messages like next because they are unresolved (we may to patch glib to hide them, almost the same)
231 # warning: Schema '*' has path '*'. Paths starting with '/apps/', '/desktop/' or '/system/' are deprecated.
232 [ -n "$uschm" ] && chroot "$root/" /usr/bin/glib-compile-schemas /usr/share/glib-2.0/schemas 2>&1 | fgrep -v '/apps/'
233 # package 'gdk-pixbuf'
234 [ -n "$upixb" ] && chroot "$root/" /usr/bin/gdk-pixbuf-query-loaders --update-cache
235 # packages 'busybox', 'kmod', 'depmod'
236 [ -n "$ukrnl" ] && grep '/lib/modules' "$fl" | cut -d'/' -f4 | uniq | xargs chroot "$root/" /sbin/depmod -a
238 [ "$upd" -eq 1 ] && status
241 # [5/5] Remove package receipt and remove it from databases
242 action 'Removing package receipt...'
243 rm -rf "$INSTALLED/$PACKAGE"
244 sed -i "/ $PACKAGE-$VERSION$EXTRAVERSION.tazpkg$/d" "$PKGS_DB/installed.$SUM"
245 sed -i "/^$PACKAGE /d" "$PKGS_DB/installed.info"
246 status
248 footer "$(_ 'Package "%s" (%s) removed.' "$PACKAGE" "$VERSION$EXTRAVERSION")"
250 # Log this activity
251 log_pkg Removed
253 # Stop if non-interactive mode and no --auto option
254 if ! im && [ -z "$auto" ]; then exit 0; fi
256 # Process dependent packages
257 if [ -n "$ALTERED" ]; then
258 if [ -n "$auto" ]; then
259 answer=0
260 else
261 confirm "$(_ 'Remove packages depending on package "%s"? (y/N)' "$PACKAGE")"
262 answer=$?
263 fi
264 if [ "$answer" -eq 0 ]; then
265 for i in $ALTERED; do
266 if [ -d "$INSTALLED/$i" ]; then
267 tazpkg remove $i
268 fi
269 done
270 fi
271 fi
273 # Process changed packages
274 if [ -n "$REFRESH" ]; then
275 if [ -n "$auto" ]; then
276 answer=0
277 else
278 confirm "$(_ 'Reinstall packages modified by package "%s"? (y/N)' "$PACKAGE")"
279 answer=$?
280 fi
281 if [ "$answer" -eq 0 ]; then
282 for i in $REFRESH; do
283 if [ "$(wc -l < "$INSTALLED/$i")" -gt 1 ]; then
284 _ 'Package "%s" was modified by "%s" and other packages. It will not be reinstalled.' \
285 "${i%/modifiers}" "$PACKAGE"
286 _ 'Check "%s" for reinstallation.' "$INSTALLED/$i"
288 continue
289 fi
290 rm -r "$INSTALLED/$i"
291 tazpkg get-install ${i%/modifiers} --forced
292 done
293 fi
294 fi