#!/bin/sh
# $Id: apt-proxy-import,v 1.10 2002/04/04 10:49:39 haggai Exp $
# Import package files from incoming directories
#
# Copyright 2002 Chris Halls <chris.halls@gmx.de>
#                Manuel Estrada Sainz <ranty@debian.org>
#           GPLv2 or higher
#
# Use: apt-proxy-import directory-name ...
#
PROGNAME=apt-proxy-import
VERSION=0.3
CONFIG_FILE=/etc/apt-proxy/apt-proxy.conf
EXACT_MOVING=on
FUZZY_MATCHING="packages fuzzy_packages"
DPKG_NAME=/usr/bin/dpkg-name

usage()
{
  echo "$PROGNAME version $VERSION: import package files into apt-proxy archive"
  echo
  echo "usage: $PROGNAME [-c <config-file>] [-d] <directory> ...."
  echo
  echo -e "\t<directory>      - directory containing files to import."
  echo -e "\t-c <config-file> - location of apt-proxy configuration file"
  echo -e "\t-d		   - verbose"
  echo
  echo "example: $PROGNAME /var/cache/apt/archives"
  echo "$PROGNAME should be run as the aptproxy user, or as root."
  echo
}

line_feedback()
{
	local LINE
	while read LINE
	do
		if [ -n "$VERBOSE" ] ;then
			echo "$LINE"
		else
			echo -n "."
		fi
	done
	echo
}

mirrorpaths_packages()
{
	local filename="$1"
	grep -h "/$filename " $BACKENDS* | cut -f1 -d' ' | uniq
}

mirrorpaths_fuzzy_packages()
{
	local filename="$1"
	local packagename=$(expr $filename : '\([^_]*\)_')
	local rest=$(expr $filename : '[^_]*\(_.*\)$')

	grep -h "/${packagename}_[^ ]*\.deb " $BACKENDS* | cut -f1 -d' ' \
		| uniq | sed -e "s/_[^/]*\.deb/$rest/" 
}

mirrorpaths_deb()
{
	#This funcion is not finished
	local $filename="$1"
	unset SECTION VERSION SOURCE NAME ARCH
	eval $( dpkg --info $filename | \
		sed \
			-e's/^ Section: */SECTION=/p' \
			-e's/^ Version: *\(.*:\)\?/VERSION=/p' \
			-e's/^ Source: *\([^ ]*\).*$/SOURCE=\1/p' \
			-e's/^ Package: */NAME=/p' \
			-e's/^ Architecture: */ARCH=/p' \
			-n \
		)

	[ "$SOURCE" ] || SOURCE=$NAME
	case $SOURCE in
		lib*) HASH=`expr $SOURCE : '\(....\)'` ;;
		*) HASH=`expr $SOURCE : '\(.\)'` ;;
	esac
	case $SECTION in
		contrib*)	SECTION=contrib ;;
		non-free*)	SECTION=non-free ;;
		non-US*|non-us*)SECTION=non-US/main ;;
		*) SECTION=main;;
	esac
	echo "pool/$SECTION/$HASH/$SOURCE/$filename"
}
mirrorpaths()
{
	local filename="$1"
	if [ "$EXACT_MOVING" != "off" ] ;then
		mirrorpaths_packages "$filename"
		return
	else
		for method in $FUZZY_MATCHING
		do
			MIRRORPATHS=$(mirrorpaths_$method $filename)
			if [ -n "$MIRRORPATHS" ] ;then
				echo "$MIRRORPATHS"
				return
			fi
		done
	fi

}

add_backend()
{
    if [ -n "`ls $2.apt-proxy-filelists/* 2>/dev/null`" ] ;then
        BACKENDS="$BACKENDS $2.apt-proxy-filelists/*"
    else
        debug "Backend $2 does not have filelists - skipped"
    fi
}

# Given a directory, print out all the parents in forwards order.
# (taken from apt-proxy)
#	directories(pathname)
directories()
{
    DR_TOTAL=""
    for dr_d in `echo $1 | tr / ' '`; do
	DR_TOTAL="$DR_TOTAL/$dr_d"
	echo "$DR_TOTAL"
    done
}

debug()
{
    [ -n "$VERBOSE" ] && echo "$@"
}

unset VERBOSE

# Parse command line
ARGS=`getopt -o e:c:hvd --long \
	exact:,config-file:,help,version,verbose \
	-n "$0" -- "$@"`
if [ $? != 0 ] ; then echo "Terminating..." >&2 ; exit 1 ; fi
eval set -- "$ARGS"
while true ; do
	case "$1" in
	  '-c'|'--config-file')
		CONFIG_FILE="$2"
		shift 2
		;;
	  '-h'|'--help'|'--version'|'-v')
                usage
                exit 1
                ;;
	  '-d'|'--verbose')
		VERBOSE=1
		shift
		;;
	  '-e'|'--exact')
	  	EXACT_MOVING="$2"
		shift 2
		;;
	  '--')
 		# end of options
                shift
                break
		;;
	  *)
	  	echo "Internal error!"
		exit 1
		;;
	esac
done

[ $# -eq 0 ] && usage && exit 1

. $CONFIG_FILE

if [ ! -x "$DPKG_NAME" ];then
  echo "$PROGNAME: $DPKG_NAME not found - please install package dpkg-dev"
  exit 1
fi

if [ -z "$BACKENDS" ]; then
  echo "$PROGNAME: No backend filelists found."
  exit 1
fi

for directory in $@; do

    if [ ! -d "$directory" ]; then
        echo "directory not found:$@" 
	continue
    fi

    #Make sure that we use the correct names
    #about dpkg-name:
    #	The best we could get out of dpkg-name, without renaming the files on
    #	place, was making symlinks with the right name on a certain directory,
    #	and that it the reason for creating "$APT_PROXY_CACHE/dpkg-name.links/"

    rm -rf "$APT_PROXY_CACHE/dpkg-name.links/"
    mkdir "$APT_PROXY_CACHE/dpkg-name.links/"
    [ -z "$VERBOSE" ] && echo -n "getting file names"
    $DPKG_NAME -k -s "$APT_PROXY_CACHE/dpkg-name.links" "$directory"/*.deb \
    	| line_feedback

    for file in "$APT_PROXY_CACHE"/dpkg-name.links/*; do

    	filename=`basename $file`
	
	case "$filename" in
	*.deb)
	    cachepaths=`mirrorpaths "$filename"`

	    if [ -n "$cachepaths" ]; then

		for f in $cachepaths; do

		    dirname=`dirname $f`
		    if [ ! -d "$dirname" ]; then
			debug "Making directory $dirname"
			unset DR_LAST
			for DR in `directories $dirname`; do
			  if [ -d "$DR_LAST" -a ! -d "$DR" ]; then
			    mkdir "$DR" &&
			    chown --reference "$DR_LAST" "$DR" ||
				  echo "mkdir+chown $DR FAILED"
			  fi
			  DR_LAST="$DR"
			done
		    fi

		    if [ -f $f ]; then
			debug "Skipping $filename - already in directory $dirname"
		    else
			echo "importing $filename"
			cp -p "$file" "$f" &&
			  chown --reference "$dirname" "$f" ||
			      echo "cp+chown $file $f FAILED"
		    fi
		done
	    else
		echo "skipped $filename"
	    fi
	    ;;
	 *)
	    debug "Skipping $filename - unsupported type"
	 esac
    done
    rm -rf "$APT_PROXY_CACHE/dpkg-name.links/"
done

exit 0

        


