MLDonkey: Commit von Dateien für mehrere Benutzer

Aus NOBAQ
Wechseln zu: Navigation, Suche
Mldonkey.PNG
MLDonkey ist ein Multi-Protokoll P2P Client, der u.a. perfekt dazu geeignet ist, per BitTorrent am Server im Hintergrund Dateien herunter zu laden. In der neuen Version ist neben weiteren Features auch ein komplettes User- und Gruppenmanagement dazugekommen. Mit einem von mir geschriebenem commit-Script und einem vom Entwickler glücklicherweise zu Verfügung gestelltem Patch ist es möglich, eine Datei mittels Symlinks an mehrere Benutzer "auszuliefern", sofern die Datei einer Gruppe zugeordnet ist, die mehrere Benutzer beinhaltet...


Das erste Script hat über "netcat" auf MLdonkey zugefriffen, um die Benutzerdaten abzufragen. Das war sehr unbequem. Aus diesem Grund hat der Maintainer von MLdonkey dankenswerterweise einen Patch geschrieben, der weitere Umgebungsvariablen einführt: https://savannah.nongnu.org/patch/index.php?5821

Sofern eine Datei einer Gruppe mit mehreren Benutzern zugeordnet ist, so werden Environmentvariablen nach folgendem Muster gesetzt:

FILE_GROUP_CNT=2
FILE_GROUP_USER_0=user1
FILE_GROUP_DIR_0=user1
FILE_GROUP_USER_1=user2
FILE_GROUP_DIR=user2

Mein Script "parst" nun diese Variablen, verschiebt die Datei in ein spezielles Verzeichnis und macht für jedes Benutzerverzeichnis einen symbolischen Link.


Warum kein Hardlink?

Hardlinks wären ja wie geschaffen für genau dieses Problem. Jedoch können diese nur als root erstellt werden und mein MLdonkey läuft extra aus Sicherheitsgründen in einem chroot. Da will ich natürlich nicht einmal daran denken, dort drinnen irgendeine Möglichkeit zu lassen, etwas als root ausführen zu können (das Script wird ja innerhalb des chroots als unpriviligierter Benutzer von MLdonkey gestartet). Also habe ich mich für symbolische Links entschieden, die leider nicht ganz so elegant sind. Nachdem die Hauptdatei übrig bleibt, auch wenn jeder Benutzer seinen Link gelöscht hat, wird ausserhalb des chroots mit cron ein Script durchlaufen, und prüfen, ob in dem speziellen Verzeichnis Dateien existieren, auf die kein Link mehr zeigt. Da mir das aber nicht so wichtig ist, hab ichs noch nicht implementiert.


Was braucht man noch dazu?

Abgesehen von dem Patch oben braucht man nur noch “busybox”, da das ganze ja unter chroot läuft. Die busybox sollte der ash und arithmetischen Operationen sowie der alias Option compiliert werden und folgende Builtins besitzen: rm, ls, ln, mv, mkdir.

#!/busybox sh
 
# (c) 2007 Nikolaus Hammler <nobaq@sbox.tugraz.at>
# Licensed under GNU GPL
 
chrootdir="/home/system/mldonkey"
donkeydir="/.mldonkey"
commitdir="$donkeydir/incoming/files"
pendingdir="$donkeydir/incoming/pending"
 
BB=/busybox
alias rm="$BB rm"
alias ls="$BB ls"
alias ln="$BB ln"
alias mv="$BB mv"
alias mkdir="$BB mkdir"
 
# Debug
set
 
# this is a private download
if test "$FILE_GROUP" = "none"
then
	echo "Group is none --> private download"
	exit 1
fi
 
# Less than two groups associated, keep as-is
if test "$FILE_GROUP_CNT" -lt 1
then
	echo "Less than one group associated --> leave as is"
	exit 2
fi
 
# If there's no file, just leave it
if ! test -f "$donkeydir/$INCOMING/$FILENAME"
then
	echo "File '$donkeydir/$INCOMING/$FILENAME' not found"
	exit 3
fi
 
if ! mv "$donkeydir/$INCOMING/$FILENAME" "$pendingdir"
then
	echo "Copying file '$donkeydir/$INCOMING/$FILENAME' to '$pendingdir' failed!"
	exit 4
fi
 
ln -s "$chrootdir$pendingdir/$FILENAME" "$donkeydir/$INCOMING/$FILENAME"
echo ln -s "$chrootdir$pendingdir/$FILENAME" "$donkeydir/$INCOMING/$FILENAME"
 
echo "Und nun zu den Gruppen..."
 
i=1
while [ "$i" -le "$FILE_GROUP_CNT" ]
do
	dir=`eval echo '"$FILE_GROUP_DIR_'$i'"'`
 
	if ! test -z "$dir"
	then
		echo "Processing commit-directory $dir...."
 
		test -d "$commitdir/$dir" || mkdir "$commitdir/$dir"
 
		if ! [ -d "$commitdir/$dir" ]
		then
			echo "Warning! $commitdir/$dir does not exist!!"
		else
			if ! ln -s "$chrootdir$pendingdir/$FILENAME" "$commitdir/$dir/$FILENAME"
			then
				echo ln -s "$chrootdir$pendingdir/$FILENAME" "$commitdir/$dir/$FILENAME" NICHT erfolgreich
			else
				echo ln -s "$chrootdir$pendingdir/$FILENAME" "$commitdir/$dir/$FILENAME"
			fi
		fi
	fi
 
	: $((i++))
done
 
exit 0

Das Script ist hier zu finden: Media:donkey_commitsh.txt

Am besten man kopiert es zusammen mit “mlnet” und “busybox” in den root des chroots (andernfalls müssen Anpassungen vorgenommen werden).

Aktiviert wird das ganze in MLdonkey mit

set file_completed_cmd /donkey_commit.sh

Zum Debugging können die Meldungen auf der Konsole beobachtet werden.

Kommentare

Diskussion:MLDonkey: Commit von Dateien für mehrere Benutzer
Meine Werkzeuge