add passenger integration tests

This commit is contained in:
meysamhadeli 2022-05-24 00:55:05 +04:30
parent 0573d68f32
commit 7b1e1f0e43
37 changed files with 376 additions and 749 deletions

View File

@ -7,126 +7,126 @@
<ItemGroup>
<PackageReference Include="Ardalis.GuardClauses" Version="3.3.0"/>
<PackageReference Include="AspNetCore.HealthChecks.UI.SQLite.Storage" Version="5.0.1"/>
<PackageReference Include="Ben.BlockingDetector" Version="0.0.4"/>
<PackageReference Include="EasyCaching.Core" Version="1.4.1"/>
<PackageReference Include="EasyCaching.InMemory" Version="1.4.1"/>
<PackageReference Include="EFCore.NamingConventions" Version="6.0.0"/>
<PackageReference Include="EntityFrameworkCore.Triggered" Version="3.0.0"/>
<PackageReference Include="Figgle" Version="0.4.0"/>
<PackageReference Include="FluentValidation" Version="10.3.6"/>
<PackageReference Include="FluentValidation.AspNetCore" Version="10.3.6"/>
<PackageReference Include="Grpc.Net.Client" Version="2.44.0"/>
<PackageReference Include="MagicOnion" Version="4.4.0"/>
<PackageReference Include="MagicOnion.Abstractions" Version="4.4.0"/>
<PackageReference Include="MagicOnion.Client" Version="4.4.0"/>
<PackageReference Include="MagicOnion.Server" Version="4.4.0"/>
<PackageReference Include="MagicOnion.Server" Version="4.4.0"/>
<PackageReference Include="NSubstitute" Version="4.3.0"/>
<PackageReference Include="Polly" Version="7.2.3"/>
<PackageReference Include="Ardalis.GuardClauses" Version="3.3.0" />
<PackageReference Include="AspNetCore.HealthChecks.UI.SQLite.Storage" Version="5.0.1" />
<PackageReference Include="Ben.BlockingDetector" Version="0.0.4" />
<PackageReference Include="EasyCaching.Core" Version="1.4.1" />
<PackageReference Include="EasyCaching.InMemory" Version="1.4.1" />
<PackageReference Include="EFCore.NamingConventions" Version="6.0.0" />
<PackageReference Include="EntityFrameworkCore.Triggered" Version="3.0.0" />
<PackageReference Include="Figgle" Version="0.4.0" />
<PackageReference Include="FluentValidation" Version="10.3.6" />
<PackageReference Include="FluentValidation.AspNetCore" Version="10.3.6" />
<PackageReference Include="Grpc.Net.Client" Version="2.44.0" />
<PackageReference Include="MagicOnion" Version="4.4.0" />
<PackageReference Include="MagicOnion.Abstractions" Version="4.4.0" />
<PackageReference Include="MagicOnion.Client" Version="4.4.0" />
<PackageReference Include="MagicOnion.Server" Version="4.4.0" />
<PackageReference Include="MagicOnion.Server" Version="4.4.0" />
<PackageReference Include="NSubstitute" Version="4.3.0" />
<PackageReference Include="Polly" Version="7.2.3" />
<PackageReference Include="protobuf-net.BuildTools" Version="3.0.115">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="protobuf-net.Grpc" Version="1.0.152"/>
<PackageReference Include="Hellang.Middleware.ProblemDetails" Version="6.3.0"/>
<PackageReference Include="Humanizer.Core" Version="2.14.1"/>
<PackageReference Include="IdGen" Version="3.0.0"/>
<PackageReference Include="Mapster" Version="7.3.0"/>
<PackageReference Include="Mapster.DependencyInjection" Version="1.0.0"/>
<PackageReference Include="MediatR" Version="9.0.0"/>
<PackageReference Include="MediatR.Extensions.Microsoft.DependencyInjection" Version="9.0.0"/>
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="6.0.0"/>
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.2.2"/>
<PackageReference Include="Microsoft.AspNetCore.Mvc.Versioning.ApiExplorer" Version="5.0.0"/>
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.1"/>
<PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="6.0.1"/>
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.1"/>
<PackageReference Include="Microsoft.Extensions.Configuration.Abstractions" Version="6.0.0"/>
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="6.0.0"/>
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="6.0.0"/>
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="6.0.0"/>
<PackageReference Include="Microsoft.Extensions.Http.Polly" Version="6.0.1"/>
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="6.0.0"/>
<PackageReference Include="Microsoft.Extensions.PlatformAbstractions" Version="1.1.0"/>
<PackageReference Include="MongoDB.Driver" Version="2.14.1"/>
<PackageReference Include="Moq" Version="4.16.1"/>
<PackageReference Include="Newtonsoft.Json" Version="13.0.1"/>
<PackageReference Include="OpenTelemetry.Contrib.Instrumentation.MassTransit" Version="1.0.0-beta2"/>
<PackageReference Include="protobuf-net.Grpc.AspNetCore" Version="1.0.152"/>
<PackageReference Include="Scrutor" Version="3.3.0"/>
<PackageReference Include="Scrutor.AspNetCore" Version="3.3.0"/>
<PackageReference Include="Serilog" Version="2.10.0"/>
<PackageReference Include="Serilog.AspNetCore" Version="4.1.0"/>
<PackageReference Include="Serilog.Enrichers.Span" Version="2.2.0"/>
<PackageReference Include="Serilog.Exceptions" Version="8.1.0"/>
<PackageReference Include="Serilog.Formatting.Elasticsearch" Version="8.4.1"/>
<PackageReference Include="Serilog.Sinks.Console" Version="4.0.1"/>
<PackageReference Include="Serilog.Sinks.Elasticsearch" Version="8.4.1"/>
<PackageReference Include="Serilog.Sinks.Seq" Version="5.1.0"/>
<PackageReference Include="Serilog.Sinks.SpectreConsole" Version="0.1.1"/>
<PackageReference Include="Serilog.Sinks.XUnit" Version="3.0.3"/>
<PackageReference Include="Swashbuckle.AspNetCore.Annotations" Version="6.2.3"/>
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerGen" Version="6.2.3"/>
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerUI" Version="6.2.3"/>
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.2.3"/>
<PackageReference Include="AspNetCore.HealthChecks.UI" Version="5.0.1"/>
<PackageReference Include="AspNetCore.HealthChecks.UI.Client" Version="5.0.1"/>
<PackageReference Include="AspNetCore.HealthChecks.UI.InMemory.Storage" Version="5.0.1"/>
<PackageReference Include="Microsoft.Extensions.Diagnostics.HealthChecks" Version="6.0.1"/>
<PackageReference Include="AspNetCore.HealthChecks.MongoDb" Version="6.0.1"/>
<PackageReference Include="System.Interactive.Async" Version="5.1.0"/>
<PackageReference Include="MassTransit" Version="8.0.0"/>
<PackageReference Include="MassTransit.RabbitMQ" Version="8.0.0"/>
<PackageReference Include="DotNetCore.CAP" Version="6.0.0"/>
<PackageReference Include="DotNetCore.CAP.Dashboard" Version="6.0.0"/>
<PackageReference Include="DotNetCore.CAP.MongoDB" Version="6.0.0"/>
<PackageReference Include="DotNetCore.CAP.OpenTelemetry" Version="6.0.0"/>
<PackageReference Include="DotNetCore.CAP.RabbitMQ" Version="6.0.0"/>
<PackageReference Include="DotNetCore.CAP.SqlServer" Version="6.0.0"/>
<PackageReference Include="Duende.IdentityServer" Version="6.0.0"/>
<PackageReference Include="Duende.IdentityServer.AspNetIdentity" Version="6.0.0"/>
<PackageReference Include="Duende.IdentityServer.EntityFramework" Version="6.0.0"/>
<PackageReference Include="Duende.IdentityServer.EntityFramework.Storage" Version="6.0.3"/>
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.1"/>
<PackageReference Include="Microsoft.AspNetCore.Identity.EntityFrameworkCore" Version="6.0.0"/>
<PackageReference Include="Yarp.ReverseProxy" Version="1.0.0"/>
<PackageReference Include="Microsoft.Identity.Web" Version="1.22.3"/>
<PackageReference Include="protobuf-net.Grpc" Version="1.0.152" />
<PackageReference Include="Hellang.Middleware.ProblemDetails" Version="6.3.0" />
<PackageReference Include="Humanizer.Core" Version="2.14.1" />
<PackageReference Include="IdGen" Version="3.0.0" />
<PackageReference Include="Mapster" Version="7.3.0" />
<PackageReference Include="Mapster.DependencyInjection" Version="1.0.0" />
<PackageReference Include="MediatR" Version="9.0.0" />
<PackageReference Include="MediatR.Extensions.Microsoft.DependencyInjection" Version="9.0.0" />
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="6.0.0" />
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.2.2" />
<PackageReference Include="Microsoft.AspNetCore.Mvc.Versioning.ApiExplorer" Version="5.0.0" />
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="6.0.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.1" />
<PackageReference Include="Microsoft.Extensions.Configuration.Abstractions" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.Http.Polly" Version="6.0.1" />
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.PlatformAbstractions" Version="1.1.0" />
<PackageReference Include="MongoDB.Driver" Version="2.14.1" />
<PackageReference Include="Moq" Version="4.16.1" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.1" />
<PackageReference Include="OpenTelemetry.Contrib.Instrumentation.MassTransit" Version="1.0.0-beta2" />
<PackageReference Include="protobuf-net.Grpc.AspNetCore" Version="1.0.152" />
<PackageReference Include="Scrutor" Version="3.3.0" />
<PackageReference Include="Scrutor.AspNetCore" Version="3.3.0" />
<PackageReference Include="Serilog" Version="2.10.0" />
<PackageReference Include="Serilog.AspNetCore" Version="4.1.0" />
<PackageReference Include="Serilog.Enrichers.Span" Version="2.2.0" />
<PackageReference Include="Serilog.Exceptions" Version="8.1.0" />
<PackageReference Include="Serilog.Formatting.Elasticsearch" Version="8.4.1" />
<PackageReference Include="Serilog.Sinks.Console" Version="4.0.1" />
<PackageReference Include="Serilog.Sinks.Elasticsearch" Version="8.4.1" />
<PackageReference Include="Serilog.Sinks.Seq" Version="5.1.0" />
<PackageReference Include="Serilog.Sinks.SpectreConsole" Version="0.1.1" />
<PackageReference Include="Serilog.Sinks.XUnit" Version="3.0.3" />
<PackageReference Include="Swashbuckle.AspNetCore.Annotations" Version="6.2.3" />
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerGen" Version="6.2.3" />
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerUI" Version="6.2.3" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.2.3" />
<PackageReference Include="AspNetCore.HealthChecks.UI" Version="5.0.1" />
<PackageReference Include="AspNetCore.HealthChecks.UI.Client" Version="5.0.1" />
<PackageReference Include="AspNetCore.HealthChecks.UI.InMemory.Storage" Version="5.0.1" />
<PackageReference Include="Microsoft.Extensions.Diagnostics.HealthChecks" Version="6.0.1" />
<PackageReference Include="AspNetCore.HealthChecks.MongoDb" Version="6.0.1" />
<PackageReference Include="System.Interactive.Async" Version="5.1.0" />
<PackageReference Include="MassTransit" Version="8.0.0" />
<PackageReference Include="MassTransit.RabbitMQ" Version="8.0.0" />
<PackageReference Include="DotNetCore.CAP" Version="6.0.0" />
<PackageReference Include="DotNetCore.CAP.Dashboard" Version="6.0.0" />
<PackageReference Include="DotNetCore.CAP.MongoDB" Version="6.0.0" />
<PackageReference Include="DotNetCore.CAP.OpenTelemetry" Version="6.0.0" />
<PackageReference Include="DotNetCore.CAP.RabbitMQ" Version="6.0.0" />
<PackageReference Include="DotNetCore.CAP.SqlServer" Version="6.0.0" />
<PackageReference Include="Duende.IdentityServer" Version="6.0.0" />
<PackageReference Include="Duende.IdentityServer.AspNetIdentity" Version="6.0.0" />
<PackageReference Include="Duende.IdentityServer.EntityFramework" Version="6.0.0" />
<PackageReference Include="Duende.IdentityServer.EntityFramework.Storage" Version="6.0.3" />
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.1" />
<PackageReference Include="Microsoft.AspNetCore.Identity.EntityFrameworkCore" Version="6.0.0" />
<PackageReference Include="Yarp.ReverseProxy" Version="1.0.0" />
<PackageReference Include="Microsoft.Identity.Web" Version="1.22.3" />
<PackageReference Include="Jaeger" Version="0.3.7"/>
<PackageReference Include="OpenTracing" Version="0.12.1"/>
<PackageReference Include="prometheus-net" Version="6.0.0"/>
<PackageReference Include="prometheus-net.AspNetCore" Version="6.0.0"/>
<PackageReference Include="Jaeger" Version="0.3.7" />
<PackageReference Include="OpenTracing" Version="0.12.1" />
<PackageReference Include="prometheus-net" Version="6.0.0" />
<PackageReference Include="prometheus-net.AspNetCore" Version="6.0.0" />
<PackageReference Include="OpenTelemetry" Version="1.2.0-rc3"/>
<PackageReference Include="OpenTelemetry.Exporter.Jaeger" Version="1.2.0-rc3"/>
<PackageReference Include="OpenTelemetry.Extensions.Hosting" Version="1.0.0-rc9"/>
<PackageReference Include="OpenTelemetry.Instrumentation.AspNetCore" Version="1.0.0-rc9"/>
<PackageReference Include="OpenTelemetry.Instrumentation.Http" Version="1.0.0-rc9"/>
<PackageReference Include="OpenTelemetry" Version="1.2.0-rc3" />
<PackageReference Include="OpenTelemetry.Exporter.Jaeger" Version="1.2.0-rc3" />
<PackageReference Include="OpenTelemetry.Extensions.Hosting" Version="1.0.0-rc9" />
<PackageReference Include="OpenTelemetry.Instrumentation.AspNetCore" Version="1.0.0-rc9" />
<PackageReference Include="OpenTelemetry.Instrumentation.Http" Version="1.0.0-rc9" />
<PackageReference Include="Microsoft.VisualStudio.Threading.Analyzers" Version="17.0.64">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="EventStore.Client.Grpc.Streams" Version="22.0.0"/>
<PackageReference Include="Microsoft.Extensions.Hosting" Version="6.0.1"/>
<PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="6.0.3"/>
<PackageReference Include="EventStore.Client.Grpc.Streams" Version="22.0.0" />
<PackageReference Include="Microsoft.Extensions.Hosting" Version="6.0.1" />
<PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="6.0.3" />
<PackageReference Include="Nito.AsyncEx" Version="5.1.2"/>
<PackageReference Include="AutoBogus" Version="2.13.1"/>
<PackageReference Include="Bogus" Version="34.0.1"/>
<PackageReference Include="FluentAssertions" Version="6.2.0"/>
<PackageReference Include="MediatR" Version="9.0.0"/>
<PackageReference Include="Respawn" Version="4.0.0"/>
<PackageReference Include="Nito.AsyncEx" Version="5.1.2" />
<PackageReference Include="AutoBogus" Version="2.13.1" />
<PackageReference Include="Bogus" Version="34.0.1" />
<PackageReference Include="FluentAssertions" Version="6.2.0" />
<PackageReference Include="MediatR" Version="9.0.0" />
<PackageReference Include="Respawn" Version="4.0.0" />
</ItemGroup>
<ItemGroup>
<Folder Include="Contracts"/>
<Folder Include="EventStoreDB\BackgroundWorkers"/>
<Folder Include="Contracts" />
<Folder Include="EventStoreDB\BackgroundWorkers" />
</ItemGroup>
</Project>

