Instalá qBittorent: sudo apt install -y qbittorrent-nox o qbittorrent.

Abrí qbittorrent, view -> search engine. Ahora movete a la pestaña Search y abajo a la derecha dale a search plugins -> install a new one -> web link y pegá: https://raw.githubusercontent.com/qbittorrent/search-plugins/master/nova3/engines/jackett.py

Luego andá a ~/.local/share/qBittorrent/nova3/engines/ o seguí este tutorial: https://github.com/qbittorrent/search-plugins/wiki/How-to-configure-Jackett-plugin

creá un archivo llamado jackett.json

{
    "api_key": "YOUR_API_KEY_HERE",
    "url": "http://127.0.0.1:9117",
    "tracker_first": false,
    "thread_count": 20
}

La API key lo copias de https://localhost:9117

Abrí Jackett y agregá todos los indexers publicos seleccionando uno por uno el checkbox de la izquierda.

Finalmente abrí qbittorrent andate a Search y buscá el torrent que quieras.

Podés descargarte qbittorrent-nox para y agregar .config/qBittorrent/qBittorrent.conf debajo de [Preferences]:

WebUI\Password_PBKDF2="@ByteArray(ARQ77eY1NUZaQsuDHbIMCA==:0WMRkYTUWVT9wVvdDtHAjU9b3b7uB8NR1Gur2hmQCvCDpm39Q+PsJRJPaCU51dEiz+dTzh8qbPsL8WkFljQYFQ==)"
WebUI\Port=8080
WebUI\Username=admin
WebUI\LocalHostAuth=false

Que establece la contraseña por defecto como adminadmin para no tener que estar copiando y pegando la contraseña temporal que te genera cada vez que abrís el programa.

Para instalar jackett en Arch usando el AUR:
yay -S jackett-bin
sudo systemctl start jackett

Y sumado a eso usá opencode para complementar con jackett y qbitorrent-nox ;)

Prompt:

Programame un script de bash Chequea que qbittorrent-nox e jackett esten instalados. De no estarlo adverti al usuario. inicia qbittorrent-nox en 2do plano ejecutando qbittorrent-nox (configura la contraseña adminadmin), agregar $HOME/.config/qBittorrent/qBittorrent.conf debajo de [Preferences]: (si es que ya no está)

WebUI\Password_PBKDF2="@ByteArray(ARQ77eY1NUZaQsuDHbIMCA==:0WMRkYTUWVT9wVvdDtHAjU9b3b7uB8NR1Gur2hmQCvCDpm39Q+PsJRJPaCU51dEiz+dTzh8qbPsL8WkFljQYFQ==)"

Usa curl -s -X POST “http://127.0.0.1:8080/api/v2/auth/login” -d “username=admin&password=adminadmin” -c /tmp/qbt_cookies.txt && echo "" para comunicarte con qbittorrent-nox

y el servicio de jackett con systemd usando sudo systemctl start jackett descargame el torrent de jason vs freddie tenga muchos seeds hace una busqueda generica y despues filtra los resultados, bajame la calidad de video mas baja que encuentres y abrilo con mpv :) el servicio ya esta activo localmente en el puerto 9117 y la api key esta en $HOME/.local/share/qBittorrent/nova3/engines/jackett.json usa qbittorrent-nox adminadmin es la contraseña agrega el torrent usando qbittorrent-nox con con curl -s -X POST “http://127.0.0.1:8080/api/v2.0/torrents/add” -d “urls=magnet:?xt=XXXXXXXXX” usa la guid que empieza con magnet:? al buscar en jackett These are magnet links stored in the Guid field. Let me use those magnet links directly with qBittorrent. busca en todos los indexers. http://127.0.0.1:9117/api/v2.0/indexers/all/ para buscar algo: $ curl -s “http://127.0.0.1:9117/api/v2.0/indexers/all/results?Query=formula+1&apikey=xxxx” 2>&1 | jq ‘.’ 2>/dev/null | head -80

Y luego escribime un script de bash para automatizar todo esto.

Si se pone estúpido reinicialo.

0magnet: Needs FlareSolverr 1337x: Needs FlareSolverr 52bt: Needs FlareSolverr

El script que me generó opencode todavía tengo que arreglarlo cuando lo tenga, lo publico acá.

Opencode

#!/usr/bin/env bash
set -uo pipefail

JACKETT_URL="http://127.0.0.1:9117"
INDEXERS_DIR="${INDEXERS_DIR:-/var/lib/jackett/Indexers}"
JACKETT_KEY_FILE="$HOME/.local/share/qBittorrent/nova3/engines/jackett.json"
QBT_URL="http://127.0.0.1:8080"
DOWNLOAD_DIR="${DOWNLOAD_DIR:-/mnt/linux2/torrents}"
RESULTS_TMP="/tmp/torrent_menu_results.json"
TOP_RESULTS=20

RED='\033[0;31m'; GREEN='\033[0;32m'; YELLOW='\033[1;33m'; CYAN='\033[0;36m'; BOLD='\033[1m'; RESET='\033[0m'

info() { echo -e "${CYAN}[INFO]${RESET}  $*"; }
ok()   { echo -e "${GREEN}[OK]${RESET}    $*"; }
warn() { echo -e "${YELLOW}[WARN]${RESET}  $*"; }
die()  { echo -e "${RED}[ERROR]${RESET} $*" >&2; exit 1; }

human_size() {
    local n=$1
    if   [ "$n" -ge 1099511627776 ]; then awk "BEGIN{printf \"%.2f TB\", $n/1099511627776}"
    elif [ "$n" -ge 1073741824 ];   then awk "BEGIN{printf \"%.2f GB\", $n/1073741824}"
    elif [ "$n" -ge 1048576 ];      then awk "BEGIN{printf \"%.1f MB\", $n/1048576}"
    elif [ "$n" -ge 1024 ];         then awk "BEGIN{printf \"%.0f KB\", $n/1024}"
    else echo "${n} B"; fi
}

get_apikey() {
    jq -r '.api_key // empty' "$JACKETT_KEY_FILE" 2>/dev/null
}

