Skip to content

Commit e797300

Browse files
authored
Merge pull request #120 from samuelzedec/develop
tests: Configuração de alguns testes de integração para o endpoint de login
2 parents 7eb9a3f + 2ecbe18 commit e797300

File tree

17 files changed

+357
-144
lines changed

17 files changed

+357
-144
lines changed

Riber.slnx

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -9,15 +9,15 @@
99
<File Path="CHANGELOG.md"/>
1010
</Folder>
1111
<Folder Name="/src/">
12-
<Project Path="src\Riber.Api\Riber.Api.csproj" />
13-
<Project Path="src\Riber.Application\Riber.Application.csproj" />
14-
<Project Path="src\Riber.Domain\Riber.Domain.csproj" />
15-
<Project Path="src\Riber.Infrastructure\Riber.Infrastructure.csproj" />
12+
<Project Path="src/Riber.Api/Riber.Api.csproj" />
13+
<Project Path="src/Riber.Application/Riber.Application.csproj" />
14+
<Project Path="src/Riber.Domain/Riber.Domain.csproj" />
15+
<Project Path="src/Riber.Infrastructure/Riber.Infrastructure.csproj" />
1616
</Folder>
1717
<Folder Name="/tests/">
1818
<Project Path="tests/Riber.Api.Tests/Riber.Api.Tests.csproj" />
19-
<Project Path="tests\Riber.Application.Tests\Riber.Application.Tests.csproj" />
20-
<Project Path="tests\Riber.Domain.Tests\Riber.Domain.Tests.csproj" />
21-
<Project Path="tests\Riber.Infrastructure.Tests\Riber.Infrastructure.Tests.csproj" />
19+
<Project Path="tests/Riber.Application.Tests/Riber.Application.Tests.csproj" />
20+
<Project Path="tests/Riber.Domain.Tests/Riber.Domain.Tests.csproj" />
21+
<Project Path="tests/Riber.Infrastructure.Tests/Riber.Infrastructure.Tests.csproj" />
2222
</Folder>
2323
</Solution>

src/Riber.Api/Common/Api/BuilderExtension.cs

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using System.Text;
2+
using System.Text.Json;
23
using System.Text.Json.Serialization;
34
using Asp.Versioning;
45
using Microsoft.AspNetCore.Authorization;
@@ -21,6 +22,7 @@ public static class BuilderExtension
2122
{
2223
public static void AddPipeline(this WebApplicationBuilder builder)
2324
{
25+
builder.AddJsonConfiguration();
2426
builder.AddDocumentationApi();
2527
builder.AddDependencyInjection();
2628
builder.AddConfigurations();
@@ -42,7 +44,6 @@ private static void AddMiddleware(this WebApplicationBuilder builder)
4244
private static void AddConfigurations(this WebApplicationBuilder builder)
4345
{
4446
builder.Configuration.AddEnvironmentVariables();
45-
builder.Services.AddControllers();
4647
builder.Services.AddExceptionHandler<GlobalExceptionHandler>();
4748
builder.Services.AddProblemDetails();
4849
builder.Services.AddMemoryCache();
@@ -181,4 +182,25 @@ private static void AddDocumentationApi(this WebApplicationBuilder builder)
181182
return Task.CompletedTask;
182183
}));
183184
}
185+
186+
private static void AddJsonConfiguration(this WebApplicationBuilder builder)
187+
{
188+
builder.Services.ConfigureHttpJsonOptions(options =>
189+
{
190+
options.SerializerOptions.PropertyNamingPolicy = JsonNamingPolicy.CamelCase;
191+
options.SerializerOptions.PropertyNameCaseInsensitive = true;
192+
options.SerializerOptions.ReadCommentHandling = JsonCommentHandling.Skip;
193+
options.SerializerOptions.AllowTrailingCommas = true;
194+
options.SerializerOptions.WriteIndented = true;
195+
options.SerializerOptions.DefaultIgnoreCondition = JsonIgnoreCondition.Never;
196+
});
197+
198+
builder.Services.AddControllers()
199+
.AddJsonOptions(options =>
200+
{
201+
options.JsonSerializerOptions.PropertyNamingPolicy = JsonNamingPolicy.CamelCase;
202+
options.JsonSerializerOptions.PropertyNameCaseInsensitive = true;
203+
options.JsonSerializerOptions.DefaultIgnoreCondition = JsonIgnoreCondition.Never;
204+
});
205+
}
184206
}

src/Riber.Api/Common/Api/GlobalExceptionHandler.cs

Lines changed: 0 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -30,22 +30,9 @@ public async ValueTask<bool> TryHandleAsync(
3030
};
3131