View File

@ -2,9 +2,8 @@ namespace BuildingBlocks.Exception;
public class AggregateNotFoundException : System.Exception
{
public AggregateNotFoundException(string typeName, long id): base($"{typeName} with id '{id}' was not found")
public AggregateNotFoundException(string typeName, long id) : base($"{typeName} with id '{id}' was not found")
{
}
public static AggregateNotFoundException For<T>(long id)

View File

@ -5,26 +5,19 @@ namespace BuildingBlocks.Exception;
public class AppException : CustomException
{
public AppException(string message, string code = default!) : base(message)
public AppException(string message, string code = null) : base(message, code: code)
{
Code = code;
}
public AppException() : base()
{
}
public AppException(string message) : base(message)
public AppException(string message, HttpStatusCode statusCode, string code = null) : base(message, statusCode, code)
{
}
public AppException(string message, HttpStatusCode statusCode) : base(message, statusCode)
public AppException(string message, System.Exception innerException, string code = null) : base(message, innerException, code: code)
{
}
public AppException(string message, System.Exception innerException) : base(message, innerException)
{
}
public string Code { get; }
}

View File

@ -4,9 +4,9 @@ namespace BuildingBlocks.Exception
{
public class BadRequestException : CustomException
{
public BadRequestException(string message) : base(message)
public BadRequestException(string message, string code = null) : base(message, code: code)
{
}
}
}
}

