diff --git a/ProjectLighthouse.Servers.GameServer/Controllers/CommentController.cs b/ProjectLighthouse.Servers.GameServer/Controllers/CommentController.cs index 81edeee7..70765ea0 100644 --- a/ProjectLighthouse.Servers.GameServer/Controllers/CommentController.cs +++ b/ProjectLighthouse.Servers.GameServer/Controllers/CommentController.cs @@ -34,16 +34,15 @@ public class CommentController : ControllerBase public async Task RateComment([FromQuery] int commentId, [FromQuery] int rating, string? username, string? slotType, int slotId) { GameTokenEntity token = this.GetToken(); - UserEntity? user = await this.database.UserFromGameToken(token); if (user == null) return this.Unauthorized(); + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + // Return bad request if both are true or both are false if ((slotId == 0 || SlotHelper.IsTypeInvalid(slotType)) == (username == null)) return this.BadRequest(); - // Return bad request on unverified email if enforcement is enabled - if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); - bool success = await this.database.RateComment(token.UserId, commentId, rating); if (!success) return this.BadRequest(); @@ -55,15 +54,14 @@ public class CommentController : ControllerBase public async Task GetComments(string? username, string? slotType, int slotId) { GameTokenEntity token = this.GetToken(); - - UserEntity? user = await this.database.UserFromGameToken(token); + UserEntity? user = await this.database.UserFromGameToken(token); if (user == null) return this.Unauthorized(); - if ((slotId == 0 || SlotHelper.IsTypeInvalid(slotType)) == (username == null)) return this.BadRequest(); - - // Return bad request on unverified email if enforcement is enabled + // Return bad request on unverified email if enforcement is enabled if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + if ((slotId == 0 || SlotHelper.IsTypeInvalid(slotType)) == (username == null)) return this.BadRequest(); + int originalSlotId = slotId; if (slotType == "developer") slotId = await SlotHelper.GetPlaceholderSlotId(this.database, slotId, SlotType.Developer); @@ -108,8 +106,7 @@ public class CommentController : ControllerBase .ApplyPagination(pageData) .ToListAsync()).ToSerializableList(c => GameComment.CreateFromEntity(c, token.UserId)); - if (type == CommentType.Level && slotType == "developer" && user.IsModerator && pageData.PageStart == 1) - { + if (type == CommentType.Level && slotType == "developer" && user.IsModerator && pageData.PageStart == 1) { comments.Insert(0, new GameComment { CommentId = 0, @@ -127,16 +124,15 @@ public class CommentController : ControllerBase public async Task PostComment(string? username, string? slotType, int slotId) { GameTokenEntity token = this.GetToken(); - UserEntity? user = await this.database.UserFromGameToken(token); if (user == null) return this.Unauthorized(); + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + // Deny request if in read-only mode if (ServerConfiguration.Instance.UserGeneratedContentLimits.ReadOnlyMode) return this.BadRequest(); - // Return bad request on unverified email if enforcement is enabled - if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); - GameComment? comment = await this.DeserializeBody(); if (comment?.Message == null) return this.BadRequest(); @@ -172,17 +168,16 @@ public class CommentController : ControllerBase public async Task DeleteComment([FromQuery] int commentId, string? username, string? slotType, int slotId) { GameTokenEntity token = this.GetToken(); - UserEntity? user = await this.database.UserFromGameToken(token); + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + // Deny request if in read-only mode if (ServerConfiguration.Instance.UserGeneratedContentLimits.ReadOnlyMode) return this.BadRequest(); if ((slotId == 0 || SlotHelper.IsTypeInvalid(slotType)) == (username == null)) return this.BadRequest(); - // Return bad request on unverified email if enforcement is enabled - if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); - CommentEntity? comment = await this.database.Comments.FirstOrDefaultAsync(c => c.CommentId == commentId); if (comment == null) return this.NotFound(); diff --git a/ProjectLighthouse.Servers.GameServer/Controllers/Matching/EnterLevelController.cs b/ProjectLighthouse.Servers.GameServer/Controllers/Matching/EnterLevelController.cs index 338dea0f..d2394f3a 100644 --- a/ProjectLighthouse.Servers.GameServer/Controllers/Matching/EnterLevelController.cs +++ b/ProjectLighthouse.Servers.GameServer/Controllers/Matching/EnterLevelController.cs @@ -24,8 +24,6 @@ public class EnterLevelController : ControllerBase { private readonly DatabaseContext database; - private static readonly bool emailEnforcementEnabled = EnforceEmailConfiguration.Instance.EnableEmailEnforcement; - public EnterLevelController(DatabaseContext database) { this.database = database; @@ -41,9 +39,6 @@ public class EnterLevelController : ControllerBase if (SlotHelper.IsTypeInvalid(slotType)) return this.BadRequest(); - // Return bad request on unverified email if enforcement is enabled - if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); - // don't count plays for developer slots if (slotType == "developer") return this.Ok(); @@ -117,9 +112,6 @@ public class EnterLevelController : ControllerBase if (SlotHelper.IsTypeInvalid(slotType)) return this.BadRequest(); - // Return bad request on unverified email if enforcement is enabled - if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); - if (slotType == "developer") return this.Ok(); SlotEntity? slot = await this.database.Slots.FirstOrDefaultAsync(s => s.SlotId == slotId); diff --git a/ProjectLighthouse.Servers.GameServer/Controllers/Matching/MatchController.cs b/ProjectLighthouse.Servers.GameServer/Controllers/Matching/MatchController.cs index e0fc6afc..cec69799 100644 --- a/ProjectLighthouse.Servers.GameServer/Controllers/Matching/MatchController.cs +++ b/ProjectLighthouse.Servers.GameServer/Controllers/Matching/MatchController.cs @@ -41,7 +41,6 @@ public class MatchController : ControllerBase public async Task Match() { GameTokenEntity token = this.GetToken(); - UserEntity? user = await this.database.UserFromGameToken(token); if (user == null) return this.Unauthorized(); diff --git a/ProjectLighthouse.Servers.GameServer/Controllers/Resources/PhotosController.cs b/ProjectLighthouse.Servers.GameServer/Controllers/Resources/PhotosController.cs index 4c73d0a0..2feb0e3c 100644 --- a/ProjectLighthouse.Servers.GameServer/Controllers/Resources/PhotosController.cs +++ b/ProjectLighthouse.Servers.GameServer/Controllers/Resources/PhotosController.cs @@ -27,6 +27,8 @@ public class PhotosController : ControllerBase { private readonly DatabaseContext database; + private static readonly bool emailEnforcementEnabled = EnforceEmailConfiguration.Instance.EnableEmailEnforcement; + public PhotosController(DatabaseContext database) { this.database = database; @@ -36,6 +38,11 @@ public class PhotosController : ControllerBase public async Task UploadPhoto() { GameTokenEntity token = this.GetToken(); + UserEntity? user = await this.database.UserFromGameToken(token); + if (user == null) return this.Unauthorized(); + + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); // Deny request if in read-only mode if (ServerConfiguration.Instance.UserGeneratedContentLimits.ReadOnlyMode) return this.BadRequest(); @@ -174,6 +181,11 @@ public class PhotosController : ControllerBase [HttpGet("photos/{slotType}/{id:int}")] public async Task SlotPhotos(string slotType, int id, [FromQuery] string? by) { + GameTokenEntity token = this.GetToken(); + UserEntity? user = await this.database.UserFromGameToken(token); + + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); if (SlotHelper.IsTypeInvalid(slotType)) return this.BadRequest(); @@ -202,7 +214,6 @@ public class PhotosController : ControllerBase [HttpGet("photos/by")] public async Task UserPhotosBy(string user) { - int targetUserId = await this.database.UserIdFromUsername(user); if (targetUserId == 0) return this.NotFound(); @@ -218,7 +229,7 @@ public class PhotosController : ControllerBase [HttpGet("photos/with")] public async Task UserPhotosWith(string user) - { + { int targetUserId = await this.database.UserIdFromUsername(user); if (targetUserId == 0) return this.NotFound(); @@ -237,6 +248,10 @@ public class PhotosController : ControllerBase public async Task DeletePhoto(int id) { GameTokenEntity token = this.GetToken(); + UserEntity? user = await this.database.UserFromGameToken(token); + + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); PhotoEntity? photo = await this.database.Photos.FirstOrDefaultAsync(p => p.PhotoId == id); if (photo == null) return this.NotFound(); diff --git a/ProjectLighthouse.Servers.GameServer/Controllers/Resources/ResourcesController.cs b/ProjectLighthouse.Servers.GameServer/Controllers/Resources/ResourcesController.cs index 7231ccaf..800046a1 100644 --- a/ProjectLighthouse.Servers.GameServer/Controllers/Resources/ResourcesController.cs +++ b/ProjectLighthouse.Servers.GameServer/Controllers/Resources/ResourcesController.cs @@ -1,12 +1,15 @@ #nullable enable using System.Text; using LBPUnion.ProjectLighthouse.Configuration; +using LBPUnion.ProjectLighthouse.Database; using LBPUnion.ProjectLighthouse.Extensions; using LBPUnion.ProjectLighthouse.Files; using LBPUnion.ProjectLighthouse.Logging; using LBPUnion.ProjectLighthouse.Servers.GameServer.Types.Misc; +using LBPUnion.ProjectLighthouse.Types.Entities.Profile; using LBPUnion.ProjectLighthouse.Types.Logging; using LBPUnion.ProjectLighthouse.Types.Resources; +using LBPUnion.ProjectLighthouse.Types.Entities.Token; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; using IOFile = System.IO.File; @@ -19,10 +22,18 @@ namespace LBPUnion.ProjectLighthouse.Servers.GameServer.Controllers.Resources; [Route("LITTLEBIGPLANETPS3_XML")] public class ResourcesController : ControllerBase { + private readonly DatabaseContext database; + + public ResourcesController(DatabaseContext database) + { + this.database = database; + } [HttpPost("showModerated")] public IActionResult ShowModerated() => this.Ok(new ResourceList()); + private static readonly bool emailEnforcementEnabled = EnforceEmailConfiguration.Instance.EnableEmailEnforcement; + [HttpPost("filterResources")] [HttpPost("showNotUploaded")] public async Task FilterResources() @@ -36,8 +47,14 @@ public class ResourcesController : ControllerBase } [HttpGet("r/{hash}")] - public IActionResult GetResource(string hash) + public async Task GetResource(string hash) { + GameTokenEntity token = this.GetToken(); + UserEntity? user = await this.database.UserFromGameToken(token); + + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + string path = FileHelper.GetResourcePath(hash); string fullPath = Path.GetFullPath(path); @@ -54,6 +71,12 @@ public class ResourcesController : ControllerBase [HttpPost("upload/{hash}")] public async Task UploadResource(string hash) { + GameTokenEntity token = this.GetToken(); + UserEntity? user = await this.database.UserFromGameToken(token); + + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + string assetsDirectory = FileHelper.ResourcePath; string path = FileHelper.GetResourcePath(hash); string fullPath = Path.GetFullPath(path); diff --git a/ProjectLighthouse.Servers.GameServer/Controllers/UserController.cs b/ProjectLighthouse.Servers.GameServer/Controllers/UserController.cs index 7301bc52..c2675d13 100644 --- a/ProjectLighthouse.Servers.GameServer/Controllers/UserController.cs +++ b/ProjectLighthouse.Servers.GameServer/Controllers/UserController.cs @@ -29,6 +29,8 @@ public class UserController : ControllerBase { private readonly DatabaseContext database; + private static readonly bool emailEnforcementEnabled = EnforceEmailConfiguration.Instance.EnableEmailEnforcement; + public UserController(DatabaseContext database) { this.database = database; @@ -36,7 +38,11 @@ public class UserController : ControllerBase [HttpGet("user/{username}")] public async Task GetUser(string username) - { + { + // Return bad request on unverified email if enforcement is enabled + GameTokenEntity token = this.GetToken(); + if (emailEnforcementEnabled && !token.User.EmailAddressVerified) return this.BadRequest(); + UserEntity? user = await this.database.Users.FirstOrDefaultAsync(u => u.Username == username); if (user == null) return this.NotFound(); @@ -66,9 +72,11 @@ public class UserController : ControllerBase public async Task UpdateUser() { GameTokenEntity token = this.GetToken(); - UserEntity? user = await this.database.UserFromGameToken(token); - if (user == null) return this.Forbid(); + if (user == null) return this.Forbid(); + + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); UserUpdate? update = await this.DeserializeBody("updateUser", "user"); @@ -176,6 +184,9 @@ public class UserController : ControllerBase UserEntity? user = await this.database.UserFromGameToken(this.GetToken()); if (user == null) return this.Forbid(); + // Return bad request on unverified email if enforcement is enabled + if (emailEnforcementEnabled && !user.EmailAddressVerified) return this.BadRequest(); + string bodyString = await this.ReadBodyAsync(); Pins? pinJson = JsonSerializer.Deserialize(bodyString); diff --git a/ProjectLighthouse/Helpers/EmailHelper.cs b/ProjectLighthouse/Helpers/EmailHelper.cs index 697c3bf5..63b7ea21 100644 --- a/ProjectLighthouse/Helpers/EmailHelper.cs +++ b/ProjectLighthouse/Helpers/EmailHelper.cs @@ -9,8 +9,10 @@ using System.Threading.Tasks; using LBPUnion.ProjectLighthouse.Configuration; using LBPUnion.ProjectLighthouse.Database; using LBPUnion.ProjectLighthouse.Extensions; +using LBPUnion.ProjectLighthouse.Logging; using LBPUnion.ProjectLighthouse.Types.Entities.Profile; using LBPUnion.ProjectLighthouse.Types.Entities.Token; +using LBPUnion.ProjectLighthouse.Types.Logging; using LBPUnion.ProjectLighthouse.Types.Mail; using Microsoft.EntityFrameworkCore; @@ -91,7 +93,13 @@ public static class SMTPHelper string domain = email.Split('@')[1]; // Return false if domain is found in blacklist - return !blacklistedDomains.Contains(domain); + if (blacklistedDomains.Contains(domain)) + { + Logger.Info($"Invalid email address {email} submitted by user.", LogArea.Email); + return false; + } + + return true; } return true;