#!/bin/sh # # scratchpkg # # Copyright (c) 2018 by Emmett1 (emmett1.2miligrams@gmail.com) # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU 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 General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # msg() { echo "==> $1" } msgerr() { msg "ERROR: $*" } msgwarn() { msg "WARNING: $*" } msginst() { echo "[i] $1" } msgmiss() { echo "[m] $1" } msgnoinst() { echo "[-] $1" } needarg() { [ "$*" ] || { msgerr "This operation required an arguments!" exit 1 } } isinstalled() { if [ -s "$INDEX_DIR/$1/.pkginfo" ] && [ "$(grep $1 $INDEX_DIR/$1/.pkginfo)" ]; then return 0 else return 1 fi } allinstalled() { grep ^name "$INDEX_DIR"/*/.pkginfo | awk '{print $3}' } installed_pkg_info() { if isinstalled $1; then grep ^$2 "$INDEX_DIR/$1/.pkginfo" | cut -d " " -f3- fi } deps_alias() { [ -f $ALIAS_FILE ] || { echo $@ return } while [ "$1" ]; do getalias=$(grep -w ^$1 $ALIAS_FILE | awk '{print $2}') echo ${getalias:-$1} shift done unset getalias } getdepends() { ppath=$(getportpath $1) || return 0 deps=$(grep "^# depends[[:blank:]]*:" $ppath/$BUILD_SCRIPT \ | sed 's/^# depends[[:blank:]]*:[[:blank:]]*//' \ | tr ' ' '\n' \ | awk '!a[$0]++' \ | sed 's/,//') deps_alias $deps } getportpath() { for repo in $REPO; do if [ -f $repo/$1/$BUILD_SCRIPT ]; then dirname $repo/$1/$BUILD_SCRIPT return 0 fi done return 1 } pkg_dependent() { needarg $@ if [ "$(getportpath $1)" ]; then grep -R "# depends[[:blank:]]*:" $REPO \ | sed "s,:# depends[[:blank:]]*:[[:blank:]]*,#|,;s, ,|,g;s,$,|,g" \ | grep "|$1|" \ | awk -F "#" '{print $1}' \ | rev \ | awk -F / '{print $2}' \ | rev else msgerr "Port '$1' not exist." return 1 fi } pkg_orphan() { tmpallpkg="/tmp/.pkgquery_allpkg.$$" tmpalldep="/tmp/.pkgquery_alldep.$$" for pkg in $(allinstalled); do echo $pkg >> $tmpallpkg dep="$dep $(getdepends $pkg)" done echo $dep | tr ' ' '\n' | sort | uniq > "$tmpalldep" grep -xvF -f "$tmpalldep" "$tmpallpkg" rm "$tmpalldep" "$tmpallpkg" } pkg_dup() { dup=$(find $REPO -type d -print | grep -Exv "($(echo $REPO | tr ' ' '|'))" | \ rev | cut -d '/' -f1 | rev | sort | uniq -d) if [ "$dup" ]; then for dp in $dup; do for repo in $REPO; do [ -d $repo/$dp ] && echo "$repo/$dp" done done else msg "No duplicate ports found." fi } pkg_foreign() { for pkg in $(allinstalled); do if ! getportpath $pkg >/dev/null; then iname=$(installed_pkg_info $pkg name) iversion=$(installed_pkg_info $pkg version) irelease=$(installed_pkg_info $pkg release) echo "$iname $iversion-$irelease" fi unset iname iversion irelease done } pkg_search() { needarg $@ arg=$* for repo in $REPO; do out=$(grep -R "# description" $repo | grep $BUILD_SCRIPT | grep "$arg" | awk -F : '{print $1}' | sort) [ "$out" ] || continue for line in $out; do repo=$(echo $line | rev | awk -F / '{print $3}' | rev) desc=$(grep "^# description[[:blank:]]*:" $line | sed 's/^# description[[:blank:]]*:[[:blank:]]*//') . $line echo "($repo) $name $version-$release: $desc" unset repo desc name version release build done unset out done } pkg_locked() { for pkg in $(allinstalled); do [ -f "$INDEX_DIR/$pkg/.lock" ] && echo "$pkg" done } pkg_installed() { for all in $(allinstalled); do printf "%s" "$all " grep -e ^version -e ^release $INDEX_DIR/$all/.pkginfo | awk '{print $3}' | tr '\n' '-' | sed 's:\-$::' echo done } pkg_missingdep() { for pkg in $(allinstalled); do if getportpath "$pkg" >/dev/null; then depends=$(getdepends $pkg) fi if [ "$depends" ]; then for d in $depends; do if ! isinstalled $d; then if [ -z "$msd" ]; then msd="$d" else msd="$msd $d" fi fi done fi [ "$msd" ] && echo "$pkg: $msd" unset depends msd done } pkg_info() { needarg $@ ppath=$(getportpath $1) || return 1 . $ppath/$BUILD_SCRIPT desc=$(grep "^# description[[:blank:]]*:" $ppath/$BUILD_SCRIPT | sed 's/^# description[[:blank:]]*:[[:blank:]]*//') url=$(grep "^# homepage[[:blank:]]*:" $ppath/$BUILD_SCRIPT | sed 's/^# homepage[[:blank:]]*:[[:blank:]]*//') maint=$(grep "^# maintainer[[:blank:]]*:" $ppath/$BUILD_SCRIPT | sed 's/^# maintainer[[:blank:]]*:[[:blank:]]*//') deps=$(getdepends $1 | tr '\n' ' ') echo "Name: $1" echo "Path: $ppath" echo "Version: $version" echo "Release: $release" echo "Description: $desc" echo "Homepage: $url" echo "Maintainer: $maint" echo "Dependencies: $deps" } pkg_depends() { needarg $@ if getportpath "$1" >/dev/null; then depends=$(getdepends $1) else msgerr "Port '$1' not exist." return 1 fi for dep in $depends; do if isinstalled $dep; then msginst "$dep" elif getportpath $dep >/dev/null; then msgnoinst "$dep" else msgmiss "$dep" fi done } pkg_path() { needarg $@ if PPATH=$(getportpath "$1"); then echo "$PPATH" else msgerr "Port '$1' not exist." return 1 fi } pkg_provide() { needarg $@ arg=$(echo $1 | sed "s/^\///") grep -R "$arg" $INDEX_DIR/*/.files \ | sed "s:$INDEX_DIR/::" \ | sed "s:/.files::" \ | tr : " " \ | column -t } pkg_readme() { needarg $@ if PPATH=$(getportpath "$1"); then if [ -f "$PPATH/readme" ]; then cat "$PPATH/readme" else msgerr "Port '$1' does not have readme." fi else msgerr "Port '$1' not exist." exit 1 fi } pkg_files() { needarg $@ if isinstalled $1; then cat "$INDEX_DIR/$1/.files" else msg "Package '$1' not installed." fi } pkg_cat() { needarg $@ if PPATH=$(getportpath "$1"); then cat "$PPATH/$BUILD_SCRIPT" else msgerr "Port '$1' not exist." return 1 fi } pkg_help() { cat << EOF Usage: $(basename $0) [] Options: search find ports in repo cat print spkgbuild depends print dependencies dependent print dependent path print path in repo provide print port's provided files readme print readme file, if exist files print files installed info print information dup print duplicate ports in repo installed print all installed ports locked print loacked ports missingdep print missing dependencies orphan print orphan installed ports foreign print foreign ports help print this help msg EOF } print_runhelp_msg() { echo "Run '$(basename $0) help' to see available options." exit 2 } BUILD_SCRIPT="spkgbuild" INDEX_DIR="/var/lib/scratchpkg/index" REPO_FILE="/etc/scratchpkg.repo" ALIAS_FILE="/etc/scratchpkg.alias" if [ -f "$REPO_FILE" ]; then for repodir in $(grep -Ev '^(#|$)' "$REPO_FILE" | awk '{print $1}'); do REPO="$REPO $repodir" done fi opts=$1 if [ -z "$opts" ]; then print_runhelp_msg fi shift if [ $(type -t pkg_$opts) ]; then pkg_$opts "$@" else print_runhelp_msg fi exit $?