Added Kiss package manager

Signed-off-by: The-Repo-Club <wayne6324@gmail.com>
This commit is contained in:
The-Repo-Club 2022-10-02 12:59:09 +01:00
parent 500942bf8c
commit 127f414edb
No known key found for this signature in database
GPG Key ID: E30EC2FBFB05C44F
15 changed files with 2733 additions and 0 deletions

2003
localbin/.local/bin/kiss/kiss Executable file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,92 @@
#!/bin/sh
# Enter a kiss chroot
log() {
printf '\033[32m->\033[m %s.\n' "$*"
}
die() {
log "$*" >&2
exit 1
}
run() {
printf '%s\n' "$*"
"$@" || return "${_ret:=0}"
}
clean() {
log Unmounting host paths; {
run umount "$1/dev/shm" 2>/dev/null
run umount "$1/dev/pts"
run umount "$1/dev"
run umount "$1/proc"
run umount "$1/run"
run umount "$1/sys/firmware/efi/efivars" 2>/dev/null
run umount "$1/sys"
run umount "$1/tmp"
run umount "$1/etc/resolv.conf"
}
}
mounted() {
# This is a pure shell mountpoint implementation. We're dealing
# with basic (and fixed/known) input so this doesn't need to
# handle more complex cases.
[ -e "$1" ] || return 1
[ -e /proc/mounts ] || return 1
while read -r _ target _; do
[ "$target" = "$1" ] && return 0
done < /proc/mounts
return 1
}
mmount() {
dest=$1
shift
mounted "$dest" || run mount "$@" "$dest"
}
main() {
# Ensure input does not end in '/'.
set -- "${1%"${1##*[!/]}"}"
[ "$1" ] || die Need a path to the chroot
[ -d "$1" ] || die Given path does not exist
[ "$(id -u)" = 0 ] || die Script needs to be run as root
trap 'clean "${1%"${1##*[!/]}"}"' EXIT INT
log Mounting host paths; {
mmount "$1/dev" -o bind /dev
mmount "$1/dev/pts" -o bind /dev/pts
mmount "$1/dev/shm" -t tmpfs shmfs 2>/dev/null
mmount "$1/proc" -t proc proc
mmount "$1/run" -t tmpfs tmpfs
mmount "$1/sys" -t sysfs sys
mmount "$1/sys/firmware/efi/efivars" -t efivarfs efivarfs 2>/dev/null
mmount "$1/tmp" -o mode=1777,nosuid,nodev -t tmpfs tmpfs
touch "$1/etc/resolv.conf"
mmount "$1/etc/resolv.conf" -o bind /etc/resolv.conf
}
log Entering chroot; {
_ret=1
run chroot "$1" /usr/bin/env -i \
HOME=/root \
TERM="$TERM" \
SHELL=/bin/sh \
USER=root \
LOGNAME=root \
CFLAGS="${CFLAGS:--march=x86-64 -mtune=generic -pipe -O2}" \
CXXFLAGS="${CXXFLAGS:--march=x86-64 -mtune=generic -pipe -O2}" \
MAKEFLAGS="${MAKEFLAGS:--j$(nproc 2>/dev/null || echo 1)}" \
/bin/sh -l
} || die chroot failed
}
main "$1"

View File

@ -0,0 +1,13 @@
#!/bin/sh -ef
# Display a package's dependencies
pkg=${1:-"${PWD##*/}"}
kiss list "$pkg" >/dev/null || {
printf 'usage: kiss-depends [pkg]\n' >&2
exit 1
}
while read -r dep mak || [ "$dep" ]; do
printf '%s%s\n' "$dep" "${mak:+ "$mak"}"
done 2>/dev/null < "$KISS_ROOT/var/db/kiss/installed/$pkg/depends"

View File

@ -0,0 +1,30 @@
#!/bin/sh -ef
# Copy a package's repository files into the current directory
pkg=${1:-"${PWD##*/}"}
num=$(printf %d "${2:-0}")
dir=$(kiss search "$pkg" 2>/dev/null) || {
printf 'usage: [kiss-fork [pkg]] [index]\n'
exit 1
}
# Globbing is disabled and word splitting is intentional.
# shellcheck disable=2086
set -- $dir
[ "$num" -ge "$#" ] && {
printf 'index exceeds maximum\n'
exit 1
}
shift "$num"
[ "$1" ] || [ -d "$1" ] || {
printf 'failed to locate package\n'
exit 1
}
printf 'found package in %s\n' "$1"
cp -Lrf "$1" .
printf 'forked package to %s\n' "$PWD/$pkg"

View File

@ -0,0 +1,40 @@
#!/bin/sh -e
# Read KISS documentation
cd "$KISS_ROOT/usr/share/doc/kiss" 2>/dev/null || {
printf 'Documentation is missing from /usr/share/doc/kiss\n'
exit 1
}
_q=$1
! [ -f "${_q:-.}/index.txt" ] || file=./${_q:-.}/index.txt
! [ -f "${_q:-.}.txt" ] || file=./${_q:-.}.txt
! [ -f "${_q:-:}" ] || file=./${_q:-.}
# Fallback to package READMEs.
# False positive, intended behavior.
# shellcheck disable=2046
[ "$file" ] || {
set -f
set +f -- $(kiss s "${_q##*/}")
file=${1:+"$1/README"}
}
# Fallback to search (allows 'kiss help firefox' to work).
# False positive, intended behavior.
# shellcheck disable=2046
[ "$file" ] || {
set -f
set +f -- $(find . -name "${_q##*/}.txt")
file=$1
}
: "${file:=404.txt}"
cat <<EOF - "$file" | "${PAGER:-less}"
Reading ${file#./}
________________________________________________________________________________
EOF

View File

@ -0,0 +1,46 @@
#!/bin/sh -ef
# Link a repository file to another repository
[ "$1" ] || {
printf 'usage: kiss-link file\n'
exit 1
}
[ -f "${file:=$1}" ] || {
printf 'file %s does not exist in the current directory\n' "$1"
exit 1
}
oPWD=$PWD
# Check if the package exists in a repository and error out here
# if it does not. The error message from the package manager will
# be displayed.
kiss search "${PWD##*/}" >/dev/null
# Disable this warning as globbing is disabled and word splitting
# is intentional. This grabs the location of the package's files.
# shellcheck disable=2046
{
# Generate a list of repositories in which the package
# exists. Then 'cd' to the first found directory to do a
# comparison.
set -- $(kiss search "${PWD##*/}"); cd "$1"
# Error if the package exists nowhere but the current
# directory and this script would create a broken symlink.
[ -z "$2" ] && [ "$PWD" = "$oPWD" ] && {
printf 'error: cannot symlink file to itself\n'
exit 1
}
# If the first repository in '$KISS_PATH' is the current
# directory, use the second repository in the list.
[ "$PWD" = "$oPWD" ] && shift
# Finally, make the link to the file in whatever repository
# it was found in.
ln -sf "$1/$file" "$oPWD/$file"
}
printf 'linked %s to %s\n' "$file" "$1"

View File

@ -0,0 +1,18 @@
#!/bin/sh -ef
# Find the maintainer of a package
# Use the current directory as the package name if no package is given.
[ "$1" ] || {
export KISS_PATH=${PWD%/*}:$KISS_PATH
set -- "${PWD##*/}"
}
kiss search "$@" | uniq -u | while read -r repo; do cd "$repo"
m=$(git log -1 version 2>/dev/null) ||:
m=${m##*Author: }
m=${m%%>*}
[ "$m" ] || continue
printf '=> %s\n%s>\n' "$PWD" "$m"
done

View File

@ -0,0 +1,11 @@
#!/bin/sh -ef
# Display all files owned by a package
pkg=${1:-"${PWD##*/}"}
kiss list "$pkg" >/dev/null || {
printf 'usage: kiss-manifest [pkg]\n' >&2
exit 1
}
cat "$KISS_ROOT/var/db/kiss/installed/$pkg/manifest" 2>/dev/null

View File

@ -0,0 +1,31 @@
#!/bin/sh
# Create a boilerplate package
die() {
printf '%s\n' "$*"
exit 1
}
log() {
printf '=> %s.\n' "$1"
}
[ "$1" ] || die "usage: kiss-new [name] [version] [source]"
[ -d "$1" ] && die "error: Package $1 already exists"
mkdir -p "$1" || die "error: Couldn't create directory in $PWD"
cd "$1" || die "error: Couldn't enter directory $1/"
log "Creating build file"; {
printf '#!/bin/sh -e\n' > build
chmod +x build
}
log "Creating version file with '${2%% *} 1'"; {
printf '%s\n' "${2%% *} 1" > version
}
log "Creating sources file with '$3'"; {
printf '%s\n' "$3" > sources
}
log "Package $1 created in $PWD"

View File

@ -0,0 +1,41 @@
#!/bin/sh -e
# List orphaned packages
n='
'
cd "$KISS_ROOT/var/db/kiss/installed"
set -- *
l=$n$(
for pkg do shift
set -- "$@" -e "$pkg"
done
# Get a list of non-orphans.
grep -Fx "$@" -- */depends |
{
# Strip filename.
sed s,.\*/depends:,,
# Exclude packages which are not really orphans.
printf '%s\n' baseinit baselayout busybox bzip2 e2fsprogs gcc \
git grub kiss make musl
} |
# Remove duplicates.
sort -u
)$n
# Generate the list of orphans by finding the inverse of the non-orphan list.
for pkg do shift
case $l in (*"$n$pkg$n"*)
continue
esac
set -- "$@" "$pkg"
done
printf '%s\n' "$@"

View File

@ -0,0 +1,308 @@
#!/bin/sh
# Check repository for outdated packages
die() {
printf '%s\n' "$*" >&2
exit 1
}
mkcd() {
mkdir -p "$1" && cd "$1"
}
repology_name() {
# Fix any known naming inconsistences between packages and Repology.
remote=$(
# Strip unrelated suffixes.
remote=${1%%-bin}
remote=${remote%%-git}
# Remote names are all lowercase.
tr '[:upper:]' '[:lower:]' <<EOF |
$remote
EOF
# Remote always uses -.
tr _ -
)
case $remote in
baseinit|baselayout|kiss)
remote=-
;;
clang)
remote=llvm
;;
dash)
remote=dash-shell
;;
dejavu-ttf)
remote=fonts:dejavu
;;
dsp)
remote=dsp-audio-processing
;;
emacs-nox)
# TODO [community]: Make default emacs no x11?
remote=emacs
;;
fd)
remote=fd-find
;;
fetsh)
# TODO [community]: Rename package?
remote=fet.sh
;;
firefox-esr)
remote=firefox
;;
font-awesome-ttf)
remote=fonts:fontawesome
;;
foot-pgo)
remote=foot
;;
gc)
remote=boehm-gc
;;
gnugrep)
# shell-check is dumb here so this must be quoted.
remote='grep'
;;
gnupg[12])
# Reported to repology.org.
# https://github.com/repology/repology-rules/issues/285
remote=gnupg
;;
gtk+3)
remote=gtk3+classic
;;
gst-*)
remote=gstreamer:${remote##*-}
;;
gtar)
remote=tar
;;
eiwd)
remote=iwd
;;
hack)
# It might be nice to adopt Repology's naming scheme for
# fonts as it also makes them self-documenting and easy
# to search for ('kiss s font:\*).
remote=fonts:hack
;;
harfbuzz-icu)
# TODO: Report to repology.org?
# Package split.
remote=harfbuzz
;;
libelf)
remote=elfutils
;;
liberation-fonts)
remote=fonts:liberation
;;
libmupdf | libxaw3d)
# TODO [community]: Rename packages?
remote=${remote##lib}
;;
libseat)
remote=seatd
;;
links2)
# TODO [community]: Rename package?
remote=links
;;
linux-headers)
remote=linux
;;
lux)
remote=lux-brightness-ventto
;;
man-pages)
# TODO: Report to repology.org.
# man-pages -> manpages
# man-pages-posix -> man-pages-posix
remote=manpages
;;
netsurf-fb)
remote=netsurf
;;
openjpeg2)
# TODO [community]: Rename package?
remote=openjpeg
;;
osh)
remote=oil-shell
;;
pinentry-dmenu)
remote=pinentry-dmenu-cemkeylan
;;
pyqt5)
# TODO [community]: Rename package?
remote=python-qt
;;
python2)
remote=python
;;
qt5*)
remote=qt
;;
rage)
remote=rage-encryption-tool
;;
sane)
remote=sane-backends
;;
spleen-font)
remote=fonts:spleen
;;
sshfs)
remote=fusefs:sshfs
;;
surf)
remote=surf-browser
;;
st)
remote=st-term
;;
sway-no-seat | sway-tiny)
remote=sway
;;
terminus-font)
remote=fonts:terminus
;;
tiv)
remote=tiv-unclassified
;;
unifont)
remote=fonts:unifont
;;
webkit2gtk)
# TODO [community]: Rename package?
remote=webkitgtk
;;
xf86-*)
remote=xdrv:${remote##*-}
;;
xmlsec1)
# TODO [community]: Rename package?
remote=xmlsec
;;
esac
}
repology_version() {
[ -f "$1.svg" ] || return 1
read -r remote_ver < "$1.svg" || :
remote_ver=${remote_ver%</text>*}
remote_ver=${remote_ver##*>}
}
repo_version() {
read -r ver _ 2>/dev/null < "$2/version" || {
printf '%-30s local version not found\n' "$1" >&2
return 1
}
[ "$ver" != git ]
}
get_outdated() {
repo=${repo%%/}
printf '\n[Checking Repology for outdated packages in %s]\n\n' "$repo" >&2
for pkg in */; do
pkg=${pkg%%/}
repology_name "${pkg##*/}"
[ "$remote" = - ] ||
set -- "$@" -z "$remote.svg" \
"https://repology.org/badge/latest-versions/$remote.svg"
done
mkcd "$tmp/${repo##*/}"
curl -SsZ --parallel-max 16 --remote-name-all "$@" ||
die 'fatal: network error'
for _pkg in "$OLDPWD"/*/; do
pkg=${_pkg%%/}
pkg=${pkg##*/}
repo_version "$pkg" "$_pkg" || continue
repology_name "$pkg"
repology_version "$remote" || continue
case $remote_ver in *", $ver"* | *"$ver,"* | "$ver" | - | '')
continue
esac
printf '%-30s %s -> %s\n' "$pkg" "$ver" "$remote_ver"
done
}
main() {
set -e
[ "$1" ] ||
die 'usage: kiss [ou]tdated /path/to/repo...'
mkdir -p "${tmp:=${XDG_CACHE_HOME:-"$HOME/.cache"}/kiss/repology}"
for repo do
old_pwd=$PWD
cd "$repo"
get_outdated
cd "$old_pwd"
done
}
main "$@"

