diff --git a/api/api_specification.json b/api/api_specification.json
index c9dc81f5c6959f6e483f60992de67b7e44268038..5dd606c02d7c1a9c883648d909661f4ae9ec3abd 100644
--- a/api/api_specification.json
+++ b/api/api_specification.json
@@ -3888,14 +3888,14 @@
     "publish_medium": {
       "fields": {
         "": {
-          "allow_download": {
+          "download_url": {
             "config_directly_modifiable": false,
-            "id": "allow_download",
-            "notes": "If true, this medium might be downloaded",
+            "id": "download_url",
+            "notes": "URL where the medium can be downloaded. If not present, the medium may not be downloaded",
             "object_variant": null,
             "only_mod": false,
-            "optional": false,
-            "type": "boolean"
+            "optional": true,
+            "type": "string"
           },
           "id": {
             "config_directly_modifiable": false,
diff --git a/api/api_specification.md b/api/api_specification.md
index 3be120b485e5913db752aaae3b1a32a7255b435c..f6433b828c84bab383d988df9d4c945d156d2834 100644
--- a/api/api_specification.md
+++ b/api/api_specification.md
@@ -1,4 +1,4 @@
-# Specification of the Web API for the Video-AG Website (v0.81).
+# Specification of the Web API for the Video-AG Website (v0.82).
 
 ## Introduction
 
@@ -2809,9 +2809,9 @@ Additionally, the following objects may appear as the type of some field:
 </thead>
 <tbody>
     <tr>
-        <td>allow_download</td>
-        <td>boolean</td>
-        <td>If true, this medium might be downloaded</td>
+        <td>download_url</td>
+        <td>?string</td>
+        <td>URL where the medium can be downloaded. If not present, the medium may not be downloaded</td>
     </tr>
     <tr>
         <td>id</td>
@@ -3188,6 +3188,12 @@ Possible `error_code`:
 
 ## Changelog
 
+### v0.82
+
+* Changed `publish_medium`
+  * Removed field `allow_download`
+  * Added field `download_url`
+
 ### v0.81
 
 * Added milliseconds to `datetime` type and clarified that it is in UTC.
diff --git a/api/api_specification_template.md b/api/api_specification_template.md
index 5b45245f9d0126639743c5c80df0e53f10eb37fa..03f847cae26fd486c562576fb1daf96f6772a0c4 100644
--- a/api/api_specification_template.md
+++ b/api/api_specification_template.md
@@ -1,4 +1,4 @@
-# Specification of the Web API for the Video-AG Website (v0.81).
+# Specification of the Web API for the Video-AG Website (v0.82).
 
 ## Introduction
 
@@ -139,6 +139,12 @@ Possible `error_code`:
 
 ## Changelog
 
+### v0.82
+
+* Changed `publish_medium`
+  * Removed field `allow_download`
+  * Added field `download_url`
+
 ### v0.81
 
 * Added milliseconds to `datetime` type and clarified that it is in UTC.
diff --git a/api/src/api/routes/resources.py b/api/src/api/routes/resources.py
index a54caaf26ed4365f5b49cd1b98bccd260d82a4e2..8e0ce296e896f535c7d35e1786d4fd0b2068606a 100644
--- a/api/src/api/routes/resources.py
+++ b/api/src/api/routes/resources.py
@@ -57,8 +57,10 @@ def _decode_str_from_url(url_val: str) -> str:
 @api_route("/course/<string:course_handle>/resources/medium_file/<int:medium_file_id>", "GET", allow_while_readonly=True,
            no_documentation=True)
 def api_route_access_target_medium(course_handle: str, medium_file_id: int):
+    download = request.args.get("download", "true").lower() == "true"
     medium_file = _check_access_medium_file(course_handle, medium_file_id)
-    return redirect(f"{_FILE_URI_PREFIX}/{medium_file.file_path}?co_ha={_encode_str_for_url(course_handle)}&mf_id={medium_file.id}")
+    # TODO download stats
+    return redirect(f"{_FILE_URI_PREFIX}/{medium_file.file_path}?co_ha={_encode_str_for_url(course_handle)}&mf_id={medium_file.id}&download={"true" if download else "false"}")
 
 
 @api_route("/resources/internal_auth_check", "GET", allow_while_readonly=True,
diff --git a/common_py/src/videoag_common/objects/medium.py b/common_py/src/videoag_common/objects/medium.py
index 6f90637f8227a55d4aec8790a05b0d577052a459..52a539c0db255e26111b4fd00a428f9706392c49 100644
--- a/common_py/src/videoag_common/objects/medium.py
+++ b/common_py/src/videoag_common/objects/medium.py
@@ -405,6 +405,13 @@ class PublishMedium(VisibilityApiObject, DeletableApiObject, Base):
     def url(self) -> str:
         return f"{_API_BASE_URL}/course/{self.lecture.course.handle}/resources/medium_file/{self.medium_metadata.file.id}"
     
+    @api_include_in_data(
+        data_notes="URL where the medium can be downloaded. If not present, the medium may not be downloaded",
+        data_if=lambda medium, args: medium.medium_metadata.can_download() and (args.is_mod or medium.lecture.course.allow_download)
+    )
+    def download_url(self) -> str:
+        return f"{_API_BASE_URL}/course/{self.lecture.course.handle}/resources/medium_file/{self.medium_metadata.file.id}?download=true"
+    
     @api_include_in_data(
         data_notes="If true, this medium might be shown with the player. Otherwise, the player should ignore it because"
                    " it is only intended for download, etc."
@@ -412,13 +419,6 @@ class PublishMedium(VisibilityApiObject, DeletableApiObject, Base):
     def include_in_player(self) -> bool:
         return self.medium_metadata.can_include_in_player()
     
-    @api_include_in_data(
-        data_notes="If true, this medium might be downloaded"
-    )
-    def allow_download(self, is_mod: bool) -> bool:
-        return (self.medium_metadata.can_download()
-                and (is_mod or self.lecture.course.allow_download))
-    
     @hybrid_method
     def has_access(self, context: dict[AccessContextKey, Any]):
         cond = super().has_access(context)
diff --git a/common_py/src/videoag_common/test/object_data.py b/common_py/src/videoag_common/test/object_data.py
index d3d6bb6996d9bcb6a8db4841d5d838a90587dd6e..1d768076ba67cea46620fa12dc9ffe7537f95db8 100644
--- a/common_py/src/videoag_common/test/object_data.py
+++ b/common_py/src/videoag_common/test/object_data.py
@@ -303,7 +303,7 @@ TEST_DATA_PUBLISH_MEDIUM_186 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_15,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/5",
-        "allow_download": True,
+        "download_url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/5?download=true",
         "include_in_player": True,
     }
 TEST_DATA_PUBLISH_MEDIUM_186_MOD = TEST_DATA_PUBLISH_MEDIUM_186 | \
@@ -317,7 +317,7 @@ TEST_DATA_PUBLISH_MEDIUM_204 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_16,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/9",
-        "allow_download": True,
+        "download_url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/9?download=true",
         "include_in_player": True,
     }
 TEST_DATA_PUBLISH_MEDIUM_204_MOD = TEST_DATA_PUBLISH_MEDIUM_204 | \
@@ -331,7 +331,7 @@ TEST_DATA_PUBLISH_MEDIUM_1368 = \
         "title": "Super video!",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_5,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/07ws-buk/resources/medium_file/6",
-        "allow_download": True,
+        "download_url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/07ws-buk/resources/medium_file/6?download=true",
         "include_in_player": True,
     }
 TEST_DATA_PUBLISH_MEDIUM_1368_MOD = TEST_DATA_PUBLISH_MEDIUM_1368 | \
@@ -345,7 +345,7 @@ TEST_DATA_PUBLISH_MEDIUM_1495 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_7,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/07ws-diskrete/resources/medium_file/7",
-        "allow_download": True,
+        "download_url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/07ws-diskrete/resources/medium_file/7?download=true",
         "include_in_player": True,
     }
 TEST_DATA_PUBLISH_MEDIUM_1495_MOD = TEST_DATA_PUBLISH_MEDIUM_1495 | \
@@ -359,13 +359,12 @@ TEST_DATA_PUBLISH_MEDIUM_1497 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_19,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/11ws-infin/resources/medium_file/8",
-        "allow_download": False,
         "include_in_player": True,
     }
 TEST_DATA_PUBLISH_MEDIUM_1497_MOD = TEST_DATA_PUBLISH_MEDIUM_1497 | \
     {
         "visible": True,
-        "allow_download": True,
+        "download_url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/11ws-infin/resources/medium_file/8?download=true",
     }
 
 TEST_DATA_PUBLISH_MEDIUM_100003 = \
@@ -374,7 +373,6 @@ TEST_DATA_PUBLISH_MEDIUM_100003 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_6,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/07ws-buk/resources/medium_file/1",
-        "allow_download": False,
         "include_in_player": False,
     }
 TEST_DATA_PUBLISH_MEDIUM_100003_MOD = TEST_DATA_PUBLISH_MEDIUM_100003 | \
@@ -388,7 +386,6 @@ TEST_DATA_PUBLISH_MEDIUM_100025 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_8,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/07ws-diskrete/resources/medium_file/2",
-        "allow_download": False,
         "include_in_player": False,
     }
 TEST_DATA_PUBLISH_MEDIUM_100025_MOD = TEST_DATA_PUBLISH_MEDIUM_100025 | \
@@ -402,7 +399,6 @@ TEST_DATA_PUBLISH_MEDIUM_100186 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_17,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/3",
-        "allow_download": False,
         "include_in_player": False,
     }
 TEST_DATA_PUBLISH_MEDIUM_100186_MOD = TEST_DATA_PUBLISH_MEDIUM_100186 | \
@@ -416,7 +412,6 @@ TEST_DATA_PUBLISH_MEDIUM_101186 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_20,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/11ws-infin/resources/medium_file/4",
-        "allow_download": False,
         "include_in_player": False,
     }
 TEST_DATA_PUBLISH_MEDIUM_101186_MOD = TEST_DATA_PUBLISH_MEDIUM_101186 | \
@@ -430,7 +425,7 @@ TEST_DATA_PUBLISH_MEDIUM_101189 = \
         "title": "",
         "medium_metadata": TEST_DATA_MEDIUM_METADATA_25,
         "url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/10",
-        "allow_download": True,
+        "download_url": "https://api.video.fsmpi.rwth-aachen.de/api/v0/course/09ss-fosap/resources/medium_file/10?download=true",
         "include_in_player": True,
     }
 TEST_DATA_PUBLISH_MEDIUM_101189_MOD = TEST_DATA_PUBLISH_MEDIUM_101189 | \