Skip to content

Commit eb38cce

Browse files
authored
Merge pull request #525 from zmartzone/try-to-fix-ff-logout
restrict zero-pixel image logout to actual image requests
2 parents 9f3a4fc + ab9c386 commit eb38cce

File tree

3 files changed

+59
-4
lines changed

3 files changed

+59
-4
lines changed

Diff for: ChangeLog

+4
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
08/25/2024
2+
- don't return a zero-pixel image in logout for Firefox 128 and later
3+
see #521
4+
15
03/10/2023
26
- when looking for a bearer token an exception occured if the
37
Authorization header didn't contain any space character;

Diff for: lib/resty/openidc.lua

+34-3
Original file line numberDiff line numberDiff line change
@@ -1280,6 +1280,38 @@ local openidc_transparent_pixel = "\137\080\078\071\013\010\026\010\000\000\000\
12801280
"\002\007\001\002\154\028\049\113\000\000\000\000\073\069\078\068" ..
12811281
"\174\066\096\130"
12821282

1283+
local function request_prefers_png_over_html()
1284+
local headers = ngx.req.get_headers()
1285+
local header = get_first(headers['Accept'])
1286+
if not header then return false end
1287+
1288+
-- https://httpwg.org/specs/rfc9110.html#field.accept
1289+
local accepted = {}
1290+
local function append_accepted_type(media_range_and_quality)
1291+
local media_range, quality = media_range_and_quality:match("(.+)%s*;%s*q=%s*([^%s]+)")
1292+
if media_range and quality then
1293+
accepted[#accepted + 1] = {media_range=media_range, quality=tonumber(quality)}
1294+
else
1295+
accepted[#accepted + 1] = {media_range=media_range_and_quality, quality=1}
1296+
end
1297+
end
1298+
header:gsub("[^,]+", append_accepted_type)
1299+
1300+
table.sort(accepted, function(a1, a2)
1301+
return a1.quality > a2.quality
1302+
end)
1303+
1304+
for _, a in ipairs(accepted) do
1305+
if a.media_range:find("text/html") or a.media_range:find("application/xhtml%+xml") then
1306+
return false
1307+
end
1308+
if a.media_range:find("image/png") then
1309+
return true
1310+
end
1311+
end
1312+
return false
1313+
end
1314+
12831315
-- handle logout
12841316
local function openidc_logout(opts, session)
12851317
local session_token = session.data.enc_id_token
@@ -1308,9 +1340,8 @@ local function openidc_logout(opts, session)
13081340
end
13091341
end
13101342

1311-
local headers = ngx.req.get_headers()
1312-
local header = get_first(headers['Accept'])
1313-
if header and header:find("image/png") then
1343+
if request_prefers_png_over_html() then
1344+
-- support for Ping Federate's proprietary logout protocol
13141345
ngx.header["Cache-Control"] = "no-cache, no-store"
13151346
ngx.header["Pragma"] = "no-cache"
13161347
ngx.header["P3P"] = "CAO PSA OUR"

Diff for: tests/spec/logout_spec.lua

+21-1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,26 @@ describe("when the configured logout uri is invoked with a non-image request", f
2222
end)
2323
end)
2424

25+
describe("when the configured logout uri is invoked with Firefox 128's default Accept", function()
26+
test_support.start_server()
27+
teardown(test_support.stop_server)
28+
local _, _, cookie = test_support.login()
29+
local _, status, headers = http.request({
30+
url = "http://127.0.0.1/default/logout",
31+
headers = { cookie = cookie, accept = "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/png,image/svg+xml,*/*;q=0.8" },
32+
redirect = false
33+
})
34+
it("the response contains a default HTML-page", function()
35+
assert.are.equals(200, status)
36+
assert.are.equals("text/html", headers["content-type"])
37+
-- TODO should there be a Cache-Control header?
38+
end)
39+
it("the session cookie has been revoked", function()
40+
assert.truthy(string.match(headers["set-cookie"],
41+
"session=; Expires=Thu, 01 Jan 1970 00:00:01 GMT.*"))
42+
end)
43+
end)
44+
2545
describe("when the configured logout uri is invoked with a png request", function()
2646
-- TODO should this really take precedence over a configured end_session_endpoint?
2747
test_support.start_server({
@@ -38,7 +58,7 @@ describe("when the configured logout uri is invoked with a png request", functio
3858
headers = { cookie = cookie, accept = "image/png" },
3959
redirect = false
4060
})
41-
it("the response contains a default HTML-page", function()
61+
it("the response contains a default PNG image", function()
4262
assert.are.equals(200, status)
4363
assert.are.equals("image/png", headers["content-type"])
4464
assert.are.equals("no-cache, no-store", headers["cache-control"])

0 commit comments

Comments
 (0)