tazpanel annotate lib/libtazpanel @ rev 591

undo s/nobody/root/, add "subox/sudo tazpanel" workaround instead
author Xander Ziiryanoff <psychomaniak@xakep.ru>
date Thu Apr 28 23:18:44 2016 +0200 (2016-04-28)
parents 21f625d5ebbb
children a0d7d5836aec
rev   line source
pankso@15 1 #!/bin/sh
pankso@15 2 #
pankso@15 3 # Common functions for TazPanel CGI and cmdline interface
pankso@15 4 #
al@419 5 # Copyright (C) 2011-2015 SliTaz GNU/Linux - BSD License
al@419 6 #
al@419 7
al@437 8 . /lib/libtaz.sh
pankso@15 9
al@463 10
al@463 11 # Redefine gettext functions
al@463 12
al@463 13 _() { local T="$1"; shift; printf "$(gettext "$T")" "$@"; echo; }
al@463 14 _n() { local T="$1"; shift; printf "$(gettext "$T")" "$@"; }
al@463 15
al@463 16
psychomaniak@591 17 [ $(busybox ps | grep '127.0.0.1.*guiuser=root' |grep -v grep| awk {'print $2'}) == 'root' ] && REMOTE_USER='root'
psychomaniak@591 18 GUI_USER=nobody
pascal@562 19 [ "${HTTP_HOST/:*/:}" == "127.0.0.1:" ] &&
pascal@511 20 for i in "$HTTP_COOKIE" "$QUERY_STRING" ; do
al@525 21 v="$(echo "$i" | sed '/guiuser=/!d;s/.*guiuser=\([A-Za-z0-9_]*\).*/\1/')"
al@525 22 [ "$v" ] || continue
pascal@562 23 busybox ps | sed '/d;/d;/127\.0\.0\.1:/!d' | grep -q " $v " || continue
al@525 24 GUI_USER="$v"
pascal@511 25 done
pascal@513 26 [ "$(id -un)" == "${REMOTE_USER:=$GUI_USER}" ] || exec su -s /bin/sh -c "$(realpath $0) $@" $REMOTE_USER
pascal@376 27
al@419 28
pascal@511 29 # Get parameters with GET, POST, COOKIE and FILE functions
al@419 30
mojo@310 31 . /usr/lib/slitaz/httphelper
pascal@81 32
al@419 33
pankso@109 34 # I18n
al@419 35
pankso@286 36 . /etc/locale.conf
al@525 37 export TEXTDOMAIN='tazpanel' LANG LC_ALL
pankso@40 38
al@419 39
pankso@15 40 # We need a config file first
al@419 41
pankso@15 42 get_config() {
al@419 43 CONFIG='/etc/slitaz/tazpanel.conf'
al@419 44 if [ -f "$CONFIG" ]; then
al@419 45 . $CONFIG
al@419 46 else
al@419 47 echo "No config file found: $CONFIG"
pankso@15 48 exit 1
al@419 49 fi
pankso@15 50 }
pankso@15 51
al@419 52
al@303 53 # Display < > &
al@419 54
al@303 55 htmlize() {
pascal@552 56 sed -e '/<[a-z]*>/{:a;Nba;} s|\&|\&amp;|g; s|<|\&lt;|g; s|>|\&gt;|g'
al@303 57 }
al@303 58
al@419 59
pankso@74 60 # Syntax highlighting for config file and SHell scripts
al@419 61
pankso@74 62 syntax_highlighter() {
pankso@74 63 case $1 in
pankso@74 64 conf)
al@303 65 htmlize | sed \
al@419 66 -e 's|^\([ \t]*[A-Za-z0-9_][A-Za-z0-9_]*\)\(="*.*\)|<span class="conf-var">\1</span><span class="conf-val">\2</span>|g' \
al@419 67 -e 's|^[ \t]*#.*|<span class="conf-comment">\0</span>|g' ;;
al@419 68 #-e s"#^\#\([^']*\)#<span class='conf-comment'>\0</span>#"g \
al@419 69 #-e s"#^[A-Z]\([^']*\)=#<span class='conf-var'>\0</span>#"g \
al@419 70 #-e s"#^[a-z]\([^']*\)#<span class='conf-var'>\0</span>#"g \
al@419 71 #-e s"#[\"']\([^']*\)[\"']#<span class='conf-val'>\0</span>#"g ;;
pankso@75 72 sh)
al@303 73 htmlize | sed \
al@419 74 -e 's|^\([ \t]*[A-Za-z0-9_][A-Za-z0-9_]*\)\(="*.*\)|<span class="sh-var">\1</span><span class="sh-val">\2</span>|g' \
al@419 75 -e 's|^#.*|<span class="sh-comment">\0</span>|g' ;;
al@419 76 #-e s"#^\#\([^']*\)#<span class='sh-comment'>\0</span>#"g \
al@419 77 #-e s"#\"\([^']*\)\"#<span class='sh-val'>\0</span>#"g ;;
pascal@91 78 diff)
al@303 79 htmlize | sed \
al@419 80 -e 's|^-.*|<span class="diff-rm">\0</span>|g' \
al@419 81 -e 's|^+.*|<span class="diff-add">\0</span>|g' \
al@419 82 -e 's|^@.*|<span class="diff-at">\0</span>|g' ;;
pankso@120 83 activity)
al@419 84 # realize lazy quantification
al@419 85 sed -e "s|: |ⓒ|; s|^\(.*\)ⓒ|<span class='activity-log'>\1:</span> |" ;;
al@303 86 kernel)
al@419 87 # line with "ⓒ": realize lazy quantification
al@303 88 htmlize | sed \
al@303 89 -e "s|\([^0-9]\)\(0x[0-9a-f]\+\)|\1<span class='kernel-hex'>\2</span>|g" \
al@419 90 -e "s|: |ⓒ|; s|^\(.*\)ⓒ|<span class='kernel-id'>\1:</span> |" \
al@419 91 -e "s|\(\[[^ ]\+\]\)|<span class='kernel-id2'>\0</span>|g" \
al@419 92 -e "s|Call Trace:|<span class='kernel-trace'>\0</span>|" ;;
al@363 93 lsusb)
al@363 94 htmlize | sed \
al@363 95 -e 's|^[^:]*:[ x0-9a-f^:]*$|<span class="lsusb-t">\0</span>|g' \
al@363 96 -e 's|^Bus.*$|<span class="lsusb-h">\0</span>|g' ;;
al@363 97 lspci)
al@363 98 htmlize | sed \
al@363 99 -e 's|^[0-9a-f].*$|<span class="lspci-t">\0</span>|g' \
al@363 100 -e 's|^ \([^:]*:\)| <span class="lspci-h">\1</span>|g' ;;
al@419 101 xlog)
al@419 102 htmlize | sed \
al@419 103 -e 's|^[^]]*]|<span class="xlog xlog-timestamp">\0</span>|' \
al@419 104 -e 's|(--)|<span class="xlog xlog-probed" title="probed">\0</span>|' \
al@419 105 -e 's|(\*\*)|<span class="xlog xlog-config" title="from config file">\0</span>|' \
al@419 106 -e 's|(==)|<span class="xlog xlog-default" title="default setting">\0</span>|' \
al@419 107 -e 's|(++)|<span class="xlog xlog-cmdline" title="from command line">\0</span>|' \
al@419 108 -e 's|(!!)|<span class="xlog xlog-notice" title="notice">\0</span>|' \
al@419 109 -e 's|(II)|<span class="xlog xlog-info" title="informational">\0</span>|' \
al@419 110 -e 's|(WW)|<span class="xlog xlog-warn" title="warning">\0</span>|' \
al@419 111 -e 's|(EE)|<span class="xlog xlog-error" title="error">\0</span>|' \
al@419 112 -e 's|(NI)|<span class="xlog xlog-ni" title="not implemented">\0</span>|' \
al@419 113 -e 's|(??)|<span class="xlog xlog-unknown" title="unknown">\0</span>|' \
al@419 114 ;;
pankso@74 115 esac
pankso@53 116 }
pankso@53 117
al@419 118
pascal@99 119 # Remove status and ESC char from tazpkg/tazlito commands output
al@419 120
pascal@99 121 filter_taztools_msgs() {
al@419 122 sed \
al@419 123 -e 's|\\[0m|</span>|g' \
al@419 124 -e 's|\\[0;39m|</span>|g' \
al@419 125 -e 's|\\[0*\([0-7]*\);\([0-7]*\)m|<span class="color\1 color\2">|g' \
pascal@412 126 -e ':a;s/^\(.\{0,69\}\)\(\\[[0-9]*G\[\)/\1 \2/;ta' \
al@419 127 -e ':b;s|^\([^\]*\)\\[\([0-9]*\)G|<span style="display:inline-block;width:\2ex">\1</span>|;tb' \
al@419 128 -e 's/\[^Gm]*.//g'
pascal@99 129 }
pascal@99 130
al@419 131
pankso@51 132 # LOG activities
al@419 133
pankso@51 134 log() {
al@419 135 date=$(date "+%F %R")
al@419 136 filter_taztools_msgs | sed "s|[^']*|$date : \0|" >> $LOG_FILE
pankso@51 137 }
pankso@51 138
al@419 139
pankso@161 140 ok_status() {
al@419 141 echo '[<span class="diff-add"> OK </span>]'
pankso@161 142 }
pankso@161 143
al@419 144
pankso@40 145 # Network interface status
al@419 146
pankso@40 147 interface_status() {
pascal@486 148 ip="----"
pascal@486 149 status="----"
pascal@486 150 scan=""
al@419 151 if ifconfig | grep -A1 $1 | grep -q inet; then
al@419 152 ip=$(ifconfig | grep -A1 $1 | grep inet | awk '{ print $2 }' | cut -d: -f2)
pascal@488 153 [ "$(cat /sys/class/net/$1/carrier)" == "1" ] &&
al@558 154 scan='<a data-icon="@scan@" href="network.cgi?scan='$ip'&amp;back=network.cgi">'$(_ 'Scan')'</a>'
pankso@40 155 fi
pascal@488 156 [ "$(cat /sys/class/net/$1/carrier)" == "1" ] &&
pascal@500 157 status="$(_ 'connected')" &&
pascal@500 158 speed="$(cat /sys/class/net/$1/speed 2> /dev/null)" &&
pascal@500 159 [ "$speed" ] && status="$status ${speed}M"
pascal@487 160 echo "<td>$status</td><td>$ip</td><td>$scan</td>"
pankso@40 161 }
pankso@40 162
al@419 163
pankso@40 164 # Catch network interface (used in summary and network main page)
al@419 165
pankso@40 166 list_network_interfaces() {
al@419 167 cat <<EOT
al@419 168 <table class="wide zebra center">
al@303 169 <thead>
al@303 170 <tr>
al@443 171 <td>$(_ 'Interface')</td>
al@443 172 <td>$(_ 'Name')</td>
al@443 173 <td>$(_ 'Status')</td>
al@443 174 <td>$(_ 'IP Address')</td>
al@443 175 <td>$(_ 'Scan ports')</td>
al@303 176 </tr>
al@303 177 </thead>
al@303 178 <tbody>
pankso@40 179 EOT
al@419 180 for i in $(ls /sys/class/net); do
pankso@40 181 case $i in
pankso@40 182 eth*)
al@558 183 echo '<tr><td><a data-icon="@eth@" href="network.cgi?eth">'$i'</a></td>
al@525 184 <td>Ethernet</td> '$(interface_status $i)'</tr>';;
pankso@40 185 wlan*|ath*|ra*)
al@558 186 echo '<tr><td><a data-icon="@wifi@" href="network.cgi?wifi">'$i'</a></td>
al@525 187 <td>Wireless</td> '$(interface_status $i)'</tr>';;
pascal@482 188 ppp*)
al@558 189 echo '<tr><td><a data-icon="@removable@" href="ppp.cgi">'$i'</a></td>
al@525 190 <td>Point to point</td> '$(interface_status $i)'</tr>';;
pascal@484 191 tap[0-9]*|tun[0-9]*)
al@558 192 echo '<tr><td><span data-icon="@removable@">'$i'</span></td>
al@525 193 <td>User space</td> '$(interface_status $i)'</tr>';;
pankso@40 194 lo)
al@558 195 echo '<tr><td><span data-icon="@loopback@">'$i'</span></td>
al@525 196 <td>Loopback</td> '$(interface_status $i)'</tr>';;
pankso@40 197 *)
pankso@40 198 continue ;;
pankso@40 199 esac
pankso@40 200 done
al@419 201 cat <<EOT
al@303 202 </tbody>
al@303 203 </table>
al@303 204 EOT
pankso@40 205 }
pankso@40 206
al@419 207
slaxemulator@232 208 # Get the list of panel styles
al@419 209
slaxemulator@232 210 list_styles() {
al@498 211 for style in $PANEL/styles/*; do
slaxemulator@232 212 style=$(basename $style)
slaxemulator@232 213 echo "<option value='$style'>$style</option>"
slaxemulator@232 214 done
slaxemulator@232 215 }
slaxemulator@232 216
al@419 217
slaxemulator@232 218 # Get the list of system locales
al@419 219
slaxemulator@232 220 list_locales() {
slaxemulator@232 221 for locale in $(find /usr/share/i18n/locales -type f -name "[a-z][a-z]_[A-Z][A-Z]")
slaxemulator@232 222 do
al@525 223 echo "<option value=\"$locale\">$locale</option>"
slaxemulator@232 224 done
slaxemulator@232 225 }
slaxemulator@232 226
al@419 227
slaxemulator@232 228 # Get the list of console keymaps
al@419 229
slaxemulator@232 230 list_keymaps() {
al@525 231 if [ -d /usr/share/kbd ]; then
al@525 232 # kbd-base
pascal@440 233 find /usr/share/kbd/keymaps/i386 -type f -name '*.map*' ! -path '*include*' | \
pascal@440 234 awk -F/ '{gsub(/.map.gz/, ""); printf "<option value=\"%s\">%s (%s)\n", $8, $8, $7}'
al@525 235 else
al@525 236 # kbd-busybox
pascal@440 237 ls /usr/share/kmap/*.kmap | \
pascal@440 238 sed 's|.*kmap/\(.*\).kmap|<option value="\1">\1|'
pascal@440 239 fi | sort
slaxemulator@232 240 }
slaxemulator@232 241
al@419 242
pankso@15 243 #
pankso@15 244 # xHTML 5 (header and footer skel are from the style)
pankso@15 245 #
pankso@15 246
pankso@44 247 loading_msg() {
al@525 248 [ -n "$(GET noheader)" ] && return
al@419 249 local MSG=${1:-$LOADING_MSG}
al@498 250 [ -z "$MSG" ] && MSG="$(_ 'Please wait')"
al@419 251 cat <<EOT
al@498 252 <script type="text/javascript">statusbar("$MSG", 1)</script>
pankso@44 253 EOT
pankso@44 254 }
pankso@44 255
al@419 256
pankso@15 257 xhtml_header() {
al@525 258 [ -n "$(GET noheader)" ] && return
al@538 259
al@538 260 local subtitle="$1" header="/var/cache/tazpanel/header.$(id -un)"
al@538 261
al@538 262 # Cache header
al@538 263 if [ ! -f "$header" ]; then
al@538 264 . ${PANEL}$HEADER > "$header"
al@538 265 cat >> "$header" <<EOT
pascal@511 266 <script type="text/javascript">
pascal@512 267 document.cookie = "guiuser=; expires=Thu, 01 Jan 1970 00:00:00 UTC";
pascal@511 268 document.cookie = "guiuser=$GUI_USER";
pascal@511 269 </script>
pascal@511 270 EOT
al@538 271 fi
al@539 272 sed "s|@@TITLE@@|$TITLE|; s|@@SUBTITLE@@|$subtitle|" "$header"
al@538 273
al@538 274 # Show debug output
al@501 275 if [ "$DEBUG" -eq 1 ]; then
al@501 276 local i j x
al@501 277 args=''
al@419 278 for x in GET POST COOKIE; do
al@419 279 for i in $($x); do
pascal@81 280 if [ $($x $i count) -gt 1 ]; then
pascal@81 281 for j in $(seq 1 $($x $i count)); do
pascal@81 282 args="$args $x($i,$j)='$($x $i $j)'"
pascal@81 283 done
pascal@81 284 else
pascal@81 285 args="$args $x($i)='$($x $i)'"
pascal@81 286 fi
pascal@81 287 done
pascal@81 288 done
pascal@81 289 for i in $(FILE); do
al@419 290 for j in name size type tmpname; do
pascal@81 291 args="$args FILE($i,$j)=$(FILE $i $j)"
pascal@81 292 done
pascal@81 293 done
al@419 294 cat <<EOT
al@419 295 <pre class="debug">
pascal@81 296 QUERY_STRING="$QUERY_STRING"$args
pankso@70 297 </pre>
pankso@70 298 EOT
pankso@67 299 fi
pankso@15 300 }
pankso@15 301
al@419 302
pankso@15 303 xhtml_footer() {
al@525 304 [ -n "$(GET noheader)" ] && return
al@538 305
al@524 306 export TEXTDOMAIN='tazpkg'
al@292 307 . ${PANEL}$FOOTER
pankso@15 308 }
pankso@15 309
al@419 310
al@501 311 table_start() { echo '<table>'; }
al@501 312 table_end() { echo '</table>'; }
pankso@153 313
al@419 314
pankso@153 315 df_thead() {
al@419 316 cat <<EOT
pankso@153 317 <thead>
pankso@153 318 <tr>
al@443 319 <td>$(_ 'Disk')</td>
al@443 320 <td>$(_ 'Label')</td>
al@443 321 <td>$(_ 'Type')</td>
al@443 322 <td>$(_ 'Size')</td>
al@443 323 <td>$(_ 'Available')</td>
al@443 324 <td>$(_ 'Used')</td>
al@443 325 <td>$(_ 'Mount point')</td>
pascal@343 326 <td>UUID</td>
pankso@153 327 </tr>
pankso@153 328 </thead>
pankso@153 329 EOT
pankso@153 330 }
al@318 331
al@419 332
al@318 333 msg() {
al@318 334 msgtype="$1"; shift
al@318 335 case "$msgtype" in
al@558 336 tip) I='@msgtip@';;
al@558 337 warn|warning) I='@msgwarn@';;
al@558 338 err|error) I='@msgerr@';;
al@558 339 up) I='@msgup@';;
al@558 340 *) I='@msg@';;
al@318 341 esac
al@558 342 echo "<section class=\"box\"><span data-icon=\"$I\"></span>$@</section>"
al@318 343 }
al@318 344
al@419 345
al@318 346 is_installed() {
al@318 347 [ -d "$INSTALLED/$1" ]
al@318 348 }
pascal@364 349
al@419 350
pascal@364 351 blk2h() {
pascal@460 352 if [ "$1" ]; then
pascal@460 353 echo $1
pascal@460 354 else
pascal@460 355 cat
pascal@460 356 fi | awk '{
pascal@364 357 n = $0/2
pascal@364 358 for (i = 1; n > 1024; i++)
pascal@364 359 n /= 1024
pascal@364 360 f = "%1.0f%c"
pascal@373 361 if (n < 100)
pascal@364 362 f = "%1.1f%c"
pascal@364 363 printf f,n,substr("KMGT", i, 1)
pascal@364 364 }'
pascal@364 365 }
al@419 366
al@419 367
al@419 368 # Show "Back" button
al@419 369
al@419 370 back_button() {
pascal@534 371 printf '<form action="%s" method="post"><button data-icon="%s">%s</button></form>' \
al@558 372 "${1:-javascript:history.go(-1)}" "${3:-@back@}" "${2:-$(_ 'Back')}"
al@419 373 }
al@419 374
al@419 375
pascal@523 376 # Show "Edit" button
pascal@523 377
pascal@523 378 edit_button() {
pascal@523 379 [ -w "$1" ] && cat <<EOT
pascal@523 380 <form action="index.cgi">
pascal@523 381 <input type="hidden" name="file" value="$1"/>
al@558 382 <button name="action" value="edit" data-icon="@edit@">${2:-$(_ 'Edit')}</button>
pascal@523 383 </form>
pascal@523 384 EOT
pascal@523 385 }
pascal@523 386
al@419 387 # Mark select option as checked
al@419 388
al@419 389 selected() {
al@419 390 [ "$1" == "$2" ] && echo -n 'selected'
al@419 391 }
al@437 392
al@437 393
al@437 394 check_root_tazpanel() {
al@558 395 if [ $(id -u) -ne 0 ]; then
al@437 396 msg err "$(_ 'You must be root to show this page.')"
al@437 397 xhtml_footer; exit 0
al@437 398 fi
al@437 399 }
pascal@507 400
pascal@507 401 # Get system database. NSS compatible.
pascal@507 402
pascal@507 403 getdb() {
al@526 404 if [ -n "$(which getent)" ]; then
al@526 405 getent "$1"
al@526 406 else
al@526 407 cat "/etc/$1" | sed '/^#/d'
al@526 408 fi
pascal@507 409 }
pascal@507 410
pascal@554 411 # The html 'file' object does not return the full path. Ajax helps on localhost.
pascal@554 412
pascal@554 413 file_chooser() {
al@557 414 # 1: <input> name; 2: [predefined value]; 3: [button icon]; 4: [MIME type]
al@557 415 id="input$RANDOM"
pascal@554 416 cat <<EOT
al@557 417 <span id="$id"><input type="text" name="$1" ${2:+value="$2" }/></span>\
pascal@561 418 <button data-icon="${3:-@conf@}" onclick="ajax('index.cgi?do=file-selection&amp;name=$1&amp;type=$4', '1', '$id'); return false">\
al@556 419 $(_n 'Browse')</button>
pascal@554 420 EOT
pascal@554 421 }
pascal@554 422
pascal@554 423 dir_chooser() {
al@557 424 # 1: <input> name; 2: [predefined value]; 3: [button icon]
al@557 425 id="input$RANDOM"
pascal@554 426 cat <<EOT
al@557 427 <span id="$id"><input type="text" name="$1" ${2:+value="$2" }/></span>\
al@558 428 <button data-icon="${3:-@folder@}" onclick="ajax('index.cgi?do=dir-selection&amp;name=$1', '1', '$id'); return false">\
al@556 429 $(_n 'Browse')</button>
pascal@554 430 EOT
pascal@554 431 }