#!/usr/bin/env bash # # Portimg uses Crux port-like system for creating software deployment images. # Copyright (C) 2016 Aaron Ball # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # set -eu export BASEDIR="$(cd $(dirname ${0})/../ && pwd)" export LIBDIR="${BASEDIR}/lib" export BINDIR="${BASEDIR}/bin" source ${LIBDIR}/log.sh source ${LIBDIR}/pkg.sh source ${LIBDIR}/common.sh export PORTSDIR=${PORTSDIR:-${BASEDIR}/ports} export KEEP_BUILD=${KEEP_BUILD:-0} usage() { printf " Pkgimg is a wrapper script for a simple ports system build process. The ports system provides build instructions for individual packages/ports. The pkgimg script will build multiple ports into the same working directory, creating a composite port package image. Usage: pkgimg.sh [-c addtional_configs] Arguments: -h,--help Print this help text -c,--config Import additional configs file (shell syntax) " } img_mkpkg() { local _imgname=${1:-} local _imgversion=${2:-} local _imgrelease=${3:-} local _imgsrc=${4:-} local _imgbuildname _imgbuildname="${_imgname}#${_imgversion}_${_imgrelease}" linfo "Generating footprint file for ${_imgname}" footprint_dir ${_imgsrc} > ${BASEDIR}/${_imgbuildname}.footprint linfo "Creating deployment tarball from ${_imgsrc}" tar -cf ${BASEDIR}/${_imgbuildname}.tar -C ${_imgsrc} . linfo "Compressing ${_imgname}.tar" xz -v ${BASEDIR}/${_imgbuildname}.tar # linfo "Build dir: ${_dest}" # linfo "Deployment tarball: ${BASEDIR}/${_imgbuildname}.tar.xz" # linfo "Tarball footprint: ${BASEDIR}/${_imgbuildname}.footprint" } build_manifest() { local _manifest=${1:-} local _installbase=${2:-} local _porttmp # Path to the temporary package working directory # Port image variables local _imgname # Name of the image/port collection local _imgdepends # Dependencies to build the port image local _imgversion # Version of the image local _imgrelease # Release number of the image local _imgbuildname # Name of the built image file if [[ -z "${_manifest}" ]]; then lerror "Please specify a port manifest." return 1 fi if [[ ! -f "${_manifest}" ]]; then lerror "Path '${manifest}' does not exist or is not a manifest" return 2 fi source ${_manifest} # Set all these variables as the same variables will be set later by port # files _imgname=${name} && unset 'name' _imgdepends=("${depends[@]}") && unset 'depends[@]' _imgversion=${version} && unset 'version' _imgrelease=${release} && unset 'release' _imgbuildname="${_imgname}#${_imgversion}_${_imgrelease}" _installbase="$(mktemp -d /tmp/pkgimg-${_imgbuildname}.XXXX)" # Loop over each port in the manifest for port in ${_imgdepends[@]}; do # Build the package ${BINDIR}/pkgmk.sh ${port} [ $? -gt 0 ] && return 1 # Install the package to the image install base ${BINDIR}/pkgadd.sh "${port}" "${_installbase}" [ $? -gt 0 ] && return 1 done # Assemble the package composite img_mkpkg "${_imgname}" "${_imgversion}" "${_imgrelease}" "${_installbase}" } function main { local argv=(${@}) local i=0 local _configs=() # List of config files to load local _config # Single config file to include local _installbase # Path to the temporary image working directory local _manifest # Manifest file to compile for (( i=0; i < ${#argv[@]}; i++ )); do if [ ${argv[$i]} == '-c' ] || [ ${argv[$i]} == '--config' ]; then i=$(( i + 1 )) _configs+=(${argv[$i]}) elif [ -f ${argv[$i]} ]; then # If no switch was detected at this argument index, test to see if a # manifest file exists at argument path. If so, assume it is a manifest # file _manifest="${argv[$i]}" elif [ ${argv[$i]} == '-h' ] || [ ${argv[$i]} == '--help' ]; then usage return 0 else printf "No arguments specified (for help, run with -h,--help).\n" return 1 fi done # Ensure a manifest file was specified if [ -z "${_manifest:-}" ]; then printf "No manifest file specified.\n" return 1 fi for _config in ${_configs[@]}; do if [ -f ${_config} ]; then source ${_config} continue fi printf "Could not find or access config '%s'\n" "${_config}" return 2 done # Convert portsdir to absolute path PORTSDIR="$(cd ${PORTSDIR} && pwd)" build_manifest "${_manifest}" } main ${@}