File

util/jwt.lua @ 12047:81858fd6f198

mod_smacks: Flag both sessions to prevent duplicating queue on resumption I have no idea what is going on in this code, which session is which? Something has one of the sessions as an upvalue which is where the filter checks for it.
author Kim Alvefur <zash@zash.se>
date Tue, 14 Dec 2021 12:59:38 +0100
parent 11561:d2f33b8fdc96
child 12696:27a72982e331
line wrap: on
line source

local s_gsub = string.gsub;
local json = require "util.json";
local hashes = require "util.hashes";
local base64_encode = require "util.encodings".base64.encode;
local base64_decode = require "util.encodings".base64.decode;
local secure_equals = require "util.hashes".equals;

local b64url_rep = { ["+"] = "-", ["/"] = "_", ["="] = "", ["-"] = "+", ["_"] = "/" };
local function b64url(data)
	return (s_gsub(base64_encode(data), "[+/=]", b64url_rep));
end
local function unb64url(data)
	return base64_decode(s_gsub(data, "[-_]", b64url_rep).."==");
end

local static_header = b64url('{"alg":"HS256","typ":"JWT"}') .. '.';

local function sign(key, payload)
	local encoded_payload = json.encode(payload);
	local signed = static_header .. b64url(encoded_payload);
	local signature = hashes.hmac_sha256(key, signed);
	return signed .. "." .. b64url(signature);
end

local jwt_pattern = "^(([A-Za-z0-9-_]+)%.([A-Za-z0-9-_]+))%.([A-Za-z0-9-_]+)$"
local function verify(key, blob)
	local signed, bheader, bpayload, signature = string.match(blob, jwt_pattern);
	if not signed then
		return nil, "invalid-encoding";
	end
	local header = json.decode(unb64url(bheader));
	if not header or type(header) ~= "table" then
		return nil, "invalid-header";
	elseif header.alg ~= "HS256" then
		return nil, "unsupported-algorithm";
	end
	if not secure_equals(b64url(hashes.hmac_sha256(key, signed)), signature) then
		return false, "signature-mismatch";
	end
	local payload, err = json.decode(unb64url(bpayload));
	if err ~= nil then
		return nil, "json-decode-error";
	end
	return true, payload;
end

return {
	sign = sign;
	verify = verify;
};