epm-play 10.8 KB
Newer Older
1 2
#!/bin/sh
#
3 4
# Copyright (C) 2015, 2017, 2019, 2020, 2022  Etersoft
# Copyright (C) 2015, 2017, 2019, 2020, 2022  Vitaly Lipatov <lav@etersoft.ru>
5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#

20
load_helper epm-play-common
21

22 23
__check_installed_app()
{
24 25
    [ -s $epm_vardir/installed-app ] || return 1
    grep -q -- "^$1\$" $epm_vardir/installed-app
26 27
}

28 29
__save_installed_app()
{
30 31 32
    [ -d "$epm_vardir" ] || return 0
    __check_installed_app "$1" && return 0
    echo "$1" | sudorun tee -a $epm_vardir/installed-app >/dev/null
33 34 35 36
}

__remove_installed_app()
{
37 38 39 40 41 42
    [ -s $epm_vardir/installed-app ] || return 0
    local i
    for i in $* ; do
        sudorun sed -i "/^$i$/d" $epm_vardir/installed-app
    done
    return 0
43 44
}

45 46 47

__is_app_installed()
{
48 49
    __run_script "$1" --installed "$2"
    return
50 51
}

52

53 54
__get_app_package()
{
55
    __run_script "$1" --package-name "$2" "$3" 2>/dev/null
56 57
}

58

59 60 61 62 63 64 65 66 67 68
__list_all_packages()
{
    local name
    for name in $(__list_all_app) ; do
        __get_app_package $name
    done
}

# pkg app
__list_app_packages_table()
69
{
70 71
    local name
    for name in $(__list_all_app) ; do
72 73 74
        local pkg="$(__get_app_package $name)"
        [ -n "$pkg" ] || continue
        echo "$pkg $name"
75
    done
76 77
}

78 79 80 81 82 83 84 85 86 87
__filter_by_installed_packages()
{
    local i
    local tapt="$1"

    local pkglist
    pkglist="$(mktemp)" || fatal
    remove_on_exit $pkglist

    # get intersect between full package list and available packages table
88
    epm --short packages | LC_ALL=C sort -u >$pkglist
89 90 91 92 93
    LC_ALL=C join -11 -21 $tapt $pkglist | uniq | while read -r package description ; do
        if epm status --repacked "$package" </dev/null ; then
            echo "$package $description"
        fi
    done
94 95 96 97 98 99 100 101 102 103
    rm -f $pkglist

    # rpm on Fedora/CentOS no more print missed packages to stderr
    # get supported packages list and print lines with it
    #for i in $(epm query --short $(cat $tapt | cut -f1 -d" ") 2>/dev/null) ; do
    #    grep "^$i " $tapt
    #done
}

__get_installed_table()
104 105
{
    local i
106 107
    local tapt
    tapt="$(mktemp)" || fatal
108
    remove_on_exit $tapt
109
    __list_app_packages_table | LC_ALL=C sort -u >$tapt
110
    __filter_by_installed_packages $tapt
111
    rm -f $tapt
112
}
113

114 115 116 117
__list_installed_app()
{
    # get all installed packages and convert it to a apps list
    __get_installed_table | cut -f2 -d" "
118 119
}

120 121
__list_installed_packages()
{
122
    # get all installed packages
123
    __get_installed_table | cut -f1 -d" "
124 125
}

126

127 128 129 130 131
__epm_play_list_installed()
{
    local i
    if [ -n "$short" ] ; then
        for i in $(__list_installed_app) ; do
132 133 134
            # skip hidden apps
            local desc="$(__get_app_description $i)"
            [ -n "$desc" ] || continue
135 136 137 138 139
            echo "$i"
        done
        exit
    fi
    [ -n "$quiet" ] || echo "Installed applications:"
140
    for i in $(__list_installed_app) ; do
141
        # skip hidden apps
142
        local desc="$(__get_app_description $i)"
143
        [ -n "$desc" ] || continue
144 145 146 147 148 149
        [ -n "$quiet" ] || echo -n "  "
        printf "%-20s - %s\n" "$i" "$desc"
    done
}


