Skip to content

Add BYOC and Cloud platform badges for ADP documentation#376

Open
JakeSCahill wants to merge 32 commits into
mainfrom
feature/badge-byoc-only
Open

Add BYOC and Cloud platform badges for ADP documentation#376
JakeSCahill wants to merge 32 commits into
mainfrom
feature/badge-byoc-only

Conversation

@JakeSCahill
Copy link
Copy Markdown
Contributor

@JakeSCahill JakeSCahill commented Apr 23, 2026

Implements unified navigation system for Redpanda documentation with Data Platform hierarchy, component-themed navigation buckets, and enhanced user experience features.

Overview

This PR introduces a complete redesign of the documentation navigation to support a unified sidebar for Data Platform that combines Streaming and Connect navigation in a single, collapsible bucket structure. The implementation includes 77 files with 9,046 additions across templates, styles, and JavaScript.

Major Features

1. Unified Navigation System

  • Bucket-based sidebar - Navigation organized into expandable/collapsible buckets (Streaming, Connect)
  • Component theming - Each bucket styled with its own color theme
  • Per-bucket version selectors - Independent version switching for each component
  • Bucket icons - Tabler icons (activity, plug-connected, database, etc.) for visual distinction
  • Automatic bucket expansion - Current bucket auto-expands, others collapse by default

New files:

  • src/partials/bucket-header.hbs - Bucket header with icon, title, version selector
  • src/partials/nav-menu-scroll.hbs - Unified navigation rendering logic
  • src/js/23-nav-bucket.js - Bucket expand/collapse and version selector interactions
  • src/css/nav.css - Updated with bucket theming styles

2. Product Switcher

  • Three top-level destinations - Data Platform, Cloud, ADP
  • Modern dropdown design - Clean, accessible destination selector
  • Component-aware - Highlights current destination

New files:

  • src/partials/product-switcher.hbs - Product switching UI
  • src/js/20-product-switcher.js - Dropdown interactions
  • src/css/product-switcher.css - Product switcher styling

3. Version Selector

  • Redesigned dropdown - Modern, pill-style version selector in sticky header
  • EOL indication - Shows end-of-life status for deprecated versions
  • Release dates - Displays release dates for each version
  • Show/hide older versions - Toggle to reveal full version history

New files:

  • src/partials/version-selector.hbs - Version selector UI
  • src/js/22-version-selector.js - Version selector logic
  • src/css/version-selector.css - Version selector styling

4. Component Home Pages (v3 Layout)

  • Three-column card grid - Deployment options, popular topics
  • Dynamic component colors - Headers themed by component color
  • Responsive design - Mobile-optimized layouts

New files:

  • src/layouts/component-home-v3.hbs - New home page layout
  • src/partials/component-home-v3.hbs - Component home partial
  • src/css/component-home-v3.css - Component home styling

5. Data Platform Landing Page

  • Hero section - Large, colored hero with component branding
  • Product cards - Visual cards for child components (Streaming, Connect)
  • Guides matrix - Categorized guide links

New files:

  • src/layouts/data-platform.hbs - Data Platform layout
  • src/partials/data-platform.hbs - Data Platform content partial
  • src/css/data-platform.css - Data Platform page styling

6. Labs Home Page

  • Filter-based navigation - Category and product filters
  • Card grid layout - Browse labs by category or product
  • Search integration - Global search for labs content

New files:

  • src/layouts/labs-home.hbs - Labs landing page layout
  • src/css/labs-home.css - Labs home styling

7. Ask AI Chat Panel

  • Right-side drawer - Persistent Kapa AI integration
  • Cmd+K shortcut - Quick access keyboard shortcut
  • Cross-page persistence - Chat stays open across navigation
  • React-based UI - Using Kapa AI React SDK

New files:

  • src/partials/chat-panel.hbs - Chat panel structure
  • src/js/19-chat-panel.js - Chat panel interactions
  • src/js/react/AskAI.jsx - React chat interface (updated)
  • src/css/chat-panel.css - Chat panel styling

8. Enhanced Header Features

  • Breadcrumb collapse - Responsive breadcrumbs with ellipsis at narrow widths
  • Page options dropdown - Eyebrow-positioned markdown/edit options in sticky header
  • Improved sticky header - Better layout with version selector and page options

New files:

  • src/js/21-breadcrumb-collapse.js - Breadcrumb collapse logic
  • src/css/markdown-dropdown.css - Page options dropdown styling (updated)

9. Typography Improvements

  • Inter Display font - New display font for headers and UI elements
  • Better font hierarchy - Improved readability across the site

New files:

  • src/css/typeface-inter-display.css - Inter Display font definitions
  • src/font/inter-display/ - Inter Display font files (24 .ttf files)

Design System

Component Colors

Each component has a defined color used across the UI:

  • Data Platform: #4b44ff (purple) - Umbrella component
  • Streaming: #107569 (teal) - Self-Managed docs
  • Connect: #54478C (purple) - Connect docs
  • Cloud: #0ea5e9 (blue) - Cloud docs
  • ADP: #e24328 (orange) - ADP docs

Dark Mode

All new features include full dark mode support with appropriate contrast adjustments.

Accessibility

  • Keyboard navigation support for all interactive elements
  • ARIA labels and roles for screen readers
  • Focus management for modals and dropdowns
  • Reduced motion support

Updated Files

Templates

  • src/partials/header-content.hbs - Updated header structure
  • src/partials/nav.hbs - Updated for unified navigation
  • src/partials/home.hbs - Updated home page links

