Skip to content
Permalink
Branch: master
Find file Copy path
Find file Copy path
Fetching contributors…
Cannot retrieve contributors at this time
executable file 350 lines (297 sloc) 9.72 KB
#!/bin/sh
# vim: ft=sh sw=3 ts=3 sts=3 et ai tw=76 :
main() {
local md="$(dirname "$0")"
. "$md/../lib.sh"
local src_dir cache_dir env_dir work_dir
parse_opts "$@"
mkdir -p "$cache_dir"
[ -n "$HOME" -a -w "$HOME" ] || export HOME=/tmp
# fail fast, fail hard, possibly loud
set -e
if [ "x$DIBSPACK_VERBOSE" = "x1" ] ; then
set -x -v
__main_print_dibspack_details
fi
[ "x$work_dir" = "x$src_dir" ] \
|| [ -e "$work_dir" ] \
|| ln -s "$src_dir" "$work_dir"
export PATH="$md:$work_dir/local/bin:$work_dir/local/perl/bin:$PATH"
export PERL5LIB="$work_dir/local/lib/perl5:$PERL5LIB"
# do real build
copy_local "$cache_dir" "$work_dir"
build "$work_dir"
copy_local "$work_dir" "$cache_dir"
post_build "$work_dir" "$src_dir"
[ -z "$DIBSPACK_SAVE_ENV" ] \
|| save_build_environment "$work_dir" "$DIBSPACK_SAVE_ENV"
printf '%s\n' build_complete
}
parse_opts() {
export_all_enviles
src_dir="$DIBS_DIR_SRC"
cache_dir="$DIBS_DIR_CACHE/perl"
env_dir="$DIBS_DIR_ENV"
work_dir="${DIBSPACK_WORK_DIR:-"$src_dir"}"
local optname optval
while [ "$#" -gt 0 ] ; do
optname="$1"
shift
case "$optname" in
(--cpanm-test)
DIBSPACK_CPANM_TEST='' # does not set "--notest"
;;
(--cpanm-verbose)
DIBSPACK_CPANM_VERBOSE='' # does not set "--quiet"
;;
(-H|--home)
[ "$#" -gt 0 ] || LOGDIE "no value for option $optname"
export HOME="$1"
shift
;;
(--no-cpanm-test)
DIBSPACK_CPANM_TEST='--notest'
;;
(--no-cpanm-verbose)
DIBSPACK_CPANM_VERBOSE='--quiet'
;;
(--no-verbose)
DIBSPACK_VERBOSE=0
DIBSPACK_CPANM_VERBOSE='--quiet'
;;
(--save-env)
[ "$#" -gt 0 ] || LOGDIE "no value for option $optname"
DIBSPACK_SAVE_ENV="$1"
shift
;;
(--verbose)
DIBSPACK_VERBOSE=1
DIBSPACK_CPANM_VERBOSE='--quiet'
;;
(-V|--set-version)
[ "$#" -gt 0 ] || LOGDIE "no value for option $optname"
DIBSPACK_SET_VERSION="$1"
shift
;;
(-w|--work-dir)
[ "$#" -gt 0 ] || LOGDIE "no value for option $optname"
work_dir="$1"
shift
;;
(*)
LOGDIE "unhandled option $optname"
;;
esac
done
}
post_build() {
local work_dir="$1" src_dir="$2" pbf="$1/.post_build"
prepare_run_environment "$work_dir" "$src_dir"
if [[ -f "$pbf" ]] && [[ -x "$pbf" ]] ; then
INFO "Executing post-build operation"
"$pbf" "$@"
fi
}
prepare_run_environment() {
local profile_dir="$1/.profile.d"
local src_dir="$2"
mkdir -p "$profile_dir"
# $APPHOME/local/perl/bin is always added, it might be missing but
# no harm done
cat >"$profile_dir/10.perl-env.sh" <<'END'
: ${APPHOME:="/app"}
export PATH="$APPHOME/bin:$APPHOME/local/bin:$APPHOME/local/perl/bin:$PATH"
export PERL5LIB="$APPHOME/lib:$APPHOME/local/lib/perl5:$PERL5LIB"
END
{
# this is not really needed because DIBS_ID will eventually survive
# inside container anyway
printf 'export DIBS_ID=%s\n' "$(escape_var_value "$DIBS_ID")"
# if the version is set from outside, it's with this env var
[ -n "$DIBSPACK_SET_VERSION" ] && printf 'export VERSION=%s\n' \
"$(escape_var_value "$DIBSPACK_SET_VERSION")"
# if we're inside a git repo, save the sha digest. FIXME needs more
# care for dirty state checking etc.
if type -a git >/dev/null 2>&1 ; then
(
# "localize" change of directory
cd "$src_dir"
local sha="$(git rev-parse --short HEAD 2>/dev/null || true)"
[ -n "$sha" ] && printf 'export GIT_REF=%s\n' \
"$(escape_var_value "$sha")"
)
fi
} >"$profile_dir/20.version-env.sh"
return 0
}
copy_local() {
local src="$1"
local dst="$2"
rm -rf "$dst/local"
[ ! -d "$src/local" ] || cp -pPR "$src/local" "$dst"
}
build() {
local src_dir="$1"
(
cd "$src_dir"
mkdir -p local
__build_install_perl
__build_install_dependencies
if [ -d "script" ] ; then
mkdir -p bin
cp script/* bin
fi
)
}
########################################################################
__build_install_perl() {
local flag_file='.perl-archive'
# revert to system perl if no custom one is requested
if [ ! -r "$flag_file" ] ; then
[ -d local/perl ] && __build_install_perl_restore_system_perl
return 0
fi
# if the requested perl did not change... do nothing
local local_flag_file='local/.perl-archive'
if diff >/dev/null 2>&1 "$flag_file" "$local_flag_file" ; then
INFO keeping previous perl
return 0
fi
# remove any previous custom perl, we have to change it anyway
__build_install_perl_restore_system_perl
# download and extract new one
local url="$(cat .perl-archive)"
printf '%s\n' "getting perl from $url"
curl -s -L "$url" | tar xzf -
# move to target place, then make hash-bangs general
local archive="${url##*/}"
local version="${archive%.tar*}"
printf '%s\n' "archive is '$archive', extracted directory '$version'"
mv "$version" 'local/perl'
__perl_script_relocate 'local/perl/bin'/*
# save flag file for comparison in next build
cp "$flag_file" "$local_flag_file"
}
__build_install_perl_restore_system_perl() {
printf '%s\n' 'restoring system perl'
rm -rf local/{bin,lib,perl}
}
__perl_script_relocate() {
local f
for f in "$@" ; do
perl -i -ple 's{^#!.*perl\s*$}{#!/usr/bin/env perl} if $. == 1' "$f"
done
}
########################################################################
__build_install_dependencies() {
local save_epan="$epan"
local epan="$save_epan"
# epan dirs in "$@", sweep possible DarkPAN candidates and add them
local _d d
for _d in epan dpan ; do
d="$PWD/$_d"
[ -d "$d" ] || continue
epan="$epan --mirror $(encode_array_sed "file://$d")"
done
# if something was actually found, insist on using mirrors only
# and make sure www.cpan.org is present but at the end, so that it
# can be overridden
if [ -n "$epan" ] ; then
# append "usual" mirrors and use mirrors for index
epan="$epan --mirror http://www.cpan.org --mirror-only"
fi
# do stuff from gitpan first, because it's not in the records or
# has to override stuff in the records
[ -e gitpanfile ] && __build_install_dependencies_gitpanm
# proceed with regular stuff
if [ -e cpanfile.snapshot ] ; then
__build_install_dependencies_carton
else
# use cpanm, possibly taking array EPAN in consideration
__build_install_dependencies_cpanm --installdeps .
fi
}
__build_install_dependencies_gitpanm() {
printf '%s\n' "detected gitpanfile"
local gpm_dir="$src_dir/local/gitpanm"
mkdir -p "$gpm_dir"
# iterate through gitpanfile, one line at a time
cat gitpanfile | while read -r name repo commit ; do
# skip entries that make no sense
[ -z "${name%#*}" ] && continue # empty or comment lines
# "while" subshell here, changing directory remains localized yay!
cd "$gpm_dir"
INFO "gitpanfile -> $name $repo $commit"
[ -d "$name" ] || git clone "$repo" "$name"
cd "$name"
git fetch
if [ -n "$commit" ] ; then
git checkout "$commit"
else
git pull origin "$(git rev-parse --abbrev-ref HEAD)"
fi
# recurse for installing this repo's dependencies
__build_install_dependencies
# install the very library
cd "$gpm_dir"
__build_install_dependencies_cpanm "./$name"
done
}
__fail_cpanm_log() {
cat "$HOME"/.cpanm/build.log | sed 's/^/cpanm build.log> /'
false
}
__build_install_dependencies_carton() {
local carton=carton
local private_carton='vendor/bin/carton'
[ -x "$private_carton" ] && carton="$private_carton"
local params='install --deployment'
[ -d 'vendor/cache' ] && params="$params --cached"
# if we're recurring, chances are that carton will try to install
# stuff in the wrong place, so we have to attempt something
if [[ "$(readlink -f "$src_dir")" != "$(readlink -f '.')" ]] ; then
# try to make "local" point to the *right* local, or cross fingers
[ -e local ] || ln -s "$src_dir/local"
fi
"$carton" $params || __fail_cpanm_log
}
__build_install_dependencies_cpanm() {
local cpanm=cpanm
local private_cpanm='vendor/bin/cpanm'
[ -x "$private_cpanm" ] && cpanm="$private_cpanm"
# now do the actual installation heavylifting
"$cpanm" \
--no-man-pages \
--no-wget \
$CPANM_OPTS \
${DIBSPACK_CPANM_VERBOSE-"--quiet"} \
${DIBSPACK_CPANM_TEST-"--notest"} \
-l "$src_dir/local" \
$epan \
"$@" \
|| __fail_cpanm_log
}
########################################################################
__main_print_dibspack_details() {
printf '%s\n' "environment (sorted)"
env | sort
printf '%s\n' ''
printf '%s\n' "src_dir [$src_dir]"
ls -l "$src_dir"
printf '%s\n' "cache_dir [$cache_dir]"
ls -l "$cache_dir"
printf '%s\n' "env_dir [$env_dir]"
ls -l "$env_dir"
}
save_build_environment() {
local src_dir="$1"
local target="$2"
[ "x${target%${target#?}}" = 'x/' ] || target='/.build_env'
TARGET="$src_dir$target"
mkdir -p "$target"
env > "$target/env.sh"
set > "$target/set.sh"
}
exec 1>&2
main "$@"
exit "$?"
You can’t perform that action at this time.