View File

@ -0,0 +1,35 @@
#!/bin/sh -e
# Check which package owns a file
# Follow symlinks to any paths.
case $1 in
/*)
cd -P "$KISS_ROOT${1%/*}"
;;
*/*)
cd -P "${1%/*}"
;;
*)
cd -P .
;;
esac
[ -f "$PWD/${1##*/}" ] || {
printf 'usage: kiss-owns [/path/to/file]\n' >&2
exit 1
}
# Print the full path to the manifest file which contains
# the match to our search.
pkg_owns=$(grep -lFx \
"$PWD/${1##*/}" \
"$KISS_ROOT/var/db/kiss/installed/"*/manifest)
# Extract the package name from the path above.
pkg_owns=${pkg_owns%/*}
pkg_owns=${pkg_owns##*/}
printf '%s\n' "$pkg_owns"

View File

@ -0,0 +1,12 @@
#!/bin/sh -e
# Lists the owners of all files with conflicts
kiss a | while read -r _ path; do
if owner=$(kiss owns "$path" 2>/dev/null) && [ "$owner" ]; then
printf '%s %s\n' "$owner" "$path"
else
printf 'warning: %s has no owner\n' "$path" >&2
fi
done

View File

@ -0,0 +1,9 @@
#!/bin/sh -e
# Display packages which depend on package
[ "$1" ] || set -- "${PWD##*/}"
cd "$KISS_ROOT/var/db/kiss/installed"
grep -E "^$1( |$)" -- */depends

View File

@ -0,0 +1,44 @@
#!/bin/sh -ef
# Show the size on disk for a package
get_size() {
# Naive function to convert bytes to human readable
# sizes (MB, KB, etc). This is probably wrong in places
# though we can fix this over time. It's a start.
case ${#1} in
[0-3]) hum=$(($1))KB ;;
[4-6]) hum=$(($1 / 1024))MB ;;
[7-9]) hum=$(($1 / 1024 / 1024))GB ;;
*) hum=$(($1)) ;;
esac
printf '%s\t%s\n' "$hum" "$2"
}
# Use the current directory as the package name if no package is given.
[ "$1" ] || set -- "${PWD##*/}"
# Ignore shellcheck as we want the warning's behavior.
# shellcheck disable=2015
kiss list "${1:-null}" >/dev/null || {
printf 'usage: kiss-size [pkg]\n'
exit 1
}
# Filter directories from manifest and leave only files.
# Directories in the manifest end in a trailing '/'.
# Send the file list to 'xargs' to run through 'du',
# this prevents du from exiting due to too many arguments
sed -e "s|^|$KISS_ROOT|" -e 's|.*/$||' \
"$KISS_ROOT/var/db/kiss/installed/$1/manifest" \
| xargs du -sk -- 2>/dev/null |
# Iterate over each line and convert the byte output to human
# readable (MB, KB, GB, etc).
while read -r size file || {
get_size "$tot" total >&2
break
} do
get_size "$size" "$file"
tot=$((tot + size))
done