Skip to content
This repository was archived by the owner on Aug 1, 2021. It is now read-only.

Commit bc035ab

Browse files
committed
Client tests
1 parent 043d1b1 commit bc035ab

File tree

18 files changed

+1165
-643
lines changed

18 files changed

+1165
-643
lines changed

CHANGELOG.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
# v.1.2.1
1+
# v1.2.2
2+
3+
Added ENV for Default User and Pass, to autofill Login Page. Specially made for Dev and Docker environments
4+
5+
# v1.2.1
26

37
Now the components is available through Docker Hub.
48
* Generated docker install file to easy test

src/Backend/Jp.Domain.Core/Commands/Command.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,11 @@
11
using System;
22
using FluentValidation.Results;
33
using Jp.Domain.Core.Events;
4+
using MediatR;
45

56
namespace Jp.Domain.Core.Commands
67
{
7-
public abstract class Command : Message
8+
public abstract class Command : Message, IRequest<bool>
89
{
910
public DateTime Timestamp { get; private set; }
1011
public ValidationResult ValidationResult { get; set; }

src/Backend/Jp.Domain/CommandHandlers/ClientCommandHandler.cs

Lines changed: 21 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
using IdentityServer4.EntityFramework.Entities;
22
using IdentityServer4.EntityFramework.Mappers;
3-
using IdentityServer4.Models;
43
using Jp.Domain.Commands.Client;
54
using Jp.Domain.Core.Bus;
65
using Jp.Domain.Core.Notifications;
@@ -17,15 +16,15 @@ namespace Jp.Domain.CommandHandlers
1716
{
1817
public class ClientCommandHandler : CommandHandler,
1918
IRequestHandler<RemoveClientCommand>,
20-
IRequestHandler<UpdateClientCommand>,
19+
IRequestHandler<UpdateClientCommand, bool>,
2120
IRequestHandler<RemoveClientSecretCommand>,
2221
IRequestHandler<SaveClientSecretCommand>,
2322
IRequestHandler<RemovePropertyCommand>,
2423
IRequestHandler<SaveClientPropertyCommand>,
2524
IRequestHandler<RemoveClientClaimCommand>,
2625
IRequestHandler<SaveClientClaimCommand>,
27-
IRequestHandler<SaveClientCommand>,
28-
IRequestHandler<CopyClientCommand>
26+
IRequestHandler<SaveClientCommand, bool>,
27+
IRequestHandler<CopyClientCommand, bool>
2928
{
3029
private readonly IClientRepository _clientRepository;
3130
private readonly IClientSecretRepository _clientSecretRepository;
@@ -69,19 +68,19 @@ public async Task Handle(RemoveClientCommand request, CancellationToken cancella
6968
}
7069
}
7170

72-
public async Task Handle(UpdateClientCommand request, CancellationToken cancellationToken)
71+
public async Task<bool> Handle(UpdateClientCommand request, CancellationToken cancellationToken)
7372
{
7473
if (!request.IsValid())
7574
{
7675
NotifyValidationErrors(request);
77-
return;
76+
return false;
7877
}
7978

8079
var savedClient = await _clientRepository.GetClient(request.Client.ClientId);
8180
if (savedClient == null)
8281
{
8382
await Bus.RaiseEvent(new DomainNotification("1", "Client not found"));
84-
return;
83+
return false;
8584
}
8685

8786
var client = request.Client.ToEntity();
@@ -91,7 +90,9 @@ public async Task Handle(UpdateClientCommand request, CancellationToken cancella
9190
if (Commit())
9291
{
9392
await Bus.RaiseEvent(new ClientUpdatedEvent(request));
93+
return true;
9494
}
95+
return false;
9596

9697
}
9798

@@ -275,19 +276,19 @@ public async Task Handle(SaveClientClaimCommand request, CancellationToken cance
275276
}
276277
}
277278

278-
public async Task Handle(SaveClientCommand request, CancellationToken cancellationToken)
279+
public async Task<bool> Handle(SaveClientCommand request, CancellationToken cancellationToken)
279280
{
280281
if (!request.IsValid())
281282
{
282283
NotifyValidationErrors(request);
283-
return;
284+
return false;
284285
}
285286

286287
var savedClient = await _clientRepository.GetByClientId(request.Client.ClientId);
287288
if (savedClient != null)
288289
{
289290
await Bus.RaiseEvent(new DomainNotification("1", "Client already exists"));
290-
return;
291+
return false;
291292
}
292293

293294
var client = request.ToEntity();
@@ -297,24 +298,27 @@ public async Task Handle(SaveClientCommand request, CancellationToken cancellati
297298
if (Commit())
298299
{
299300
await Bus.RaiseEvent(new NewClientEvent(request.Client.ClientId, request.ClientType, request.Client.ClientName));
301+
return true;
300302
}
303+
304+
return false;
301305
}
302306

303-
304307

305-
public async Task Handle(CopyClientCommand request, CancellationToken cancellationToken)
308+
309+
public async Task<bool> Handle(CopyClientCommand request, CancellationToken cancellationToken)
306310
{
307311
if (!request.IsValid())
308312
{
309313
NotifyValidationErrors(request);
310-
return;
314+
return false;
311315
}
312316

313317
var savedClient = await _clientRepository.GetByClientId(request.Client.ClientId);
314318
if (savedClient == null)
315319
{
316320
await Bus.RaiseEvent(new DomainNotification("1", "Client not found"));
317-
return;
321+
return false;
318322
}
319323

320324
var copyOf = savedClient.ToModel();
@@ -328,7 +332,10 @@ public async Task Handle(CopyClientCommand request, CancellationToken cancellati
328332
if (Commit())
329333
{
330334
await Bus.RaiseEvent(new ClientClonedEvent(request.Client.ClientId, newClient.ClientId));
335+
return true;
331336
}
337+
338+
return false;
332339
}
333340
}
334341

src/Backend/Jp.Domain/Commands/Client/SaveClientCommand.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
using IdentityServer4.Models;
33
using Jp.Domain.Validations.Client;
44
using System;
5+
using MediatR;
56

67
namespace Jp.Domain.Commands.Client
78
{

src/Backend/Jp.Domain/Validations/Client/ClientValidations.cs

Lines changed: 40 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,54 @@
1-
using System;
21
using FluentValidation;
2+
using IdentityServer4.Models;
33
using Jp.Domain.Commands.Client;
4+
using System;
5+
using System.Collections.Generic;
6+
using System.Linq;
47

58
namespace Jp.Domain.Validations.Client
69
{
710
public abstract class ClientValidation<T> : AbstractValidator<T> where T : ClientCommand
811
{
912
protected void ValidateGrantType()
1013
{
14+
var message = string.Empty;
1115
RuleFor(c => c.Client.AllowedGrantTypes)
12-
.NotEmpty();
16+
.NotEmpty().WithMessage("At Least 1 grant type must be selected")
17+
.Must(m => ValidateGrantCombination(m, out message)).WithMessage(message);
18+
1319
}
20+
21+
private bool ValidateGrantCombination(ICollection<string> grantTypes, out string message)
22+
{
23+
message = "Grant types list cannot contain both {0} and {1}";
24+
25+
// would allow response_type downgrade attack from code to token
26+
if (DisallowGrantTypeCombination(GrantType.Implicit, GrantType.AuthorizationCode, grantTypes))
27+
{
28+
message = string.Format(message, GrantType.Implicit, GrantType.AuthorizationCode);
29+
return false;
30+
}
31+
32+
if (DisallowGrantTypeCombination(GrantType.Implicit, GrantType.Hybrid, grantTypes))
33+
{
34+
message = string.Format(message, GrantType.Implicit, GrantType.Hybrid);
35+
return false;
36+
}
37+
38+
if (DisallowGrantTypeCombination(GrantType.AuthorizationCode, GrantType.Hybrid, grantTypes))
39+
{
40+
message = string.Format(message, GrantType.AuthorizationCode, GrantType.Hybrid);
41+
return false;
42+
}
43+
44+
return true;
45+
}
46+
private bool DisallowGrantTypeCombination(string value1, string value2, IEnumerable<string> grantTypes)
47+
{
48+
return grantTypes.Contains(value1, StringComparer.Ordinal) &&
49+
grantTypes.Contains(value2, StringComparer.Ordinal);
50+
}
51+
1452
protected void ValidateClientId()
1553
{
1654
RuleFor(c => c.Client.ClientId).NotEmpty().WithMessage("ClientId must be set");

src/Backend/Jp.Domain/Validations/Client/SaveClientCommandValidation.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ public SaveClientCommandValidation()
88
{
99
ValidateClientId();
1010
ValidateClientName();
11+
1112
}
1213
}
1314
}

src/Backend/Jp.Infra.CrossCutting.IoC/DomainCommandsBootStrapper.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -51,15 +51,15 @@ public static void RegisterServices(IServiceCollection services)
5151
* Client commands
5252
*/
5353
services.AddScoped<IRequestHandler<RemoveClientCommand>, ClientCommandHandler>();
54-
services.AddScoped<IRequestHandler<UpdateClientCommand>, ClientCommandHandler>();
54+
services.AddScoped<IRequestHandler<UpdateClientCommand, bool>, ClientCommandHandler>();
5555
services.AddScoped<IRequestHandler<RemoveClientSecretCommand>, ClientCommandHandler>();
5656
services.AddScoped<IRequestHandler<SaveClientSecretCommand>, ClientCommandHandler>();
5757
services.AddScoped<IRequestHandler<RemovePropertyCommand>, ClientCommandHandler>();
5858
services.AddScoped<IRequestHandler<SaveClientPropertyCommand>, ClientCommandHandler>();
5959
services.AddScoped<IRequestHandler<RemoveClientClaimCommand>, ClientCommandHandler>();
6060
services.AddScoped<IRequestHandler<SaveClientClaimCommand>, ClientCommandHandler>();
61-
services.AddScoped<IRequestHandler<SaveClientCommand>, ClientCommandHandler>();
62-
services.AddScoped<IRequestHandler<CopyClientCommand>, ClientCommandHandler>();
61+
services.AddScoped<IRequestHandler<SaveClientCommand, bool>, ClientCommandHandler>();
62+
services.AddScoped<IRequestHandler<CopyClientCommand, bool>, ClientCommandHandler>();
6363

6464
/*
6565
* Regiser commands

src/Frontend/Jp.AdminUI/package-lock.json

Lines changed: 3 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/Frontend/Jp.UI.SSO/Properties/launchSettings.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,9 @@
1919
"environmentVariables": {
2020
"ASPNETCORE_URLS": "http://localhost:5000;https://localhost:5001",
2121
"ASPNETCORE_ENVIRONMENT": "Development",
22-
"APPINSIGHTS_INSTRUMENTATIONKEY": "205fabcd-09ee-46f5-bb74-95780fc873da"
22+
"APPINSIGHTS_INSTRUMENTATIONKEY": "205fabcd-09ee-46f5-bb74-95780fc873da",
23+
"DEFAULT_USER": "bruno",
24+
"DEFAULT_PASS": "Pa$$word123"
2325
},
2426
"applicationUrl": "http://localhost:5000;https://localhost:5001"
2527
}

src/Frontend/Jp.UI.SSO/Views/Account/Login.cshtml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,15 +24,15 @@
2424
<i class="icon-user"></i>
2525
</span>
2626
</div>
27-
<input class="form-control" placeholder="Username" value="bruno" asp-for=Username autofocus>
27+
<input class="form-control" placeholder="Username" value="@Environment.GetEnvironmentVariable("DEFAULT_USER")" asp-for=Username autofocus>
2828
</div>
2929
<div class="input-group mb-4">
3030
<div class="input-group-prepend">
3131
<span class="input-group-text">
3232
<i class="icon-lock"></i>
3333
</span>
3434
</div>
35-
<input type="password" class="form-control" placeholder="Password" value="Pa$$word123" asp-for=Password autocomplete="off">
35+
<input type="password" class="form-control" placeholder="Password" value="@Environment.GetEnvironmentVariable("DEFAULT_PASS")" asp-for=Password autocomplete="off">
3636
</div>
3737
@if (Model.AllowRememberLogin)
3838
{

0 commit comments

Comments
 (0)