Skip to content

Commit 8db3f90

Browse files
Merge pull request #4 from Ryex/fix/fetch_mojang_out_of_date
fix: properly fetch out of date minecraft versions
2 parents 521462e + c0077ee commit 8db3f90

File tree

2 files changed

+46
-13
lines changed

2 files changed

+46
-13
lines changed

libmcmeta/src/models/mojang.rs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -55,10 +55,12 @@ pub struct MojangVersionManifestVersion {
5555
pub version_type: String,
5656
/// The URL to the version's JSON.
5757
pub url: String,
58-
/// The time the version was released.
59-
pub time: String,
6058
/// The time the version was last updated.
61-
pub release_time: String,
59+
#[serde(with = "time::serde::iso8601")]
60+
pub time: time::OffsetDateTime,
61+
/// The time the version was released.
62+
#[serde(with = "time::serde::iso8601")]
63+
pub release_time: time::OffsetDateTime,
6264
/// Compliance level
6365
pub compliance_level: i32,
6466
/// The sha1 hash of the version's JSON.

mcmeta/src/storage/mojang.rs

Lines changed: 41 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ async fn update_mojang_metadata_json(
7171

7272
info!("Acquiring remote Mojang metadata");
7373
let remote_manifest = download::mojang::load_manifest().await?;
74-
let remote_verions: HashMap<String, MojangVersionManifestVersion> = HashMap::from_iter(
74+
let remote_versions: HashMap<String, MojangVersionManifestVersion> = HashMap::from_iter(
7575
remote_manifest
7676
.versions
7777
.iter()
@@ -81,20 +81,50 @@ async fn update_mojang_metadata_json(
8181
HashSet::<String>::from_iter(remote_manifest.versions.iter().map(|v| v.id.clone()));
8282

8383
let local_manifest_path = mojang_meta_dir.join("version_manifest_v2.json");
84-
let pending_ids: Vec<String> = if !local_manifest_path.is_file() {
84+
let pending_ids: Vec<(String, bool)> = if !local_manifest_path.is_file() {
8585
info!("Local Mojang metadata does not exist, saving it");
8686
let manifest_json = serde_json::to_string_pretty(&remote_manifest)?;
8787
std::fs::write(&local_manifest_path, manifest_json)?;
8888

89-
remote_ids.into_iter().collect()
89+
remote_ids.into_iter().map(|id| (id, true)).collect()
9090
} else {
9191
let local_manifest = serde_json::from_str::<MojangVersionManifest>(
9292
&std::fs::read_to_string(&local_manifest_path)?,
9393
)?;
94+
let local_versions: HashMap<String, MojangVersionManifestVersion> = HashMap::from_iter(
95+
local_manifest
96+
.versions
97+
.iter()
98+
.map(|v| (v.id.clone(), v.clone())),
99+
);
94100
let local_ids =
95101
HashSet::<String>::from_iter(local_manifest.versions.iter().map(|v| v.id.clone()));
96102

97-
remote_ids.difference(&local_ids).cloned().collect()
103+
let mut diff: Vec<(String, bool)> = remote_ids
104+
.difference(&local_ids)
105+
.cloned()
106+
.map(|id| (id, false))
107+
.collect();
108+
let mut out_of_date: Vec<(String, bool)> = local_ids
109+
.iter()
110+
.filter_map(|id| {
111+
let remote_version = remote_versions
112+
.get(id)
113+
.expect("local version to exist remotely");
114+
let local_version = local_versions
115+
.get(id)
116+
.expect("local version to exist localy");
117+
if remote_version.time > local_version.time {
118+
Some(id)
119+
} else {
120+
None
121+
}
122+
})
123+
.cloned()
124+
.map(|id| (id, true))
125+
.collect();
126+
diff.append(&mut out_of_date);
127+
diff
98128
};
99129

100130
let versions_dir = mojang_meta_dir.join("versions");
@@ -108,11 +138,11 @@ async fn update_mojang_metadata_json(
108138
}
109139

110140
let tasks = stream::iter(pending_ids)
111-
.map(|version| {
112-
let v = remote_verions.get(&version).unwrap().clone();
141+
.map(|(version, force_update)| {
142+
let v = remote_versions.get(&version).unwrap().clone();
113143
let dir = versions_dir.clone();
114144
tokio::spawn(async move {
115-
update_mojang_version_manifest_json(&dir, &v)
145+
update_mojang_version_manifest_json(&dir, &v, force_update)
116146
.await
117147
.with_context(|| format!("Failed to initialize Mojang version {}", v.id))
118148
})
@@ -229,12 +259,13 @@ async fn update_mojang_static_metadata_json(
229259
pub async fn update_mojang_version_manifest_json(
230260
versions_dir: &std::path::Path,
231261
version: &MojangVersionManifestVersion,
262+
force_update: bool,
232263
) -> Result<()> {
233264
let version_file = versions_dir.join(format!("{}.json", &version.id));
234-
if !version_file.is_file() {
265+
if !version_file.is_file() || force_update {
235266
info!(
236-
"Mojang metadata for version {} does not exist, downloading it",
237-
&version.id
267+
"Updating Mojang metadata for version {} to timestamp {}",
268+
&version.id, &version.time
238269
);
239270
let version_manifest = download::mojang::load_version_manifest(&version.url)
240271
.await

0 commit comments

Comments
 (0)