View File

@ -2,10 +2,8 @@ namespace BuildingBlocks.Exception
{
public class ConflictException : CustomException
{
public virtual string Code { get; }
public ConflictException(string message, string code = default!) : base(message)
public ConflictException(string message, string code = null) : base(message, code: code)
{
Code = code;
}
}
}
}

View File

@ -2,28 +2,36 @@ using System.Net;
namespace BuildingBlocks.Exception;
public class CustomException: System.Exception
public class CustomException : System.Exception
{
public CustomException(
string message,
HttpStatusCode statusCode = HttpStatusCode.BadRequest) : base(message)
HttpStatusCode statusCode = HttpStatusCode.BadRequest,
string code = null) : base(message)
{
StatusCode = statusCode;
Code = code;
}
public CustomException(
string message,
System.Exception innerException,
HttpStatusCode statusCode = HttpStatusCode.BadRequest) : base(message, innerException)
HttpStatusCode statusCode = HttpStatusCode.BadRequest,
string code = null) : base(message, innerException)
{
StatusCode = statusCode;
Code = code;
}
public CustomException(
HttpStatusCode statusCode = HttpStatusCode.BadRequest) : base()
HttpStatusCode statusCode = HttpStatusCode.BadRequest,
string code = null) : base()
{
StatusCode = statusCode;
Code = code;
}
public HttpStatusCode StatusCode { get; }
public string Code { get; }
}

View File

@ -6,13 +6,6 @@ namespace BuildingBlocks.Exception;
public class GrpcExceptionInterceptor : Interceptor
{
private readonly ILogger<GrpcExceptionInterceptor> _logger;
public GrpcExceptionInterceptor(ILogger<GrpcExceptionInterceptor> logger)
{
_logger = logger;
}
public override async Task<TResponse> UnaryServerHandler<TRequest, TResponse>(
TRequest request,
ServerCallContext context,

View File

@ -2,10 +2,10 @@ using System.Net;
namespace BuildingBlocks.Exception;
public class IdentityException: CustomException
public class IdentityException : CustomException
{
public IdentityException(string message = default, HttpStatusCode statusCode = default)
: base(message, statusCode)
public IdentityException(string message = default, HttpStatusCode statusCode = default, string code = null)
: base(message, statusCode, code)
{
}
}
}

View File

@ -1,5 +1,6 @@
using System;
using System.Globalization;
using System.Net;
namespace BuildingBlocks.Exception
{
@ -7,11 +8,11 @@ namespace BuildingBlocks.Exception
{
public InternalServerException() : base() { }
public InternalServerException(string message) : base(message) { }
public InternalServerException(string message, string code) : base(message, HttpStatusCode.InternalServerError, code: code) { }
public InternalServerException(string message, params object[] args)
: base(String.Format(CultureInfo.CurrentCulture, message, args))
public InternalServerException(string message, string code = null, params object[] args)
: base(message:String.Format(CultureInfo.CurrentCulture, message, args, HttpStatusCode.InternalServerError, code))
{
}
}
}
}

View File

@ -2,8 +2,8 @@ namespace BuildingBlocks.Exception
{
public class NotFoundException : CustomException
{
public NotFoundException(string message) : base(message)
public NotFoundException(string message, string code = null) : base(message, code: code)
{
}
}
}
}

View File

@ -0,0 +1,8 @@
using Microsoft.AspNetCore.Mvc;
namespace BuildingBlocks.Exception;
public class ProblemDetailsWithCode : ProblemDetails
{
public string Code { get; set; }
}

View File

@ -8,6 +8,7 @@ namespace BuildingBlocks.Exception
{
ValidationResultModel = validationResultModel;
}
public ValidationResultModel ValidationResultModel { get; }
}
}
}

View File

