Skip to content

Invalid cookie headers being returned #175

Open
@Ovid

Description

@Ovid

Hi there,

I think this might belong against HTTP::Headers::Fast, but it's popping up in a client's Plack stack, so I thought I would start here first. This is a small test case:

#!/usr/bin/env perl

use Test::Most;
use Plack::Response;
use Plack::Test;

my $response = Plack::Response->new(200);
$response->content('Hello World');
$response->cookies->{foo} = {
    value   => 'test',
    expires => time + 24 * 60 * 60,
    secure  => 1,
};
$response->cookies->{bar} = {
    value   => 'test2',
    expires => time + 24 * 60 * 60,
    secure  => 1,
};
$response->headers->push_header( 'Set-Cookie', 'foo=that' );

# traditional - named params
test_psgi
  app    => $response->to_app,
  client => sub {
    my $cb  = shift;
    my $req = HTTP::Request->new( GET => "http://localhost/hello" );
    my $res = $cb->($req);
    like $res->content, qr/Hello World/;
    explain scalar $res->headers->header('Set-Cookie');
  };

done_testing;

That final line prints:

foo=that, bar=test2; expires=Wed, 06-Jul-2022 12:27:13 GMT; secure, foo=test; expires=Wed, 06-Jul-2022 12:27:13 GMT; secure

Per the IETF spec, we have a couple of violations:

Origin servers SHOULD NOT fold multiple Set-Cookie header fields into a single header field. The usual mechanism for folding HTTP headers fields (i.e., as defined in [RFC2616]) might change the semantics of the Set-Cookie header field because the %x2C (",") character is used by Set-Cookie in a way that conflicts with such folding.

As a consequence of the above, in the last sentence of section 4.1.2, we find the following:

User agents ignore unrecognized cookie attributes (but not the entire cookie).

Because the header fields are joined on a comma, we have an invalid secure, attribute, which suggests that strict cookie parsers might accept the cookie, but ignore the strict attribute. This might be a serious security concern.

Servers SHOULD NOT include more than one Set-Cookie header field in the same response with the same cookie-name. (See Section 5.2 for how user agents handle this case.)

In the above example, we have the cookie foo being set twice, with different values and attributes. This caused a serious authentication issue in our client's code.

Admittedly, this code is being used extensively and I'm unsure about a decent approach to solving it.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions