Skip to content

Commit 0b2adff

Browse files
committed
[WIP] Validation Adapter
1 parent 65749f8 commit 0b2adff

File tree

5 files changed

+205
-15
lines changed

5 files changed

+205
-15
lines changed

WebApiResource/Common/CustomExceptionFilterAttribute.cs renamed to WebApiResource/Common/ResourceErrorFilter.cs

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,35 +1,39 @@
11
using Microsoft.AspNetCore.Mvc;
22
using Microsoft.AspNetCore.Mvc.Filters;
3-
using System.Resources;
43
using WebApiResource.Resources;
54

65
namespace WebApiResource.Filters
76
{
8-
public class ResourceExceptionFilter : ExceptionFilterAttribute
7+
public class ResourceErrorFilter : ExceptionFilterAttribute
98
{
10-
private static readonly ResourceManager _resourceManager = new(typeof(ErrorMessages));
9+
private readonly MessageResourceContext _messageResourceContext;
10+
11+
public ResourceErrorFilter(MessageResourceContext messageResourceFactory)
12+
{
13+
_messageResourceContext = messageResourceFactory;
14+
}
1115

1216
public override void OnException(ExceptionContext context)
1317
{
1418
var statusCode = GetHttpStatusCodeFromException(context);
1519

1620
var errorMessage = GetErrorMessage(statusCode);
17-
context.Result = new ObjectResult(new
21+
22+
var returnPattern = new
1823
{
1924
title = "One or more errors occurred.",
2025
status = statusCode,
2126
message = errorMessage,
22-
})
23-
{
24-
StatusCode = statusCode,
2527
};
2628

29+
context.Result = new ObjectResult(returnPattern) { StatusCode = statusCode };
30+
2731
context.ExceptionHandled = true;
2832
}
2933

30-
private static string GetErrorMessage(int statusCode)
34+
private string GetErrorMessage(int statusCode)
3135
{
32-
string errorMessage = _resourceManager.GetString(name: $"{statusCode}");
36+
string errorMessage = _messageResourceContext.GetMessage(statusCode.ToString());
3337

3438
return string.IsNullOrEmpty(errorMessage) ? "Internal Server Error" : errorMessage;
3539
}
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
using System.ComponentModel.DataAnnotations;
2+
using System.Resources;
3+
using Microsoft.AspNetCore.Mvc.DataAnnotations;
4+
using Microsoft.Extensions.Localization;
5+
using WebApiResource.Resources;
6+
7+
public class ResourceValidationAttributeAdapterProvider : IValidationAttributeAdapterProvider
8+
{
9+
private readonly IValidationAttributeAdapterProvider _baseProvider;
10+
private readonly MessageResourceContext _messageResourceContext;
11+
12+
public ResourceValidationAttributeAdapterProvider(IValidationAttributeAdapterProvider baseProvider, MessageResourceContext messageResourceFactory)
13+
{
14+
_baseProvider = baseProvider;
15+
_messageResourceContext = messageResourceFactory;
16+
}
17+
18+
public IAttributeAdapter GetAttributeAdapter(ValidationAttribute attribute, IStringLocalizer stringLocalizer)
19+
{
20+
if (attribute is RequiredAttribute requiredAttribute)
21+
{
22+
var resourceManager = _messageResourceContext.GetMessage(name);
23+
return new RequiredAttributeAdapter(requiredAttribute, _messageResourceContext);
24+
}
25+
26+
if (attribute is StringLengthAttribute stringLengthAttribute)
27+
{
28+
var resourceManager = _resourceManagerFactory.Create(typeof(ValidationMessages));
29+
return new StringLengthAttributeAdapter(stringLengthAttribute, resourceManager);
30+
}
31+
32+
// Add more custom attribute adapters as needed
33+
34+
return _baseProvider.GetAttributeAdapter(attribute, stringLocalizer);
35+
}
36+
37+
private class RequiredAttributeAdapter : AttributeAdapterBase<RequiredAttribute>
38+
{
39+
public RequiredAttributeAdapter(RequiredAttribute attribute, ResourceManager resourceManager)
40+
: base(attribute, resourceManager)
41+
{
42+
}
43+
}
44+
45+
private class StringLengthAttributeAdapter : AttributeAdapterBase<StringLengthAttribute>
46+
{
47+
public StringLengthAttributeAdapter(StringLengthAttribute attribute, ResourceManager resourceManager)
48+
: base(attribute, resourceManager)
49+
{
50+
}
51+
}
52+
53+
// public LocalizedValidationAttributeAdapterProvider(IValidationAttributeAdapterProvider baseProvider, IStringLocalizer<ValidationMessages> localizer)
54+
// {
55+
// _baseProvider = baseProvider;
56+
// _localizer = localizer;
57+
// }
58+
59+
// public IAttributeAdapter GetAttributeAdapter(ValidationAttribute attribute, IStringLocalizer stringLocalizer)
60+
// {
61+
// var baseAdapter = _baseProvider.GetAttributeAdapter(attribute, stringLocalizer);
62+
63+
// if (baseAdapter is ValidationAttributeAdapter adapter)
64+
// {
65+
// adapter.Attribute.ErrorMessage = _resourceManager.GetString(name: adapter.Attribute.ErrorMessage);
66+
// }
67+
// return baseAdapter;
68+
// }
69+
// }

WebApiResource/Controllers/UserController.cs

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
using System.Net;
12
using Microsoft.AspNetCore.Mvc;
23
using WebApiResource.Models;
34

@@ -15,7 +16,14 @@ public UserController()
1516
[HttpPost]
1617
public IActionResult Post([FromBody] User userModel)
1718
{
18-
// throw new HttpRequestException("", null, HttpStatusCode.Forbidden);
19-
return Ok(userModel);
19+
try
20+
{
21+
throw new HttpRequestException("", null, HttpStatusCode.Forbidden);
22+
return Ok(userModel);
23+
}
24+
catch (Exception)
25+
{
26+
throw;
27+
}
2028
}
2129
}

WebApiResource/Program.cs

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,32 @@
1+
using System.Resources;
2+
using Microsoft.AspNetCore.Mvc.DataAnnotations;
13
using WebApiResource.Filters;
4+
using WebApiResource.Resources;
25

36
var builder = WebApplication.CreateBuilder(args);
47

58
// Add services to the container.
69

7-
builder.Services.AddControllers(options =>
8-
{
9-
options.Filters.Add<ResourceExceptionFilter>();
10-
});
10+
11+
// builder.Services.AddLocalization(options => options.ResourcesPath = "Resources");
12+
13+
// builder.Services.AddSingleton<IBuilderMessageResourceError>(provider => new BuilderMessageResourceError(ResourceManager)));
14+
// builder.Services.AddSingleton<IBuilderMessageResourceValidation>(provider => new BuilderMessageResourceValidation(ResourceManager)));
15+
16+
// builder.Services.AddSingleton<ResourceManager>(provider => { return new ResourceManager(typeof(ErrorMessages)); });
17+
// builder.Services.AddSingleton<ResourceManager>(provider => { return new ResourceManager(typeof(ValidationMessages)); });
18+
// builder.Services.AddSingleton<IBuilderMessageResourceError, BuilderMessageResourceError>();
19+
// builder.Services.AddSingleton<IBuilderMessageResourceValidation, BuilderMessageResourceValidation>();
20+
// builder.Services.AddSingleton<IMessageResource>(provider => new MessageResource(ValidationMessages));
21+
// builder.Services.AddSingleton<IValidationAttributeAdapterProvider, ResourceValidationAttributeAdapterProvider>();
22+
// builder.Services.AddScoped<ResourceExceptionFilter>();
23+
24+
// builder.Services.AddSingleton<MessageResourceFactory>();
25+
26+
builder.Services.AddSingleton(provider => { return new MessageResourceContext(typeof(ErrorMessages)); });
27+
28+
builder.Services.AddControllers(options => { options.Filters.Add<ResourceErrorFilter>(); });
29+
1130
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
1231
builder.Services.AddEndpointsApiExplorer();
1332
builder.Services.AddSwaggerGen();
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
using System.Resources;
2+
3+
namespace WebApiResource.Resources
4+
{
5+
6+
public class MessageResourceContext
7+
{
8+
private readonly ResourceManager _resourceManager;
9+
10+
public MessageResourceContext(Type resourceType) => _resourceManager = new ResourceManager(resourceType);
11+
12+
public string GetMessage(string name)
13+
{
14+
return _resourceManager.GetString(name);
15+
}
16+
}
17+
18+
19+
// public interface IMessageResource
20+
// {
21+
// string GetMessage(Type resourceType, string name);
22+
// }
23+
24+
// public class MessageResourceContext : IMessageResource
25+
// {
26+
// private MessageResourceFactory _messageResourceFactory = new MessageResourceFactory();
27+
// private static ResourceManager _resourceManager;
28+
29+
30+
// public string GetMessage(Type resourceType, string name)
31+
// {
32+
// _resourceManager = _messageResourceFactory.createMessageResource(resourceType);
33+
// return _resourceManager.GetString(name);
34+
// }
35+
// }
36+
37+
// public class MessageResourceFactory
38+
// {
39+
// public ResourceManager createMessageResource(Type resourceType)
40+
// {
41+
42+
// return new ResourceManager(resourceType);
43+
// }
44+
// }
45+
46+
47+
// ===========
48+
49+
50+
// public interface IBuilderMessageResourceError
51+
// {
52+
// string GetMessage(int statusCode);
53+
// }
54+
// public interface IBuilderMessageResourceValidation
55+
// {
56+
// string GetMessage(string name);
57+
// }
58+
59+
// public class BuilderMessageResourceError : IBuilderMessageResourceError
60+
// {
61+
// private ResourceManager? _resourceManager;
62+
63+
// public BuilderMessageResourceError(ResourceManager resourceManager)
64+
// {
65+
// _resourceManager = resourceManager;
66+
// }
67+
68+
// public string GetMessage(int statusCode)
69+
// {
70+
// _resourceManager = new ResourceManager(typeof(ErrorMessages));
71+
// return _resourceManager.GetString(name: $"{statusCode}");
72+
// }
73+
// }
74+
75+
// public class BuilderMessageResourceValidation : IBuilderMessageResourceValidation
76+
// {
77+
// private ResourceManager? _resourceManager;
78+
79+
// public BuilderMessageResourceValidation(ResourceManager resourceManager)
80+
// {
81+
// _resourceManager = resourceManager;
82+
// }
83+
84+
// public string GetMessage(string name)
85+
// {
86+
// _resourceManager = new ResourceManager(typeof(ValidationMessages));
87+
// return _resourceManager.GetString(name);
88+
// }
89+
// }
90+
}

0 commit comments

Comments
 (0)