#!/bin/sh
# 2005-2006, 2009 (c) Etersoft www.etersoft.ru
# Author: Vitaly Lipatov <lav@etersoft.ru>
# Public domain
#
# GS - get source
#
# Скачивает исходники, автоматически выправляя ситуацию с gz/bz2/tgz/zip (tar для git, tar.bz2 для src.rpm)
# Параметры:
# - название спек-файла
# -a - get all source
# check for the same file with other compression

# load common functions, compatible with local and installed script
. `dirname $0`/../share/eterbuild/functions/common
load_mod rpm tarball web

WEXT=""
GETSOURCE=""
LOADLIST="0"

#############################
Usage="Usage: $name [GIRAR] [-a -r ] spec [new_version]"
function mygetopts()
{
name=${0##*/}
Descr="$name - get sources by spec / repository"

phelp()
{
	echog "$Descr"
	echog "$Usage"
	echog "You can run 'rpmgs file.spec new_version' for set new version and download it"
	echog "Options:"
	echog " -a - get all source (not only Source|Source0)"
	echog " -f - force download (remove source before download)"
}

while getopts :haf opt; do
    case $opt in
    h) phelp; exit 0;;
    a) LOADLIST=" 0 1 2 3 4 5 6 7 8" ;;
    f) FORCEDOWNLOAD=-f ;;
    +?) echog "$name: options should not be preceded by a '+'." 1>&2; exit 2;;
    ?)  echog "$name: $OPTARG: bad option.  Use -h for help." 1>&2 ; exit 2;;
    esac
done
 
# remove args that were options
shift $((OPTIND - 1))

LISTRPMARGS=$@

}

# supports only .tar.bz2 or .tar files in SOURCE
get_archive()
{
	URL=${GETSOURCE/.bz2/}
	URL=${URL/.tar/}
	WEXT=`basename "$URL"`
	[ -n "$FORCEDOWNLOAD" ] && rm -f "$WEXT.$1"
	test -f "$WEXT.$1" && echog "$WEXT.$1 already exists" && return
	download_url "$URL.$1" || return
	test -f "$WEXT.$1" || return
	[ "$1" = "tar.bz2" ] || echog -n "Converting to $WEXT.tar..."
}

# supports only bz2
get_archive1()
{
	URL=${GETSOURCE/.bz2/}
	WEXT=`basename "$URL"`
	test -f "$WEXT.$1" download_url "$URL.$1" || return
	test -f "$WEXT.$1" || return
	echog -n "Converting to $WEXT.bz2..."
}

#TODO: use functions from tarball
get_tarbz2()
{
	get_archive tar.bz2 || return
	bunzip -t $WEXT.tar.bz2 && return
	rm -fv $WEXT.tar.bz2
	return 1
}

get_bz2()
{
	get_archive1 bz2 || return
	bunzip -t $WEXT.bz2 && return
	rm -fv $WEXT.bz2
	return 1
}

function get_gz()
{
	get_archive1 gz || return
	gunzip -f $WEXT.gz && return
	rm -fv $WEXT.gz
	return 1
}

function get_raw()
{
	download_url "$GETSOURCE"
	WEXT=`basename $GETSOURCE`
	test -f "$WEXT"
}


function get_targz()
{
	get_archive tar.gz || return
	gunzip -f $WEXT.tar.gz && return
	rm -fv $WEXT.tar.gz
	return 1
}

function get_tarxz()
{
	BIN7ZIP=/usr/bin/7z
	test -x $BIN7ZIP || return
	get_archive tar.xz || return
	$BIN7ZIP x $WEXT.tar.xz && return
	rm -fv $WEXT.tar.xz
	return 1
}

function get_tar()
{
	get_archive tar || return
	test -f $WEXT.tar
}

function get_tgz()
{
	get_archive tgz || return
	gunzip -f $WEXT.tgz && return
	rm -fv $WEXT.tgz
	return 1
}

