Refactor API security handling and enhance metadata endpoint#464
Merged
Conversation
… Endpoint - Updated the AuthorizationOperationFilter to streamline the handling of API key attributes and service filters, reducing redundancy in security requirement checks. - Introduced a new method to create a security reference document for API keys, enhancing the Swagger documentation. - Added a new endpoint in MetadataProxyController for fetching game metadata from ScreenScraper by game ID or checksum, including detailed XML comments for API documentation. - Implemented logic to handle multiple identifier types (gameid, crc, md5, sha1) and return appropriate metadata or error responses. - Enhanced Swagger configuration in StartupExtensions to apply security definitions for API keys.
…L response format - Added logic to strip sensitive login details from media URLs in the response. - Rewrote media URLs to point to a local cache instead of the original URLs. - Implemented XML serialization for the response when requested, defaulting to JSON otherwise.
…rce access patterns - Refactored embedded resource naming to follow the new namespace convention `hasheous_lib.Schema.` and `hasheous_lib.Support.`. - Updated resource access patterns to ensure compatibility with the new naming scheme. - Adjusted related documentation to reflect these changes and ensure clarity for future resource additions.
Contributor
There was a problem hiding this comment.
Pull request overview
This PR refactors how API security requirements are represented in Swagger/OpenAPI, introduces a shared proxy cache manager for media/bundle caching (local + S3 fallback), and adds new ScreenScraper proxy endpoints for game metadata and media retrieval. It also updates several package versions and extends configuration/maintenance to support the new caching behavior.
Changes:
- Refactor Swagger security requirement detection and scheme referencing for API key–based auth.
- Replace per-endpoint local/S3 cache logic with a centralized
ProxyCacheManager, and wire cache maintenance into hourly maintenance. - Add ScreenScraper proxy endpoints (
jeuInfos.php,systemesListe.php,media*.php) with URL sanitization and optional XML output.
Reviewed changes
Copilot reviewed 9 out of 9 changed files in this pull request and generated 14 comments.
Show a summary per file
| File | Description |
|---|---|
| hasheous/StartupExtensions.cs | Small SwaggerGen registration tweak (static lambda) and comment clarifying security definitions. |
| hasheous/Controllers/V1.0/MetadataProxyController.cs | Refactors IGDB/TheGamesDB/GiantBomb media caching to use ProxyCacheManager; adds ScreenScraper proxy endpoints and response shaping. |
| hasheous-lib/hasheous-lib.csproj | Bumps package versions (AWS S3 SDK, Redis, hasheous-client, gaseous-signature-parser). |
| hasheous-lib/Classes/SwaggerSecurityRequirements.cs | Updates Swagger operation filter logic for detecting API-key requirements and uses scheme references. |
| hasheous-lib/Classes/SwaggerIDocumentFilter.cs | Adjusts security scheme reference to use the active OpenAPI document. |
| hasheous-lib/Classes/ProxyCacheManager.cs | New centralized cache helper: download+cache, local/S3 read fallback, and tiered local eviction. |
| hasheous-lib/Classes/Metadata/ScreenScraper/IMetadata_ScreenScraper.cs | Refactors platform search method name, extracts reusable API download helper, and adds a ScreenScraper media endpoint builder. |
| hasheous-lib/Classes/Maintenance.cs | Runs proxy cache maintenance as part of hourly maintenance. |
| hasheous-lib/Classes/Config.cs | Adds persisted config for proxy cache policies (Policies) and a convenience accessor (Config.CachePolicies). |
| } | ||
|
|
||
| string resourcePath = $"Images/{systemeid}/{jeuid}/{media}.{extension}"; | ||
| string url = Classes.MetadataLib.MetadataScreenScraper.ssMedia.Endpoint(jeuid, systemeid, media, null); |
Comment on lines
+1454
to
+1458
| var cachedStream = await ProxyCacheManager.ResolveReadAsync("Screenscraper", resourcePath, CachePolicyType.Media, mimeType); | ||
| if (cachedStream != null) | ||
| { | ||
| return File(cachedStream.Stream, mimeType); | ||
| } |
Comment on lines
+1461
to
+1465
| var fileStream = await ProxyCacheManager.DownloadAndCacheAsync(url, "Screenscraper", resourcePath, CachePolicyType.Media, mimeType, HttpContext); | ||
| if (fileStream != null) | ||
| { | ||
| return File(fileStream.Stream, mimeType); | ||
| } |
…ove caching logic
- Added instructions for registering response disposal wrappers in ProxyCacheManager to prevent resource leaks. - Introduced tiered cache policy configuration details, including retention settings for media and bundles. - Documented new ScreenScraper proxy routes for metadata retrieval and media caching. - Clarified maintenance tasks for proxy cache policy and updated job scheduling details. - Included sensitive credential handling for ScreenScraper queries in response shaping.
Comment on lines
+1247
to
+1250
| if (metadataItem != null && !string.IsNullOrEmpty(metadataItem.ImmutableId)) | ||
| { | ||
| gameid = long.Parse(metadataItem.ImmutableId); | ||
| } |
| IActionResult? cachedResult = await TryServeFromLocalOrS3Async(imageFile, s3Key, "image/jpeg"); | ||
| if (cachedResult != null) | ||
| // strip all media urls of login details since screenscraper requires credentials in the url, and we don't want to expose that in the response | ||
| foreach (var media in gameItem.medias) |
| return cachedResult; | ||
| if (!string.IsNullOrEmpty(media.url)) | ||
| { | ||
| string endpointUrl = Classes.MetadataLib.MetadataScreenScraper.ssMedia.Endpoint((long)gameItem.id, long.Parse(gameItem.systeme.id), media.type, media.region); |
| } | ||
|
|
||
| string resourcePath = $"Images/{systemeid}/{jeuid}/{media}.{extension}"; | ||
| string url = Classes.MetadataLib.MetadataScreenScraper.ssMedia.Endpoint(jeuid, systemeid, media, null); |
Comment on lines
+5
to
+8
| using System.Threading; | ||
| using System.Threading.Tasks; | ||
| using hasheous_server.Classes; | ||
| using Microsoft.AspNetCore.Http; |
Comment on lines
+1212
to
+1215
| [HttpGet] | ||
| [ProducesResponseType(typeof(hasheous_server.Classes.MetadataLib.MetadataScreenScraper.GameItem), StatusCodes.Status200OK)] | ||
| [ProducesResponseType(StatusCodes.Status400BadRequest)] | ||
| [Route("ScreenScraper/jeuInfos.php")] |
Comment on lines
+1370
to
+1373
| [HttpGet] | ||
| [ProducesResponseType(StatusCodes.Status200OK)] | ||
| [ProducesResponseType(StatusCodes.Status404NotFound)] | ||
| [Route("ScreenScraper/media{endpoint}.php")] |
|
|
||
| #region ScreenScraper | ||
| /// <summary> | ||
| /// Get game metadata from ScreenScraper by game ID or checksum (CRC, MD5, SHA1). Returns a response containing game metadata, mirroring the response from the jueInfos.php endpoint of ScreenScraper. If multiple identifiers are provided, the order of precedence is: gameid > md5 > sha1> crc. If no identifiers are provided, a BadRequest response will be returned. |
Comment on lines
+775
to
+777
| string endpointName = ""; | ||
| switch (type) | ||
| { |
…e null media collections
… method and simplify response handling
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Update package versions and refactor the Swagger security requirements to streamline API key handling. Introduce a new endpoint for fetching game metadata from ScreenScraper, with improved response handling and XML support. Sanitize media URLs and update resource naming conventions for clarity and compatibility.