Fix metadata.json JsonParsingException crash (#1062)

* Load defualt metadata if the metadata.json gets corrupt

* Write to disk immediately to decrease the chances of corruption
This commit is contained in:
Xpl0itR 2020-04-23 13:01:23 +01:00 committed by GitHub
parent cdbb689b80
commit 72b560d15c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -1,4 +1,3 @@
using JsonPrettyPrinterPlus;
using LibHac; using LibHac;
using LibHac.Common; using LibHac.Common;
using LibHac.Fs; using LibHac.Fs;
@ -17,7 +16,6 @@ using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Globalization; using System.Globalization;
using System.IO; using System.IO;
using System.Linq;
using System.Reflection; using System.Reflection;
using System.Text; using System.Text;
using Utf8Json; using Utf8Json;
@ -511,7 +509,7 @@ namespace Ryujinx.Ui
string metadataFolder = Path.Combine(_virtualFileSystem.GetBasePath(), "games", titleId, "gui"); string metadataFolder = Path.Combine(_virtualFileSystem.GetBasePath(), "games", titleId, "gui");
string metadataFile = Path.Combine(metadataFolder, "metadata.json"); string metadataFile = Path.Combine(metadataFolder, "metadata.json");
IJsonFormatterResolver resolver = CompositeResolver.Create(new[] { StandardResolver.AllowPrivateSnakeCase }); IJsonFormatterResolver resolver = CompositeResolver.Create(StandardResolver.AllowPrivateSnakeCase);
ApplicationMetadata appMetadata; ApplicationMetadata appMetadata;
@ -526,21 +524,39 @@ namespace Ryujinx.Ui
LastPlayed = "Never" LastPlayed = "Never"
}; };
byte[] data = JsonSerializer.Serialize(appMetadata, resolver); using (FileStream stream = File.Create(metadataFile, 4096, FileOptions.WriteThrough))
File.WriteAllText(metadataFile, Encoding.UTF8.GetString(data, 0, data.Length).PrettyPrintJson()); {
JsonSerializer.Serialize(stream, appMetadata, resolver);
}
} }
using (Stream stream = File.OpenRead(metadataFile)) using (Stream stream = File.OpenRead(metadataFile))
{ {
appMetadata = JsonSerializer.Deserialize<ApplicationMetadata>(stream, resolver); try
{
appMetadata = JsonSerializer.Deserialize<ApplicationMetadata>(stream, resolver);
}
catch (JsonParsingException)
{
Logger.PrintWarning(LogClass.Application, $"Failed to parse metadata json for {titleId}. Loading defaults.");
appMetadata = new ApplicationMetadata
{
Favorite = false,
TimePlayed = 0,
LastPlayed = "Never"
};
}
} }
if (modifyFunction != null) if (modifyFunction != null)
{ {
modifyFunction(appMetadata); modifyFunction(appMetadata);
byte[] saveData = JsonSerializer.Serialize(appMetadata, resolver); using (FileStream stream = File.Create(metadataFile, 4096, FileOptions.WriteThrough))
File.WriteAllText(metadataFile, Encoding.UTF8.GetString(saveData, 0, saveData.Length).PrettyPrintJson()); {
JsonSerializer.Serialize(stream, appMetadata, resolver);
}
} }
return appMetadata; return appMetadata;