list_indexers() {
    [ -d "$INDEXERS_DIR" ] || warn "No se pudo leer $INDEXERS_DIR"
    ok "Indexers configurados:"
    ls "$INDEXERS_DIR"/*.json 2>/dev/null | xargs -n1 basename 2>/dev/null | sed 's/\.json$//' | sort | nl
    exit 0
}

resolve_indexer() {
    local want="$1" wlower id ilower found=""
    wlower=$(printf '%s' "$want" | tr '[:upper:]' '[:lower:]')
    for f in "$INDEXERS_DIR"/*.json; do
        [ -e "$f" ] || continue
        id=$(basename "$f" .json)
        [ "$id" = "$want" ] && { echo "$id"; return 0; }
        [ -z "$found" ] &&             [ "$(printf '%s' "$id" | tr '[:upper:]' '[:lower:]')" = "$wlower" ] && found="$id"
    done
    if [ -n "$found" ]; then echo "$found"; return 0; fi
    return 1
}

search_jackett() {
    local query="$1" idx="${2:-all}" apikey total encoded
    apikey=$(get_apikey)
    [ -n "$apikey" ] || die "No se encontró API key en $JACKETT_KEY_FILE"

    encoded=$(python3 -c "import urllib.parse,sys; print(urllib.parse.quote(sys.argv[1]))" "$query")
    info "Consultando Jackett indexer: $idx ..."
    curl -s -m 300 -f "${JACKETT_URL}/api/v2.0/indexers/${idx}/results?Query=${encoded}&apikey=${apikey}" > "$RESULTS_TMP" \
        || die "Jackett no respondió. ¿Está corriendo en $JACKETT_URL?"

    total=$(jq '.Results | length' "$RESULTS_TMP" 2>/dev/null)
    [ "$total" -gt 0 ] 2>/dev/null || die "Sin resultados para '$query'."
    ok "Resultados: $total"
    tracker_summary
}

tracker_summary() {
    local line
    echo -e "${CYAN}  Por indexer:${RESET}"
    while IFS=$'\t' read -r tr c; do
        printf "     %-22s %s\n" "$tr" "$c"
    done < <(jq -r '[.Results[].Tracker] | group_by(.) | map("\(.[0])\t\(length)") | .[]' "$RESULTS_TMP" 2>/dev/null \
        | sort -t $'\t' -k2 -rn)
}

build_list() {
    jq -r --argjson top "$TOP_RESULTS" '
      def ds: .PublishDate // "" | strptime("%Y-%m-%dT%H:%M:%S")? | mktime // 0;
      def skey: [-(.Seeders // 0), -ds];
      (.Results | map(select((.Guid | startswith("magnet:?")) or ((.Link // "") | startswith("http"))))) as $c
      | (($c | group_by(.Tracker) | length) | if . > 0 then . else 1 end) as $nt
      | (((($top + $nt - 1) / $nt) | floor)) as $per
      | $c
      | group_by(.Tracker)
      | map(sort_by(skey) | .[0:$per])
      | add
      | (sort_by(skey) | .[0:$top])[] as $x
      | [ 0,   # placeholder, se numera en show_menu
          $x.Seeders,
          $x.Size,
          ($x.Title | gsub("[
	]";" ")),
          ($x.IndexerError // $x.Tracker // ""),
          $x.Guid,
          $x.Link,
          ($x.PublishDate // "" | split("T")[0]) ]
      | @tsv
    ' "$RESULTS_TMP"
}

show_menu() {
    echo ""
    echo -e "${BOLD}Resultados (seeds, luego más reciente; balanceado entre indexers):${RESET}"
    echo -e "${CYAN}------------------------------------------------------------${RESET}"
    local i=0
    while IFS=$'	' read -r _x seeds size title idxr guid link pdate; do
        i=$((i+1))
        ttype="[m]"
        [[ "$link" == "http"* ]] && ttype="[t]"
        d=${pdate:0:10}
        printf "%2s │ %-4s│ %10s │ %-60s %s %s %s
"             "$i" "$seeds seeds" "$(human_size "$size")" "${title:0:60}" "[$idxr]" "$ttype" "[${d:2}]"
    done < <(build_list)
    echo -e "${CYAN}------------------------------------------------------------${RESET}"
}

pick_magnet() {
    local choice
    local n
    n=$(build_list | wc -l)
    [ "$n" -eq 0 ] && warn "Sin resultados descargables (magnet o .torrent)." && return 1

    read -rp "Número a descargar (Enter=salir, 0=volver a buscar): " choice
    [ -z "$choice" ] && echo "cancelado" && return 1
    [ "$choice" = "0" ] && return 2

    if [ "$choice" -ge 1 ] 2>/dev/null && [ "$choice" -le "$n" ] 2>/dev/null; then
        MAGNET=$(build_list | sed -n "${choice}p" | cut -f6)
        TORRENT_LINK=$(build_list | sed -n "${choice}p" | cut -f7)
        TITLE=$(build_list | sed -n "${choice}p" | cut -f4)
        ok "Elegido: ${TITLE:0:80}"
        return 0
    fi
    warn "Opción inválida"
    return 1
}

add_torrent() {
    local source_url="$MAGNET"
    if [[ "$MAGNET" == "http"* ]]; then
        source_url="$TORRENT_LINK"
    fi
    info "Agregando a qBittorrent (destino: $DOWNLOAD_DIR)..."
    curl -sf -X POST "${QBT_URL}/api/v2/torrents/add" \
        --data-urlencode "urls=$source_url" \
        -d "savepath=$DOWNLOAD_DIR" \
        -d "category=menu" \
        -w "" -o /dev/null || curl -s -X POST "${QBT_URL}/api/v2/torrents/add" \
        --data-urlencode "urls=$source_url" \
        -d "savepath=$DOWNLOAD_DIR" \
        -d "category=menu"
    ok "Torrent agregado. Ver estado en $QBT_URL o corre: torrent_menu.sh --estado"
}

show_status() {
    echo -e "${BOLD}Estado de descargas:${RESET}"
    curl -sf "${QBT_URL}/api/v2/torrents/info?category=menu" | jq -r '.[] | "  [\(.state)] \(.progress*100|floor)%%  \(.name[0:60])"' 2>/dev/null \
        || echo "  (sin torrents o qBittorrent sin respuesta)"
}

usage() {
    echo "Uso:"
    echo "  $0 \"nombre\"              Buscar en TODOS los indexers (puede tardar 1-2 min)"
    echo "  $0 --indexer NOMBRE \"q\"  Buscar solo en UN indexer (no sensible a mayúsculas)"
  echo "  $0 --list-indexers      Listar indexers configurados"
    echo "  $0 --estado               Ver estado de descargas"
    echo "  $0 --servicios            Verificar servicios (jackett, qbittorrent-nox)"
    exit 0
}

check_services() {
    info "jackett:      $(systemctl is-active jackett 2>/dev/null || echo inactivo)"
    info "qbittorrent:  $(systemctl is-active qbittorrent-nox 2>/dev/null || echo inactivo)"
    info "ruta destino: $DOWNLOAD_DIR"
}

case "${1:-}" in
    --estado)    show_status; exit 0 ;;
    --servicios) check_services; exit 0 ;;
    --help|-h)   usage ;;
    --list-indexers) list_indexers ;;
    --indexer)
        [ $# -ge 3 ] || die "Uso: $0 --indexer NOMBRE \"búsqueda\""
        IDX_RESOLVED=$(resolve_indexer "${2:-}") || die "Indexer '${2:-}' no encontrado. Usa: $0 --list-indexers"
        IDX="${IDX_RESOLVED}"
        QUERY="$3"
        ;;
    "")
        read -rp "¿Qué querés buscar? " QUERY
        [ -n "$QUERY" ] || die "Búsqueda vacía."
        ;;
    *) QUERY="$*" ;;
esac

check_services
if [ -n "${IDX:-}" ]; then
    info "Buscando '$QUERY' SOLO en indexer: $IDX"
    INDEXER_PATH="$IDX"
else
    warn "Buscando en TODOS los indexers, puede tardar 1-2 min..."
    INDEXER_PATH="all"
fi
search_jackett "$QUERY" "$INDEXER_PATH"

while true; do
    show_menu
    pick_magnet
    rc=$?
    if [ "$rc" -eq 2 ]; then
        read -rp "Nueva búsqueda: " QUERY; search_jackett "$QUERY" "$INDEXER_PATH"; continue
    fi
    [ "$rc" -eq 0 ] || exit 0
    add_torrent
    echo ""
    read -rp "¿Descargar otro? [s/N]: " again
    [[ "$again" =~ ^[sSyY] ]] || break
done
ok "Listo."

Los torrents se guardan en /var/lib/qbittorrent/Downloads

Despues de que Claude AI me genere ese script fenomenal le pedi esto:

Me encanto, aun asi cuando abria el video con mpv parece que abria el directorio entero en vez de abrir el video que habia descargado, fuera de eso que no es tanta complicacion. Lo que me gustaria es que me de a elegir ahora quiero que sea mas como un buscador pero ordenalos por los que tienen mas seeds primero y que sean recientes, y eso de 720 o 1080 no lo tomes en consideracion porque a veces yo quiero descargar archivos o audios que no son videos. No se si me entendes, ahora quiero algo mas como un buscador eficiente quiero descargar algo que tenga muchos seeds sino no funciona y quiero poder elegir que me de una lista de torrents y yo elijo cual quiero descargar.

En /var/lib/jackett/Indexers

Está la lista de indexs si es que los activaste uno por uno guardalos para no tener que volver a hacerlo.