Google Drive: Fixed a crash that occurred on the first sync when enabling google drive integration

This commit is contained in:
Souryo 2016-09-07 17:05:08 -04:00
parent 9abebbb688
commit 5fbec9e87e
2 changed files with 45 additions and 23 deletions

View file

@ -38,7 +38,8 @@ namespace Mesen.GUI.GoogleDriveIntegration
try { try {
InteropEmu.DisplayMessage("GoogleDrive", "SynchronizationStarted"); InteropEmu.DisplayMessage("GoogleDrive", "SynchronizationStarted");
using(_accessor = new GoogleDriveAccessor()) { using(_accessor = new GoogleDriveAccessor()) {
if(!CloudSyncHelper.DownloadData()) { FileDownloadResult result = CloudSyncHelper.DownloadData();
if(result == FileDownloadResult.Error) {
InteropEmu.DisplayMessage("GoogleDrive", "SynchronizationFailed"); InteropEmu.DisplayMessage("GoogleDrive", "SynchronizationFailed");
return false; return false;
} }
@ -86,31 +87,39 @@ namespace Mesen.GUI.GoogleDriveIntegration
} }
} }
private static bool DownloadData() private static FileDownloadResult DownloadData()
{ {
using(MemoryStream stream = new MemoryStream()) { using(MemoryStream stream = new MemoryStream()) {
bool result = _accessor.DownloadFile(stream, "MesenData.zip"); FileDownloadResult result = _accessor.DownloadFile(stream, "MesenData.zip");
if(result) { if(result == FileDownloadResult.OK) {
stream.Position = 0; try {
stream.Position = 0;
string homeFolder = ConfigManager.HomeFolder; string homeFolder = ConfigManager.HomeFolder;
//Make sure the folders exist //Make sure the folders exist
string saveFolder = ConfigManager.SaveFolder; string saveFolder = ConfigManager.SaveFolder;
string saveStateFolder = ConfigManager.SaveStateFolder; string saveStateFolder = ConfigManager.SaveStateFolder;
using(ZipArchive archive = new ZipArchive(stream)) { using(ZipArchive archive = new ZipArchive(stream)) {
foreach(ZipArchiveEntry entry in archive.Entries) { foreach(ZipArchiveEntry entry in archive.Entries) {
if(!string.IsNullOrWhiteSpace(entry.Name)) { if(!string.IsNullOrWhiteSpace(entry.Name)) {
string[] fileAndFolder = entry.FullName.Split('/'); string[] fileAndFolder = entry.FullName.Split('/');
string fileName = Path.Combine(homeFolder, fileAndFolder[0], fileAndFolder[1]); string fileName = Path.Combine(homeFolder, fileAndFolder[0], fileAndFolder[1]);
if(!File.Exists(fileName) || File.GetLastWriteTime(fileName) < entry.LastWriteTime.ToLocalTime()) { if(!File.Exists(fileName) || File.GetLastWriteTime(fileName) < entry.LastWriteTime.ToLocalTime()) {
//File on server is more recent, or doesn't exist on local computer, extract it //File on server is more recent, or doesn't exist on local computer, extract it
entry.ExtractToFile(fileName, true); try {
entry.ExtractToFile(fileName, true);
} catch {
//Files might be opened by another program or not read-only, etc.
}
}
} }
} }
} }
} catch {
result = FileDownloadResult.FileCorrupted;
} }
} else if(_accessor.Revoked) { } else if(_accessor.Revoked) {
ConfigManager.Config.PreferenceInfo.CloudSaveIntegration = false; ConfigManager.Config.PreferenceInfo.CloudSaveIntegration = false;

View file

@ -12,6 +12,14 @@ using Google.Apis.Upload;
namespace Mesen.GUI.GoogleDriveIntegration namespace Mesen.GUI.GoogleDriveIntegration
{ {
public enum FileDownloadResult
{
OK = 0,
FileNotFound = 1,
Error = 2,
FileCorrupted = 3,
};
public class GoogleDriveAccessor : IDisposable public class GoogleDriveAccessor : IDisposable
{ {
private const string _contentType = @"application/zip"; private const string _contentType = @"application/zip";
@ -46,13 +54,13 @@ namespace Mesen.GUI.GoogleDriveIntegration
return _connected; return _connected;
} }
public bool DownloadFile(System.IO.MemoryStream fileStream, string filename) public FileDownloadResult DownloadFile(System.IO.MemoryStream fileStream, string filename)
{ {
try { try {
this.Connect().GetAwaiter().GetResult(); this.Connect().GetAwaiter().GetResult();
if(_connected) { if(_connected) {
this.DownloadFileAsync(fileStream, filename).GetAwaiter().GetResult(); return this.DownloadFileAsync(fileStream, filename).GetAwaiter().GetResult();
} }
} catch(TokenResponseException) { } catch(TokenResponseException) {
_revoked = true; _revoked = true;
@ -64,7 +72,7 @@ namespace Mesen.GUI.GoogleDriveIntegration
_credentials = null; _credentials = null;
_service = null; _service = null;
} }
return _connected; return FileDownloadResult.Error;
} }
public bool AcquireToken() public bool AcquireToken()
@ -168,7 +176,7 @@ namespace Mesen.GUI.GoogleDriveIntegration
return task; return task;
} }
private async Task DownloadFileAsync(System.IO.MemoryStream outStream, string filename) private async Task<FileDownloadResult> DownloadFileAsync(System.IO.MemoryStream outStream, string filename)
{ {
File driveFile = this.GetFileMatchingName(filename); File driveFile = this.GetFileMatchingName(filename);
@ -177,15 +185,20 @@ namespace Mesen.GUI.GoogleDriveIntegration
var progress = await request.DownloadAsync(outStream).ConfigureAwait(false); var progress = await request.DownloadAsync(outStream).ConfigureAwait(false);
if(progress.Status == DownloadStatus.Completed) { if(progress.Status == DownloadStatus.Completed) {
_driveFile = driveFile; _driveFile = driveFile;
return FileDownloadResult.OK;
} else { } else {
_driveFile = null; _driveFile = null;
return FileDownloadResult.Error;
} }
} }
return FileDownloadResult.FileNotFound;
} }
private async Task DeleteFile(File file) public async Task DeleteFile(string filename)
{ {
await _service.Files.Delete(file.Id).ExecuteAsync().ConfigureAwait(false); this.Connect().GetAwaiter().GetResult();
File driveFile = this.GetFileMatchingName(filename);
await _service.Files.Delete(driveFile.Id).ExecuteAsync().ConfigureAwait(false);
} }
void Upload_ResponseReceived(File file) void Upload_ResponseReceived(File file)