#!/bin/sh

set -eu

# bin/plx-packed is a committed release artifact.  Its bundled dependency
# versions live in maint/fatpack-cpanfile; this script installs those into an
# isolated, temporary toolchain before rebuilding the artifact.
project_dir=$(CDPATH='' cd -- "$(dirname -- "$0")/.." && pwd)
build_dir="${project_dir}/packbuild"
toolchain_dir="${build_dir}/toolchain"
toolchain_lib="${toolchain_dir}/lib/perl5"
packed_file="${project_dir}/bin/plx-packed"
packed_temp="${packed_file}.new"
bootstrap_cpanm=${CPANM:-}

if [ -z "$bootstrap_cpanm" ]; then
  bootstrap_cpanm=$(command -v cpanm || :)
fi
if [ -z "$bootstrap_cpanm" ]; then
  echo "maint/buildpack requires cpanm (or set CPANM)" >&2
  exit 1
fi

rm -rf "$build_dir"
trap 'rm -rf "$build_dir" "$packed_temp"' EXIT HUP INT TERM

mkdir -p "$build_dir"
PERL_CPANM_HOME="${build_dir}/cpanm-home" "$bootstrap_cpanm" \
  --quiet --notest -L "$toolchain_dir" \
  --cpanfile "${project_dir}/maint/fatpack-cpanfile" --installdeps "$project_dir"

mkdir -p "${build_dir}/fatlib/local"
cp "${toolchain_lib}/local/lib.pm" "${build_dir}/fatlib/local/"
mkdir -p "${build_dir}/fatlib/File"
cp "${toolchain_lib}/File/Which.pm" "${build_dir}/fatlib/File/"


fragment () {
  PATH="${toolchain_dir}/bin:${PATH}" PERL5LIB="$toolchain_lib" perl -e '
  use File::Which;
  my $cpanm = do { local (@ARGV, $/) = which("cpanm"); <> };
  $cpanm =~ s/^/  /mg;
  $cpanm =~ s/"--> Working on/"--"."> Working on/;
  (my $out = $ARGV[0]) =~ s/__CPANM__/$cpanm/;
  print $out
' '
BEGIN {
  our $INLINE_CPANM = <<'"'"'CPANM'"'"';
__CPANM__
CPANM
  if (@ARGV and $ARGV[0] eq "--spiner") {
    shift @ARGV;
    my $cpanm = $INLINE_CPANM;
    $cpanm =~ s/^  //mg;
    $cpanm =~ s/\Qunless (caller)/if (1)/;
    warn "Running packed cpanm\n";
    eval $cpanm;
    die $@ if $@;
    exit 0;
  }
}
local *App::plx::find_cpanm = sub {
  return ($0, "--spiner") unless $0 eq "-";
  require File::Temp;
  # the tempfile will get unlinked when the 'local' of this sub vanishes
  use feature 'state';
  state $tempfile = do {
    my $fh = File::Temp->new;
    my $cpanm = $INLINE_CPANM;
    $cpanm =~ s/^  //mg;
    print $fh $cpanm;
    close $fh;
    $fh;
  };
  return ($tempfile->filename);
};
'

}

(
  echo '#!/usr/bin/env perl';
  cd "$project_dir";
  PERL5LIB="$toolchain_lib" perl -E \
    'require "./bin/plx"; say q{$App::plx::VERSION = }.$App::plx::VERSION.";";'
  (cd "$build_dir"; PATH="${toolchain_dir}/bin:${PATH}" \
    PERL5LIB="$toolchain_lib" fatpack file);
  fragment;
  cat "${project_dir}/bin/plx";
) >"$packed_temp"

chmod --reference="$packed_file" "$packed_temp" 2>/dev/null || chmod 0644 "$packed_temp"
mv "$packed_temp" "$packed_file"