@ -22,60 +22,66 @@ public static class ProblemDetailsExtensions
var env = ctx.RequestServices.GetRequiredService<IHostEnvironment>();
return env.IsDevelopment() || env.IsStaging();
};
x.Map<ConflictException>(ex => new ProblemDetails
x.Map<ConflictException>(ex => new ProblemDetailsWithCode
{
Title = "Application rule broken",
Status = StatusCodes.Status409Conflict,
Detail = ex.Message,
Type = "https://somedomain/application-rule-validation-error"
Type = "https://somedomain/application-rule-validation-error",
Code = ex.Code
});
// Exception will produce and returns from our FluentValidation RequestValidationBehavior
x.Map<ValidationException>(ex => new ProblemDetails
x.Map<ValidationException>(ex => new ProblemDetailsWithCode
{
Title = "input validation rules broken",
Status = StatusCodes.Status400BadRequest,
Detail = JsonConvert.SerializeObject(ex.ValidationResultModel.Errors),
Type = "https://somedomain/input-validation-rules-error"
Type = "https://somedomain/input-validation-rules-error",
Code = ex.Code
});
x.Map<BadRequestException>(ex => new ProblemDetails
x.Map<BadRequestException>(ex => new ProblemDetailsWithCode
{
Title = "bad request exception",
Status = StatusCodes.Status400BadRequest,
Detail = ex.Message,
Type = "https://somedomain/bad-request-error"
Type = "https://somedomain/bad-request-error",
Code = ex.Code
});
x.Map<NotFoundException>(ex => new ProblemDetails
x.Map<NotFoundException>(ex => new ProblemDetailsWithCode
{
Title = "not found exception",
Status = StatusCodes.Status404NotFound,
Detail = ex.Message,
Type = "https://somedomain/not-found-error"
Type = "https://somedomain/not-found-error",
Code = ex.Code
});
x.Map<InternalServerException>(ex => new ProblemDetails
x.Map<InternalServerException>(ex => new ProblemDetailsWithCode
{
Title = "api server exception",
Status = StatusCodes.Status500InternalServerError,
Detail = ex.Message,
Type = "https://somedomain/api-server-error"
Type = "https://somedomain/api-server-error",
Code = ex.Code
});
x.Map<AppException>(ex => new ProblemDetails
x.Map<AppException>(ex => new ProblemDetailsWithCode
{
Title = "application exception",
Status = StatusCodes.Status500InternalServerError,
Detail = ex.Message,
Type = "https://somedomain/application-error"
Type = "https://somedomain/application-error",
Code = ex.Code
});
x.Map<IdentityException>(ex =>
{
var pd = new ProblemDetails
var pd = new ProblemDetailsWithCode
{
Status = (int)ex.StatusCode,
Title = "identity exception",
Detail = ex.Message,
Type = "https://somedomain/identity-error"
Type = "https://somedomain/identity-error",
Code = ex.Code
};
return pd;
});
x.MapToStatusCode<ArgumentNullException>(StatusCodes.Status400BadRequest);

View File

@ -0,0 +1,14 @@
using Flight.Flights.Features.CreateFlight;
namespace Integration.Test.Fakes;
public static class FakeFlightCreated
{
public static global::Flight.Flights.Models.Flight Generate(CreateFlightCommand command)
{
return global::Flight.Flights.Models.Flight.Create(command.Id, command.FlightNumber,
command.AircraftId, command.DepartureAirportId, command.DepartureDate,
command.ArriveDate, command.ArriveAirportId, command.DurationMinutes,
command.FlightDate, command.Status, command.Price);
}
}

View File

@ -24,13 +24,8 @@ public class GetAvailableFlightsTests
var flightCommand1 = new FakeCreateFlightCommand().Generate();
var flightCommand2 = new FakeCreateFlightCommand().Generate();
var flightEntity1 = global::Flight.Flights.Models.Flight.Create(
flightCommand1.Id, flightCommand1.FlightNumber, flightCommand1.AircraftId, flightCommand1.DepartureAirportId, flightCommand1.DepartureDate,
flightCommand1.ArriveDate, flightCommand1.ArriveAirportId, flightCommand1.DurationMinutes, flightCommand1.FlightDate, flightCommand1.Status, flightCommand1.Price);
var flightEntity2 = global::Flight.Flights.Models.Flight.Create(
flightCommand2.Id, flightCommand2.FlightNumber, flightCommand2.AircraftId, flightCommand2.DepartureAirportId, flightCommand2.DepartureDate,
flightCommand2.ArriveDate, flightCommand2.ArriveAirportId, flightCommand2.DurationMinutes, flightCommand2.FlightDate, flightCommand2.Status, flightCommand2.Price);
var flightEntity1 = FakeFlightCreated.Generate(flightCommand1);
var flightEntity2 = FakeFlightCreated.Generate(flightCommand2);
await _fixture.InsertAsync(flightEntity1, flightEntity2);

View File

@ -21,9 +21,7 @@ public class GetFlightByIdTests
{
// Arrange
var command = new FakeCreateFlightCommand().Generate();
var flightEntity = global::Flight.Flights.Models.Flight.Create(
command.Id, command.FlightNumber, command.AircraftId, command.DepartureAirportId, command.DepartureDate,
command.ArriveDate, command.ArriveAirportId, command.DurationMinutes, command.FlightDate, command.Status, command.Price);
var flightEntity = FakeFlightCreated.Generate(command);
await _fixture.InsertAsync(flightEntity);
var query = new GetFlightByIdQuery(flightEntity.Id);

View File

@ -25,10 +25,7 @@ public class UpdateFlightTests
{
// Arrange
var fakeCreateCommandFlight = new FakeCreateFlightCommand().Generate();
var flightEntity = global::Flight.Flights.Models.Flight.Create(fakeCreateCommandFlight.Id, fakeCreateCommandFlight.FlightNumber,
fakeCreateCommandFlight.AircraftId, fakeCreateCommandFlight.DepartureAirportId, fakeCreateCommandFlight.DepartureDate,
fakeCreateCommandFlight.ArriveDate, fakeCreateCommandFlight.ArriveAirportId, fakeCreateCommandFlight.DurationMinutes,
fakeCreateCommandFlight.FlightDate, fakeCreateCommandFlight.Status, fakeCreateCommandFlight.Price);
var flightEntity = FakeFlightCreated.Generate(fakeCreateCommandFlight);
await _fixture.InsertAsync(flightEntity);
var command = new FakeUpdateFlightCommand(flightEntity.Id).Generate();

View File

@ -6,10 +6,10 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.Mvc" Version="2.2.0"/>
<PackageReference Include="Microsoft.AspNetCore.Mvc.Testing" Version="6.0.4"/>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.0.0"/>
<PackageReference Include="xunit" Version="2.4.1"/>
<PackageReference Include="Microsoft.AspNetCore.Mvc" Version="2.2.0" />
<PackageReference Include="Microsoft.AspNetCore.Mvc.Testing" Version="6.0.4" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.0.0" />
<PackageReference Include="xunit" Version="2.4.1" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.4.3">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>

View File

@ -1,98 +0,0 @@
// <auto-generated />
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
using Passenger.Data;
#nullable disable
namespace Passenger.Data.Migrations
{
[DbContext(typeof(PassengerDbContext))]
[Migration("20220309230648_initial")]
partial class initial
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder
.HasAnnotation("ProductVersion", "6.0.1")
.HasAnnotation("Relational:MaxIdentifierLength", 128);
SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder, 1L, 1);
modelBuilder.Entity("BuildingBlocks.Outbox.OutboxMessage", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<Guid?>("CorrelationId")
.HasColumnType("uniqueidentifier");
b.Property<string>("Data")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<string>("EventType")
.IsRequired()
.HasMaxLength(50)
.IsUnicode(false)
.HasColumnType("varchar(50)");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<DateTime>("OccurredOn")
.HasColumnType("datetime2");
b.Property<DateTime?>("ProcessedOn")
.HasColumnType("datetime2");
b.Property<string>("Type")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.HasKey("Id");
b.ToTable("OutboxMessages", (string)null);
});
modelBuilder.Entity("Passenger.Passenger.Models.Passenger", b =>
{
b.Property<long>("Id")
.HasColumnType("bigint");
b.Property<int>("Age")
.HasColumnType("int");
b.Property<bool>("IsDeleted")
.HasColumnType("bit");
b.Property<DateTime>("LastModified")
.HasColumnType("datetime2");
b.Property<int?>("ModifiedBy")
.HasColumnType("int");
b.Property<string>("Name")
.HasColumnType("nvarchar(max)");
b.Property<int>("PassengerType")
.HasColumnType("int");
b.Property<string>("PassportNumber")
.HasColumnType("nvarchar(max)");
b.HasKey("Id");
b.ToTable("Passenger", "dbo");
});
#pragma warning restore 612, 618
}
}
}

View File

@ -1,85 +0,0 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace Passenger.Data.Migrations
{
public partial class Audit : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.RenameColumn(
name: "ModifiedBy",
schema: "dbo",
table: "Passenger",
newName: "LastModifiedBy");
migrationBuilder.AlterColumn<DateTime>(
name: "LastModified",
schema: "dbo",
table: "Passenger",
type: "datetime2",
nullable: true,
oldClrType: typeof(DateTime),
oldType: "datetime2");
migrationBuilder.AddColumn<DateTime>(
name: "CreatedAt",
schema: "dbo",
table: "Passenger",
type: "datetime2",
nullable: true);
migrationBuilder.AddColumn<int>(
name: "CreatedBy",
schema: "dbo",
table: "Passenger",
type: "int",
nullable: true);
migrationBuilder.AddColumn<long>(
name: "Version",
schema: "dbo",
table: "Passenger",
type: "bigint",
nullable: false,
defaultValue: 0L);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "CreatedAt",
schema: "dbo",
table: "Passenger");
migrationBuilder.DropColumn(
name: "CreatedBy",
schema: "dbo",
table: "Passenger");
migrationBuilder.DropColumn(
name: "Version",
schema: "dbo",
table: "Passenger");
migrationBuilder.RenameColumn(
name: "LastModifiedBy",
schema: "dbo",
table: "Passenger",
newName: "ModifiedBy");
migrationBuilder.AlterColumn<DateTime>(
name: "LastModified",
schema: "dbo",
table: "Passenger",
type: "datetime2",
nullable: false,
defaultValue: new DateTime(1, 1, 1, 0, 0, 0, 0, DateTimeKind.Unspecified),
oldClrType: typeof(DateTime),
oldType: "datetime2",
oldNullable: true);
}
}
}

View File

@ -1,139 +0,0 @@
// <auto-generated />
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
using Passenger.Data;
#nullable disable
namespace Passenger.Data.Migrations
{
[DbContext(typeof(PassengerDbContext))]
[Migration("20220422175724_Update-EventId")]
partial class UpdateEventId
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder
.HasAnnotation("ProductVersion", "6.0.1")
.HasAnnotation("Relational:MaxIdentifierLength", 128);
SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder, 1L, 1);
modelBuilder.Entity("BuildingBlocks.InternalProcessor.InternalMessage", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<string>("CommandType")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<Guid?>("CorrelationId")
.HasColumnType("uniqueidentifier");
b.Property<string>("Data")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<DateTime>("OccurredOn")
.HasColumnType("datetime2");
b.Property<DateTime?>("ProcessedOn")
.HasColumnType("datetime2");
b.HasKey("EventId");
b.ToTable("InternalMessages", (string)null);
});
modelBuilder.Entity("BuildingBlocks.Outbox.OutboxMessage", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<Guid?>("CorrelationId")
.HasColumnType("uniqueidentifier");
b.Property<string>("Data")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<string>("EventType")
.IsRequired()
.HasMaxLength(50)
.IsUnicode(false)
.HasColumnType("varchar(50)");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<DateTime>("OccurredOn")
.HasColumnType("datetime2");
b.Property<DateTime?>("ProcessedOn")
.HasColumnType("datetime2");
b.Property<string>("Type")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.HasKey("EventId");
b.ToTable("OutboxMessages", (string)null);
});
modelBuilder.Entity("Passenger.Passengers.Models.Passenger", b =>
{
b.Property<long>("Id")
.HasColumnType("bigint");
b.Property<int>("Age")
.HasColumnType("int");
b.Property<DateTime?>("CreatedAt")
.HasColumnType("datetime2");
b.Property<long?>("CreatedBy")
.HasColumnType("bigint");
b.Property<bool>("IsDeleted")
.HasColumnType("bit");
b.Property<DateTime?>("LastModified")
.HasColumnType("datetime2");
b.Property<long?>("LastModifiedBy")
.HasColumnType("bigint");
b.Property<string>("Name")
.HasColumnType("nvarchar(max)");
b.Property<int>("PassengerType")
.HasColumnType("int");
b.Property<string>("PassportNumber")
.HasColumnType("nvarchar(max)");
b.Property<long>("Version")
.HasColumnType("bigint");
b.HasKey("Id");
b.ToTable("Passenger", "dbo");
});
#pragma warning restore 612, 618
}
}
}

View File

@ -1,86 +0,0 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace Passenger.Data.Migrations
{
public partial class UpdateEventId : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.RenameColumn(
name: "Id",
table: "OutboxMessages",
newName: "EventId");
migrationBuilder.AlterColumn<long>(
name: "LastModifiedBy",
schema: "dbo",
table: "Passenger",
type: "bigint",
nullable: true,
oldClrType: typeof(int),
oldType: "int",
oldNullable: true);
migrationBuilder.AlterColumn<long>(
name: "CreatedBy",
schema: "dbo",
table: "Passenger",
type: "bigint",
nullable: true,
oldClrType: typeof(int),
oldType: "int",
oldNullable: true);
migrationBuilder.CreateTable(
name: "InternalMessages",
columns: table => new
{
EventId = table.Column<Guid>(type: "uniqueidentifier", nullable: false),
Name = table.Column<string>(type: "nvarchar(max)", nullable: false),
OccurredOn = table.Column<DateTime>(type: "datetime2", nullable: false),
CommandType = table.Column<string>(type: "nvarchar(max)", nullable: false),
Data = table.Column<string>(type: "nvarchar(max)", nullable: false),
ProcessedOn = table.Column<DateTime>(type: "datetime2", nullable: true),
CorrelationId = table.Column<Guid>(type: "uniqueidentifier", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("PK_InternalMessages", x => x.EventId);
});
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "InternalMessages");
migrationBuilder.RenameColumn(
name: "EventId",
table: "OutboxMessages",
newName: "Id");
migrationBuilder.AlterColumn<int>(
name: "LastModifiedBy",
schema: "dbo",
table: "Passenger",
type: "int",
nullable: true,
oldClrType: typeof(long),
oldType: "bigint",
oldNullable: true);
migrationBuilder.AlterColumn<int>(
name: "CreatedBy",
schema: "dbo",
table: "Passenger",
type: "int",
nullable: true,
oldClrType: typeof(long),
oldType: "bigint",
oldNullable: true);
}
}
}

View File

