changeset 4440:95262bd1bcb2

mod_register_web: Add hCaptcha provider
author Michel Le Bihan <michel@lebihan.pl>
date Mon, 15 Feb 2021 21:04:19 +0100
parents 6ae1c7b9c58b
children 58a112bd9792
files mod_register_web/mod_register_web.lua mod_register_web/templates/hcaptcha.html
diffstat 2 files changed, 73 insertions(+), 31 deletions(-) [+]
line wrap: on
line diff
--- a/mod_register_web/mod_register_web.lua	Mon Feb 15 20:23:28 2021 +0100
+++ b/mod_register_web/mod_register_web.lua	Mon Feb 15 21:04:19 2021 +0100
@@ -42,40 +42,76 @@
 -- COMPAT `or request.conn:ip()`
 
 if next(captcha_options) ~= nil then
-	local recaptcha_tpl = get_template "recaptcha";
+	local provider = captcha_options.provider;
+	if provider == nil or provider == "recaptcha" then
+		local recaptcha_tpl = get_template "recaptcha";
 
-	function generate_captcha(display_options)
-		return recaptcha_tpl.apply(setmetatable({
-			recaptcha_display_error = display_options and display_options.recaptcha_error
-			and ("&error="..display_options.recaptcha_error) or "";
-		}, {
-			__index = function (_, k)
-				if captcha_options[k] then return captcha_options[k]; end
-				module:log("error", "Missing parameter from captcha_options: %s", k);
-			end
-		}));
-	end
-	function verify_captcha(request, form, callback)
-		http.request("https://www.google.com/recaptcha/api/siteverify", {
-			body = http.formencode {
-				secret = captcha_options.recaptcha_private_key;
-				remoteip = request.ip or request.conn:ip();
-				response = form["g-recaptcha-response"];
-			};
-		}, function (verify_result, code)
-			local result = json(verify_result);
-			if not result then
-				module:log("warn", "Unable to decode response from recaptcha: [%d] %s", code, verify_result);
-				callback(false, "Captcha API error");
-			elseif result.success == true then
-				callback(true);
-			else
-				callback(false, t_concat(result["error-codes"]));
-			end
-		end);
+		function generate_captcha(display_options)
+			return recaptcha_tpl.apply(setmetatable({
+				recaptcha_display_error = display_options and display_options.recaptcha_error
+				and ("&error="..display_options.recaptcha_error) or "";
+			}, {
+				__index = function (_, k)
+					if captcha_options[k] then return captcha_options[k]; end
+					module:log("error", "Missing parameter from captcha_options: %s", k);
+				end
+			}));
+		end
+		function verify_captcha(request, form, callback)
+			http.request("https://www.google.com/recaptcha/api/siteverify", {
+				body = http.formencode {
+					secret = captcha_options.recaptcha_private_key;
+					remoteip = request.ip or request.conn:ip();
+					response = form["g-recaptcha-response"];
+				};
+			}, function (verify_result, code)
+				local result = json(verify_result);
+				if not result then
+					module:log("warn", "Unable to decode response from recaptcha: [%d] %s", code, verify_result);
+					callback(false, "Captcha API error");
+				elseif result.success == true then
+					callback(true);
+				else
+					callback(false, t_concat(result["error-codes"]));
+				end
+			end);
+		end
+	elseif provider == "hcaptcha" then
+		local captcha_tpl = get_template "hcaptcha";
+
+		function generate_captcha(display_options)
+			return captcha_tpl.apply(setmetatable({
+				captcha_display_error = display_options and display_options.captcha_error
+				and ("&error="..display_options.captcha_error) or "";
+			}, {
+				__index = function (_, k)
+					if captcha_options[k] then return captcha_options[k]; end
+					module:log("error", "Missing parameter from captcha_options: %s", k);
+				end
+			}));
+		end
+		function verify_captcha(request, form, callback)
+			http.request("https://hcaptcha.com/siteverify", {
+				body = http.formencode {
+					secret = captcha_options.captcha_private_key;
+					remoteip = request.ip or request.conn:ip();
+					response = form["h-captcha-response"];
+				};
+			}, function (verify_result, code)
+				local result = json(verify_result);
+				if not result then
+					module:log("warn", "Unable to decode response from hcaptcha: [%d] %s", code, verify_result);
+					callback(false, "Captcha API error");
+				elseif result.success == true then
+					callback(true);
+				else
+					callback(false, t_concat(result["error-codes"]));
+				end
+			end);
+		end
 	end
 else
-	module:log("debug", "No Recaptcha options set, using fallback captcha")
+	module:log("debug", "No captcha options set, using fallback captcha")
 	local random = math.random;
 	local hmac_sha1 = require "util.hashes".hmac_sha1;
 	local secret = require "util.uuid".generate()
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mod_register_web/templates/hcaptcha.html	Mon Feb 15 21:04:19 2021 +0100
@@ -0,0 +1,6 @@
+<tr>
+  <td colspan="2">
+    <script src="https://hcaptcha.com/1/api.js" async defer></script>
+    <div class="h-captcha" data-sitekey="{captcha_public_key}"></div>
+  </td>
+</tr>