Helpers

  • src/helpers/get-component-color.js - Component color lookup
  • src/helpers/get-header-data.js - Header data extraction
  • src/helpers/get-component-header-data.js - Component-specific header data
  • src/helpers/get-page-info.js - Updated page info extraction
  • src/helpers/add-suggested-labs.js - Updated component references
  • src/helpers/list-related-labs.js - Updated component references

Styles

  • src/css/doc.css - Article page improvements
  • src/css/home.css - Home page styling updates
  • src/css/nav.css - Unified navigation bucket styles
  • src/css/vars.css - New component color variables

Scripts

  • src/js/06-copy-to-clipboard.js - Updated for new layouts
  • src/js/16-bloblang-interactive.js - Updated for chat panel

Breaking Changes

Component Renames (Anticipated)

This UI is designed to work with renamed components:

  • ROOTstreaming
  • redpanda-cloudcloud-data-platform
  • redpanda-connectconnect
  • redpanda-labslabs

The UI bundle includes fallback logic to handle both old and new component names during transition.

Related PRs

Antora Extension

Content Repository Updates

docs-site Playbook

Playbook updates needed to:

  1. Reference unified-navigation extension from docs-extensions-and-macros
  2. Add data-platform umbrella component
  3. Reference feature branches for testing

Testing

Local Testing

# Build UI bundle
cd docs-ui && gulp bundle

# Build docs with unified navigation
cd docs-site && npx antora local-antora-playbook.yml

# Preview
npx http-server build/site -p 8080

Test Scenarios

  • Unified navigation displays with both buckets
  • Bucket expand/collapse works
  • Per-bucket version selectors function correctly
  • Product switcher shows three destinations
  • Component home pages render with v3 layout
  • Data Platform landing page displays correctly
  • Labs home page with filters works
  • Ask AI chat panel opens/closes correctly
  • Breadcrumb collapse works at narrow widths
  • Page options dropdown positions correctly in sticky header
  • Dark mode works for all new features
  • Mobile responsive design functions properly

Deployment Notes

This UI bundle is compatible with existing Antora content but requires:

  1. Unified navigation extension registered in playbook
  2. Component page-header-data attributes (section, color, order, icon)
  3. data-platform umbrella component in docs-site

The bundle can be deployed independently for visual testing before content/extension PRs are merged.

JakeSCahill and others added 2 commits April 22, 2026 12:39
- Add badge--byoc CSS class with blue styling for BYOC-only features
- Add badge--cloud CSS class with purple styling for Cloud features
- Define CSS variables for badge colors and backgrounds

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add availability block showing Cloud/BYOC support on ADP pages
- Add info icon with Tippy.js tooltip explaining availability
- Add BYOC and Cloud badge CSS variables for light/dark modes
- Update article.hbs to render availability block for ADP pages
- Minor fixes to header, nav, and TOC styling

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@netlify
Copy link
Copy Markdown

netlify Bot commented Apr 23, 2026

Deploy Preview for docs-ui ready!

Name Link
🔨 Latest commit 862085d
🔍 Latest deploy log https://app.netlify.com/projects/docs-ui/deploys/6a0b29c0dbb2aa0008c94fc7
😎 Deploy Preview https://deploy-preview-376--docs-ui.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.
Lighthouse
Lighthouse
1 paths audited
Performance: 32 (🔴 down 2 from production)
Accessibility: 91 (🔴 down 2 from production)
Best Practices: 92 (no change from production)
SEO: 89 (no change from production)
PWA: -
View the detailed breakdown and full score reports

To edit notification comments on pull requests, go to your Netlify project configuration.

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Apr 23, 2026

Important

Review skipped

Auto incremental reviews are disabled on this repository.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: cf712928-9736-48d2-a000-d817c9b82f0e

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

This PR adds extensive UI and behavioral changes across docs: new badges and an availability block for BYOC/Cloud with theme-aware CSS variables and dark-mode overrides; a redesigned topbar, sidebar, breadcrumbs, footer, home page, and many component styles; updates to Bloblang Prism grammar; new Handlebars template branches and tooltip initialization for BYOC/Cloud badges; helper modules for BYOC/cloud/EOL detection and resource resolution; updated JS for Ask-AI/chat integration (window.openChatWithQuery), markdown dropdown positioning, nav show/hide, and chat React improvements; and build/task tweaks (PostCSS variable preservation, font globs).

Sequence Diagram(s)

sequenceDiagram
    participant User as User
    participant Page as Page Script (Ask UI)
    participant Drawer as Chat Drawer (chat-panel)
    participant Backend as Chat Service

    User->>Page: Click "Ask AI" / submit ask form
    Page->>Page: build aiPromptText from context (selection/code)
    Page->>Drawer: call window.openChatWithQuery(aiPromptText, true)
    Drawer->>Page: confirm opened / focus textarea
    Drawer->>Backend: submit query (autoSubmit=true)
    Backend-->>Drawer: respond with AI result
    Drawer-->>User: display response
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

Suggested reviewers

  • paulohtb6
  • Feediver1
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feature/badge-byoc-only

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🧹 Nitpick comments (2)
src/css/doc.css (1)

1012-1018: Add the same fallback for the info icon color.

Line 1017 uses --availability-block-border without the fallback used on Line 993, so the icon color can become invalid if a theme omits that variable.

🎨 Proposed fallback
 .doc .availability-block .availability-info {
   display: inline-flex;
   align-items: center;
   margin-left: 0.5rem;
   cursor: help;
-  color: var(--availability-block-border);
+  color: var(--availability-block-border, var(--note-border-color));
   vertical-align: middle;
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/css/doc.css` around lines 1012 - 1018, The color declaration inside the
.doc .availability-block .availability-info rule uses
var(--availability-block-border) without a fallback; update the color property
to use the same fallback pattern as earlier (e.g.
var(--availability-block-border, var(--availability-border))) so the info icon
color remains valid when --availability-block-border is not defined. Locate the
.doc .availability-block .availability-info selector and replace the color value
to include the fallback variable.
src/partials/article.hbs (1)

80-96: Consider attribute-driving the tooltip content and consolidating the init script.

Two small consistency nits for this new inline block:

  1. The tooltip copy is hardcoded in the template, whereas the existing BYOC/Cloud/beta/limited-availability tooltips read from page attributes (e.g., page.attributes.byoc-text at Line 170, page.attributes.cloud-only-text at Line 196). Using something like page.attributes.availability-text with a sensible default keeps content editable without a UI rebuild and matches the pattern already established in this file.
  2. Initialization is split across two DOMContentLoaded handlers (here and the one starting at Line 103). Folding this tippy init into the existing handler reduces duplicate listeners and keeps all tooltip setup in one place. Note that the existing handler bails early at Line 107–109 if .metadata--main/.metadata--nav are missing, so if you consolidate, initialize the availability-info tooltip before that early return (or adjust the guard) so ADP pages still get it.

Both are optional; leaving as-is is functional.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/partials/article.hbs` around lines 80 - 96, Replace the hardcoded tooltip
text and separate listener by reading content from
page.attributes.availability-text (with the current hardcoded string as a
sensible default) when creating the tooltip for the element selected as
availabilityInfo, and move the tippy initialization into the existing
DOMContentLoaded handler that already sets up other tooltips; ensure you
reference availabilityInfo and call tippy(...) with the same options but
initialize it before the early return that checks for
.metadata--main/.metadata--nav (or adjust that guard) so ADP pages still get the
availability tooltip.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/css/header.css`:
- Around line 153-155: The desktop override for right-side nav items still uses
var(--navbar-font-color) so custom header text colors from --nav-text-color
aren't applied; update the selector .navbar-end > .navbar-item and .navbar-end
.navbar-link to use color: var(--nav-text-color, var(--navbar-menu-font-color))
(matching the other .navbar-item/.navbar-link rule) so desktop right-side nav
items inherit the custom header text color.

In `@src/css/vars.css`:
- Around line 185-195: Override the badge label text color variables in the
dark-theme block so the bright BYOC/Cloud backgrounds keep good contrast:
add/override --byoc-label-color and --cloud-label-color inside
html[data-theme=dark] (matching the existing --byoc-label-background and
--cloud-label-background variables) and set them to a dark, high-contrast color
instead of inheriting `#fff`; update any usages of these badges that read the
label color variable (e.g., the BYOC/Cloud badge styles that reference
--byoc-label-color / --cloud-label-color) to ensure the new variables are
applied.

In `@src/partials/article.hbs`:
- Around line 55-71: The availability block (class "availability-block" in
article.hbs) fails to render any platform when both page.attributes.byoc and
page.attributes.cloud-only are true; change the conditional logic to explicitly
handle all four states (both true, only byoc, only cloud-only, neither) so the
both-true case emits a sensible label (e.g., "Cloud, BYOC"); implement this by
replacing the nested if/unless chain with an explicit sequence: if both
page.attributes.byoc and page.attributes.cloud-only => "Cloud, BYOC", else if
page.attributes.byoc => "BYOC", else if page.attributes.cloud-only => "Cloud",
else => "Cloud, BYOC" (or equivalent join of computed platforms) so the
availability-block always shows a value.

In `@src/partials/header-content.hbs`:
- Line 18: The anchor element rendering the navbar item currently injects an
inline style for non-standalone pages (using
`@root.page.component.latest.asciidoc.attributes.page-header-data.text-color`),
which overrides stylesheet hover/current states; update the template so the
inline style is only applied for standalone widgets (keep the existing
`@root.isStandaloneWidget` branch that sets style="color: white;") and remove the
else-if branch that sets color from page-header-data.text-color, relying on the
existing --nav-text-color set elsewhere to control non-standalone link color and
hover/is-current states; locate the anchor with class "navbar-item {{`#if` (eq
this.title `@root.page.component.title`)}}is-current{{/if}}" and remove the
non-standalone inline color injection.

In `@src/partials/nav-tree.hbs`:
- Line 8: Add two new helpers is-byoc-feature.js and is-cloud-feature.js in
src/helpers modeled after is-beta-feature.js and is-enterprise.js that use
contentCatalog to look up the target page by URL and return true when target
page attributes include page-byoc and page-cloud-only respectively; then update
the ADP guard logic used in nav-tree.hbs so it checks the target nav item's
attributes (via the same helper/lookup) rather than `@root.page.attributes.adp`,
ensuring BYOC/Cloud badge classes are suppressed only when the target page is an
ADP page.

---

Nitpick comments:
In `@src/css/doc.css`:
- Around line 1012-1018: The color declaration inside the .doc
.availability-block .availability-info rule uses
var(--availability-block-border) without a fallback; update the color property
to use the same fallback pattern as earlier (e.g.
var(--availability-block-border, var(--availability-border))) so the info icon
color remains valid when --availability-block-border is not defined. Locate the
.doc .availability-block .availability-info selector and replace the color value
to include the fallback variable.

In `@src/partials/article.hbs`:
- Around line 80-96: Replace the hardcoded tooltip text and separate listener by
reading content from page.attributes.availability-text (with the current
hardcoded string as a sensible default) when creating the tooltip for the
element selected as availabilityInfo, and move the tippy initialization into the
existing DOMContentLoaded handler that already sets up other tooltips; ensure
you reference availabilityInfo and call tippy(...) with the same options but
initialize it before the early return that checks for
.metadata--main/.metadata--nav (or adjust that guard) so ADP pages still get the
availability tooltip.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 2920838c-1e2e-46cf-b4e4-3cf4e6cf2378

📥 Commits

Reviewing files that changed from the base of the PR and between 6941e66 and 37bacc1.

📒 Files selected for processing (10)
  • src/css/doc.css
  • src/css/header.css
  • src/css/metadata.css
  • src/css/nav.css
  • src/css/vars.css
  • src/js/vendor/prism/prism-bloblang.js
  • src/partials/article.hbs
  • src/partials/header-content.hbs
  • src/partials/nav-tree.hbs
  • src/partials/toc.hbs

Comment thread src/css/header.css
Comment thread src/css/vars.css
Comment thread src/partials/article.hbs Outdated
Comment thread src/partials/header-content.hbs Outdated
Comment thread src/partials/nav-tree.hbs
- Add is-byoc-feature.js helper to detect page-byoc attribute
- Add is-cloud-feature.js helper to detect page-cloud-only attribute
- These helpers enable nav badge display for ADP documentation

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@JakeSCahill JakeSCahill marked this pull request as draft April 24, 2026 12:02
JakeSCahill and others added 5 commits April 24, 2026 13:07
- Fix header.css: Use --nav-text-color for navbar-end items
- Fix vars.css: Add dark mode label color overrides for BYOC/Cloud badges
- Fix article.hbs: Handle case when both byoc and cloud-only attributes are true
- Fix header-content.hbs: Remove inline color that overrides CSS hover states
- Fix doc.css: Add fallback for availability info icon color

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
ADP Cloud is descoped from the 2026-06-15 GA. With BYOC as the only
deployment shape, the "Available in: Cloud, BYOC" / "Available in:
BYOC" admonition no longer informs the reader and adds visual noise
on every ADP page.

Drop the entire `page.attributes.adp` availability block from
src/partials/article.hbs. Other badges (beta, limited-availability,
context-switcher, BYOC/Cloud labels for non-ADP pages) keep working
unchanged.

Companion PR: redpanda-data/adp-docs#13 ships the same change locally
via Antora's supplemental_files mechanism so the deploy preview is fixed
immediately. Once a new docs-ui release tag is cut from this branch and
the adp-docs / docs-site playbooks are bumped to it, the supplemental
override in adp-docs becomes redundant and can be deleted.

Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@JakeSCahill JakeSCahill force-pushed the feature/badge-byoc-only branch from 699c046 to 2a4cff4 Compare May 7, 2026 14:46
Adds inline status badges in the sticky header for ADP pages when
features are limited to specific platforms:
- "Only in BYOC" badge when :page-byoc-only: true is set
- "Only in Cloud" badge when :page-cloud-only: true is set

Both attributes require :adp: true (set in ADP component antora.yml).
Badges are mutually exclusive - set only one.

Also includes:
- Version dropdown alignment fix (aligns left with button)
- Removed the availability block in favor of compact inline badges
@JakeSCahill
Copy link
Copy Markdown
Contributor Author

@coderabbitai review

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 12, 2026

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 12

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
src/partials/nav-explore.hbs (1)

16-33: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

The default-version path renders an empty dropdown.

When the current version is 'default' and page.versions.length > 1, line 6 still makes this a dropdown, but lines 19-32 skip rendering every option. That leaves a visible chevron with an empty menu. Remove that inner guard or render the default-version alternatives there as well.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/partials/nav-explore.hbs` around lines 16 - 33, The dropdown shows a
chevron but no items because the inner guard "{{`#if` (ne
page.componentVersion.displayVersion 'default')}}" prevents rendering when the
current displayVersion is 'default'; remove that guard (or change the logic to
always iterate page.versions) so the template always runs the "{{`#each`
page.versions}}" block and emits version links (still skipping the current
version via "{{`#if` (ne ./version `@root.page.version`)}}" and using "{{`#with`
(resolve-resource ./url) as |targetPage|}}", the "{{{relativize ../url}}}" href,
and the existing "{{../displayVersion}}"/"{{`#if` (is-eol
../asciidoc.attributes)}}" handling).
src/partials/article.hbs (1)

95-220: ⚠️ Potential issue | 🔴 Critical | ⚡ Quick win

Critical: undefined metadataContainer breaks all tooltip/observer setup.

metadataContainer is used on Line 154, Line 180, and Line 219 but never defined. This will throw at runtime and abort the entire DOMContentLoaded handler. Also, navMetadataContainer.querySelector(...) is called without guarding null.

💡 Suggested fix
   document.addEventListener("DOMContentLoaded", () => {
     const stickyHeader = document.querySelector(".component-indicator-sticky");
+    const metadataContainer = document.querySelector(".metadata--main");
     const navMetadataContainer = document.querySelector(".metadata--nav");
@@
-    const topByocBadge = metadataContainer.querySelector(".byoc-label p");
-    const navByocBadge = navMetadataContainer.querySelector(".nav-byoc-label");
+    const topByocBadge = metadataContainer?.querySelector(".byoc-label p");
+    const navByocBadge = navMetadataContainer?.querySelector(".nav-byoc-label");
@@
-    const topCloudBadge = metadataContainer.querySelector(".cloud-label p");
-    const navCloudBadge = navMetadataContainer.querySelector(".nav-cloud-label");
+    const topCloudBadge = metadataContainer?.querySelector(".cloud-label p");
+    const navCloudBadge = navMetadataContainer?.querySelector(".nav-cloud-label");
@@
-    observer.observe(metadataContainer);
+    if (metadataContainer && navMetadataContainer) {
+      observer.observe(metadataContainer);
+    }
   });
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/partials/article.hbs` around lines 95 - 220, The handler uses an
undefined metadataContainer and calls querySelector on navMetadataContainer
without null checks, causing runtime failures; define and assign
metadataContainer at the top of the DOMContentLoaded block (e.g., const
metadataContainer = document.querySelector(".metadata") or the actual selector
used elsewhere), guard uses of navMetadataContainer (and metadataContainer)
before calling .querySelector or accessing properties (wrap tippy
initializations for topByocBadge/topCloudBadge and nav*Badge initializations in
if (metadataContainer) / if (navMetadataContainer) checks), and only call
observer.observe(metadataContainer) when metadataContainer is non-null to avoid
errors. Ensure you update references to topByocBadge/topCloudBadge to query from
metadataContainer only after that null check.
🧹 Nitpick comments (1)
src/partials/head-scripts.hbs (1)

117-128: 💤 Low value

Consider extracting theme toggle logic to reduce duplication.

The sidebar theme toggle handler (lines 118-128) duplicates the logic from the main theme toggle handler (lines 71-77). Both handlers toggle between light and dark themes, update localStorage, and call setTheme.

♻️ Optional refactor to share toggle logic
+  function toggleTheme() {
+    const currentTheme = document.documentElement.getAttribute('data-theme') || 'light';
+    const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
+    localStorage.setItem('theme', newTheme);
+    setTheme(newTheme);
+  }
+
   window.addEventListener('DOMContentLoaded', function() {
     const switchButton = document.getElementById('switch-theme');
     // ... existing code ...
     if (switchButton) {
       setTheme(initialTheme);  // Apply initial theme on load
       switchButton.addEventListener('click', function() {
-        // Toggle theme on button click
-        const currentTheme = document.body.getAttribute('data-theme');
-        const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
-        localStorage.setItem('theme', newTheme);
-        setTheme(newTheme);
+        toggleTheme();
       });
     }
     // ... existing code ...
   });
   
   // Connect sidebar theme toggle to main theme switcher
   window.addEventListener('DOMContentLoaded', function() {
     const sidebarThemeToggle = document.getElementById('sidebar-theme-toggle');
     if (sidebarThemeToggle) {
-      sidebarThemeToggle.addEventListener('click', function() {
-        const currentTheme = document.documentElement.getAttribute('data-theme') || 'light';
-        const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
-        localStorage.setItem('theme', newTheme);
-        setTheme(newTheme);
-      });
+      sidebarThemeToggle.addEventListener('click', toggleTheme);
     }
   });
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/partials/head-scripts.hbs` around lines 117 - 128, Extract the duplicated
toggle logic into a reusable function (e.g., toggleTheme) and call it from both
the sidebar handler and the main theme handler: move the code that reads
data-theme from document.documentElement, computes newTheme, sets
localStorage('theme'), and calls setTheme into a single function (referencing
setTheme and the new toggleTheme helper), then replace the inline click
callbacks on the sidebarThemeToggle element and the main theme toggle element to
just call toggleTheme; keep the DOMContentLoaded listener but update it to
attach the click handlers to their elements (sidebar-theme-toggle and the main
toggle) which both invoke toggleTheme.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/css/bloblang-playground.css`:
- Around line 1203-1209: The CSS rule .bloblang-playground .validation-error
uses the deprecated property value `word-break: break-word`; remove that
declaration and replace it with the modern wrapping rule `overflow-wrap:
anywhere` (keeping existing properties like `white-space: normal` and
`word-break` entirely removed) so lint no longer flags it and text still wraps
correctly. Ensure you update the .bloblang-playground .validation-error block to
drop `word-break: break-word` and add `overflow-wrap: anywhere`.

In `@src/css/header.css`:
- Around line 209-213: Rename the keyframe identifier bcDropdownIn to a
kebab-case name (e.g., bc-dropdown-in) wherever it appears: update the
`@keyframes` rule name and all references to it (for example the animation
property that currently uses bcDropdownIn) to match the kebab-case name so
linting passes; ensure both the declaration (`@keyframes` bc-dropdown-in { ... })
and uses (animation: bc-dropdown-in 0.15s ease-out;) are updated consistently.

In `@src/css/home.css`:
- Around line 394-400: The CSS has stylelint failures: the keyframe name casing
(toastSlideIn) and keyword case in color-mix usage (in sRGB). Rename the
keyframes to follow the configured pattern (e.g., toast-slide-in or other
project keyframes convention) wherever referenced (look for toastSlideIn usage
in `@keyframes` and animation names) and change all occurrences of "in sRGB"
inside color-mix(...) to "in srgb" (apply to the shown block and the other
reported locations) so value-keyword-case passes; run gulp lint to verify.

In `@src/css/nav.css`:
- Around line 329-342: Rename the keyframes and their animation references from
camelCase to kebab-case to satisfy stylelint: change `@keyframes` versionMenuIn
and `@keyframes` statusPulse to `@keyframes` version-menu-in and `@keyframes`
status-pulse, and update every corresponding animation: versionMenuIn ... and
animation: statusPulse ... usages to animation: version-menu-in ... and
animation: status-pulse ... (also apply the same changes in the other occurrence
around lines 721-755).

In `@src/css/toc.css`:
- Line 245: The CSS uses the deprecated property word-wrap: break-word; —
replace that declaration with the modern equivalent overflow-wrap: break-word;
(remove or replace the word-wrap line in src/css/toc.css so the selector that
currently contains "word-wrap" instead uses "overflow-wrap: break-word;") to
clear the Stylelint failure.

In `@src/css/typeface-inter.css`:
- Line 8: The six `@font-face` blocks in src/css/typeface-inter.css use quoted
font-family values (e.g., font-family: "Inter") which triggers stylelint errors;
update each `@font-face` block to use an unquoted identifier (font-family: Inter)
for all occurrences in the file (the font-family declarations inside the
`@font-face` rules at the six blocks) so gulp lint passes.

In `@src/helpers/is-byoc-feature.js`:
- Line 20: The BYOC detection uses the wrong page attribute key; update the
check in the urlCache.set call (currently using the expression
urlCache.set(p.pub.url, !!p.asciidoc?.attributes?.['page-byoc'])) to use the
documented attribute 'page-byoc-only' instead so BYOC-only pages are detected
(i.e., replace 'page-byoc' with 'page-byoc-only' in that expression).

In `@src/js/react/AskAI.jsx`:
- Around line 49-59: The code currently calls createRoot(...).render(<App />)
for both element queries (homeEl and panelEl), which can mount two App instances
if both `#kapa-chat-root` and `#chat-panel-kapa-root` exist; change the logic to
mount to exactly one target by selecting a single element (for example prefer
panelEl over homeEl or use the first non-null) and only call
createRoot(...).render(<App />) once — update the block that references homeEl,
panelEl, createRoot, and App to use an if/else (or a single chosenEl variable)
so only one App is rendered.

In `@src/partials/bloblang-playground.hbs`:
- Around line 1643-1648: The "Ask AI" button still appears when
window.openChatWithQuery isn't available — instead of merely console.warn-ing in
the click handlers (the block that checks typeof window.openChatWithQuery ===
'function'), proactively disable or hide the CTA at render/time and update the
two click-handler locations to not show a non-functional button; specifically,
check typeof window.openChatWithQuery !== 'function' early and either add a
disabled attribute/class and aria-disabled to the Ask AI button (querySelector
for the button element or template variable controlling visibility) or call the
previous modal fallback if you want to preserve behavior; apply this change to
both places where window.openChatWithQuery is checked so the button is never
visible/active when the chat API is absent.

In `@src/partials/head-scripts.hbs`:
- Around line 23-28: The JS sets CSS variable --announcement-bar-height to
'50px' for mobile when announcementType !== 'bloblang' but the CSS for
.announcement-bar.is-active uses max-height: 60px, causing a 10px mismatch and
potential layout shift; fix by making the reserved height match the actual
animated max height — either change the JS assignment for mobile in the if block
where announcementType is checked (the code that sets --announcement-bar-height
and --announcement-bar-height--desktop) to '60px', or change the CSS max-height
in the announcement banner stylesheet (.announcement-bar.is-active) from 60px to
50px so both values are identical.

In `@src/partials/nav-explore.hbs`:
- Around line 6-17: The version selector is currently rendered as non-focusable
spans (container with class "container" and the span "current-version" plus the
material-symbols icon), which prevents keyboard users from opening the versions
menu; replace the clickable trigger (the span.current-version and the adjacent
material icon) with a real <button> element that is focusable and toggles an
aria-expanded attribute and references the menu via aria-controls, ensure the
button keeps the existing classes/markup semantics (e.g., "current-version"
styling) and that the dropdown container retains the "has-dropdown" behavior,
and update any JS that toggles the menu to read/write aria-expanded on that
button and to open/close the element with the matching id used by aria-controls.

In `@src/partials/nav.hbs`:
- Around line 22-28: Replace the non-semantic div used as the search trigger
with a native button element: change the element with class "sb-search" and
data-action="open-search" from <div> to <button type="button">, remove the
redundant tabindex and role attributes, keep the aria-label="Search docs" and
the inner SVG and span.sb-search-text intact, and ensure any JS that queries
".sb-search" still works (or update selectors to target the button) so keyboard
activation and accessibility work correctly.

---

Outside diff comments:
In `@src/partials/article.hbs`:
- Around line 95-220: The handler uses an undefined metadataContainer and calls
querySelector on navMetadataContainer without null checks, causing runtime
failures; define and assign metadataContainer at the top of the DOMContentLoaded
block (e.g., const metadataContainer = document.querySelector(".metadata") or
the actual selector used elsewhere), guard uses of navMetadataContainer (and
metadataContainer) before calling .querySelector or accessing properties (wrap
tippy initializations for topByocBadge/topCloudBadge and nav*Badge
initializations in if (metadataContainer) / if (navMetadataContainer) checks),
and only call observer.observe(metadataContainer) when metadataContainer is
non-null to avoid errors. Ensure you update references to
topByocBadge/topCloudBadge to query from metadataContainer only after that null
check.

In `@src/partials/nav-explore.hbs`:
- Around line 16-33: The dropdown shows a chevron but no items because the inner
guard "{{`#if` (ne page.componentVersion.displayVersion 'default')}}" prevents
rendering when the current displayVersion is 'default'; remove that guard (or
change the logic to always iterate page.versions) so the template always runs
the "{{`#each` page.versions}}" block and emits version links (still skipping the
current version via "{{`#if` (ne ./version `@root.page.version`)}}" and using
"{{`#with` (resolve-resource ./url) as |targetPage|}}", the "{{{relativize
../url}}}" href, and the existing "{{../displayVersion}}"/"{{`#if` (is-eol
../asciidoc.attributes)}}" handling).

---

Nitpick comments:
In `@src/partials/head-scripts.hbs`:
- Around line 117-128: Extract the duplicated toggle logic into a reusable
function (e.g., toggleTheme) and call it from both the sidebar handler and the
main theme handler: move the code that reads data-theme from
document.documentElement, computes newTheme, sets localStorage('theme'), and
calls setTheme into a single function (referencing setTheme and the new
toggleTheme helper), then replace the inline click callbacks on the
sidebarThemeToggle element and the main theme toggle element to just call
toggleTheme; keep the DOMContentLoaded listener but update it to attach the
click handlers to their elements (sidebar-theme-toggle and the main toggle)
which both invoke toggleTheme.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 0ae3d5c1-a924-44aa-96d1-a2cc63b9835e

📥 Commits

Reviewing files that changed from the base of the PR and between 37bacc1 and 30917d0.

⛔ Files ignored due to path filters (1)
  • package-lock.json is excluded by !**/package-lock.json
📒 Files selected for processing (51)
  • gulp.d/tasks/build.js
  • preview-src/ui-model.yml
  • src/css/announcement-banner.css
  • src/css/bloblang-playground.css
  • src/css/body.css
  • src/css/breadcrumbs.css
  • src/css/dark-mode.css
  • src/css/doc.css
  • src/css/footer.css
  • src/css/header.css
  • src/css/home.css
  • src/css/main.css
  • src/css/markdown-dropdown.css
  • src/css/nav.css
  • src/css/pagination.css
  • src/css/search-bump.css
  • src/css/search.css
  • src/css/site.css
  • src/css/toc.css
  • src/css/toolbar.css
  • src/css/typeface-inter.css
  • src/css/vars.css
  • src/helpers/is-byoc-feature.js
  • src/helpers/is-cloud-feature.js
  • src/helpers/is-eol.js
  • src/helpers/resolve-resource.js
  • src/js/01-nav.js
  • src/js/06-copy-to-clipboard.js
  • src/js/11-editable-placeholders.js
  • src/js/14-markdown-dropdown.js
  • src/js/react/AskAI.jsx
  • src/js/react/components/ChatInterface.jsx
  • src/layouts/default.hbs
  • src/layouts/index.hbs
  • src/layouts/lab.hbs
  • src/layouts/labs-search.hbs
  • src/layouts/search.hbs
  • src/partials/algolia-script.hbs
  • src/partials/article.hbs
  • src/partials/bloblang-playground.hbs
  • src/partials/body.hbs
  • src/partials/breadcrumbs.hbs
  • src/partials/footer.hbs
  • src/partials/head-scripts.hbs
  • src/partials/head-styles.hbs
  • src/partials/header-content.hbs
  • src/partials/home.hbs
  • src/partials/nav-explore.hbs
  • src/partials/nav-menu.hbs
  • src/partials/nav.hbs
  • src/partials/toc.hbs
✅ Files skipped from review due to trivial changes (5)
  • src/partials/footer.hbs
  • src/partials/head-styles.hbs
  • src/layouts/search.hbs
  • src/css/dark-mode.css
  • src/css/site.css

Comment thread src/css/bloblang-playground.css
Comment thread src/css/header.css
Comment thread src/css/home.css
Comment thread src/css/nav.css
Comment thread src/css/toc.css
Comment thread src/js/react/AskAI.jsx Outdated
Comment thread src/partials/bloblang-playground.hbs
Comment thread src/partials/head-scripts.hbs
Comment thread src/partials/nav-explore.hbs Outdated
Comment thread src/partials/nav.hbs Outdated
Major UI updates for hierarchical navigation system:

Navigation System:
- Add unified navigation with bucket structure (Self-Managed → Streaming/Connect)
- New bucket-header.hbs partial with icons, titles, and per-bucket version selectors
- nav-bucket.js for expand/collapse and version selector interactions
- Bucket theming with custom CSS properties for colors

Layouts & Templates:
- component-home-v3.hbs layout for new landing page design
- data-platform.hbs layout for umbrella pages
- labs-home.hbs layout for labs directory
- Updated article.hbs to move page options to sticky header eyebrow
- Updated nav-menu-scroll.hbs for unified navigation rendering

Styling:
- chat-panel.css for Ask AI sidebar
- component-home-v3.css for new landing page layouts
- data-platform.css for umbrella page styling
- labs-home.css for labs directory
- product-switcher.css for top-level destination switcher
- Updated nav.css with bucket theming
- Updated markdown-dropdown.css for eyebrow positioning
- Inter Display font for landing pages

Components:
- product-switcher.hbs partial for three-destination switcher
- version-selector.hbs partial for per-bucket version dropdowns
- chat-panel.hbs with correct sparkle icon
- status-footer.hbs for version status information

Helpers:
- get-component-color.js, get-header-color.js, get-header-data.js
- get-component-header-data.js, get-home-navigation.js
- format-release-date.js, support-end-date.js, version-status.js
- Utility helpers: gte.js, lt.js, split.js, subtract.js

JavaScript:
- 19-chat-panel.js for Ask AI interactions
- 20-product-switcher.js for destination switching
- 21-breadcrumb-collapse.js for responsive breadcrumbs
- 22-version-selector.js for version dropdown
- 23-nav-bucket.js for bucket interactions
- Updated 14-markdown-dropdown.js to remove positioning logic

Fixes:
- Page options font consistency (11px, 600 weight)
- Focus outline visibility with proper padding
- Dropdown menu alignment
- Icon consistency (Connect plug-connected, Ask AI sparkle)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
@JakeSCahill
Copy link
Copy Markdown
Contributor Author

@coderabbitai review

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 12, 2026

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

Exclude *.png files from repository root while preserving
legitimate images in /src/img/.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@JakeSCahill
Copy link
Copy Markdown
Contributor Author

JakeSCahill commented May 12, 2026

Jira: DOC-2180

- Fix markdown dropdown positioning (focus outline cutoff, right overflow,
  mobile visibility)
- Add toolbar to component-home-v3 layout for mobile nav toggle
- Add new icon options: plug-connected, kubernetes, docker, linux
- Update helpers to support preview mode without contentCatalog
- Update preview-src/ui-model.yml with renamed components

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
JakeSCahill added a commit to redpanda-data/docs-site that referenced this pull request May 12, 2026
Adds Antora resource ID attributes for home page product card navigation:

- :page-cloud-quickstart: / :page-cloud-docs: - Cloud product links
- :page-self-managed-quickstart: / :page-self-managed-docs: - Self-Managed links
- :page-connect-quickstart: / :page-connect-docs: - Connect product links
- :page-adp-quickstart: / :page-adp-docs: - Agentic Data Plane links

These attributes allow the UI template to dynamically resolve navigation
links rather than hardcoding them.

Related: redpanda-data/docs-ui#376
JakeSCahill and others added 9 commits May 12, 2026 15:08
Change SVG dimensions from width='16' height='16' to width='24' height='24'
to match viewBox='0 0 24 24'. This fixes visual distortion where icons
appeared compressed because the coordinate system didn't match the render size.

Affects: Kubernetes, Linux, Docker deployment option icons and Streaming/Connect
component card icons on Self-Managed landing page.
- Use same plug icon as nav tree for Connect (plug-connected)
- Replace kubernetes icon with shield/helm badge shape
- Replace docker icon with stacked containers

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Previously styled first 3 consecutive paragraphs as intro text.
Now only the first paragraph (or paragraphs with .lead class) gets
the larger intro styling.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- chatPersistence.js: Save/restore conversation to localStorage with 24hr expiry
- persistentApiService.js: Wrap Kapa API to inject saved threadId
- AskAI.jsx: Use custom apiService, save conversation on answer completion
- ChatInterface.jsx: Restore conversation display on mount, clear on reset

Users can now navigate between pages and continue their chat conversation.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The component-indicator-sticky element has a negative top margin that
was causing it to overlap the H1 title on the playground page. This
adds a margin-top override specifically for the playground to prevent
the overlap.
The component indicator was overlapping the H1 title on the playground
page due to the page's unique layout with a banner element. Since the
breadcrumbs already show the location (Connect > Bloblang > Playground),
the indicator is redundant and hiding it resolves the overlap issue while
keeping the H1 clearly visible.
- Remove display: none that was hiding the indicator
- Override negative top margin to prevent overlap
- Add margin-top to H1 for proper spacing
- Indicator now sticks correctly like on other pages
Increase component indicator bottom margin from 24px to 48px to ensure
proper spacing between the eyebrow and H1 title. Both elements are now
fully visible without overlap.
JakeSCahill added a commit to redpanda-data/docs-extensions-and-macros that referenced this pull request May 14, 2026
Adds :page-support-months: attribute to pages processed by the EOL
extension. This attribute contains the configured support period in
months, enabling templates to display support duration information.

Bumps version to 4.17.3.

Related: redpanda-data/docs-ui#376
JakeSCahill and others added 11 commits May 15, 2026 17:34
- Cloud card now appears first (left position)
- Self-Managed card now appears second (right position)
- Maintains all functionality and styling

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Handlebars helper to check if a URL is external (http/https).
Used in templates to conditionally handle external URLs vs Antora resource IDs.

Returns true for URLs starting with http:// or https://
Returns false for Antora resource IDs (component:module:page.adoc)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Log detailed error context when resource resolution fails
- Include component, version, module, and page info in error
- Helps identify broken links during build
- Returns unresolved resource string as fallback

Errors format: [resolve-resource] Unresolved resource: "..." in context: {...}

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Use is-external-url helper to detect URL type
- External URLs: add target="_blank" and rel="noopener noreferrer"
- Antora resource IDs: resolve through resolve-resource helper
- Applies to all 4 labs links on component home pages

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Remove path icons, deploy icons, feature icons, popular icons
- Icons don't provide meaningful value, clean up visual design
- Only diagonal arrows remain for external lab links (indicates new tab)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Remove product bullet icons and popular topic icons
- Cleaner visual design without decorative elements
- Consistent with Cloud landing page icon removal

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Update all helper functions to use new attribute name
- More accurate: this is component-level metadata, not page-level
- Affected helpers: get-component-header-data, get-header-data, get-header-color, get-component-color, sort-components

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Update product switcher template
- Update breadcrumbs template
- Update head component color template
- Consistent with helper function renames

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
- Fix mobile nav not reopening after collapse: Reset navToggle is-active
  state and remove is-clipped--nav from html when using sidebar collapse
- Add explicit light mode styles for nav-expand button with 2px border
  and stronger shadow for better visibility
- Make topbar fully opaque (remove 92% transparency) for better
  readability when scrolling over colored content
- Reduce gap between product selector and nav items in mobile nav
- Add mobile overflow menu for header actions
- Various CSS improvements for light/dark mode consistency

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Update wasm_exec.js to match Go GOROOT version
- Use semantic button for search trigger in nav.hbs
- Use semantic button for version selector trigger in nav-explore.hbs
- Add aria-expanded toggle for version dropdown in JS
- Fix announcement bar height mismatch (50px to 60px for mobile)
- Add focus-visible styles for new button elements

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Remove quotes from font-family in typeface-inter.css (stylelint fix)
- Use correct page attribute 'page-byoc-only' in is-byoc-feature.js
- Prevent mounting duplicate App instances in AskAI.jsx
- Remove AI help buttons when chat panel unavailable in bloblang-playground

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants