1use crate::paths::remove_path_if_exists;
4use crate::registry_torrent::{fetch_torrent_artifact_to_path, fetch_torrent_manifest};
5use crate::PrayResult;
6use std::fs;
7use std::time::{SystemTime, UNIX_EPOCH};
8
9pub use crate::registry_http::{
10 http_get, http_get_with_headers, http_post, http_put, join_url, HttpResponse,
11};
12pub use crate::resource_limits::{MAX_HTTP_RESPONSE_BYTES, MAX_TORRENT_ARTIFACT_BYTES};
13
14pub fn download_registry_artifact(
16 source_url: &str,
17 artifact_relative_path: &str,
18) -> PrayResult<Vec<u8>> {
19 let artifact_url = join_url(source_url, artifact_relative_path);
20 if let Some(manifest) = fetch_torrent_manifest(source_url, artifact_relative_path)? {
21 let stamp = SystemTime::now()
22 .duration_since(UNIX_EPOCH)
23 .map(|duration| duration.as_nanos())
24 .unwrap_or(0);
25 let staging = std::env::temp_dir().join(format!("pray-torrent-{stamp}"));
26 fs::create_dir_all(&staging)?;
27 let destination = staging.join("package.praypkg");
28 let result = fetch_torrent_artifact_to_path(
29 source_url,
30 artifact_relative_path,
31 &manifest,
32 &destination,
33 );
34 let bytes = match result {
35 Ok(bytes) => bytes,
36 Err(error) => {
37 let _ = remove_path_if_exists(&staging);
38 return Err(error);
39 }
40 };
41 let _ = remove_path_if_exists(&staging);
42 return Ok(bytes);
43 }
44 http_get(&artifact_url)
45}