changeset 5222:578a72982bb2

mod_http_oauth2: Separate extracting credentials from requests and verifying The token endpoint also uses Basic auth, but the password would be the client_secret, so we need to verify against that instead of using test_password(). Splitting this up here avoids code duplication. Possibly this new function could go into util.http...
author Matthew Wild <mwild1@gmail.com>
date Tue, 07 Mar 2023 15:18:41 +0000
parents 22483cfce3ce
children 8b2a36847912
files mod_http_oauth2/mod_http_oauth2.lua
diffstat 1 files changed, 28 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/mod_http_oauth2/mod_http_oauth2.lua	Tue Mar 07 14:52:43 2023 +0000
+++ b/mod_http_oauth2/mod_http_oauth2.lua	Tue Mar 07 15:18:41 2023 +0000
@@ -341,22 +341,43 @@
 	return {};
 end
 
-local function check_credentials(request, allow_token)
+local function get_request_credentials(request)
 	local auth_type, auth_data = string.match(request.headers.authorization, "^(%S+)%s(.+)$");
 
 	if auth_type == "Basic" then
 		local creds = base64.decode(auth_data);
-		if not creds then return false; end
+		if not creds then return; end
 		local username, password = string.match(creds, "^([^:]+):(.*)$");
-		if not username then return false; end
-		username, password = encodings.stringprep.nodeprep(username), encodings.stringprep.saslprep(password);
-		if not username then return false; end
+		if not username then return; end
+		return {
+			type = "basic";
+			username = username;
+			password = password;
+		};
+	elseif auth_type == "Bearer" then
+		return {
+			type = "bearer";
+			bearer_token = auth_data;
+		};
+	end
+
+	return nil;
+end
+
+local function check_credentials(request, allow_token)
+	local credentials = get_request_credentials(request);
+	if not credentials then return nil; end
+
+	if credentials.username and credentials.password then
+		local username = encodings.stringprep.nodeprep(credentials.username);
+		local password = encodings.stringprep.saslprep(credentials.password);
+		if not (username and password) then return false; end
 		if not usermanager.test_password(username, module.host, password) then
 			return false;
 		end
 		return username;
-	elseif auth_type == "Bearer" and allow_token then
-		local token_info = tokens.get_token_info(auth_data);
+	elseif allow_token and credentials.bearer_token then
+		local token_info = tokens.get_token_info(credentials.bearer_token);
 		if not token_info or not token_info.session or token_info.session.host ~= module.host then
 			return false;
 		end