3232
await httpContext.WriteUnauthorizedResponse(
33-
title: GetErrorCode(statusCode),
3433
code: statusCode,
3534
messages: messages
3635
);
3736
return true;
3837
}
39-
40-
private static string GetErrorCode(int statusCode) => statusCode switch
41-
{
42-
400 => "BAD_REQUEST",
43-
401 => "UNAUTHORIZED",
44-
404 => "NOT_FOUND",
45-
408 => "REQUEST_TIMEOUT",
46-
409 => "CONFLICT",
47-
422 => "UNPROCESSABLE_ENTITY",
48-
500 => "INTERNAL_SERVER_ERROR",
49-
_ => "APPLICATION_ERROR"
50-
};
5138
}

src/Riber.Api/Controllers/CompanyController.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ public async Task<IActionResult> CreateCompany(
2828
CancellationToken cancellationToken)
2929
{
3030
var response = await mediator.Send(withAdminCommand, cancellationToken);
31-
return Created($"/api/company/{response.Value.CompanyId}", response);
31+
return Created($"/api/company/{response.Value?.CompanyId}", response);
3232
}
3333

3434
[HttpPut]

src/Riber.Api/Controllers/UserController.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,6 @@ public async Task<IActionResult> CreateUser(
2424
CancellationToken cancellationToken)
2525
{
2626
var response = await mediator.Send(command, cancellationToken);
27-
return Created($"/api/user/{response.Value.Email}", response);
27+
return Created($"/api/user/{response.Value?.Email}", response);
2828
}
2929
}

src/Riber.Api/Extensions/HttpContextExtension.cs

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -15,20 +15,27 @@ public static class HttpContextExtension
1515

1616
public static async Task WriteUnauthorizedResponse(
1717
this HttpContext context,
18-
string title,
1918
int code,
2019
params string[] messages)
2120
{
22-
var result = Result.Failure(new Error(title, messages));
23-
var response = new
24-
{
25-
isSuccess = result.IsSuccess,
26-
error = new { code = result.Error.Code, messages }
27-
};
21+
var jsonResponse = JsonSerializer.Serialize(
22+
Result.Failure<object>(new Error(GetErrorCode(code), messages)), JsonOptions);
2823

29-
var jsonResponse = JsonSerializer.Serialize(response, JsonOptions);
3024
context.Response.StatusCode = code;
3125
context.Response.ContentType = "application/json";
26+
3227
await context.Response.WriteAsync(jsonResponse);
3328
}
29+
30+
private static string GetErrorCode(int statusCode) => statusCode switch
31+
{
32+
400 => "BAD_REQUEST",
33+
401 => "UNAUTHORIZED",
34+
404 => "NOT_FOUND",
35+
408 => "REQUEST_TIMEOUT",
36+
409 => "CONFLICT",
37+
422 => "UNPROCESSABLE_ENTITY",
38+
500 => "INTERNAL_SERVER_ERROR",
39+
_ => "APPLICATION_ERROR"
40+
};
3441
}

