Initial Commit ...
This commit is contained in:
@@ -0,0 +1,8 @@
|
||||
#
|
||||
# DotNet ...
|
||||
bin
|
||||
obj
|
||||
|
||||
#
|
||||
# Natural Docs ...
|
||||
Documentation/*
|
||||
@@ -0,0 +1,38 @@
|
||||
using System.Linq;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.AspNetCore.Mvc.Filters;
|
||||
using xCommons.Constants;
|
||||
using xCommons.Extensions;
|
||||
|
||||
namespace xCommons.Attributes {
|
||||
public partial class RequireXPoweredAttribute : AuthorizeAttribute, IAuthorizationFilter {
|
||||
|
||||
private readonly bool ignoreAnonymous;
|
||||
|
||||
public RequireXPoweredAttribute (bool IgnoreAnonymous = true) {
|
||||
ignoreAnonymous = IgnoreAnonymous;
|
||||
}
|
||||
|
||||
public void OnAuthorization (AuthorizationFilterContext context) {
|
||||
//
|
||||
var config = context.GetXAppConfiguration ();
|
||||
|
||||
//
|
||||
var isExistsXPowered = context.HttpContext.Request.Headers
|
||||
.Any (h => h.Key
|
||||
.ToNormalString () == XAuthorization.XPoweredBy.ToNormalString () &&
|
||||
h.Value == config.XPoweredValue);
|
||||
|
||||
//
|
||||
var isAnonymous = context.IsAnonymousAllowed ();
|
||||
var handler = ignoreAnonymous ? isAnonymous ? false : true : true;
|
||||
|
||||
//
|
||||
if (handler &&
|
||||
!isExistsXPowered) {
|
||||
context.Result = new UnauthorizedResult ();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using IdentityModel;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
|
||||
namespace xCommons.Authorization {
|
||||
public partial class RequiredRolesHandler : AuthorizationHandler<RequiredRolesRequirement> {
|
||||
protected override Task HandleRequirementAsync (
|
||||
AuthorizationHandlerContext context,
|
||||
RequiredRolesRequirement requirement
|
||||
) {
|
||||
//
|
||||
var conatinsRole = context.User.HasClaim (c => c.Type == JwtClaimTypes.Role);
|
||||
if (!conatinsRole) {
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
//
|
||||
var roleClaim = context.User.Claims.FirstOrDefault (c => c.Type == JwtClaimTypes.Role);
|
||||
if (roleClaim == null ||
|
||||
!requirement.Roles.Contains (roleClaim.Value)
|
||||
) {
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
//
|
||||
context.Succeed (requirement);
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
|
||||
namespace xCommons.Authorization {
|
||||
public partial class RequiredRolesRequirement : IAuthorizationRequirement {
|
||||
public string[] Roles { get; }
|
||||
public RequiredRolesRequirement (params string[] Roles) {
|
||||
this.Roles = Roles;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace xCommons.Configurations {
|
||||
/// <summary>
|
||||
/// represent an xBackend Application
|
||||
/// </summary>
|
||||
public partial class XAppConfiguration {
|
||||
public string Name { get; set; }
|
||||
public string Version { get; set; }
|
||||
public string XPoweredValue { get; set; }
|
||||
public IEnumerable<string> AllowedOrigins { get; set; }
|
||||
public string WelcomeMessage { get; set; }
|
||||
public string DefaultLanguage { get; set; }
|
||||
public XMessageResourceTitles MessageResourceTitles { get; set; }
|
||||
}
|
||||
|
||||
public partial class XMessageResourceTitles {
|
||||
public string Terms { get; set; }
|
||||
public string Invite { get; set; }
|
||||
public string RegistrationApprove { get; set; }
|
||||
public string Registered { get; set; }
|
||||
public string VerificationCode { get; set; }
|
||||
public string ChangePassword { get; set; }
|
||||
public string PasswordChanged { get; set; }
|
||||
public string NewDeviceLoggedIn { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
namespace xCommons.Configurations {
|
||||
public partial class XSwaggerConfiguration {
|
||||
public string Title { get; set; } = "";
|
||||
public string Version { get; set; } = "V1.0";
|
||||
public string Description { get; set; } = "";
|
||||
public string TermsOfServiceUrl { get; set; } = "";
|
||||
|
||||
public XSwaggerContact Contact { get; set; } = null;
|
||||
public XSwaggerLicence License { get; set; } = null;
|
||||
}
|
||||
|
||||
public partial class XSwaggerContact {
|
||||
public string Name { get; set; }
|
||||
public string Email { get; set; }
|
||||
public string Url { get; set; }
|
||||
}
|
||||
|
||||
public partial class XSwaggerLicence {
|
||||
public string Name { get; set; }
|
||||
public string Url { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
namespace xCommons.Constants {
|
||||
public partial class CommonConstants {
|
||||
public static char DEFAULT_LIST_SEPERATOR = ',';
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
namespace xCommons.Constants {
|
||||
public partial struct ConfigurationNodeNames {
|
||||
public const string CERTIFICATES_NODE = "Certificates";
|
||||
public const string SWAGGER_NODE = "SwaggerConfiguration";
|
||||
public const string MESSAGE_RESOURCE_TITLES_NODE = "MessageResourceTitles";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
namespace xCommons.Constants {
|
||||
public partial struct XAuthentication {
|
||||
public const string JWT = "jwt";
|
||||
public const string BEARER = "Bearer";
|
||||
public const string TOKEN = "token";
|
||||
public const string INTROSPECTION = "introspection";
|
||||
public const string IDENTITY_SERVER_LOCAL_API = "IdentityServerAccessToken";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
namespace xCommons.Constants {
|
||||
public partial struct XAuthorization {
|
||||
public const string TokenIdentifier = "Bearer ";
|
||||
public const string Header = "Authorization";
|
||||
public const string AccessToken = "access_token";
|
||||
public const string RefreshToken = "refresh_token";
|
||||
public const string ExpiresAt = "expires_at";
|
||||
public const string AccessTokenExpired = "AccessToken-Expired";
|
||||
public const string RevisionChecksum = "revision_checksum";
|
||||
public const string XPoweredBy = "X-PoweredBy";
|
||||
public const int ThresholdBeforeTokenExpiration = 600;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
namespace xCommons.Constants {
|
||||
public partial struct XCustomClaims {
|
||||
public const string IsEnabled = "is_enabled";
|
||||
public const string IsBanned = "is_banned";
|
||||
public const string Issuer = "iss";
|
||||
public const string ExpiredOn = "exp";
|
||||
public const string Audience = "aud";
|
||||
public const string ClientId = "client_id";
|
||||
public const string AuthenticatedOn = "auth_time";
|
||||
public const string UserId = "sub";
|
||||
public const string UserName = "unique_name";
|
||||
public const string FirstName = "given_name";
|
||||
public const string LastName = "family_name";
|
||||
public const string Gender = "gender";
|
||||
public const string Picture = "picture";
|
||||
public const string BrithDate = "birthdate";
|
||||
public const string Email = "email";
|
||||
public const string EmailVerified = "email_verified";
|
||||
public const string PhoneNumber = "phone_number";
|
||||
public const string PhoneNumberVerified = "phone_number_verified";
|
||||
public const string Role = "role";
|
||||
public const string Scope = "scope";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
namespace xCommons.Constants {
|
||||
/// <summary>
|
||||
/// a collection of available Client Devices
|
||||
/// </summary>
|
||||
public enum XDeviceType {
|
||||
Unknown,
|
||||
Mobile,
|
||||
Tablet,
|
||||
Desktop
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
namespace xCommons.Constants {
|
||||
public enum XFileType {
|
||||
Image,
|
||||
ProfileImasge,
|
||||
CoverImage,
|
||||
Audio,
|
||||
Video,
|
||||
Document
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
namespace xCommons.Constants {
|
||||
public partial struct XPolicy {
|
||||
public const string AllowedOrigins = "AllowedOrigins";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,139 @@
|
||||
using System;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using xCommons.Attributes;
|
||||
using xCommons.Configurations;
|
||||
using xCommons.Extensions;
|
||||
using xCommons.Providers;
|
||||
using xExceptions.Constants;
|
||||
|
||||
namespace xCommons.Controllers {
|
||||
/// <summary>
|
||||
/// Base Controller
|
||||
/// </summary>
|
||||
[Route ("[controller]")]
|
||||
[Produces ("application/json")]
|
||||
public abstract partial class XBaseController : ControllerBase {
|
||||
public ILogger Logger { get; }
|
||||
public XAppConfiguration AppConfiguration { get; }
|
||||
public XValidationProvider ValidationProvider { get; }
|
||||
|
||||
public XBaseController (
|
||||
ILogger logger,
|
||||
XAppConfiguration appConfiguration,
|
||||
XValidationProvider validationProvider
|
||||
) {
|
||||
Logger = logger;
|
||||
AppConfiguration = appConfiguration;
|
||||
ValidationProvider = validationProvider;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check the Controller Up and Running
|
||||
/// </summary>
|
||||
/// <returns>string message</returns>
|
||||
[HttpGet]
|
||||
[Route ("Test/Hi")]
|
||||
[AllowAnonymous]
|
||||
public virtual IActionResult Hi () {
|
||||
//
|
||||
var controllerName = GetControllerName ();
|
||||
var message = $"{controllerName} Controller is Up and running ...";
|
||||
|
||||
//
|
||||
return Ok (message);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check Controller ByPass XPowered Filter
|
||||
/// </summary>
|
||||
/// <returns>string message</returns>
|
||||
[HttpGet]
|
||||
[AllowAnonymous]
|
||||
[RequireXPowered (false)]
|
||||
[Route ("Test/PassRequireXPowered")]
|
||||
public virtual IActionResult PassRequireXPowered () {
|
||||
//
|
||||
var controllerName = GetControllerName ();
|
||||
var message = $"{controllerName} Controller bypass RequiredXPowered and Up and running ...";
|
||||
|
||||
//
|
||||
return Ok (message);
|
||||
}
|
||||
|
||||
//
|
||||
#region Non Actions ...
|
||||
/// <summary>
|
||||
/// Convert an Exception to Propper Error Result
|
||||
/// </summary>
|
||||
/// <param name="ex"></param>
|
||||
/// <returns></returns>
|
||||
[NonAction]
|
||||
public ActionResult GetExceptionActionResult (Exception ex) {
|
||||
//
|
||||
var exception = GetExceptionResult (ex);
|
||||
var error = ex.Message.ToXError ();
|
||||
|
||||
//
|
||||
Logger.LogError ($"exception: {exception}, error: {error}");
|
||||
|
||||
//
|
||||
try {
|
||||
var xError = exception.Message.ToXError ();
|
||||
var xException = (XException) xError.Id;
|
||||
|
||||
//
|
||||
switch (xException) {
|
||||
//
|
||||
case XException.NotFound:
|
||||
return NotFound (error);
|
||||
|
||||
//
|
||||
case XException.NotAuthorized:
|
||||
return Unauthorized ();
|
||||
}
|
||||
} catch { }
|
||||
|
||||
//
|
||||
return BadRequest (error);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Return Structured Exception
|
||||
/// </summary>
|
||||
/// <param name="ex"></param>
|
||||
/// <returns></returns>
|
||||
[NonAction]
|
||||
public Exception GetExceptionResult (Exception ex) {
|
||||
//
|
||||
// Log Exception Message ...
|
||||
Logger.LogError (ex.Message);
|
||||
|
||||
//
|
||||
// if Happens Exception is Know Error
|
||||
// catch it and return it in BadRequest Container ...
|
||||
var isEr = ex.Message.IsXError ();
|
||||
|
||||
//
|
||||
if (isEr) {
|
||||
return ex;
|
||||
}
|
||||
|
||||
//
|
||||
// if catched Exception Contains Unknown Error
|
||||
// return an Unknown Error ...
|
||||
return XException.Unknown.ToException ();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Retrieve ControllerName
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
[NonAction]
|
||||
public string GetControllerName () {
|
||||
return this.ControllerContext.RouteData.Values["controller"].ToString ();
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using xCommons.Providers;
|
||||
|
||||
public static partial class XDIHelperExtension {
|
||||
/// <summary>
|
||||
/// Register XCommons Module Services
|
||||
/// </summary>
|
||||
/// <param name="services"></param>
|
||||
public static void AddXCommons (this IServiceCollection services) {
|
||||
services.AddSingleton<XValidationProvider> ();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using xCommons.Constants;
|
||||
using xCommons.Models;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class CertificateExtensions {
|
||||
/// <summary>
|
||||
/// Retrieve Specific Certificate From app Settings
|
||||
/// </summary>
|
||||
/// <param name="configuration"></param>
|
||||
/// <param name="name"></param>
|
||||
/// <returns></returns>
|
||||
public static XCertificate GetCertificate (this IConfiguration configuration, string name) {
|
||||
//
|
||||
var certificatesSection = configuration.GetSection (ConfigurationNodeNames.CERTIFICATES_NODE);
|
||||
var certificateSection = certificatesSection.GetSection (name);
|
||||
var certificate = certificateSection.Get<XCertificate> ();
|
||||
|
||||
//
|
||||
return certificate;
|
||||
}
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,319 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Microsoft.AspNetCore.Builder;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.OpenApi.Models;
|
||||
using Swashbuckle.AspNetCore.SwaggerGen;
|
||||
using Swashbuckle.AspNetCore.SwaggerUI;
|
||||
using xCommons.Configurations;
|
||||
using xCommons.Constants;
|
||||
using xCommons.Filters;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class DIExtensions {
|
||||
|
||||
/// <summary>
|
||||
/// Inject Specific Registered Service from IServiceCollection
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static T GetRegisteredService<T> (this IServiceCollection source) {
|
||||
//
|
||||
var serviceProvider = source.BuildServiceProvider ();
|
||||
return serviceProvider.GetService<T> ();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Register App Configuration as a Service
|
||||
/// </summary>
|
||||
/// <param name="services"></param>
|
||||
/// <param name="configuration"></param>
|
||||
public static void AddXAppConfiguration (this IServiceCollection services, IConfiguration configuration) {
|
||||
//
|
||||
var appConfiguration = configuration.GetXAppConfiguration ();
|
||||
services.AddSingleton<XAppConfiguration> (appConfiguration);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add Required OperationFilters and Authorization Fields to Swagger Options
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="xmlFilePath"></param>
|
||||
/// <param name="addRequiredXPoweredFilter"></param>
|
||||
/// <param name="addXTokenAuthorization"></param>
|
||||
public static void AddXSwaggerGenOptions (
|
||||
this SwaggerGenOptions source,
|
||||
string xmlFilePath = null,
|
||||
bool addRequiredXPoweredFilter = true,
|
||||
bool addXTokenAuthorization = true
|
||||
) {
|
||||
//
|
||||
if (source.IsNull ()) {
|
||||
source = new SwaggerGenOptions ();
|
||||
}
|
||||
|
||||
//
|
||||
// Add Xml File Path ...
|
||||
if (!xmlFilePath.IsNullOrEmpty ()) {
|
||||
source.IncludeXmlComments (xmlFilePath);
|
||||
}
|
||||
|
||||
//
|
||||
// Handle RequireXPowered Filter ...
|
||||
if (addRequiredXPoweredFilter) {
|
||||
source.OperationFilter<RequireXPoweredOperationFilter> ();
|
||||
}
|
||||
|
||||
//
|
||||
// Handle XToken Authorizations ...
|
||||
if (addXTokenAuthorization) {
|
||||
//
|
||||
#region Bearer AccessToken ...
|
||||
//
|
||||
source.AddSecurityDefinition (nameof (XAuthorization.AccessToken), new OpenApiSecurityScheme {
|
||||
In = ParameterLocation.Header,
|
||||
Description = "Bearer token",
|
||||
Type = SecuritySchemeType.ApiKey,
|
||||
Name = XAuthorization.Header
|
||||
});
|
||||
|
||||
//
|
||||
source.AddSecurityRequirement (new OpenApiSecurityRequirement {
|
||||
{
|
||||
new OpenApiSecurityScheme {
|
||||
Reference = new OpenApiReference {
|
||||
Id = nameof (XAuthorization.AccessToken),
|
||||
Type = ReferenceType.SecurityScheme
|
||||
}
|
||||
}, Array.Empty<string> ()
|
||||
}
|
||||
});
|
||||
#endregion
|
||||
|
||||
//
|
||||
#region RefreshToken ...
|
||||
//
|
||||
source.AddSecurityDefinition (nameof (XAuthorization.RefreshToken), new OpenApiSecurityScheme {
|
||||
In = ParameterLocation.Header,
|
||||
Description = "refresh token",
|
||||
Type = SecuritySchemeType.ApiKey,
|
||||
Name = nameof (XAuthorization.RefreshToken)
|
||||
});
|
||||
|
||||
//
|
||||
source.AddSecurityRequirement (new OpenApiSecurityRequirement {
|
||||
{
|
||||
new OpenApiSecurityScheme {
|
||||
Reference = new OpenApiReference {
|
||||
Id = nameof (XAuthorization.RefreshToken),
|
||||
Type = ReferenceType.SecurityScheme
|
||||
}
|
||||
}, Array.Empty<string> ()
|
||||
}
|
||||
});
|
||||
#endregion
|
||||
|
||||
//
|
||||
#region ExpiresAt ...
|
||||
//
|
||||
source.AddSecurityDefinition (nameof (XAuthorization.ExpiresAt), new OpenApiSecurityScheme {
|
||||
In = ParameterLocation.Header,
|
||||
Description = "expires at",
|
||||
Type = SecuritySchemeType.ApiKey,
|
||||
Name = nameof (XAuthorization.ExpiresAt)
|
||||
});
|
||||
|
||||
//
|
||||
source.AddSecurityRequirement (new OpenApiSecurityRequirement {
|
||||
{
|
||||
new OpenApiSecurityScheme {
|
||||
Reference = new OpenApiReference {
|
||||
Id = nameof (XAuthorization.ExpiresAt),
|
||||
Type = ReferenceType.SecurityScheme
|
||||
}
|
||||
}, Array.Empty<string> ()
|
||||
}
|
||||
});
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Register Swagger
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="configuration"></param>
|
||||
/// <param name="settings"></param>
|
||||
/// <param name="xmlFilePath"></param>
|
||||
/// <param name="addRequiredXPoweredFilter"></param>
|
||||
/// <param name="addXTokenAuthorization"></param>
|
||||
public static void AddXSwagger (
|
||||
this IServiceCollection source,
|
||||
IConfiguration configuration,
|
||||
SwaggerGenOptions settings = null,
|
||||
string xmlFilePath = null,
|
||||
bool addRequiredXPoweredFilter = true,
|
||||
bool addXTokenAuthorization = true
|
||||
) {
|
||||
//
|
||||
var xSwaggerConfig = configuration.GetXSwaggerConfiguration ();
|
||||
if (xSwaggerConfig.IsNull ()) {
|
||||
xSwaggerConfig = new XSwaggerConfiguration ();
|
||||
}
|
||||
|
||||
//
|
||||
#region Prepare SwaggerGenOptions ...
|
||||
if (settings.IsNull ()) {
|
||||
settings = new SwaggerGenOptions ();
|
||||
}
|
||||
settings.AddXSwaggerGenOptions (
|
||||
xmlFilePath: xmlFilePath,
|
||||
addRequiredXPoweredFilter: addRequiredXPoweredFilter,
|
||||
addXTokenAuthorization: addXTokenAuthorization
|
||||
);
|
||||
#endregion
|
||||
|
||||
//
|
||||
#region Prepare Swagger Doc ...
|
||||
//
|
||||
// Api Document Section ...
|
||||
var apiDoc = new OpenApiInfo {
|
||||
Title = xSwaggerConfig.Title,
|
||||
Version = xSwaggerConfig.Version,
|
||||
Description = xSwaggerConfig.Description,
|
||||
};
|
||||
|
||||
//
|
||||
// Api Document TermsOfUse URL ...
|
||||
if (!xSwaggerConfig.TermsOfServiceUrl.IsNullOrEmpty ()) {
|
||||
apiDoc.TermsOfService = new Uri (xSwaggerConfig.TermsOfServiceUrl);
|
||||
}
|
||||
|
||||
//
|
||||
// Contact Section ...
|
||||
if (!xSwaggerConfig.Contact.IsNull ()) {
|
||||
//
|
||||
var apiContact = new OpenApiContact {
|
||||
Name = xSwaggerConfig.Contact.Name,
|
||||
Email = xSwaggerConfig.Contact.Email
|
||||
};
|
||||
|
||||
//
|
||||
// Contact URL ...
|
||||
if (!xSwaggerConfig.Contact.Url.IsNullOrEmpty ()) {
|
||||
apiContact.Url = new Uri (xSwaggerConfig.Contact.Url);
|
||||
}
|
||||
|
||||
//
|
||||
apiDoc.Contact = apiContact;
|
||||
}
|
||||
|
||||
//
|
||||
// License Section ...
|
||||
if (!xSwaggerConfig.License.IsNull ()) {
|
||||
//
|
||||
var apiLicense = new OpenApiLicense {
|
||||
Name = xSwaggerConfig.License.Name,
|
||||
};
|
||||
|
||||
//
|
||||
// License URL ...
|
||||
if (!xSwaggerConfig.License.Url.IsNullOrEmpty ()) {
|
||||
apiLicense.Url = new Uri (xSwaggerConfig.License.Url);
|
||||
}
|
||||
|
||||
//
|
||||
apiDoc.License = apiLicense;
|
||||
}
|
||||
#endregion
|
||||
|
||||
//
|
||||
// Register Swagger ...
|
||||
source.AddSwaggerGen (
|
||||
opt => {
|
||||
//
|
||||
opt.UpdateData (settings);
|
||||
|
||||
//
|
||||
opt.SwaggerDoc ("v1", apiDoc);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Use Sagger
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="options"></param>
|
||||
public static void UseXSwagger (
|
||||
this IApplicationBuilder source,
|
||||
SwaggerUIOptions options = null
|
||||
) {
|
||||
//
|
||||
source.UseSwagger ();
|
||||
|
||||
//
|
||||
if (options.IsNull ()) {
|
||||
source.UseSwaggerUI ();
|
||||
} else {
|
||||
source.UseSwaggerUI (options: options);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add Cross Origin Resource Sharings
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="allowedOrigins"></param>
|
||||
public static void AddXCors (
|
||||
this IServiceCollection source,
|
||||
IEnumerable<string> allowedOrigins
|
||||
) {
|
||||
//
|
||||
if (!allowedOrigins.HasChild ()) {
|
||||
//
|
||||
Console.WriteLine ($"XCommons: there is no provided allowedOrigins, start app without any specific cors, this may be unsecure ...");
|
||||
|
||||
//
|
||||
source.AddCors (options => {
|
||||
options.AddPolicy (XPolicy.AllowedOrigins,
|
||||
builder => {
|
||||
builder
|
||||
.AllowAnyOrigin ()
|
||||
.AllowAnyHeader ()
|
||||
.AllowAnyMethod ()
|
||||
.WithExposedHeaders ("*");
|
||||
});
|
||||
});
|
||||
|
||||
//
|
||||
return;
|
||||
}
|
||||
|
||||
//
|
||||
source.AddCors (options => {
|
||||
options.AddPolicy (XPolicy.AllowedOrigins,
|
||||
builder => {
|
||||
builder
|
||||
.WithOrigins (allowedOrigins.ToArray ())
|
||||
.AllowAnyHeader ()
|
||||
.AllowAnyMethod ()
|
||||
.AllowCredentials ()
|
||||
.WithExposedHeaders ("*");
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Use X Registered Cross Origin Resource Sharings
|
||||
/// </summary>
|
||||
/// <param name="sources"></param>
|
||||
public static void UseXCors (this IApplicationBuilder sources) {
|
||||
//
|
||||
sources.UseCors (XPolicy.AllowedOrigins);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class EnumExtensions {
|
||||
public static string GetKey (this Enum source) {
|
||||
return Enum.GetName (source.GetType (), source);
|
||||
}
|
||||
|
||||
public static T GetValue<T> (this string source) {
|
||||
return (T) Enum.Parse (typeof (T), source);
|
||||
}
|
||||
|
||||
public static void Iterate<T> (this IEnumerator<T> source, Action<T> action) {
|
||||
//
|
||||
while (source.MoveNext ()) {
|
||||
//
|
||||
var current = source.Current;
|
||||
action (current);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,170 @@
|
||||
using System;
|
||||
using xExceptions.Constants;
|
||||
using xExceptions.Models;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
/// <summary>
|
||||
/// this is an extension pack for Exceptions
|
||||
/// </summary>
|
||||
public static partial class ExceptionExtensions {
|
||||
|
||||
/// <summary>
|
||||
/// determines an string contains an XError content or not
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsXError (this string source) {
|
||||
//
|
||||
if (source.IsNullOrEmpty ()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
//
|
||||
var xError = source.ToXError ();
|
||||
if (xError != null) {
|
||||
return true;
|
||||
}
|
||||
|
||||
//
|
||||
// If Convert Proccess fails ...
|
||||
var normalString = source.ToNormalString ();
|
||||
|
||||
//
|
||||
// Return result based on string values ...
|
||||
return normalString.Contains ("id") && normalString.Contains ("message");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// deserialize an string to to XError class instance
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static XError ToXError (this string source) {
|
||||
//
|
||||
if (source.IsNullOrEmpty ()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
//
|
||||
try {
|
||||
//
|
||||
var err = source.FromJSON<XError> ();
|
||||
|
||||
//
|
||||
// if err is null we have to manually get value
|
||||
if (err == null) {
|
||||
//
|
||||
var normalString = source.ToNormalString ();
|
||||
var parts = normalString.Split (',');
|
||||
if (parts.Length > 2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
//
|
||||
var idContainer = parts[0];
|
||||
var messageContainer = parts[1];
|
||||
}
|
||||
|
||||
//
|
||||
return err;
|
||||
} catch {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public static XError ToXError (this XException source) {
|
||||
//
|
||||
var errorId = (int) source;
|
||||
var errorMessage = source.GetStringValue ();
|
||||
|
||||
//
|
||||
return new XError {
|
||||
Id = errorId,
|
||||
Message = errorMessage
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Convert an XError instance to an Exception
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static Exception ToException (this XError source) {
|
||||
//
|
||||
var jsonStr = source.ToJSON ();
|
||||
return new Exception (jsonStr);
|
||||
}
|
||||
|
||||
public static Exception ToException (this XException source) {
|
||||
return source
|
||||
.ToXError ()
|
||||
.ToException ();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Convert an Exception to corresponding XError Object
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static XError FromException (this Exception source) {
|
||||
//
|
||||
if (source == null || source.Message.IsNullOrEmpty ()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
//
|
||||
return source.Message.ToXError ();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add Content to Contentable XException member and return XError Object
|
||||
/// </summary>
|
||||
/// <param name="exception"></param>
|
||||
/// <param name="value"></param>
|
||||
/// <returns></returns>
|
||||
public static XError AddContentToError (this XException exception, string value) {
|
||||
//
|
||||
var xError = exception.ToXError ();
|
||||
xError.Message = string.Format (xError.Message, value);
|
||||
|
||||
//
|
||||
return xError;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add Content to Contentable XException member and return Exception Object
|
||||
/// </summary>
|
||||
/// <param name="exception"></param>
|
||||
/// <param name="value"></param>
|
||||
/// <returns></returns>
|
||||
public static Exception AddContentToException (this XException exception, string value) {
|
||||
//
|
||||
var xError = exception.ToXError ();
|
||||
xError.Message = string.Format (xError.Message, value);
|
||||
|
||||
//
|
||||
return xError.ToException ();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Throw Specific Exception ...
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="content"></param>
|
||||
public static void Throw (
|
||||
this XException source,
|
||||
string content = null
|
||||
) {
|
||||
//
|
||||
Exception exception = null;
|
||||
if (content.IsNullOrEmpty ()) {
|
||||
exception = source.ToException ();
|
||||
} else {
|
||||
exception = source.AddContentToException (content);
|
||||
}
|
||||
|
||||
//
|
||||
throw exception;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
using System.Linq;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc.Filters;
|
||||
using xCommons.Configurations;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class FilterExtensions {
|
||||
public static XAppConfiguration GetXAppConfiguration (this ActionExecutingContext source) {
|
||||
//
|
||||
var services = source.HttpContext.RequestServices;
|
||||
return (XAppConfiguration) services.GetService (typeof (XAppConfiguration));
|
||||
}
|
||||
|
||||
public static XAppConfiguration GetXAppConfiguration (this AuthorizationFilterContext source) {
|
||||
//
|
||||
var services = source.HttpContext.RequestServices;
|
||||
return (XAppConfiguration) services.GetService (typeof (XAppConfiguration));
|
||||
}
|
||||
|
||||
public static bool IsAnonymousAllowed (this AuthorizationFilterContext source) {
|
||||
//
|
||||
var result = source.Filters
|
||||
.Any (f => f.GetType () == typeof (AllowAnonymousFilter)) ||
|
||||
source.ActionDescriptor.FilterDescriptors
|
||||
.Any (f => f.GetType () == typeof (AllowAnonymousFilter)) ||
|
||||
source.ActionDescriptor.EndpointMetadata
|
||||
.Any (f => f.GetType () == typeof (AllowAnonymousAttribute));
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,48 @@
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using xCommons.Configurations;
|
||||
using xCommons.Constants;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class IConfigurationExtensions {
|
||||
/// <summary>
|
||||
/// Retrieve AppConfiguration from Configurations
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static XAppConfiguration GetXAppConfiguration (this IConfiguration source) {
|
||||
//
|
||||
var xMessageResourceTitlesConfigSection = source
|
||||
.GetSection (ConfigurationNodeNames.MESSAGE_RESOURCE_TITLES_NODE);
|
||||
|
||||
//
|
||||
var result = new XAppConfiguration {
|
||||
Name = source[nameof (XAppConfiguration.Name)],
|
||||
Version = source[nameof (XAppConfiguration.Version)],
|
||||
XPoweredValue = source[nameof (XAppConfiguration.XPoweredValue)],
|
||||
WelcomeMessage = source[nameof (XAppConfiguration.WelcomeMessage)],
|
||||
AllowedOrigins = source
|
||||
.GetSection (nameof (XAppConfiguration.AllowedOrigins))
|
||||
.Get<IEnumerable<string>> (),
|
||||
DefaultLanguage = source[nameof (XAppConfiguration.DefaultLanguage)],
|
||||
MessageResourceTitles = xMessageResourceTitlesConfigSection
|
||||
.Get<XMessageResourceTitles> ()
|
||||
};
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Retrieve Swagger Configurations
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static XSwaggerConfiguration GetXSwaggerConfiguration (this IConfiguration source) {
|
||||
//
|
||||
var xSwaggerConfigSection = source
|
||||
.GetSection (ConfigurationNodeNames.SWAGGER_NODE);
|
||||
return xSwaggerConfigSection.Get<XSwaggerConfiguration> ();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,283 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Linq;
|
||||
using System.Linq.Expressions;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class ModelExtensions {
|
||||
/// <summary>
|
||||
/// Update an Instance of a Typed Object with Data Provided by another Instance of Typed Object
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="updateWith"></param>
|
||||
/// <param name="propertyWhiteList"></param>
|
||||
/// <param name="propertyBlackList"></param>
|
||||
/// <param name="propertyValueProviders"></param>
|
||||
/// <param name="updateWithNullOrEmptyValues"></param>
|
||||
/// <param name="throwExceptionOnFails"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <typeparam name="D"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static T UpdateData<T, D> (
|
||||
this T source,
|
||||
D updateWith,
|
||||
ICollection<string> propertyWhiteList = null,
|
||||
ICollection<string> propertyBlackList = null,
|
||||
ICollection<KeyValuePair<string, Func<D, object>>> propertyValueProviders = null,
|
||||
bool updateWithNullOrEmptyValues = false,
|
||||
bool throwExceptionOnFails = false
|
||||
)
|
||||
where T : class
|
||||
where D : class {
|
||||
//
|
||||
var hasWhiteList = propertyWhiteList.HasChild<string> ();
|
||||
var hasBlackList = propertyBlackList.HasChild<string> ();
|
||||
var hasValueProvider = propertyValueProviders.HasChild<KeyValuePair<string, Func<D, object>>> ();
|
||||
|
||||
//
|
||||
var fullPropertyList = updateWith.GetType ().GetProperties ().Select (prop => prop.Name);
|
||||
var mustSetProps = (hasWhiteList ? propertyWhiteList : fullPropertyList);
|
||||
|
||||
//
|
||||
if (hasBlackList) {
|
||||
mustSetProps = mustSetProps.Where (propName => !propertyBlackList.Contains (propName));
|
||||
}
|
||||
|
||||
//
|
||||
mustSetProps.ToList ().ForEach (propName => {
|
||||
//
|
||||
try {
|
||||
//
|
||||
var sourceProp = source.GetType ().GetProperty (propName);
|
||||
var sourceValue = sourceProp.GetValue (source);
|
||||
var sourceValueType = sourceValue.IsNull () ? null : sourceValue.GetType ();
|
||||
|
||||
//
|
||||
var updateWithProp = updateWith.GetType ().GetProperty (propName);
|
||||
var updateWithValue = updateWithProp.GetValue (updateWith);
|
||||
var updateWithValueType = updateWithValue.IsNull () ? null : updateWithValue.GetType ();
|
||||
|
||||
//
|
||||
var valueProviderValue = hasValueProvider ? propertyValueProviders
|
||||
.FirstOrDefault (p => p.Key == propName).Value : null;
|
||||
var updateVal = !valueProviderValue.IsNull () ?
|
||||
valueProviderValue.Invoke (updateWith) :
|
||||
(updateWithValue.IsNull () && !updateWithNullOrEmptyValues) ?
|
||||
sourceValue : updateWithValue;
|
||||
var updateValType = updateVal.IsNull () ? null : updateVal.GetType ();
|
||||
|
||||
//
|
||||
Type t = Nullable.GetUnderlyingType (sourceProp.PropertyType) ?? sourceProp.PropertyType;
|
||||
object safeValue =
|
||||
(updateVal == null) ?
|
||||
null :
|
||||
!updateValType.IsCollectionType () ?
|
||||
Convert.ChangeType (updateVal, t) :
|
||||
updateVal;
|
||||
|
||||
//
|
||||
sourceProp.SetValue (source, safeValue);
|
||||
} catch (Exception ex) {
|
||||
//
|
||||
if (throwExceptionOnFails) {
|
||||
throw ex;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
//
|
||||
return source;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Check two Instance of Typed Object Values are Same or not
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <param name="dest"></param>
|
||||
/// <param name="propertyWhiteList"></param>
|
||||
/// <param name="propertyBlackList"></param>
|
||||
/// <param name="throwExceptionOnFails"></param>
|
||||
/// <param name="propertyValueCheckers"></param>
|
||||
/// /// <typeparam name="T"></typeparam>
|
||||
/// <typeparam name="D"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static bool IsSameContent<T, D> (
|
||||
this T source,
|
||||
D dest,
|
||||
ICollection<string> propertyWhiteList = null,
|
||||
ICollection<string> propertyBlackList = null,
|
||||
ICollection<KeyValuePair<string, Func<T, D, bool>>> propertyValueCheckers = null,
|
||||
bool throwExceptionOnFails = false
|
||||
)
|
||||
where T : class
|
||||
where D : class {
|
||||
//
|
||||
var hasWhiteList = propertyWhiteList.HasChild<string> ();
|
||||
var hasBlackList = propertyBlackList.HasChild<string> ();
|
||||
var hasCheckerProvider = propertyValueCheckers.HasChild<KeyValuePair<string, Func<T, D, bool>>> ();
|
||||
|
||||
//
|
||||
var fullPropertyList = dest.GetType ().GetProperties ().Select (prop => prop.Name);
|
||||
var mustCheckProps = (hasWhiteList ? propertyWhiteList : fullPropertyList);
|
||||
if (hasBlackList) {
|
||||
mustCheckProps = mustCheckProps.Where (propName => !propertyBlackList.Contains (propName));
|
||||
}
|
||||
|
||||
//
|
||||
var result = true;
|
||||
mustCheckProps.ToList ().ForEach (propName => {
|
||||
//
|
||||
try {
|
||||
//
|
||||
var sourceProp = source.GetType ().GetProperty (propName);
|
||||
var destProp = dest.GetType ().GetProperty (propName);
|
||||
|
||||
//
|
||||
// Check Types ...
|
||||
var isSameType = true;
|
||||
|
||||
//
|
||||
// Check
|
||||
var isSameValue = false;
|
||||
var mustDoCustomCheck = hasCheckerProvider && propertyValueCheckers.Any (p => p.Key == propName);
|
||||
if (mustDoCustomCheck) {
|
||||
//
|
||||
// Check Values ...
|
||||
var valueChecker = propertyValueCheckers.FirstOrDefault (p => p.Key == propName).Value;
|
||||
isSameValue = valueChecker.Invoke (source, dest);
|
||||
} else {
|
||||
// //
|
||||
// isSameType = (sourceProp.PropertyType == destProp.PropertyType &&
|
||||
// sourceProp.ReflectedType == destProp.ReflectedType);
|
||||
|
||||
//
|
||||
// Check Values ...
|
||||
isSameValue = Equals (sourceProp.GetValue (source), destProp.GetValue (dest));
|
||||
}
|
||||
|
||||
//
|
||||
if (!isSameType || !isSameValue) {
|
||||
result = false;
|
||||
}
|
||||
} catch (Exception ex) {
|
||||
//
|
||||
if (throwExceptionOnFails) {
|
||||
throw ex;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check specific type is Collection Type or not
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsCollectionType (this Type source) {
|
||||
//
|
||||
if (source.IsNull () || !source.IsGenericType) {
|
||||
return false;
|
||||
}
|
||||
|
||||
//
|
||||
var genericTypeDefinition = source.GetGenericTypeDefinition ();
|
||||
var result = genericTypeDefinition == typeof (List<>) ||
|
||||
genericTypeDefinition == typeof (HashSet<>) ||
|
||||
genericTypeDefinition == typeof (Collection<>) ||
|
||||
genericTypeDefinition == typeof (ICollection<>) ||
|
||||
genericTypeDefinition == typeof (IEnumerable<>);
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Retrieve a Property Value in Generic
|
||||
/// </summary>
|
||||
/// <param name="item"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static string GetPropValues<T> (this T item)
|
||||
where T : class {
|
||||
//
|
||||
var props = item.GetType ().GetProperties ();
|
||||
var vals = props.Select (p => p.GetValue (item));
|
||||
|
||||
//
|
||||
return vals.ToJSON ();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a Property Value Contains specific value
|
||||
/// </summary>
|
||||
/// <param name="item"></param>
|
||||
/// <param name="value"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static bool PropValuesContains<T> (this T item, string value)
|
||||
where T : class {
|
||||
//
|
||||
return item.GetPropValues ()
|
||||
.ToNormalString ()
|
||||
.Contains (value
|
||||
.ToNormalString ());
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Generate Default Column Map
|
||||
/// </summary>
|
||||
/// <param name="item"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static IDictionary<string, Expression<Func<T, object>>> GetDefaultColumnsMap<T> (this T item)
|
||||
where T : class {
|
||||
//
|
||||
if (item.IsNull ()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
//
|
||||
var result = new Dictionary<string, Expression<Func<T, object>>> ();
|
||||
var props = item.GetType ().GetProperties ();
|
||||
|
||||
//
|
||||
foreach (var prop in props) {
|
||||
result.Add (prop.Name, t => t.GetType ().GetProperty (prop.Name).GetValue (t, null));
|
||||
}
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Generate Default Column Map
|
||||
/// </summary>
|
||||
/// <param name="item"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static IDictionary<string, string> GetPropValuesDictionary<T> (this T item)
|
||||
where T : class {
|
||||
//
|
||||
if (item.IsNull ()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
//
|
||||
var result = new Dictionary<string, string> ();
|
||||
var props = item.GetType ().GetProperties ();
|
||||
|
||||
//
|
||||
foreach (var prop in props) {
|
||||
result.Add (prop.Name, prop.GetValue (item).ToJSON ());
|
||||
}
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using xCommons.Helpers;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static class ServiceProviderExtensions {
|
||||
/// <summary>
|
||||
/// Get all registered <see cref="ServiceDescriptor"/>
|
||||
/// </summary>
|
||||
/// <param name="provider"></param>
|
||||
/// <returns></returns>
|
||||
public static Dictionary<Type, ServiceDescriptor> GetAllServiceDescriptors (this IServiceProvider provider) {
|
||||
//
|
||||
if (provider is ServiceProvider serviceProvider) {
|
||||
//
|
||||
var result = new Dictionary<Type, ServiceDescriptor> ();
|
||||
|
||||
//
|
||||
var engine = serviceProvider.GetFieldValue ("_engine");
|
||||
var callSiteFactory = engine.GetPropertyValue ("CallSiteFactory");
|
||||
var descriptorLookup = callSiteFactory.GetFieldValue ("_descriptorLookup");
|
||||
if (descriptorLookup is IDictionary dictionary) {
|
||||
foreach (DictionaryEntry entry in dictionary) {
|
||||
result.Add ((Type) entry.Key, (ServiceDescriptor) entry.Value.GetPropertyValue ("Last"));
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
//
|
||||
throw new NotSupportedException ($"Type '{provider.GetType()}' is not supported!");
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
using System.IO;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
|
||||
namespace xCommons.Extensions {
|
||||
public static partial class XHttpContextExtensions {
|
||||
/// <summary>
|
||||
/// Convert IFormFile to Bytes Array
|
||||
/// </summary>
|
||||
/// <param name="source"></param>
|
||||
/// <returns></returns>
|
||||
public static byte[] ToByteArray (this IFormFile source) {
|
||||
//
|
||||
byte[] data;
|
||||
using (var br = new BinaryReader (source.OpenReadStream ())) {
|
||||
data = br.ReadBytes ((int) source.OpenReadStream ().Length);
|
||||
}
|
||||
|
||||
//
|
||||
return data;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
using System;
|
||||
using Microsoft.AspNetCore.Builder;
|
||||
using xCommons.Middlewares;
|
||||
|
||||
namespace xCommons.Extensions
|
||||
{
|
||||
public static class XMiddlewareExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Use XRequestLogger Middleware for log Requests ...
|
||||
/// </summary>
|
||||
/// <param name="app"></param>
|
||||
public static void UseXRequestLogger(this IApplicationBuilder app) {
|
||||
app.UseMiddleware<XRequestLogger>();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.OpenApi.Any;
|
||||
using Microsoft.OpenApi.Models;
|
||||
using Swashbuckle.AspNetCore.SwaggerGen;
|
||||
using xCommons.Configurations;
|
||||
using xCommons.Constants;
|
||||
using xCommons.Extensions;
|
||||
|
||||
namespace xCommons.Filters {
|
||||
/// <summary>
|
||||
/// RequireXPowered for NGSwag
|
||||
/// </summary>
|
||||
public partial class RequireXPoweredOperationFilter : IOperationFilter {
|
||||
private readonly XAppConfiguration config;
|
||||
|
||||
public RequireXPoweredOperationFilter (XAppConfiguration config) {
|
||||
this.config = config;
|
||||
}
|
||||
|
||||
public void Apply (OpenApiOperation operation, OperationFilterContext context) {
|
||||
//
|
||||
if (operation.Parameters.IsNull ()) {
|
||||
operation.Parameters = new List<OpenApiParameter> ();
|
||||
}
|
||||
|
||||
//
|
||||
operation.Parameters.Add (new OpenApiParameter {
|
||||
In = ParameterLocation.Header,
|
||||
Name = XAuthorization.XPoweredBy,
|
||||
Description = "a Basic Authorization Filter",
|
||||
Required = false,
|
||||
Schema = new OpenApiSchema {
|
||||
Type = "String",
|
||||
Default = new OpenApiString (config.XPoweredValue)
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,99 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace xCommons.Helpers {
|
||||
public partial class ObjectHelper {
|
||||
/// <summary>
|
||||
/// Convert Enum Keys to Array
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static Array GetKeys<T> () {
|
||||
//
|
||||
ValidateEnumbType<T> ();
|
||||
var type = typeof (T);
|
||||
|
||||
//
|
||||
var result = Enum.GetNames (type);
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Convert EnumValues to Array
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static Array GetValues<T> () {
|
||||
//
|
||||
ValidateEnumbType<T> ();
|
||||
var type = typeof (T);
|
||||
|
||||
//
|
||||
var result = Enum.GetValues (type);
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Convert an Enum to IEnumerable of it's Childs
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static IEnumerable<T> ToEnumerableValues<T> () {
|
||||
//
|
||||
ValidateEnumbType<T> ();
|
||||
var type = typeof (T);
|
||||
|
||||
//
|
||||
var result = GetValues<T> ()
|
||||
.Cast<T> ();
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Retrieve Keys of an Enumerable
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns></returns>
|
||||
public static IEnumerable<string> ToEnumerableKeys<T> () {
|
||||
//
|
||||
ValidateEnumbType<T> ();
|
||||
var type = typeof (T);
|
||||
|
||||
//
|
||||
var result = GetKeys<T> ()
|
||||
.Cast<string> ();
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
public static IDictionary<string, int> ToDictionary<T> () {
|
||||
//
|
||||
ValidateEnumbType<T> ();
|
||||
|
||||
//
|
||||
var result = new Dictionary<string, int> ();
|
||||
foreach (var name in Enum.GetNames (typeof (T))) {
|
||||
result.Add (name, (int) Enum.Parse (typeof (T), name));
|
||||
}
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
private static void ValidateEnumbType<T> () {
|
||||
//
|
||||
var type = typeof (T);
|
||||
if (!type.IsEnum) {
|
||||
throw new InvalidCastException ();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace xCommons.Helpers {
|
||||
public partial class XDateHelper {
|
||||
/// <summary>
|
||||
/// retrieve utc now timestam unix like representation ...
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
public static long UtcNowTimespan () {
|
||||
return DateTimeOffset.UtcNow.ToUnixTimeMilliseconds ();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,178 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using System.Xml;
|
||||
|
||||
namespace xCommons.Helpers {
|
||||
public partial class XMLToJSONHelper {
|
||||
//
|
||||
#region Actions ...
|
||||
public static string ToJSON (string xml) {
|
||||
//
|
||||
XmlDocument doc = new XmlDocument ();
|
||||
doc.LoadXml (xml);
|
||||
|
||||
//
|
||||
return XmlToJSON (doc);
|
||||
}
|
||||
|
||||
public static string XmlToJSON (XmlDocument xmlDoc) {
|
||||
//
|
||||
StringBuilder sbJSON = new StringBuilder ();
|
||||
|
||||
//
|
||||
sbJSON.Append ("{ ");
|
||||
XmlToJSONnode (sbJSON, xmlDoc.DocumentElement, true);
|
||||
sbJSON.Append ("}");
|
||||
|
||||
//
|
||||
return sbJSON.ToString ();
|
||||
}
|
||||
#endregion
|
||||
|
||||
//
|
||||
#region Private ...
|
||||
//
|
||||
private static void XmlToJSONnode (StringBuilder sbJSON, XmlElement node, bool showNodeName) {
|
||||
//
|
||||
if (showNodeName) {
|
||||
sbJSON.Append ("\"" + SafeJSON (node.Name) + "\": ");
|
||||
}
|
||||
|
||||
//
|
||||
sbJSON.Append ("{");
|
||||
|
||||
//
|
||||
// Build a sorted list of key-value pairs
|
||||
// where key is case-sensitive nodeName
|
||||
// value is an ArrayList of string or XmlElement
|
||||
// so that we know whether the nodeName is an array or not.
|
||||
SortedList<string, object> childNodeNames = new SortedList<string, object> ();
|
||||
|
||||
//
|
||||
// Add in all node attributes
|
||||
if (node.Attributes != null)
|
||||
foreach (XmlAttribute attr in node.Attributes)
|
||||
StoreChildNode (childNodeNames, attr.Name, attr.InnerText);
|
||||
|
||||
//
|
||||
// Add in all nodes
|
||||
foreach (XmlNode cnode in node.ChildNodes) {
|
||||
//
|
||||
if (cnode is XmlText) {
|
||||
StoreChildNode (childNodeNames, "value", cnode.InnerText);
|
||||
} else if (cnode is XmlElement) {
|
||||
StoreChildNode (childNodeNames, cnode.Name, cnode);
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Now output all stored info
|
||||
foreach (string childname in childNodeNames.Keys) {
|
||||
//
|
||||
List<object> alChild = (List<object>) childNodeNames[childname];
|
||||
if (alChild.Count == 1) {
|
||||
OutputNode (childname, alChild[0], sbJSON, true);
|
||||
} else {
|
||||
//
|
||||
sbJSON.Append (" \"" + SafeJSON (childname) + "\": [ ");
|
||||
|
||||
//
|
||||
foreach (object Child in alChild) {
|
||||
OutputNode (childname, Child, sbJSON, false);
|
||||
}
|
||||
|
||||
//
|
||||
sbJSON.Remove (sbJSON.Length - 2, 2);
|
||||
sbJSON.Append (" ], ");
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
sbJSON.Remove (sbJSON.Length - 2, 2);
|
||||
sbJSON.Append (" }");
|
||||
}
|
||||
|
||||
//
|
||||
// StoreChildNode: Store data associated with each nodeName
|
||||
// so that we know whether the nodeName is an array or not.
|
||||
private static void StoreChildNode (SortedList<string, object> childNodeNames, string nodeName, object nodeValue) {
|
||||
//
|
||||
// Pre-process contraction of XmlElement-s
|
||||
if (nodeValue is XmlElement) {
|
||||
//
|
||||
// Convert <aa></aa> into "aa":null
|
||||
// <aa>xx</aa> into "aa":"xx"
|
||||
XmlNode cnode = (XmlNode) nodeValue;
|
||||
if (cnode.Attributes.Count == 0) {
|
||||
//
|
||||
XmlNodeList children = cnode.ChildNodes;
|
||||
if (children.Count == 0) {
|
||||
nodeValue = null;
|
||||
} else if (children.Count == 1 && (children[0] is XmlText)) {
|
||||
nodeValue = ((XmlText) (children[0])).InnerText;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Add nodeValue to ArrayList associated with each nodeName
|
||||
// If nodeName doesn't exist then add it
|
||||
List<object> ValuesAL;
|
||||
|
||||
//
|
||||
if (childNodeNames.ContainsKey (nodeName)) {
|
||||
ValuesAL = (List<object>) childNodeNames[nodeName];
|
||||
} else {
|
||||
//
|
||||
ValuesAL = new List<object> ();
|
||||
childNodeNames[nodeName] = ValuesAL;
|
||||
}
|
||||
|
||||
//
|
||||
ValuesAL.Add (nodeValue);
|
||||
}
|
||||
|
||||
//
|
||||
private static void OutputNode (string childname, object alChild, StringBuilder sbJSON, bool showNodeName) {
|
||||
if (alChild == null) {
|
||||
if (showNodeName)
|
||||
sbJSON.Append ("\"" + SafeJSON (childname) + "\": ");
|
||||
sbJSON.Append ("null");
|
||||
} else if (alChild is string) {
|
||||
if (showNodeName)
|
||||
sbJSON.Append ("\"" + SafeJSON (childname) + "\": ");
|
||||
string sChild = (string) alChild;
|
||||
sChild = sChild.Trim ();
|
||||
sbJSON.Append ("\"" + SafeJSON (sChild) + "\"");
|
||||
} else
|
||||
XmlToJSONnode (sbJSON, (XmlElement) alChild, showNodeName);
|
||||
sbJSON.Append (", ");
|
||||
}
|
||||
|
||||
//
|
||||
// Make a string safe for JSON
|
||||
private static string SafeJSON (string sIn) {
|
||||
//
|
||||
StringBuilder sbOut = new StringBuilder (sIn.Length);
|
||||
foreach (char ch in sIn) {
|
||||
//
|
||||
if (Char.IsControl (ch) || ch == '\'') {
|
||||
//
|
||||
int ich = (int) ch;
|
||||
sbOut.Append (@"\u" + ich.ToString ("x4"));
|
||||
continue;
|
||||
} else if (ch == '\"' || ch == '\\' || ch == '/') {
|
||||
sbOut.Append ('\\');
|
||||
}
|
||||
|
||||
//
|
||||
sbOut.Append (ch);
|
||||
}
|
||||
|
||||
//
|
||||
return sbOut.ToString ();
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,81 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Net.NetworkInformation;
|
||||
using System.Net.Sockets;
|
||||
using System.Threading.Tasks;
|
||||
using xCommons.Models;
|
||||
|
||||
namespace xCommons.Helpers {
|
||||
public static class XNetworkHelper {
|
||||
/// <summary>
|
||||
/// Retrieve Application Host's Machin IP Addresses ...
|
||||
/// </summary>
|
||||
/// <returns>string</returns>
|
||||
public static string GetIp () {
|
||||
//
|
||||
var name = Dns.GetHostName (); // get container id
|
||||
var result = Dns.GetHostEntry (name)
|
||||
.AddressList
|
||||
.FirstOrDefault (
|
||||
x => x.AddressFamily == AddressFamily.InterNetwork
|
||||
)
|
||||
.MapToIPv4 ()
|
||||
.ToString ();
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Retrieve All Available IP's in Application Host's Machin ...
|
||||
/// </summary>
|
||||
/// <returns>a Collection of XNetworkInfo class instances</returns>
|
||||
public static IEnumerable<XNetworkInfo> GetNetworkInfos () {
|
||||
//
|
||||
var result = System.Net.NetworkInformation.NetworkInterface
|
||||
.GetAllNetworkInterfaces ()
|
||||
.Where (
|
||||
ni =>
|
||||
!ni.IsReceiveOnly &&
|
||||
ni.OperationalStatus == OperationalStatus.Up &&
|
||||
ni.NetworkInterfaceType != NetworkInterfaceType.Loopback
|
||||
)
|
||||
.SelectMany (ni =>
|
||||
ni
|
||||
.GetIPProperties ()
|
||||
.GatewayAddresses
|
||||
.Select (ga =>
|
||||
new {
|
||||
Name = ni.Name,
|
||||
Description = ni.Description,
|
||||
Gateway = ga.Address
|
||||
.MapToIPv4 ()
|
||||
.ToString (),
|
||||
NI = ni
|
||||
}
|
||||
)
|
||||
)
|
||||
.SelectMany (data =>
|
||||
data.NI
|
||||
.GetIPProperties ()
|
||||
.UnicastAddresses
|
||||
.Select (ip =>
|
||||
new XNetworkInfo {
|
||||
Name = data.Name,
|
||||
Gateway = data.Gateway,
|
||||
Description = data.Description,
|
||||
NetworkInterface = data.NI,
|
||||
IP = ip.Address
|
||||
.MapToIPv4 ()
|
||||
.ToString ()
|
||||
}
|
||||
)
|
||||
);
|
||||
|
||||
//
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,70 @@
|
||||
using System;
|
||||
using System.Reflection;
|
||||
|
||||
namespace xCommons.Helpers {
|
||||
public static class XReflectionHelper {
|
||||
public static object GetFieldValue (this object obj, string fieldName) {
|
||||
if (obj == null)
|
||||
throw new ArgumentNullException (nameof (obj));
|
||||
Type objType = obj.GetType ();
|
||||
var fieldInfo = GetFieldInfo (objType, fieldName);
|
||||
if (fieldInfo == null)
|
||||
throw new ArgumentOutOfRangeException (fieldName,
|
||||
$"Couldn't find field {fieldName} in type {objType.FullName}");
|
||||
return fieldInfo.GetValue (obj);
|
||||
}
|
||||
|
||||
public static void SetFieldValue (this object obj, string fieldName, object val) {
|
||||
if (obj == null)
|
||||
throw new ArgumentNullException (nameof (obj));
|
||||
Type objType = obj.GetType ();
|
||||
var fieldInfo = GetFieldInfo (objType, fieldName);
|
||||
if (fieldInfo == null)
|
||||
throw new ArgumentOutOfRangeException (fieldName,
|
||||
$"Couldn't find field {fieldName} in type {objType.FullName}");
|
||||
fieldInfo.SetValue (obj, val);
|
||||
}
|
||||
|
||||
private static FieldInfo GetFieldInfo (Type type, string fieldName) {
|
||||
FieldInfo fieldInfo = null;
|
||||
do {
|
||||
fieldInfo = type.GetField (fieldName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
|
||||
type = type.BaseType;
|
||||
} while (fieldInfo == null && type != null);
|
||||
|
||||
return fieldInfo;
|
||||
}
|
||||
|
||||
public static object GetPropertyValue (this object obj, string propertyName) {
|
||||
if (obj == null)
|
||||
throw new ArgumentNullException (nameof (obj));
|
||||
Type objType = obj.GetType ();
|
||||
var propertyInfo = GetPropertyInfo (objType, propertyName);
|
||||
if (propertyInfo == null)
|
||||
throw new ArgumentOutOfRangeException (propertyName,
|
||||
$"Couldn't find property {propertyName} in type {objType.FullName}");
|
||||
return propertyInfo.GetValue (obj, null);
|
||||
}
|
||||
|
||||
public static void SetPropertyValue (this object obj, string propertyName, object val) {
|
||||
if (obj == null)
|
||||
throw new ArgumentNullException (nameof (obj));
|
||||
Type objType = obj.GetType ();
|
||||
var propertyInfo = GetPropertyInfo (objType, propertyName);
|
||||
if (propertyInfo == null)
|
||||
throw new ArgumentOutOfRangeException (propertyName,
|
||||
$"Couldn't find property {propertyName} in type {objType.FullName}");
|
||||
propertyInfo.SetValue (obj, val, null);
|
||||
}
|
||||
|
||||
private static PropertyInfo GetPropertyInfo (Type type, string propertyName) {
|
||||
PropertyInfo propertyInfo = null;
|
||||
do {
|
||||
propertyInfo = type.GetProperty (propertyName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
|
||||
type = type.BaseType;
|
||||
} while (propertyInfo == null && type != null);
|
||||
|
||||
return propertyInfo;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,144 @@
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using xCommons.Extensions;
|
||||
using xCommons.Models;
|
||||
|
||||
namespace xCommons.Middlewares {
|
||||
public partial class XRequestLogger {
|
||||
|
||||
private readonly ILogger logger;
|
||||
private readonly RequestDelegate next;
|
||||
|
||||
public XRequestLogger (
|
||||
RequestDelegate next,
|
||||
ILoggerFactory loggerFactory
|
||||
) {
|
||||
//
|
||||
this.next = next;
|
||||
this.logger = loggerFactory
|
||||
.CreateLogger<XRequestLogger> ();
|
||||
}
|
||||
|
||||
public async Task InvokeAsync (HttpContext context) {
|
||||
//
|
||||
var logModel = new XLoggerModel ();
|
||||
|
||||
//
|
||||
logModel.Path = context.Request.Path;
|
||||
logModel.Schema = context.Request.Scheme;
|
||||
logModel.Method = context.Request.Method;
|
||||
logModel.Headers = context.Request.Headers;
|
||||
logModel.Host = context.Request.Host.ToString ();
|
||||
logModel.QueryString = context.Request.QueryString.ToString ();
|
||||
logModel.UserID = context.User.Identity.IsAuthenticated ? context.User.Identity.Name : "Not Authenticated";
|
||||
|
||||
//
|
||||
logModel.Connection = new XLoggerHttpConnection {
|
||||
Id = context.Connection.Id,
|
||||
RemoteIpAddress = context.Connection.RemoteIpAddress.ToString (),
|
||||
RemotePort = context.Connection.RemotePort.ToString (),
|
||||
LocalIpAddress = context.Connection.LocalIpAddress.ToString (),
|
||||
LocalPort = context.Connection.LocalPort.ToString (),
|
||||
};
|
||||
|
||||
//
|
||||
// Check if a request is a Post Call so read data from Body ...
|
||||
if (context.Request.Method.ToNormalString () == "post") {
|
||||
//
|
||||
context.Request.EnableBuffering ();
|
||||
var request = await new StreamReader (context.Request.Body)
|
||||
.ReadToEndAsync ();
|
||||
|
||||
//
|
||||
context.Request.Body.Position = 0;
|
||||
logModel.Request = request;
|
||||
}
|
||||
|
||||
//
|
||||
logModel.RequestedOn = DateTime.UtcNow;
|
||||
|
||||
//
|
||||
// Do Request ...
|
||||
await next.Invoke (context);
|
||||
|
||||
//
|
||||
using (Stream originalRequest = context.Response.Body) {
|
||||
try {
|
||||
using (var memStream = new MemoryStream ()) {
|
||||
//
|
||||
context.Response.Body = memStream;
|
||||
|
||||
//
|
||||
// All the Request processing as described above
|
||||
// happens from here.
|
||||
// Response handling starts from here
|
||||
// set the pointer to the beginning of the
|
||||
// memory stream to read
|
||||
memStream.Position = 0;
|
||||
|
||||
//
|
||||
// read the memory stream till the end
|
||||
var response = await new StreamReader (memStream)
|
||||
.ReadToEndAsync ();
|
||||
|
||||
//
|
||||
logModel.Response = response;
|
||||
logModel.RespondedOn = DateTime.UtcNow;
|
||||
logModel.StatusCode = context.Response.StatusCode;
|
||||
logModel.IsSucceed = context.Response.StatusCode >= 200 && context.Response.StatusCode <= 299;
|
||||
|
||||
//
|
||||
// since we have read till the end of the stream,
|
||||
// reset it onto the first position
|
||||
memStream.Position = 0;
|
||||
|
||||
//
|
||||
// now copy the content of the temporary memory
|
||||
// stream we have passed to the actual response body
|
||||
// which will carry the response out.
|
||||
await memStream.CopyToAsync (originalRequest);
|
||||
}
|
||||
} catch (Exception ex) {
|
||||
//
|
||||
// Log Exception ...
|
||||
logger.LogError ($"Error on Logging Request/Response ... {ex.ToJSON()}");
|
||||
} finally {
|
||||
//
|
||||
// assign the response body to the actual context
|
||||
context.Response.Body = originalRequest;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Log Response ...
|
||||
logger.LogCritical ($"Http Response/Response Information:{Environment.NewLine}" +
|
||||
$"Schema:{logModel.Schema} " + Environment.NewLine +
|
||||
$"Host: {logModel.Host} " + Environment.NewLine +
|
||||
$"Path: {logModel.Path} " + Environment.NewLine +
|
||||
$"Method: {logModel.Method} " + Environment.NewLine +
|
||||
$"UserID: {logModel.UserID} " + Environment.NewLine +
|
||||
$"QueryString: {context.Request.QueryString} " + Environment.NewLine +
|
||||
$"Headers: {logModel.Headers.ToJSON()}" + Environment.NewLine +
|
||||
$"" + Environment.NewLine +
|
||||
$"Http Connection: " + Environment.NewLine +
|
||||
$"Id: {logModel.Connection.Id}" + Environment.NewLine +
|
||||
$"RemoteIpAddress: {logModel.Connection.RemoteIpAddress}" + Environment.NewLine +
|
||||
$"RemotePort: {logModel.Connection.RemotePort}" + Environment.NewLine +
|
||||
$"LocalIpAddress: {logModel.Connection.LocalIpAddress}" + Environment.NewLine +
|
||||
$"LocalPort: {logModel.Connection.LocalPort}" + Environment.NewLine +
|
||||
$"" + Environment.NewLine +
|
||||
$"Request Body: {logModel.Request}" + Environment.NewLine +
|
||||
$"RequestedOn: {logModel.RequestedOn}" + Environment.NewLine +
|
||||
$"" + Environment.NewLine +
|
||||
$"IsSucceed: {logModel.IsSucceed}" + Environment.NewLine +
|
||||
$"StatucCode: {logModel.StatusCode}" + Environment.NewLine +
|
||||
$"Response Body: {logModel.Response}" + Environment.NewLine +
|
||||
$"RespondedOn: {logModel.RespondedOn}" + Environment.NewLine +
|
||||
$"" + Environment.NewLine
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
namespace xCommons.Models {
|
||||
public partial class XCertificate {
|
||||
public string Path { get; set; }
|
||||
public string Secret { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
using System;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
|
||||
namespace xCommons.Models {
|
||||
public class XLoggerModel {
|
||||
public string Schema { get; set; }
|
||||
public string Host { get; set; }
|
||||
public string Path { get; set; }
|
||||
public string Method { get; set; }
|
||||
public string UserID { get; set; }
|
||||
public string QueryString { get; set; }
|
||||
public IHeaderDictionary Headers { get; set; }
|
||||
public string Request { get; set; }
|
||||
public int StatusCode { get; set; }
|
||||
public bool IsSucceed { get; set; }
|
||||
public string Response { get; set; }
|
||||
public DateTime RequestedOn { get; set; }
|
||||
public DateTime RespondedOn { get; set; }
|
||||
public XLoggerHttpConnection Connection { get; set; }
|
||||
}
|
||||
|
||||
public class XLoggerHttpConnection {
|
||||
public string Id { get; set; }
|
||||
public string RemoteIpAddress { get; set; }
|
||||
public string RemotePort { get; set; }
|
||||
public string LocalIpAddress { get; set; }
|
||||
public string LocalPort { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net.NetworkInformation;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace xCommons.Models {
|
||||
public class XNetworkInfo {
|
||||
/// <summary>
|
||||
/// Network Name ...
|
||||
/// </summary>
|
||||
/// <value></value>
|
||||
public string Name { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Network Description ...
|
||||
/// </summary>
|
||||
/// <value></value>
|
||||
public string Description { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// IP Address which Exists on Current Network ...
|
||||
/// </summary>
|
||||
/// <value></value>
|
||||
public string IP { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Current Networks Gateway Address ...
|
||||
/// </summary>
|
||||
/// <value></value>
|
||||
public string Gateway { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Network Interface Object ...
|
||||
/// </summary>
|
||||
/// <value></value>
|
||||
public NetworkInterface NetworkInterface { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,405 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using xCommons.Extensions;
|
||||
using xExceptions.Constants;
|
||||
|
||||
namespace xCommons.Providers {
|
||||
public partial class XValidationProvider {
|
||||
private ICollection<System.Action> validationGroup;
|
||||
|
||||
//
|
||||
#region Simple Validators ...
|
||||
/// <summary>
|
||||
/// given objects must not null
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotNull (
|
||||
params object[] values) {
|
||||
//
|
||||
foreach (var o in values) {
|
||||
//
|
||||
if (o == null) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// given strings must not empty or null
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotEmpty (
|
||||
params string[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s.IsNullOrEmpty ()) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a numeric value is bigger than 0
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotZero (
|
||||
params int[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s == 0) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a numeric value is bigger than 0
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotZero (
|
||||
params long[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s == 0) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a numeric value is bigger than 0
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotZero (
|
||||
params decimal[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s == 0) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a Value is a Valid Guid ...
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void IsGuid (params string[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (!s.IsGuid () || s.IsDefaultGuid ()) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a Value is a Valid Guid ...
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void IsGuid (params Guid[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s.IsNull () || s.IsDefaultGuid ()) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check a Value is an MD5 ...
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void IsMD5 (params string[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (!s.IsMD5String ()) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// non zero childs
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotZeroChilds (
|
||||
params IEnumerable<object>[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s == null ||
|
||||
s.Count () == 0) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// non zero childs
|
||||
/// </summary>
|
||||
/// <param name="values"></param>
|
||||
public void NotZeroChilds (
|
||||
params ICollection<object>[] values) {
|
||||
//
|
||||
foreach (var s in values) {
|
||||
//
|
||||
if (s == null ||
|
||||
s.Count == 0) {
|
||||
XException.InvalidArgs.Throw ();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// given string must be a valid URL ...
|
||||
/// </summary>
|
||||
/// <param name="url"></param>
|
||||
/// <param name="exception"></param>
|
||||
public void Url (
|
||||
string url,
|
||||
Exception exception = null
|
||||
) {
|
||||
//
|
||||
NotEmpty (url);
|
||||
|
||||
//
|
||||
if (exception == null) {
|
||||
exception = XException.InavlidUrl.ToException ();
|
||||
}
|
||||
|
||||
//
|
||||
if (!url.IsValidUrl ()) {
|
||||
throw exception;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// given string must be a valid Email Address ...
|
||||
/// </summary>
|
||||
/// <param name="emailAdress"></param>
|
||||
/// <param name="exception"></param>
|
||||
public void EmailAddress (
|
||||
string emailAdress,
|
||||
Exception exception = null
|
||||
) {
|
||||
//
|
||||
NotEmpty (emailAdress);
|
||||
|
||||
//
|
||||
if (exception == null) {
|
||||
exception = XException.InvalidEmailAddress.ToException ();
|
||||
}
|
||||
|
||||
//
|
||||
if (!emailAdress.IsValidEmail ()) {
|
||||
throw exception;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// given string must be a valid Mobile Number ...
|
||||
/// </summary>
|
||||
/// <param name="mobileNumber"></param>
|
||||
/// <param name="exception"></param>
|
||||
public void MobileNumber (
|
||||
string mobileNumber,
|
||||
Exception exception = null
|
||||
) {
|
||||
//
|
||||
NotEmpty (mobileNumber);
|
||||
|
||||
//
|
||||
if (exception == null) {
|
||||
exception = XException.InvalidMobileNumber.ToException ();
|
||||
}
|
||||
|
||||
//
|
||||
if (!mobileNumber.IsValidMobileNumber ()) {
|
||||
throw exception;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
//
|
||||
#region Group Validatos ...
|
||||
public XValidationProvider GroupValidationBuilder () {
|
||||
//
|
||||
validationGroup = new List<System.Action> ();
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotEmpty (params string[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotEmpty (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotNull (params object[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotNull (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotZero (params int[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotZero (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotZero (params long[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotZero (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotZero (params decimal[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotZero (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddIsGuid (params string[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.IsGuid (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddIsGuid (params Guid[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.IsGuid (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddIsMD5 (params string[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.IsMD5 (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotZeroChilds (params IEnumerable<object>[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotZeroChilds (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddNotZeroChilds (params ICollection<object>[] values) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.NotZeroChilds (values)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddEmailAddress (
|
||||
string emailAdress,
|
||||
Exception exception = null) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.EmailAddress (emailAdress, exception)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddMobileNumber (
|
||||
string mobileNumber,
|
||||
Exception exception = null) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.MobileNumber (mobileNumber, exception)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public XValidationProvider AddUrl (
|
||||
string url,
|
||||
Exception exception = null) {
|
||||
//
|
||||
this.validationGroup.Add (() =>
|
||||
this.Url (url, exception)
|
||||
);
|
||||
|
||||
//
|
||||
return this;
|
||||
}
|
||||
|
||||
public void ValidateGroup () {
|
||||
//
|
||||
// Run each Tasks ...
|
||||
foreach (var action in validationGroup) {
|
||||
action.Invoke ();
|
||||
}
|
||||
|
||||
//
|
||||
// Clear Task List ...
|
||||
validationGroup.Clear ();
|
||||
}
|
||||
|
||||
public async Task ValidateGroupAsync () {
|
||||
//
|
||||
// Run each Tasks ...
|
||||
foreach (var action in validationGroup) {
|
||||
await Task.Run (action);
|
||||
}
|
||||
|
||||
//
|
||||
// Clear Task List ...
|
||||
validationGroup.Clear ();
|
||||
}
|
||||
#endregion
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,148 @@
|
||||
# xCommons
|
||||
|
||||
it is a Part of xDashboard on SaherElm IT Center which provides:
|
||||
|
||||
- Common Configuration Models.
|
||||
- Common Usefull extra Extensions.
|
||||
- Data Validation Provider.
|
||||
- Provided features such as Enums, Models, Attributes, Filters, Authorization Policies, Middlewares and Helpers.
|
||||
- etc.
|
||||
|
||||
this module has no dependency and itself uses as a base dependency for all XProject modules/
|
||||
|
||||
for configure and use this Module refer to DI.XDIHelperExtension.cs file.
|
||||
|
||||
## Implementing
|
||||
|
||||
after adding this package as a dependency to your project you can do following:
|
||||
|
||||
### 1. Register it on DI
|
||||
|
||||
```c#
|
||||
public void ConfigureServices (IServiceCollection services) {
|
||||
...
|
||||
//
|
||||
// Register Validation Provider and all XCommons Module Services ...
|
||||
services.AddXCommons ();
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
this will provide XValidationHelper service which accessible through DI.
|
||||
|
||||
### 2. Register Application Configuration on DI
|
||||
|
||||
since many of features in this Framework works by accessing the configuration of class application. you had to register it on DI.
|
||||
|
||||
configure you app in **appSettings.json**:
|
||||
|
||||
```javascript
|
||||
{
|
||||
...
|
||||
"Version": "0.1",
|
||||
"Name": "SaherElm Sample App",
|
||||
"DefaultLanguage": "fa-IR",
|
||||
"XPoweredValue": "SaherElmITCenter",
|
||||
"WelcomeMessage": "Welcome to Application",
|
||||
"AllowedOrigins": [
|
||||
"http://localhost:4200",
|
||||
"https://localhost:4200"
|
||||
],
|
||||
...
|
||||
},
|
||||
```
|
||||
|
||||
then register your configuration on DI in **Startup** file:
|
||||
|
||||
```c#
|
||||
public void ConfigureServices (IServiceCollection services) {
|
||||
...
|
||||
//
|
||||
// Register App Configuration ...
|
||||
services.AddXAppConfiguration (Configuration);
|
||||
var appConfiguration = services.GetRegisteredService<XAppConfiguration> ();
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
### 3. Register Available Cross Origin Resource sharing (Cors)
|
||||
|
||||
for determining which addresses can access your application and enabling core mechanism you can simply do it by follow this structure ...
|
||||
|
||||
**NOTE**: notice that you have configured allowed origins in **appSettings.json** before on AppConfiguration section.
|
||||
|
||||
```c#
|
||||
public void ConfigureServices (IServiceCollection services) {
|
||||
...
|
||||
//
|
||||
// Register Allowed Origins ...
|
||||
services.AddXCors (appConfiguration.AllowedOrigins);
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
the you can enable cors handling like this:
|
||||
|
||||
```c#
|
||||
public void Configure (IApplicationBuilder app, IWebHostEnvironment env) {
|
||||
...
|
||||
//
|
||||
// Using Cors ...
|
||||
app.UseXCors ();
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
**Note**: remember **AllowedOrigins** can provided using **appSettings.json** file dynamically;
|
||||
|
||||
### 4. Enable Swagger
|
||||
|
||||
also you can add swagger documentation to your project:
|
||||
|
||||
```c#
|
||||
public void ConfigureServices (IServiceCollection services) {
|
||||
...
|
||||
//
|
||||
// Register Api Versioning ...
|
||||
services.AddApiVersioning (opt => {
|
||||
//
|
||||
// Set Default Api Version ...
|
||||
opt.DefaultApiVersion = new ApiVersion (1, 0);
|
||||
|
||||
//
|
||||
// Set Routing to Default API Version, if Version unspecified ...
|
||||
opt.AssumeDefaultVersionWhenUnspecified = true;
|
||||
|
||||
//
|
||||
// Report All Available Api Versions on Response ...
|
||||
opt.ReportApiVersions = true;
|
||||
});
|
||||
|
||||
//
|
||||
// Register Swagger ...
|
||||
var xmlFile = $"{Assembly.GetExecutingAssembly().GetName().Name}.xml";
|
||||
var xmlPath = Path.Combine (AppContext.BaseDirectory, xmlFile);
|
||||
services.AddXSwagger (Configuration, xmlFilePath : xmlPath);
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
the you can enable swagger middleware like this:
|
||||
|
||||
```c#
|
||||
public void Configure (IApplicationBuilder app, IWebHostEnvironment env) {
|
||||
...
|
||||
//
|
||||
// Use Swagger Middleware ...
|
||||
app.UseXSwagger ();
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
## Maintainer
|
||||
|
||||
Hadi Khazaee asl
|
||||
|
||||
[https://www.saherelm.ir](https://www.saherelm.ir)
|
||||
|
||||
[hadi_khazaee_asl@yahoo.com](mailto:hadi_khazaee_asl@yahoo.com)
|
||||
@@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<configuration>
|
||||
<packageSources>
|
||||
<add key="nuget" value="https://api.nuget.org/v3/index.json" protocolVersion="3" />
|
||||
<add key="liget" value="https://nuget.saherelmhub.ir/v3/index.json" protocolVersion="3" />
|
||||
</packageSources>
|
||||
</configuration>
|
||||
@@ -0,0 +1,63 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<!-- Runtime Definition -->
|
||||
<PropertyGroup>
|
||||
<TargetFramework>netstandard2.0</TargetFramework>
|
||||
<PackageId>xDashboard.xCommons</PackageId>
|
||||
<Version>1.0.0</Version>
|
||||
<Authors>Hadi Khazaee Asl</Authors>
|
||||
<Company>SaherElm IT Center</Company>
|
||||
<Description>
|
||||
provide all commonly used actions/extensions and classes which required to xDashboard project.
|
||||
</Description>
|
||||
|
||||
<!-- Icon Definition -->
|
||||
<PackageIcon>icon.png</PackageIcon>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Icon Handling -->
|
||||
<ItemGroup>
|
||||
<None Include="../../Resources/Images/favicon.png" Link="icon.png" Pack="true" PackagePath="\icon.png" />
|
||||
</ItemGroup>
|
||||
|
||||
<!-- Local Dependencies -->
|
||||
<ItemGroup>
|
||||
<PackageReference Include="xDashboard.xExceptions" Version="1.0.0" />
|
||||
<!-- <ProjectReference Include="../xExceptions/xExceptions.csproj" /> -->
|
||||
</ItemGroup>
|
||||
|
||||
<!-- Dependencies -->
|
||||
<ItemGroup>
|
||||
<PackageReference Include="AutoMapper" Version="10.1.1" />
|
||||
<PackageReference Include="IdentityModel" Version="5.0.1" />
|
||||
<PackageReference Include="System.Reactive" Version="5.0.0" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="12.0.3" />
|
||||
<PackageReference Include="libphonenumber-csharp" Version="8.12.17" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Cors" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.Core" Version="2.2.5" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration" Version="5.0.0" />
|
||||
<PackageReference Include="Microsoft.IO.RecyclableMemoryStream" Version="1.4.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.Abstractions" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="5.0.1" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Authorization.Policy" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="5.0.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.Abstractions" Version="2.2.0" />
|
||||
<PackageReference Include="AutoMapper.Extensions.Microsoft.DependencyInjection" Version="8.1.0" />
|
||||
</ItemGroup>
|
||||
|
||||
<!-- Swagger -->
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.0.2" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerGen" Version="6.0.2" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerUI" Version="6.0.2" />
|
||||
</ItemGroup>
|
||||
|
||||
<!-- For XML Documentation Support -->
|
||||
<PropertyGroup>
|
||||
<CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
|
||||
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
||||
<NoWarn>$(NoWarn);1591</NoWarn>
|
||||
</PropertyGroup>
|
||||
|
||||
</Project>
|
||||
Reference in New Issue
Block a user