function get_tbz2()
{
	get_archive tbz2 || return
	mv -f $WEXT.tbz2 $WEXT.tar.bz2
	bunzip -t $WEXT.tar.bz2 && return
	rm -fv $WEXT.tar.bz2
	return 1
}

function get_tbz()
{
	get_archive tbz || return
	mv -f $WEXT.tbz $WEXT.tar.bz2
	bunzip -t $WEXT.tar.bz2 && return
	rm -fv $WEXT.tar.bz2
	return 1
}

# TODO: use external converter
function get_zip()
{
	get_archive zip || return
	mkdir $WEXT.zip.dir || return
	cd $WEXT.zip.dir
	unzip -q ../$WEXT.zip && tar cf ../$WEXT.tar ./* || { rm -fv $WEXT.zip ; return 1; }
	cd ..
	rm -rf $WEXT.zip.dir
}

# TODO: use external converter
function get_rar()
{
	UNRAR=/usr/bin/unrar
	test -x $UNRAR || return
	get_archive rar || return
	mkdir $WEXT.rar.dir || return
	cd $WEXT.rar.dir
	$UNRAR x ../$WEXT.rar && tar cf ../$WEXT.tar ./* || { rm -fv $WEXT.rar ; return 1; }
	cd ..
	rm -rf $WEXT.rar.dir
}

# TODO: use external converter
function get_7z()
{
	BIN7ZIP=/usr/bin/7z
	test -x $BIN7ZIP || return
	get_archive 7z || return
	mkdir $WEXT.7z.dir || return
	cd $WEXT.7z.dir
	$BIN7ZIP x ../$WEXT.7z && tar cf ../$WEXT.tar ./* || { rm -fv $WEXT.7z ; return 1; }
	cd ..
	rm -rf $WEXT.7z.dir
}

function dir_name()
{
	rm .listing
	#wget `dirname $MAINSOURCE` --dont-remove-listing
	
}

function get_source()
{
	GETSOURCE=$(eval_spec $1 | get_var "$2")
}

# download GETSOURCE url to tar.bz2 or tar (set WEXT as without extension name)
download_any_tarball()
{
	get_tarbz2 || get_targz || get_tgz || get_7z || get_zip || get_tbz2 || get_tbz || get_tar || get_tarxz || get_rar || dir_name || fatal "Cannot retrieve $GETSOURCE"
}

# param: spec name number (f.i., url for Source-url)
function source_ext()
{
	local GETSOURCEEXT=
	# %define SourceUrl ftp://updates.etersoft.ru/pub/Etersoft/WINE@Etersoft/last/sources/tarball/%name-%version.tar.gz
	#GETSOURCEURL=$(eval_spec $1 | grep -i "^%define ${2}Url${3} " | head -n 1 | sed -e "s/ *\$//g" | sed -e "s/^%define[ \t].*[ \t]//g")
	if grep -q "# Source$3-$2:" "$1" ; then
		local TMPSPEC=$1.tmpurl
		local NEWSOURCE=$(grep "# Source$3-$2:" "$1" | sed -e "s/.*$2:[ \t]*//g")
		test -n "$NEWSOURCE" || fatal "Can't extract URL from $Source$3-$2"
		cat $1 | sed -e "s|^Summary:.*|Summary: $NEWSOURCE|g" > $TMPSPEC
		GETSOURCEEXT=$(eval_spec "$TMPSPEC" | get_var "Summary")
		rm -f "$TMPSPEC"
	fi
	echo "$GETSOURCEEXT"
	test -n "$GETSOURCEEXT"
}


# Source-svn: http://svn.wikimedia.org/svnroot/mediawiki/trunk/extensions/Collection/
function get_source_svn()
{
	GETSOURCESVN=$(source_ext "$1" svn "$2")
	#if [ -n "$GETSOURCESVN" ] ; then
	#	warning "Source-svn is not supported yet"
	#	( cd $SPECDIR ; git svn clone $GETSOURCESVN .)
	#fi
	#test -n "$GETSOURCESVN"
}


# Source-git: http://git.altlinux.org/people/lav/packages/rpm-build-fonts.git
function get_source_git()
{
	fatal "realize me"
}

