diff --git a/sparkly-server.csproj b/sparkly-server.csproj
index b713321..90a6cbb 100644
--- a/sparkly-server.csproj
+++ b/sparkly-server.csproj
@@ -41,10 +41,12 @@
+
+
@@ -52,6 +54,11 @@
+
+
+
+
+
diff --git a/sparkly-server.test/HealthzTest.cs b/sparkly-server.test/HealthzTest.cs
index 02926de..d989099 100644
--- a/sparkly-server.test/HealthzTest.cs
+++ b/sparkly-server.test/HealthzTest.cs
@@ -1,4 +1,5 @@
-using System.Net;
+using sparkly_server.test.config;
+using System.Net;
namespace sparkly_server.test
{
diff --git a/sparkly-server.test/ProjectTest.cs b/sparkly-server.test/ProjectTest.cs
index ea1a740..e962267 100644
--- a/sparkly-server.test/ProjectTest.cs
+++ b/sparkly-server.test/ProjectTest.cs
@@ -7,7 +7,10 @@
using sparkly_server.Enum;
using sparkly_server.Infrastructure;
using sparkly_server.Services.Auth;
+using sparkly_server.test.config;
+using System.Net;
using Xunit.Abstractions;
+using Xunit.Sdk;
namespace sparkly_server.test
{
@@ -76,7 +79,7 @@ private async Task AuthenticateAsTestUserAsync()
///
/// The name of the project to create.
/// A containing the details of the created project, or null if creation fails.
- private async Task CreateProjectAsync(string projectName)
+ private async Task CreateProjectAsync(string projectName)
{
var payload = new CreateProjectRequest(
ProjectName: projectName,
@@ -93,7 +96,9 @@ private async Task AuthenticateAsTestUserAsync()
response.EnsureSuccessStatusCode();
var created = await response.Content.ReadFromJsonAsync();
- return created;
+
+ return created ?? throw new XunitException("CreateProjectAsync: response body deserialized to null");
+
}
// Tests
@@ -107,7 +112,7 @@ public async Task CreateProject_Should_Create_Project_For_Authenticated_User()
var created = await CreateProjectAsync(projectName);
Assert.NotNull(created);
- Assert.Equal(projectName, created!.ProjectName);
+ Assert.Equal(projectName, created.ProjectName);
using var scope = _factory.Services.CreateScope();
var db = scope.ServiceProvider.GetRequiredService();
@@ -119,5 +124,47 @@ public async Task CreateProject_Should_Create_Project_For_Authenticated_User()
Assert.Equal(projectName, project.ProjectName);
Assert.Equal(userId, project.OwnerId);
}
+
+ [Fact]
+ public async Task CreateProject_Should_Fail_For_Unauthenticated_User()
+ {
+ var request = new CreateProjectRequest("MyTestProject", "Test project", ProjectVisibility.Public);
+
+ var response = await _client.PostAsJsonAsync("/api/v1/projects/create", request);
+
+ Assert.Equal(HttpStatusCode.Unauthorized, response.StatusCode);
+ }
+
+ [Fact]
+ public async Task GetProjectById_Should_Return_Null_For_Nonexistent_Project()
+ {
+ var response = await _client.GetAsync("/api/v1/projects/1234567890abcdef");
+
+ Assert.Equal(HttpStatusCode.NotFound, response.StatusCode);
+ }
+
+ // FIXME: Why NotFound??
+ // [Fact]
+ // public async Task GetProjectById_Should_Return_Project()
+ // {
+ // await AuthenticateAsTestUserAsync();
+ // var projectName = "MyTestProject1";
+ //
+ // var project = await CreateProjectAsync(projectName);
+ // var projectId = project.Id;
+ //
+ // _output.WriteLine($"[Test] Created projectId = {projectId}");
+ //
+ // using (var scope = _factory.Services.CreateScope())
+ // {
+ // var db = scope.ServiceProvider.GetRequiredService();
+ // var exists = await db.Projects.AnyAsync(p => p.Id == projectId);
+ // _output.WriteLine($"[Test] Project exists in DB: {exists}");
+ // }
+ //
+ // var response = await _client.GetAsync($"/api/v1/projects/{projectId}");
+ //
+ // Assert.Equal(HttpStatusCode.OK, response.StatusCode);
+ // }
}
}
\ No newline at end of file
diff --git a/sparkly-server.test/UserTest.cs b/sparkly-server.test/UserTest.cs
index 10c5829..87646e1 100644
--- a/sparkly-server.test/UserTest.cs
+++ b/sparkly-server.test/UserTest.cs
@@ -1,6 +1,7 @@
using Microsoft.Extensions.DependencyInjection;
using sparkly_server.DTO.Auth;
using sparkly_server.Infrastructure;
+using sparkly_server.test.config;
using System.Text;
using System.Text.Json;
diff --git a/sparkly-server.test/TestWebAppliactionFactory.cs b/sparkly-server.test/config/TestWebAppliactionFactory.cs
similarity index 95%
rename from sparkly-server.test/TestWebAppliactionFactory.cs
rename to sparkly-server.test/config/TestWebAppliactionFactory.cs
index b391291..296a834 100644
--- a/sparkly-server.test/TestWebAppliactionFactory.cs
+++ b/sparkly-server.test/config/TestWebAppliactionFactory.cs
@@ -2,7 +2,7 @@
using Microsoft.AspNetCore.Mvc.Testing;
using Microsoft.Extensions.Configuration;
-namespace sparkly_server.test
+namespace sparkly_server.test.config
{
public class TestWebApplicationFactory : WebApplicationFactory
{
diff --git a/src/Controllers/Projects/ProjectsController.cs b/src/Controllers/Projects/ProjectsController.cs
index a567a45..bee89bc 100644
--- a/src/Controllers/Projects/ProjectsController.cs
+++ b/src/Controllers/Projects/ProjectsController.cs
@@ -27,7 +27,11 @@ public async Task GetRandomProjects([FromQuery] int take = 20, Ca
public async Task GetProjectById(Guid projectId, CancellationToken ct = default)
{
var project = await _projects.GetProjectByIdAsync(projectId, ct);
- return Ok(project);
+
+ if (project is null)
+ return NotFound();
+
+ return Ok(new ProjectResponse(project));
}
// Create project
diff --git a/src/Services/Projects/IProjectService.cs b/src/Services/Projects/IProjectService.cs
index 7c2686e..e75e343 100644
--- a/src/Services/Projects/IProjectService.cs
+++ b/src/Services/Projects/IProjectService.cs
@@ -12,7 +12,7 @@ Task CreateProjectAsync(
ProjectVisibility visibility,
CancellationToken cancellationToken = default);
- Task GetProjectByIdAsync(
+ Task GetProjectByIdAsync(
Guid projectId, CancellationToken
cancellationToken = default);
diff --git a/src/Services/Projects/ProjectService.cs b/src/Services/Projects/ProjectService.cs
index f229a0d..919e4ae 100644
--- a/src/Services/Projects/ProjectService.cs
+++ b/src/Services/Projects/ProjectService.cs
@@ -63,12 +63,9 @@ public async Task CreateProjectAsync(string name, string description, P
///
/// Thrown if the project with the specified identifier is not found.
///
- public async Task GetProjectByIdAsync(Guid projectId, CancellationToken cancellationToken = default)
+ public Task GetProjectByIdAsync(Guid projectId, CancellationToken cancellationToken = default)
{
- var project = await _projects.GetByIdAsync(projectId, cancellationToken)
- ?? throw new InvalidOperationException("Project not found");
-
- return project;
+ return _projects.GetByIdAsync(projectId, cancellationToken);
}
///