Skip to content

Instantly share code, notes, and snippets.

@marco79cgn
Last active July 14, 2025 09:08
Show Gist options
  • Save marco79cgn/b09e26beaaf466cb04f9d74122866048 to your computer and use it in GitHub Desktop.
Save marco79cgn/b09e26beaaf466cb04f9d74122866048 to your computer and use it in GitHub Desktop.
Ein Skript zum downloaden von Videos bei ARD Plus (→ https://github.com/marco79cgn/ard-plus-dl)
Umgezogen, jetzt hier zu finden:
https://github.com/marco79cgn/ard-plus-dl
@marco79cgn
Copy link
Author

marco79cgn commented May 26, 2025

@kobeegh
Ich habe gerade das parsen des Tokens angepasst im Skript. Es funktioniert jetzt auch mit alten Versionen von curl. Zudem prüft das Skript jetzt, ob überhaupt ein Token zurück kommt beim Login und ob er vom Typ JWT ist. Falls nicht, beendet sich das Skript und es wird keine leere Datei gespeichert geschweigedenn versucht, ohne Token mit deren API zu kommunizieren.

@profhccaesar
Copy link

Hallo, bin gerade auf dein Skript gestoßen.

Leider schaffe ich es nicht, Videos herunter zu laden, ich bekomme immer folgende Meldung:

$ ./ard-plus-dl.sh 'https://www.ardplus.de/details/a0S010000037hjZ-kommissar-dupin-bretonischer-ruhm' 'meinuser' 'meinpw'
Couldn't get season details. Trying again!
cat: content-result.txt: Datei oder Verzeichnis nicht gefunden
Lade Film  ()...
ERROR: [generic] '?' is not a valid URL. Set --default-search "ytsearch" (or run  yt-dlp "ytsearch:?" ) to search YouTube

Ich habe das einmal weiter analysiert und festgestellt, dass der HTTP-Request per curl immer den Code 000 (anstatt 200) zurückliefert.

Mache ich etwas falsch oder hat ARD schon wieder Änderungen vorgenommen?

P. S. Ich habe folgende Änderungen an deinem Skript vorgenommen:

  1. Beim wiederholten Versuch, die Filmdaten per curl zu holen, fehlt das Fehler-Handling, weshalb die seltsame Meldung content-result.txt: Datei oder Verzeichnis nicht gefunden auftaucht.
  2. Ausgabe des HTTP-Status-Codes in der Meldung.
--- ard-plus-dl.sh	2025-06-02 19:07:34.513796353 +0200
+++ ard-plus-dl.sh-patched	2025-06-02 19:10:02.053509897 +0200
@@ -109,7 +109,7 @@
     -H 'user-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36')
 if [[ $seasonsStatus != "200" ]]; then
     #retry once
-    echo "Couldn't get season details. Trying again!"
+    echo "Couldn't get season details (HTTP-Status $seasonsStatus). Trying again!"
     sleep 2
     seasonsStatus=$(curl -s -o content-result.txt -w "%{http_code}" "${contentUrl}" \
     -H 'authority: data.ardplus.de' \
@@ -118,6 +118,10 @@
     -H 'origin: https://www.ardplus.de' \
     -H 'referer: https://www.ardplus.de/' \
     -H 'user-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36')
+    if [[ $seasonsStatus != "200" ]]; then
+        echo "Couldn't get season details (HTTP-Status $seasonsStatus). Giving up."
+        exit 1
+    fi
     contentResult=$(cat content-result.txt)
 else
     contentResult=$(cat content-result.txt)

Schöne Grüße
Raimund

@marco79cgn
Copy link
Author

Ich habe das einmal weiter analysiert und festgestellt, dass der HTTP-Request per curl immer den Code 000 (anstatt 200)zurückliefert.

Das Skript bzw. der curl Befehl versucht, die Metadaten über das ARD Plus API zu bekommen und speichert diese temporär in einer Datei namens content-result.txt.

curl -s -o content-result.txt -w "%{http_code}" "${contentUrl}"

Der Grund hierfür ist, dass ich primär an den http status code kommen will, um zu prüfen, dass der 200 (=success) ist. Denn dann kann man davon ausgehen, dass der Aufruf auch erfolgreich war. Der Grund hierfür ist das Fehlerhandling. Wenn da bei dir stattdessen 000 zurück kommt, dann ist genau das das Problem. Welche curl Version benutzt du denn?

@marco79cgn
Copy link
Author

@profhccaesar
Habe es eben auf einem alten Raspberry Pi OS bullseye nachgestellt. Die neueste curl-Version via apt ist dort 7.74.0 und die hat auch diesen Bug, der zu 000 führt. Scheint ein Problem zu sein mit https im Zusammenhang mit -w "%{http_code}" in alten Curl Versionen. (Das Problem ist seit langem gefixt.)

Workaround:
neue curl Version per snap installieren. Beim Raspberry Pi klappt das wie hier beschrieben. Damit konnte ich das Problem direkt lösen!

Ich habe gerade das Skript angepasst und in der ersten Zeile die Möglichkeit ergänzt, einen alternativen Pfad für das curl binary anzugeben. Man muss es entsprechend nur an dieser einen Stelle ändern.

Vielleicht sollte ich das Ganze als Docker Container anbieten. Eigentlich habe ich gedacht, bei den wenigen Abhängigkeiten kann nicht viel schief gehen. Aber offensichtlich sind viele unterschiedliche curl Versionen im Umlauf, die oft veraltet sind und/oder Bugs enthalten.

@profhccaesar
Copy link

@marco79cgn
Vielen Dank für den Typ - obwohl ich täglich mit curl arbeite, ist mir dieser Bug noch nicht in die Quere gekommen.

Leider gestaltete es sich etwas schwierig, eine aktuelle curl-Version auf meinem System zum Laufen zu bekommen - snapd ist aus diversen Gründen deaktiviert. Ich habe deshalb deine Idee des Docker-Containers aufgegriffen und einen gebaut, liegt hier auf Github im Projekt docker-ard-plus-dl. Bitte nach Belieben verwenden und anpassen - das Ding unterliegt der "Unlicense"-Lizenz.

Die Verwendung ist - eine lauffähige Docker-Installation vorausgesetzt - sehr einfach:

# Projekt herunterladen:
git clone https://github.com/profhccaesar/docker-ard-plus-dl.git ./docker-ard-plus-dl

# Video herunterladen:
cd docker-ard-plus-dl
./ard-plus-dl-docker.sh --dir ~/Downloads 'https://www.ardplus.de/details/a0S010000037hjZ-kommissar-dupin-bretonischer-ruhm' 'myuser' 'mypassword'

Wenn nötig, wird das Image gebaut, yt-dlp und ard-plus-dl.sh werden in der jeweils aktuellsten Version heruntergeladen. Anschliessend wird ard-plus-dl.sh im Container gestartet. Die heruntergeladenen Dateien landen im angegebenen Verzeichnis (--dir, im Beispiel also ~/Downloads).

Werden Änderungen am Image vorgenommen (Anpassung Dockerfile / Startskript) oder gibt es eine neue Version von yt-dlp oder ard-plus-dl.sh, muss lediglich der Parameter --force angegeben werden, dann wird das vorhandene Image gelöscht und mit den neuesten Versionen der Skripte neu gebaut:

./ard-plus-dl-docker.sh --force --dir ~/Downloads 'https://www.ardplus.de/details/a0S010000037hjZ-kommissar-dupin-bretonischer-ruhm' 'myuser' 'mypassword'

@marco79cgn
Copy link
Author

@profhccaesar
Super, vielen Dank! Ich hatte die gleiche Idee und bin beim über-optimieren an Alpine gescheitert (wollte das Image so klein wie möglich haben, aber ist eigentlich auch nicht so extrem wichtig).

Ich werde es zeitnah ausprobieren. Was ich bei einem anderen Projekt festgestellt habe: die mwader/static-ffmpeg binaries beschleunigen nicht nur das initiale bauen des Containers, sie machen ihn vor allem wesentlich kleiner, was die Größe anbelangt.

@profhccaesar
Copy link

profhccaesar commented Jun 4, 2025

P. S. Fehler im Docker-Image behoben, bitte von Github aktualisieren (z. B. git pull) und einmal mit Parameter --force aufrufen.

* (Bugfix) Missing dependency bsdextrautils.
* (Bugfix) Container now interactive - ard-plus-dl.sh sometimes requires user interaction, e. g. for season selection.

@marco79cgn
Um ehrlich zu sein, habe ich mich um die Größe des Images herzlich wenig gekümmert. Es ist 970 MB groß, der Container benötigt nur ein paar Bytes. Jedes heruntergeladene Video ist um ein Mehrfaches größer - eine Optimierung der Größe bringt also in Relation kaum etwas.

$ docker system df -v
Images space usage:

