Skip to content

Commit 8f900ca

Browse files
committed
Cleaning up crumbles
1 parent 14c07ee commit 8f900ca

File tree

3 files changed

+35
-70
lines changed

3 files changed

+35
-70
lines changed

src/browser/storage/cookie.zig

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -274,9 +274,8 @@ pub const Cookie = struct {
274274
const aa = arena.allocator();
275275
const owned_name = try aa.dupe(u8, cookie_name);
276276
const owned_value = try aa.dupe(u8, cookie_value);
277-
const owned_path = try parse_path(aa, uri.path, path);
278-
const host = uri.host orelse return error.InvalidURI;
279-
const owned_domain = try parse_domain(aa, host, domain);
277+
const owned_path = try parsePath(aa, uri, path);
278+
const owned_domain = try parseDomain(aa, uri, domain);
280279

281280
var normalized_expires: ?i64 = null;
282281
if (max_age) |ma| {
@@ -301,7 +300,7 @@ pub const Cookie = struct {
301300
};
302301
}
303302

304-
pub fn parse_path(arena: Allocator, url_path: std.Uri.Component, explicit_path: ?[]const u8) ![]const u8 {
303+
pub fn parsePath(arena: Allocator, uri: ?*const std.Uri, explicit_path: ?[]const u8) ![]const u8 {
305304
// path attribute value either begins with a '/' or we
306305
// ignore it and use the "default-path" algorithm
307306
if (explicit_path) |path| {
@@ -311,6 +310,8 @@ pub const Cookie = struct {
311310
}
312311

313312
// default-path
313+
const url_path = (uri orelse return "/").path;
314+
314315
const either = url_path.percent_encoded;
315316
if (either.len == 0 or (either.len == 1 and either[0] == '/')) {
316317
return "/";
@@ -323,9 +324,14 @@ pub const Cookie = struct {
323324
return try arena.dupe(u8, owned_path[0 .. last + 1]);
324325
}
325326

326-
pub fn parse_domain(arena: Allocator, url_host: std.Uri.Component, explicit_domain: ?[]const u8) ![]const u8 {
327-
const encoded_host = try percentEncode(arena, url_host, isHostChar);
328-
_ = toLower(encoded_host);
327+
pub fn parseDomain(arena: Allocator, uri: ?*const std.Uri, explicit_domain: ?[]const u8) ![]const u8 {
328+
var encoded_host: ?[]const u8 = null;
329+
if (uri) |uri_| {
330+
const uri_host = uri_.host orelse return error.InvalidURI;
331+
const host = try percentEncode(arena, uri_host, isHostChar);
332+
_ = toLower(host);
333+
encoded_host = host;
334+
}
329335

330336
if (explicit_domain) |domain| {
331337
if (domain.len > 0) {
@@ -342,14 +348,17 @@ pub const Cookie = struct {
342348
// can't set a cookie for a TLD
343349
return error.InvalidDomain;
344350
}
345-
if (std.mem.endsWith(u8, encoded_host, owned_domain[1..]) == false) {
346-
return error.InvalidDomain;
351+
if (encoded_host) |host| {
352+
if (std.mem.endsWith(u8, host, owned_domain[1..]) == false) {
353+
return error.InvalidDomain;
354+
}
347355
}
356+
348357
return owned_domain;
349358
}
350359
}
351360

352-
return encoded_host; // default-domain
361+
return encoded_host orelse return error.InvalidDomain; // default-domain
353362
}
354363

355364
// TODO when getting cookeis Note: Chrome does not apply rules like removing a leading `.` from the domain.

src/cdp/domains/network.zig

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -116,14 +116,18 @@ fn deleteCookies(cmd: anytype) !void {
116116
const cookies = &bc.session.cookie_jar.cookies;
117117

118118
const uri = if (params.url) |url| std.Uri.parse(url) catch return error.InvalidParams else null;
119+
const uri_ptr = if (uri) |u| &u else null;
119120

120121
var index = cookies.items.len;
121122
while (index > 0) {
122123
index -= 1;
123124
const cookie = &cookies.items[index];
124-
const domain = try CdpStorage.percentEncodedDomainOrHost(cmd.arena, uri, params.domain);
125-
// TBD does chrome take the path from the url as default? (unlike setCookies)
126-
if (cookieMatches(cookie, params.name, domain, params.path)) {
125+
const domain = try Cookie.parseDomain(cmd.arena, uri_ptr, params.domain);
126+
const path = try Cookie.parsePath(cmd.arena, uri_ptr, params.path);
127+
128+
// We do not want to use Cookie.appliesTo here. As a Cookie with a shorter path would match.
129+
// Similar to deduplicating with areCookiesEqual, except domain and path are optional.
130+
if (cookieMatches(cookie, params.name, domain, path)) {
127131
cookies.swapRemove(index).deinit();
128132
}
129133
}
@@ -173,15 +177,11 @@ fn getCookies(cmd: anytype) !void {
173177
for (params.urls) |url| {
174178
const uri = std.Uri.parse(url) catch return error.InvalidParams;
175179

176-
const host_component = uri.host orelse return error.InvalidParams;
177-
const host = CdpStorage.toLower(try CdpStorage.percentEncode(cmd.arena, host_component, CdpStorage.isHostChar));
178-
179-
var path: []const u8 = try CdpStorage.percentEncode(cmd.arena, uri.path, CdpStorage.isPathChar);
180-
if (path.len == 0) path = "/";
181-
182-
const secure = std.mem.eql(u8, uri.scheme, "https");
183-
184-
urls.appendAssumeCapacity(.{ .host = host, .path = path, .secure = secure });
180+
urls.appendAssumeCapacity(.{
181+
.host = try Cookie.parseDomain(cmd.arena, &uri, null),
182+
.path = try Cookie.parsePath(cmd.arena, &uri, null),
183+
.secure = std.mem.eql(u8, uri.scheme, "https"),
184+
});
185185
}
186186

187187
var jar = &bc.session.cookie_jar;

src/cdp/domains/storage.zig

Lines changed: 4 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,6 @@ const log = @import("../../log.zig");
2323
const Cookie = @import("../../browser/storage/storage.zig").Cookie;
2424
const CookieJar = @import("../../browser/storage/storage.zig").CookieJar;
2525
pub const PreparedUri = @import("../../browser/storage/cookie.zig").PreparedUri;
26-
pub const toLower = @import("../../browser/storage/cookie.zig").toLower;
2726

2827
pub fn processMessage(cmd: anytype) !void {
2928
const action = std.meta.stringToEnum(enum {
@@ -143,13 +142,15 @@ pub fn setCdpCookie(cookie_jar: *CookieJar, param: CdpCookie) !void {
143142

144143
// NOTE: The param.url can affect the default domain, path, source port, and source scheme.
145144
const uri = if (param.url) |url| std.Uri.parse(url) catch return error.InvalidParams else null;
146-
const domain = try percentEncodedDomainOrHost(a, uri, param.domain) orelse return error.InvalidParams; // TODO Domain needs to be prefixed with a dot if is explicitely set
145+
const uri_ptr = if (uri) |*u| u else null;
146+
const domain = try Cookie.parseDomain(a, uri_ptr, param.domain);
147+
const path = try Cookie.parsePath(a, uri_ptr, param.path);
147148

148149
const cookie = Cookie{
149150
.arena = arena,
150151
.name = try a.dupe(u8, param.name),
151152
.value = try a.dupe(u8, param.value),
152-
.path = if (param.path) |path| try a.dupe(u8, path) else "/", // Chrome does not actually take the path from the url and just defaults to "/".
153+
.path = path,
153154
.domain = domain,
154155
.expires = param.expires,
155156
.secure = param.secure,
@@ -163,51 +164,6 @@ pub fn setCdpCookie(cookie_jar: *CookieJar, param: CdpCookie) !void {
163164
try cookie_jar.add(cookie, std.time.timestamp());
164165
}
165166

166-
// Note: Chrome does not apply rules like removing a leading `.` from the domain.
167-
pub fn percentEncodedDomainOrHost(allocator: Allocator, default_url: ?std.Uri, domain: ?[]const u8) !?[]const u8 {
168-
if (domain) |domain_| {
169-
const output = try allocator.dupe(u8, domain_);
170-
return toLower(output);
171-
} else if (default_url) |url| {
172-
const host = url.host orelse return error.InvalidParams;
173-
const output = try percentEncode(allocator, host, isHostChar); // TODO remove subdomains
174-
return toLower(output);
175-
} else return null;
176-
}
177-
178-
pub fn percentEncode(arena: Allocator, component: std.Uri.Component, comptime isValidChar: fn (u8) bool) ![]u8 {
179-
switch (component) {
180-
.raw => |str| {
181-
var list = std.ArrayList(u8).init(arena);
182-
try list.ensureTotalCapacity(str.len); // Expect no precents needed
183-
try std.Uri.Component.percentEncode(list.writer(), str, isValidChar);
184-
return list.items; // @memory retains memory used before growing
185-
},
186-
.percent_encoded => |str| {
187-
return try arena.dupe(u8, str);
188-
},
189-
}
190-
}
191-
192-
pub fn isHostChar(c: u8) bool {
193-
return switch (c) {
194-
'A'...'Z', 'a'...'z', '0'...'9', '-', '.', '_', '~' => true,
195-
'!', '$', '&', '\'', '(', ')', '*', '+', ',', ';', '=' => true,
196-
':' => true,
197-
'[', ']' => true,
198-
else => false,
199-
};
200-
}
201-
202-
pub fn isPathChar(c: u8) bool {
203-
return switch (c) {
204-
'A'...'Z', 'a'...'z', '0'...'9', '-', '.', '_', '~' => true,
205-
'!', '$', '&', '\'', '(', ')', '*', '+', ',', ';', '=' => true,
206-
'/', ':', '@' => true,
207-
else => false,
208-
};
209-
}
210-
211167
pub const CookieWriter = struct {
212168
cookies: []const Cookie,
213169
urls: ?[]const PreparedUri = null,

0 commit comments

Comments
 (0)