diff --git a/DatabaseMigrations/7.sql b/DatabaseMigrations/7.sql new file mode 100644 index 00000000..ac8e1bc9 --- /dev/null +++ b/DatabaseMigrations/7.sql @@ -0,0 +1,17 @@ +create table QueuedLevels +( + QueuedLevelId int, + UserId int not null, + SlotId int not null +); + +create unique index QueuedLevels_QueuedLevelId_uindex + on QueuedLevels (QueuedLevelId); + +alter table QueuedLevels + add constraint QueuedLevels_pk + primary key (QueuedLevelId); + +alter table QueuedLevels + modify QueuedLevelId int auto_increment; + diff --git a/ProjectLighthouse/Controllers/LevelQueueController.cs b/ProjectLighthouse/Controllers/LevelQueueController.cs new file mode 100644 index 00000000..85d464c8 --- /dev/null +++ b/ProjectLighthouse/Controllers/LevelQueueController.cs @@ -0,0 +1,63 @@ +#nullable enable +using System.Collections.Generic; +using System.Linq; +using System.Threading.Tasks; +using Microsoft.AspNetCore.Mvc; +using Microsoft.EntityFrameworkCore; +using ProjectLighthouse.Serialization; +using ProjectLighthouse.Types; + +namespace ProjectLighthouse.Controllers { + [ApiController] + [Route("LITTLEBIGPLANETPS3_XML/")] + [Produces("text/xml")] + public class LevelQueueController : ControllerBase { + [HttpGet("slots/lolcatftw/{username}")] + public IActionResult GetLevelQueue(string username) { + IEnumerable queuedLevels = new Database().QueuedLevels + .Include(q => q.User) + .Include(q => q.Slot) + .Where(q => q.User.Username == username) + .AsEnumerable(); + + string response = queuedLevels.Aggregate(string.Empty, (current, q) => current + q.Slot.Serialize()); + + return this.Ok(LbpSerializer.TaggedStringElement("slots", response, "total", 1)); + } + + [HttpPost("lolcatftw/remove/user/{id:int}")] + public async Task RemoveQueuedLevel(int id) { + await using Database database = new(); + + User? user = await database.UserFromRequest(this.Request); + if(user == null) return this.StatusCode(403, ""); + + QueuedLevel queuedLevel = await database.QueuedLevels.FirstOrDefaultAsync(q => q.UserId == user.UserId && q.SlotId == id); + if(queuedLevel != null) database.QueuedLevels.Remove(queuedLevel); + + await database.SaveChangesAsync(); + + return this.Ok(); + } + + [HttpPost("lolcatftw/add/user/{id:int}")] + public async Task AddQueuedLevel(int id) { + await using Database database = new(); + + User? user = await database.UserFromRequest(this.Request); + if(user == null) return this.StatusCode(403, ""); + + QueuedLevel queuedLevel = await database.QueuedLevels.FirstOrDefaultAsync(q => q.UserId == user.UserId && q.SlotId == id); + if(queuedLevel != null) return this.Ok(); + + database.QueuedLevels.Add(new QueuedLevel { + SlotId = id, + UserId = user.UserId + }); + + await database.SaveChangesAsync(); + + return this.Ok(); + } + } +} \ No newline at end of file diff --git a/ProjectLighthouse/Controllers/SlotsController.cs b/ProjectLighthouse/Controllers/SlotsController.cs index 3f2735d9..cd8a544c 100644 --- a/ProjectLighthouse/Controllers/SlotsController.cs +++ b/ProjectLighthouse/Controllers/SlotsController.cs @@ -25,8 +25,7 @@ namespace ProjectLighthouse.Controllers { return this.Ok(LbpSerializer.TaggedStringElement("slots", response, "total", 1)); } - - [HttpGet("s/user/{id:int}")] + public async Task SUser(int id) { Slot slot = await this.database.Slots .Include(s => s.Creator) @@ -35,16 +34,5 @@ namespace ProjectLighthouse.Controllers { return this.Ok(slot.Serialize()); } - - [HttpGet("slots/lolcatftw/{username}")] - public IActionResult SlotsLolCat(string username) { - string response = Enumerable.Aggregate( - database.Slots - .Include(s => s.Creator) - .Include(s => s.Location) - , string.Empty, (current, slot) => current + slot.Serialize()); - - return this.Ok(LbpSerializer.TaggedStringElement("slots", response, "total", 1)); - } } } \ No newline at end of file diff --git a/ProjectLighthouse/Database.cs b/ProjectLighthouse/Database.cs index 1c1f16da..295ddcd5 100644 --- a/ProjectLighthouse/Database.cs +++ b/ProjectLighthouse/Database.cs @@ -1,4 +1,3 @@ -#nullable enable using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.EntityFrameworkCore; @@ -10,6 +9,7 @@ namespace ProjectLighthouse { public DbSet Users { get; set; } public DbSet Locations { get; set; } public DbSet Slots { get; set; } + public DbSet QueuedLevels { get; set; } public DbSet Comments { get; set; } public DbSet Tokens { get; set; } @@ -38,6 +38,7 @@ namespace ProjectLighthouse { } + #nullable enable public async Task AuthenticateUser(LoginData loginData) { // TODO: don't use psn name to authenticate User user = await this.Users.FirstOrDefaultAsync(u => u.Username == loginData.Username) @@ -71,5 +72,6 @@ namespace ProjectLighthouse { return await UserFromAuthToken(mmAuth); } + #nullable disable } } \ No newline at end of file diff --git a/ProjectLighthouse/Types/QueuedLevel.cs b/ProjectLighthouse/Types/QueuedLevel.cs new file mode 100644 index 00000000..f9e191a7 --- /dev/null +++ b/ProjectLighthouse/Types/QueuedLevel.cs @@ -0,0 +1,18 @@ +using System.ComponentModel.DataAnnotations; +using System.ComponentModel.DataAnnotations.Schema; + +namespace ProjectLighthouse.Types { + public class QueuedLevel { + [Key] public int QueuedLevelId { get; set; } + + public int UserId { get; set; } + + [ForeignKey(nameof(UserId))] + public User User { get; set; } + + public int SlotId { get; set; } + + [ForeignKey(nameof(SlotId))] + public Slot Slot { get; set; } + } +} \ No newline at end of file