150
epm_play_help()
151
{
152
    message '
153 154 155 156 157
Usage: epm play [options] [<app>]
Options:
    <app>                 - install <app>
    --remove <app>        - uninstall <app>
    --update [<app>|all]  - update <app> (or all installed apps) if there is new version
158
    --latest <app>        - forced to install the latest version of the application
159 160
    --list                - list all installed apps
    --list-all            - list all available apps
161
    --list-scripts        - list all available scripts
162 163
    --short (with --list) - list names only
    --installed <app>     - check if the app is installed
164
    --ipfs <app>          - use IPFS for downloading
165 166 167 168 169 170 171
    --product-alternatives- list alternatives (use like epm play app=beta)

Examples:
    epm play --remove opera
    epm play yandex-browser = beta
    epm play telegram = beta
    epm play telegram = 4.7.1
172
    epm play --update all
173
'
174 175
}

176 177 178 179


__epm_play_update()
{
180
    local i RES
181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207
    local CMDUPDATE="$1"
    shift
    RES=0
    for i in $* ; do
        echo
        echo "$i"
            if ! __is_app_installed "$i" ; then
                continue
            fi
        prescription="$i"
        if ! __check_play_script $prescription ; then
            warning "Can't find executable play script for $prescription. Try epm play --remove $prescription if you don't need it anymore."
            RES=1
            continue
        fi
        __epm_play_run $prescription $CMDUPDATE || RES=$?
    done
    return $RES
}


# name argument
__epm_play_install_one()
{
    local prescription="$1"
    shift

208 209 210 211 212 213
    if __epm_is_shell_script "$prescription"  ; then
        # direct run play script
        __epm_play_run_script "$prescription" --run "$@" || fatal "There was some error during install the application."
        return
    fi

214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234
    if __check_play_script "$prescription" ; then
        #__is_app_installed "$prescription" && info "$$prescription is already installed (use --remove to remove)" && exit 1
        __epm_play_run "$prescription" --run "$@" && __save_installed_app "$prescription" || fatal "There was some error during install the application."
    else
        opsdir=$psdir
        psdir=$prsdir
        __check_play_script "$prescription" || fatal "We have no idea how to play $prescription (checked in $opsdir and $prsdir)"
        __epm_play_run "$prescription" --run "$@" || fatal "There was some error during run $prescription script."
    fi
}


__epm_play_install()
{
   local i RES
   RES=0

   load_helper epm-check_updated_repo

   update_repo_if_needed

235 236 237 238 239 240 241 242 243 244
   # get all options
   options=''
   for i in  $* ; do
       case "$i" in
           --*)
               options="$options $i"
               ;;
       esac
   done

245
   while [ -n "$1" ] ; do
246 247 248 249 250 251
       case "$1" in
           --*)
               shift
               continue
               ;;
       esac
252 253
       local p="$1"
       local v=''
254
       # drop spaces
255 256 257 258 259 260 261
       n="$(echo $2)"
       if [ "$n" = "=" ] ; then
           v="$3"
           shift 3
       else
           shift
       fi
262
       __epm_play_install_one "$p" "$v" $options || RES=1
263 264 265 266 267
   done

   return $RES
}

268 269 270 271
__epm_play_download_epm_file()
{
    local target="$1"
    local file="$2"
272 273
    # use short version (3.4.5)
    local epmver="$(epm --short --version)"
274 275 276
    # use baseversion
    epmver=$(echo "$epmver" | sed -e 's|\.[0-9]*$||')

277 278 279 280 281
    local URL
    for URL in "https://eepm.ru/releases/$epmver/app-versions" "https://eepm.ru/app-versions" ; do
        info "Updating local IPFS DB in $eget_ipfs_db file from $URL/eget-ipfs-db.txt"
        docmd eget -q -O "$target" "$URL/$file" && return
    done
282 283 284
}


285
__epm_play_initialize_ipfs()
286
{
287
    if [ ! -d "$(dirname "$eget_ipfs_db")" ] ; then
288 289 290 291 292 293 294
        warning "ipfs db dir $eget_ipfs_db does not exist, skipping IPFS mode"
        return 1
    fi

    if [ ! -r "$eget_ipfs_db" ] ; then
        sudorun touch "$eget_ipfs_db" >&2
        sudorun chmod -v a+rw "$eget_ipfs_db" >&2
295
    fi
296 297

    # download and merge with local db
298 299 300
    local t
    t=$(mktemp) || fatal
    remove_on_exit $t
301
    __epm_play_download_epm_file "$t" "eget-ipfs-db.txt" || warning "Can't update IPFS DB"
302
    if [ -s "$t" ] && [ -z "$EPM_IPFS_DB_UPDATE_SKIPPING" ] ; then
303 304 305 306 307
        echo >>$t
        cat $eget_ipfs_db >>$t
        sort -u < $t | grep -v "^$" > $eget_ipfs_db
    fi

308
    # the only one thing is needed to enable IPFS in eget
309
    export EGET_IPFS_DB="$eget_ipfs_db"
310
}
311

