Skip to content

Commit

Permalink
Merge pull request #41 from HoodDigital/dev
Browse files Browse the repository at this point in the history
v6.0.10
  • Loading branch information
JorjeRedemption authored May 25, 2022
2 parents 8dc7ad3 + 6fbae46 commit 2ba74be
Show file tree
Hide file tree
Showing 49 changed files with 118 additions and 8,779 deletions.
55 changes: 0 additions & 55 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -54,61 +54,6 @@
"sourceFileMap": {
"/Views": "${workspaceFolder}/projects/Hood.Development/Views"
}
},

{
// Use IntelliSense to find out which attributes exist for C# debugging
// Use hover for the description of the existing attributes
// For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
"name": "Hood.Web (Development)",
"type": "coreclr",
"request": "launch",
"preLaunchTask": "build-web",
// If you have changed target frameworks, make sure to update the program path.
"program": "${workspaceFolder}/projects/Hood.Web/bin/Debug/net5.0/Hood.Web.dll",
"args": [],
"cwd": "${workspaceFolder}/projects/Hood.Web/",
"stopAtEntry": false,
// Enable launching a web browser when ASP.NET Core starts. For more information: https://aka.ms/VSCode-CS-LaunchJson-WebBrowser
"serverReadyAction": {
"action": "openExternally",
"pattern": "\\bNow listening on:\\s+(https?://\\S+)"
},
"env": {
"ASPNETCORE_ENVIRONMENT": "Development",
"ASPNETCORE_URLS": "https://localhost:5153",
"Hood:BypassCDN": "true"
},
"sourceFileMap": {
"/Views": "${workspaceFolder}/projects/Hood.Web/Views"
}
},
{
// Use IntelliSense to find out which attributes exist for C# debugging
// Use hover for the description of the existing attributes
// For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
"name": "Hood.Web (Production)",
"type": "coreclr",
"request": "launch",
"preLaunchTask": "build-web",
// If you have changed target frameworks, make sure to update the program path.
"program": "${workspaceFolder}/projects/Hood.Web/bin/Debug/net5.0/Hood.Web.dll",
"args": [],
"cwd": "${workspaceFolder}/projects/Hood.Web/",
"stopAtEntry": false,
// Enable launching a web browser when ASP.NET Core starts. For more information: https://aka.ms/VSCode-CS-LaunchJson-WebBrowser
"serverReadyAction": {
"action": "openExternally",
"pattern": "\\bNow listening on:\\s+(https?://\\S+)"
},
"env": {
"ASPNETCORE_ENVIRONMENT": "Production",
"ASPNETCORE_URLS": "https://localhost:5153",
"Hood:BypassCDN": "true"
},
"sourceFileMap": {
"/Views": "${workspaceFolder}/projects/Hood.Web/Views"
}
}
]
}
2 changes: 1 addition & 1 deletion projects/Hood.Admin/Hood.Admin.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<AssemblyName>Hood.Admin</AssemblyName>
<PackageId>Hood.Admin</PackageId>

<Version>6.0.9</Version>
<Version>6.0.10</Version>
<TargetFramework>net5.0</TargetFramework>
<Authors>Hood Digital;George Whysall;</Authors>
<OutputType>Library</OutputType>
Expand Down
2 changes: 1 addition & 1 deletion projects/Hood.Core.Admin/Hood.Core.Admin.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<AssemblyName>Hood.Core.Admin</AssemblyName>
<PackageId>Hood.Core.Admin</PackageId>

