╭ changed ─────────╮ │src/ui/AuthTab.zig│ ╰──────────────────╯ ╭──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮ │25 var text_box = try wgt.TextBox(ui.Widget).init(allocator, "login", .{ .border_style = .single, .rounded_corners = true, .wrap_kind = .none });│ │26 errdefer text_box.deinit(allocator); │ │27 text_box.getFocus().focusable = true; │ │28 - text_box.getFocus().kind = .{ .custom = "a:/auth" }; │ │28 + text_box.getFocus().kind = .{ .custom = "ai:/auth" }; │ │29 return .{ │ │30 .text_box = text_box, │ │31 .data = data, │ ╰──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯ ╭ changed ─────────────╮ │src/ui/Home/Header.zig│ ╰──────────────────────╯ ╭──────────────────────────────────────────────────────────────────────────────────╮ │61 // the tab matching the current page is focused initially; matching by│ │62 // link (rather than position) keeps this robust to tab changes. │ │63 const current_link: []const u8 = switch (session.data.current_page) { │ │64 - .home_repos => "a:/repos", │ │65 - .home_settings => "a:/settings", │ │66 - .home_auth => "a:/auth", │ │67 - else => "a:/users", │ │64 + .home_repos => "ai:/repos", │ │65 + .home_settings => "ai:/settings", │ │66 + .home_auth => "ai:/auth", │ │67 + else => "ai:/users", │ │68 }; │ │69 var selected_tab: ?usize = null; │ │70 │ ╰──────────────────────────────────────────────────────────────────────────────────╯ ╭──────────────────────────────────────────────────────────────────────────────────────────╮ │71 // tabs │ │72 for ( │ │73 [_][]const u8{ "users", "repos", "", "settings", "" }, │ │74 - [_][]const u8{ "a:/users", "a:/repos", "", "a:/settings", "a:/auth" }, │ │74 + [_][]const u8{ "ai:/users", "ai:/repos", "", "ai:/settings", "ai:/auth" },│ │75 ) |name, focus_name| { │ │76 // spacer │ │77 if (focus_name.len == 0) { │ ╰──────────────────────────────────────────────────────────────────────────────────────────╯ ╭─────────────────────────────────────────────────────────────────────────────────────────────╮ │84 }); │ │85 } │ │86 // auth │ │87 - else if (std.mem.eql(u8, "a:/auth", focus_name)) { │ │87 + else if (std.mem.eql(u8, "ai:/auth", focus_name)) { │ │88 var auth_tab = try AuthTab.View.init(allocator, &data.auth_tab, session);│ │89 errdefer auth_tab.deinit(allocator); │ │90 try tab_ids.put(allocator, auth_tab.getFocus().id, {}); │ ╰─────────────────────────────────────────────────────────────────────────────────────────────╯ ╭ changed ─────────────╮ │src/ui/Repo/Header.zig│ ╰──────────────────────╯ ╭─────────────────────────────────────────────────────────────────────────────────────────────────────╮ │ 93 │ │ 94 // every tab link is repo-scoped so selecting one stays on this page — │ │ 95 // switching its stack and updating the url — instead of navigating to │ │ 96 - // the global settings or auth pages. the files tab routes through the │ │ 97 - // shared helper so the /repo/.../files url format lives in one place. │ │ 96 + // the global settings or auth pages. the "ai:" prefix makes each an │ │ 97 + // in-page anchor: crossPageLink ignores it so a wasm click just switches │ │ 98 + // tabs (the page already holds every tab's content), while the href is │ │ 99 + // still followed with js off. the files tab routes through the shared │ │100 + // helper so the /repo/.../files url format lives in one place. │ │101 const identity = try std.fmt.allocPrint(aa, "{s}/{s}", .{ data.owner_name, data.name });│ │102 // both tabs link to the ref/oid this page is viewing, so switching tabs │ │103 // keeps the same ref (the files tab opens at its root directory). │ ╰─────────────────────────────────────────────────────────────────────────────────────────────────────╯ ╭──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮ │104 const files_route = ui.RoutablePage.repoFilesRoute(identity, data.ref_or_oid, data.ref_or_oid_value, "", 0) orelse return error.RouteTooLong;│ │102 - const files_link = try std.fmt.allocPrint(aa, "a:{s}", .{try files_route.urlAlloc(session.page_arena)}); │ │105 + const files_link = try std.fmt.allocPrint(aa, "ai:{s}", .{try files_route.urlAlloc(session.page_arena)}); │ │106 const commits_route = ui.RoutablePage.repoCommitsRoute(identity, data.ref_or_oid, data.ref_or_oid_value, 0) orelse return error.RouteTooLong;│ │104 - const commits_link = try std.fmt.allocPrint(aa, "a:{s}", .{try commits_route.urlAlloc(session.page_arena)}); │ │105 - const refs_link = try std.fmt.allocPrint(aa, "a:/repo/{s}/{s}/refs", .{ data.owner_name, data.name }); │ │106 - const settings_link = try std.fmt.allocPrint(aa, "a:/repo/{s}/{s}/settings", .{ data.owner_name, data.name }); │ │107 - const auth_link = try std.fmt.allocPrint(aa, "a:/repo/{s}/{s}/auth", .{ data.owner_name, data.name }); │ │107 + const commits_link = try std.fmt.allocPrint(aa, "ai:{s}", .{try commits_route.urlAlloc(session.page_arena)}); │ │108 + const refs_link = try std.fmt.allocPrint(aa, "ai:/repo/{s}/{s}/refs", .{ data.owner_name, data.name }); │ │109 + const settings_link = try std.fmt.allocPrint(aa, "ai:/repo/{s}/{s}/settings", .{ data.owner_name, data.name }); │ │110 + const auth_link = try std.fmt.allocPrint(aa, "ai:/repo/{s}/{s}/auth", .{ data.owner_name, data.name }); │ │111 │ │112 // the tab matching the current page is focused initially; matching by │ │113 // link (rather than position) keeps this robust to tab changes. │ ╰──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯ ╭──────────────────────────────────────────────────────────────────────────────────────────╮ │191 }); │ │192 } │ │193 │ │191 - // auth tab (login / logout). AuthTab defaults to the global a:/auth link; │ │192 - // repoint its instance at this repo's auth route so it stays local too. │ │194 + // auth tab (login / logout). AuthTab defaults to the global ai:/auth │ │195 + // link; repoint its instance at this repo's auth route so it stays local. │ │196 { │ │197 var auth_tab = try AuthTab.View.init(allocator, &data.auth_tab, session);│ │198 errdefer auth_tab.deinit(allocator); │ ╰──────────────────────────────────────────────────────────────────────────────────────────╯ ╭ changed ─────────────╮ │src/ui/User/Header.zig│ ╰──────────────────────╯ ╭────────────────────────────────────────────────────────────────────────────────────────────────────╮ │64 │ │65 // every tab link is user-scoped so selecting one stays on this page — │ │66 // switching its stack and updating the url — instead of navigating to │ │67 - // the global settings or auth pages. allocated in the page arena so the │ │68 - // focus kinds that borrow them live as long as this page's widget tree. │ │67 + // the global settings or auth pages. the "ai:" prefix makes each an │ │68 + // in-page anchor: crossPageLink ignores it so a wasm click just switches │ │69 + // tabs (the page already holds every tab's content), while the href is │ │70 + // still followed with js off. allocated in the page arena so the focus │ │71 + // kinds that borrow them live as long as this page's widget tree. │ │72 const aa = session.page_arena.allocator(); │ │70 - const repos_link = try std.fmt.allocPrint(aa, "a:/user/{s}", .{data.name}); │ │71 - const settings_link = try std.fmt.allocPrint(aa, "a:/user/{s}/settings", .{data.name}); │ │72 - const auth_link = try std.fmt.allocPrint(aa, "a:/user/{s}/auth", .{data.name}); │ │73 + const repos_link = try std.fmt.allocPrint(aa, "ai:/user/{s}", .{data.name}); │ │74 + const settings_link = try std.fmt.allocPrint(aa, "ai:/user/{s}/settings", .{data.name});│ │75 + const auth_link = try std.fmt.allocPrint(aa, "ai:/user/{s}/auth", .{data.name}); │ │76 │ │77 // the tab matching the current page is focused initially; matching by │ │78 // link (rather than position) keeps this robust to tab changes. │ ╰────────────────────────────────────────────────────────────────────────────────────────────────────╯ ╭──────────────────────────────────────────────────────────────────────────────────────────╮ │124 }); │ │125 } │ │126 │ │124 - // auth tab (login / logout). AuthTab defaults to the global a:/auth link; │ │125 - // repoint its instance at this user's auth route so it stays local too. │ │127 + // auth tab (login / logout). AuthTab defaults to the global ai:/auth │ │128 + // link; repoint its instance at this user's auth route so it stays local. │ │129 { │ │130 var auth_tab = try AuthTab.View.init(allocator, &data.auth_tab, session);│ │131 errdefer auth_tab.deinit(allocator); │ ╰──────────────────────────────────────────────────────────────────────────────────────────╯