193 lines
5.3 KiB
Bash
Executable File
193 lines
5.3 KiB
Bash
Executable File
#!/bin/sh
|
||
# shellcheck source=/dev/null
|
||
#
|
||
# pfetch - Simple POSIX sh fetch script.
|
||
|
||
die() {
|
||
printf '\033[31;1merror\033[m: %s.\n' "$@" >&2
|
||
exit 1
|
||
}
|
||
|
||
log() {
|
||
# PF_COLOR1: Control color of info name.
|
||
# PF_SEP: Control the separator between info name and info data.
|
||
# PF_COLOR2: Control color of info data.
|
||
printf '\033[15C\033[3%s;1m%s\033[m%s\033[3%sm%s\033[m\n' \
|
||
"${PF_COLOR1:-1}" "$1" "${PF_SEP:- }" "${PF_COLOR2:-7}" "${2:-?}"
|
||
|
||
# Keep track of the number of times 'log()' has been run.
|
||
log=$((log + 1))
|
||
}
|
||
|
||
get_os() {
|
||
case $kernel_name in
|
||
Linux|GNU*) os=linux ;;
|
||
|
||
*)
|
||
die "Unknown OS detected '$kernel_name'" \
|
||
"Open an issue on GitHub to add support for your OS"
|
||
;;
|
||
esac
|
||
}
|
||
|
||
get_title() {
|
||
case $os in
|
||
linux)
|
||
read -r hostname < /proc/sys/kernel/hostname
|
||
;;
|
||
esac
|
||
|
||
# Username is retrieved by first checking '$USER' with a fallback
|
||
# to the 'whoami' command.
|
||
#
|
||
# Hostname is retrieved by first checking '$HOSTNAME' with a fallback
|
||
# to the OS specific detection above and finally an additional fallback
|
||
# to the 'hostname' command.
|
||
#
|
||
# PF_SEP and PF_COLOR2 change printing options in the 'log()' function.
|
||
#
|
||
# Disable the warning about '$HOSTNAME' being undefined in POSIX sh as
|
||
# it is intended for allowing the user to overwrite the value on invocation.
|
||
# shellcheck disable=SC2039
|
||
PF_SEP=@ PF_COLOR2='3;1' \
|
||
log "${USER:-$(whoami)}" "${HOSTNAME:-${hostname:-$(hostname)}}"
|
||
}
|
||
|
||
get_distro() {
|
||
case $os in
|
||
linux)
|
||
. /etc/os-release && distro=$PRETTY_NAME
|
||
;;
|
||
esac
|
||
|
||
log os "$distro"
|
||
}
|
||
|
||
get_kernel() {
|
||
log kernel "$kernel_version"
|
||
}
|
||
|
||
get_uptime() {
|
||
# Uptime works by retrieving the data in total seconds and then
|
||
# converting that data into days, hours and minutes using simple
|
||
# math.
|
||
case $os in
|
||
linux)
|
||
IFS=. read -r s _ < /proc/uptime
|
||
;;
|
||
esac
|
||
|
||
# Convert the uptime from seconds into days, hours and minutes.
|
||
d=$((s / 60 / 60 / 24))
|
||
h=$((s / 60 / 60 % 24))
|
||
m=$((s / 60 % 60))
|
||
|
||
# Only append days, hours and minutes if they're non-zero.
|
||
[ "$d" = 0 ] || uptime="${uptime}${d}d "
|
||
[ "$h" = 0 ] || uptime="${uptime}${h}h "
|
||
[ "$m" = 0 ] || uptime="${uptime}${m}m "
|
||
|
||
log uptime "${uptime:-0m}"
|
||
}
|
||
|
||
get_memory() {
|
||
case $os in
|
||
# Used memory is calculated using the following "formula" (Linux):
|
||
# MemUsed = MemTotal + Shmem - MemFree - Buffers - Cached - SReclaimable
|
||
# Source: https://github.com/KittyKatt/screenFetch/issues/386
|
||
linux)
|
||
# Parse the '/proc/meminfo' file splitting on ':' and 'k'.
|
||
# The format of the file is 'key: 000kB' and an additional
|
||
# split is used on 'k' to filter out 'kB'.
|
||
while IFS=:k read -r key val _; do
|
||
case $key in
|
||
MemTotal)
|
||
mem_used=$((mem_used + val))
|
||
mem_total=$val
|
||
;;
|
||
|
||
Shmem)
|
||
mem_used=$((mem_used + val))
|
||
;;
|
||
|
||
MemFree|Buffers|Cached|SReclaimable)
|
||
mem_used=$((mem_used - val))
|
||
;;
|
||
esac
|
||
done < /proc/meminfo
|
||
|
||
mem_used=$((mem_used / 1024))
|
||
mem_total=$((mem_total / 1024))
|
||
;;
|
||
esac
|
||
|
||
log memory "${mem_used}MiB / ${mem_total}MiB"
|
||
}
|
||
|
||
get_ascii() {
|
||
case $os in
|
||
linux)
|
||
ascii="\
|
||
${c4} ___
|
||
(${c7}.· ${c4}|
|
||
(${c5}<> ${c4}|
|
||
/ ${c7}__ ${c4}\\
|
||
( ${c3}/ \\ ${c4}/|
|
||
${c5}_${c4}/\\ ${c7}__)${c4}/${c5}_${c4})
|
||
${c5}\/${c4}-____${c5}\/
|
||
"
|
||
;;
|
||
esac
|
||
|
||
# Store the height of the ascii art for cursor positioning.
|
||
# This script prints to the screen *almost* like a TUI does.
|
||
# It uses escape sequences to allow dynamic printing of the
|
||
# information through user configuration.
|
||
ascii_height=$(printf %s "$ascii" | wc -l)
|
||
|
||
# Print the ascii art and position the cursor back where we
|
||
# started prior to printing it.
|
||
# '\033[1m': Print the ascii in bold.
|
||
# '\033[m': Clear bold.
|
||
# '\033[%sA: Move the cursor up '$ascii_height' amount of lines.
|
||
printf '\033[1m%s\033[m\033[%sA' "$ascii" "$ascii_height"
|
||
}
|
||
|
||
main() {
|
||
# Generic color list.
|
||
# Disable warning about unused variables.
|
||
# shellcheck disable=2034
|
||
{
|
||
c1=[31m; c2=[32m
|
||
c3=[33m; c4=[34m
|
||
c5=[35m; c6=[36m
|
||
c7=[37m; c8=[38m
|
||
}
|
||
|
||
# Hide 'stderr' unless the first argument is '-v'. This saves
|
||
# polluting the script with '2>/dev/null'.
|
||
[ "$1" = -v ] || exec 2>/dev/null
|
||
|
||
# Store the output of 'uname' to avoid calling it multiple times
|
||
# throughout the script. 'read <<EOF' is the simplest way of reading
|
||
# a command into a list of variables.
|
||
read -r kernel_name kernel_version <<EOF
|
||
$(uname -sr)
|
||
EOF
|
||
|
||
get_os
|
||
get_ascii
|
||
get_title
|
||
get_distro
|
||
get_kernel
|
||
get_uptime
|
||
get_memory
|
||
|
||
# Position the cursor below both the ascii art and information lines.
|
||
# 'log' contains the amount of 'get_' info lines that were printed.
|
||
# '\033[%sB': Move the cursor down N lines.
|
||
printf '\033[%sB\n' "$((ascii_height - log))"
|
||
}
|
||
|
||
main "$@"
|