Files
config/users/pbsds/home/profiles/bashrc.d/nix-shell.sh
T
2025-03-16 00:30:34 +01:00

136 lines
4.3 KiB
Bash

_ns() {
local is_dev=$1; shift # "true" or "false"
if $is_dev; then
local arg_suffix="^*"
else
local arg_suffix=""
fi
local args=()
for pkg in "$@"; do
if [[ "$pkg" = -- ]]; then
break
fi
if [[ "$pkg" =~ ^.*[#:/].*$ ]]; then
args+=("${pkg}${arg_suffix}")
else
args+=(nixpkgs#"${pkg}${arg_suffix}")
fi
done
# Run anything after -- as a command
local cmd=("$@")
while [[ "${#cmd[@]}" -gt 1 && "${cmd[0]}" != "--" ]]; do
cmd=("${cmd[@]:1}")
done
cmd=("${cmd[@]:1}")
if [[ ${#cmd[@]} -gt 0 ]]; then
(
_ns "$is_dev" "${args[@]}"
set -x
"${cmd[@]}"
)
return $?
fi
# echo current shell
# >&2 echo -n + exec nix shell
>&2 echo -n + ns
if [[ -v _PREVIOUS_NS_ARGS ]]; then
>&2 echo -n " ${_PREVIOUS_NS_ARGS:-}"
fi
>&2 printf " %q" "${args[@]}"
>&2 echo
if [[ "${#args[@]}" -eq 0 ]]; then
return
fi
local outpaths="$(
export NIXPKGS_ALLOW_BROKEN
export NIXPKGS_ALLOW_UNSUPPORTED_SYSTEM
export NIXPKGS_ALLOW_UNFREE
export NIXPKGS_ALLOW_INSECURE
nix --extra-experimental-features "nix-command flakes" build --impure "${args[@]}" --print-out-paths --no-link
)"
if [[ $? -ne 0 || -z "$outpaths" ]]; then
return
fi
local -a storepaths_native=()
local -a storepaths_build=()
readarray -d $'\n' -t storepaths_native <<<"$outpaths"
readarray -d $'\n' -t storepaths_build <<<"$outpaths"
# traverse propagated inputs
# this is safe since the store paths form a DAG
# TODO: rethink native logic
local -i idx=-1
while [[ $((++idx)) -lt "${#storepaths_native[@]}" ]]; do
if [[ -f "${storepaths_native[$idx]}"/nix-support/propagated-native-build-inputs ]]; then
storepaths_native+=($(cat "${storepaths_native[$idx]}"/nix-support/propagated-native-build-inputs))
fi
# TODO: needed?
if [[ -f "${storepaths_native[$idx]}"/nix-support/propagated-build-inputs ]]; then
storepaths_build+=($(cat "${storepaths_native[$idx]}"/nix-support/propagated-build-inputs))
fi
done
local -i idx=-1
while [[ $((++idx)) -lt "${#storepaths_build[@]}" ]]; do
if [[ -f "${storepaths_build[$idx]}"/nix-support/propagated-build-inputs ]]; then
storepaths_build+=($(cat "${storepaths_build[$idx]}"/nix-support/propagated-build-inputs))
fi
done
# find things to add to env
local -A seen=()
# for storepath in "${storepaths_native[@]}"; do
for storepath in "${storepaths_build[@]}"; do
if [[ -v seen["$storepath"] ]]; then
continue
fi
seen["$storepath"]=1
if [[ -d "$storepath/bin" ]]; then
export PATH="$storepath/bin${PATH:+":$PATH"}"
fi
if >/dev/null compgen -G "$storepath/lib/*.so*"; then
export LDPATH="-L$storepath/lib${LDPATH:+" $LDPATH"}"
export LD_LIBRARY_PATH="$storepath/lib${LD_LIBRARY_PATH:+":$LD_LIBRARY_PATH"}"
export CMAKE_LIBRARY_PATH="$storepath/lib${CMAKE_LIBRARY_PATH:+":$CMAKE_LIBRARY_PATH"}"
fi
if [[ -d "$storepath/lib/pkgconfig" ]]; then
export PKG_CONFIG_PATH="$storepath/lib/pkgconfig${PKG_CONFIG_PATH:+":$PKG_CONFIG_PATH"}"
fi
if [[ -d "$storepath/share" ]]; then
export XDG_DATA_DIRS="$storepath/share${XDG_DATA_DIRS:+":$XDG_DATA_DIRS"}"
fi
if [[ -d "$storepath/share/man" ]]; then
export MANPATH="$storepath/share/man${MANPATH:+":$MANPATH"}"
fi
if [[ -d "$storepath/share/pkgconfig" ]]; then
export PKG_CONFIG_PATH="$storepath/share/pkgconfig${PKG_CONFIG_PATH:+":$PKG_CONFIG_PATH"}"
fi
if [[ -d "$storepath/lib/pkgconfig" ]]; then
export PKG_CONFIG_PATH="$storepath/lib/pkgconfig${PKG_CONFIG_PATH:+":$PKG_CONFIG_PATH"}"
fi
if [[ -d "$storepath/include" ]]; then
export CPATH="$storepath/include${CPATH:+":$CPATH"}"
export CMAKE_INCLUDE_PATH="$storepath/include${CMAKE_INCLUDE_PATH:+":$CMAKE_INCLUDE_PATH"}"
fi
if >/dev/null compgen -G "$storepath/lib/python*/site-packages"; then
export PYTHONPATH="$(IFS=: ; printf "%s" "$storepath"/lib/python*/site-packages)${PYTHONPATH:+":$PYTHONPATH"}"
# export PYTHONNOUSERSITE=1
fi
done
if [[ -v _PREVIOUS_NS_ARGS ]]; then
export _PREVIOUS_NS_ARGS="$_PREVIOUS_NS_ARGS$(printf " %q" "${args[@]}")"
else
export _PREVIOUS_NS_ARGS="$(printf " %q" "${args[@]}" | cut -c2-)"
fi
}
ns() { _ns false "$@"; }
nd() { _ns true "$@"; }