Una de las maneras mas rápidas y sencillas de descargar ficheros es mediante BitTorrent, pero hay contenido que solo lo tienen un reducido número de personas y la descarga puede llevar horas o incluso días, en estos casos vale la pena tener un servidor de descargas dedicado exclusivamente a esta tarea, de este modo no será necesario dejar nuestro equipo encendido todo ese tiempo. En este artículo se explicará como instalar un servidor de transmission en modo headless, como configurar un cliente para gestionar las descargas desde nuestro pc y como compartir el contenido descargado mediante ZFS-NFS4.
El artículo se compone de distintas secciones:
- Montaje de la jail y configuración del padre
- Directorio de descargas
- Configuración mínima de la jail
- Instalación y configuración de Transmission
- Instalación, configuración y gestión del cliente
- Acceso NFS
- Firewall
- Acceso NFS cliente
- Script descargas
- Debug
Montaje de la jail y configuración del padre:
Para mayor versatibilidad y comodidad vamos a montar el servidor sobre una jail
Iocage
:
iocage set ip4_addr=“nfe0|192.168.69.7/24” Lomax
iocage list
+-----+---------+-------+--------------+--------------+
| JID | NAME | STATE | RELEASE | IP4 |
+=====+=========+=======+==============+==============+
| 10 | Lomax | up | 12.2-RELEASE | 192.168.69.7 |
+-----+---------+-------+--------------+--------------+
Transmission precisa de unos buffers UDP mas altos de lo normal, si no los subimos veremos el siguiente error en el log de messages al arrancar el servicio:
Nov 17 22:10:19 Lomax transmission-daemon[2775]: UDP Failed to set receive buffer: requested 4194304, got 42080 (/wrkdirs/usr/ports/net-p2p/transmission-daemon/work/transmission-3.00/libtransmission/tr-udp.c:97)
FreeBSD por defecto trae los siguientes valores:
kern.ipc.maxsockbuf: 2097152
net.inet.udp.recvspace: 42080
Los modificamos mediante el fichero sysctl.conf:
kern.ipc.maxsockbuf=5242880
net.inet.udp.recvspace=4194304
Aplicamos los cambios:
Destacar que estamos modificando los parámetros para todas las jails, en la propia jail no es posible hacerlo ya que el kernel es compartido, si lo intentamos obtendremos el siguiente mensaje de error:
sysctl: kern.ipc.maxsockbuf=5242880 at line 10: Operation not permitted
sysctl: net.inet.udp.recvspace=4194304 at line 11: Operation not permitted
Directorio de descargas:
Creamos un dataset con compresión habilitada, este directorio será vinculado en la jail y servirá como directorio de descargas:
Accedemos a la jail y asignamos un password a la cuenta de root:
passwd
Creamos el directorio de descargas:
exit
Vinculamos el dataset con el directorio de descargas de la jail:
iocage fstab -l Lomax
+-------+---------------------------------------------------------------------------------------------------+
| INDEX | FSTAB ENTRY |
+=======+===================================================================================================+
| 0 | /storage/torrents /zroot/iocage/jails/Lomax/root/storage/torrents nullfs rw 0 0 |
+-------+---------------------------------------------------------------------------------------------------+
Reiniciamos la jail:
iocage start Lomax
Configuración mínima de la jail:
Accedemos a la jail para instalar el software base y añadir un usuario:
Instalamos algunos programas básicos y Python
pkg install vim htop bash screen py37-pip curl
Instalamos mediante pip el paquete requests:
Habilitamos y arrancamos el servicio Ssh:
service sshd start
Creamos un usuario regular con el que operaremos:
Login group is kr0m. Invite kr0m into other groups? []: wheel
Shell (sh csh tcsh bash rbash nologin) [sh]: bash
Instalación y configuración de Transmission:
Ahora que ya tenemos nuestro usuario y Ssh habilitado podemos seguir el resto de los pasos desde una consola Ssh:
su -l
Instalamos transmission:
Podemos ver los parámetros de configuración que se permiten en el rc.conf en el siguiente fichero:
En nuestro caso tan solo debemos modificar el directorio de descargas:
En cuanto a las flags tendremos que consultar el man:
En mi caso debo permitir el acceso a las direcciones ip de la propia jail y de mi pc, además del filtrado ip asignamos un usuario y password:
NOTA: Nunca debemos hacer un restart del servicio, parece no recargar la configuración, así que haremos un stop/start.
El resto de parámetros de configuración los modificaremos en el fichero settings.json, parando el servicio previamente:
vi /usr/local/etc/transmission/home/settings.json
service transmission start
Solo tocamos los parámetros que no podamos modificar por los dos métodos descritos anteriormente, si no respetamos esta norma transmission nos sobreescribirá la configuración.
Cambiamos los permisos del directorio de descargas:
Habilitamos y arrancamos el servicio:
service transmission start
Comprobamos que haya arrancado con los parámetros correctos:
transmission 89161 0.4 0.3 41292 12172 - SsJ 12:59 0:00.07 /usr/local/bin/transmission-daemon -g /usr/local/etc/transmission/home -w /storage/torrents -x /var/run/transmission/daemon.pid -a 192.168.69.4,192.168.69.7 -t -u kr0m -v PASSWORD
Instalación, configuración y gestión del cliente:
Instalamos Transmission en el pc para poder gestionar las descargas de forma remota:
Comprobamos que tanto el filtro ip como el usuario/password funcionen:
ID Done Have ETA Up Down Ratio Status Name
Sum: None 0.0 0.0
Añadir un torrent es tan sencillo como indicarle la URL del mismo:
También podemos pasarle un enlace magnet:
Comprobamos el estado de las descargas:
ID Done Have ETA Up Down Ratio Status Name
1 0% None Unknown 0.0 0.0 None Idle debian-10.6.0-arm64-xfce-CD-1.iso
2 n/a None Unknown 0.0 0.0 None Idle Lynda+-+Learning+Debian+Linux+[AhLaN]
Sum: None 0.0 0.0
Para eliminar un torrent debemos pasarle el ID del torrent a eliminar y el parámetro -r:
Se pueden eliminar múltiples torrents con un solo comando:
Para operar con Transmission de una forma mas sencilla podemos crear el siguiente alias:
alias tsm="transmission-remote 192.168.69.7 --auth kr0m:PASSWORD"
Ahora consultar los torrents es tan sencillo como esto:
ID Done Have ETA Up Down Ratio Status Name
1 n/a None Unknown 0.0 0.0 None Idle Lynda+-+Learning+Debian+Linux+[AhLaN]
3 54% 398.4 MB 1 min 0.0 11717.0 0.0 Downloading debian-10.6.0-arm64-xfce-CD-1.iso
Sum: 462.2 MB 0.0 15387.0
Acceso NFS:
Una de las ventajas de servir el contenido descargado por NFS es que si se trata de un fichero multimedia podremos realizar el streaming directamente desde el servidor sin tener que copiar el fichero a nuestro equipo.
El acceso por NFS se realizará desde el padre de la jail, habilitamos el servicio de NFS4 y lo arrancamos:
sysrc nfsv4_server_enable="yes"
sysrc nfsuserd_enable="yes"
service nfsd start
Compartimos el directorio restringiendo el acceso por ip:
NOTA: Con la opción mapall=root hacemos que los accesos al NFS se hagan con el usuario root, todos los accesos desde los clientes tienen los permisos de root del servidor remoto, si no lo configurasemos deberíamos de tener los mismos usuarios con los mismos UIDs/GIDs tanto en el servidor NFS como en todos los clientes a los que les demos acceso.
Mi primera idea fué mapearlo al usuario transmission y no a root, pero como compartimos desde el padre el usuario transmission no existe y NFS4 ya no permite mapear por UID :
uid/gid numbers are no longer used in the NFSv4 protocol
Firewall:
Configuramos las reglas de firewall para que solo nuestro pc tenga acceso al NFS y al servicio de configuración RPC de Transmission, para que las reglas queden mas claras indico a continuación la correspondencia de las direcciones ip:
- Pc: 192.168.69.4
- Padre: 192.168.69.2
- jail: 192.168.69.7
# Torrent NFS access:
# NFS access:
# NFS: Port tcp/udp 111
$cmd 00805 allow tcp from 192.168.69.4 to 192.168.69.2 111 in via $wanif
$cmd 00805 allow tcp from 192.168.69.2 111 to 192.168.69.4 out via $wanif
$cmd 00805 allow udp from 192.168.69.4 to 192.168.69.2 111 in via $wanif
$cmd 00805 allow udp from 192.168.69.2 111 to 192.168.69.4 out via $wanif
$cmd 00805 deny tcp from any to 192.168.69.2 111 in via $wanif
$cmd 00805 deny udp from any to 192.168.69.2 111 in via $wanif
# NFS: Port tcp/udp 950
$cmd 00805 allow tcp from 192.168.69.4 to 192.168.69.2 950 in via $wanif
$cmd 00805 allow tcp from 192.168.69.2 950 to 192.168.69.4 out via $wanif
$cmd 00805 allow udp from 192.168.69.4 to 192.168.69.2 950 in via $wanif
$cmd 00805 allow udp from 192.168.69.2 950 to 192.168.69.4 out via $wanif
$cmd 00805 deny tcp from any to 192.168.69.2 950 in via $wanif
$cmd 00805 deny udp from any to 192.168.69.2 950 in via $wanif
# NFS: Port tcp/udp 2049
$cmd 00805 allow tcp from 192.168.69.4 to 192.168.69.2 2049 in via $wanif
$cmd 00805 allow tcp from 192.168.69.2 2049 to 192.168.69.4 out via $wanif
$cmd 00805 allow udp from 192.168.69.4 to 192.168.69.2 2049 in via $wanif
$cmd 00805 allow udp from 192.168.69.2 2049 to 192.168.69.4 out via $wanif
$cmd 00805 deny tcp from any to 192.168.69.2 2049 in via $wanif
$cmd 00805 deny udp from any to 192.168.69.2 2049 in via $wanif
# NFS: Port tcp/udp 882
$cmd 00805 allow tcp from 192.168.69.4 to 192.168.69.2 882 in via $wanif
$cmd 00805 allow tcp from 192.168.69.2 882 to 192.168.69.4 out via $wanif
$cmd 00805 allow udp from 192.168.69.4 to 192.168.69.2 882 in via $wanif
$cmd 00805 allow udp from 192.168.69.2 882 to 192.168.69.4 out via $wanif
$cmd 00805 deny tcp from any to 192.168.69.2 882 in via $wanif
$cmd 00805 deny udp from any to 192.168.69.2 882 in via $wanif
# Transmission Lomax RPC:
$cmd 00805 allow tcp from 192.168.69.4 to 192.168.69.7 9091 in via $wanif
$cmd 00805 allow tcp from 192.168.69.7 9091 to 192.168.69.4 out via $wanif
$cmd 00805 deny tcp from any to 192.168.69.7 9091 in via $wanif
# All other Lomax traffic
$cmd 00805 allow all from any to 192.168.69.7 any in via $wanif
$cmd 00805 allow all from 192.168.69.7 any to any out via $wanif
Reiniciamos el servicio ipfw:
Acceso NFS cliente:
Desde mi pc podemos ver los recursos servidos por NFS:
Exports list on 192.168.69.2:
/storage/torrents 192.168.69.4
Montamos el recurso /storage/torrents:
mount 192.168.69.2:/storage/torrents /nfs/torrents
Podemos automatizar el proceso mediante un sencillo script pero tendremos que concederle algunos permisos a nuestro usuario:
kr0m ALL=(ALL) NOPASSWD: /sbin/mount 192.168.69.2\:/storage/torrents /nfs/torrents
kr0m ALL=(ALL) NOPASSWD: /sbin/umount /nfs/torrents
El script lo generaremos desde nuestro usuario kr0m:
#!/usr/local/bin/bash
mount|grep '192.168.69.2:/storage/torrents'
if [ $? -eq 1 ]; then
echo -e "-- Mounting NFS: /nfs/torrents"
sudo /sbin/mount 192.168.69.2:/storage/torrents /nfs/torrents
else
echo -e "-- Umouning NFS: /nfs/torrents"
sudo /sbin/umount /nfs/torrents
fi
Asignamos los permisos necesarios:
Script descargas:
Transmission es capaz de ejecutar un script cada vez que finaliza una descarga, nuestro script enviará un Telegram con el nombre del torrent recién descargado y lo eliminará de la lista de torrents:
#!/usr/local/bin/bash
function sendTelegram {
message=${@:1}
/usr/local/bin/curl -s -X POST https://api.telegram.org/botAPI_KEY/sendMessage -d chat_id=CHAT_ID -d text="$message"
}
tsm='/usr/local/bin/transmission-remote 192.168.69.7 --auth kr0m:PASSWORD'
DOWNLOADED=$($tsm -l | /usr/bin/awk '$2 == "100%" {print $10" "$11" "$12" "$13" "$14" "$15" "$16" "$17" "$18" "$19" "$20}')
IFS_ORI=$IFS
IFS=$'\n'
for TORRENT in $DOWNLOADED; do
/bin/echo "TORRENT: $TORRENT"
msg="Downloaded: $TORRENT"
sendTelegram $msg
done
IFS=$IFS_ORI
DOWNLOADED_IDS=$($tsm -l | /usr/bin/awk '$2 == "100%" {print $1}')
for ID in $DOWNLOADED_IDS; do
/bin/echo "ID: $ID"
$tsm -t $ID -r
done
Asignamos los permisos necesarios y cambiamos el propietario del script:
chown transmission:transmission /usr/local/etc/transmission/home/notifyTorrentDownload.sh
Paramos el servicio:
Modificamos la configuración para que tenga en cuenta el script:
"script-torrent-done-enabled": true,
"script-torrent-done-filename": "/usr/local/etc/transmission/home/notifyTorrentDownload.sh",
Arrancamos el servicio:
Cuando un torrent finalice recibiremos una notificación vía Telegram similar a la siguiente:
Debug:
Paramos el servicio:
Arrancamos el servicio en foreground como root:
Cuando terminemos tendremos que rectificar algunos permisos de ficheros generados mientras el proceso estaba corriendo como root:
chown -R transmission:transmission /storage/torrents/
Arrancamos de forma regular el servicio:
Transmission escribe sus logs en /var/log/messages, así que comprobamos en este fichero que no aparezca ningún error:
También es posible ejecutar comandos con el usuario transmission pero para ello tendremos que cambiar la shell temporalmente, ejecutar el comando y revertir el cambio:
su transmission -c “/usr/local/etc/transmission/home/notifyTorrentDownload.sh”
chsh -s /usr/sbin/nologin transmission