REPOSITORY                            TAG              IMAGE ID       CREATED         SIZE      SHARED SIZE   UNIQUE SIZE   CONTAINERS
ard-plus-dl                           latest           423ff031ddb0   13 hours ago    971MB     0B            970.9MB       1
...
Containers space usage:

CONTAINER ID   IMAGE                        COMMAND                  LOCAL VOLUMES   SIZE      CREATED              STATUS                NAMES
629bbfd5db5e   ard-plus-dl                  "bash"                   0               0B        About a minute ago   Up About a minute     ard-plus-dl
...

Die Zeit zum Bauen des Images hat mich auch nicht viel mehr interessiert, das es nur ein einziges Mal stattfindet; außerdem muss man auch hier die Verhältnismäßigkeit sehen: jeder Video-Download benötigt mehrere Minuten; da fällt die einmalige "Investition" von etwa 20 Sekunden für den Bau des Image kaum ins Gewicht.

Zudem wird der größte Zeitanteil beim Bauen des Images sowieso durch das Herunterladen der benötigten Programme per apt-get und das Klonen des yt-dlp-Repositories beansprucht; da bringen eine geschicktere Auswahl des Images und der verwendeten Pakete in der Relation nicht viel.

@marco79cgn
Copy link
Author

marco79cgn commented Jun 4, 2025

@profhccaesar
Ja, da hast du natürlich vollkommen Recht. Es ist der innere Monk. ;) Ich habe die Größe jetzt dennoch runter bekommen auf 223 MB. Deine Variante ist robuster, speziell was die ganzen Berechtigungen angeht. Ich habe jetzt dennoch alles mal in ein richtiges Github Repository geworfen. Das macht Änderungen am Skript einfacher und du kannst auch leichter die aktuelle Version verlinken.

https://github.com/marco79cgn/ard-plus-dl/tree/main

Dort wird auch automatisch ein Docker image gebaut via Github Actions zur direkten Verwendung (optional).

@horstepipe
Copy link

horstepipe commented Jul 13, 2025

Hallo zusammen,
ich bekomme leider auch folgenden Fehler, sowohl bei Serien als auch bei Filmen. Ist das Skript aktuell noch lauffähig?

~/Apps/ARDPlus$ ./ard-plus-dl.sh 'https://www.ardplus.de/details/a0S01000001xKyx-ein-brennender-sommer' 'user' 'password'
Couldn't get season details. Trying again!
cat: content-result.txt: No such file or directory
Lade Film  ()...
ERROR: [generic] None: '?' is not a valid URL. Set --default-search "ytsearch" (or run  yt-dlp "ytsearch:?" ) to search YouTube

Bekomme den Fehler sowohl bei Serien als auch bei Filmen.
curl 7.88.1 unter Debian
Unter dem Linuxsystem für Windows erscheint derselbe Fehler.

Jemand eine Idee?

@marco79cgn
Copy link
Author

@horstepipe
Copy link

mache ich, danke!

@bananateaa
Copy link

bananateaa commented Jul 14, 2025

Hallo,

ich bekomme auch den Fehler Login not possible! Please check credentials and subscription for user ....
Ich habe schon versuch mein Passwort so zu ändern, dass da keine Sonderzeichen mehr drin sind, in meiner Mailadresse ist jedoch ein +, könnte das ein Problem darstellen?

Ich habe das ganze über diesen Befehl laufen lassen:
docker run --rm -it -v $(pwd)/:/data ghcr.io/marco79cgn/ard-plus-dl download '<url>' 'username' 'password'

Soll ich das ganze mal ohne + in der Mailadresse probieren, oder kann es daran eigentlich nicht liegen?

Ich weiß nicht, ob das relevant ist, da ich das ja über den Docker Container gemacht habe, aber meine curl version ist 8.14.1

@marco79cgn
Copy link
Author

marco79cgn commented Jul 14, 2025

@bananateaa
Ich habe das Skript eben angepasst und explizit Username und Password url-encodiert. Könntest du es bitte nochmal probieren mit der neuesten Version? Also inklusive deiner Sonderzeichen?

Vorher die neue Version pullen: docker pull ghcr.io/marco79cgn/ard-plus-dl

@bananateaa
Copy link

bananateaa commented Jul 14, 2025

Top, danke dir!
Funktioniert jetzt und fängt an herunterzuladen 👍

(Danke auch, dass du noch erwähnt hast, dass und wie ich davor die neue Version pullen muss)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment