diff --git a/gaseous-server/Classes/ImportGames.cs b/gaseous-server/Classes/ImportGames.cs index fd2c474..c4c4aed 100644 --- a/gaseous-server/Classes/ImportGames.cs +++ b/gaseous-server/Classes/ImportGames.cs @@ -36,66 +36,84 @@ namespace gaseous_server.Classes public void ImportGameFile(string GameFileImportPath, bool IsDirectory = false) { - Logging.Log(Logging.LogType.Information, "Import Game", "Processing item " + GameFileImportPath); - if (IsDirectory == false) - { - FileInfo fi = new FileInfo(GameFileImportPath); - - // process as a single file - // check 1: do we have a signature for it? - Common.hashObject hash = new Common.hashObject(GameFileImportPath); - gaseous_server.Controllers.SignaturesController sc = new Controllers.SignaturesController(); - List signatures = sc.GetSignature(hash.md5hash); - if (signatures.Count == 0) - { - // no md5 signature found - try sha1 - signatures = sc.GetSignature("", hash.sha1hash); - } - - Models.Signatures_Games discoveredSignature = new Models.Signatures_Games(); - if (signatures.Count == 1) - { - // only 1 signature found! - discoveredSignature = signatures.ElementAt(0); - gaseous_server.Models.PlatformMapping.GetIGDBPlatformMapping(ref discoveredSignature, fi, false); - } - else if (signatures.Count > 1) - { - // more than one signature found - find one with highest score - foreach(Models.Signatures_Games Sig in signatures) - { - if (Sig.Score > discoveredSignature.Score) - { - discoveredSignature = Sig; - gaseous_server.Models.PlatformMapping.GetIGDBPlatformMapping(ref discoveredSignature, fi, false); - } - } - } - else - { - // no signature match found - try alternate methods - Models.Signatures_Games.GameItem gi = new Models.Signatures_Games.GameItem(); - Models.Signatures_Games.RomItem ri = new Models.Signatures_Games.RomItem(); - - // game title is the file name without the extension or path - gi.Name = Path.GetFileNameWithoutExtension(GameFileImportPath); - - // guess platform - gaseous_server.Models.PlatformMapping.GetIGDBPlatformMapping(ref discoveredSignature, fi, true); - - // get rom data - ri.Name = Path.GetFileName(GameFileImportPath); - ri.Md5 = hash.md5hash; - ri.Sha1 = hash.sha1hash; - - discoveredSignature.Game = gi; - discoveredSignature.Rom = ri; - } - - //Console.WriteLine(Newtonsoft.Json.JsonConvert.SerializeObject(discoveredSignature)); - - IGDB.Models.Platform determinedPlatform = Metadata.Platforms.GetPlatform(discoveredSignature.Flags.IGDBPlatformId); + if (String.Equals(Path.GetFileName(GameFileImportPath),".DS_STORE", StringComparison.OrdinalIgnoreCase)) + { + Logging.Log(Logging.LogType.Information, "Import Game", "Skipping item " + GameFileImportPath); } + else + { + Logging.Log(Logging.LogType.Information, "Import Game", "Processing item " + GameFileImportPath); + if (IsDirectory == false) + { + FileInfo fi = new FileInfo(GameFileImportPath); + + // process as a single file + // check 1: do we have a signature for it? + Common.hashObject hash = new Common.hashObject(GameFileImportPath); + gaseous_server.Controllers.SignaturesController sc = new Controllers.SignaturesController(); + List signatures = sc.GetSignature(hash.md5hash); + if (signatures.Count == 0) + { + // no md5 signature found - try sha1 + signatures = sc.GetSignature("", hash.sha1hash); + } + + Models.Signatures_Games discoveredSignature = new Models.Signatures_Games(); + if (signatures.Count == 1) + { + // only 1 signature found! + discoveredSignature = signatures.ElementAt(0); + gaseous_server.Models.PlatformMapping.GetIGDBPlatformMapping(ref discoveredSignature, fi, false); + } + else if (signatures.Count > 1) + { + // more than one signature found - find one with highest score + foreach (Models.Signatures_Games Sig in signatures) + { + if (Sig.Score > discoveredSignature.Score) + { + discoveredSignature = Sig; + gaseous_server.Models.PlatformMapping.GetIGDBPlatformMapping(ref discoveredSignature, fi, false); + } + } + } + else + { + // no signature match found - try alternate methods + Models.Signatures_Games.GameItem gi = new Models.Signatures_Games.GameItem(); + Models.Signatures_Games.RomItem ri = new Models.Signatures_Games.RomItem(); + + discoveredSignature.Game = gi; + discoveredSignature.Rom = ri; + + // game title is the file name without the extension or path + gi.Name = Path.GetFileNameWithoutExtension(GameFileImportPath); + + // guess platform + gaseous_server.Models.PlatformMapping.GetIGDBPlatformMapping(ref discoveredSignature, fi, true); + + // get rom data + ri.Name = Path.GetFileName(GameFileImportPath); + ri.Md5 = hash.md5hash; + ri.Sha1 = hash.sha1hash; + } + + Console.WriteLine("Importing " + discoveredSignature.Game.Name + " (" + discoveredSignature.Game.Year + ") " + discoveredSignature.Game.System); + // get discovered platform + IGDB.Models.Platform determinedPlatform = Metadata.Platforms.GetPlatform(discoveredSignature.Flags.IGDBPlatformId); + // search discovered game + IGDB.Models.Game[] games = Metadata.Games.SearchForGame(discoveredSignature.Game.Name, discoveredSignature.Flags.IGDBPlatformId, Metadata.Games.SearchType.where); + if (games.Length == 0) + { + games = Metadata.Games.SearchForGame(discoveredSignature.Game.Name, discoveredSignature.Flags.IGDBPlatformId, Metadata.Games.SearchType.search); + } + if (games.Length > 0) + { + IGDB.Models.Game determinedGame = Metadata.Games.GetGame((long)games[0].Id); + Console.WriteLine(" IGDB game: " + determinedGame.Name); + } + } + } } } } diff --git a/gaseous-server/Classes/Metadata/Artworks.cs b/gaseous-server/Classes/Metadata/Artworks.cs new file mode 100644 index 0000000..4348941 --- /dev/null +++ b/gaseous-server/Classes/Metadata/Artworks.cs @@ -0,0 +1,168 @@ +using System; +using gaseous_tools; +using IGDB; +using IGDB.Models; +using MySqlX.XDevAPI.Common; +using static gaseous_tools.Config.ConfigFile; + +namespace gaseous_server.Classes.Metadata +{ + public class Artworks + { + const string fieldList = "fields alpha_channel,animated,checksum,game,height,image_id,url,width;"; + + public Artworks() + { + } + + private static IGDBClient igdb = new IGDBClient( + // Found in Twitch Developer portal for your app + Config.IGDB.ClientId, + Config.IGDB.Secret + ); + + public static Artwork? GetArtwork(long? Id, string LogoPath) + { + if ((Id == 0) || (Id == null)) + { + return null; + } + else + { + Task RetVal = _GetArtwork(SearchUsing.id, Id, LogoPath); + return RetVal.Result; + } + } + + public static Artwork GetArtwork(string Slug, string LogoPath) + { + Task RetVal = _GetArtwork(SearchUsing.slug, Slug, LogoPath); + return RetVal.Result; + } + + private static async Task _GetArtwork(SearchUsing searchUsing, object searchValue, string LogoPath) + { + // check database first + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("Artwork", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("Artwork", (string)searchValue); + } + + // set up where clause + string WhereClause = ""; + switch (searchUsing) + { + case SearchUsing.id: + WhereClause = "where id = " + searchValue; + break; + case SearchUsing.slug: + WhereClause = "where slug = " + searchValue; + break; + default: + throw new Exception("Invalid search type"); + } + + Artwork returnValue = new Artwork(); + bool forceImageDownload = false; + LogoPath = Path.Combine(LogoPath, "Artwork"); + switch (cacheStatus) + { + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue); + forceImageDownload = true; + break; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue, true); + forceImageDownload = true; + break; + case Storage.CacheStatus.Current: + returnValue = Storage.GetCacheValue(returnValue, "id", (long)searchValue); + break; + default: + throw new Exception("How did you get here?"); + } + + if ((!File.Exists(Path.Combine(LogoPath, returnValue.ImageId + ".jpg"))) || forceImageDownload == true) + { + //GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_thumb, returnValue.ImageId); + //GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_logo_med, returnValue.ImageId); + GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_original, returnValue.ImageId); + } + + return returnValue; + } + + private enum SearchUsing + { + id, + slug + } + + private static async Task GetObjectFromServer(string WhereClause, string LogoPath) + { + // get Artwork metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.Artworks, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); + + //GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId); + //GetImageFromServer(result.Url, LogoPath, LogoSize.t_logo_med, result.ImageId); + GetImageFromServer(result.Url, LogoPath, LogoSize.t_original, result.ImageId); + + return result; + } + + private static void GetImageFromServer(string Url, string LogoPath, LogoSize logoSize, string ImageId) + { + using (var client = new HttpClient()) + { + string fileName = "Artwork.jpg"; + string extension = "jpg"; + switch (logoSize) + { + case LogoSize.t_thumb: + fileName = "_Thumb"; + extension = "jpg"; + break; + case LogoSize.t_logo_med: + fileName = "_Medium"; + extension = "png"; + break; + case LogoSize.t_original: + fileName = "_Original"; + extension = "png"; + break; + default: + fileName = "Artwork"; + extension = "jpg"; + break; + } + fileName = ImageId + fileName; + string imageUrl = Url.Replace(LogoSize.t_thumb.ToString(), logoSize.ToString()).Replace("jpg", extension); + + using (var s = client.GetStreamAsync("https:" + imageUrl)) + { + if (!Directory.Exists(LogoPath)) { Directory.CreateDirectory(LogoPath); } + using (var fs = new FileStream(Path.Combine(LogoPath, fileName + "." + extension), FileMode.OpenOrCreate)) + { + s.Result.CopyTo(fs); + } + } + } + } + + private enum LogoSize + { + t_thumb, + t_logo_med, + t_original + } + } +} + diff --git a/gaseous-server/Classes/Metadata/Covers.cs b/gaseous-server/Classes/Metadata/Covers.cs new file mode 100644 index 0000000..a0276cc --- /dev/null +++ b/gaseous-server/Classes/Metadata/Covers.cs @@ -0,0 +1,166 @@ +using System; +using gaseous_tools; +using IGDB; +using IGDB.Models; +using MySqlX.XDevAPI.Common; +using static gaseous_tools.Config.ConfigFile; + +namespace gaseous_server.Classes.Metadata +{ + public class Covers + { + const string fieldList = "fields alpha_channel,animated,checksum,game,height,image_id,url,width;"; + + public Covers() + { + } + + private static IGDBClient igdb = new IGDBClient( + // Found in Twitch Developer portal for your app + Config.IGDB.ClientId, + Config.IGDB.Secret + ); + + public static Cover? GetCover(long? Id, string LogoPath) + { + if ((Id == 0) || (Id == null)) + { + return null; + } + else + { + Task RetVal = _GetCover(SearchUsing.id, Id, LogoPath); + return RetVal.Result; + } + } + + public static Cover GetCover(string Slug, string LogoPath) + { + Task RetVal = _GetCover(SearchUsing.slug, Slug, LogoPath); + return RetVal.Result; + } + + private static async Task _GetCover(SearchUsing searchUsing, object searchValue, string LogoPath) + { + // check database first + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("Cover", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("Cover", (string)searchValue); + } + + // set up where clause + string WhereClause = ""; + switch (searchUsing) + { + case SearchUsing.id: + WhereClause = "where id = " + searchValue; + break; + case SearchUsing.slug: + WhereClause = "where slug = " + searchValue; + break; + default: + throw new Exception("Invalid search type"); + } + + Cover returnValue = new Cover(); + bool forceImageDownload = false; + switch (cacheStatus) + { + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue); + forceImageDownload = true; + break; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue, true); + forceImageDownload = true; + break; + case Storage.CacheStatus.Current: + returnValue = Storage.GetCacheValue(returnValue, "id", (long)searchValue); + break; + default: + throw new Exception("How did you get here?"); + } + + if ((!File.Exists(Path.Combine(LogoPath, "Cover.jpg"))) || forceImageDownload == true) + { + //GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_thumb, returnValue.ImageId); + //GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_logo_med, returnValue.ImageId); + GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_original, returnValue.ImageId); + } + + return returnValue; + } + + private enum SearchUsing + { + id, + slug + } + + private static async Task GetObjectFromServer(string WhereClause, string LogoPath) + { + // get Cover metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.Covers, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); + + //GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId); + //GetImageFromServer(result.Url, LogoPath, LogoSize.t_logo_med, result.ImageId); + GetImageFromServer(result.Url, LogoPath, LogoSize.t_original, result.ImageId); + + return result; + } + + private static void GetImageFromServer(string Url, string LogoPath, LogoSize logoSize, string ImageId) + { + using (var client = new HttpClient()) + { + string fileName = "Cover.jpg"; + string extension = "jpg"; + switch (logoSize) + { + case LogoSize.t_thumb: + fileName = "Cover_Thumb"; + extension = "jpg"; + break; + case LogoSize.t_logo_med: + fileName = "Cover_Medium"; + extension = "png"; + break; + case LogoSize.t_original: + fileName = "Cover_Original"; + extension = "png"; + break; + default: + fileName = "Cover"; + extension = "jpg"; + break; + } + string imageUrl = Url.Replace(LogoSize.t_thumb.ToString(), logoSize.ToString()).Replace("jpg", extension); + + using (var s = client.GetStreamAsync("https:" + imageUrl)) + { + if (!Directory.Exists(LogoPath)) { Directory.CreateDirectory(LogoPath); } + using (var fs = new FileStream(Path.Combine(LogoPath, fileName + "." + extension), FileMode.OpenOrCreate)) + { + s.Result.CopyTo(fs); + } + } + } + } + + private enum LogoSize + { + t_thumb, + t_logo_med, + t_original + } + } +} + diff --git a/gaseous-server/Classes/Metadata/Games.cs b/gaseous-server/Classes/Metadata/Games.cs new file mode 100644 index 0000000..27dc20d --- /dev/null +++ b/gaseous-server/Classes/Metadata/Games.cs @@ -0,0 +1,167 @@ +using System; +using gaseous_tools; +using IGDB; +using IGDB.Models; + +namespace gaseous_server.Classes.Metadata +{ + public class Games + { + const string fieldList = "fields age_ratings,aggregated_rating,aggregated_rating_count,alternative_names,artworks,bundles,category,checksum,collection,cover,created_at,dlcs,expanded_games,expansions,external_games,first_release_date,follows,forks,franchise,franchises,game_engines,game_localizations,game_modes,genres,hypes,involved_companies,keywords,language_supports,multiplayer_modes,name,parent_game,platforms,player_perspectives,ports,rating,rating_count,release_dates,remakes,remasters,screenshots,similar_games,slug,standalone_expansions,status,storyline,summary,tags,themes,total_rating,total_rating_count,updated_at,url,version_parent,version_title,videos,websites;"; + + public Games() + { + + } + + private static IGDBClient igdb = new IGDBClient( + // Found in Twitch Developer portal for your app + Config.IGDB.ClientId, + Config.IGDB.Secret + ); + + public static Game? GetGame(long Id) + { + if (Id == 0) + { + return null; + } + else + { + Task RetVal = _GetGame(SearchUsing.id, Id); + return RetVal.Result; + } + } + + public static Game GetGame(string Slug) + { + Task RetVal = _GetGame(SearchUsing.slug, Slug); + return RetVal.Result; + } + + private static async Task _GetGame(SearchUsing searchUsing, object searchValue) + { + // check database first + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("Game", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("Game", (string)searchValue); + } + + // set up where clause + string WhereClause = ""; + switch (searchUsing) + { + case SearchUsing.id: + WhereClause = "where id = " + searchValue; + break; + case SearchUsing.slug: + WhereClause = "where slug = " + searchValue; + break; + default: + throw new Exception("Invalid search type"); + } + + Game returnValue = new Game(); + switch (cacheStatus) + { + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause); + Storage.NewCacheValue(returnValue); + UpdateSubClasses(returnValue); + return returnValue; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause); + Storage.NewCacheValue(returnValue, true); + UpdateSubClasses(returnValue); + return returnValue; + case Storage.CacheStatus.Current: + return Storage.GetCacheValue(returnValue, "id", (long)searchValue); + default: + throw new Exception("How did you get here?"); + } + } + + private static void UpdateSubClasses(Game Game) + { + if (Game.Artworks != null) + { + foreach (long ArtworkId in Game.Artworks.Ids) + { + Artwork GameArtwork = Artworks.GetArtwork(ArtworkId, Config.LibraryConfiguration.LibraryMetadataDirectory_Game(Game)); + } + } + if (Game.Cover != null) + { + Cover GameCover = Covers.GetCover(Game.Cover.Id, Config.LibraryConfiguration.LibraryMetadataDirectory_Game(Game)); + } + if (Game.Platforms != null) + { + foreach (long PlatformId in Game.Platforms.Ids) + { + Platform GamePlatform = Platforms.GetPlatform(PlatformId); + } + } + if (Game.Screenshots != null) + { + foreach (long ScreenshotId in Game.Screenshots.Ids) + { + Screenshot GameScreenshot = Screenshots.GetScreenshot(ScreenshotId, Config.LibraryConfiguration.LibraryMetadataDirectory_Game(Game)); + } + } + } + + private enum SearchUsing + { + id, + slug + } + + private static async Task GetObjectFromServer(string WhereClause) + { + // get Game metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.Games, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); + + return result; + } + + public static Game[] SearchForGame(string SearchString, long PlatformId, SearchType searchType) + { + Task games = _SearchForGame(SearchString, PlatformId, searchType); + return games.Result; + } + + private static async Task _SearchForGame(string SearchString, long PlatformId, SearchType searchType) + { + string searchBody = ""; + searchBody += "fields id,name,slug,platforms,summary; "; + switch (searchType) + { + case SearchType.search: + searchBody += "search \"" + SearchString + "\"; "; + searchBody += "where platforms = (" + PlatformId + ");"; + break; + case SearchType.where: + searchBody += "where platforms = (" + PlatformId + ") & name ~ *\"" + SearchString + "\"*;"; + break; + } + + + // get Game metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.Games, query: searchBody); + + return results; + } + + public enum SearchType + { + where, + search + } + } +} \ No newline at end of file diff --git a/gaseous-server/Classes/Metadata/PlatformLogos.cs b/gaseous-server/Classes/Metadata/PlatformLogos.cs index aeefb33..f873dad 100644 --- a/gaseous-server/Classes/Metadata/PlatformLogos.cs +++ b/gaseous-server/Classes/Metadata/PlatformLogos.cs @@ -9,6 +9,8 @@ namespace gaseous_server.Classes.Metadata { public class PlatformLogos { + const string fieldList = "fields alpha_channel,animated,checksum,height,image_id,url,width;"; + public PlatformLogos() { } @@ -19,23 +21,139 @@ namespace gaseous_server.Classes.Metadata Config.IGDB.Secret ); - public async static void GetPlatformLogo(long Id, string LogoPath) + public static PlatformLogo? GetPlatformLogo(long? Id, string LogoPath) { - var logo_results = await igdb.QueryAsync(IGDBClient.Endpoints.PlatformLogos, query: "fields alpha_channel,animated,checksum,height,image_id,url,width; where id = " + Id + ";"); - var logo_result = logo_results.First(); + if ((Id == 0) || (Id == null)) + { + return null; + } + else + { + Task RetVal = _GetPlatformLogo(SearchUsing.id, Id, LogoPath); + return RetVal.Result; + } + } + public static PlatformLogo GetPlatformLogo(string Slug, string LogoPath) + { + Task RetVal = _GetPlatformLogo(SearchUsing.slug, Slug, LogoPath); + return RetVal.Result; + } + + private static async Task _GetPlatformLogo(SearchUsing searchUsing, object searchValue, string LogoPath) + { + // check database first + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("PlatformLogo", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("PlatformLogo", (string)searchValue); + } + + // set up where clause + string WhereClause = ""; + switch (searchUsing) + { + case SearchUsing.id: + WhereClause = "where id = " + searchValue; + break; + case SearchUsing.slug: + WhereClause = "where slug = " + searchValue; + break; + default: + throw new Exception("Invalid search type"); + } + + PlatformLogo returnValue = new PlatformLogo(); + bool forceImageDownload = false; + switch (cacheStatus) + { + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue); + forceImageDownload = true; + break; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue, true); + forceImageDownload = true; + break; + case Storage.CacheStatus.Current: + returnValue = Storage.GetCacheValue(returnValue, "id", (long)searchValue); + break; + default: + throw new Exception("How did you get here?"); + } + + if ((!File.Exists(Path.Combine(LogoPath, "Logo.jpg"))) || forceImageDownload == true) + { + GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_thumb); + GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_logo_med); + } + + return returnValue; + } + + private enum SearchUsing + { + id, + slug + } + + private static async Task GetObjectFromServer(string WhereClause, string LogoPath) + { + // get PlatformLogo metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.PlatformLogos, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); + + GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb); + GetImageFromServer(result.Url, LogoPath, LogoSize.t_logo_med); + + return result; + } + + private static void GetImageFromServer(string Url, string LogoPath, LogoSize logoSize) + { using (var client = new HttpClient()) { - using (var s = client.GetStreamAsync("https:" + logo_result.Url)) + string fileName = "Logo.jpg"; + string extension = "jpg"; + switch (logoSize) { - if (!Directory.Exists(Path.GetDirectoryName(LogoPath))) { Directory.CreateDirectory(Path.GetDirectoryName(LogoPath)); } - using (var fs = new FileStream(LogoPath, FileMode.OpenOrCreate)) + case LogoSize.t_thumb: + fileName = "Logo_Thumb"; + extension = "jpg"; + break; + case LogoSize.t_logo_med: + fileName = "Logo_Medium"; + extension = "png"; + break; + default: + fileName = "Logo"; + extension = "jpg"; + break; + } + string imageUrl = Url.Replace(LogoSize.t_thumb.ToString(), logoSize.ToString()).Replace("jpg", extension); + + using (var s = client.GetStreamAsync("https:" + imageUrl)) + { + if (!Directory.Exists(LogoPath)) { Directory.CreateDirectory(LogoPath); } + using (var fs = new FileStream(Path.Combine(LogoPath, fileName + "." + extension), FileMode.OpenOrCreate)) { s.Result.CopyTo(fs); } } } } + + private enum LogoSize + { + t_thumb, + t_logo_med + } } } diff --git a/gaseous-server/Classes/Metadata/PlatformVersions.cs b/gaseous-server/Classes/Metadata/PlatformVersions.cs index cfb3ee7..a15f6a0 100644 --- a/gaseous-server/Classes/Metadata/PlatformVersions.cs +++ b/gaseous-server/Classes/Metadata/PlatformVersions.cs @@ -8,53 +8,23 @@ namespace gaseous_server.Classes.Metadata { public class PlatformVersions { - public PlatformVersions() + const string fieldList = "fields checksum,companies,connectivity,cpu,graphics,main_manufacturer,media,memory,name,online,os,output,platform_logo,platform_version_release_dates,resolutions,slug,sound,storage,summary,url;"; + + public PlatformVersions() { } - public static PlatformVersion UnknownPlatformVersion - { - get - { - PlatformVersion unkownPlatformVersion = new PlatformVersion - { - Id = 0, - Checksum = "", - Companies = new IdentitiesOrValues(), - Connectivity = "", - CPU = "", - Graphics = "", - MainManufacturer = new IdentityOrValue(0), - Media = "", - Memory = "", - Name = "Unknown", - OS = "", - Output = "", - PlatformLogo = new IdentityOrValue(0), - PlatformVersionReleaseDates = new IdentitiesOrValues(), - Resolutions = "", - Slug = "Unknown", - Sound = "", - Storage = "", - Summary = "", - Url = "" - }; - - return unkownPlatformVersion; - } - } - private static IGDBClient igdb = new IGDBClient( // Found in Twitch Developer portal for your app Config.IGDB.ClientId, Config.IGDB.Secret ); - public static PlatformVersion GetPlatformVersion(long Id, Platform ParentPlatform) + public static PlatformVersion? GetPlatformVersion(long Id, Platform ParentPlatform) { if (Id == 0) { - return UnknownPlatformVersion; + return null; } else { @@ -72,7 +42,15 @@ namespace gaseous_server.Classes.Metadata private static async Task _GetPlatformVersion(SearchUsing searchUsing, object searchValue, Platform ParentPlatform) { // check database first - PlatformVersion? platformVersion = DBGetPlatformVersion(searchUsing, searchValue); + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("PlatformVersion", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("PlatformVersion", (string)searchValue); + } // set up where clause string WhereClause = ""; @@ -88,45 +66,31 @@ namespace gaseous_server.Classes.Metadata throw new Exception("Invalid search type"); } - if (platformVersion == null) + PlatformVersion returnValue = new PlatformVersion(); + switch (cacheStatus) { - // get platform version metadata - var results = await igdb.QueryAsync(IGDBClient.Endpoints.PlatformVersions, query: "fields checksum,companies,connectivity,cpu,graphics,main_manufacturer,media,memory,name,online,os,output,platform_logo,platform_version_release_dates,resolutions,slug,sound,storage,summary,url; " + WhereClause + ";"); - var result = results.First(); - - DBInsertPlatformVersion(result, true); - - // get platform logo - if (result.PlatformLogo != null) - { - PlatformLogos.GetPlatformLogo((long)result.PlatformLogo.Id, Path.Combine(Config.LibraryConfiguration.LibraryMetadataDirectory_Platform(ParentPlatform), result.Slug, "platform_logo.jpg")); - } - - return result; - } - else - { - return platformVersion; + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause); + Storage.NewCacheValue(returnValue); + UpdateSubClasses(ParentPlatform, returnValue); + return returnValue; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause); + Storage.NewCacheValue(returnValue, true); + UpdateSubClasses(ParentPlatform, returnValue); + return returnValue; + case Storage.CacheStatus.Current: + return Storage.GetCacheValue(returnValue, "id", (long)searchValue); + default: + throw new Exception("How did you get here?"); } } - private static PlatformVersion? DBGetPlatformVersion(SearchUsing searchUsing, object searchValue) + private static void UpdateSubClasses(Platform ParentPlatform, PlatformVersion platformVersion) { - Dictionary dbDict = new Dictionary(); - switch (searchUsing) + if (platformVersion.PlatformLogo != null) { - case SearchUsing.id: - dbDict.Add("id", searchValue); - - return _DBGetPlatformVersion("SELECT * FROM platforms_versions WHERE id = @id", dbDict); - - case SearchUsing.slug: - dbDict.Add("slug", searchValue); - - return _DBGetPlatformVersion("SELECT * FROM platforms_versions WHERE slug = @slug", dbDict); - - default: - throw new Exception("Invalid Search Type"); + PlatformLogo platformLogo = PlatformLogos.GetPlatformLogo(platformVersion.PlatformLogo.Id, Path.Combine(Config.LibraryConfiguration.LibraryMetadataDirectory_Platform(ParentPlatform), "Versions", platformVersion.Slug)); } } @@ -136,104 +100,13 @@ namespace gaseous_server.Classes.Metadata slug } - private static PlatformVersion? _DBGetPlatformVersion(string sql, Dictionary searchParams) + private static async Task GetObjectFromServer(string WhereClause) { - Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); + // get PlatformVersion metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.PlatformVersions, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); - DataTable dbResponse = db.ExecuteCMD(sql, searchParams); - - if (dbResponse.Rows.Count > 0) - { - return ConvertDataRowToPlatformVersion(dbResponse.Rows[0]); - } - else - { - return null; - } - } - - private static PlatformVersion ConvertDataRowToPlatformVersion(DataRow PlatformDR) - { - PlatformVersion returnPlatformVersion = new PlatformVersion - { - Id = (long)(UInt64)PlatformDR["id"], - Checksum = (string?)PlatformDR["checksum"], - Companies = Newtonsoft.Json.JsonConvert.DeserializeObject>((string?)PlatformDR["companies"]), - Connectivity = (string?)PlatformDR["connectivity"], - CPU = (string?)PlatformDR["cpu"], - Graphics = (string?)PlatformDR["graphics"], - MainManufacturer = new IdentityOrValue((int?)PlatformDR["main_manufacturer"]), - Media = (string?)PlatformDR["media"], - Memory = (string?)PlatformDR["memory"], - Name = (string?)PlatformDR["name"], - OS = (string?)PlatformDR["os"], - Output = (string?)PlatformDR["output"], - PlatformLogo = new IdentityOrValue((int?)PlatformDR["platform_logo"]), - PlatformVersionReleaseDates = Newtonsoft.Json.JsonConvert.DeserializeObject>((string?)PlatformDR["platform_version_release_dates"]), - Resolutions = (string?)PlatformDR["resolutions"], - Slug = (string?)PlatformDR["slug"], - Sound = (string?)PlatformDR["sound"], - Storage = (string?)PlatformDR["storage"], - Summary = (string?)PlatformDR["summary"], - Url = (string?)PlatformDR["url"] - }; - - return returnPlatformVersion; - } - - private static void DBInsertPlatformVersion(PlatformVersion PlatformVersionItem, bool Insert) - { - Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); - string sql = "INSERT INTO platforms_versions (id, checksum, connectivity, cpu, graphics, main_manufacturer, media, memory, name, os, output, platform_logo, platform_version_release_dates, resolutions, slug, sound, storage, summary, url, dateAdded, lastUpdated) VALUES (@id, @checksum, @connectivity, @cpu, @graphics, @main_manufacturer, @media, @memory, @name, @os, @output, @platform_logo, @platform_version_release_dates, @resolutions, @slug, @sound, @storage, @summary, @url, @lastUpdated, @lastUpdated)"; - if (Insert == false) - { - sql = "UPDATE platforms_versions SET checksum=@checksum, connectivity=@connectivity, cpu=@cpu, graphics=@graphics, main_manufacturer=@main_manufacturer, media=@media, memory=@memory, name=@name, os=@os, output=@output, platform_logo=@platform_logo, platform_version_release_dates=@platform_version_release_dates, resolutions=@resolutions, slug=@slug, sound=@sound, storage=@storage, summary=@summary, url=@url, lastUpdated=@lastUpdated WHERE id=@id"; - } - Dictionary dbDict = new Dictionary(); - string EmptyJson = "{\"Ids\": [], \"Values\": null}"; - dbDict.Add("id", PlatformVersionItem.Id); - dbDict.Add("checksum", Common.ReturnValueIfNull(PlatformVersionItem.Checksum, "")); - dbDict.Add("connectivity", Common.ReturnValueIfNull(PlatformVersionItem.Connectivity, "")); - dbDict.Add("cpu", Common.ReturnValueIfNull(PlatformVersionItem.CPU, "")); - dbDict.Add("graphics", Common.ReturnValueIfNull(PlatformVersionItem.Graphics, "")); - if (PlatformVersionItem.MainManufacturer == null) - { - dbDict.Add("main_manufacturer", 0); - } - else - { - dbDict.Add("main_manufacturer", Common.ReturnValueIfNull(PlatformVersionItem.MainManufacturer.Id, 0)); - } - dbDict.Add("media", Common.ReturnValueIfNull(PlatformVersionItem.Media, "")); - dbDict.Add("memory", Common.ReturnValueIfNull(PlatformVersionItem.Memory, "")); - dbDict.Add("name", Common.ReturnValueIfNull(PlatformVersionItem.Name, "")); - dbDict.Add("os", Common.ReturnValueIfNull(PlatformVersionItem.OS, "")); - dbDict.Add("output", Common.ReturnValueIfNull(PlatformVersionItem.Output, "")); - if (PlatformVersionItem.PlatformLogo == null) - { - dbDict.Add("platform_logo", 0); - } - else - { - dbDict.Add("platform_logo", Common.ReturnValueIfNull(PlatformVersionItem.PlatformLogo.Id, 0)); - } - if (PlatformVersionItem.PlatformVersionReleaseDates == null) - { - dbDict.Add("platform_version_release_dates", EmptyJson); - } - else - { - dbDict.Add("platform_version_release_dates", Newtonsoft.Json.JsonConvert.SerializeObject(PlatformVersionItem.PlatformVersionReleaseDates)); - } - dbDict.Add("resolutions", Common.ReturnValueIfNull(PlatformVersionItem.Resolutions, "")); - dbDict.Add("slug", Common.ReturnValueIfNull(PlatformVersionItem.Slug, "")); - dbDict.Add("sound", Common.ReturnValueIfNull(PlatformVersionItem.Sound, "")); - dbDict.Add("storage", Common.ReturnValueIfNull(PlatformVersionItem.Storage, "")); - dbDict.Add("summary", Common.ReturnValueIfNull(PlatformVersionItem.Summary, "")); - dbDict.Add("url", Common.ReturnValueIfNull(PlatformVersionItem.Url, "")); - dbDict.Add("lastUpdated", DateTime.UtcNow); - - db.ExecuteCMD(sql, dbDict); + return result; } } } diff --git a/gaseous-server/Classes/Metadata/Platforms.cs b/gaseous-server/Classes/Metadata/Platforms.cs index d181b29..93ad177 100644 --- a/gaseous-server/Classes/Metadata/Platforms.cs +++ b/gaseous-server/Classes/Metadata/Platforms.cs @@ -7,51 +7,26 @@ using IGDB.Models; namespace gaseous_server.Classes.Metadata { - public class Platforms + public class Platforms { - public Platforms() + const string fieldList = "fields abbreviation,alternative_name,category,checksum,created_at,generation,name,platform_family,platform_logo,slug,summary,updated_at,url,versions,websites;"; + + public Platforms() { + } - public static Platform UnknownPlatform - { - get - { - Platform unkownPlatform = new Platform - { - Id = 0, - Abbreviation = "", - AlternativeName = "", - Category = PlatformCategory.Computer, - Checksum = "", - CreatedAt = DateTime.UtcNow, - Generation = 1, - Name = "Unknown", - PlatformFamily = new IdentityOrValue(0), - PlatformLogo = new IdentityOrValue(0), - Slug = "Unknown", - Summary = "", - UpdatedAt = DateTime.UtcNow, - Url = "", - Versions = new IdentitiesOrValues(), - Websites = new IdentitiesOrValues() - }; - - return unkownPlatform; - } - } - private static IGDBClient igdb = new IGDBClient( // Found in Twitch Developer portal for your app Config.IGDB.ClientId, Config.IGDB.Secret ); - public static Platform GetPlatform(int Id) + public static Platform? GetPlatform(long Id) { if (Id == 0) { - return UnknownPlatform; + return null; } else { @@ -69,7 +44,15 @@ namespace gaseous_server.Classes.Metadata private static async Task _GetPlatform(SearchUsing searchUsing, object searchValue) { // check database first - Platform? platform = DBGetPlatform(searchUsing, searchValue); + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("platform", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("platform", (string)searchValue); + } // set up where clause string WhereClause = ""; @@ -85,51 +68,39 @@ namespace gaseous_server.Classes.Metadata throw new Exception("Invalid search type"); } - if (platform == null) + Platform returnValue = new Platform(); + switch (cacheStatus) { - // get platform metadata - var results = await igdb.QueryAsync(IGDBClient.Endpoints.Platforms, query: "fields abbreviation,alternative_name,category,checksum,created_at,generation,name,platform_family,platform_logo,slug,summary,updated_at,url,versions,websites; " + WhereClause + ";"); - var result = results.First(); - - DBInsertPlatform(result, true); - - // get platform logo - if (result.PlatformLogo != null) - { - PlatformLogos.GetPlatformLogo((long)result.PlatformLogo.Id, Path.Combine(Config.LibraryConfiguration.LibraryMetadataDirectory_Platform(result), "platform_logo.jpg")); - } - - // get platform versions - foreach (long platformVersionId in result.Versions.Ids) - { - PlatformVersions.GetPlatformVersion(platformVersionId, result); - } - - return result; - } - else - { - return platform; + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause); + Storage.NewCacheValue(returnValue); + UpdateSubClasses(returnValue); + return returnValue; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause); + Storage.NewCacheValue(returnValue, true); + UpdateSubClasses(returnValue); + return returnValue; + case Storage.CacheStatus.Current: + return Storage.GetCacheValue(returnValue, "id", (long)searchValue); + default: + throw new Exception("How did you get here?"); } } - private static Platform? DBGetPlatform(SearchUsing searchUsing, object searchValue) + private static void UpdateSubClasses(Platform platform) { - Dictionary dbDict = new Dictionary(); - switch (searchUsing) + if (platform.Versions != null) { - case SearchUsing.id: - dbDict.Add("id", searchValue); + foreach (long PlatformVersionId in platform.Versions.Ids) + { + PlatformVersion platformVersion = PlatformVersions.GetPlatformVersion(PlatformVersionId, platform); + } + } - return _DBGetPlatform("SELECT * FROM platforms WHERE id = @id", dbDict); - - case SearchUsing.slug: - dbDict.Add("slug", searchValue); - - return _DBGetPlatform("SELECT * FROM platforms WHERE slug = @slug", dbDict); - - default: - throw new Exception("Invalid Search Type"); + if (platform.PlatformLogo != null) + { + PlatformLogo platformLogo = PlatformLogos.GetPlatformLogo(platform.PlatformLogo.Id, Config.LibraryConfiguration.LibraryMetadataDirectory_Platform(platform)); } } @@ -139,104 +110,13 @@ namespace gaseous_server.Classes.Metadata slug } - private static Platform? _DBGetPlatform(string sql, Dictionary searchParams) + private static async Task GetObjectFromServer(string WhereClause) { - Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); + // get platform metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.Platforms, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); - DataTable dbResponse = db.ExecuteCMD(sql, searchParams); - - if (dbResponse.Rows.Count > 0) - { - return ConvertDataRowToPlatform(dbResponse.Rows[0]); - } - else - { - return null; - } - } - - private static Platform ConvertDataRowToPlatform(DataRow PlatformDR) - { - Platform returnPlatform = new Platform - { - Id = (long)(UInt64)PlatformDR["id"], - Abbreviation = (string?)PlatformDR["abbreviation"], - AlternativeName = (string?)PlatformDR["alternative_name"], - Category = (PlatformCategory)PlatformDR["category"], - Checksum = (string?)PlatformDR["checksum"], - CreatedAt = (DateTime?)PlatformDR["created_at"], - Generation = (int?)PlatformDR["generation"], - Name = (string?)PlatformDR["name"], - PlatformFamily = new IdentityOrValue((int?)PlatformDR["platform_family"]), - PlatformLogo = new IdentityOrValue((int?)PlatformDR["platform_logo"]), - Slug = (string?)PlatformDR["slug"], - Summary = (string?)PlatformDR["summary"], - UpdatedAt = (DateTime?)PlatformDR["updated_at"], - Url = (string?)PlatformDR["url"], - Versions = Newtonsoft.Json.JsonConvert.DeserializeObject>((string?)PlatformDR["versions"]), - Websites = Newtonsoft.Json.JsonConvert.DeserializeObject>((string?)PlatformDR["websites"]) - }; - - return returnPlatform; - } - - private static void DBInsertPlatform(Platform PlatformItem, bool Insert) - { - Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); - string sql = "INSERT INTO platforms (id, abbreviation, alternative_name, category, checksum, created_at, generation, name, platform_family, platform_logo, slug, summary, updated_at, url, versions, websites, dateAdded, lastUpdated) VALUES (@id, @abbreviation, @alternative_name, @category, @checksum, @created_at, @generation, @name, @platform_family, @platform_logo, @slug, @summary, @updated_at, @url, @versions, @websites, @lastUpdated, @lastUpdated)"; - if (Insert == false) - { - sql = "UPDATE platforms SET abbreviation=@abbreviation, alternative_name=@alternative_name, category=@category, checksum=@checksum, created_at=@created_at, generation=@generation, name=@name, platform_family=@platform_family, platform_logo=@platform_logo, slug=@slug, summary=@summary, updated_at=@updated_at, url=@url, versions=@versions, websites=@websites, lastUpdated=@lastUpdated WHERE id=@id"; - } - Dictionary dbDict = new Dictionary(); - dbDict.Add("id", PlatformItem.Id); - dbDict.Add("abbreviation", Common.ReturnValueIfNull(PlatformItem.Abbreviation, "")); - dbDict.Add("alternative_name", Common.ReturnValueIfNull(PlatformItem.AlternativeName, "")); - dbDict.Add("category", Common.ReturnValueIfNull(PlatformItem.Category, PlatformCategory.Computer)); - dbDict.Add("checksum", Common.ReturnValueIfNull(PlatformItem.Checksum, "")); - dbDict.Add("created_at", Common.ReturnValueIfNull(PlatformItem.CreatedAt, DateTime.UtcNow)); - dbDict.Add("generation", Common.ReturnValueIfNull(PlatformItem.Generation, 1)); - dbDict.Add("name", Common.ReturnValueIfNull(PlatformItem.Name, "")); - if (PlatformItem.PlatformFamily == null) - { - dbDict.Add("platform_family", 0); - } - else - { - dbDict.Add("platform_family", Common.ReturnValueIfNull(PlatformItem.PlatformFamily.Id, 0)); - } - if (PlatformItem.PlatformLogo == null) - { - dbDict.Add("platform_logo", 0); - } - else - { - dbDict.Add("platform_logo", Common.ReturnValueIfNull(PlatformItem.PlatformLogo.Id, 0)); - } - dbDict.Add("slug", Common.ReturnValueIfNull(PlatformItem.Slug, "")); - dbDict.Add("summary", Common.ReturnValueIfNull(PlatformItem.Summary, "")); - dbDict.Add("updated_at", Common.ReturnValueIfNull(PlatformItem.UpdatedAt, DateTime.UtcNow)); - dbDict.Add("url", Common.ReturnValueIfNull(PlatformItem.Url, "")); - dbDict.Add("lastUpdated", DateTime.UtcNow); - string EmptyJson = "{\"Ids\": [], \"Values\": null}"; - if (PlatformItem.Versions == null) - { - dbDict.Add("versions", EmptyJson); - } - else - { - dbDict.Add("versions", Newtonsoft.Json.JsonConvert.SerializeObject(PlatformItem.Versions)); - } - if (PlatformItem.Websites == null) - { - dbDict.Add("websites", EmptyJson); - } - else - { - dbDict.Add("websites", Newtonsoft.Json.JsonConvert.SerializeObject(PlatformItem.Websites)); - } - - db.ExecuteCMD(sql, dbDict); + return result; } } } diff --git a/gaseous-server/Classes/Metadata/Screenshots.cs b/gaseous-server/Classes/Metadata/Screenshots.cs new file mode 100644 index 0000000..7d1ddc6 --- /dev/null +++ b/gaseous-server/Classes/Metadata/Screenshots.cs @@ -0,0 +1,168 @@ +using System; +using gaseous_tools; +using IGDB; +using IGDB.Models; +using MySqlX.XDevAPI.Common; +using static gaseous_tools.Config.ConfigFile; + +namespace gaseous_server.Classes.Metadata +{ + public class Screenshots + { + const string fieldList = "fields alpha_channel,animated,checksum,game,height,image_id,url,width;"; + + public Screenshots() + { + } + + private static IGDBClient igdb = new IGDBClient( + // Found in Twitch Developer portal for your app + Config.IGDB.ClientId, + Config.IGDB.Secret + ); + + public static Screenshot? GetScreenshot(long? Id, string LogoPath) + { + if ((Id == 0) || (Id == null)) + { + return null; + } + else + { + Task RetVal = _GetScreenshot(SearchUsing.id, Id, LogoPath); + return RetVal.Result; + } + } + + public static Screenshot GetScreenshot(string Slug, string LogoPath) + { + Task RetVal = _GetScreenshot(SearchUsing.slug, Slug, LogoPath); + return RetVal.Result; + } + + private static async Task _GetScreenshot(SearchUsing searchUsing, object searchValue, string LogoPath) + { + // check database first + Storage.CacheStatus? cacheStatus = new Storage.CacheStatus(); + if (searchUsing == SearchUsing.id) + { + cacheStatus = Storage.GetCacheStatus("Screenshot", (long)searchValue); + } + else + { + cacheStatus = Storage.GetCacheStatus("Screenshot", (string)searchValue); + } + + // set up where clause + string WhereClause = ""; + switch (searchUsing) + { + case SearchUsing.id: + WhereClause = "where id = " + searchValue; + break; + case SearchUsing.slug: + WhereClause = "where slug = " + searchValue; + break; + default: + throw new Exception("Invalid search type"); + } + + Screenshot returnValue = new Screenshot(); + bool forceImageDownload = false; + LogoPath = Path.Combine(LogoPath, "Screenshots"); + switch (cacheStatus) + { + case Storage.CacheStatus.NotPresent: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue); + forceImageDownload = true; + break; + case Storage.CacheStatus.Expired: + returnValue = await GetObjectFromServer(WhereClause, LogoPath); + Storage.NewCacheValue(returnValue, true); + forceImageDownload = true; + break; + case Storage.CacheStatus.Current: + returnValue = Storage.GetCacheValue(returnValue, "id", (long)searchValue); + break; + default: + throw new Exception("How did you get here?"); + } + + if ((!File.Exists(Path.Combine(LogoPath, "Screenshot.jpg"))) || forceImageDownload == true) + { + //GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_thumb, returnValue.ImageId); + //GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_logo_med, returnValue.ImageId); + GetImageFromServer(returnValue.Url, LogoPath, LogoSize.t_original, returnValue.ImageId); + } + + return returnValue; + } + + private enum SearchUsing + { + id, + slug + } + + private static async Task GetObjectFromServer(string WhereClause, string LogoPath) + { + // get Screenshot metadata + var results = await igdb.QueryAsync(IGDBClient.Endpoints.Screenshots, query: fieldList + " " + WhereClause + ";"); + var result = results.First(); + + //GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId); + //GetImageFromServer(result.Url, LogoPath, LogoSize.t_logo_med, result.ImageId); + GetImageFromServer(result.Url, LogoPath, LogoSize.t_original, result.ImageId); + + return result; + } + + private static void GetImageFromServer(string Url, string LogoPath, LogoSize logoSize, string ImageId) + { + using (var client = new HttpClient()) + { + string fileName = "Artwork.jpg"; + string extension = "jpg"; + switch (logoSize) + { + case LogoSize.t_thumb: + fileName = "_Thumb"; + extension = "jpg"; + break; + case LogoSize.t_logo_med: + fileName = "_Medium"; + extension = "png"; + break; + case LogoSize.t_original: + fileName = "_Original"; + extension = "png"; + break; + default: + fileName = "Artwork"; + extension = "jpg"; + break; + } + fileName = ImageId + fileName; + string imageUrl = Url.Replace(LogoSize.t_thumb.ToString(), logoSize.ToString()).Replace("jpg", extension); + + using (var s = client.GetStreamAsync("https:" + imageUrl)) + { + if (!Directory.Exists(LogoPath)) { Directory.CreateDirectory(LogoPath); } + using (var fs = new FileStream(Path.Combine(LogoPath, fileName + "." + extension), FileMode.OpenOrCreate)) + { + s.Result.CopyTo(fs); + } + } + } + } + + private enum LogoSize + { + t_thumb, + t_logo_med, + t_original + } + } +} + diff --git a/gaseous-server/Classes/Metadata/Storage.cs b/gaseous-server/Classes/Metadata/Storage.cs new file mode 100644 index 0000000..8ac0ac6 --- /dev/null +++ b/gaseous-server/Classes/Metadata/Storage.cs @@ -0,0 +1,266 @@ +using System; +using System.Data; +using System.Reflection; +using gaseous_tools; +using IGDB; +using IGDB.Models; + +namespace gaseous_server.Classes.Metadata +{ + public class Storage + { + public enum CacheStatus + { + NotPresent, + Current, + Expired + } + + public static CacheStatus GetCacheStatus(string Endpoint, string Slug) + { + return _GetCacheStatus(Endpoint, "slug", Slug); + } + + public static CacheStatus GetCacheStatus(string Endpoint, long Id) + { + return _GetCacheStatus(Endpoint, "id", Id); + } + + private static CacheStatus _GetCacheStatus(string Endpoint, string SearchField, object SearchValue) + { + Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); + + string sql = "SELECT lastUpdated FROM " + Endpoint + " WHERE " + SearchField + " = @" + SearchField; + + Dictionary dbDict = new Dictionary(); + dbDict.Add("Endpoint", Endpoint); + dbDict.Add(SearchField, SearchValue); + + DataTable dt = db.ExecuteCMD(sql, dbDict); + if (dt.Rows.Count == 0) + { + // no data stored for this item, or lastUpdated + return CacheStatus.NotPresent; + } + else + { + DateTime CacheExpiryTime = DateTime.UtcNow.AddHours(-24); + if ((DateTime)dt.Rows[0]["lastUpdated"] < CacheExpiryTime) + { + return CacheStatus.Expired; + } + else + { + return CacheStatus.Current; + } + } + } + + public static void NewCacheValue(object ObjectToCache, bool UpdateRecord = false) + { + // get the object type name + string ObjectTypeName = ObjectToCache.GetType().Name; + + // build dictionary + string objectJson = Newtonsoft.Json.JsonConvert.SerializeObject(ObjectToCache); + Dictionary objectDict = Newtonsoft.Json.JsonConvert.DeserializeObject>(objectJson); + objectDict.Add("dateAdded", DateTime.UtcNow); + objectDict.Add("lastUpdated", DateTime.UtcNow); + + // generate sql + string fieldList = ""; + string valueList = ""; + string updateFieldValueList = ""; + foreach (KeyValuePair key in objectDict) + { + if (fieldList.Length > 0) + { + fieldList = fieldList + ", "; + valueList = valueList + ", "; + updateFieldValueList = updateFieldValueList + ", "; + } + fieldList = fieldList + key.Key; + valueList = valueList + "@" + key.Key; + if ((key.Key != "id") && (key.Key != "dateAdded")) + { + updateFieldValueList = key.Key + " = @" + key.Key; + } + + // check property type + Type objectType = ObjectToCache.GetType(); + if (objectType != null) + { + PropertyInfo objectProperty = objectType.GetProperty(key.Key); + if (objectProperty != null) + { + string compareName = objectProperty.PropertyType.Name.ToLower().Split("`")[0]; + var objectValue = objectProperty.GetValue(ObjectToCache); + if (objectValue != null) + { + string newObjectValue; + Dictionary newDict; + switch (compareName) + { + case "identityorvalue": + newObjectValue = Newtonsoft.Json.JsonConvert.SerializeObject(objectValue); + newDict = Newtonsoft.Json.JsonConvert.DeserializeObject>(newObjectValue); + objectDict[key.Key] = newDict["Id"]; + break; + case "identitiesorvalues": + newObjectValue = Newtonsoft.Json.JsonConvert.SerializeObject(objectValue); + newDict = Newtonsoft.Json.JsonConvert.DeserializeObject>(newObjectValue); + newObjectValue = Newtonsoft.Json.JsonConvert.SerializeObject(newDict["Ids"]); + objectDict[key.Key] = newObjectValue; + break; + case "int32[]": + newObjectValue = Newtonsoft.Json.JsonConvert.SerializeObject(objectValue); + objectDict[key.Key] = newObjectValue; + break; + } + } + } + } + } + + string sql = ""; + if (UpdateRecord == false) + { + sql = "INSERT INTO " + ObjectTypeName + " (" + fieldList + ") VALUES (" + valueList + ")"; + } + else + { + sql = "UPDATE " + ObjectTypeName + " SET " + updateFieldValueList + " WHERE Id = @Id"; + } + + // execute sql + Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); + db.ExecuteCMD(sql, objectDict); + } + + public static T GetCacheValue(T EndpointType, string SearchField, object SearchValue) + { + string Endpoint = EndpointType.GetType().Name; + + Database db = new gaseous_tools.Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString); + + string sql = "SELECT * FROM " + Endpoint + " WHERE " + SearchField + " = @" + SearchField; + + Dictionary dbDict = new Dictionary(); + dbDict.Add("Endpoint", Endpoint); + dbDict.Add(SearchField, SearchValue); + + DataTable dt = db.ExecuteCMD(sql, dbDict); + if (dt.Rows.Count == 0) + { + // no data stored for this item + throw new Exception("No record found that matches endpoint " + Endpoint + " with search value " + SearchValue); + } + else + { + DataRow dataRow = dt.Rows[0]; + foreach (PropertyInfo property in EndpointType.GetType().GetProperties()) + { + if (dataRow.Table.Columns.Contains(property.Name)) + { + if (dataRow[property.Name] != DBNull.Value) + { + string objectTypeName = property.PropertyType.Name.ToLower().Split("`")[0]; + string subObjectTypeName = ""; + object? objectToStore = null; + if (objectTypeName == "nullable") + { + objectTypeName = property.PropertyType.UnderlyingSystemType.ToString().Split("`1")[1].Replace("[System.", "").Replace("]", "").ToLower(); + } + try + { + switch (objectTypeName) + { + case "datetimeoffset": + DateTimeOffset? storedDate = (DateTime?)dataRow[property.Name]; + property.SetValue(EndpointType, storedDate); + break; + //case "nullable": + // Console.WriteLine("Nullable: " + property.PropertyType.UnderlyingSystemType); + // break; + case "identityorvalue": + subObjectTypeName = property.PropertyType.UnderlyingSystemType.ToString().Split("`1")[1].Replace("[IGDB.Models.", "").Replace("]", "").ToLower(); + + switch (subObjectTypeName) + { + case "platformfamily": + objectToStore = new IdentityOrValue(id: (long)(int)dataRow[property.Name]); + break; + case "platformlogo": + objectToStore = new IdentityOrValue(id: (long)(int)dataRow[property.Name]); + break; + case "platformversioncompany": + objectToStore = new IdentityOrValue(id: (long)(int)dataRow[property.Name]); + break; + } + + if (objectToStore != null) + { + property.SetValue(EndpointType, objectToStore); + } + + break; + case "identitiesorvalues": + subObjectTypeName = property.PropertyType.UnderlyingSystemType.ToString().Split("`1")[1].Replace("[IGDB.Models.", "").Replace("]", "").ToLower(); + + long[] fromJsonObject = Newtonsoft.Json.JsonConvert.DeserializeObject((string)dataRow[property.Name]); + + switch (subObjectTypeName) + { + case "platformversion": + objectToStore = new IdentitiesOrValues(ids: fromJsonObject); + break; + case "platformwebsite": + objectToStore = new IdentitiesOrValues(ids: fromJsonObject); + break; + case "platformversioncompany": + objectToStore = new IdentitiesOrValues(ids: fromJsonObject); + break; + case "platformversionreleasedate": + objectToStore = new IdentitiesOrValues(ids: fromJsonObject); + break; + } + + if (objectToStore != null) + { + property.SetValue(EndpointType, objectToStore); + } + + break; + case "int32[]": + Int32[] fromJsonObject_int32Array = Newtonsoft.Json.JsonConvert.DeserializeObject((string)dataRow[property.Name]); + if (fromJsonObject_int32Array != null) + { + property.SetValue(EndpointType, fromJsonObject_int32Array); + } + break; + case "[igdb.models.category": + property.SetValue(EndpointType, (Category)dataRow[property.Name]); + break; + case "[igdb.models.gamestatus": + property.SetValue(EndpointType, (GameStatus)dataRow[property.Name]); + break; + default: + property.SetValue(EndpointType, dataRow[property.Name]); + break; + } + } + catch (Exception ex) + { + Console.WriteLine("Error occurred in column " + property.Name); + Console.WriteLine(ex.ToString()); + } + } + } + } + + return EndpointType; + } + } + } +} + diff --git a/gaseous-server/Models/PlatformMapping.cs b/gaseous-server/Models/PlatformMapping.cs index 86a1614..a8c0798 100644 --- a/gaseous-server/Models/PlatformMapping.cs +++ b/gaseous-server/Models/PlatformMapping.cs @@ -44,6 +44,7 @@ namespace gaseous_server.Models if (Signature.Game != null) { Signature.Game.System = PlatformMapping.IGDBName; } } Signature.Flags.IGDBPlatformId = PlatformMapping.IGDBId; + Signature.Flags.IGDBPlatformName = PlatformMapping.IGDBName; } } } diff --git a/gaseous-server/Models/Signatures_Games.cs b/gaseous-server/Models/Signatures_Games.cs index 8aec7a4..89f4524 100644 --- a/gaseous-server/Models/Signatures_Games.cs +++ b/gaseous-server/Models/Signatures_Games.cs @@ -229,6 +229,7 @@ namespace gaseous_server.Models public class SignatureFlags { public int IGDBPlatformId { get; set; } + public string IGDBPlatformName { get; set; } } } } diff --git a/gaseous-server/gaseous-server.csproj b/gaseous-server/gaseous-server.csproj index 8c81cda..8c80069 100644 --- a/gaseous-server/gaseous-server.csproj +++ b/gaseous-server/gaseous-server.csproj @@ -10,9 +10,9 @@ - + - + diff --git a/gaseous-signature-ingestor/gaseous-signature-ingestor.csproj b/gaseous-signature-ingestor/gaseous-signature-ingestor.csproj index 119e791..a83ccc7 100644 --- a/gaseous-signature-ingestor/gaseous-signature-ingestor.csproj +++ b/gaseous-signature-ingestor/gaseous-signature-ingestor.csproj @@ -14,7 +14,7 @@ - + diff --git a/gaseous-tools/Config.cs b/gaseous-tools/Config.cs index 5ca8588..de72de4 100644 --- a/gaseous-tools/Config.cs +++ b/gaseous-tools/Config.cs @@ -257,7 +257,14 @@ namespace gaseous_tools public string LibraryMetadataDirectory_Platform(Platform platform) { - string MetadataPath = Path.Combine(LibraryMetadataDirectory, platform.Slug); + string MetadataPath = Path.Combine(LibraryMetadataDirectory, "Platforms", platform.Slug); + if (!Directory.Exists(MetadataPath)) { Directory.CreateDirectory(MetadataPath); } + return MetadataPath; + } + + public string LibraryMetadataDirectory_Game(Game game) + { + string MetadataPath = Path.Combine(LibraryMetadataDirectory, "Games", game.Slug); if (!Directory.Exists(MetadataPath)) { Directory.CreateDirectory(MetadataPath); } return MetadataPath; } diff --git a/gaseous-tools/Database/MySQL/gaseous-1000.sql b/gaseous-tools/Database/MySQL/gaseous-1000.sql index ba3f120..13b74ae 100644 --- a/gaseous-tools/Database/MySQL/gaseous-1000.sql +++ b/gaseous-tools/Database/MySQL/gaseous-1000.sql @@ -15,12 +15,274 @@ /*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */; /*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */; +-- +-- Table structure for table `artwork` +-- + +DROP TABLE IF EXISTS `artwork`; +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `artwork` ( + `id` bigint NOT NULL, + `alphachannel` tinyint(1) DEFAULT NULL, + `animated` tinyint(1) DEFAULT NULL, + `checksum` varchar(45) DEFAULT NULL, + `game` bigint DEFAULT NULL, + `height` int DEFAULT NULL, + `imageid` varchar(45) DEFAULT NULL, + `url` varchar(255) DEFAULT NULL, + `width` int DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `cover` +-- + +DROP TABLE IF EXISTS `cover`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `cover` ( + `id` bigint NOT NULL, + `alphachannel` tinyint(1) DEFAULT NULL, + `animated` tinyint(1) DEFAULT NULL, + `checksum` varchar(45) DEFAULT NULL, + `game` bigint DEFAULT NULL, + `height` int DEFAULT NULL, + `imageid` varchar(45) DEFAULT NULL, + `url` varchar(255) DEFAULT NULL, + `width` int DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `game` +-- + +DROP TABLE IF EXISTS `game`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `game` ( + `id` bigint NOT NULL, + `ageratings` json DEFAULT NULL, + `aggregatedrating` double DEFAULT NULL, + `aggregatedratingcount` int DEFAULT NULL, + `alternativenames` json DEFAULT NULL, + `artworks` json DEFAULT NULL, + `bundles` json DEFAULT NULL, + `category` int DEFAULT NULL, + `checksum` varchar(45) DEFAULT NULL, + `collection` bigint DEFAULT NULL, + `cover` bigint DEFAULT NULL, + `createdat` datetime DEFAULT NULL, + `dlcs` json DEFAULT NULL, + `expansions` json DEFAULT NULL, + `externalgames` json DEFAULT NULL, + `firstreleasedate` datetime DEFAULT NULL, + `follows` int DEFAULT NULL, + `franchise` bigint DEFAULT NULL, + `franchises` json DEFAULT NULL, + `gameengines` json DEFAULT NULL, + `gamemodes` json DEFAULT NULL, + `genres` json DEFAULT NULL, + `hypes` int DEFAULT NULL, + `involvedcompanies` json DEFAULT NULL, + `keywords` json DEFAULT NULL, + `multiplayermodes` json DEFAULT NULL, + `name` varchar(255) DEFAULT NULL, + `parentgame` bigint DEFAULT NULL, + `platforms` json DEFAULT NULL, + `playerperspectives` json DEFAULT NULL, + `rating` double DEFAULT NULL, + `ratingcount` int DEFAULT NULL, + `releasedates` json DEFAULT NULL, + `screenshots` json DEFAULT NULL, + `similargames` json DEFAULT NULL, + `slug` varchar(100) DEFAULT NULL, + `standaloneexpansions` json DEFAULT NULL, + `status` int DEFAULT NULL, + `storyline` longtext, + `summary` longtext, + `tags` json DEFAULT NULL, + `themes` json DEFAULT NULL, + `totalrating` double DEFAULT NULL, + `totalratingcount` int DEFAULT NULL, + `updatedat` datetime DEFAULT NULL, + `url` varchar(100) DEFAULT NULL, + `versionparent` bigint DEFAULT NULL, + `versiontitle` varchar(100) DEFAULT NULL, + `videos` json DEFAULT NULL, + `websites` json DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`), + UNIQUE KEY `id_UNIQUE` (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `games_roms` +-- + +DROP TABLE IF EXISTS `games_roms`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `games_roms` ( + `id` bigint NOT NULL AUTO_INCREMENT, + `platformid` bigint DEFAULT NULL, + `gameid` bigint DEFAULT NULL, + `name` varchar(255) DEFAULT NULL, + `size` bigint DEFAULT NULL, + `crc` varchar(20) DEFAULT NULL, + `md5` varchar(100) DEFAULT NULL, + `sha1` varchar(100) DEFAULT NULL, + `developmentstatus` varchar(100) DEFAULT NULL, + `flags` json DEFAULT NULL, + `romtype` int DEFAULT NULL, + `romtypemedia` varchar(100) DEFAULT NULL, + `medialabel` varchar(100) DEFAULT NULL, + `path` longtext, + PRIMARY KEY (`id`), + UNIQUE KEY `id_UNIQUE` (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `platform` +-- + +DROP TABLE IF EXISTS `platform`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `platform` ( + `id` bigint NOT NULL, + `abbreviation` varchar(45) DEFAULT NULL, + `alternativename` varchar(45) DEFAULT NULL, + `category` int DEFAULT NULL, + `checksum` varchar(45) DEFAULT NULL, + `createdat` datetime DEFAULT NULL, + `generation` int DEFAULT NULL, + `name` varchar(45) DEFAULT NULL, + `platformfamily` int DEFAULT NULL, + `platformlogo` int DEFAULT NULL, + `slug` varchar(45) DEFAULT NULL, + `summary` longtext, + `updatedat` datetime DEFAULT NULL, + `url` varchar(255) DEFAULT NULL, + `versions` json DEFAULT NULL, + `websites` json DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`), + UNIQUE KEY `id_UNIQUE` (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `platformlogo` +-- + +DROP TABLE IF EXISTS `platformlogo`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `platformlogo` ( + `id` bigint NOT NULL, + `alphachannel` tinyint(1) DEFAULT NULL, + `animated` tinyint(1) DEFAULT NULL, + `checksum` varchar(45) DEFAULT NULL, + `height` int DEFAULT NULL, + `imageid` varchar(45) DEFAULT NULL, + `url` varchar(255) DEFAULT NULL, + `width` int DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `platformversion` +-- + +DROP TABLE IF EXISTS `platformversion`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `platformversion` ( + `id` bigint NOT NULL, + `checksum` varchar(45) DEFAULT NULL, + `companies` json DEFAULT NULL, + `connectivity` longtext, + `cpu` longtext, + `graphics` longtext, + `mainmanufacturer` bigint DEFAULT NULL, + `media` longtext, + `memory` longtext, + `name` longtext, + `os` longtext, + `output` longtext, + `platformlogo` int DEFAULT NULL, + `platformversionreleasedates` json DEFAULT NULL, + `resolutions` longtext, + `slug` longtext, + `sound` longtext, + `storage` longtext, + `summary` longtext, + `url` varchar(255) DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `screenshot` +-- + +DROP TABLE IF EXISTS `screenshot`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `screenshot` ( + `id` bigint NOT NULL, + `alphachannel` tinyint(1) DEFAULT NULL, + `animated` tinyint(1) DEFAULT NULL, + `checksum` varchar(45) DEFAULT NULL, + `game` bigint DEFAULT NULL, + `height` int DEFAULT NULL, + `imageid` varchar(45) DEFAULT NULL, + `url` varchar(255) DEFAULT NULL, + `width` int DEFAULT NULL, + `dateAdded` datetime DEFAULT NULL, + `lastUpdated` datetime DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + +-- +-- Table structure for table `settings` +-- + +DROP TABLE IF EXISTS `settings`; + +/*!50503 SET character_set_client = utf8mb4 */; +CREATE TABLE `settings` ( + `setting` varchar(45) NOT NULL, + `value` longtext, + PRIMARY KEY (`setting`), + UNIQUE KEY `setting_UNIQUE` (`setting`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; + + -- -- Table structure for table `signatures_games` -- DROP TABLE IF EXISTS `signatures_games`; -/*!40101 SET @saved_cs_client = @@character_set_client */; + /*!50503 SET character_set_client = utf8mb4 */; CREATE TABLE `signatures_games` ( `id` int NOT NULL AUTO_INCREMENT, @@ -43,14 +305,14 @@ CREATE TABLE `signatures_games` ( CONSTRAINT `publisher` FOREIGN KEY (`publisherid`) REFERENCES `signatures_publishers` (`id`) ON DELETE CASCADE ON UPDATE CASCADE, CONSTRAINT `system` FOREIGN KEY (`systemid`) REFERENCES `signatures_platforms` (`id`) ON DELETE CASCADE ON UPDATE CASCADE ) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; -/*!40101 SET character_set_client = @saved_cs_client */; + -- -- Table structure for table `signatures_platforms` -- DROP TABLE IF EXISTS `signatures_platforms`; -/*!40101 SET @saved_cs_client = @@character_set_client */; + /*!50503 SET character_set_client = utf8mb4 */; CREATE TABLE `signatures_platforms` ( `id` int NOT NULL AUTO_INCREMENT, @@ -59,14 +321,14 @@ CREATE TABLE `signatures_platforms` ( UNIQUE KEY `idsignatures_platforms_UNIQUE` (`id`), KEY `platforms_idx` (`platform`,`id`) USING BTREE ) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; -/*!40101 SET character_set_client = @saved_cs_client */; + -- -- Table structure for table `signatures_publishers` -- DROP TABLE IF EXISTS `signatures_publishers`; -/*!40101 SET @saved_cs_client = @@character_set_client */; + /*!50503 SET character_set_client = utf8mb4 */; CREATE TABLE `signatures_publishers` ( `id` int NOT NULL AUTO_INCREMENT, @@ -75,14 +337,14 @@ CREATE TABLE `signatures_publishers` ( UNIQUE KEY `id_UNIQUE` (`id`), KEY `publisher_idx` (`publisher`,`id`) ) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; -/*!40101 SET character_set_client = @saved_cs_client */; + -- -- Table structure for table `signatures_roms` -- DROP TABLE IF EXISTS `signatures_roms`; -/*!40101 SET @saved_cs_client = @@character_set_client */; + /*!50503 SET character_set_client = utf8mb4 */; CREATE TABLE `signatures_roms` ( `id` int NOT NULL AUTO_INCREMENT, @@ -105,14 +367,14 @@ CREATE TABLE `signatures_roms` ( KEY `flags_idx` ((cast(`flags` as char(255) array))), CONSTRAINT `gameid` FOREIGN KEY (`gameid`) REFERENCES `signatures_games` (`id`) ON DELETE CASCADE ON UPDATE CASCADE ) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; -/*!40101 SET character_set_client = @saved_cs_client */; + -- -- Table structure for table `signatures_sources` -- DROP TABLE IF EXISTS `signatures_sources`; -/*!40101 SET @saved_cs_client = @@character_set_client */; + /*!50503 SET character_set_client = utf8mb4 */; CREATE TABLE `signatures_sources` ( `id` int NOT NULL AUTO_INCREMENT, @@ -132,15 +394,29 @@ CREATE TABLE `signatures_sources` ( KEY `sourcemd5_idx` (`sourcemd5`,`id`) USING BTREE, KEY `sourcesha1_idx` (`sourcesha1`,`id`) USING BTREE ) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; -/*!40101 SET character_set_client = @saved_cs_client */; -/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */; -/*!40101 SET SQL_MODE=@OLD_SQL_MODE */; -/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */; -/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */; -/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */; -/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */; -/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; -/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */; +-- +-- Final view structure for view `view_signatures_games` +-- --- Dump completed on 2023-02-27 8:54:22 +DROP VIEW IF EXISTS `view_signatures_games`; +CREATE VIEW `view_signatures_games` AS + SELECT + `signatures_games`.`id` AS `id`, + `signatures_games`.`name` AS `name`, + `signatures_games`.`description` AS `description`, + `signatures_games`.`year` AS `year`, + `signatures_games`.`publisherid` AS `publisherid`, + `signatures_publishers`.`publisher` AS `publisher`, + `signatures_games`.`demo` AS `demo`, + `signatures_games`.`systemid` AS `platformid`, + `signatures_platforms`.`platform` AS `platform`, + `signatures_games`.`systemvariant` AS `systemvariant`, + `signatures_games`.`video` AS `video`, + `signatures_games`.`country` AS `country`, + `signatures_games`.`language` AS `language`, + `signatures_games`.`copyright` AS `copyright` + FROM + ((`signatures_games` + JOIN `signatures_publishers` ON ((`signatures_games`.`publisherid` = `signatures_publishers`.`id`))) + JOIN `signatures_platforms` ON ((`signatures_games`.`systemid` = `signatures_platforms`.`id`))); \ No newline at end of file diff --git a/gaseous-tools/Database/MySQL/gaseous-1001.sql b/gaseous-tools/Database/MySQL/gaseous-1001.sql deleted file mode 100644 index 98eb6e0..0000000 --- a/gaseous-tools/Database/MySQL/gaseous-1001.sql +++ /dev/null @@ -1,21 +0,0 @@ -CREATE VIEW `view_signatures_games` AS - SELECT - `signatures_games`.`id` AS `id`, - `signatures_games`.`name` AS `name`, - `signatures_games`.`description` AS `description`, - `signatures_games`.`year` AS `year`, - `signatures_games`.`publisherid` AS `publisherid`, - `signatures_publishers`.`publisher` AS `publisher`, - `signatures_games`.`demo` AS `demo`, - `signatures_games`.`systemid` AS `platformid`, - `signatures_platforms`.`platform` AS `platform`, - `signatures_games`.`systemvariant` AS `systemvariant`, - `signatures_games`.`video` AS `video`, - `signatures_games`.`country` AS `country`, - `signatures_games`.`language` AS `language`, - `signatures_games`.`copyright` AS `copyright` - FROM - ((`signatures_games` - JOIN `signatures_publishers` ON ((`signatures_games`.`publisherid` = `signatures_publishers`.`id`))) - JOIN `signatures_platforms` ON ((`signatures_games`.`systemid` = `signatures_platforms`.`id`))); - diff --git a/gaseous-tools/Database/MySQL/gaseous-1002.sql b/gaseous-tools/Database/MySQL/gaseous-1002.sql deleted file mode 100644 index 29ed498..0000000 --- a/gaseous-tools/Database/MySQL/gaseous-1002.sql +++ /dev/null @@ -1,6 +0,0 @@ -CREATE TABLE `gaseous`.`settings` ( - `setting` VARCHAR(45) NOT NULL, - `value` LONGTEXT NULL, - UNIQUE INDEX `setting_UNIQUE` (`setting` ASC) VISIBLE, - PRIMARY KEY (`setting`)); - diff --git a/gaseous-tools/Database/MySQL/gaseous-1003.sql b/gaseous-tools/Database/MySQL/gaseous-1003.sql deleted file mode 100644 index 38f81ee..0000000 --- a/gaseous-tools/Database/MySQL/gaseous-1003.sql +++ /dev/null @@ -1,24 +0,0 @@ - -CREATE TABLE `platforms` ( - `id` bigint unsigned NOT NULL, - `abbreviation` varchar(45) DEFAULT NULL, - `alternative_name` varchar(45) DEFAULT NULL, - `category` int DEFAULT NULL, - `checksum` varchar(45) DEFAULT NULL, - `created_at` datetime DEFAULT NULL, - `generation` int DEFAULT NULL, - `name` varchar(45) DEFAULT NULL, - `platform_family` int DEFAULT NULL, - `platform_logo` int DEFAULT NULL, - `slug` varchar(45) DEFAULT NULL, - `summary` varchar(255) DEFAULT NULL, - `updated_at` datetime DEFAULT NULL, - `url` varchar(255) DEFAULT NULL, - `versions` json DEFAULT NULL, - `websites` json DEFAULT NULL, - `dateAdded` datetime DEFAULT NULL, - `lastUpdated` datetime DEFAULT NULL, - PRIMARY KEY (`id`), - UNIQUE KEY `id_UNIQUE` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci; -SELECT * FROM gaseous.platforms; \ No newline at end of file diff --git a/gaseous-tools/gaseous-tools.csproj b/gaseous-tools/gaseous-tools.csproj index 025a8d2..400f6b9 100644 --- a/gaseous-tools/gaseous-tools.csproj +++ b/gaseous-tools/gaseous-tools.csproj @@ -8,7 +8,7 @@ - + @@ -16,9 +16,6 @@ - - - @@ -26,8 +23,5 @@ - - -