View difference between Paste ID: kDXqafxf and
SHOW: | | - or go back to the newest paste.
1-
1+
#!/bin/bash
2
#
3
#  apt-sources-update
4
#
5
#  by travisn000 <travisn000 at gmail.com>
6
#
7
#  This program is free software; you can redistribute it and/or modify
8
#  it under the terms of the GNU General Public License as published by
9
#  the Free Software Foundation; either version 2 of the License, or
10
#  (at your option) any later version.
11
#
12
#  This program is distributed in the hope that it will be useful,
13
#  but WITHOUT ANY WARRANTY; without even the implied warranty of
14
#  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
#  GNU General Public License for more details.
16
#
17
#  You should have received a copy of the GNU General Public License
18
#  along with this program; if not, write to the Free Software
19
#  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20
#
21
 
22
myname=$(basename "$0"); 
23
export TEXTDOMAIN=apt-sources-update
24
export TEXTDOMAINDIR="/usr/share/locale"
25
26
27
# verbose output for debugging
28
setverbose () { set -xv; }
29
30
showhelp () {
31
	echo -e $"
32
$myname is a utility that will download the latest PCLinuxOS apt
33
sources.list from the main ibiblio server, verify that they
34
have been recently synced to the ibiblio server, and test 
35
all updated repositories for download speed.
36
37
Once testing is completed the user will be given a speed 
38
rated list of repositories from which they can select a 
39
default repository to use for future software needs.
40
41
It is meant to be run as a regular user, and will prompt 
42
for root permisions before making any changes to the apt 
43
sources.list file.  This script also requires that zenity 
44
is installed so that GUI dialogs are properly displayed.
45
46
Available console options to override default behavior include:.
47
  -a, -age=<time in days>           Allowed repo age before FAIL
48
  -n, -number=<number of repos>     Max number of official repos to keep (fastest)
49
  -s, -sources=<url of file>        Location of official online sources.list
50
  -t, -timeout=<time in seconds>    Time to start file download before FAIL
51
  -v, -verbose                      Verbose output for debugging
52
  -w, -write                        Prompt to write new sources.list to /etc/apt (root password)
53
  -u, -usage                        Display sample command line usage, help
54
  -h, -help                         Display this help message
55
"
56
57
	[ -n "$1" ] && exit $1      # only exit if exit status is passed to function
58
}
59
60
usage () {
61
	showhelp
62
	echo -e $"
63
Examples:
64
        $myname -timeout=3 -age=2
65
        $myname -s http://myserver.org/sources.list
66
        $myname  -t 2 -a 2 -n 8 -w
67
68
"
69
	exit
70
}
71
72
73
# Set script title
74
VERSION=0.3.1
75
TITLE=$"Repo Speed Test $VERSION"
76
WINDOW_ICON="/usr/share/pixmaps/synaptic.png"
77
78
TMP_DIR="$HOME/repo-speed-test"
79
TESTFILE="srclist.main.bz2"
80
REPO_BASE_YEAR="2010"
81
TESTFILEDIR="pclinuxos/${REPO_BASE_YEAR}/base/"
82
UPDATED_SOURCESLIST="http://distro.ibiblio.org/pclinuxos/repo${REPO_BASE_YEAR}/sources.list"
83
MEGA_GAMES_REPO="http://ftp.nl.freebsd.org/pub/os/Linux/distr/pclinuxos/megagames/apt/ pclinuxos/${REPO_BASE_YEAR} megagames"
84
TIMEOUT="3"
85
86
87
while getopts a:n:t:s:wvuh op
88
do	case "$op" in
89
	a) REPO_AGE=$(($OPTARG*1));;
90
	n) REPOS_MAX=$(($OPTARG*1));;
91
	t) TIMEOUT=$(($OPTARG*1));;
92
	s) UPDATED_SOURCESLIST="$OPTARG";;
93
	w) WRITE_APTSL=0;;
94
	v) setverbose;;
95
	u) usage;;
96
	h|?) showhelp 0;;
97
	esac
98
done
99
100
shift $(( $OPTIND-1 ))
101
[ -n "$1" ] && echo -e $"Extra parameter(s) \"$@\" ignored...\n"
102
103
if ! cd ~; then
104
	echo $"Cannot change directory to your home directory... quitting."
105
	exit 1
106
fi
107
108
for c in $(echo "/ | # ! = _ ~ :")
109
do	if ! [[ "$@" =~ "$c" ]]; then
110
		s=$c ; break
111
	fi
112
done
113
if [ -z "$s" ]; then
114
	echo $"Try again without using all of \"/|#!=_~:\" in your arguments... quitting."
115
	exit 1
116
fi
117
118
119
120
121
# Check if kdialog exists, if not, use gdialog for some dialogs.
122
# Note: Most dialogs are pure zenity, but zenity does not have the yes/no function :(
123
if [ -f /usr/bin/kdialog ]; then
124
    DIALOG=kdialog
125
else
126
    DIALOG=gdialog
127
fi
128
129
130
if [ ! -e /usr/bin/zenity ]; then
131
  $DIALOG --yesno $"Zenity is required to run this script.\n\nWould you like to install it now?"
132
  if [ "$?" == "0" ]; then
133
   ktsuss synaptic &
134
    exit
135
  elif [ "$?" == "1" ]; then
136
    kdialog --sorry $"Exiting now"
137
    exit
138
  fi
139
fi
140
141
142
# check that package managers are closed
143
for idx in synaptic smart ksmarttray kpackage apt-get
144
do 
145
 if [ -n "`pidof $idx`" ]; then
146
  zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Please close your package manager '$idx' and then click on the link again.\n\nExiting..."
147
#  echo -e "Please close your ${idx} package manager and then try again.\n\nExiting...\n\n"
148
  sleep 2
149
  exit 1
150
 fi
151
done
152
153
154
# Check if user is logged in as root  ..or not ???
155
if [ "$UID" == "0" ]; then
156
    zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Please <b>DO NOT</b> run this script as root!"
157
    showhelp
158
    echo -e $"\nPlease use this command as normal user, not root."
159
    exit 1
160
fi
161
162
163
164
165
166
167
#############################################
168
##          Execution starts here          ##
169
#############################################
170
171
172
aptsl="/etc/apt/sources.list"
173
newaptsl="$TMP_DIR/sources.list.new"
174
atemp="$TMP_DIR/atemp.$$"
175
176
177
178
editsl_file () {
179
	exec 9<${aptsl} #$aptsl
180
181
	echo -e $"\n\nLocal repo line(s) found:\n"
182
	while read -u 9 r
183
#	do	if [[ $r =~ $rpm_file ]]; then
184
	do	if [[ $r =~ $rpm_local ]]; then
185
			echo -e "$r\n"
186
			zenity --window-icon="$WINDOW_ICON" --question --text=$"The following local repository exists:\n$r\n\nWould you like to keep it?"
187
			if [ "$?" = "0" ]; then
188
				if ( echo $r | grep ^[[:space:]]*# ); then
189
				    echo -e "${r}\n">>$newaptsl
190
				else
191
				    echo -e "# ${r}\n">>$newaptsl
192
				fi
193
				echo -e $"\n..successfully recovered; you may reactivate using Synaptic\n"
194
			fi
195
		fi
196
	done
197
	exec 9<&-
198
}	###### end editsl_file ######
199
200
201
editsl_pass () {
202
	exec 9<${aptsl}
203
204
	echo -e $"\n\nPASS repo line found:\n"
205
	while read -u 9 r
206
	do	if [[ $r =~ $rpm_pass ]]; then
207
			echo -e "$r\n"
208
			zenity --window-icon="$WINDOW_ICON" --question --text=$"The following pass repository exists:\n$r\n\nWould you like to keep it?"
209
			if [ "$?" = "0" ]; then
210
				if ( echo $r | grep ^[[:space:]]*"#" ); then
211
				    echo -e "${r}\n">>$newaptsl
212
				else
213
				    echo -e "# ${r}\n">>$newaptsl
214
				fi
215
				echo -e $"\n..successfully recovered; you may reactivate using Synaptic\n"
216
			fi
217
218
		fi
219
	done
220
	exec 9<&-
221
}	###### end editsl_pass ######
222
223
224
225
makesl () {
226
head=$"# Package repository URL's
227
228
# Signed repositories have a [<key>] where <key> is the name of the key
229
# as it appears in vendors.list. If you remove it, no digital signature check
230
# will be made.
231
"
232
233
234
kde_section="kde4"
235
236
237
#if [ -d /usr/share/kde4 ]; then kde_section="kde4" ; fi
238
#if [ `rpm -qa kdebase4|wc -l` -gt 0 ];then kde_section="kde4" ; fi
239
240
dsx="pclinuxos/${REPO_BASE_YEAR} main updates nonfree games ${kde_section}"
241
242
243
244
# echo -e "\nIf your network connection is not active, please"
245
# read -p "activate it now, then press Enter to continue. "
246
zenity --window-icon="$WINDOW_ICON" --info --title="$TITLE" --text=$"If your network connection is not active, please\nactivate it now, then press OK to continue. "
247
if [ "$?" != "0" ]; then
248
  zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Operation Canceled! \n\nExiting $myname... "
249
  exit 1
250
fi
251
252
253
echo -e $"\nRetrieving updated apt sources.list...\n"
254
255
rm -fR $TMP_DIR &>/dev/null
256
mkdir -p $TMP_DIR
257
wget --directory-prefix=$TMP_DIR $UPDATED_SOURCESLIST 2>&1 \
258
| sed -u 's/.*\ \([0-9]\+%\)\ \+\([0-9.]\+\ [KMB\/s]\+\)$/\1\n# Downloading \2/' \
259
| zenity --window-icon="$WINDOW_ICON" --progress --auto-close --title="$TITLE" --text=$"Downloading updated apt sources.list file..."
260
#| zenity --window-icon="$WINDOW_ICON" --progress --pulsate --auto-close --title="$TITLE" --text=$"Downloading updated apt sources.list file..."
261
262
263
264
if [ -f $TMP_DIR/sources.list ]; then
265
266
  zenity --window-icon="$WINDOW_ICON" --info --title="$TITLE" --text=$"Connection successful.. \nRetrieved new sources.list file. "
267
268
# repo list with NO line breaks
269
# 	REPOSLIST=""
270
# 	for url in `grep rpm.*p:// $TMP_DIR/sources.list | sed -e 's@^[# \t]*rpm @@' | cut -d" " -f1`; do REPOSLIST="$REPOSLIST $url "; done;
271
272
# repo list with line breaks
273
  REPOSLIST=( `grep rpm.*:/ $TMP_DIR/sources.list | sed -e 's@^[# \t]*rpm @@' | cut -d" " -f1` )
274
#  echo ${REPOSLIST[@]}
275
276
else
277
  zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Unable to retrieve new sources.list file. \n\n Verify internet connection and try again. "
278
  exit 1
279
fi
280
281
282
ans=""
283
# while ! [[ $ans == [0-9] || $ans == [0-9][0-9] ]]; do
284
#     read -p"Enter acceptable repo sync age (0-99 days): " ans
285
# done
286
[[ "$REPO_AGE" =~ ^[0-9]+$ ]] && ans=$REPO_AGE || ans=$(zenity --window-icon="$WINDOW_ICON" --scale --title="$TITLE" --text=$"Select acceptable repo sync age in days.. " --min-value=1 --max-value=10 --value=5 --step 1)
287
if [ "$?" != "0" ]; then
288
  zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Operation Canceled! \n\nExiting $myname... "
289
  exit 1
290
fi
291
292
293
DATE_OLD=$(date --date "now - $ans days" +%Y%m%d) #; echo $DATE_OLD
294
GOODLIST=""
295
BADLIST=""
296
REPOCOUNT=${#REPOSLIST[@]}
297
298
299
300
echo -e $"\nTesting repo sync age and download speeds..\n"
301
rm -f $TMP_DIR/repo_goodlist.txt
302
rm -f $TMP_DIR/repo_badlist.txt
303
cd $TMP_DIR
304
#for REPO in ${REPOSLIST[@]} ; do
305
for (( i=0; i<${REPOCOUNT}; i++ )); do
306
    the_progress=$((100*${i}/${REPOCOUNT}))
307
    URL="${REPOSLIST[$i]}${TESTFILEDIR}${TESTFILE}"
308
    GETSPEED=$(curl --max-time ${TIMEOUT} --time-cond ${DATE_OLD} --silent --write-out %{speed_download} -O ${URL})
309
#    GETTIME=$(curl --max-time ${TIMEOUT} --time-cond ${DATE_OLD} --silent --write-out %{total_time} -O ${URL})
310
    GETSPEED=$( echo $GETSPEED| cut -d"." -f1 ) #make integer
311
312
#    if [ "$GETTIME" ==  "0.000" ]; then
313
    if [ "$GETSPEED" ==  "0" ]; then
314
	echo $"# REPO:  ${REPOSLIST[$i]}\nSTATUS:  FAILED"
315
	echo "${REPOSLIST[$i]}" >> $TMP_DIR/repo_badlist.txt
316
	echo "$the_progress"
317
    else
318
	echo $"# REPO:  ${REPOSLIST[$i]}\nSPEED: $GETSPEED bytes/second"
319
	echo "$GETSPEED ${REPOSLIST[$i]}" >> $TMP_DIR/repo_goodlist.txt
320
	echo "$the_progress"
321
    fi
322
done | zenity --window-icon="$WINDOW_ICON" --progress --auto-close --title="$TITLE" --text=$"Starting repo speed test..." --width=400
323
#  --pulsate
324
325
rm -f $TMP_DIR/$TESTFILE
326
327
REPO_SELECTION=$(sort -nr $TMP_DIR/repo_goodlist.txt | 
328
awk -F" " '{print $2,"\n",$1}' | 
329
zenity --window-icon="$WINDOW_ICON" --list --title="$TITLE" \
330
  --column=$" Repo URL" --column $"bytes/second" \
331
  --text=$"Select your preferred repo from the list below.\n\n(Ordered fastest to slowest - please do <b>NOT</b> use ibiblio.org)" --width=750 )
332
333
if [ "$REPO_SELECTION" == "" ]; then   zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Operation Canceled! \n\nExiting $myname... "; exit; fi
334
335
336
337
finalrepolist=( `cat $TMP_DIR/repo_goodlist.txt | sort -nr | cut -d" " -f2` )
338
339
340
if  [ -f $TMP_DIR/repo_badlist.txt ] ; then
341
    echo
342
    echo -e $"\nThe following mirrors timed out, are out of date, or are not valid :\n"
343
    cat $TMP_DIR/repo_badlist.txt;
344
    sleep 2
345
fi 
346
347
348
echo -e $"\nPCLinuxOS official repositories: \n(ordered by speed-test results, fastest to slowest)"
349
echo -e $"(average download speed in bytes/seconds for ~500 KB file) \n\n"
350
sort -nr $TMP_DIR/repo_goodlist.txt | awk -F" " '{print $1,"  \t",$2}'
351
352
353
if  [ "$finalrepolist" != "" ]; then
354
355
# find item in array
356
bash__is_in_array () {
357
  haystack=( "$@" )
358
  haystack_size=( "${#haystack[@]}" )
359
  needle=${haystack[$((${haystack_size}-1))]}
360
  for ((i=0;i<$(($haystack_size-1));i++)); do
361
    h=${haystack[${i}]};
362
    [ $h = $needle ] && return $i
363
  done
364
}
365
366
bash__is_in_array "${finalrepolist[@]}" $REPO_SELECTION
367
n=$?
368
369
370
    active_repo="${finalrepolist[$n]}"
371
    echo -e $"\n\n  Activating $active_repo"
372
    echo -e $"  Creating $aptsl\n"
373
374
375
[[ "$REPOS_MAX" =~ ^[0-9]+$ ]] && list_length=$REPOS_MAX || list_length=$(zenity --window-icon="$WINDOW_ICON" --scale --title="$TITLE" --text=$"Select number of online repositories to keep: " --min-value=1 --max-value=${#finalrepolist[@]} --value=5 --step 1)
376
if [ "$?" != "0" ]; then
377
  zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Operation Canceled! \n\nExiting $myname... "
378
  exit 1
379
fi
380
381
    # write sources.list.new header
382
    echo "$head" > $newaptsl
383
384
    # add user selected online repo first (top of the repo list)
385
    echo -e "rpm ${finalrepolist[$n]} $dsx\n" >> $newaptsl
386
    
387
    # ask for enable megagames
388
    zenity --window-icon="$WINDOW_ICON" --question --text=$"If you want to enable the repo for megames?"  --title="$TITLE" 
389
	if [ "$?" = "0" ]; then
390
	# add megagames repo next
391
    echo -e "rpm ${MEGA_GAMES_REPO}\n" >> $newaptsl
392
    else
393
    echo -e "# rpm ${MEGA_GAMES_REPO}\n" >> $newaptsl
394
    fi
395
396
    rs="# rpm"; 
397
398
    # write sources.list.new local / pass repositories
399
    rpm_local="rpm.*file:/|rpm.*tp://localhost|rpm.*tp://192.168.|rpm.*tp://10.|rpm.*tp://172.16."
400
    egrep -q "$rpm_local" ${aptsl} && editsl_file
401
402
    rpm_pass="@"
403
#    rpm_pass="rpm.*@"
404
    egrep -q "$rpm_pass" ${aptsl} && editsl_pass
405
406
    # write sources.list.new online repositories
407
    for (( r=0; r<${list_length}; r++ )); do
408
    if [ "$r" != "$n" ]; then # do not add user selected online repo.. it was already added above
409
	    echo -e "$rs ${finalrepolist[$r]} $dsx\n" >> $newaptsl
410
    fi
411
    done
412
else
413
    echo -e $"\nUnable to contact any PCLinuxOS software repository \(REQUIRED\). \n\nExiting..  please verify your network connection and try again.\n\n"
414
    zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"\nUnable to contact any PCLinuxOS software repository \(REQUIRED\). \n\nExiting..  please verify your network connection and try again.\n"
415
    sleep 3
416
    exit 1
417
fi
418
419
}	###### end makesl ######
420
421
422
423
424
425
426
if ! [ -f "$aptsl" ]; then
427
	echo -e $"Can\'t find ${aptsl} \n\nExiting... "
428
	zenity --window-icon="$WINDOW_ICON" --error --title="$TITLE" --text=$"Can\'t find ${aptsl} \n\nExiting... "
429
	exit 1
430
fi
431
432
root_script=backup-n-overwrite-sources.sh
433
434
makesl && cat > $TMP_DIR/$root_script <<EOF
435
#!/bin/bash
436
# REQUIRES ROOT PRIVLIGES
437
438
if [ \$UID -ne 0 ]; then
439
	echo -e $"\nPlease use this script as root.\n"
440
	exit 1
441
fi
442
443
if [ -f "$aptsl" ]; then
444
	cp -f --backup $aptsl ${aptsl}.old #2>/dev/null
445
	aptslbk=\$?
446
else
447
	aptslbk=999
448
fi
449
450
[ "\$aptslbk" != "999" ] && force=1
451
[ -n "\$force" -a -f ${aptsl}.old ] && cp -f --backup=off $TMP_DIR/sources.list.new $aptsl 2>/dev/null
452
453
# -r => launch synaptic with repository selection dialog open
454
#( synaptic -r &>/dev/null )&
455
synaptic -r
456
457
echo -e \$(basename "\$0") complete..;
458
459
EOF
460
461
chmod 755 $TMP_DIR/$root_script
462
463
[[ "$WRITE_APTSL" == "0" ]] && zenity --window-icon="$WINDOW_ICON" --question --text=$"The repo speed test has completed and 
464
a new apt sources.list has been saved to your home directory.
465
466
Would you like to overwrite your current sources.list file? 
467
(a back up copy of the current file will be made)"
468
if [ "$?" = "0" ]; then
469
470
cd $TMP_DIR
471
mysu=`which gksu 2>/dev/null` || mysu=`which kdesu 2>/dev/null` && $mysu "./$root_script"
472
cd ~
473
zenity --window-icon="$WINDOW_ICON" --question --text=$"Would you like to remove the repo-speed-test working directory from your home folder?"
474
	if [ "$?" = "0" ]; then
475
		rm -fR $TMP_DIR &>/dev/null
476
	fi
477
fi
478
479
[[ "$WRITE_APTSL" != "0" ]] && zenity --window-icon="$WINDOW_ICON" --warning --text=$"The repo speed test has completed and a new apt sources.list \nhas been saved to your home directory.\n\nTo activate it you must copy it to the /etc/apt directory."
480
481
echo $"${myname} is now finished."
482
echo; echo;
483
484
sleep 1