# Source-url: ftp://updates.etersoft.ru/pub/Etersoft/WINE@Etersoft/last/sources/tarball/%name-%version.tar.gz
# Get real Url from comment
function get_source_url()
{
	GETSOURCEURL=$(source_ext "$1" url "$2")
}

function print_error()
{
	echog "You have no spec files as arg"
	echog "Please use for spec files only. If you wish to download src.rpm, use rpmgp script."
	exit 1
}

# tarball dirname [options]
gear_update_from_tarball()
{
	local CREATEFLAG=
	local TARBALL="$1"
	local CURNAME="$2"
	shift 2
	[ -d "$CURNAME" ] || CREATEFLAG=-c
	# TODO: check tarball ext. for unsupported arch and realize it here or in gear-update
	echo "Commit tarball '$TARBALL' to git subdir '$CURNAME'..."
	if ! gear-update $CREATEFLAG $@ "$TARBALL" "$CURNAME" ; then
		if gear-update $CREATEFLAG $@ "$TARBALL" "$CURNAME" 2>&1 | grep -q "More than one subdirectory specified" ; then
			echo "Try unpack as is"
			CREATEFLAG="$CREATEFLAG -a"
			gear-update $CREATEFLAG $@ "$TARBALL" "$CURNAME" && return
		fi
	else
		return 0
	fi
	fatal "can't import tarball '$TARBALL'"
}

parse_cmd_pre_spec "$@"
mygetopts $LISTARGS

test -z "$VERBOSE" || echo "'$LISTNAMES' @ '$LISTRPMARGS'"

if [ -n "$LISTRPMARGS" ] ; then
	if [ -z "${LISTRPMARGS/*spec/}" ] ; then
		fatal "run with incorrect filename $LISTRPMARGS"
	fi
	if [ ! -f "$LISTNAMES" ] ; then
		fatal "set version permitted only for one file"
	fi
	if [ "${LISTRPMARGS/ /}" != "$LISTRPMARGS" ] ; then
		fatal "you run rpmgs with more than one version"
	fi
	GSSETVERSION=$LISTRPMARGS
fi

test -z "$LISTNAMES" && print_error

[ -z "$GSSETRELEASE" ] || GSSKIPADDCHANGELOG=1