@ -12,8 +12,8 @@ using Passenger.Data;
namespace Passenger.Data.Migrations
{
[DbContext(typeof(PassengerDbContext))]
[Migration("20220416172933_Audit")]
partial class Audit
[Migration("20220523195643_initial")]
partial class initial
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
@ -24,44 +24,6 @@ namespace Passenger.Data.Migrations
SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder, 1L, 1);
modelBuilder.Entity("BuildingBlocks.Outbox.OutboxMessage", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<Guid?>("CorrelationId")
.HasColumnType("uniqueidentifier");
b.Property<string>("Data")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<string>("EventType")
.IsRequired()
.HasMaxLength(50)
.IsUnicode(false)
.HasColumnType("varchar(50)");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<DateTime>("OccurredOn")
.HasColumnType("datetime2");
b.Property<DateTime?>("ProcessedOn")
.HasColumnType("datetime2");
b.Property<string>("Type")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.HasKey("Id");
b.ToTable("OutboxMessages", (string)null);
});
modelBuilder.Entity("Passenger.Passengers.Models.Passenger", b =>
{
b.Property<long>("Id")
@ -73,8 +35,8 @@ namespace Passenger.Data.Migrations
b.Property<DateTime?>("CreatedAt")
.HasColumnType("datetime2");
b.Property<int?>("CreatedBy")
.HasColumnType("int");
b.Property<long?>("CreatedBy")
.HasColumnType("bigint");
b.Property<bool>("IsDeleted")
.HasColumnType("bit");
@ -82,8 +44,8 @@ namespace Passenger.Data.Migrations
b.Property<DateTime?>("LastModified")
.HasColumnType("datetime2");
b.Property<int?>("LastModifiedBy")
.HasColumnType("int");
b.Property<long?>("LastModifiedBy")
.HasColumnType("bigint");
b.Property<string>("Name")
.HasColumnType("nvarchar(max)");

View File

@ -12,24 +12,6 @@ namespace Passenger.Data.Migrations
migrationBuilder.EnsureSchema(
name: "dbo");
migrationBuilder.CreateTable(
name: "OutboxMessages",
columns: table => new
{
Id = table.Column<Guid>(type: "uniqueidentifier", nullable: false),
Name = table.Column<string>(type: "nvarchar(max)", nullable: false),
OccurredOn = table.Column<DateTime>(type: "datetime2", nullable: false),
Type = table.Column<string>(type: "nvarchar(max)", nullable: false),
Data = table.Column<string>(type: "nvarchar(max)", nullable: false),
ProcessedOn = table.Column<DateTime>(type: "datetime2", nullable: true),
EventType = table.Column<string>(type: "varchar(50)", unicode: false, maxLength: 50, nullable: false),
CorrelationId = table.Column<Guid>(type: "uniqueidentifier", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("PK_OutboxMessages", x => x.Id);
});
migrationBuilder.CreateTable(
name: "Passenger",
schema: "dbo",
@ -40,9 +22,12 @@ namespace Passenger.Data.Migrations
Name = table.Column<string>(type: "nvarchar(max)", nullable: true),
PassengerType = table.Column<int>(type: "int", nullable: false),
Age = table.Column<int>(type: "int", nullable: false),
LastModified = table.Column<DateTime>(type: "datetime2", nullable: false),
CreatedAt = table.Column<DateTime>(type: "datetime2", nullable: true),
CreatedBy = table.Column<long>(type: "bigint", nullable: true),
LastModified = table.Column<DateTime>(type: "datetime2", nullable: true),
LastModifiedBy = table.Column<long>(type: "bigint", nullable: true),
IsDeleted = table.Column<bool>(type: "bit", nullable: false),
ModifiedBy = table.Column<int>(type: "int", nullable: true)
Version = table.Column<long>(type: "bigint", nullable: false)
},
constraints: table =>
{
@ -52,9 +37,6 @@ namespace Passenger.Data.Migrations
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "OutboxMessages");
migrationBuilder.DropTable(
name: "Passenger",
schema: "dbo");

View File

@ -22,76 +22,6 @@ namespace Passenger.Data.Migrations
SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder, 1L, 1);
modelBuilder.Entity("BuildingBlocks.InternalProcessor.InternalMessage", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<string>("CommandType")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<Guid?>("CorrelationId")
.HasColumnType("uniqueidentifier");
b.Property<string>("Data")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<DateTime>("OccurredOn")
.HasColumnType("datetime2");
b.Property<DateTime?>("ProcessedOn")
.HasColumnType("datetime2");
b.HasKey("EventId");
b.ToTable("InternalMessages", (string)null);
});
modelBuilder.Entity("BuildingBlocks.Outbox.OutboxMessage", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<Guid?>("CorrelationId")
.HasColumnType("uniqueidentifier");
b.Property<string>("Data")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<string>("EventType")
.IsRequired()
.HasMaxLength(50)
.IsUnicode(false)
.HasColumnType("varchar(50)");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.Property<DateTime>("OccurredOn")
.HasColumnType("datetime2");
b.Property<DateTime?>("ProcessedOn")
.HasColumnType("datetime2");
b.Property<string>("Type")
.IsRequired()
.HasColumnType("nvarchar(max)");
b.HasKey("EventId");
b.ToTable("OutboxMessages", (string)null);
});
modelBuilder.Entity("Passenger.Passengers.Models.Passenger", b =>
{
b.Property<long>("Id")

View File

@ -19,7 +19,7 @@ public class RegisterNewUserConsumerHandler : IConsumer<UserCreated>
{
Guard.Against.Null(context.Message, nameof(UserCreated));
var passenger = Passengers.Models.Passenger.Create(context.Message.Id, context.Message.Name, context.Message.PassportNumber);
var passenger = Passengers.Models.Passenger.Create(SnowFlakIdGenerator.NewId(), context.Message.Name, context.Message.PassportNumber);
await _passengerDbContext.AddAsync(passenger);

View File

@ -13,12 +13,12 @@
</ItemGroup>
<ItemGroup>
<Folder Include="Data\Migrations"/>
<Folder Include="Extensions"/>
<Folder Include="Data\Migrations" />
<Folder Include="Extensions" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\..\..\..\BuildingBlocks\BuildingBlocks.csproj"/>
<ProjectReference Include="..\..\..\..\BuildingBlocks\BuildingBlocks.csproj" />
</ItemGroup>
</Project>

View File

@ -1,8 +1,11 @@
using BuildingBlocks.IdsGenerator;
using MediatR;
using Passenger.Passengers.Dtos;
using Passenger.Passengers.Models;
namespace Passenger.Passengers.Features.CompleteRegisterPassenger;
public record CompleteRegisterPassengerCommand
(string PassportNumber, PassengerType PassengerType, int Age) : IRequest<PassengerResponseDto>;
public record CompleteRegisterPassengerCommand(string PassportNumber, PassengerType PassengerType, int Age) : IRequest<PassengerResponseDto>
{
public long Id { get; set; } = SnowFlakIdGenerator.NewId();
}

View File

@ -24,8 +24,7 @@ public class CompleteRegisterPassengerCommandHandler : IRequestHandler<CompleteR
Guard.Against.Null(command, nameof(command));
var passenger = await _passengerDbContext.Passengers.AsNoTracking().SingleOrDefaultAsync(
x => x.PassportNumber == command.PassportNumber,
cancellationToken);
x => x.PassportNumber == command.PassportNumber, cancellationToken);
if (passenger is null)
throw new PassengerNotExist();

View File

@ -0,0 +1,18 @@
using AutoBogus;
using BuildingBlocks.IdsGenerator;
using Passenger.Passengers.Features.CompleteRegisterPassenger;
using Passenger.Passengers.Models;
namespace Integration.Test.Fakes;
public sealed class FakeCompleteRegisterPassengerCommand : AutoFaker<CompleteRegisterPassengerCommand>
{
public FakeCompleteRegisterPassengerCommand(string passportNumber)
{
RuleFor(r => r.Id, _ => SnowFlakIdGenerator.NewId());
RuleFor(r => r.PassportNumber, _ => passportNumber);
RuleFor(r => r.PassengerType, _ => PassengerType.Male);
RuleFor(r => r.Age, _ => 30);
}
}

View File

@ -0,0 +1,12 @@
using BuildingBlocks.Contracts.EventBus.Messages;
using BuildingBlocks.IdsGenerator;
namespace Integration.Test.Fakes;
public static class FakePassengerCreated
{
public static global::Passenger.Passengers.Models.Passenger Generate(UserCreated userCreated)
{
return global::Passenger.Passengers.Models.Passenger.Create(SnowFlakIdGenerator.NewId(), userCreated.Name, userCreated.PassportNumber);
}
}

View File

@ -0,0 +1,15 @@
using AutoBogus;
using BuildingBlocks.Contracts.EventBus.Messages;
using BuildingBlocks.IdsGenerator;
namespace Integration.Test.Fakes;
public class FakeUserCreated : AutoFaker<UserCreated>
{
public FakeUserCreated()
{
RuleFor(r => r.Id, _ => SnowFlakIdGenerator.NewId());
RuleFor(r => r.Name, _ => "Meysam");
RuleFor(r => r.PassportNumber, _ => "1299878");
}
}

View File

@ -0,0 +1,33 @@
using System.Threading.Tasks;
using BuildingBlocks.Contracts.EventBus.Messages;
using Integration.Test.Fakes;
using MassTransit.Testing;
using Xunit;
namespace Integration.Test.Identity.Features;
[Collection(nameof(TestFixture))]
public class RegisterNewUserConsumerTests
{
private readonly TestFixture _fixture;
private readonly ITestHarness _testHarness;
public RegisterNewUserConsumerTests(TestFixture fixture)
{
_fixture = fixture;
_testHarness = _fixture.TestHarness;
}
[Fact]
public async Task should_register_new_user_consume_handler_consume_user_created_message()
{
// // Arrange
var message = new FakeUserCreated().Generate();
// // Act
await _testHarness.Bus.Publish(message);
// // Assert
await _testHarness.Consumed.Any<UserCreated>();
}
}

View File

@ -8,10 +8,10 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.Mvc" Version="2.2.0"/>
<PackageReference Include="Microsoft.AspNetCore.Mvc.Testing" Version="6.0.4"/>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.0.0"/>
<PackageReference Include="xunit" Version="2.4.1"/>
<PackageReference Include="Microsoft.AspNetCore.Mvc" Version="2.2.0" />
<PackageReference Include="Microsoft.AspNetCore.Mvc.Testing" Version="6.0.4" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.0.0" />
<PackageReference Include="xunit" Version="2.4.1" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.4.3">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
@ -26,9 +26,4 @@
<ProjectReference Include="..\..\src\Passenger.Api\Passenger.Api.csproj" />
</ItemGroup>
<ItemGroup>
<Folder Include="Fakes" />
<Folder Include="Passenger\Features" />
</ItemGroup>
</Project>

View File

@ -0,0 +1,45 @@
using System.Threading.Tasks;
using BuildingBlocks.Contracts.EventBus.Messages;
using BuildingBlocks.IdsGenerator;
using FluentAssertions;
using Integration.Test.Fakes;
using MassTransit;
using MassTransit.Testing;
using Xunit;
namespace Integration.Test.Passenger.Features;
[Collection(nameof(TestFixture))]
public class CompleteRegisterPassengerTests
{
private readonly TestFixture _fixture;
private readonly ITestHarness _testHarness;
public CompleteRegisterPassengerTests(TestFixture fixture)
{
_fixture = fixture;
_testHarness = _fixture.TestHarness;
}
[Fact]
public async Task should_complete_register_passenger_and_update_to_db()
{
// Arrange
var userCreated = new FakeUserCreated().Generate();
await _testHarness.Bus.Publish(userCreated);
await _testHarness.Consumed.Any<UserCreated>();
await _fixture.InsertAsync(FakePassengerCreated.Generate(userCreated));
var command = new FakeCompleteRegisterPassengerCommand(userCreated.PassportNumber).Generate();
// Act
var response = await _fixture.SendAsync(command);
// Assert
response.Should().NotBeNull();
response?.Name.Should().Be(userCreated.Name);
response?.PassportNumber.Should().Be(command.PassportNumber);
response?.PassengerType.Should().Be(command.PassengerType);
response?.Age.Should().Be(command.Age);
}
}

View File

@ -0,0 +1,42 @@
using System.Threading.Tasks;
using BuildingBlocks.Contracts.EventBus.Messages;
using FluentAssertions;
using Integration.Test.Fakes;
using MassTransit.Testing;
using Passenger.Passengers.Features.GetPassengerById;
using Xunit;
namespace Integration.Test.Passenger.Features;
[Collection(nameof(TestFixture))]
public class GetPassengerByIdTests
{
private readonly TestFixture _fixture;
private readonly ITestHarness _testHarness;
public GetPassengerByIdTests(TestFixture fixture)
{
_fixture = fixture;
_testHarness = _fixture.TestHarness;
}
[Fact]
public async Task should_retrive_a_passenger_by_id_currectly()
{
// Arrange
var userCreated = new FakeUserCreated().Generate();
await _testHarness.Bus.Publish(userCreated);
await _testHarness.Consumed.Any<UserCreated>();
var passengerEntity = FakePassengerCreated.Generate(userCreated);
await _fixture.InsertAsync(passengerEntity);
var query = new GetPassengerQueryById(passengerEntity.Id);
// Act
var response = await _fixture.SendAsync(query);
// Assert
response.Should().NotBeNull();
response?.Id.Should().Be(passengerEntity.Id);
}
}

View File

@ -1,12 +0,0 @@
using Xunit;
namespace Integration.Test;
public class UnitTest1
{
[Fact]
public void Test1()
{
}
}