Compare commits
5 Commits
v1.7.0-pre
...
v1.7.0-pre
Author | SHA1 | Date | |
---|---|---|---|
![]() |
b691eab0ee | ||
![]() |
907b3e42c4 | ||
![]() |
128bbcc1df | ||
![]() |
789ec7fc17 | ||
![]() |
32051493a8 |
@@ -10,6 +10,7 @@ using gaseous_server.Controllers;
|
|||||||
using gaseous_server.Models;
|
using gaseous_server.Models;
|
||||||
using IGDB.Models;
|
using IGDB.Models;
|
||||||
using Microsoft.AspNetCore.Identity;
|
using Microsoft.AspNetCore.Identity;
|
||||||
|
using Microsoft.AspNetCore.Mvc.Filters;
|
||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
|
|
||||||
namespace gaseous_server.Classes
|
namespace gaseous_server.Classes
|
||||||
@@ -220,7 +221,10 @@ namespace gaseous_server.Classes
|
|||||||
} else {
|
} else {
|
||||||
// get all platforms to pull from
|
// get all platforms to pull from
|
||||||
Dictionary<string, object> FilterDict = Filters.Filter(AgeRatings.AgeGroups.AgeRestrictionGroupings.Adult, true);
|
Dictionary<string, object> FilterDict = Filters.Filter(AgeRatings.AgeGroups.AgeRestrictionGroupings.Adult, true);
|
||||||
platforms.AddRange((List<Filters.FilterPlatform>)FilterDict["platforms"]);
|
List<Classes.Filters.FilterItem> filteredPlatforms = (List<Classes.Filters.FilterItem>)FilterDict["platforms"];
|
||||||
|
foreach (Filters.FilterItem filterItem in filteredPlatforms) {
|
||||||
|
platforms.Add(Platforms.GetPlatform(filterItem.Id));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// build collection
|
// build collection
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System.Collections.Concurrent;
|
||||||
using System.Security.Cryptography;
|
using System.Security.Cryptography;
|
||||||
|
|
||||||
namespace gaseous_server.Classes
|
namespace gaseous_server.Classes
|
||||||
@@ -111,5 +111,29 @@ namespace gaseous_server.Classes
|
|||||||
.TrimEnd(Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar);
|
.TrimEnd(Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Provides a way to set contextual data that flows with the call and
|
||||||
|
/// async context of a test or invocation.
|
||||||
|
/// </summary>
|
||||||
|
public static class CallContext
|
||||||
|
{
|
||||||
|
static ConcurrentDictionary<string, AsyncLocal<object>> state = new ConcurrentDictionary<string, AsyncLocal<object>>();
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Stores a given object and associates it with the specified name.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="name">The name with which to associate the new item in the call context.</param>
|
||||||
|
/// <param name="data">The object to store in the call context.</param>
|
||||||
|
public static void SetData(string name, object data) =>
|
||||||
|
state.GetOrAdd(name, _ => new AsyncLocal<object>()).Value = data;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Retrieves an object with the specified name from the <see cref="CallContext"/>.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="name">The name of the item in the call context.</param>
|
||||||
|
/// <returns>The object in the call context associated with the specified name, or <see langword="null"/> if not found.</returns>
|
||||||
|
public static object GetData(string name) =>
|
||||||
|
state.TryGetValue(name, out AsyncLocal<object> data) ? data.Value : null;
|
||||||
|
}
|
||||||
|
}
|
@@ -2,6 +2,7 @@
|
|||||||
using System.Data;
|
using System.Data;
|
||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
using IGDB.Models;
|
using IGDB.Models;
|
||||||
|
using gaseous_server.Classes.Metadata;
|
||||||
|
|
||||||
namespace gaseous_server.Classes
|
namespace gaseous_server.Classes
|
||||||
{
|
{
|
||||||
@@ -57,6 +58,14 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static ConfigFile.MetadataAPI MetadataConfiguration
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return _config.MetadataConfiguration;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public static ConfigFile.IGDB IGDB
|
public static ConfigFile.IGDB IGDB
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
@@ -247,6 +256,8 @@ namespace gaseous_server.Classes
|
|||||||
[JsonIgnore]
|
[JsonIgnore]
|
||||||
public Library LibraryConfiguration = new Library();
|
public Library LibraryConfiguration = new Library();
|
||||||
|
|
||||||
|
public MetadataAPI MetadataConfiguration = new MetadataAPI();
|
||||||
|
|
||||||
public IGDB IGDBConfiguration = new IGDB();
|
public IGDB IGDBConfiguration = new IGDB();
|
||||||
|
|
||||||
public Logging LoggingConfiguration = new Logging();
|
public Logging LoggingConfiguration = new Logging();
|
||||||
@@ -460,6 +471,26 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class MetadataAPI
|
||||||
|
{
|
||||||
|
private static Communications.MetadataSources _Source
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
if (!String.IsNullOrEmpty(Environment.GetEnvironmentVariable("metadatasource")))
|
||||||
|
{
|
||||||
|
return (Communications.MetadataSources)Enum.Parse(typeof(Communications.MetadataSources), Environment.GetEnvironmentVariable("metadatasource"));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return Communications.MetadataSources.IGDB;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public Communications.MetadataSources Source = _Source;
|
||||||
|
}
|
||||||
|
|
||||||
public class IGDB
|
public class IGDB
|
||||||
{
|
{
|
||||||
private static string _DefaultIGDBClientId
|
private static string _DefaultIGDBClientId
|
||||||
|
@@ -14,7 +14,7 @@ namespace gaseous_server.Classes
|
|||||||
Dictionary<string, object> FilterSet = new Dictionary<string, object>();
|
Dictionary<string, object> FilterSet = new Dictionary<string, object>();
|
||||||
|
|
||||||
// platforms
|
// platforms
|
||||||
List<FilterPlatform> platforms = new List<FilterPlatform>();
|
List<FilterItem> platforms = new List<FilterItem>();
|
||||||
|
|
||||||
string ageRestriction_Platform = "Game.AgeGroupId <= " + (int)MaximumAgeRestriction;
|
string ageRestriction_Platform = "Game.AgeGroupId <= " + (int)MaximumAgeRestriction;
|
||||||
string ageRestriction_Generic = "view_Games.AgeGroupId <= " + (int)MaximumAgeRestriction;
|
string ageRestriction_Generic = "view_Games.AgeGroupId <= " + (int)MaximumAgeRestriction;
|
||||||
@@ -30,57 +30,52 @@ namespace gaseous_server.Classes
|
|||||||
|
|
||||||
foreach (DataRow dr in dbResponse.Rows)
|
foreach (DataRow dr in dbResponse.Rows)
|
||||||
{
|
{
|
||||||
FilterPlatform platformItem = new FilterPlatform(Classes.Metadata.Platforms.GetPlatform((long)dr["id"]));
|
FilterItem platformItem = new FilterItem(dr);
|
||||||
platformItem.GameCount = (int)(long)dr["GameCount"];
|
|
||||||
platforms.Add(platformItem);
|
platforms.Add(platformItem);
|
||||||
|
|
||||||
}
|
}
|
||||||
FilterSet.Add("platforms", platforms);
|
FilterSet.Add("platforms", platforms);
|
||||||
|
|
||||||
// genres
|
// genres
|
||||||
List<FilterGenre> genres = new List<FilterGenre>();
|
List<FilterItem> genres = new List<FilterItem>();
|
||||||
dbResponse = GetGenericFilterItem(db, "Genre", ageRestriction_Generic);
|
dbResponse = GetGenericFilterItem(db, "Genre", ageRestriction_Generic);
|
||||||
|
|
||||||
foreach (DataRow dr in dbResponse.Rows)
|
foreach (DataRow dr in dbResponse.Rows)
|
||||||
{
|
{
|
||||||
FilterGenre genreItem = new FilterGenre(Classes.Metadata.Genres.GetGenres((long)dr["id"]));
|
FilterItem genreItem = new FilterItem(dr);
|
||||||
genreItem.GameCount = (int)(long)dr["GameCount"];
|
|
||||||
genres.Add(genreItem);
|
genres.Add(genreItem);
|
||||||
}
|
}
|
||||||
FilterSet.Add("genres", genres);
|
FilterSet.Add("genres", genres);
|
||||||
|
|
||||||
// game modes
|
// game modes
|
||||||
List<FilterGameMode> gameModes = new List<FilterGameMode>();
|
List<FilterItem> gameModes = new List<FilterItem>();
|
||||||
dbResponse = GetGenericFilterItem(db, "GameMode", ageRestriction_Generic);
|
dbResponse = GetGenericFilterItem(db, "GameMode", ageRestriction_Generic);
|
||||||
|
|
||||||
foreach (DataRow dr in dbResponse.Rows)
|
foreach (DataRow dr in dbResponse.Rows)
|
||||||
{
|
{
|
||||||
FilterGameMode gameModeItem = new FilterGameMode(Classes.Metadata.GameModes.GetGame_Modes((long)dr["id"]));
|
FilterItem gameModeItem = new FilterItem(dr);
|
||||||
gameModeItem.GameCount = (int)(long)dr["GameCount"];
|
|
||||||
gameModes.Add(gameModeItem);
|
gameModes.Add(gameModeItem);
|
||||||
}
|
}
|
||||||
FilterSet.Add("gamemodes", gameModes);
|
FilterSet.Add("gamemodes", gameModes);
|
||||||
|
|
||||||
// player perspectives
|
// player perspectives
|
||||||
List<FilterPlayerPerspective> playerPerspectives = new List<FilterPlayerPerspective>();
|
List<FilterItem> playerPerspectives = new List<FilterItem>();
|
||||||
dbResponse = GetGenericFilterItem(db, "PlayerPerspective", ageRestriction_Generic);
|
dbResponse = GetGenericFilterItem(db, "PlayerPerspective", ageRestriction_Generic);
|
||||||
|
|
||||||
foreach (DataRow dr in dbResponse.Rows)
|
foreach (DataRow dr in dbResponse.Rows)
|
||||||
{
|
{
|
||||||
FilterPlayerPerspective playerPerspectiveItem = new FilterPlayerPerspective(Classes.Metadata.PlayerPerspectives.GetGame_PlayerPerspectives((long)dr["id"]));
|
FilterItem playerPerspectiveItem = new FilterItem(dr);
|
||||||
playerPerspectiveItem.GameCount = (int)(long)dr["GameCount"];
|
|
||||||
playerPerspectives.Add(playerPerspectiveItem);
|
playerPerspectives.Add(playerPerspectiveItem);
|
||||||
}
|
}
|
||||||
FilterSet.Add("playerperspectives", playerPerspectives);
|
FilterSet.Add("playerperspectives", playerPerspectives);
|
||||||
|
|
||||||
// themes
|
// themes
|
||||||
List<FilterTheme> themes = new List<FilterTheme>();
|
List<FilterItem> themes = new List<FilterItem>();
|
||||||
dbResponse = GetGenericFilterItem(db, "Theme", ageRestriction_Generic);
|
dbResponse = GetGenericFilterItem(db, "Theme", ageRestriction_Generic);
|
||||||
|
|
||||||
foreach (DataRow dr in dbResponse.Rows)
|
foreach (DataRow dr in dbResponse.Rows)
|
||||||
{
|
{
|
||||||
FilterTheme themeItem = new FilterTheme(Classes.Metadata.Themes.GetGame_Themes((long)dr["id"]));
|
FilterItem themeItem = new FilterItem(dr);
|
||||||
themeItem.GameCount = (int)(long)dr["GameCount"];
|
|
||||||
themes.Add(themeItem);
|
themes.Add(themeItem);
|
||||||
}
|
}
|
||||||
FilterSet.Add("themes", themes);
|
FilterSet.Add("themes", themes);
|
||||||
@@ -120,87 +115,18 @@ namespace gaseous_server.Classes
|
|||||||
return dbResponse;
|
return dbResponse;
|
||||||
}
|
}
|
||||||
|
|
||||||
public class FilterPlatform : IGDB.Models.Platform
|
public class FilterItem
|
||||||
{
|
{
|
||||||
public FilterPlatform(Platform obj)
|
public FilterItem(DataRow dr)
|
||||||
{
|
{
|
||||||
var properties = obj.GetType().GetProperties();
|
this.Id = (long)dr["Id"];
|
||||||
foreach (var prop in properties)
|
this.Name = (string)dr["Name"];
|
||||||
{
|
this.GameCount = (int)(long)dr["GameCount"];
|
||||||
if (prop.GetGetMethod() != null)
|
|
||||||
{
|
|
||||||
this.GetType().GetProperty(prop.Name).SetValue(this, prop.GetValue(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public int GameCount { get; set; }
|
public long Id { get; set; }
|
||||||
}
|
|
||||||
|
|
||||||
public class FilterGenre : IGDB.Models.Genre
|
public string Name { get; set; }
|
||||||
{
|
|
||||||
public FilterGenre(Genre obj)
|
|
||||||
{
|
|
||||||
var properties = obj.GetType().GetProperties();
|
|
||||||
foreach (var prop in properties)
|
|
||||||
{
|
|
||||||
if (prop.GetGetMethod() != null)
|
|
||||||
{
|
|
||||||
this.GetType().GetProperty(prop.Name).SetValue(this, prop.GetValue(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GameCount { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class FilterGameMode : IGDB.Models.GameMode
|
|
||||||
{
|
|
||||||
public FilterGameMode(GameMode obj)
|
|
||||||
{
|
|
||||||
var properties = obj.GetType().GetProperties();
|
|
||||||
foreach (var prop in properties)
|
|
||||||
{
|
|
||||||
if (prop.GetGetMethod() != null)
|
|
||||||
{
|
|
||||||
this.GetType().GetProperty(prop.Name).SetValue(this, prop.GetValue(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GameCount { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class FilterPlayerPerspective : IGDB.Models.PlayerPerspective
|
|
||||||
{
|
|
||||||
public FilterPlayerPerspective(PlayerPerspective obj)
|
|
||||||
{
|
|
||||||
var properties = obj.GetType().GetProperties();
|
|
||||||
foreach (var prop in properties)
|
|
||||||
{
|
|
||||||
if (prop.GetGetMethod() != null)
|
|
||||||
{
|
|
||||||
this.GetType().GetProperty(prop.Name).SetValue(this, prop.GetValue(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GameCount { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class FilterTheme : IGDB.Models.Theme
|
|
||||||
{
|
|
||||||
public FilterTheme(Theme obj)
|
|
||||||
{
|
|
||||||
var properties = obj.GetType().GetProperties();
|
|
||||||
foreach (var prop in properties)
|
|
||||||
{
|
|
||||||
if (prop.GetGetMethod() != null)
|
|
||||||
{
|
|
||||||
this.GetType().GetProperty(prop.Name).SetValue(this, prop.GetValue(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GameCount { get; set; }
|
public int GameCount { get; set; }
|
||||||
}
|
}
|
||||||
|
@@ -1,17 +1,19 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Data;
|
using System.Data;
|
||||||
using System.IO.Compression;
|
using System.IO.Compression;
|
||||||
|
using System.Security.Authentication;
|
||||||
using System.Security.Policy;
|
using System.Security.Policy;
|
||||||
using System.Text.RegularExpressions;
|
using System.Text.RegularExpressions;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using gaseous_server.Classes.Metadata;
|
using gaseous_server.Classes.Metadata;
|
||||||
using IGDB.Models;
|
using IGDB.Models;
|
||||||
using NuGet.Common;
|
using NuGet.Common;
|
||||||
|
using NuGet.LibraryModel;
|
||||||
using static gaseous_server.Classes.Metadata.Games;
|
using static gaseous_server.Classes.Metadata.Games;
|
||||||
|
|
||||||
namespace gaseous_server.Classes
|
namespace gaseous_server.Classes
|
||||||
{
|
{
|
||||||
public class ImportGames
|
public class ImportGames : QueueItemStatus
|
||||||
{
|
{
|
||||||
public ImportGames(string ImportPath)
|
public ImportGames(string ImportPath)
|
||||||
{
|
{
|
||||||
@@ -21,9 +23,15 @@ namespace gaseous_server.Classes
|
|||||||
string[] importContents_Directories = Directory.GetDirectories(ImportPath);
|
string[] importContents_Directories = Directory.GetDirectories(ImportPath);
|
||||||
|
|
||||||
// import files first
|
// import files first
|
||||||
|
int importCount = 1;
|
||||||
foreach (string importContent in importContents_Files) {
|
foreach (string importContent in importContents_Files) {
|
||||||
|
SetStatus(importCount, importContents_Files.Length, "Importing file: " + importContent);
|
||||||
|
|
||||||
ImportGame.ImportGameFile(importContent, null);
|
ImportGame.ImportGameFile(importContent, null);
|
||||||
|
|
||||||
|
importCount += 1;
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
|
|
||||||
// import sub directories
|
// import sub directories
|
||||||
foreach (string importDir in importContents_Directories) {
|
foreach (string importDir in importContents_Directories) {
|
||||||
@@ -40,7 +48,7 @@ namespace gaseous_server.Classes
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public class ImportGame
|
public class ImportGame : QueueItemStatus
|
||||||
{
|
{
|
||||||
public static void ImportGameFile(string GameFileImportPath, IGDB.Models.Platform? OverridePlatform)
|
public static void ImportGameFile(string GameFileImportPath, IGDB.Models.Platform? OverridePlatform)
|
||||||
{
|
{
|
||||||
@@ -600,7 +608,7 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void LibraryScan()
|
public void LibraryScan()
|
||||||
{
|
{
|
||||||
foreach (GameLibrary.LibraryItem library in GameLibrary.GetLibraries)
|
foreach (GameLibrary.LibraryItem library in GameLibrary.GetLibraries)
|
||||||
{
|
{
|
||||||
@@ -645,8 +653,10 @@ namespace gaseous_server.Classes
|
|||||||
// search for files in the library that aren't in the database
|
// search for files in the library that aren't in the database
|
||||||
Logging.Log(Logging.LogType.Information, "Library Scan", "Looking for orphaned library files to add");
|
Logging.Log(Logging.LogType.Information, "Library Scan", "Looking for orphaned library files to add");
|
||||||
string[] LibraryFiles = Directory.GetFiles(library.Path, "*.*", SearchOption.AllDirectories);
|
string[] LibraryFiles = Directory.GetFiles(library.Path, "*.*", SearchOption.AllDirectories);
|
||||||
|
int StatusCount = 0;
|
||||||
foreach (string LibraryFile in LibraryFiles)
|
foreach (string LibraryFile in LibraryFiles)
|
||||||
{
|
{
|
||||||
|
SetStatus(StatusCount, LibraryFiles.Length, "Processing file " + LibraryFile);
|
||||||
if (!Common.SkippableFiles.Contains<string>(Path.GetFileName(LibraryFile), StringComparer.OrdinalIgnoreCase))
|
if (!Common.SkippableFiles.Contains<string>(Path.GetFileName(LibraryFile), StringComparer.OrdinalIgnoreCase))
|
||||||
{
|
{
|
||||||
Common.hashObject LibraryFileHash = new Common.hashObject(LibraryFile);
|
Common.hashObject LibraryFileHash = new Common.hashObject(LibraryFile);
|
||||||
@@ -702,6 +712,7 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
|
|
||||||
sql = "SELECT * FROM Games_Roms WHERE LibraryId=@libraryid ORDER BY `name`";
|
sql = "SELECT * FROM Games_Roms WHERE LibraryId=@libraryid ORDER BY `name`";
|
||||||
dtRoms = db.ExecuteCMD(sql, dbDict);
|
dtRoms = db.ExecuteCMD(sql, dbDict);
|
||||||
@@ -746,7 +757,7 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void Rematcher(bool ForceExecute = false)
|
public void Rematcher(bool ForceExecute = false)
|
||||||
{
|
{
|
||||||
// rescan all titles with an unknown platform or title and see if we can get a match
|
// rescan all titles with an unknown platform or title and see if we can get a match
|
||||||
Logging.Log(Logging.LogType.Information, "Rematch Scan", "Rematch scan starting");
|
Logging.Log(Logging.LogType.Information, "Rematch Scan", "Rematch scan starting");
|
||||||
@@ -764,8 +775,11 @@ namespace gaseous_server.Classes
|
|||||||
Dictionary<string, object> dbDict = new Dictionary<string, object>();
|
Dictionary<string, object> dbDict = new Dictionary<string, object>();
|
||||||
dbDict.Add("lastmatchattemptdate", DateTime.UtcNow.AddDays(-7));
|
dbDict.Add("lastmatchattemptdate", DateTime.UtcNow.AddDays(-7));
|
||||||
DataTable data = db.ExecuteCMD(sql, dbDict);
|
DataTable data = db.ExecuteCMD(sql, dbDict);
|
||||||
|
int StatusCount = -0;
|
||||||
foreach (DataRow row in data.Rows)
|
foreach (DataRow row in data.Rows)
|
||||||
{
|
{
|
||||||
|
SetStatus(StatusCount, data.Rows.Count, "Running rematcher");
|
||||||
|
|
||||||
// get library
|
// get library
|
||||||
GameLibrary.LibraryItem library = GameLibrary.GetLibrary((int)row["LibraryId"]);
|
GameLibrary.LibraryItem library = GameLibrary.GetLibrary((int)row["LibraryId"]);
|
||||||
|
|
||||||
@@ -800,9 +814,13 @@ namespace gaseous_server.Classes
|
|||||||
dbLastAttemptDict.Add("id", romId);
|
dbLastAttemptDict.Add("id", romId);
|
||||||
dbLastAttemptDict.Add("lastmatchattemptdate", DateTime.UtcNow);
|
dbLastAttemptDict.Add("lastmatchattemptdate", DateTime.UtcNow);
|
||||||
db.ExecuteCMD(attemptSql, dbLastAttemptDict);
|
db.ExecuteCMD(attemptSql, dbLastAttemptDict);
|
||||||
|
|
||||||
|
StatusCount += 1;
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
|
|
||||||
Logging.Log(Logging.LogType.Information, "Rematch Scan", "Rematch scan completed");
|
Logging.Log(Logging.LogType.Information, "Rematch Scan", "Rematch scan completed");
|
||||||
|
ClearStatus();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -75,8 +75,42 @@ namespace gaseous_server.Classes
|
|||||||
LogToDisk(logItem, TraceOutput, null);
|
LogToDisk(logItem, TraceOutput, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
string correlationId;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (CallContext.GetData("CorrelationId").ToString() == null)
|
||||||
|
{
|
||||||
|
correlationId = "";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
correlationId = CallContext.GetData("CorrelationId").ToString();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
correlationId = "";
|
||||||
|
}
|
||||||
|
|
||||||
|
string callingProcess;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (CallContext.GetData("CallingProcess").ToString() == null)
|
||||||
|
{
|
||||||
|
callingProcess = "";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
callingProcess = CallContext.GetData("CallingProcess").ToString();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
callingProcess = "";
|
||||||
|
}
|
||||||
|
|
||||||
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
||||||
string sql = "DELETE FROM ServerLogs WHERE EventTime < @EventRententionDate; INSERT INTO ServerLogs (EventTime, EventType, Process, Message, Exception) VALUES (@EventTime, @EventType, @Process, @Message, @Exception);";
|
string sql = "DELETE FROM ServerLogs WHERE EventTime < @EventRententionDate; INSERT INTO ServerLogs (EventTime, EventType, Process, Message, Exception, CorrelationId, CallingProcess) VALUES (@EventTime, @EventType, @Process, @Message, @Exception, @correlationid, @callingprocess);";
|
||||||
Dictionary<string, object> dbDict = new Dictionary<string, object>();
|
Dictionary<string, object> dbDict = new Dictionary<string, object>();
|
||||||
dbDict.Add("EventRententionDate", DateTime.UtcNow.AddDays(Config.LoggingConfiguration.LogRetention * -1));
|
dbDict.Add("EventRententionDate", DateTime.UtcNow.AddDays(Config.LoggingConfiguration.LogRetention * -1));
|
||||||
dbDict.Add("EventTime", logItem.EventTime);
|
dbDict.Add("EventTime", logItem.EventTime);
|
||||||
@@ -84,6 +118,8 @@ namespace gaseous_server.Classes
|
|||||||
dbDict.Add("Process", logItem.Process);
|
dbDict.Add("Process", logItem.Process);
|
||||||
dbDict.Add("Message", logItem.Message);
|
dbDict.Add("Message", logItem.Message);
|
||||||
dbDict.Add("Exception", Common.ReturnValueIfNull(logItem.ExceptionValue, "").ToString());
|
dbDict.Add("Exception", Common.ReturnValueIfNull(logItem.ExceptionValue, "").ToString());
|
||||||
|
dbDict.Add("correlationid", correlationId);
|
||||||
|
dbDict.Add("callingprocess", callingProcess);
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -184,6 +220,24 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (model.CorrelationId != null)
|
||||||
|
{
|
||||||
|
if (model.CorrelationId.Length > 0)
|
||||||
|
{
|
||||||
|
dbDict.Add("correlationId", model.CorrelationId);
|
||||||
|
whereClauses.Add("CorrelationId = @correlationId");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (model.CallingProcess != null)
|
||||||
|
{
|
||||||
|
if (model.CallingProcess.Length > 0)
|
||||||
|
{
|
||||||
|
dbDict.Add("callingProcess", model.CallingProcess);
|
||||||
|
whereClauses.Add("CallingProcess = @callingProcess");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// compile WHERE clause
|
// compile WHERE clause
|
||||||
string whereClause = "";
|
string whereClause = "";
|
||||||
if (whereClauses.Count > 0)
|
if (whereClauses.Count > 0)
|
||||||
@@ -220,7 +274,9 @@ namespace gaseous_server.Classes
|
|||||||
EventType = (LogType)row["EventType"],
|
EventType = (LogType)row["EventType"],
|
||||||
Process = (string)row["Process"],
|
Process = (string)row["Process"],
|
||||||
Message = (string)row["Message"],
|
Message = (string)row["Message"],
|
||||||
ExceptionValue = (string)row["Exception"]
|
ExceptionValue = (string)row["Exception"],
|
||||||
|
CorrelationId = (string)row["CorrelationId"],
|
||||||
|
CallingProcess = (string)row["CallingProcess"]
|
||||||
};
|
};
|
||||||
|
|
||||||
logs.Add(log);
|
logs.Add(log);
|
||||||
@@ -243,6 +299,8 @@ namespace gaseous_server.Classes
|
|||||||
public DateTime EventTime { get; set; }
|
public DateTime EventTime { get; set; }
|
||||||
public LogType? EventType { get; set; }
|
public LogType? EventType { get; set; }
|
||||||
public string Process { get; set; } = "";
|
public string Process { get; set; } = "";
|
||||||
|
public string CorrelationId { get; set; } = "";
|
||||||
|
public string? CallingProcess { get; set; } = "";
|
||||||
private string _Message = "";
|
private string _Message = "";
|
||||||
public string Message
|
public string Message
|
||||||
{
|
{
|
||||||
@@ -267,6 +325,8 @@ namespace gaseous_server.Classes
|
|||||||
public DateTime? StartDateTime { get; set; }
|
public DateTime? StartDateTime { get; set; }
|
||||||
public DateTime? EndDateTime { get; set; }
|
public DateTime? EndDateTime { get; set; }
|
||||||
public string? SearchText { get; set; }
|
public string? SearchText { get; set; }
|
||||||
|
public string? CorrelationId { get; set; }
|
||||||
|
public string? CallingProcess { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -5,11 +5,11 @@ using Microsoft.VisualStudio.Web.CodeGeneration;
|
|||||||
|
|
||||||
namespace gaseous_server.Classes
|
namespace gaseous_server.Classes
|
||||||
{
|
{
|
||||||
public class Maintenance
|
public class Maintenance : QueueItemStatus
|
||||||
{
|
{
|
||||||
const int MaxFileAge = 30;
|
const int MaxFileAge = 30;
|
||||||
|
|
||||||
public static void RunMaintenance()
|
public void RunMaintenance()
|
||||||
{
|
{
|
||||||
// delete files and directories older than 7 days in PathsToClean
|
// delete files and directories older than 7 days in PathsToClean
|
||||||
List<string> PathsToClean = new List<string>();
|
List<string> PathsToClean = new List<string>();
|
||||||
@@ -49,8 +49,11 @@ namespace gaseous_server.Classes
|
|||||||
string sql = "SHOW TABLES;";
|
string sql = "SHOW TABLES;";
|
||||||
DataTable tables = db.ExecuteCMD(sql);
|
DataTable tables = db.ExecuteCMD(sql);
|
||||||
|
|
||||||
|
int StatusCounter = 1;
|
||||||
foreach (DataRow row in tables.Rows)
|
foreach (DataRow row in tables.Rows)
|
||||||
{
|
{
|
||||||
|
SetStatus(StatusCounter, tables.Rows.Count, "Optimising table " + row[0].ToString());
|
||||||
|
|
||||||
sql = "OPTIMIZE TABLE " + row[0].ToString();
|
sql = "OPTIMIZE TABLE " + row[0].ToString();
|
||||||
DataTable response = db.ExecuteCMD(sql);
|
DataTable response = db.ExecuteCMD(sql);
|
||||||
foreach (DataRow responseRow in response.Rows)
|
foreach (DataRow responseRow in response.Rows)
|
||||||
@@ -60,9 +63,12 @@ namespace gaseous_server.Classes
|
|||||||
{
|
{
|
||||||
retVal += responseRow.ItemArray[i] + "; ";
|
retVal += responseRow.ItemArray[i] + "; ";
|
||||||
}
|
}
|
||||||
Logging.Log(Logging.LogType.Information, "Maintenance", "Optimise table " + row[0].ToString() + ": " + retVal);
|
Logging.Log(Logging.LogType.Information, "Maintenance", "(" + StatusCounter + "/" + tables.Rows.Count + "): Optimise table " + row[0].ToString() + ": " + retVal);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
StatusCounter += 1;
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@@ -15,12 +15,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static AgeRating? GetAgeRatings(long? Id)
|
public static AgeRating? GetAgeRatings(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -117,7 +111,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<AgeRating> GetObjectFromServer(string WhereClause)
|
private static async Task<AgeRating> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get AgeRatings metadata
|
// get AgeRatings metadata
|
||||||
var results = await igdb.QueryAsync<AgeRating>(IGDBClient.Endpoints.AgeRating, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<AgeRating>(IGDBClient.Endpoints.AgeRating, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static AgeRatingContentDescription? GetAgeRatingContentDescriptions(long? Id)
|
public static AgeRatingContentDescription? GetAgeRatingContentDescriptions(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<AgeRatingContentDescription> GetObjectFromServer(string WhereClause)
|
private static async Task<AgeRatingContentDescription> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get AgeRatingContentDescriptionContentDescriptions metadata
|
// get AgeRatingContentDescriptionContentDescriptions metadata
|
||||||
var results = await igdb.QueryAsync<AgeRatingContentDescription>(IGDBClient.Endpoints.AgeRatingContentDescriptions, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<AgeRatingContentDescription>(IGDBClient.Endpoints.AgeRatingContentDescriptions, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static AlternativeName? GetAlternativeNames(long? Id)
|
public static AlternativeName? GetAlternativeNames(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<AlternativeName> GetObjectFromServer(string WhereClause)
|
private static async Task<AlternativeName> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get AlternativeNames metadata
|
// get AlternativeNames metadata
|
||||||
var results = await igdb.QueryAsync<AlternativeName>(IGDBClient.Endpoints.AlternativeNames, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<AlternativeName>(IGDBClient.Endpoints.AlternativeNames, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
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)
|
public static Artwork? GetArtwork(long? Id, string LogoPath)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -113,7 +107,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Artwork> GetObjectFromServer(string WhereClause, string LogoPath)
|
private static async Task<Artwork> GetObjectFromServer(string WhereClause, string LogoPath)
|
||||||
{
|
{
|
||||||
// get Artwork metadata
|
// get Artwork metadata
|
||||||
var results = await igdb.QueryAsync<Artwork>(IGDBClient.Endpoints.Artworks, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Artwork>(IGDBClient.Endpoints.Artworks, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
//GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId);
|
//GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId);
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static Collection? GetCollections(long? Id)
|
public static Collection? GetCollections(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Collection> GetObjectFromServer(string WhereClause)
|
private static async Task<Collection> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Collections metadata
|
// get Collections metadata
|
||||||
var results = await igdb.QueryAsync<Collection>(IGDBClient.Endpoints.Collections, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Collection>(IGDBClient.Endpoints.Collections, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
238
gaseous-server/Classes/Metadata/Communications.cs
Normal file
238
gaseous-server/Classes/Metadata/Communications.cs
Normal file
@@ -0,0 +1,238 @@
|
|||||||
|
using System.Net;
|
||||||
|
using IGDB;
|
||||||
|
using RestEase;
|
||||||
|
|
||||||
|
namespace gaseous_server.Classes.Metadata
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Handles all metadata API communications
|
||||||
|
/// </summary>
|
||||||
|
public class Communications
|
||||||
|
{
|
||||||
|
private static IGDBClient igdb = new IGDBClient(
|
||||||
|
// Found in Twitch Developer portal for your app
|
||||||
|
Config.IGDB.ClientId,
|
||||||
|
Config.IGDB.Secret
|
||||||
|
);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Configure metadata API communications
|
||||||
|
/// </summary>
|
||||||
|
public static MetadataSources MetadataSource
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return _MetadataSource;
|
||||||
|
}
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_MetadataSource = value;
|
||||||
|
|
||||||
|
switch (value)
|
||||||
|
{
|
||||||
|
case MetadataSources.IGDB:
|
||||||
|
// set rate limiter avoidance values
|
||||||
|
RateLimitAvoidanceWait = 1500;
|
||||||
|
RateLimitAvoidanceThreshold = 3;
|
||||||
|
RateLimitAvoidancePeriod = 1;
|
||||||
|
|
||||||
|
// set rate limiter recovery values
|
||||||
|
RateLimitRecoveryWaitTime = 10000;
|
||||||
|
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
// leave all values at default
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
private static MetadataSources _MetadataSource = MetadataSources.None;
|
||||||
|
|
||||||
|
// rate limit avoidance - what can we do to ensure that rate limiting is avoided?
|
||||||
|
// these values affect all communications
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// How long to wait to avoid hitting an API rate limiter
|
||||||
|
/// </summary>
|
||||||
|
private static int RateLimitAvoidanceWait = 2000;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// How many API calls in the period are allowed before we start introducing a wait
|
||||||
|
/// </summary>
|
||||||
|
private static int RateLimitAvoidanceThreshold = 80;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// A counter of API calls since the beginning of the period
|
||||||
|
/// </summary>
|
||||||
|
private static int RateLimitAvoidanceCallCount = 0;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// How large the period (in seconds) to measure API call counts against
|
||||||
|
/// </summary>
|
||||||
|
private static int RateLimitAvoidancePeriod = 60;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The start of the rate limit avoidance period
|
||||||
|
/// </summary>
|
||||||
|
private static DateTime RateLimitAvoidanceStartTime = DateTime.UtcNow;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Used to determine if we're already in rate limit avoidance mode - always query "InRateLimitAvoidanceMode"
|
||||||
|
/// for up to date mode status.
|
||||||
|
/// This bool is used to track status changes and should not be relied upon for current status.
|
||||||
|
/// </summary>
|
||||||
|
private static bool InRateLimitAvoidanceModeStatus = false;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Determine if we're in rate limit avoidance mode.
|
||||||
|
/// </summary>
|
||||||
|
private static bool InRateLimitAvoidanceMode
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
if (RateLimitAvoidanceStartTime.AddSeconds(RateLimitAvoidancePeriod) <= DateTime.UtcNow)
|
||||||
|
{
|
||||||
|
// avoidance period has expired - reset
|
||||||
|
RateLimitAvoidanceCallCount = 0;
|
||||||
|
RateLimitAvoidanceStartTime = DateTime.UtcNow;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// we're in the avoidance period
|
||||||
|
if (RateLimitAvoidanceCallCount > RateLimitAvoidanceThreshold)
|
||||||
|
{
|
||||||
|
// the number of call counts indicates we should throttle things a bit
|
||||||
|
if (InRateLimitAvoidanceModeStatus == false)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Information, "API Connection", "Entered rate limit avoidance period, API calls will be throttled by " + RateLimitAvoidanceWait + " milliseconds.");
|
||||||
|
InRateLimitAvoidanceModeStatus = true;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// still in full speed mode - no throttle required
|
||||||
|
if (InRateLimitAvoidanceModeStatus == true)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Information, "API Connection", "Exited rate limit avoidance period, API call rate is returned to full speed.");
|
||||||
|
InRateLimitAvoidanceModeStatus = false;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// rate limit handling - how long to wait to allow the server to recover and try again
|
||||||
|
// these values affect ALL communications if a 429 response code is received
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// How long to wait (in milliseconds) if a 429 status code is received before trying again
|
||||||
|
/// </summary>
|
||||||
|
private static int RateLimitRecoveryWaitTime = 10000;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The time when normal communications can attempt to be resumed
|
||||||
|
/// </summary>
|
||||||
|
private static DateTime RateLimitResumeTime = DateTime.UtcNow.AddMinutes(5 * -1);
|
||||||
|
|
||||||
|
// rate limit retry - how many times to retry before aborting
|
||||||
|
private int RetryAttempts = 0;
|
||||||
|
private int RetryAttemptsMax = 3;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Supported metadata sources
|
||||||
|
/// </summary>
|
||||||
|
public enum MetadataSources
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// None - always returns null for metadata requests - should not really be using this source
|
||||||
|
/// </summary>
|
||||||
|
None,
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// IGDB - queries the IGDB service for metadata
|
||||||
|
/// </summary>
|
||||||
|
IGDB
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Request data from the metadata API
|
||||||
|
/// </summary>
|
||||||
|
/// <typeparam name="T">Type of object to return</typeparam>
|
||||||
|
/// <param name="Endpoint">API endpoint segment to use</param>
|
||||||
|
/// <param name="Fields">Fields to request from the API</param>
|
||||||
|
/// <param name="Query">Selection criteria for data to request</param>
|
||||||
|
/// <returns></returns>
|
||||||
|
public async Task<T[]?> APIComm<T>(string Endpoint, string Fields, string Query)
|
||||||
|
{
|
||||||
|
switch (_MetadataSource)
|
||||||
|
{
|
||||||
|
case MetadataSources.None:
|
||||||
|
return null;
|
||||||
|
case MetadataSources.IGDB:
|
||||||
|
return await IGDBAPI<T>(Endpoint, Fields, Query);
|
||||||
|
default:
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async Task<T[]> IGDBAPI<T>(string Endpoint, string Fields, string Query)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Debug, "API Connection", "Accessing API for endpoint: " + Endpoint);
|
||||||
|
|
||||||
|
if (RateLimitResumeTime > DateTime.UtcNow)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Information, "API Connection", "IGDB rate limit hit. Pausing API communications until " + RateLimitResumeTime.ToString() + ". Attempt " + RetryAttempts + " of " + RetryAttemptsMax + " retries.");
|
||||||
|
Thread.Sleep(RateLimitRecoveryWaitTime);
|
||||||
|
}
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (InRateLimitAvoidanceMode == true)
|
||||||
|
{
|
||||||
|
// sleep for a moment to help avoid hitting the rate limiter
|
||||||
|
Thread.Sleep(RateLimitAvoidanceWait);
|
||||||
|
}
|
||||||
|
|
||||||
|
// perform the actual API call
|
||||||
|
var results = await igdb.QueryAsync<T>(Endpoint, query: Fields + " " + Query + ";");
|
||||||
|
|
||||||
|
// increment rate limiter avoidance call count
|
||||||
|
RateLimitAvoidanceCallCount += 1;
|
||||||
|
|
||||||
|
return results;
|
||||||
|
}
|
||||||
|
catch (ApiException apiEx)
|
||||||
|
{
|
||||||
|
switch (apiEx.StatusCode)
|
||||||
|
{
|
||||||
|
case HttpStatusCode.TooManyRequests:
|
||||||
|
if (RetryAttempts >= RetryAttemptsMax)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Warning, "API Connection", "IGDB rate limiter attempts expired. Aborting.", apiEx);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Information, "API Connection", "IGDB API rate limit hit while accessing endpoint " + Endpoint, apiEx);
|
||||||
|
|
||||||
|
RetryAttempts += 1;
|
||||||
|
|
||||||
|
return await IGDBAPI<T>(Endpoint, Fields, Query);
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
Logging.Log(Logging.LogType.Warning, "API Connection", "Exception when accessing endpoint " + Endpoint, apiEx);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch(Exception ex)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Warning, "API Connection", "Exception when accessing endpoint " + Endpoint, ex);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@@ -12,12 +12,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static Company? GetCompanies(long? Id)
|
public static Company? GetCompanies(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -111,7 +105,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Company> GetObjectFromServer(string WhereClause)
|
private static async Task<Company> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Companies metadata
|
// get Companies metadata
|
||||||
var results = await igdb.QueryAsync<Company>(IGDBClient.Endpoints.Companies, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Company>(IGDBClient.Endpoints.Companies, fieldList, WhereClause);
|
||||||
if (results.Length > 0)
|
if (results.Length > 0)
|
||||||
{
|
{
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static CompanyLogo? GetCompanyLogo(long? Id, string LogoPath)
|
public static CompanyLogo? GetCompanyLogo(long? Id, string LogoPath)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -118,7 +112,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<CompanyLogo?> GetObjectFromServer(string WhereClause, string LogoPath)
|
private static async Task<CompanyLogo?> GetObjectFromServer(string WhereClause, string LogoPath)
|
||||||
{
|
{
|
||||||
// get CompanyLogo metadata
|
// get CompanyLogo metadata
|
||||||
var results = await igdb.QueryAsync<CompanyLogo>(IGDBClient.Endpoints.CompanyLogos, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<CompanyLogo>(IGDBClient.Endpoints.CompanyLogos, fieldList, WhereClause);
|
||||||
if (results.Length > 0)
|
if (results.Length > 0)
|
||||||
{
|
{
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
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)
|
public static Cover? GetCover(long? Id, string LogoPath)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -113,7 +107,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Cover> GetObjectFromServer(string WhereClause, string LogoPath)
|
private static async Task<Cover> GetObjectFromServer(string WhereClause, string LogoPath)
|
||||||
{
|
{
|
||||||
// get Cover metadata
|
// get Cover metadata
|
||||||
var results = await igdb.QueryAsync<Cover>(IGDBClient.Endpoints.Covers, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Cover>(IGDBClient.Endpoints.Covers, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
//GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId);
|
//GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId);
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static ExternalGame? GetExternalGames(long? Id)
|
public static ExternalGame? GetExternalGames(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -106,7 +100,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<ExternalGame?> GetObjectFromServer(string WhereClause)
|
private static async Task<ExternalGame?> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get ExternalGames metadata
|
// get ExternalGames metadata
|
||||||
var results = await igdb.QueryAsync<ExternalGame>(IGDBClient.Endpoints.ExternalGames, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<ExternalGame>(IGDBClient.Endpoints.ExternalGames, fieldList, WhereClause);
|
||||||
if (results.Length > 0)
|
if (results.Length > 0)
|
||||||
{
|
{
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static Franchise? GetFranchises(long? Id)
|
public static Franchise? GetFranchises(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Franchise> GetObjectFromServer(string WhereClause)
|
private static async Task<Franchise> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get FranchiseContentDescriptions metadata
|
// get FranchiseContentDescriptions metadata
|
||||||
var results = await igdb.QueryAsync<Franchise>(IGDBClient.Endpoints.Franchies, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Franchise>(IGDBClient.Endpoints.Franchies, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static GameMode? GetGame_Modes(long? Id)
|
public static GameMode? GetGame_Modes(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<GameMode> GetObjectFromServer(string WhereClause)
|
private static async Task<GameMode> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Game_Modes metadata
|
// get Game_Modes metadata
|
||||||
var results = await igdb.QueryAsync<GameMode>(IGDBClient.Endpoints.GameModes, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<GameMode>(IGDBClient.Endpoints.GameModes, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static GameVideo? GetGame_Videos(long? Id)
|
public static GameVideo? GetGame_Videos(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<GameVideo> GetObjectFromServer(string WhereClause)
|
private static async Task<GameVideo> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Game_Videos metadata
|
// get Game_Videos metadata
|
||||||
var results = await igdb.QueryAsync<GameVideo>(IGDBClient.Endpoints.GameVideos, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<GameVideo>(IGDBClient.Endpoints.GameVideos, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -20,12 +20,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{}
|
{}
|
||||||
}
|
}
|
||||||
|
|
||||||
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, bool getAllMetadata, bool followSubGames, bool forceRefresh)
|
public static Game? GetGame(long Id, bool getAllMetadata, bool followSubGames, bool forceRefresh)
|
||||||
{
|
{
|
||||||
if (Id == 0)
|
if (Id == 0)
|
||||||
@@ -295,7 +289,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Game> GetObjectFromServer(string WhereClause)
|
private static async Task<Game> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Game metadata
|
// get Game metadata
|
||||||
var results = await igdb.QueryAsync<Game>(IGDBClient.Endpoints.Games, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Game>(IGDBClient.Endpoints.Games, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
@@ -310,7 +305,7 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Game[]> _SearchForGame(string SearchString, long PlatformId, SearchType searchType)
|
private static async Task<Game[]> _SearchForGame(string SearchString, long PlatformId, SearchType searchType)
|
||||||
{
|
{
|
||||||
string searchBody = "";
|
string searchBody = "";
|
||||||
searchBody += "fields id,name,slug,platforms,summary; ";
|
string searchFields = "fields id,name,slug,platforms,summary; ";
|
||||||
switch (searchType)
|
switch (searchType)
|
||||||
{
|
{
|
||||||
case SearchType.searchNoPlatform:
|
case SearchType.searchNoPlatform:
|
||||||
@@ -330,7 +325,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
|
|
||||||
|
|
||||||
// get Game metadata
|
// get Game metadata
|
||||||
var results = await igdb.QueryAsync<Game>(IGDBClient.Endpoints.Games, query: searchBody);
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Game>(IGDBClient.Endpoints.Games, searchFields, searchBody);
|
||||||
|
|
||||||
return results;
|
return results;
|
||||||
}
|
}
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static Genre? GetGenres(long? Id)
|
public static Genre? GetGenres(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Genre> GetObjectFromServer(string WhereClause)
|
private static async Task<Genre> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Genres metadata
|
// get Genres metadata
|
||||||
var results = await igdb.QueryAsync<Genre>(IGDBClient.Endpoints.Genres, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Genre>(IGDBClient.Endpoints.Genres, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -12,12 +12,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static InvolvedCompany? GetInvolvedCompanies(long? Id)
|
public static InvolvedCompany? GetInvolvedCompanies(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -113,7 +107,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
// get InvolvedCompanies metadata
|
// get InvolvedCompanies metadata
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var results = await igdb.QueryAsync<InvolvedCompany>(IGDBClient.Endpoints.InvolvedCompanies, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<InvolvedCompany>(IGDBClient.Endpoints.InvolvedCompanies, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static MultiplayerMode? GetGame_MultiplayerModes(long? Id)
|
public static MultiplayerMode? GetGame_MultiplayerModes(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<MultiplayerMode> GetObjectFromServer(string WhereClause)
|
private static async Task<MultiplayerMode> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Game_MultiplayerModes metadata
|
// get Game_MultiplayerModes metadata
|
||||||
var results = await igdb.QueryAsync<MultiplayerMode>(IGDBClient.Endpoints.MultiplayerModes, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<MultiplayerMode>(IGDBClient.Endpoints.MultiplayerModes, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static PlatformLogo? GetPlatformLogo(long? Id, string LogoPath)
|
public static PlatformLogo? GetPlatformLogo(long? Id, string LogoPath)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -118,7 +112,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<PlatformLogo?> GetObjectFromServer(string WhereClause, string LogoPath)
|
private static async Task<PlatformLogo?> GetObjectFromServer(string WhereClause, string LogoPath)
|
||||||
{
|
{
|
||||||
// get PlatformLogo metadata
|
// get PlatformLogo metadata
|
||||||
var results = await igdb.QueryAsync<PlatformLogo>(IGDBClient.Endpoints.PlatformLogos, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<PlatformLogo>(IGDBClient.Endpoints.PlatformLogos, fieldList, WhereClause);
|
||||||
if (results.Length > 0)
|
if (results.Length > 0)
|
||||||
{
|
{
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
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)
|
if (Id == 0)
|
||||||
@@ -113,7 +107,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<PlatformVersion?> GetObjectFromServer(string WhereClause)
|
private static async Task<PlatformVersion?> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get PlatformVersion metadata
|
// get PlatformVersion metadata
|
||||||
var results = await igdb.QueryAsync<PlatformVersion>(IGDBClient.Endpoints.PlatformVersions, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<PlatformVersion>(IGDBClient.Endpoints.PlatformVersions, fieldList, WhereClause);
|
||||||
if (results.Length > 0)
|
if (results.Length > 0)
|
||||||
{
|
{
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
@@ -15,12 +15,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static Platform? GetPlatform(long Id, bool forceRefresh = false)
|
public static Platform? GetPlatform(long Id, bool forceRefresh = false)
|
||||||
{
|
{
|
||||||
if (Id == 0)
|
if (Id == 0)
|
||||||
@@ -168,7 +162,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Platform> GetObjectFromServer(string WhereClause)
|
private static async Task<Platform> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get platform metadata
|
// get platform metadata
|
||||||
var results = await igdb.QueryAsync<Platform>(IGDBClient.Endpoints.Platforms, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Platform>(IGDBClient.Endpoints.Platforms, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static PlayerPerspective? GetGame_PlayerPerspectives(long? Id)
|
public static PlayerPerspective? GetGame_PlayerPerspectives(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -105,7 +99,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<PlayerPerspective> GetObjectFromServer(string WhereClause)
|
private static async Task<PlayerPerspective> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Game_PlayerPerspectives metadata
|
// get Game_PlayerPerspectives metadata
|
||||||
var results = await igdb.QueryAsync<PlayerPerspective>(IGDBClient.Endpoints.PlayerPerspectives, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<PlayerPerspective>(IGDBClient.Endpoints.PlayerPerspectives, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static ReleaseDate? GetReleaseDates(long? Id)
|
public static ReleaseDate? GetReleaseDates(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -103,7 +97,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<ReleaseDate> GetObjectFromServer(string WhereClause)
|
private static async Task<ReleaseDate> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get ReleaseDates metadata
|
// get ReleaseDates metadata
|
||||||
var results = await igdb.QueryAsync<ReleaseDate>(IGDBClient.Endpoints.ReleaseDates, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<ReleaseDate>(IGDBClient.Endpoints.ReleaseDates, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
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)
|
public static Screenshot? GetScreenshot(long? Id, string LogoPath)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -114,7 +108,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Screenshot> GetObjectFromServer(string WhereClause, string LogoPath)
|
private static async Task<Screenshot> GetObjectFromServer(string WhereClause, string LogoPath)
|
||||||
{
|
{
|
||||||
// get Screenshot metadata
|
// get Screenshot metadata
|
||||||
var results = await igdb.QueryAsync<Screenshot>(IGDBClient.Endpoints.Screenshots, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Screenshot>(IGDBClient.Endpoints.Screenshots, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
//GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId);
|
//GetImageFromServer(result.Url, LogoPath, LogoSize.t_thumb, result.ImageId);
|
||||||
|
@@ -16,32 +16,32 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
Expired
|
Expired
|
||||||
}
|
}
|
||||||
|
|
||||||
private static Dictionary<string, MemoryCacheObject> ObjectCache = new Dictionary<string, MemoryCacheObject>();
|
//private static Dictionary<string, MemoryCacheObject> ObjectCache = new Dictionary<string, MemoryCacheObject>();
|
||||||
|
|
||||||
public static CacheStatus GetCacheStatus(string Endpoint, string Slug)
|
public static CacheStatus GetCacheStatus(string Endpoint, string Slug)
|
||||||
{
|
{
|
||||||
CacheClean();
|
// CacheClean();
|
||||||
if (ObjectCache.ContainsKey(Endpoint + Slug))
|
// if (ObjectCache.ContainsKey(Endpoint + Slug))
|
||||||
{
|
// {
|
||||||
return CacheStatus.Current;
|
// return CacheStatus.Current;
|
||||||
}
|
// }
|
||||||
else
|
// else
|
||||||
{
|
// {
|
||||||
return _GetCacheStatus(Endpoint, "slug", Slug);
|
return _GetCacheStatus(Endpoint, "slug", Slug);
|
||||||
}
|
// }
|
||||||
}
|
}
|
||||||
|
|
||||||
public static CacheStatus GetCacheStatus(string Endpoint, long Id)
|
public static CacheStatus GetCacheStatus(string Endpoint, long Id)
|
||||||
{
|
{
|
||||||
CacheClean();
|
// CacheClean();
|
||||||
if (ObjectCache.ContainsKey(Endpoint + Id))
|
// if (ObjectCache.ContainsKey(Endpoint + Id))
|
||||||
{
|
// {
|
||||||
return CacheStatus.Current;
|
// return CacheStatus.Current;
|
||||||
}
|
// }
|
||||||
else
|
// else
|
||||||
{
|
// {
|
||||||
return _GetCacheStatus(Endpoint, "id", Id);
|
return _GetCacheStatus(Endpoint, "id", Id);
|
||||||
}
|
// }
|
||||||
}
|
}
|
||||||
|
|
||||||
public static CacheStatus GetCacheStatus(DataRow Row)
|
public static CacheStatus GetCacheStatus(DataRow Row)
|
||||||
@@ -185,20 +185,20 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
string Endpoint = EndpointType.GetType().Name;
|
string Endpoint = EndpointType.GetType().Name;
|
||||||
|
|
||||||
if (ObjectCache.ContainsKey(Endpoint + SearchValue))
|
// if (ObjectCache.ContainsKey(Endpoint + SearchValue))
|
||||||
{
|
// {
|
||||||
MemoryCacheObject cacheObject = ObjectCache[Endpoint + SearchValue];
|
// MemoryCacheObject cacheObject = ObjectCache[Endpoint + SearchValue];
|
||||||
if (cacheObject.ExpiryTime < DateTime.UtcNow)
|
// if (cacheObject.ExpiryTime < DateTime.UtcNow)
|
||||||
{
|
// {
|
||||||
// object has expired, remove it
|
// // object has expired, remove it
|
||||||
ObjectCache.Remove(Endpoint + SearchValue);
|
// ObjectCache.Remove(Endpoint + SearchValue);
|
||||||
}
|
// }
|
||||||
else
|
// else
|
||||||
{
|
// {
|
||||||
// object is valid, return it
|
// // object is valid, return it
|
||||||
return (T)cacheObject.Object;
|
// return (T)cacheObject.Object;
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
||||||
|
|
||||||
@@ -218,19 +218,19 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
DataRow dataRow = dt.Rows[0];
|
DataRow dataRow = dt.Rows[0];
|
||||||
object returnObject = BuildCacheObject<T>(EndpointType, dataRow);
|
object returnObject = BuildCacheObject<T>(EndpointType, dataRow);
|
||||||
try {
|
// try {
|
||||||
if (!ObjectCache.ContainsKey(Endpoint + SearchValue))
|
// if (!ObjectCache.ContainsKey(Endpoint + SearchValue))
|
||||||
{
|
// {
|
||||||
ObjectCache.Add(Endpoint + SearchValue, new MemoryCacheObject{
|
// ObjectCache.Add(Endpoint + SearchValue, new MemoryCacheObject{
|
||||||
Object = returnObject
|
// Object = returnObject
|
||||||
});
|
// });
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
catch
|
// catch
|
||||||
{
|
// {
|
||||||
// unable add item to cache
|
// // unable add item to cache
|
||||||
ObjectCache.Clear();
|
// ObjectCache.Clear();
|
||||||
}
|
// }
|
||||||
return (T)returnObject;
|
return (T)returnObject;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -414,6 +414,12 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
case "[igdb.models.startdatecategory":
|
case "[igdb.models.startdatecategory":
|
||||||
property.SetValue(EndpointType, (StartDateCategory)dataRow[property.Name]);
|
property.SetValue(EndpointType, (StartDateCategory)dataRow[property.Name]);
|
||||||
break;
|
break;
|
||||||
|
case "[igdb.models.releasedateregion":
|
||||||
|
property.SetValue(EndpointType, (ReleaseDateRegion)dataRow[property.Name]);
|
||||||
|
break;
|
||||||
|
case "[igdb.models.releasedatecategory":
|
||||||
|
property.SetValue(EndpointType, (ReleaseDateCategory)dataRow[property.Name]);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
property.SetValue(EndpointType, dataRow[property.Name]);
|
property.SetValue(EndpointType, dataRow[property.Name]);
|
||||||
break;
|
break;
|
||||||
@@ -464,28 +470,28 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void CacheClean()
|
// private static void CacheClean()
|
||||||
{
|
// {
|
||||||
try
|
// try
|
||||||
{
|
// {
|
||||||
if (ObjectCache == null)
|
// if (ObjectCache == null)
|
||||||
{
|
// {
|
||||||
ObjectCache = new Dictionary<string, MemoryCacheObject>();
|
// ObjectCache = new Dictionary<string, MemoryCacheObject>();
|
||||||
}
|
// }
|
||||||
Dictionary<string, MemoryCacheObject> workCache = ObjectCache;
|
// Dictionary<string, MemoryCacheObject> workCache = ObjectCache;
|
||||||
foreach (KeyValuePair<string, MemoryCacheObject> objectCache in workCache)
|
// foreach (KeyValuePair<string, MemoryCacheObject> objectCache in workCache)
|
||||||
{
|
// {
|
||||||
if (objectCache.Value.ExpiryTime < DateTime.UtcNow)
|
// if (objectCache.Value.ExpiryTime < DateTime.UtcNow)
|
||||||
{
|
// {
|
||||||
ObjectCache.Remove(objectCache.Key);
|
// ObjectCache.Remove(objectCache.Key);
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
catch
|
// catch
|
||||||
{
|
// {
|
||||||
ObjectCache = new Dictionary<string, MemoryCacheObject>();
|
// ObjectCache = new Dictionary<string, MemoryCacheObject>();
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
private class MemoryCacheObject
|
private class MemoryCacheObject
|
||||||
{
|
{
|
||||||
|
@@ -13,12 +13,6 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
public static Theme? GetGame_Themes(long? Id)
|
public static Theme? GetGame_Themes(long? Id)
|
||||||
{
|
{
|
||||||
if ((Id == 0) || (Id == null))
|
if ((Id == 0) || (Id == null))
|
||||||
@@ -105,7 +99,8 @@ namespace gaseous_server.Classes.Metadata
|
|||||||
private static async Task<Theme> GetObjectFromServer(string WhereClause)
|
private static async Task<Theme> GetObjectFromServer(string WhereClause)
|
||||||
{
|
{
|
||||||
// get Game_Themes metadata
|
// get Game_Themes metadata
|
||||||
var results = await igdb.QueryAsync<Theme>(IGDBClient.Endpoints.Themes, query: fieldList + " " + WhereClause + ";");
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Theme>(IGDBClient.Endpoints.Themes, fieldList, WhereClause);
|
||||||
var result = results.First();
|
var result = results.First();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
@@ -4,30 +4,39 @@ using gaseous_server.Models;
|
|||||||
|
|
||||||
namespace gaseous_server.Classes
|
namespace gaseous_server.Classes
|
||||||
{
|
{
|
||||||
public class MetadataManagement
|
public class MetadataManagement : QueueItemStatus
|
||||||
{
|
{
|
||||||
public static void RefreshMetadata(bool forceRefresh = false)
|
public void RefreshMetadata(bool forceRefresh = false)
|
||||||
{
|
{
|
||||||
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
||||||
string sql = "";
|
string sql = "";
|
||||||
DataTable dt = new DataTable();
|
DataTable dt = new DataTable();
|
||||||
|
|
||||||
|
// disabling forceRefresh
|
||||||
|
forceRefresh = false;
|
||||||
|
|
||||||
// update platforms
|
// update platforms
|
||||||
sql = "SELECT Id, `Name` FROM Platform;";
|
sql = "SELECT Id, `Name` FROM Platform;";
|
||||||
dt = db.ExecuteCMD(sql);
|
dt = db.ExecuteCMD(sql);
|
||||||
|
|
||||||
|
int StatusCounter = 1;
|
||||||
foreach (DataRow dr in dt.Rows)
|
foreach (DataRow dr in dt.Rows)
|
||||||
{
|
{
|
||||||
|
SetStatus(StatusCounter, dt.Rows.Count, "Refreshing metadata for platform " + dr["name"]);
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
Logging.Log(Logging.LogType.Information, "Metadata Refresh", "Refreshing metadata for platform " + dr["name"] + " (" + dr["id"] + ")");
|
Logging.Log(Logging.LogType.Information, "Metadata Refresh", "(" + StatusCounter + "/" + dt.Rows.Count + "): Refreshing metadata for platform " + dr["name"] + " (" + dr["id"] + ")");
|
||||||
Metadata.Platforms.GetPlatform((long)dr["id"], true);
|
Metadata.Platforms.GetPlatform((long)dr["id"], true);
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
Logging.Log(Logging.LogType.Critical, "Metadata Refresh", "An error occurred while refreshing metadata for " + dr["name"], ex);
|
Logging.Log(Logging.LogType.Critical, "Metadata Refresh", "An error occurred while refreshing metadata for " + dr["name"], ex);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
StatusCounter += 1;
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
|
|
||||||
// update games
|
// update games
|
||||||
if (forceRefresh == true)
|
if (forceRefresh == true)
|
||||||
@@ -42,18 +51,24 @@ namespace gaseous_server.Classes
|
|||||||
}
|
}
|
||||||
dt = db.ExecuteCMD(sql);
|
dt = db.ExecuteCMD(sql);
|
||||||
|
|
||||||
|
StatusCounter = 1;
|
||||||
foreach (DataRow dr in dt.Rows)
|
foreach (DataRow dr in dt.Rows)
|
||||||
{
|
{
|
||||||
|
SetStatus(StatusCounter, dt.Rows.Count, "Refreshing metadata for game " + dr["name"]);
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
Logging.Log(Logging.LogType.Information, "Metadata Refresh", "Refreshing metadata for game " + dr["name"] + " (" + dr["id"] + ")");
|
Logging.Log(Logging.LogType.Information, "Metadata Refresh", "(" + StatusCounter + "/" + dt.Rows.Count + "): Refreshing metadata for game " + dr["name"] + " (" + dr["id"] + ")");
|
||||||
Metadata.Games.GetGame((long)dr["id"], true, false, forceRefresh);
|
Metadata.Games.GetGame((long)dr["id"], true, false, forceRefresh);
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
Logging.Log(Logging.LogType.Critical, "Metadata Refresh", "An error occurred while refreshing metadata for " + dr["name"], ex);
|
Logging.Log(Logging.LogType.Critical, "Metadata Refresh", "An error occurred while refreshing metadata for " + dr["name"], ex);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
StatusCounter += 1;
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
41
gaseous-server/Classes/QueueItemStatus.cs
Normal file
41
gaseous-server/Classes/QueueItemStatus.cs
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
namespace gaseous_server.Classes
|
||||||
|
{
|
||||||
|
public class QueueItemStatus
|
||||||
|
{
|
||||||
|
internal ProcessQueue.QueueItem? CallingQueueItem = null;
|
||||||
|
|
||||||
|
private int _CurrentItemNumber = 0;
|
||||||
|
private int _MaxItemsNumber = 0;
|
||||||
|
private string _StatusText = "";
|
||||||
|
|
||||||
|
public int CurrentItemNumber => _CurrentItemNumber;
|
||||||
|
public int MaxItemsNumber => _MaxItemsNumber;
|
||||||
|
public string StatusText => _StatusText;
|
||||||
|
|
||||||
|
public void SetStatus(int CurrentItemNumber, int MaxItemsNumber, string StatusText)
|
||||||
|
{
|
||||||
|
this._CurrentItemNumber = CurrentItemNumber;
|
||||||
|
this._MaxItemsNumber = MaxItemsNumber;
|
||||||
|
this._StatusText = StatusText;
|
||||||
|
|
||||||
|
if (CallingQueueItem != null)
|
||||||
|
{
|
||||||
|
CallingQueueItem.CurrentState = _CurrentItemNumber + " of " + _MaxItemsNumber + ": " + _StatusText;
|
||||||
|
CallingQueueItem.CurrentStateProgress = _CurrentItemNumber + " of " + _MaxItemsNumber;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void ClearStatus()
|
||||||
|
{
|
||||||
|
this._CurrentItemNumber = 0;
|
||||||
|
this._MaxItemsNumber = 0;
|
||||||
|
this._StatusText = "";
|
||||||
|
|
||||||
|
if (CallingQueueItem != null)
|
||||||
|
{
|
||||||
|
CallingQueueItem.CurrentState = "";
|
||||||
|
CallingQueueItem.CurrentStateProgress = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@@ -6,7 +6,7 @@ using System.Data;
|
|||||||
|
|
||||||
namespace gaseous_server.SignatureIngestors.XML
|
namespace gaseous_server.SignatureIngestors.XML
|
||||||
{
|
{
|
||||||
public class XMLIngestor
|
public class XMLIngestor : QueueItemStatus
|
||||||
{
|
{
|
||||||
public void Import(string SearchPath, gaseous_signature_parser.parser.SignatureParser XMLType)
|
public void Import(string SearchPath, gaseous_signature_parser.parser.SignatureParser XMLType)
|
||||||
{
|
{
|
||||||
@@ -31,222 +31,232 @@ namespace gaseous_server.SignatureIngestors.XML
|
|||||||
{
|
{
|
||||||
string XMLFile = PathContents[i];
|
string XMLFile = PathContents[i];
|
||||||
|
|
||||||
// check xml file md5
|
SetStatus(i + 1, PathContents.Length, "Processing signature file: " + XMLFile);
|
||||||
Common.hashObject hashObject = new Common.hashObject(XMLFile);
|
|
||||||
sql = "SELECT * FROM Signatures_Sources WHERE SourceMD5=@sourcemd5";
|
|
||||||
dbDict = new Dictionary<string, object>();
|
|
||||||
dbDict.Add("sourcemd5", hashObject.md5hash);
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
|
|
||||||
if (sigDB.Rows.Count == 0)
|
if (Common.SkippableFiles.Contains(Path.GetFileName(XMLFile), StringComparer.OrdinalIgnoreCase))
|
||||||
{
|
{
|
||||||
try
|
Logging.Log(Logging.LogType.Information, "Signature Ingestor - XML", "Skipping file: " + XMLFile);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// check xml file md5
|
||||||
|
Common.hashObject hashObject = new Common.hashObject(XMLFile);
|
||||||
|
sql = "SELECT * FROM Signatures_Sources WHERE SourceMD5=@sourcemd5";
|
||||||
|
dbDict = new Dictionary<string, object>();
|
||||||
|
dbDict.Add("sourcemd5", hashObject.md5hash);
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
|
||||||
|
if (sigDB.Rows.Count == 0)
|
||||||
{
|
{
|
||||||
Logging.Log(Logging.LogType.Information, "Signature Ingestor - XML", "Importing file: " + XMLFile);
|
try
|
||||||
|
|
||||||
// start parsing file
|
|
||||||
gaseous_signature_parser.parser Parser = new gaseous_signature_parser.parser();
|
|
||||||
RomSignatureObject Object = Parser.ParseSignatureDAT(XMLFile, XMLType);
|
|
||||||
|
|
||||||
// store in database
|
|
||||||
string[] flipNameAndDescription = {
|
|
||||||
"MAMEArcade",
|
|
||||||
"MAMEMess"
|
|
||||||
};
|
|
||||||
|
|
||||||
// store source object
|
|
||||||
bool processGames = false;
|
|
||||||
if (Object.SourceMd5 != null)
|
|
||||||
{
|
{
|
||||||
sql = "SELECT * FROM Signatures_Sources WHERE SourceMD5=@sourcemd5";
|
Logging.Log(Logging.LogType.Information, "Signature Ingestor - XML", "Importing file: " + XMLFile);
|
||||||
dbDict = new Dictionary<string, object>();
|
|
||||||
string sourceUriStr = "";
|
// start parsing file
|
||||||
if (Object.Url != null)
|
gaseous_signature_parser.parser Parser = new gaseous_signature_parser.parser();
|
||||||
|
RomSignatureObject Object = Parser.ParseSignatureDAT(XMLFile, XMLType);
|
||||||
|
|
||||||
|
// store in database
|
||||||
|
string[] flipNameAndDescription = {
|
||||||
|
"MAMEArcade",
|
||||||
|
"MAMEMess"
|
||||||
|
};
|
||||||
|
|
||||||
|
// store source object
|
||||||
|
bool processGames = false;
|
||||||
|
if (Object.SourceMd5 != null)
|
||||||
{
|
{
|
||||||
sourceUriStr = Object.Url.ToString();
|
sql = "SELECT * FROM Signatures_Sources WHERE SourceMD5=@sourcemd5";
|
||||||
}
|
dbDict = new Dictionary<string, object>();
|
||||||
dbDict.Add("name", Common.ReturnValueIfNull(Object.Name, ""));
|
string sourceUriStr = "";
|
||||||
dbDict.Add("description", Common.ReturnValueIfNull(Object.Description, ""));
|
if (Object.Url != null)
|
||||||
dbDict.Add("category", Common.ReturnValueIfNull(Object.Category, ""));
|
|
||||||
dbDict.Add("version", Common.ReturnValueIfNull(Object.Version, ""));
|
|
||||||
dbDict.Add("author", Common.ReturnValueIfNull(Object.Author, ""));
|
|
||||||
dbDict.Add("email", Common.ReturnValueIfNull(Object.Email, ""));
|
|
||||||
dbDict.Add("homepage", Common.ReturnValueIfNull(Object.Homepage, ""));
|
|
||||||
dbDict.Add("uri", sourceUriStr);
|
|
||||||
dbDict.Add("sourcetype", Common.ReturnValueIfNull(Object.SourceType, ""));
|
|
||||||
dbDict.Add("sourcemd5", Object.SourceMd5);
|
|
||||||
dbDict.Add("sourcesha1", Object.SourceSHA1);
|
|
||||||
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
if (sigDB.Rows.Count == 0)
|
|
||||||
{
|
|
||||||
// entry not present, insert it
|
|
||||||
sql = "INSERT INTO Signatures_Sources (Name, Description, Category, Version, Author, Email, Homepage, Url, SourceType, SourceMD5, SourceSHA1) VALUES (@name, @description, @category, @version, @author, @email, @homepage, @uri, @sourcetype, @sourcemd5, @sourcesha1)";
|
|
||||||
|
|
||||||
db.ExecuteCMD(sql, dbDict);
|
|
||||||
|
|
||||||
processGames = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (processGames == true)
|
|
||||||
{
|
|
||||||
for (int x = 0; x < Object.Games.Count; ++x)
|
|
||||||
{
|
{
|
||||||
RomSignatureObject.Game gameObject = Object.Games[x];
|
sourceUriStr = Object.Url.ToString();
|
||||||
|
}
|
||||||
|
dbDict.Add("name", Common.ReturnValueIfNull(Object.Name, ""));
|
||||||
|
dbDict.Add("description", Common.ReturnValueIfNull(Object.Description, ""));
|
||||||
|
dbDict.Add("category", Common.ReturnValueIfNull(Object.Category, ""));
|
||||||
|
dbDict.Add("version", Common.ReturnValueIfNull(Object.Version, ""));
|
||||||
|
dbDict.Add("author", Common.ReturnValueIfNull(Object.Author, ""));
|
||||||
|
dbDict.Add("email", Common.ReturnValueIfNull(Object.Email, ""));
|
||||||
|
dbDict.Add("homepage", Common.ReturnValueIfNull(Object.Homepage, ""));
|
||||||
|
dbDict.Add("uri", sourceUriStr);
|
||||||
|
dbDict.Add("sourcetype", Common.ReturnValueIfNull(Object.SourceType, ""));
|
||||||
|
dbDict.Add("sourcemd5", Object.SourceMd5);
|
||||||
|
dbDict.Add("sourcesha1", Object.SourceSHA1);
|
||||||
|
|
||||||
// set up game dictionary
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
dbDict = new Dictionary<string, object>();
|
if (sigDB.Rows.Count == 0)
|
||||||
if (flipNameAndDescription.Contains(Object.SourceType))
|
{
|
||||||
{
|
// entry not present, insert it
|
||||||
dbDict.Add("name", Common.ReturnValueIfNull(gameObject.Description, ""));
|
sql = "INSERT INTO Signatures_Sources (Name, Description, Category, Version, Author, Email, Homepage, Url, SourceType, SourceMD5, SourceSHA1) VALUES (@name, @description, @category, @version, @author, @email, @homepage, @uri, @sourcetype, @sourcemd5, @sourcesha1)";
|
||||||
dbDict.Add("description", Common.ReturnValueIfNull(gameObject.Name, ""));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
dbDict.Add("name", Common.ReturnValueIfNull(gameObject.Name, ""));
|
|
||||||
dbDict.Add("description", Common.ReturnValueIfNull(gameObject.Description, ""));
|
|
||||||
}
|
|
||||||
dbDict.Add("year", Common.ReturnValueIfNull(gameObject.Year, ""));
|
|
||||||
dbDict.Add("publisher", Common.ReturnValueIfNull(gameObject.Publisher, ""));
|
|
||||||
dbDict.Add("demo", (int)gameObject.Demo);
|
|
||||||
dbDict.Add("system", Common.ReturnValueIfNull(gameObject.System, ""));
|
|
||||||
dbDict.Add("platform", Common.ReturnValueIfNull(gameObject.System, ""));
|
|
||||||
dbDict.Add("systemvariant", Common.ReturnValueIfNull(gameObject.SystemVariant, ""));
|
|
||||||
dbDict.Add("video", Common.ReturnValueIfNull(gameObject.Video, ""));
|
|
||||||
dbDict.Add("country", Common.ReturnValueIfNull(gameObject.Country, ""));
|
|
||||||
dbDict.Add("language", Common.ReturnValueIfNull(gameObject.Language, ""));
|
|
||||||
dbDict.Add("copyright", Common.ReturnValueIfNull(gameObject.Copyright, ""));
|
|
||||||
|
|
||||||
// store platform
|
db.ExecuteCMD(sql, dbDict);
|
||||||
int gameSystem = 0;
|
|
||||||
if (gameObject.System != null)
|
|
||||||
{
|
|
||||||
sql = "SELECT Id FROM Signatures_Platforms WHERE Platform=@platform";
|
|
||||||
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
processGames = true;
|
||||||
if (sigDB.Rows.Count == 0)
|
}
|
||||||
|
|
||||||
|
if (processGames == true)
|
||||||
|
{
|
||||||
|
for (int x = 0; x < Object.Games.Count; ++x)
|
||||||
|
{
|
||||||
|
RomSignatureObject.Game gameObject = Object.Games[x];
|
||||||
|
|
||||||
|
// set up game dictionary
|
||||||
|
dbDict = new Dictionary<string, object>();
|
||||||
|
if (flipNameAndDescription.Contains(Object.SourceType))
|
||||||
{
|
{
|
||||||
// entry not present, insert it
|
dbDict.Add("name", Common.ReturnValueIfNull(gameObject.Description, ""));
|
||||||
sql = "INSERT INTO Signatures_Platforms (Platform) VALUES (@platform); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
dbDict.Add("description", Common.ReturnValueIfNull(gameObject.Name, ""));
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
|
|
||||||
gameSystem = Convert.ToInt32(sigDB.Rows[0][0]);
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
gameSystem = (int)sigDB.Rows[0][0];
|
dbDict.Add("name", Common.ReturnValueIfNull(gameObject.Name, ""));
|
||||||
|
dbDict.Add("description", Common.ReturnValueIfNull(gameObject.Description, ""));
|
||||||
}
|
}
|
||||||
}
|
dbDict.Add("year", Common.ReturnValueIfNull(gameObject.Year, ""));
|
||||||
dbDict.Add("systemid", gameSystem);
|
dbDict.Add("publisher", Common.ReturnValueIfNull(gameObject.Publisher, ""));
|
||||||
|
dbDict.Add("demo", (int)gameObject.Demo);
|
||||||
|
dbDict.Add("system", Common.ReturnValueIfNull(gameObject.System, ""));
|
||||||
|
dbDict.Add("platform", Common.ReturnValueIfNull(gameObject.System, ""));
|
||||||
|
dbDict.Add("systemvariant", Common.ReturnValueIfNull(gameObject.SystemVariant, ""));
|
||||||
|
dbDict.Add("video", Common.ReturnValueIfNull(gameObject.Video, ""));
|
||||||
|
dbDict.Add("country", Common.ReturnValueIfNull(gameObject.Country, ""));
|
||||||
|
dbDict.Add("language", Common.ReturnValueIfNull(gameObject.Language, ""));
|
||||||
|
dbDict.Add("copyright", Common.ReturnValueIfNull(gameObject.Copyright, ""));
|
||||||
|
|
||||||
// store publisher
|
// store platform
|
||||||
int gamePublisher = 0;
|
int gameSystem = 0;
|
||||||
if (gameObject.Publisher != null)
|
if (gameObject.System != null)
|
||||||
{
|
|
||||||
sql = "SELECT * FROM Signatures_Publishers WHERE Publisher=@publisher";
|
|
||||||
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
if (sigDB.Rows.Count == 0)
|
|
||||||
{
|
{
|
||||||
// entry not present, insert it
|
sql = "SELECT Id FROM Signatures_Platforms WHERE Platform=@platform";
|
||||||
sql = "INSERT INTO Signatures_Publishers (Publisher) VALUES (@publisher); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
gamePublisher = Convert.ToInt32(sigDB.Rows[0][0]);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
gamePublisher = (int)sigDB.Rows[0][0];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
dbDict.Add("publisherid", gamePublisher);
|
|
||||||
|
|
||||||
// store game
|
|
||||||
int gameId = 0;
|
|
||||||
sql = "SELECT * FROM Signatures_Games WHERE Name=@name AND Year=@year AND Publisherid=@publisher AND Systemid=@systemid AND Country=@country AND Language=@language";
|
|
||||||
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
if (sigDB.Rows.Count == 0)
|
|
||||||
{
|
|
||||||
// entry not present, insert it
|
|
||||||
sql = "INSERT INTO Signatures_Games " +
|
|
||||||
"(Name, Description, Year, PublisherId, Demo, SystemId, SystemVariant, Video, Country, Language, Copyright) VALUES " +
|
|
||||||
"(@name, @description, @year, @publisherid, @demo, @systemid, @systemvariant, @video, @country, @language, @copyright); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
|
||||||
|
|
||||||
gameId = Convert.ToInt32(sigDB.Rows[0][0]);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
gameId = (int)sigDB.Rows[0][0];
|
|
||||||
}
|
|
||||||
|
|
||||||
// store rom
|
|
||||||
foreach (RomSignatureObject.Game.Rom romObject in gameObject.Roms)
|
|
||||||
{
|
|
||||||
if (romObject.Md5 != null || romObject.Sha1 != null)
|
|
||||||
{
|
|
||||||
int romId = 0;
|
|
||||||
sql = "SELECT * FROM Signatures_Roms WHERE GameId=@gameid AND MD5=@md5";
|
|
||||||
dbDict = new Dictionary<string, object>();
|
|
||||||
dbDict.Add("gameid", gameId);
|
|
||||||
dbDict.Add("name", Common.ReturnValueIfNull(romObject.Name, ""));
|
|
||||||
dbDict.Add("size", Common.ReturnValueIfNull(romObject.Size, ""));
|
|
||||||
dbDict.Add("crc", Common.ReturnValueIfNull(romObject.Crc, "").ToString().ToLower());
|
|
||||||
dbDict.Add("md5", Common.ReturnValueIfNull(romObject.Md5, "").ToString().ToLower());
|
|
||||||
dbDict.Add("sha1", Common.ReturnValueIfNull(romObject.Sha1, "").ToString().ToLower());
|
|
||||||
dbDict.Add("developmentstatus", Common.ReturnValueIfNull(romObject.DevelopmentStatus, ""));
|
|
||||||
|
|
||||||
if (romObject.Attributes != null)
|
|
||||||
{
|
|
||||||
if (romObject.Attributes.Count > 0)
|
|
||||||
{
|
|
||||||
dbDict.Add("attributes", Newtonsoft.Json.JsonConvert.SerializeObject(romObject.Attributes));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
dbDict.Add("attributes", "[ ]");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
dbDict.Add("attributes", "[ ]");
|
|
||||||
}
|
|
||||||
dbDict.Add("romtype", (int)romObject.RomType);
|
|
||||||
dbDict.Add("romtypemedia", Common.ReturnValueIfNull(romObject.RomTypeMedia, ""));
|
|
||||||
dbDict.Add("medialabel", Common.ReturnValueIfNull(romObject.MediaLabel, ""));
|
|
||||||
dbDict.Add("metadatasource", romObject.SignatureSource);
|
|
||||||
dbDict.Add("ingestorversion", 2);
|
|
||||||
|
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
if (sigDB.Rows.Count == 0)
|
if (sigDB.Rows.Count == 0)
|
||||||
{
|
{
|
||||||
// entry not present, insert it
|
// entry not present, insert it
|
||||||
sql = "INSERT INTO Signatures_Roms (GameId, Name, Size, CRC, MD5, SHA1, DevelopmentStatus, Attributes, RomType, RomTypeMedia, MediaLabel, MetadataSource, IngestorVersion) VALUES (@gameid, @name, @size, @crc, @md5, @sha1, @developmentstatus, @attributes, @romtype, @romtypemedia, @medialabel, @metadatasource, @ingestorversion); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
sql = "INSERT INTO Signatures_Platforms (Platform) VALUES (@platform); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
||||||
sigDB = db.ExecuteCMD(sql, dbDict);
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
|
||||||
|
gameSystem = Convert.ToInt32(sigDB.Rows[0][0]);
|
||||||
romId = Convert.ToInt32(sigDB.Rows[0][0]);
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
romId = (int)sigDB.Rows[0][0];
|
gameSystem = (int)sigDB.Rows[0][0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
dbDict.Add("systemid", gameSystem);
|
||||||
|
|
||||||
|
// store publisher
|
||||||
|
int gamePublisher = 0;
|
||||||
|
if (gameObject.Publisher != null)
|
||||||
|
{
|
||||||
|
sql = "SELECT * FROM Signatures_Publishers WHERE Publisher=@publisher";
|
||||||
|
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
if (sigDB.Rows.Count == 0)
|
||||||
|
{
|
||||||
|
// entry not present, insert it
|
||||||
|
sql = "INSERT INTO Signatures_Publishers (Publisher) VALUES (@publisher); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
gamePublisher = Convert.ToInt32(sigDB.Rows[0][0]);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
gamePublisher = (int)sigDB.Rows[0][0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
dbDict.Add("publisherid", gamePublisher);
|
||||||
|
|
||||||
|
// store game
|
||||||
|
int gameId = 0;
|
||||||
|
sql = "SELECT * FROM Signatures_Games WHERE Name=@name AND Year=@year AND Publisherid=@publisher AND Systemid=@systemid AND Country=@country AND Language=@language";
|
||||||
|
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
if (sigDB.Rows.Count == 0)
|
||||||
|
{
|
||||||
|
// entry not present, insert it
|
||||||
|
sql = "INSERT INTO Signatures_Games " +
|
||||||
|
"(Name, Description, Year, PublisherId, Demo, SystemId, SystemVariant, Video, Country, Language, Copyright) VALUES " +
|
||||||
|
"(@name, @description, @year, @publisherid, @demo, @systemid, @systemvariant, @video, @country, @language, @copyright); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
|
||||||
|
gameId = Convert.ToInt32(sigDB.Rows[0][0]);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
gameId = (int)sigDB.Rows[0][0];
|
||||||
|
}
|
||||||
|
|
||||||
|
// store rom
|
||||||
|
foreach (RomSignatureObject.Game.Rom romObject in gameObject.Roms)
|
||||||
|
{
|
||||||
|
if (romObject.Md5 != null || romObject.Sha1 != null)
|
||||||
|
{
|
||||||
|
int romId = 0;
|
||||||
|
sql = "SELECT * FROM Signatures_Roms WHERE GameId=@gameid AND MD5=@md5";
|
||||||
|
dbDict = new Dictionary<string, object>();
|
||||||
|
dbDict.Add("gameid", gameId);
|
||||||
|
dbDict.Add("name", Common.ReturnValueIfNull(romObject.Name, ""));
|
||||||
|
dbDict.Add("size", Common.ReturnValueIfNull(romObject.Size, ""));
|
||||||
|
dbDict.Add("crc", Common.ReturnValueIfNull(romObject.Crc, "").ToString().ToLower());
|
||||||
|
dbDict.Add("md5", Common.ReturnValueIfNull(romObject.Md5, "").ToString().ToLower());
|
||||||
|
dbDict.Add("sha1", Common.ReturnValueIfNull(romObject.Sha1, "").ToString().ToLower());
|
||||||
|
dbDict.Add("developmentstatus", Common.ReturnValueIfNull(romObject.DevelopmentStatus, ""));
|
||||||
|
|
||||||
|
if (romObject.Attributes != null)
|
||||||
|
{
|
||||||
|
if (romObject.Attributes.Count > 0)
|
||||||
|
{
|
||||||
|
dbDict.Add("attributes", Newtonsoft.Json.JsonConvert.SerializeObject(romObject.Attributes));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dbDict.Add("attributes", "[ ]");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dbDict.Add("attributes", "[ ]");
|
||||||
|
}
|
||||||
|
dbDict.Add("romtype", (int)romObject.RomType);
|
||||||
|
dbDict.Add("romtypemedia", Common.ReturnValueIfNull(romObject.RomTypeMedia, ""));
|
||||||
|
dbDict.Add("medialabel", Common.ReturnValueIfNull(romObject.MediaLabel, ""));
|
||||||
|
dbDict.Add("metadatasource", romObject.SignatureSource);
|
||||||
|
dbDict.Add("ingestorversion", 2);
|
||||||
|
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
if (sigDB.Rows.Count == 0)
|
||||||
|
{
|
||||||
|
// entry not present, insert it
|
||||||
|
sql = "INSERT INTO Signatures_Roms (GameId, Name, Size, CRC, MD5, SHA1, DevelopmentStatus, Attributes, RomType, RomTypeMedia, MediaLabel, MetadataSource, IngestorVersion) VALUES (@gameid, @name, @size, @crc, @md5, @sha1, @developmentstatus, @attributes, @romtype, @romtypemedia, @medialabel, @metadatasource, @ingestorversion); SELECT CAST(LAST_INSERT_ID() AS SIGNED);";
|
||||||
|
sigDB = db.ExecuteCMD(sql, dbDict);
|
||||||
|
|
||||||
|
|
||||||
|
romId = Convert.ToInt32(sigDB.Rows[0][0]);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
romId = (int)sigDB.Rows[0][0];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
Logging.Log(Logging.LogType.Warning, "Signature Ingestor - XML", "Invalid import file: " + XMLFile, ex);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
else
|
||||||
{
|
{
|
||||||
Logging.Log(Logging.LogType.Warning, "Signature Ingestor - XML", "Invalid import file: " + XMLFile, ex);
|
Logging.Log(Logging.LogType.Debug, "Signature Ingestor - XML", "Rejecting already imported file: " + XMLFile);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
Logging.Log(Logging.LogType.Debug, "Signature Ingestor - XML", "Rejecting already imported file: " + XMLFile);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
ClearStatus();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@@ -18,7 +18,7 @@ namespace gaseous_server.Controllers
|
|||||||
[ApiVersion("1.1")]
|
[ApiVersion("1.1")]
|
||||||
[Authorize]
|
[Authorize]
|
||||||
[ApiController]
|
[ApiController]
|
||||||
public class FilterController : ControllerBase
|
public class FilterController : Controller
|
||||||
{
|
{
|
||||||
private readonly UserManager<ApplicationUser> _userManager;
|
private readonly UserManager<ApplicationUser> _userManager;
|
||||||
private readonly SignInManager<ApplicationUser> _signInManager;
|
private readonly SignInManager<ApplicationUser> _signInManager;
|
||||||
|
@@ -22,7 +22,7 @@ namespace gaseous_server.Controllers
|
|||||||
[ApiVersion("1.1")]
|
[ApiVersion("1.1")]
|
||||||
[Authorize]
|
[Authorize]
|
||||||
[ApiController]
|
[ApiController]
|
||||||
public class GamesController : ControllerBase
|
public class GamesController : Controller
|
||||||
{
|
{
|
||||||
[MapToApiVersion("1.0")]
|
[MapToApiVersion("1.0")]
|
||||||
[HttpGet]
|
[HttpGet]
|
||||||
|
@@ -22,7 +22,7 @@ namespace gaseous_server.Controllers
|
|||||||
[ApiVersion("1.1")]
|
[ApiVersion("1.1")]
|
||||||
[Authorize]
|
[Authorize]
|
||||||
[ApiController]
|
[ApiController]
|
||||||
public class RomsController : ControllerBase
|
public class RomsController : Controller
|
||||||
{
|
{
|
||||||
[MapToApiVersion("1.0")]
|
[MapToApiVersion("1.0")]
|
||||||
[MapToApiVersion("1.1")]
|
[MapToApiVersion("1.1")]
|
||||||
|
@@ -3,6 +3,7 @@ using System.Collections.Generic;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using gaseous_server.Classes;
|
using gaseous_server.Classes;
|
||||||
|
using gaseous_server.Classes.Metadata;
|
||||||
using IGDB;
|
using IGDB;
|
||||||
using IGDB.Models;
|
using IGDB.Models;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
@@ -19,12 +20,6 @@ namespace gaseous_server.Controllers
|
|||||||
[Authorize]
|
[Authorize]
|
||||||
public class SearchController : Controller
|
public class SearchController : Controller
|
||||||
{
|
{
|
||||||
private static IGDBClient igdb = new IGDBClient(
|
|
||||||
// Found in Twitch Developer portal for your app
|
|
||||||
Config.IGDB.ClientId,
|
|
||||||
Config.IGDB.Secret
|
|
||||||
);
|
|
||||||
|
|
||||||
[MapToApiVersion("1.0")]
|
[MapToApiVersion("1.0")]
|
||||||
[MapToApiVersion("1.1")]
|
[MapToApiVersion("1.1")]
|
||||||
[HttpGet]
|
[HttpGet]
|
||||||
@@ -39,11 +34,12 @@ namespace gaseous_server.Controllers
|
|||||||
private static async Task<List<Platform>> _SearchForPlatform(string SearchString)
|
private static async Task<List<Platform>> _SearchForPlatform(string SearchString)
|
||||||
{
|
{
|
||||||
string searchBody = "";
|
string searchBody = "";
|
||||||
searchBody += "fields abbreviation,alternative_name,category,checksum,created_at,generation,name,platform_family,platform_logo,slug,summary,updated_at,url,versions,websites; ";
|
string searchFields = "fields abbreviation,alternative_name,category,checksum,created_at,generation,name,platform_family,platform_logo,slug,summary,updated_at,url,versions,websites; ";
|
||||||
searchBody += "where name ~ *\"" + SearchString + "\"*;";
|
searchBody += "where name ~ *\"" + SearchString + "\"*;";
|
||||||
|
|
||||||
// get Platform metadata
|
// get Platform metadata
|
||||||
var results = await igdb.QueryAsync<Platform>(IGDBClient.Endpoints.Platforms, query: searchBody);
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Platform>(IGDBClient.Endpoints.Platforms, searchFields, searchBody);
|
||||||
|
|
||||||
return results.ToList();
|
return results.ToList();
|
||||||
}
|
}
|
||||||
@@ -62,12 +58,13 @@ namespace gaseous_server.Controllers
|
|||||||
private static async Task<List<Game>> _SearchForGame(long PlatformId, string SearchString)
|
private static async Task<List<Game>> _SearchForGame(long PlatformId, string SearchString)
|
||||||
{
|
{
|
||||||
string searchBody = "";
|
string searchBody = "";
|
||||||
searchBody += "fields cover.*,first_release_date,name,platforms,slug; ";
|
string searchFields = "fields cover.*,first_release_date,name,platforms,slug; ";
|
||||||
searchBody += "search \"" + SearchString + "\";";
|
searchBody += "search \"" + SearchString + "\";";
|
||||||
searchBody += "where platforms = (" + PlatformId + ");";
|
searchBody += "where platforms = (" + PlatformId + ");";
|
||||||
|
|
||||||
// get Platform metadata
|
// get Platform metadata
|
||||||
var results = await igdb.QueryAsync<Game>(IGDBClient.Endpoints.Games, query: searchBody);
|
Communications comms = new Communications();
|
||||||
|
var results = await comms.APIComm<Game>(IGDBClient.Endpoints.Games, searchFields, searchBody);
|
||||||
|
|
||||||
return results.ToList();
|
return results.ToList();
|
||||||
}
|
}
|
||||||
|
@@ -18,7 +18,7 @@ namespace gaseous_server.Controllers
|
|||||||
[ApiVersion("1.0")]
|
[ApiVersion("1.0")]
|
||||||
[ApiVersion("1.1")]
|
[ApiVersion("1.1")]
|
||||||
[Authorize]
|
[Authorize]
|
||||||
public class SignaturesController : ControllerBase
|
public class SignaturesController : Controller
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Get the current signature counts from the database
|
/// Get the current signature counts from the database
|
||||||
|
@@ -450,26 +450,14 @@ namespace gaseous_server.Controllers.v1_1
|
|||||||
|
|
||||||
// compile data for return
|
// compile data for return
|
||||||
int pageOffset = pageSize * (pageNumber - 1);
|
int pageOffset = pageSize * (pageNumber - 1);
|
||||||
for (int i = 0; i < dbResponse.Rows.Count; i++)
|
for (int i = pageOffset; i < dbResponse.Rows.Count; i++)
|
||||||
{
|
{
|
||||||
DataRow dr = dbResponse.Rows[i];
|
if (i >= (pageOffset + pageSize))
|
||||||
|
|
||||||
bool includeGame = false;
|
|
||||||
|
|
||||||
if (pageSize == 0)
|
|
||||||
{
|
{
|
||||||
// page size is full size include all
|
break;
|
||||||
includeGame = true;
|
|
||||||
}
|
|
||||||
else if (i >= pageOffset && i < (pageOffset + pageSize))
|
|
||||||
{
|
|
||||||
includeGame = true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (includeGame == true)
|
RetVal.Add(Classes.Metadata.Games.GetGame(dbResponse.Rows[i]));
|
||||||
{
|
|
||||||
RetVal.Add(Classes.Metadata.Games.GetGame(dr));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
GameReturnPackage gameReturn = new GameReturnPackage(RecordCount, RetVal);
|
GameReturnPackage gameReturn = new GameReturnPackage(RecordCount, RetVal);
|
||||||
|
@@ -1,4 +1,6 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.ComponentModel.Design.Serialization;
|
||||||
|
using System.Data;
|
||||||
using gaseous_server.Classes;
|
using gaseous_server.Classes;
|
||||||
|
|
||||||
namespace gaseous_server
|
namespace gaseous_server
|
||||||
@@ -13,7 +15,7 @@ namespace gaseous_server
|
|||||||
{
|
{
|
||||||
_ItemType = ItemType;
|
_ItemType = ItemType;
|
||||||
_ItemState = QueueItemState.NeverStarted;
|
_ItemState = QueueItemState.NeverStarted;
|
||||||
_LastRunTime = DateTime.Parse(Config.ReadSetting("LastRun_" + _ItemType.ToString(), DateTime.UtcNow.ToString("yyyy-MM-ddThh:mm:ssZ")));
|
_LastRunTime = DateTime.Parse(Config.ReadSetting("LastRun_" + _ItemType.ToString(), DateTime.UtcNow.ToString("yyyy-MM-ddThh:mm:ssZ"))).AddMinutes(-5);
|
||||||
_Interval = ExecutionInterval;
|
_Interval = ExecutionInterval;
|
||||||
_AllowManualStart = AllowManualStart;
|
_AllowManualStart = AllowManualStart;
|
||||||
_RemoveWhenStopped = RemoveWhenStopped;
|
_RemoveWhenStopped = RemoveWhenStopped;
|
||||||
@@ -23,7 +25,7 @@ namespace gaseous_server
|
|||||||
{
|
{
|
||||||
_ItemType = ItemType;
|
_ItemType = ItemType;
|
||||||
_ItemState = QueueItemState.NeverStarted;
|
_ItemState = QueueItemState.NeverStarted;
|
||||||
_LastRunTime = DateTime.Parse(Config.ReadSetting("LastRun_" + _ItemType.ToString(), DateTime.UtcNow.ToString("yyyy-MM-ddThh:mm:ssZ")));
|
_LastRunTime = DateTime.Parse(Config.ReadSetting("LastRun_" + _ItemType.ToString(), DateTime.UtcNow.ToString("yyyy-MM-ddThh:mm:ssZ"))).AddMinutes(-5);
|
||||||
_Interval = ExecutionInterval;
|
_Interval = ExecutionInterval;
|
||||||
_AllowManualStart = AllowManualStart;
|
_AllowManualStart = AllowManualStart;
|
||||||
_RemoveWhenStopped = RemoveWhenStopped;
|
_RemoveWhenStopped = RemoveWhenStopped;
|
||||||
@@ -33,6 +35,7 @@ namespace gaseous_server
|
|||||||
private QueueItemType _ItemType = QueueItemType.NotConfigured;
|
private QueueItemType _ItemType = QueueItemType.NotConfigured;
|
||||||
private QueueItemState _ItemState = QueueItemState.NeverStarted;
|
private QueueItemState _ItemState = QueueItemState.NeverStarted;
|
||||||
private DateTime _LastRunTime = DateTime.UtcNow;
|
private DateTime _LastRunTime = DateTime.UtcNow;
|
||||||
|
private double _LastRunDuration = 0;
|
||||||
private DateTime _LastFinishTime
|
private DateTime _LastFinishTime
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
@@ -55,13 +58,16 @@ namespace gaseous_server
|
|||||||
private bool _AllowManualStart = true;
|
private bool _AllowManualStart = true;
|
||||||
private bool _RemoveWhenStopped = false;
|
private bool _RemoveWhenStopped = false;
|
||||||
private bool _IsBlocked = false;
|
private bool _IsBlocked = false;
|
||||||
|
private string _CorrelationId = "";
|
||||||
private List<QueueItemType> _Blocks = new List<QueueItemType>();
|
private List<QueueItemType> _Blocks = new List<QueueItemType>();
|
||||||
|
|
||||||
public QueueItemType ItemType => _ItemType;
|
public QueueItemType ItemType => _ItemType;
|
||||||
public QueueItemState ItemState => _ItemState;
|
public QueueItemState ItemState => _ItemState;
|
||||||
public DateTime LastRunTime => _LastRunTime;
|
public DateTime LastRunTime => _LastRunTime;
|
||||||
public DateTime LastFinishTime => _LastFinishTime;
|
public DateTime LastFinishTime => _LastFinishTime;
|
||||||
public DateTime NextRunTime {
|
public double LastRunDuration => _LastRunDuration;
|
||||||
|
public DateTime NextRunTime
|
||||||
|
{
|
||||||
get
|
get
|
||||||
{
|
{
|
||||||
return LastRunTime.AddMinutes(Interval);
|
return LastRunTime.AddMinutes(Interval);
|
||||||
@@ -85,6 +91,9 @@ namespace gaseous_server
|
|||||||
public bool RemoveWhenStopped => _RemoveWhenStopped;
|
public bool RemoveWhenStopped => _RemoveWhenStopped;
|
||||||
public bool IsBlocked => _IsBlocked;
|
public bool IsBlocked => _IsBlocked;
|
||||||
public object? Options { get; set; } = null;
|
public object? Options { get; set; } = null;
|
||||||
|
public string CurrentState { get; set; } = "";
|
||||||
|
public string CurrentStateProgress { get; set; } = "";
|
||||||
|
public string CorrelationId => _CorrelationId;
|
||||||
public List<QueueItemType> Blocks => _Blocks;
|
public List<QueueItemType> Blocks => _Blocks;
|
||||||
|
|
||||||
public void Execute()
|
public void Execute()
|
||||||
@@ -99,7 +108,14 @@ namespace gaseous_server
|
|||||||
_LastResult = "";
|
_LastResult = "";
|
||||||
_LastError = null;
|
_LastError = null;
|
||||||
|
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Executing " + _ItemType);
|
// set the correlation id
|
||||||
|
Guid correlationId = Guid.NewGuid();
|
||||||
|
_CorrelationId = correlationId.ToString();
|
||||||
|
CallContext.SetData("CorrelationId", correlationId);
|
||||||
|
CallContext.SetData("CallingProcess", _ItemType.ToString());
|
||||||
|
|
||||||
|
// log the start
|
||||||
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Executing " + _ItemType + " with correlation id " + _CorrelationId);
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -107,7 +123,10 @@ namespace gaseous_server
|
|||||||
{
|
{
|
||||||
case QueueItemType.SignatureIngestor:
|
case QueueItemType.SignatureIngestor:
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Signature Ingestor");
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Signature Ingestor");
|
||||||
SignatureIngestors.XML.XMLIngestor tIngest = new SignatureIngestors.XML.XMLIngestor();
|
SignatureIngestors.XML.XMLIngestor tIngest = new SignatureIngestors.XML.XMLIngestor
|
||||||
|
{
|
||||||
|
CallingQueueItem = this
|
||||||
|
};
|
||||||
|
|
||||||
Logging.Log(Logging.LogType.Debug, "Signature Import", "Processing TOSEC files");
|
Logging.Log(Logging.LogType.Debug, "Signature Import", "Processing TOSEC files");
|
||||||
tIngest.Import(Path.Combine(Config.LibraryConfiguration.LibrarySignatureImportDirectory, "TOSEC"), gaseous_signature_parser.parser.SignatureParser.TOSEC);
|
tIngest.Import(Path.Combine(Config.LibraryConfiguration.LibrarySignatureImportDirectory, "TOSEC"), gaseous_signature_parser.parser.SignatureParser.TOSEC);
|
||||||
@@ -124,7 +143,10 @@ namespace gaseous_server
|
|||||||
|
|
||||||
case QueueItemType.TitleIngestor:
|
case QueueItemType.TitleIngestor:
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Title Ingestor");
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Title Ingestor");
|
||||||
Classes.ImportGames importGames = new Classes.ImportGames(Config.LibraryConfiguration.LibraryImportDirectory);
|
Classes.ImportGames importGames = new Classes.ImportGames(Config.LibraryConfiguration.LibraryImportDirectory)
|
||||||
|
{
|
||||||
|
CallingQueueItem = this
|
||||||
|
};
|
||||||
|
|
||||||
Classes.ImportGame.DeleteOrphanedDirectories(Config.LibraryConfiguration.LibraryImportDirectory);
|
Classes.ImportGame.DeleteOrphanedDirectories(Config.LibraryConfiguration.LibraryImportDirectory);
|
||||||
|
|
||||||
@@ -134,7 +156,11 @@ namespace gaseous_server
|
|||||||
|
|
||||||
case QueueItemType.MetadataRefresh:
|
case QueueItemType.MetadataRefresh:
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Metadata Refresher");
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Metadata Refresher");
|
||||||
Classes.MetadataManagement.RefreshMetadata(_ForceExecute);
|
Classes.MetadataManagement metadataManagement = new MetadataManagement
|
||||||
|
{
|
||||||
|
CallingQueueItem = this
|
||||||
|
};
|
||||||
|
metadataManagement.RefreshMetadata(_ForceExecute);
|
||||||
|
|
||||||
_SaveLastRunTime = true;
|
_SaveLastRunTime = true;
|
||||||
|
|
||||||
@@ -150,7 +176,11 @@ namespace gaseous_server
|
|||||||
|
|
||||||
case QueueItemType.LibraryScan:
|
case QueueItemType.LibraryScan:
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Library Scanner");
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Library Scanner");
|
||||||
Classes.ImportGame.LibraryScan();
|
Classes.ImportGame import = new ImportGame
|
||||||
|
{
|
||||||
|
CallingQueueItem = this
|
||||||
|
};
|
||||||
|
import.LibraryScan();
|
||||||
|
|
||||||
_SaveLastRunTime = true;
|
_SaveLastRunTime = true;
|
||||||
|
|
||||||
@@ -158,7 +188,11 @@ namespace gaseous_server
|
|||||||
|
|
||||||
case QueueItemType.Rematcher:
|
case QueueItemType.Rematcher:
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Rematch");
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Rematch");
|
||||||
Classes.ImportGame.Rematcher(_ForceExecute);
|
Classes.ImportGame importRematch = new ImportGame
|
||||||
|
{
|
||||||
|
CallingQueueItem = this
|
||||||
|
};
|
||||||
|
importRematch.Rematcher(_ForceExecute);
|
||||||
|
|
||||||
_SaveLastRunTime = true;
|
_SaveLastRunTime = true;
|
||||||
|
|
||||||
@@ -181,7 +215,10 @@ namespace gaseous_server
|
|||||||
|
|
||||||
case QueueItemType.Maintainer:
|
case QueueItemType.Maintainer:
|
||||||
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Maintenance");
|
Logging.Log(Logging.LogType.Debug, "Timered Event", "Starting Maintenance");
|
||||||
Classes.Maintenance.RunMaintenance();
|
Classes.Maintenance maintenance = new Maintenance{
|
||||||
|
CallingQueueItem = this
|
||||||
|
};
|
||||||
|
maintenance.RunMaintenance();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -196,8 +233,9 @@ namespace gaseous_server
|
|||||||
_ForceExecute = false;
|
_ForceExecute = false;
|
||||||
_ItemState = QueueItemState.Stopped;
|
_ItemState = QueueItemState.Stopped;
|
||||||
_LastFinishTime = DateTime.UtcNow;
|
_LastFinishTime = DateTime.UtcNow;
|
||||||
|
_LastRunDuration = Math.Round((DateTime.UtcNow - _LastRunTime).TotalSeconds, 2);
|
||||||
|
|
||||||
Logging.Log(Logging.LogType.Information, "Timered Event", "Total " + _ItemType + " run time = " + (DateTime.UtcNow - _LastRunTime).TotalSeconds);
|
Logging.Log(Logging.LogType.Information, "Timered Event", "Total " + _ItemType + " run time = " + _LastRunDuration);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -211,6 +249,66 @@ namespace gaseous_server
|
|||||||
{
|
{
|
||||||
_IsBlocked = BlockState;
|
_IsBlocked = BlockState;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public HasErrorsItem HasErrors
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return new HasErrorsItem(_CorrelationId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class HasErrorsItem
|
||||||
|
{
|
||||||
|
public HasErrorsItem(string? CorrelationId)
|
||||||
|
{
|
||||||
|
if (CorrelationId != null)
|
||||||
|
{
|
||||||
|
if (CorrelationId.Length > 0)
|
||||||
|
{
|
||||||
|
Database db = new Database(Database.databaseType.MySql, Config.DatabaseConfiguration.ConnectionString);
|
||||||
|
string sql = "SELECT EventType, COUNT(EventType) AS EventTypes FROM gaseous.ServerLogs WHERE CorrelationId = @correlationid GROUP BY EventType ORDER BY EventType DESC LIMIT 1;";
|
||||||
|
Dictionary<string, object> dbDict = new Dictionary<string, object>();
|
||||||
|
dbDict.Add("correlationid", CorrelationId);
|
||||||
|
|
||||||
|
DataTable data = db.ExecuteCMD(sql, dbDict);
|
||||||
|
|
||||||
|
if (data.Rows.Count == 0)
|
||||||
|
{
|
||||||
|
ErrorType = null;
|
||||||
|
ErrorCount = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Logging.LogType errorType = (Logging.LogType)data.Rows[0]["EventType"];
|
||||||
|
if (errorType != Logging.LogType.Information)
|
||||||
|
{
|
||||||
|
ErrorType = errorType;
|
||||||
|
ErrorCount = (int)(long)data.Rows[0]["EventTypes"];
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ErrorType = null;
|
||||||
|
ErrorCount = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ErrorType = null;
|
||||||
|
ErrorCount = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ErrorType = null;
|
||||||
|
ErrorCount = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public Logging.LogType? ErrorType { get; set; }
|
||||||
|
public int ErrorCount { get; set; }
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public enum QueueItemType
|
public enum QueueItemType
|
||||||
|
@@ -49,6 +49,9 @@ Config.InitSettings();
|
|||||||
// write updated settings back to the config file
|
// write updated settings back to the config file
|
||||||
Config.UpdateConfig();
|
Config.UpdateConfig();
|
||||||
|
|
||||||
|
// set api metadata source from config
|
||||||
|
Communications.MetadataSource = Config.MetadataConfiguration.Source;
|
||||||
|
|
||||||
// set initial values
|
// set initial values
|
||||||
Guid APIKey = Guid.NewGuid();
|
Guid APIKey = Guid.NewGuid();
|
||||||
if (Config.ReadSetting("API Key", "Test API Key") == "Test API Key")
|
if (Config.ReadSetting("API Key", "Test API Key") == "Test API Key")
|
||||||
@@ -292,29 +295,22 @@ using (var scope = app.Services.CreateScope())
|
|||||||
await roleManager.CreateAsync(applicationRole, CancellationToken.None);
|
await roleManager.CreateAsync(applicationRole, CancellationToken.None);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// // set up administrator account
|
|
||||||
// var userManager = scope.ServiceProvider.GetRequiredService<UserStore>();
|
|
||||||
// if (await userManager.FindByNameAsync("admin@localhost", CancellationToken.None) == null)
|
|
||||||
// {
|
|
||||||
// ApplicationUser adminUser = new ApplicationUser{
|
|
||||||
// Id = Guid.NewGuid().ToString(),
|
|
||||||
// Email = "admin@localhost",
|
|
||||||
// NormalizedEmail = "ADMIN@LOCALHOST",
|
|
||||||
// EmailConfirmed = true,
|
|
||||||
// UserName = "administrator",
|
|
||||||
// NormalizedUserName = "ADMINISTRATOR"
|
|
||||||
// };
|
|
||||||
|
|
||||||
// //set user password
|
|
||||||
// PasswordHasher<ApplicationUser> ph = new PasswordHasher<ApplicationUser>();
|
|
||||||
// adminUser.PasswordHash = ph.HashPassword(adminUser, "letmein");
|
|
||||||
|
|
||||||
// await userManager.CreateAsync(adminUser, CancellationToken.None);
|
|
||||||
// await userManager.AddToRoleAsync(adminUser, "Admin", CancellationToken.None);
|
|
||||||
// }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
app.Use(async (context, next) =>
|
||||||
|
{
|
||||||
|
// set the correlation id
|
||||||
|
string correlationId = Guid.NewGuid().ToString();
|
||||||
|
CallContext.SetData("CorrelationId", correlationId);
|
||||||
|
CallContext.SetData("CallingProcess", context.Request.Method + ": " + context.Request.Path);
|
||||||
|
|
||||||
|
context.Response.Headers.Add("x-correlation-id", correlationId.ToString());
|
||||||
|
await next();
|
||||||
|
});
|
||||||
|
|
||||||
app.UseAuthorization();
|
app.UseAuthorization();
|
||||||
|
|
||||||
app.UseDefaultFiles();
|
app.UseDefaultFiles();
|
||||||
|
26
gaseous-server/Support/Database/MySQL/gaseous-1008.sql
Normal file
26
gaseous-server/Support/Database/MySQL/gaseous-1008.sql
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
ALTER TABLE `ClassificationMap`
|
||||||
|
ADD INDEX `idx_RatingId` (`RatingId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `Relation_Game_AgeRatings`
|
||||||
|
ADD INDEX `idx_SecondaryColumn` (`AgeRatingsId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `Relation_Game_GameModes`
|
||||||
|
ADD INDEX `idx_SecondaryColumn` (`GameModesId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `Relation_Game_Genres`
|
||||||
|
ADD INDEX `idx_SecondaryColumn` (`GenresId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `Relation_Game_Platforms`
|
||||||
|
ADD INDEX `idx_SecondaryColumn` (`PlatformsId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `Relation_Game_PlayerPerspectives`
|
||||||
|
ADD INDEX `idx_SecondaryColumn` (`PlayerPerspectivesId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `Relation_Game_Themes`
|
||||||
|
ADD INDEX `idx_SecondaryColumn` (`ThemesId` ASC) VISIBLE;
|
||||||
|
|
||||||
|
ALTER TABLE `ServerLogs`
|
||||||
|
ADD COLUMN `CorrelationId` VARCHAR(45) NULL AFTER `Exception`,
|
||||||
|
ADD COLUMN `CallingProcess` VARCHAR(255) NULL AFTER `CorrelationId`,
|
||||||
|
ADD INDEX `idx_CorrelationId` (`CorrelationId` ASC) VISIBLE,
|
||||||
|
ADD INDEX `idx_CallingProcess` (`CallingProcess` ASC) VISIBLE;
|
@@ -48,6 +48,7 @@
|
|||||||
<None Remove="Support\Database\MySQL\gaseous-1005.sql" />
|
<None Remove="Support\Database\MySQL\gaseous-1005.sql" />
|
||||||
<None Remove="Support\Database\MySQL\gaseous-1006.sql" />
|
<None Remove="Support\Database\MySQL\gaseous-1006.sql" />
|
||||||
<None Remove="Support\Database\MySQL\gaseous-1007.sql" />
|
<None Remove="Support\Database\MySQL\gaseous-1007.sql" />
|
||||||
|
<None Remove="Support\Database\MySQL\gaseous-1008.sql" />
|
||||||
<None Remove="Classes\Metadata\" />
|
<None Remove="Classes\Metadata\" />
|
||||||
<None Remove="Assets\" />
|
<None Remove="Assets\" />
|
||||||
<None Remove="Assets\Ratings\" />
|
<None Remove="Assets\Ratings\" />
|
||||||
@@ -178,5 +179,6 @@
|
|||||||
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1005.sql" />
|
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1005.sql" />
|
||||||
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1006.sql" />
|
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1006.sql" />
|
||||||
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1007.sql" />
|
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1007.sql" />
|
||||||
|
<EmbeddedResource Include="Support\Database\MySQL\gaseous-1008.sql" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
|
@@ -3,7 +3,7 @@
|
|||||||
<head>
|
<head>
|
||||||
<meta charset="utf-8" />
|
<meta charset="utf-8" />
|
||||||
<script src="/api/v1.1/System/VersionFile"></script>
|
<script src="/api/v1.1/System/VersionFile"></script>
|
||||||
<link type="text/css" rel="stylesheet" dat-href="/styles/style.css" />
|
<link type="text/css" rel="stylesheet" href="/styles/style.css" dat-href="/styles/style.css" />
|
||||||
<script src="/scripts/jquery-3.6.0.min.js"></script>
|
<script src="/scripts/jquery-3.6.0.min.js"></script>
|
||||||
<script src="/scripts/moment-with-locales.min.js"></script>
|
<script src="/scripts/moment-with-locales.min.js"></script>
|
||||||
<link href="/styles/select2.min.css" rel="stylesheet" />
|
<link href="/styles/select2.min.css" rel="stylesheet" />
|
||||||
|
@@ -47,6 +47,10 @@
|
|||||||
SelectTab(selectedTab);
|
SelectTab(selectedTab);
|
||||||
|
|
||||||
function SelectTab(TabName) {
|
function SelectTab(TabName) {
|
||||||
|
if (selectedTab != TabName) {
|
||||||
|
window.location.href = '/index.html?page=settings&sub=' + TabName;
|
||||||
|
}
|
||||||
|
|
||||||
var tocs = document.getElementsByName('properties_toc_item');
|
var tocs = document.getElementsByName('properties_toc_item');
|
||||||
for (var i = 0; i < tocs.length; i++) {
|
for (var i = 0; i < tocs.length; i++) {
|
||||||
if ((tocs[i].id) == ("properties_toc_" + TabName)) {
|
if ((tocs[i].id) == ("properties_toc_" + TabName)) {
|
||||||
|
@@ -5,10 +5,7 @@
|
|||||||
<table style="width: 960px; max-width: 960px;" cellspacing="0">
|
<table style="width: 960px; max-width: 960px;" cellspacing="0">
|
||||||
<tr>
|
<tr>
|
||||||
<td>
|
<td>
|
||||||
<input type="datetime-local" id="logs_startdate" />
|
<input type="datetime-local" id="logs_startdate" style="width: 30%;" /> <input type="datetime-local" id="logs_enddate" style="width: 30%;" />
|
||||||
</td>
|
|
||||||
<td>
|
|
||||||
<input type="datetime-local" id="logs_enddate" />
|
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<input type="checkbox" id="logs_type_info"><label for="logs_type_info">Information</label>
|
<input type="checkbox" id="logs_type_info"><label for="logs_type_info">Information</label>
|
||||||
@@ -19,10 +16,17 @@
|
|||||||
<td>
|
<td>
|
||||||
<input type="checkbox" id="logs_type_critical"><label for="logs_type_critical">Critical</label>
|
<input type="checkbox" id="logs_type_critical"><label for="logs_type_critical">Critical</label>
|
||||||
</td>
|
</td>
|
||||||
<td>
|
</tr>
|
||||||
<input type="text" id="logs_textsearch" placeholder="Search" />
|
<tr>
|
||||||
|
<td colspan="1">
|
||||||
|
<input type="text" id="logs_textsearch" placeholder="Search" style="width: 75%;" />
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td colspan="3">
|
||||||
|
<input type="text" id="logs_correlationid" placeholder="Correlation Id" style="width: 75%;" />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td colspan="4" style="text-align: right;">
|
||||||
<button onclick="loadLogs();">Search</button>
|
<button onclick="loadLogs();">Search</button>
|
||||||
<button onclick="resetFilters();">Reset</button>
|
<button onclick="resetFilters();">Reset</button>
|
||||||
</td>
|
</td>
|
||||||
@@ -43,6 +47,13 @@
|
|||||||
var currentPage = 1;
|
var currentPage = 1;
|
||||||
var searchModel = {};
|
var searchModel = {};
|
||||||
|
|
||||||
|
var correlationIdParam = getQueryString('correlationid', 'string');
|
||||||
|
if (correlationIdParam) {
|
||||||
|
if (correlationIdParam.length > 0) {
|
||||||
|
document.getElementById('logs_correlationid').value = correlationIdParam;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
function resetFilters() {
|
function resetFilters() {
|
||||||
document.getElementById('logs_startdate').value = '';
|
document.getElementById('logs_startdate').value = '';
|
||||||
document.getElementById('logs_enddate').value = '';
|
document.getElementById('logs_enddate').value = '';
|
||||||
@@ -50,6 +61,7 @@
|
|||||||
document.getElementById('logs_type_warning').checked = false;
|
document.getElementById('logs_type_warning').checked = false;
|
||||||
document.getElementById('logs_type_critical').checked = false;
|
document.getElementById('logs_type_critical').checked = false;
|
||||||
document.getElementById('logs_textsearch').value = '';
|
document.getElementById('logs_textsearch').value = '';
|
||||||
|
document.getElementById('logs_correlationid').value = '';
|
||||||
|
|
||||||
loadLogs();
|
loadLogs();
|
||||||
}
|
}
|
||||||
@@ -81,6 +93,9 @@
|
|||||||
var searchText = null;
|
var searchText = null;
|
||||||
var searchTextObj = document.getElementById('logs_textsearch');
|
var searchTextObj = document.getElementById('logs_textsearch');
|
||||||
if (searchTextObj.value != null) { searchText = searchTextObj.value; }
|
if (searchTextObj.value != null) { searchText = searchTextObj.value; }
|
||||||
|
var correlationId = null;
|
||||||
|
var correlationIdTextObj = document.getElementById('logs_correlationid');
|
||||||
|
if (correlationIdTextObj.value != null) { correlationId = correlationIdTextObj.value; }
|
||||||
|
|
||||||
model = {
|
model = {
|
||||||
"StartIndex": StartIndex,
|
"StartIndex": StartIndex,
|
||||||
@@ -89,7 +104,8 @@
|
|||||||
"Status": statusList,
|
"Status": statusList,
|
||||||
"StartDateTime": startDate,
|
"StartDateTime": startDate,
|
||||||
"EndDateTime": endDate,
|
"EndDateTime": endDate,
|
||||||
"SearchText": searchText
|
"SearchText": searchText,
|
||||||
|
"CorrelationId": correlationId
|
||||||
}
|
}
|
||||||
searchModel = model;
|
searchModel = model;
|
||||||
}
|
}
|
||||||
@@ -131,7 +147,7 @@
|
|||||||
result[i].message
|
result[i].message
|
||||||
];
|
];
|
||||||
|
|
||||||
newTable.appendChild(createTableRow(false, newRow, 'romrow logs_table_row_' + result[i].eventType, 'romcell logs_table_cell'));
|
newTable.appendChild(createTableRow(false, newRow, 'logs_table_row_' + result[i].eventType, 'romcell logs_table_cell'));
|
||||||
|
|
||||||
if (result[i].exceptionValue) {
|
if (result[i].exceptionValue) {
|
||||||
var exceptionString = "<h3>Exception</h3><pre class='logs_table_exception' style='width: 795px; word-wrap: break-word; overflow-wrap: break-word; overflow-y: scroll;'>" + syntaxHighlight(JSON.stringify(result[i].exceptionValue, null, 2)).replace(/\\n/g, "<br /> ") + "</pre>";
|
var exceptionString = "<h3>Exception</h3><pre class='logs_table_exception' style='width: 795px; word-wrap: break-word; overflow-wrap: break-word; overflow-y: scroll;'>" + syntaxHighlight(JSON.stringify(result[i].exceptionValue, null, 2)).replace(/\\n/g, "<br /> ") + "</pre>";
|
||||||
|
@@ -25,66 +25,90 @@
|
|||||||
<h3>Signatures</h3>
|
<h3>Signatures</h3>
|
||||||
<div id="system_signatures"></div>
|
<div id="system_signatures"></div>
|
||||||
|
|
||||||
<script type="text/javascript">function SystemLoadStatus() {
|
<script type="text/javascript">
|
||||||
|
function SystemLoadStatus() {
|
||||||
ajaxCall('/api/v1.1/BackgroundTasks', 'GET', function (result) {
|
ajaxCall('/api/v1.1/BackgroundTasks', 'GET', function (result) {
|
||||||
var newTable = document.createElement('table');
|
var newTable = document.createElement('table');
|
||||||
newTable.className = 'romtable';
|
newTable.className = 'romtable';
|
||||||
newTable.setAttribute('cellspacing', 0);
|
newTable.setAttribute('cellspacing', 0);
|
||||||
newTable.appendChild(createTableRow(true, ['Task', 'Status', 'Interval', 'Last Run Time', 'Next Run Time', '']));
|
newTable.appendChild(createTableRow(true, ['Task', 'Status', 'Interval<br/>(minutes)', 'Last Run Duration<br />(hh:mm:ss)', '', 'Last Run Start', 'Next Run Start', '']));
|
||||||
|
|
||||||
if (result) {
|
if (result) {
|
||||||
for (var i = 0; i < result.length; i++) {
|
for (var i = 0; i < result.length; i++) {
|
||||||
var itemTypeName = GetTaskFriendlyName(result[i].itemType, result[i].options);
|
if (result[i].itemState != "Disabled") {
|
||||||
|
var itemTypeName = GetTaskFriendlyName(result[i].itemType, result[i].options);
|
||||||
|
|
||||||
var itemStateName;
|
var itemStateName;
|
||||||
var itemLastStart;
|
var itemLastStart;
|
||||||
if (result[i].isBlocked == false) {
|
|
||||||
switch (result[i].itemState) {
|
var hasError = "";
|
||||||
case 'NeverStarted':
|
if (result[i].hasErrors) {
|
||||||
itemStateName = "Never started";
|
if (result[i].hasErrors.errorType != null) {
|
||||||
itemLastStart = '-';
|
hasError = " (" + result[i].hasErrors.errorType + ")";
|
||||||
break;
|
}
|
||||||
case 'Stopped':
|
|
||||||
itemStateName = "Stopped";
|
|
||||||
itemLastStart = moment(result[i].lastRunTime).fromNow();
|
|
||||||
break;
|
|
||||||
case 'Running':
|
|
||||||
itemStateName = "Running";
|
|
||||||
itemLastStart = moment(result[i].lastRunTime).fromNow();
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
itemStateName = "Unknown status";
|
|
||||||
itemLastStart = moment(result[i].lastRunTime).fromNow();
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
itemStateName = "Blocked";
|
|
||||||
itemLastStart = moment(result[i].lastRunTime).fromNow();
|
|
||||||
}
|
|
||||||
|
|
||||||
var itemInterval = result[i].interval;
|
if (result[i].isBlocked == false) {
|
||||||
var nextRunTime = moment(result[i].nextRunTime).fromNow();
|
switch (result[i].itemState) {
|
||||||
var startButton = '';
|
case 'NeverStarted':
|
||||||
if (userProfile.roles.includes("Admin")) {
|
itemStateName = "Never started";
|
||||||
if (result[i].allowManualStart == true && result[i].itemState != "Running") {
|
itemLastStart = '-';
|
||||||
startButton = "<span id='startProcess' class='romstart' onclick='StartProcess(\"" + result[i].itemType + "\");'>Start</span>";
|
break;
|
||||||
|
case 'Stopped':
|
||||||
|
itemStateName = "Stopped";
|
||||||
|
itemLastStart = moment(result[i].lastRunTime).format("YYYY-MM-DD h:mm:ss a");
|
||||||
|
break;
|
||||||
|
case 'Running':
|
||||||
|
var progressPercent = "";
|
||||||
|
if (result[i].currentStateProgress) {
|
||||||
|
progressPercent = " (" + result[i].currentStateProgress + ")";
|
||||||
|
}
|
||||||
|
itemStateName = "Running" + progressPercent;
|
||||||
|
itemLastStart = moment(result[i].lastRunTime).format("YYYY-MM-DD h:mm:ss a");
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
itemStateName = "Unknown status";
|
||||||
|
itemLastStart = moment(result[i].lastRunTime).format("YYYY-MM-DD h:mm:ss a");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
itemStateName = "Blocked";
|
||||||
|
itemLastStart = moment(result[i].lastRunTime).format("YYYY-MM-DD h:mm:ss a");
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if (result[i].allowManualStart == false && result[i].removeWhenStopped == true) {
|
itemStateName += hasError;
|
||||||
itemInterval = '';
|
|
||||||
nextRunTime = '';
|
|
||||||
}
|
|
||||||
|
|
||||||
var newRow = [
|
var itemInterval = result[i].interval;
|
||||||
itemTypeName,
|
var nextRunTime = moment(result[i].nextRunTime).format("YYYY-MM-DD h:mm:ss a");
|
||||||
itemStateName,
|
var startButton = '';
|
||||||
itemInterval,
|
if (userProfile.roles.includes("Admin")) {
|
||||||
itemLastStart,
|
if (result[i].allowManualStart == true && result[i].itemState != "Running") {
|
||||||
nextRunTime,
|
startButton = "<span id='startProcess' class='romstart' onclick='StartProcess(\"" + result[i].itemType + "\");'>Start</span>";
|
||||||
startButton
|
}
|
||||||
];
|
}
|
||||||
newTable.appendChild(createTableRow(false, newRow, 'romrow', 'romcell'));
|
|
||||||
|
if (result[i].allowManualStart == false && result[i].removeWhenStopped == true) {
|
||||||
|
itemInterval = '';
|
||||||
|
nextRunTime = '';
|
||||||
|
}
|
||||||
|
|
||||||
|
var logLink = '';
|
||||||
|
if (result[i].correlationId) {
|
||||||
|
logLink = '<a href="/index.html?page=settings&sub=logs&correlationid=' + result[i].correlationId + '" class="romlink">View Log</a>';
|
||||||
|
}
|
||||||
|
|
||||||
|
var newRow = [
|
||||||
|
itemTypeName,
|
||||||
|
itemStateName,
|
||||||
|
itemInterval,
|
||||||
|
new Date(result[i].lastRunDuration * 1000).toISOString().slice(11, 19),
|
||||||
|
logLink,
|
||||||
|
itemLastStart,
|
||||||
|
nextRunTime,
|
||||||
|
startButton
|
||||||
|
];
|
||||||
|
newTable.appendChild(createTableRow(false, newRow, 'romrow', 'romcell'));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -176,6 +200,9 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
function BuildLibraryStatisticsBar(TargetObject, TargetObjectLegend, LibraryStatistics, LibrarySize) {
|
function BuildLibraryStatisticsBar(TargetObject, TargetObjectLegend, LibraryStatistics, LibrarySize) {
|
||||||
|
TargetObject.innerHTML = '';
|
||||||
|
TargetObjectLegend.innerHTML = '';
|
||||||
|
|
||||||
var newTable = document.createElement('table');
|
var newTable = document.createElement('table');
|
||||||
newTable.setAttribute('cellspacing', 0);
|
newTable.setAttribute('cellspacing', 0);
|
||||||
newTable.setAttribute('style', 'width: 100%; height: 10px;');
|
newTable.setAttribute('style', 'width: 100%; height: 10px;');
|
||||||
@@ -239,8 +266,9 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
SystemLoadStatus();
|
SystemLoadStatus();
|
||||||
setInterval(SystemLoadStatus, 30000);
|
setInterval(SystemLoadStatus, 3000);
|
||||||
SystemLoadSystemStatus();
|
SystemLoadSystemStatus();
|
||||||
setInterval(SystemLoadStatus, 60000);
|
setInterval(SystemLoadSystemStatus, 60000);
|
||||||
SystemSignaturesStatus();
|
SystemSignaturesStatus();
|
||||||
setInterval(SystemSignaturesStatus, 300000);</script>
|
setInterval(SystemSignaturesStatus, 300000);
|
||||||
|
</script>
|
||||||
|
@@ -90,17 +90,36 @@ function formatGamesPanel(targetElement, result, pageNumber, pageSize) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// add page numbers
|
// add page numbers
|
||||||
|
var pageEitherSide = 4;
|
||||||
|
var currentPage = Number(pagerCheck.innerHTML);
|
||||||
var pageNumbers = document.createElement('span');
|
var pageNumbers = document.createElement('span');
|
||||||
for (var i = 1; i <= pageCount; i++) {
|
for (var i = 1; i <= pageCount; i++) {
|
||||||
var pageNum = document.createElement('span');
|
if (
|
||||||
if (Number(pagerCheck.innerHTML) == i) {
|
(
|
||||||
pageNum.className = 'games_pager_number_disabled';
|
(i >= currentPage - pageEitherSide) &&
|
||||||
} else {
|
(i <= currentPage + pageEitherSide)
|
||||||
pageNum.className = 'games_pager_number';
|
) ||
|
||||||
pageNum.setAttribute('onclick', 'executeFilter1_1(' + i + ');');
|
(
|
||||||
|
(
|
||||||
|
i <= (pageEitherSide * 2 + 1) &&
|
||||||
|
currentPage <= (pageEitherSide)
|
||||||
|
) ||
|
||||||
|
(
|
||||||
|
i >= (pageCount - (pageEitherSide * 2)) &&
|
||||||
|
currentPage >= (pageCount - (pageEitherSide))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
) {
|
||||||
|
var pageNum = document.createElement('span');
|
||||||
|
if (Number(pagerCheck.innerHTML) == i) {
|
||||||
|
pageNum.className = 'games_pager_number_disabled';
|
||||||
|
} else {
|
||||||
|
pageNum.className = 'games_pager_number';
|
||||||
|
pageNum.setAttribute('onclick', 'executeFilter1_1(' + i + ');');
|
||||||
|
}
|
||||||
|
pageNum.innerHTML = i;
|
||||||
|
pageNumbers.appendChild(pageNum);
|
||||||
}
|
}
|
||||||
pageNum.innerHTML = i;
|
|
||||||
pageNumbers.appendChild(pageNum);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// add next page button
|
// add next page button
|
||||||
|
@@ -316,7 +316,10 @@ input[id='filter_panel_userrating_max'] {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.games_pager_number {
|
.games_pager_number {
|
||||||
|
display: inline-block;
|
||||||
padding: 5px;
|
padding: 5px;
|
||||||
|
width: 40px;
|
||||||
|
text-align: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.games_pager_number:hover {
|
.games_pager_number:hover {
|
||||||
@@ -325,7 +328,10 @@ input[id='filter_panel_userrating_max'] {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.games_pager_number_disabled {
|
.games_pager_number_disabled {
|
||||||
|
display: inline-block;
|
||||||
padding: 5px;
|
padding: 5px;
|
||||||
|
width: 40px;
|
||||||
|
text-align: center;
|
||||||
color: grey;
|
color: grey;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1054,22 +1060,38 @@ button:disabled {
|
|||||||
vertical-align: top;
|
vertical-align: top;
|
||||||
}
|
}
|
||||||
|
|
||||||
.logs_table_row_Information:hover {
|
.logs_table_row_Information:nth-child(even) {
|
||||||
background: rgba(42, 41, 150, 0.3);
|
background: rgba(42, 41, 150, 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
.logs_table_row_Warning:hover {
|
.logs_table_row_Information:nth-child(odd) {
|
||||||
|
background: rgba(10, 9, 83, 0.3);
|
||||||
|
}
|
||||||
|
|
||||||
|
.logs_table_row_Warning:nth-child(even) {
|
||||||
background: rgba(139, 150, 41, 0.3);
|
background: rgba(139, 150, 41, 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
.logs_table_row_Critical:hover {
|
.logs_table_row_Warning:nth-child(odd) {
|
||||||
|
background: rgba(49, 53, 14, 0.3);
|
||||||
|
}
|
||||||
|
|
||||||
|
.logs_table_row_Critical:nth-child(even) {
|
||||||
background: rgba(150, 41, 41, 0.3);
|
background: rgba(150, 41, 41, 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
.logs_table_row_Debug:hover {
|
.logs_table_row_Critical:nth-child(odd) {
|
||||||
|
background: rgba(58, 16, 16, 0.3);
|
||||||
|
}
|
||||||
|
|
||||||
|
.logs_table_row_Debug:nth-child(even) {
|
||||||
background: rgba(150, 41, 135, 0.3);
|
background: rgba(150, 41, 135, 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.logs_table_row_Debug:nth-child(odd) {
|
||||||
|
background: rgba(68, 18, 61, 0.3);
|
||||||
|
}
|
||||||
|
|
||||||
.logs_table_exception {
|
.logs_table_exception {
|
||||||
margin-right: 10px;
|
margin-right: 10px;
|
||||||
padding: 5px;
|
padding: 5px;
|
||||||
|
Reference in New Issue
Block a user