<Version>6.0.9</Version>
<Version>6.0.10</Version>
<TargetFramework>net5.0</TargetFramework>
<Authors>Hood Digital;George Whysall;</Authors>
<OutputType>Library</OutputType>
Expand Down
38 changes: 0 additions & 38 deletions projects/Hood.Core/Extensions/HttpContextExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,44 +12,6 @@ namespace Hood.Extensions
{
public static class HttpContextExtensions
{
public static async Task ProcessCaptchaOrThrowAsync(this HttpRequest request)
{
if (Engine.Settings.Integrations.EnableGoogleRecaptcha)
{
var captcha = request.Form["g-recaptcha-response"].FirstOrDefault();
if (captcha.IsSet())
{
// process the captcha.
using (var client = new HttpClient())
{
var remoteIpAddress = request.HttpContext.Connection.RemoteIpAddress.ToString();
var values = new Dictionary<string, string>
{
{ "secret", Engine.Settings.Integrations.GoogleRecaptchaSecretKey },
{ "response", captcha },
{ "remoteip", remoteIpAddress }
};

var content = new FormUrlEncodedContent(values);

var responseContent = await client.PostAsync("https://www.google.com/recaptcha/api/siteverify", content);

var responseString = await responseContent.Content.ReadAsStringAsync();

RecaptchaResponse response = JsonConvert.DeserializeObject<RecaptchaResponse>(responseString);

if (!response.success)
throw new Exception("Sorry, your reCaptcha validation failed.");

if (request.Host.Host != response.hostname)
throw new Exception("Sorry, your reCaptcha validation failed, your host name does not match the validated host name.");
}
}
else
throw new Exception("Sorry, your reCaptcha validation failed, no captcha response found.");
}
}

public static string GetSubdomain(this HttpContext httpContext)
{

Expand Down
2 changes: 1 addition & 1 deletion projects/Hood.Core/Hood.Core.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<AssemblyName>Hood.Core</AssemblyName>
<PackageId>Hood.Core</PackageId>

<Version>6.0.9</Version>
<Version>6.0.10</Version>
<TargetFramework>net5.0</TargetFramework>
<Authors>Hood Digital;George Whysall;</Authors>
<OutputType>Library</OutputType>
Expand Down
2 changes: 2 additions & 0 deletions projects/Hood.Core/Models/Settings/IntegrationSettings.cs
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,8 @@ public bool IsGoogleRecaptchaEnabled
public string GoogleRecaptchaSiteKey { get; set; }
[Display(Name = "Google Recaptcha Secret Key")]
public string GoogleRecaptchaSecretKey { get; set; }
[Display(Name = "Google Recaptcha Security Threshold")]
public decimal GoogleRecaptchaThreshold { get; set; }


// Unsplash Api
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,6 @@ namespace Hood.Services
{
public interface IRecaptchaService
{
System.Threading.Tasks.Task<RecaptchaResponse> Validate(HttpRequest request, bool antiForgery = true);
System.Threading.Tasks.Task<RecaptchaResponse> Validate(HttpRequest request);
}
}
26 changes: 21 additions & 5 deletions projects/Hood.Core/Services/RecaptchaService/RecaptchaResponse.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,20 +5,36 @@ namespace Hood.Services
{
public class RecaptchaResponse
{
public RecaptchaResponse()
{ }

public RecaptchaResponse(bool success, string message)
{
Passed = success;
Message = message;
}

[JsonProperty(PropertyName = "success")]
public bool Success { get; set; }
internal bool Success { get; set; }

[JsonProperty(PropertyName = "score")]
public decimal Score { get; set; }
internal decimal Score { get; set; }

[JsonProperty(PropertyName = "action")]
public string Action { get; set; }
internal string Action { get; set; }

[JsonProperty(PropertyName = "challenge_ts")]
public DateTime ChallengeTS { get; set; }
internal DateTime ChallengeTS { get; set; }

[JsonProperty(PropertyName = "hostname")]
public string HostName { get; set; }
internal string HostName { get; set; }

[JsonIgnore]
public bool Passed { get; internal set; }

[JsonIgnore]
public string Message { get; internal set; }

}
}

52 changes: 34 additions & 18 deletions projects/Hood.Core/Services/RecaptchaService/RecaptchaService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,35 +10,51 @@ namespace Hood.Services
public class RecaptchaService : IRecaptchaService
{
public static bool UseRecaptchaNet { get; set; } = false;
public async Task<RecaptchaResponse> Validate(HttpRequest request, bool antiForgery = true)
public async Task<RecaptchaResponse> Validate(HttpRequest request)
{
Models.IntegrationSettings settings = Engine.Settings.Integrations;
try
{
Models.IntegrationSettings settings = Engine.Settings.Integrations;

if (!Engine.Settings.Integrations.EnableGoogleRecaptcha)
return new RecaptchaResponse() { Success = true };
if (!Engine.Settings.Integrations.EnableGoogleRecaptcha)
return new RecaptchaResponse() { Success = true };

if (!request.Form.ContainsKey("g-recaptcha-response")) // error if no reason to do anything, this is to alert developers they are calling it without reason.
{
throw new ValidationException("Google recaptcha response not found in form. Did you forget to include it?");
}
if (!request.Form.ContainsKey("g-recaptcha-response")) // error if no reason to do anything, this is to alert developers they are calling it without reason.
{
throw new ValidationException("Google recaptcha response not found in form. Did you forget to include it?");
}

string domain = UseRecaptchaNet ? "www.recaptcha.net" : "www.google.com";
string response = request.Form["g-recaptcha-response"];
string domain = UseRecaptchaNet ? "www.recaptcha.net" : "www.google.com";
string response = request.Form["g-recaptcha-response"];

HttpClient client = new HttpClient();
string result = await client.GetStringAsync($"https://{domain}/recaptcha/api/siteverify?secret={settings.GoogleRecaptchaSecretKey}&response={response}");
RecaptchaResponse captchaResponse = JsonConvert.DeserializeObject<RecaptchaResponse>(result);
client.Dispose();
HttpClient client = new HttpClient();
string result = await client.GetStringAsync($"https://{domain}/recaptcha/api/siteverify?secret={settings.GoogleRecaptchaSecretKey}&response={response}");
RecaptchaResponse captchaResponse = JsonConvert.DeserializeObject<RecaptchaResponse>(result);
client.Dispose();

if (!captchaResponse.Success)
{
throw new ValidationException("Recaptcha failed to validate.");
}

if (captchaResponse.Success && antiForgery)
{
if (captchaResponse.HostName?.ToLower() != request.Host.Host?.ToLower())
{
throw new ValidationException("Recaptcha host, and request host do not match. Forgery attempt?");
}
}

return captchaResponse;
if (captchaResponse.Score < Engine.Settings.Integrations.GoogleRecaptchaThreshold)
{
throw new ValidationException("Recaptcha failed to pass security threshold.");
}

// Reached here? Fairly sure we are golden, marke as passed and return.
captchaResponse.Passed = true;
return captchaResponse;
}
catch (ValidationException ex)
{
return new RecaptchaResponse(false, ex.Message);
}
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,10 @@
Layout = "_Layout_Settings";
}
@section buttons {
@if (User.IsAdminOrBetter())
{
<a asp-action="ResetIntegrations" class="btn btn-danger warning-alert" data-warning="This will completely reset these settings to their default state, are you sure!?"><i class="fa fa-refresh"></i> Reset to Default</a>
}
@if (User.IsAdminOrBetter())
{
<a asp-action="ResetIntegrations" class="btn btn-danger warning-alert" data-warning="This will completely reset these settings to their default state, are you sure!?"><i class="fa fa-refresh"></i> Reset to Default</a>
}
}
<div class="card">
<div class="card-header">
Expand Down Expand Up @@ -59,11 +59,22 @@
<label asp-for="GoogleRecaptchaSiteKey"></label>
<small asp-for="GoogleRecaptchaSiteKey"></small>
</div>
<div class="form-floating">
<div class="form-floating mb-3">
<input asp-for="GoogleRecaptchaSecretKey" class="form-control">
<label asp-for="GoogleRecaptchaSecretKey"></label>
<small asp-for="GoogleRecaptchaSecretKey"></small>
</div>
<div class="form-floating">
<select asp-for="GoogleRecaptchaThreshold" class="form-select">
<option value="0.1">Easy</option>
<option value="0.3">Low</option>
<option value="0.5">Medium</option>
<option value="0.7">High</option>
<option value="0.9">Strict</option>
</select>
<label asp-for="GoogleRecaptchaThreshold"></label>
<small asp-for="GoogleRecaptchaThreshold"></small>
</div>
</div>
<div id="unsplash" class="tab-pane in" role="tabpanel" aria-labelledby="unsplash-tab">
<div class="form-floating mb-3">
Expand Down
30 changes: 15 additions & 15 deletions projects/Hood.Development/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "hoodcms",
"version": "6.0.9",
"version": "6.0.10",
"description": "A fully customisable content management system built in ASP.NET Core 5 & Bootstrap 5.",
"keywords": [
"hood",
Expand Down Expand Up @@ -48,9 +48,9 @@
"dependencies": {
"@popperjs/core": "^2.11.5",
"@simonwep/pickr": "^1.8.2",
"@types/bootstrap": "^5.1.9",
"@types/bootstrap": "^5.1.12",
"@types/dropzone": "^5.7.4",
"@types/google.maps": "^3.48.5",
"@types/google.maps": "^3.49.0",
"@types/jquery": "^3.5.14",
"@types/jquery-toast-plugin": "^1.3.3",
"@types/jquery.slimscroll": "^1.3.31",
Expand All @@ -61,17 +61,17 @@
"jquery": "^3.6.0",
"jquery-slimscroll": "^1.3.8",
"jquery-toast-plugin": "^1.3.2",
"jquery-validation": "^1.19.3",
"sweetalert2": "^11.4.8",
"jquery-validation": "^1.19.4",
"sweetalert2": "^11.4.16",
"tinymce": "^5.10.3"
},
"devDependencies": {
"@lopatnov/rollup-plugin-uglify": "^2.1.2",
"@rollup/plugin-commonjs": "^21.0.3",
"@rollup/plugin-node-resolve": "^13.1.3",
"@rollup/plugin-typescript": "^8.3.1",
"cssnano": "^5.1.7",
"eslint": "^8.12.0",
"@rollup/plugin-node-resolve": "^13.3.0",
"@rollup/plugin-typescript": "^8.3.2",
"cssnano": "^5.1.9",
"eslint": "^8.16.0",
"gulp": "^4.0.2",
"gulp-autoprefixer": "^8.0.0",
"gulp-concat": "^2.6.1",
Expand All @@ -85,13 +85,13 @@
"node-sass-tilde-importer": "^1.0.2",
"npm-run-all": "^4.1.5",
"npm-watch": "^0.11.0",
"postcss": "^8.4.12",
"rollup": "^2.70.1",
"postcss": "^8.4.14",
"rollup": "^2.74.1",
"rollup-pluginutils": "^2.8.2",
"sass": "^1.49.11",
"stylelint": "^14.6.1",
"terser": "^5.12.1",
"typescript": "^4.6.3"
"sass": "^1.52.1",
"stylelint": "^14.8.3",
"terser": "^5.13.1",
"typescript": "^4.6.4"
},
"watch": {
"scss": {
Expand Down
Loading

0 comments on commit 2ba74be

Please sign in to comment.