src/Riber.Api/Middlewares/SecurityStampMiddleware.cs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@ public async Task InvokeAsync(HttpContext context, RequestDelegate next)
2424
{
2525
logger.LogError("Valores: userId = {UserId}, securityStamp = {TokenSecurityStamp}", userId, tokenSecurityStamp);
2626
await context.WriteUnauthorizedResponse(
27-
"Acesso não autorizado",
2827
StatusCodes.Status401Unauthorized,
2928
"Token do usuário inválido ou mal formado."
3029
);
@@ -36,7 +35,6 @@ await context.WriteUnauthorizedResponse(
3635
if (user is null || user.SecurityStamp != tokenSecurityStamp)
3736
{
3837
await context.WriteUnauthorizedResponse(
39-
title: "Acesso não autorizado",
4038
code: StatusCodes.Status401Unauthorized,
4139
messages: "Security stamp inválido ou usuário não encontrado."
4240
);
Lines changed: 43 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,47 +1,66 @@
1-
using System.Diagnostics.CodeAnalysis;
1+
using System.Text.Json.Serialization;
22
using Riber.Domain.Abstractions;
33

44
namespace Riber.Application.Common;
55

66
public class Result
77
{
8+
#region Properties
9+
10+
[JsonInclude] public bool IsSuccess { get; init; }
11+
[JsonInclude] public Error Error { get; init; } = new();
12+
13+
#endregion
14+
15+
#region Constructors
16+
17+
[JsonConstructor]
18+
protected Result() { }
19+
820
protected Result(bool isSuccess, Error error)
921
{
10-
switch (isSuccess)
11-
{
12-
case true when error != Error.None:
13-
case false when error == Error.None:
14-
throw new InvalidOperationException();
15-
16-
default:
17-
IsSuccess = isSuccess;
18-
Error = error;
19-
break;
20-
}
22+
IsSuccess = isSuccess;
23+
Error = error;
2124
}
2225

23-
public bool IsSuccess { get; }
24-
public Error Error { get; }
26+
#endregion
2527

26-
public static Result Success() => new(true, Error.None);
27-
public static Result<T> Success<T>(T value) => new(value, true, Error.None);
28+
#region Static Methods
2829

29-
public static Result Failure(Error error) => new(false, error);
30+
public static Result<object> Success() => new(null, true, new Error());
31+
public static Result<T> Success<T>(T value) => new(value, true, new Error());
3032
public static Result<T> Failure<T>(Error error) => new(default, false, error);
3133

32-
public static Result<T> Create<T>(T? value) =>
33-
value is not null ? Success(value) : Failure<T>(Error.NullValue);
34+
protected static Result<T> Create<T>(T? value) =>
35+
value is not null ? Success(value) : Failure<T>(new Error());
36+
37+
#endregion
3438
}
3539

3640
public class Result<T> : Result
3741
{
38-
private readonly T? _value;
42+
#region Properties
43+
44+
[JsonInclude]
45+
[JsonIgnore(Condition = JsonIgnoreCondition.Never)]
46+
public T? Value { get; init; }
47+
48+
#endregion
49+
50+
#region Constructors
51+
52+
[JsonConstructor]
53+
protected Result() { }
3954

4055
protected internal Result(T? value, bool isSuccess, Error error) : base(isSuccess, error)
41-
=> _value = value;
56+
=> Value = value;
57+
58+
#endregion
59+
60+
#region Overrides
4261

43-
[NotNull]
44-
public T Value => _value! ?? throw new InvalidOperationException("Result has no value");
62+
public static implicit operator Result<T>(T? value)
63+
=> Create(value);
4564

46-
public static implicit operator Result<T>(T? value) => Create(value);
65+
#endregion
4766
}
Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,29 @@
1-
namespace Riber.Domain.Abstractions;
1+
using System.Text.Json.Serialization;
2+
3+
namespace Riber.Domain.Abstractions;
24

35
/// <summary>
46
/// Representa um erro com um código identificador e uma mensagem descritiva.
57
/// </summary>
6-
/// <param name="Code">Código único que identifica o tipo de erro.</param>
7-
/// <param name="Messages">Mensagens descritivas e legível sobre os errors.</param>
8-
public record Error(string Code, params string[] Messages)
8+
public sealed class Error
99
{
10-
public static readonly Error None = new(string.Empty);
11-
public static readonly Error NullValue = new("Error.NullValue", "Um valor nulo foi fornecido!");
10+
#region Properties
11+
12+
public string Code { get; init; } = string.Empty;
13+
public string[] Messages { get; init; } = [];
14+
15+
#endregion
16+
17+
#region Constructors
18+
19+
[JsonConstructor]
20+
public Error() {}
21+
22+
public Error(string code, params string[] messages)
23+
{
24+
Code = code;
25+
Messages = messages;
26+
}
27+
28+
#endregion
1229
}

src/Riber.Infrastructure/DependencyInjection.cs

Lines changed: 0 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,6 @@
44
using Microsoft.Extensions.Configuration;
55
using Microsoft.Extensions.DependencyInjection;
66
using Microsoft.Extensions.Logging;
7-
using Newtonsoft.Json;
8-
using Newtonsoft.Json.Serialization;
97
using OpenTelemetry.Logs;
108
using OpenTelemetry.Metrics;
119
using OpenTelemetry.Resources;
@@ -52,7 +50,6 @@ public static void AddInfrastructure(this IServiceCollection services, IConfigur
5250
services.AddServices(configuration);
5351
services.AddAwsServices(configuration);
5452
services.AddBackgroundJobs(defaultConnection);
55-
services.AddJsonConfiguration();
5653
services.AddHealthChecksConfiguration(defaultConnection);
5754
services.AddSchedulersAndJobs();
5855
services.AddTelemetry();
@@ -181,19 +178,6 @@ private static void AddBackgroundJobs(this IServiceCollection services, string d
181178
options.WaitForJobsToComplete = true);
182179
}
183180

184-
private static void AddJsonConfiguration(this IServiceCollection _)
185-
{
186-
JsonConvert.DefaultSettings = () => new JsonSerializerSettings
187-
{
188-
ReferenceLoopHandling = ReferenceLoopHandling.Ignore,
189-
Formatting = Formatting.Indented,
190-
NullValueHandling = NullValueHandling.Ignore,
191-
DefaultValueHandling = DefaultValueHandling.Ignore,
192-
ContractResolver = new CamelCasePropertyNamesContractResolver(),
193-
TypeNameHandling = TypeNameHandling.Auto
194-
};
195-
}
196-
197181
private static void AddTelemetry(this IServiceCollection services)
198182
{
199183
services.AddOpenTelemetry()

0 commit comments

Comments
 (0)