312 313 314 315 316
epm_play()
{
[ "$EPMMODE" = "package" -o "$EPMMODE" = "git" ] || fatal "epm play is not supported in single file mode"
local psdir="$(realpath $CONFIGDIR/play.d)"
local prsdir="$(realpath $CONFIGDIR/prescription.d)"
317

318
if [ -z "$1" ] ; then
319
    [ -n "$short" ] || [ -n "$quiet" ] || echo "Available applications (for current arch $DISTRARCH):"
320
    __epm_play_list $psdir
321 322 323
    exit
fi

324 325 326
# allow enable ipfs in global conf
[ "$ipfs" = "--ipfs" ] && __epm_play_initialize_ipfs

327

328 329 330 331 332 333
while [ -n "$1" ] ; do
case "$1" in
    -h|--help)
        epm_play_help
        exit
        ;;
334

335 336
    --ipfs)
        shift
337
        [ "$ipfs" = "--ipfs" ] || __epm_play_initialize_ipfs
338
        ;;
339

340
    --remove)
341
        shift
342 343 344 345 346 347 348
        if [ -z "$1" ] ; then
            fatal "run --remove with 'all' or a project name"
        fi

        local list
        if [ "$1" = "all" ] ; then
            shift
349
            info "Retrieving list of installed apps ..."
350 351 352 353 354 355
            list="$(__list_installed_app)"
        else
            list="$*"
        fi

        __epm_play_remove $list
356 357
        exit
        ;;
358

359
    --update|--upgrade)
360 361
        shift
        local CMDUPDATE="--update"
362 363
        # check --force on common.sh side
        #[ -n "$force" ] && CMDUPDATE="--run"
364

365 366 367
        if [ -z "$1" ] ; then
            fatal "run --update with 'all' or a project name"
        fi
368

369 370 371
        local list
        if [ "$1" = "all" ] ; then
            shift
372
            info "Retrieving list of installed apps ..."
373 374 375 376 377 378 379 380 381
            list="$(__list_installed_app)"
        else
            list="$*"
        fi

        __epm_play_update $CMDUPDATE $list
        exit
        ;;

382
    --installed)
383 384 385 386 387
        shift
        __is_app_installed "$1" "$2"
        #[ -n "$quiet" ] && exit
        exit
        ;;
388

389
    # internal options
390
    --installed-version|--package-name|--product-alternatives|--info)
391 392 393
        __run_script "$2" "$1" "$3"
        exit
        ;;
394
    --list-installed-packages)
395 396 397
        __list_installed_packages
        exit
        ;;
398
    --list|--list-installed)
399 400 401
        __epm_play_list_installed
        exit
        ;;
402 403

    --full-list-all)
404
        [ -n "$short" ] || [ -n "$quiet" ] || echo "Available applications (for current arch $DISTRARCH):"
405
        __epm_play_list $psdir extra
406 407
        exit
        ;;
408

409
    --list-all)
410
        [ -n "$short" ] || [ -n "$quiet" ] || echo "Available applications (for current arch $DISTRARCH):"
411 412 413 414 415 416 417
        __epm_play_list $psdir
        [ -n "$quiet" ] || [ -n "$*" ] && exit
        echo
        #echo "Run epm play --help for help"
        epm_play_help
        exit
        ;;
418

419
    --list-scripts)
420 421 422 423
        [ -n "$short" ] || [ -n "$quiet" ] || echo "Run with a name of a play script to run:"
        __epm_play_list $prsdir
        exit
        ;;
424 425 426 427 428

    --latest)
        shift
        export latest="true"
        ;;
429 430 431 432 433 434 435
    -*)
        fatal "Unknown option $1"
        ;;
     *)
        break
        ;;
esac
436

437
done
438

439
__epm_play_install $(echo "$*" | sed -e 's|=| = |g')
440
}