for i in $LISTNAMES
do
	if [ -n "${i/*spec/}" ] ; then
		print_error
	fi
	
	set_specdir $i

	# Set version if needed
	if [ -n "$GSSETVERSION" ] ; then
		CURVER=$(get_version $i)
		set_version $i $GSSETVERSION
		if [ "$CURVER" != "$GSSETVERSION" ] ; then
			[ -n "$GSSETRELEASE" ] || GSSETRELEASE=alt1
			set_release $i $GSSETRELEASE
			echo "Set new $GSSETVERSION-$GSSETRELEASE version for $i"
		else
			echo "Version $GSSETVERSION already set"
			GSSKIPADDCHANGELOG=1
		fi
	fi

	for nn in "" $LOADLIST
	do
		get_source $i "Source$nn"
		[ "$GETSOURCE$nn" = "0" ] && continue
		test -z "$GETSOURCE" && { echog "Skip Source${nn} from $i" ; continue ; }
		FTB=`basename "$GETSOURCE"`
		# for get RPMSOURCEDIR
		build_rpms_name $i

		[ -n "$FORCEDOWNLOAD" ] && rm -f "$RPMSOURCEDIR/$FTB"
		[ -f "$RPMSOURCEDIR/$FTB" ] && { echog "Tarball $FTB already exists in $RPMSOURCEDIR dir, skipping." ; continue ; }

		mkdir -p $RPMSOURCEDIR/ && pushd $RPMSOURCEDIR/ || fatal "Can't create/chdir..."

		# Test for eterbuild extensions
		get_source_url $i $nn || get_source_svn $i $nn

		if [ -n "${GETSOURCESVN}" ] ; then
			is_gear $SPECDIR || fatal "Source-svn works only with gear repo"
		elif is_gear $SPECDIR; then
			echog "Try to load ${GETSOURCEURL:-$GETSOURCE} for $i"
			if [ -n "${GETSOURCE/*.tar/}" ] ; then
				warning "It is recommended to use .tar tarballs for sources in gear"
			fi
			# TODO: rewrite code to use original file format and temp. download dir
			if [ -n "${GETSOURCEURL}" ] ; then
				# UpUrl for gear
				download_url "$GETSOURCEURL"
				# FIXME: gear-update can use any tarball
				copy_tarball_to_tar $(basename "$GETSOURCEURL") $FTB
			elif [ -z "${GETSOURCE/*.tar/}" ] ; then
				# tar target: try to load and convert
				download_any_tarball
				test -f $WEXT.tar.bz2 && FTB=$WEXT.tar.bz2
			elif [ -z "${GETSOURCE/*.tar.bz2/}" ] ; then
				# tar.bz2 target: for src.rpm policy compatibility
				download_any_tarball 
				test -f $WEXT.tar.bz2 || bzipit $WEXT.tar || fatal "Cannot bzip $WEXT.tar"
			else
				download_url "$GETSOURCE"
			fi
		else
			[ -z "${GETSOURCEURL}" ] || fatal "Source git works only with gear repo"
			echog "Try to load ${GETSOURCEURL:-$GETSOURCE} for $i"
			if [ -n "${GETSOURCE/*.bz2/}" ] ; then
				warning "It is recommended to use .bz2 tarballs for sources in rpm"
			fi
			if [ -n "${GETSOURCEURL}" ] ; then
				# UpUrl for rpm
				download_url "$GETSOURCEURL"
				copy_tarball_to_tar_bz2 $(basename "$GETSOURCEURL") $FTB
			elif [ -n "${GETSOURCE/*.tar.bz2/}" ] ; then
				# if not tar.bz2 target, direct download
				download_url "$GETSOURCE"
			elif [ -z "${GETSOURCE/*.tar.bz2/}" ] ; then
				# if tar.bz2 target
				download_any_tarball
				#echog -n "Compressing to $WEXT.tar.bz2..."
				test -f $WEXT.tar.bz2 || bzipit $WEXT.tar || fatal "Cannot bzip $WEXT.tar"
			elif [ -z "${GETSOURCE/*.bz2/}" ] ; then
				warning "It is not tarball (possible single file)..."
				get_bz2 || get_gz || get_raw || fatal "Cannot retrieve $GETSOURCE"
			else
				fatal "Logical error with $GETSOURCE"
			fi
		fi

		echo "DONE"
		popd

	done

	if [ -z "$GSSKIPADDCHANGELOG" ] ; then
		# Write changelog if all done
		CURVER=$(get_version $i)
		CURREL=$(get_release $i)
		EGEARME=""
		is_gear && EGEARME=" import in git"
		add_changelog_helper "- new version ($CURVER)$EGEARME" $i || echog "Changelog entry for $CURVER-$CURREL already exists"
	fi

	if [ -n "$GSSETVERSION" ] || [ -n "$FORCEDOWNLOAD" ]; then
		if [ -n "${GETSOURCESVN}" ] ; then
			# clone svn repo to current dir
			# FIXME: need to clone in git root dir
			GITROOT=.
			[ $(basename `pwd`) = ".gear" ] && GITROOT=../
			git svn clone $GETSOURCESVN $GITROOT
			echo "Run svn rebase from $GETSOURCESVN"
			git svn rebase
		elif is_gear ; then
			CURNAME=$BASENAME
			test -d "$CURNAME" || CURNAME=$(get_tarballname "$i")
			gear_update_from_tarball "$RPMSOURCEDIR/$FTB" "$CURNAME" $FORCEDOWNLOAD
			rm -f "$RPMSOURCEDIR/$FTB"
			git commit -m "just import $FTB with rpmgs script"
		fi
	else
		is_gear && echo "Skip tarball committing (run with version or with -f option)."
	fi
done

exit 0

