Skip to content

Conversation

@MananTank
Copy link
Member

@MananTank MananTank commented Sep 25, 2025


PR-Codex overview

This PR focuses on enhancing the styling and structure of the application, updating CSS properties, improving component layouts, and optimizing imports. It also includes updates to package dependencies.

Detailed summary

  • Added font-feature-settings in globals.css.
  • Updated text-rendering, -webkit-font-smoothing, and text-size-adjust in global.css.
  • Modified class names for layout adjustments in page.mdx.
  • Increased margin in a Document/Paragraph component.
  • Changed background opacity in an InlineCode component.
  • Updated text color in a Subscribe component.
  • Enhanced tailwind.config.ts with new font families.
  • Adjusted class names for better styling in various components.
  • Replaced icons in Anchor and ChatButton components.
  • Improved layout and styles for NextPageButton and PageFooter.
  • Refactored the EditPage component to use a Button.
  • Updated heading styles across Heading components.
  • Adjusted DocSidebarMobile for improved layout.
  • Enhanced styles in RequestExample component.
  • Updated SearchModalContent for better spacing and layout.
  • Improved styling consistency in multiple components.
  • Updated Header component structure and styling.
  • Added geist dependency in package.json.

✨ Ask PR-Codex anything about this PR by commenting with /codex {your question}

Summary by CodeRabbit

  • Style

    • Switched site typography to Geist, enabled ligatures and improved font rendering.
    • Redesigned header with central branding, consolidated controls, mobile menu and backdrop.
    • Visual refresh across search, footer, sidebar, platform selector, steps, cards, code/inline code, and mobile sidebar.
    • Updated icons (chat, next-page, anchors), spacing/typography tweaks; vault features now stack vertically.
  • Refactor

    • Localized an article-card component; reorganized footer/next-page flows and Edit link composition.
  • Chores

    • Added Geist dependency and extended Tailwind font settings; global font/rendering tweaks.

@MananTank MananTank requested review from a team as code owners September 25, 2025 09:08
@changeset-bot
Copy link

changeset-bot bot commented Sep 25, 2025

⚠️ No Changeset found

Latest commit: 10fb338

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@vercel
Copy link

vercel bot commented Sep 25, 2025

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Preview Comments Updated (UTC)
docs-v2 Ready Ready Preview Comment Sep 25, 2025 11:01pm
nebula Ready Ready Preview Comment Sep 25, 2025 11:01pm
thirdweb_playground Ready Ready Preview Comment Sep 25, 2025 11:01pm
thirdweb-www Ready Ready Preview Comment Sep 25, 2025 11:01pm
wallet-ui Ready Ready Preview Comment Sep 25, 2025 11:01pm

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Sep 25, 2025

Walkthrough

Swapped site fonts to Geist and added font/tailwind vars; broad UI restyling across header, document pages, search, sidebar, and other components; inlined an ArticleIconCard; added header mobile menu/backdrop. No API or data-flow logic changes.

Changes

Cohort / File(s) Summary
Typography & Global CSS
apps/portal/package.json, apps/portal/src/app/layout.tsx, apps/portal/tailwind.config.ts, apps/portal/src/app/globals.css, packages/ui/src/global.css
Add geist dependency; switch to Geist Sans/Mono in layout; add Tailwind fontFamily vars; enable font ligatures and font-smoothing/text-rendering CSS.
Header & Top-level Layout
apps/portal/src/app/Header.tsx
Rework header structure and z-index; move controls into XL/mobile clusters; add burger menu and backdrop with blur and z-index adjustments; adjust top/bottom row containers.
PageLayout / Inlined Component
apps/portal/src/app/references/components/TDoc/PageLayout.tsx, apps/portal/src/app/vault/page.mdx
Inline ArticleIconCard into PageLayout; change vault page features from grid to vertical stack; adjust index/link rendering and spacing.
Document UI & Cards
apps/portal/src/components/Document/*, apps/portal/src/components/Document/Steps/*
Multiple className/markup updates: Heading, Paragraph, FeatureCard, ArticleCard, InlineCode, Code, NextPageButton, PageFooter, EditPage, APIEndpoint, RequestExample, Steps CSS/TSX — visual, spacing, rounding, icon swaps.
Search, Sidebar, Platform & Misc UI
apps/portal/src/components/others/DocSearch.tsx, .../PlatformSelector.tsx, .../Sidebar.tsx, .../Feedback.tsx, .../Subscribe.tsx, apps/portal/src/components/ui/Anchor.tsx, apps/portal/src/components/AI/chat-button.tsx
DocSearch tightened spacing and sizing; PlatformSelector trigger/content restyled; Sidebar mobile/category wrappers restyled; Feedback layout simplified; Subscribe text color adjusted; Anchor icon changed to HashIcon; Chat button icon swapped to BrainIcon.

Sequence Diagram(s)

sequenceDiagram
  participant User
  participant Header
  participant Backdrop

  User->>Header: tap burger button
  Header->>Header: set menuOpen = true
  Header->>Backdrop: render backdrop (semi-opaque + blur)
  Note right of Backdrop #eef6ff: visual overlay displayed

  User->>Backdrop: tap backdrop
  Backdrop->>Header: set menuOpen = false
  Header->>Backdrop: hide backdrop
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Pre-merge checks and finishing touches

❌ Failed checks (2 warnings, 1 inconclusive)
Check name Status Explanation Resolution
Description Check ⚠️ Warning The PR description only includes the commented‐out template and an automated Codex summary, but it does not fill in any of the required sections such as the formatted title, notes for the reviewer, or testing instructions. As a result, it fails to meet the repository’s description template requirements and leaves important context and verification steps unspecified. Please populate the PR description by replacing the template comments with a properly formatted title section, add notes for the reviewer highlighting any important details, and include clear instructions on how to test the changes.
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
Title Check ❓ Inconclusive The title “Portal: UI tweaks 2” is vague and generic, as it does not convey the specific styling, layout, and dependency changes made across the portal components and global configuration. This phrasing fails to clearly communicate the primary updates, such as the new font integration, header rework, and various component style refinements. Simply labeling changes as “UI tweaks” offers little insight into the scope or purpose of the pull request. Consider renaming the pull request using the repository’s convention and a concise description of the main changes, for example: “[Portal] Feature: Integrate Geist fonts and overhaul header and component styling.”
✨ Finishing touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch 09-25-portal_ui_tweaks

📜 Recent review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

Disabled knowledge base sources:

  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 76b94eb and 10fb338.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (29)
  • apps/portal/package.json (1 hunks)
  • apps/portal/src/app/Header.tsx (2 hunks)
  • apps/portal/src/app/globals.css (1 hunks)
  • apps/portal/src/app/layout.tsx (2 hunks)
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx (2 hunks)
  • apps/portal/src/app/vault/page.mdx (1 hunks)
  • apps/portal/src/components/AI/chat-button.tsx (2 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx (0 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (4 hunks)
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Code.tsx (1 hunks)
  • apps/portal/src/components/Document/EditPage.tsx (1 hunks)
  • apps/portal/src/components/Document/FeatureCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Heading.tsx (4 hunks)
  • apps/portal/src/components/Document/InlineCode.tsx (1 hunks)
  • apps/portal/src/components/Document/NextPageButton.tsx (1 hunks)
  • apps/portal/src/components/Document/PageFooter.tsx (1 hunks)
  • apps/portal/src/components/Document/Paragraph.tsx (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.module.css (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.tsx (1 hunks)
  • apps/portal/src/components/Layouts/DocLayout.tsx (1 hunks)
  • apps/portal/src/components/others/DocSearch.tsx (10 hunks)
  • apps/portal/src/components/others/Feedback.tsx (1 hunks)
  • apps/portal/src/components/others/PlatformSelector.tsx (2 hunks)
  • apps/portal/src/components/others/Sidebar.tsx (3 hunks)
  • apps/portal/src/components/others/Subscribe.tsx (1 hunks)
  • apps/portal/src/components/ui/Anchor.tsx (2 hunks)
  • apps/portal/tailwind.config.ts (1 hunks)
  • packages/ui/src/global.css (1 hunks)
💤 Files with no reviewable changes (1)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx
✅ Files skipped from review due to trivial changes (1)
  • apps/portal/src/components/Document/InlineCode.tsx
🚧 Files skipped from review as they are similar to previous changes (13)
  • apps/portal/src/components/AI/chat-button.tsx
  • packages/ui/src/global.css
  • apps/portal/src/components/Document/Code.tsx
  • apps/portal/src/components/others/Subscribe.tsx
  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/package.json
  • apps/portal/src/app/globals.css
  • apps/portal/src/components/Document/Steps/Steps.module.css
  • apps/portal/src/components/Document/FeatureCard.tsx
  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/components/Document/Heading.tsx
  • apps/portal/src/components/Document/Paragraph.tsx
  • apps/portal/src/components/Document/EditPage.tsx
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (CLAUDE.md)

**/*.{ts,tsx}: Write idiomatic TypeScript with explicit function declarations and return types
Limit each file to one stateless, single-responsibility function for clarity
Re-use shared types from @/types or local types.ts barrels
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Choose composition over inheritance; leverage utility types (Partial, Pick, etc.)
Comment only ambiguous logic; avoid restating TypeScript in prose

**/*.{ts,tsx}: Use explicit function declarations and explicit return types in TypeScript
Limit each file to one stateless, single‑responsibility function
Re‑use shared types from @/types where applicable
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Prefer composition over inheritance; use utility types (Partial, Pick, etc.)
Lazy‑import optional features and avoid top‑level side‑effects to reduce bundle size

Files:

  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/tailwind.config.ts
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/Document/Steps/Steps.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/others/Sidebar.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
**/*.{ts,tsx,js,jsx}

📄 CodeRabbit inference engine (CLAUDE.md)

Load heavy dependencies inside async paths to keep initial bundle lean (lazy loading)

Files:

  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/tailwind.config.ts
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/Document/Steps/Steps.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/others/Sidebar.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
🧠 Learnings (13)
📚 Learning: 2025-05-29T00:46:09.063Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7188
File: apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/accounts/components/accounts-count.tsx:15-15
Timestamp: 2025-05-29T00:46:09.063Z
Learning: In the accounts component at apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/accounts/components/accounts-count.tsx, the 3-column grid layout (md:grid-cols-3) is intentionally maintained even when rendering only one StatCard, as part of the design structure for this component.

Applied to files:

  • apps/portal/src/app/vault/page.mdx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/layout.tsx : Building layout shells (`layout.tsx`) and top-level pages that mainly assemble data.

Applied to files:

  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
📚 Learning: 2025-06-18T04:30:04.326Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-06-18T04:27:16.172Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:27:16.172Z
Learning: Next.js Link component supports external URLs without throwing errors. When used with absolute URLs (like https://...), it behaves like a regular anchor tag without client-side routing, but does not cause runtime crashes or errors as previously believed.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Use `NavLink` (`@/components/ui/NavLink`) for internal navigation so active states are handled automatically.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Prefer composable primitives over custom markup: `Button`, `Input`, `Select`, `Tabs`, `Card`, `Sidebar`, `Separator`, `Badge`.

Applied to files:

  • apps/portal/src/components/others/PlatformSelector.tsx
📚 Learning: 2025-07-07T21:21:47.488Z
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:19:55.613Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: CLAUDE.md:0-0
Timestamp: 2025-07-18T19:19:55.613Z
Learning: Applies to apps/{dashboard,playground-web}/**/*.{ts,tsx} : Use `NavLink` for internal navigation with automatic active states in dashboard and playground apps

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-08-29T15:37:38.513Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: AGENTS.md:0-0
Timestamp: 2025-08-29T15:37:38.513Z
Learning: Applies to apps/{dashboard,playground}/**/*.{ts,tsx} : Use `NavLink` for internal navigation to get active state handling

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Icons come from `lucide-react` or the project-specific `…/icons` exports – never embed raw SVG.

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-31T16:17:42.753Z
Learnt from: MananTank
PR: thirdweb-dev/js#7768
File: apps/playground-web/src/app/navLinks.ts:1-1
Timestamp: 2025-07-31T16:17:42.753Z
Learning: Configuration files that import and reference React components (like icon components from lucide-react) need the "use client" directive, even if they primarily export static data, because the referenced components need to be executed in a client context when used by other client components.

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Layouts should reuse `SidebarLayout` / `FullWidthSidebarLayout` (`@/components/blocks/SidebarLayout`).

Applied to files:

  • apps/portal/src/components/others/Sidebar.tsx
📚 Learning: 2025-08-29T23:44:47.512Z
Learnt from: MananTank
PR: thirdweb-dev/js#7951
File: apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/_layout/contract-page-layout.tsx:38-38
Timestamp: 2025-08-29T23:44:47.512Z
Learning: The ContractPageLayout component in apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/_layout/contract-page-layout.tsx is not the root layout - it's nested within the dashboard layout which already handles footer positioning with min-h-dvh and AppFooter placement. The ContractPageLayout needs flex flex-col grow to properly participate in the parent's flex layout.

Applied to files:

  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
🧬 Code graph analysis (6)
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)
apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)
  • ArticleIconCard (31-70)
apps/portal/src/app/Header.tsx (3)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
apps/portal/src/components/others/DocSearch.tsx (1)
  • DocSearch (313-389)
apps/portal/src/components/AI/chat-button.tsx (1)
  • ChatButton (13-80)
apps/portal/src/components/others/PlatformSelector.tsx (1)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (1)
apps/playground-web/src/components/ui/select.tsx (3)
  • SelectTrigger (155-155)
  • SelectValue (154-154)
  • SelectContent (156-156)
apps/portal/src/app/layout.tsx (1)
packages/ui/src/lib/utils.ts (1)
  • cn (4-6)
apps/portal/src/components/Document/PageFooter.tsx (1)
apps/portal/src/components/Document/AutoNextPageButton.tsx (1)
  • AutoNextPageButton (8-27)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: Size
  • GitHub Check: Lint Packages
  • GitHub Check: E2E Tests (pnpm, webpack)
  • GitHub Check: Analyze (javascript)
🔇 Additional comments (15)
apps/portal/src/components/Document/Steps/Steps.tsx (1)

8-8: Dashed step connector reads nicely.

The added border-dashed styling sharpens the visual separation without affecting layout—looks great.

apps/portal/src/components/ui/Anchor.tsx (1)

3-29: Hash icon swap matches anchor semantics.

The new icon aligns with anchor link behavior and follows the lucide “Icon” suffix rule.

apps/portal/src/components/others/Sidebar.tsx (3)

229-240: Cleaner nested list spacing looks good

The padded wrapper plus border-l/gap-1 flex stack keeps the nested links aligned with the new visual system without touching interaction semantics. Nice polish.


252-252: Mobile trigger tweaks align with the new card style

h-auto, the rounded-xl shape, and the bordered card background make the trigger consistent with the rest of the portal buttons while preserving the DropdownMenu behavior. Looks solid.


264-264: Revised dropdown container matches the refreshed modal treatment

The compact horizontal padding and rounded-xl wrapper keep the mobile sidebar consistent with the new surface styling without impacting functionality. Nicely done.

apps/portal/src/components/others/PlatformSelector.tsx (1)

21-28: Trigger still needs to be the real control

DropdownMenuTrigger is styling a nested <div>, so focus/hover states land on the invisible wrapper button instead of the visible control. Use asChild and move the styles onto a <button> so keyboard focus and ARIA states work correctly.

-      <DropdownMenuTrigger>
-        <div className="flex gap-2 font-medium text-sm text-foreground hover:bg-accent justify-between items-center py-1.5 px-2.5 rounded-lg">
+      <DropdownMenuTrigger asChild>
+        <button
+          type="button"
+          className="flex gap-2 font-medium text-sm text-foreground hover:bg-accent justify-between items-center py-1.5 px-2.5 rounded-lg focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring"
+        >
           <div className="flex gap-2 items-center">
             <platform.icon className="size-4 text-foreground" />
             {platform.name}
           </div>
           <ChevronDownIcon className="w-4 text-muted-foreground opacity-70" />
-        </div>
+        </button>
       </DropdownMenuTrigger>
apps/portal/tailwind.config.ts (1)

17-20: Restore shared Tailwind font tokens before adding Geist

By assigning a fresh fontFamily map on Line 17 after spreading tailwindConfig.theme?.extend, we overwrite every font token shipped by the shared config (display, brand, etc.). Anything consuming those classes will now fall back to browser defaults. Please merge the existing entries instead of replacing them outright.

       extend: {
         ...tailwindConfig.theme?.extend,
-      fontFamily: {
-        sans: ["var(--font-geist-sans)"],
-        mono: ["var(--font-geist-mono)"],
-      },
+      fontFamily: {
+        ...(tailwindConfig.theme?.extend?.fontFamily ?? {}),
+        sans: ["var(--font-geist-sans)"],
+        mono: ["var(--font-geist-mono)"],
+      },
apps/portal/src/components/Document/PageFooter.tsx (1)

19-28: Avoid rendering an empty “next page” row

Line 22 still renders the wrapper whenever sidebarLinks is provided, even though AutoNextPageButton returns null for the current/last page. That leaves a blank padded row—a regression previously called out. Cache the button first and gate the wrapper on that truthy JSX.

 export function PageFooter(props: {
   editPageButton?: true;
   sidebarLinks?: SidebarLink[];
 }) {
+  const nextPageButton = props.sidebarLinks ? (
+    <AutoNextPageButton sidebarLinks={props.sidebarLinks} />
+  ) : null;
+
   return (
     <footer className="flex flex-col" data-noindex>
-      {props.sidebarLinks && (
+      {nextPageButton && (
         <div className="flex gap-4 justify-end items-center py-6">
-          <AutoNextPageButton sidebarLinks={props.sidebarLinks} />
+          {nextPageButton}
         </div>
       )}
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)

338-369: Import React types before using them

The new ArticleIconCard references React.FC (Line 341), but React isn’t in scope, so TypeScript can’t compile this file. Pull in the type explicitly (or switch to ComponentType) to restore type-checking.

 import { FileTextIcon, FolderOpenIcon } from "lucide-react";
 import type { Metadata } from "next";
 import Link from "next/link";
 import { notFound } from "next/navigation";
 import invariant from "tiny-invariant";
 import type { TransformedDoc } from "typedoc-better-json";
+import type { ComponentType } from "react";
 import { createMetadata, Details, Heading } from "@/components/Document";
 ...
 function ArticleIconCard(props: {
   title: string;
   href: string;
-  icon?: React.FC<{ className?: string }>;
+  icon?: ComponentType<{ className?: string }>;
   className?: string;
 }) {
⛔ Skipped due to learnings
Learnt from: MananTank
PR: thirdweb-dev/js#7356
File: apps/nebula/src/app/not-found.tsx:1-1
Timestamp: 2025-06-17T18:30:52.976Z
Learning: In the thirdweb/js project, the React namespace is available for type annotations (like React.FC) without needing to explicitly import React. This is project-specific configuration that differs from typical TypeScript/React setups.
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Icons come from `lucide-react` or the project-specific `…/icons` exports – never embed raw SVG.
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.
Learnt from: MananTank
PR: thirdweb-dev/js#7768
File: apps/playground-web/src/app/navLinks.ts:1-1
Timestamp: 2025-07-31T16:17:42.753Z
Learning: Configuration files that import and reference React components (like icon components from lucide-react) need the "use client" directive, even if they primarily export static data, because the referenced components need to be executed in a client context when used by other client components.
apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)

41-48: Add rel when opening external links in a new tab

We’re setting target="_blank" but not the protective rel="noopener noreferrer", which keeps the newly opened page from gaining a handle on our window (tab-nabbing/vector for hijacking). Please add the rel attribute alongside the conditional target.

-      data-noindex
-      href={props.href}
-      target={isExternal ? "_blank" : undefined}
+      data-noindex
+      href={props.href}
+      rel={isExternal ? "noopener noreferrer" : undefined}
+      target={isExternal ? "_blank" : undefined}
⛔ Skipped due to learnings
Learnt from: MananTank
PR: thirdweb-dev/js#7984
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/payments/components/FeatureCard.client.tsx:93-99
Timestamp: 2025-09-05T19:45:22.949Z
Learning: In the thirdweb dashboard project, rel="noopener noreferrer" attributes are not required for external links with target="_blank" in Link components, as confirmed by MananTank.
Learnt from: MananTank
PR: thirdweb-dev/js#7812
File: apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx:48-60
Timestamp: 2025-08-07T20:43:21.864Z
Learning: In the TokenBanner component at apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx, the Link components use target="_blank" with internal application routes (starting with "/") to open pages in new tabs within the same application. These internal links do not require rel="noopener noreferrer" security attributes, which are only needed for external URLs.
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:27:16.172Z
Learning: Next.js Link component supports external URLs without throwing errors. When used with absolute URLs (like https://...), it behaves like a regular anchor tag without client-side routing, but does not cause runtime crashes or errors as previously believed.
apps/portal/src/app/Header.tsx (1)

236-243: Harden external link to GitHub with rel="noopener noreferrer"

Same concern here: opening GitHub in a new tab without rel="noopener noreferrer" leaves a reverse‑tabnabbing hole. Let’s add the rel attribute together with the target.

-              <Link
-                className="text-foreground"
-                href="https://github.com/thirdweb-dev"
-                target="_blank"
-              >
+              <Link
+                className="text-foreground"
+                href="https://github.com/thirdweb-dev"
+                rel="noopener noreferrer"
+                target="_blank"
+              >
⛔ Skipped due to learnings
Learnt from: MananTank
PR: thirdweb-dev/js#7984
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/payments/components/FeatureCard.client.tsx:93-99
Timestamp: 2025-09-05T19:45:22.949Z
Learning: In the thirdweb dashboard project, rel="noopener noreferrer" attributes are not required for external links with target="_blank" in Link components, as confirmed by MananTank.
Learnt from: MananTank
PR: thirdweb-dev/js#7812
File: apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx:48-60
Timestamp: 2025-08-07T20:43:21.864Z
Learning: In the TokenBanner component at apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx, the Link components use target="_blank" with internal application routes (starting with "/") to open pages in new tabs within the same application. These internal links do not require rel="noopener noreferrer" security attributes, which are only needed for external URLs.
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.
apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (1)

76-183: UI polish aligns with new card aesthetic.

The rounded triggers and bg-card surface harmonize this control bar with the rest of the refreshed portal styling without touching behavior. Looks good.

apps/portal/src/app/vault/page.mdx (1)

21-48: Layout simplification reads well.

Switching the feature grid to a simple vertical stack keeps the section consistent with the new spacing rhythm while preserving content order. Nicely done.

apps/portal/src/app/layout.tsx (1)

3-27: Geist font wiring looks correct.

Importing the Geist font variables directly and piping them through cn(...) on the <body> mirrors Vercel’s recommended setup and keeps the Tailwind font-sans hook intact. All good here.

apps/portal/src/components/others/DocSearch.tsx (1)

149-495: DocSearch refinements land cleanly.

The tighter spacing, dashed section divider, and updated badge styles modernize the modal without affecting the underlying query/tag logic. Hover/selection states remain intact—nice sweep.

Warning

Review ran into problems

🔥 Problems

Errors were encountered while retrieving linked issues.

Errors (1)
  • TEAM-0000: Entity not found: Issue - Could not find referenced Issue.

Comment @coderabbitai help to get the list of available commands and usage tips.

@graphite-app
Copy link
Contributor

graphite-app bot commented Sep 25, 2025

How to use the Graphite Merge Queue

Add either label to this PR to merge it via the merge queue:

  • merge-queue - adds this PR to the back of the merge queue
  • hotfix - for urgent hot fixes, skip the queue and merge this PR next

You must have a Graphite account in order to use the merge queue. Sign up using this link.

An organization admin has enabled the Graphite Merge Queue in this repository.

Please do not merge from GitHub as this will restart CI on PRs being processed by the merge queue.

@github-actions github-actions bot added Portal Involves changes to the Portal (docs) codebase. packages labels Sep 25, 2025
@MananTank MananTank changed the title Portal: UI tweaks Portal: UI tweaks 2 Sep 25, 2025
@socket-security
Copy link

socket-security bot commented Sep 25, 2025

Review the following changes in direct dependencies. Learn more about Socket for GitHub.

Diff Package Supply Chain
Security
Vulnerability Quality Maintenance License
Addedgeist@​1.5.11001001009090

View full report

@github-actions
Copy link
Contributor

github-actions bot commented Sep 25, 2025

size-limit report 📦

Path Size Loading time (3g) Running time (snapdragon) Total time
thirdweb (esm) 64.09 KB (0%) 1.3 s (0%) 605 ms (+155.27% 🔺) 1.9 s
thirdweb (cjs) 361.63 KB (0%) 7.3 s (0%) 2.5 s (+16.98% 🔺) 9.7 s
thirdweb (minimal + tree-shaking) 5.73 KB (0%) 115 ms (0%) 291 ms (+2856.71% 🔺) 406 ms
thirdweb/chains (tree-shaking) 526 B (0%) 11 ms (0%) 59 ms (+608.43% 🔺) 69 ms
thirdweb/react (minimal + tree-shaking) 19.14 KB (0%) 383 ms (0%) 235 ms (+1747.17% 🔺) 618 ms

Copy link
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: 3

Caution

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

⚠️ Outside diff range comments (2)
apps/portal/src/app/layout.tsx (1)

3-27: Instantiate the Geist fonts before using their CSS variables.

Right now GeistMono/GeistSans are still the loader functions, so GeistMono.variable / GeistSans.variable evaluate to undefined. That means we never register the --font-geist-* custom properties your Tailwind config points at, and the body keeps falling back to the default sans stack. Please instantiate the fonts (and assign the variable option) before wiring them into cn(...).

-import { GeistMono } from "geist/font/mono";
-import { GeistSans } from "geist/font/sans";
+import { GeistMono } from "geist/font/mono";
+import { GeistSans } from "geist/font/sans";-export default function RootLayout({
+const geistMono = GeistMono({
+  subsets: ["latin"],
+  variable: "--font-geist-mono",
+});
+
+const geistSans = GeistSans({
+  subsets: ["latin"],
+  variable: "--font-geist-sans",
+});
+
+export default function RootLayout({
   children,
 }: {
   children: React.ReactNode;
 }) {
   return (
     <html lang="en" suppressHydrationWarning>
       <body
-        className={cn(GeistMono.variable, GeistSans.variable, "font-sans")}
+        className={cn(geistMono.variable, geistSans.variable, "font-sans")}
         suppressHydrationWarning
       >
apps/portal/src/components/others/Sidebar.tsx (1)

106-115: Prevent reverse‑tabnabbing on external links.

External links opened with target="_blank" lack rel="noopener noreferrer".

-        target={link.href.startsWith("http") ? "_blank" : undefined}
+        target={link.href.startsWith("http") ? "_blank" : undefined}
+        rel={link.href.startsWith("http") ? "noopener noreferrer" : undefined}

Apply the same change to the other Link variant below.

Also applies to: 124-133

🧹 Nitpick comments (5)
apps/portal/src/components/Document/NextPageButton.tsx (1)

10-10: Trim leading whitespace inside the span

The literal space before {props.name} renders as a leading space in the label. Since the flex container already applies gap-2, this extra whitespace is redundant—please drop it to keep the text tidy.

-      <span> {props.name}</span>
+      <span>{props.name}</span>
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)

338-369: Avoid duplicating ArticleIconCard.

We now have two components with the same name but diverging props/styles (@/components/Document/Cards/ArticleCard and this local copy). That duplication will drift quickly and complicate future tweaks. Please reuse the shared component (overriding via className as needed) or rename this local variant to make the distinction explicit.

apps/portal/src/components/others/Sidebar.tsx (3)

229-240: Use tokenized border color and stable list keys (avoid index).

  • Add border-border for consistent theming.
  • Replace array index keys to prevent reconciliation issues on reorders.
-      <div className="pl-4 py-1">
-        <ul className="flex flex-col border-l pl-2 gap-1">
-          {links.map((link, i) => {
+      <div className="pl-4 py-1">
+        <ul className="flex flex-col border-l border-border pl-2 gap-1">
+          {links.map((link) => {
             return (
               // biome-ignore lint/suspicious/noArrayIndexKey: TODO - fix this
-              <li key={i}>
+              <li key={getSidebarKey(link)}>
                 <SidebarItem link={link} onLinkClick={props.onLinkClick} />
               </li>
             );
           })}
         </ul>
       </div>

Add this helper near other utils:

function getSidebarKey(link: SidebarLink): string {
  if ("separator" in link) return "sep";
  if ("links" in link) return `group:${link.name}`;
  return `link:${link.href ?? link.name}`;
}

252-252: Tokenize border color on the trigger Button.

Add border-border to align with theme borders.

-        <Button className="w-full justify-between border bg-card py-3 h-auto rounded-xl text-left text-foreground hover:bg-card xl:hidden">
+        <Button className="w-full justify-between border border-border bg-card py-3 h-auto rounded-xl text-left text-foreground hover:bg-card xl:hidden">

264-264: Tokenize dropdown container border color.

Add border-border for consistent visuals.

-        <div className="max-h-[70vh] w-[calc(100vw-32px)] overflow-y-auto rounded-xl border bg-card px-2">
+        <div className="max-h-[70vh] w-[calc(100vw-32px)] overflow-y-auto rounded-xl border border-border bg-card px-2">
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

Disabled knowledge base sources:

  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 7bc513c and 1880b3f.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (29)
  • apps/portal/package.json (1 hunks)
  • apps/portal/src/app/Header.tsx (2 hunks)
  • apps/portal/src/app/globals.css (1 hunks)
  • apps/portal/src/app/layout.tsx (2 hunks)
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx (2 hunks)
  • apps/portal/src/app/vault/page.mdx (1 hunks)
  • apps/portal/src/components/AI/chat-button.tsx (2 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx (0 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (4 hunks)
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Code.tsx (1 hunks)
  • apps/portal/src/components/Document/EditPage.tsx (1 hunks)
  • apps/portal/src/components/Document/FeatureCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Heading.tsx (4 hunks)
  • apps/portal/src/components/Document/InlineCode.tsx (1 hunks)
  • apps/portal/src/components/Document/NextPageButton.tsx (1 hunks)
  • apps/portal/src/components/Document/PageFooter.tsx (2 hunks)
  • apps/portal/src/components/Document/Paragraph.tsx (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.module.css (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.tsx (1 hunks)
  • apps/portal/src/components/Layouts/DocLayout.tsx (1 hunks)
  • apps/portal/src/components/others/DocSearch.tsx (10 hunks)
  • apps/portal/src/components/others/Feedback.tsx (1 hunks)
  • apps/portal/src/components/others/PlatformSelector.tsx (2 hunks)
  • apps/portal/src/components/others/Sidebar.tsx (3 hunks)
  • apps/portal/src/components/others/Subscribe.tsx (1 hunks)
  • apps/portal/src/components/ui/Anchor.tsx (2 hunks)
  • apps/portal/tailwind.config.ts (1 hunks)
  • packages/ui/src/global.css (1 hunks)
💤 Files with no reviewable changes (1)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx
🧰 Additional context used
📓 Path-based instructions (3)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (CLAUDE.md)

**/*.{ts,tsx}: Write idiomatic TypeScript with explicit function declarations and return types
Limit each file to one stateless, single-responsibility function for clarity
Re-use shared types from @/types or local types.ts barrels
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Choose composition over inheritance; leverage utility types (Partial, Pick, etc.)
Comment only ambiguous logic; avoid restating TypeScript in prose

**/*.{ts,tsx}: Use explicit function declarations and explicit return types in TypeScript
Limit each file to one stateless, single‑responsibility function
Re‑use shared types from @/types where applicable
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Prefer composition over inheritance; use utility types (Partial, Pick, etc.)
Lazy‑import optional features and avoid top‑level side‑effects to reduce bundle size

Files:

  • apps/portal/src/components/Document/Steps/Steps.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/components/Document/EditPage.tsx
  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/components/Document/Code.tsx
  • apps/portal/src/components/others/Sidebar.tsx
  • apps/portal/src/components/others/Subscribe.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/Document/Paragraph.tsx
  • apps/portal/src/components/Document/InlineCode.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
  • apps/portal/src/components/Document/FeatureCard.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/Document/Heading.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/tailwind.config.ts
**/*.{ts,tsx,js,jsx}

📄 CodeRabbit inference engine (CLAUDE.md)

Load heavy dependencies inside async paths to keep initial bundle lean (lazy loading)

Files:

  • apps/portal/src/components/Document/Steps/Steps.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/components/Document/EditPage.tsx
  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/components/Document/Code.tsx
  • apps/portal/src/components/others/Sidebar.tsx
  • apps/portal/src/components/others/Subscribe.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/Document/Paragraph.tsx
  • apps/portal/src/components/Document/InlineCode.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
  • apps/portal/src/components/Document/FeatureCard.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/Document/Heading.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/tailwind.config.ts
**/package.json

📄 CodeRabbit inference engine (AGENTS.md)

Track bundle budgets via package.json#size-limit

Files:

  • apps/portal/package.json
🧠 Learnings (17)
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Layouts should reuse `SidebarLayout` / `FullWidthSidebarLayout` (`@/components/blocks/SidebarLayout`).

Applied to files:

  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/components/others/Sidebar.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Stick to design-tokens: background (`bg-card`), borders (`border-border`), muted text (`text-muted-foreground`) etc.

Applied to files:

  • apps/portal/src/components/Layouts/DocLayout.tsx
📚 Learning: 2025-08-29T15:37:38.513Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: AGENTS.md:0-0
Timestamp: 2025-08-29T15:37:38.513Z
Learning: Applies to apps/{dashboard,playground}/**/*.{ts,tsx} : Stick to design tokens (e.g., bg-card, border-border, text-muted-foreground)

Applied to files:

  • apps/portal/src/components/Layouts/DocLayout.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/layout.tsx : Building layout shells (`layout.tsx`) and top-level pages that mainly assemble data.

Applied to files:

  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
📚 Learning: 2025-06-18T04:30:04.326Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.

Applied to files:

  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-06-18T04:27:16.172Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:27:16.172Z
Learning: Next.js Link component supports external URLs without throwing errors. When used with absolute URLs (like https://...), it behaves like a regular anchor tag without client-side routing, but does not cause runtime crashes or errors as previously believed.

Applied to files:

  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Use `NavLink` (`@/components/ui/NavLink`) for internal navigation so active states are handled automatically.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-31T16:17:42.753Z
Learnt from: MananTank
PR: thirdweb-dev/js#7768
File: apps/playground-web/src/app/navLinks.ts:1-1
Timestamp: 2025-07-31T16:17:42.753Z
Learning: Configuration files that import and reference React components (like icon components from lucide-react) need the "use client" directive, even if they primarily export static data, because the referenced components need to be executed in a client context when used by other client components.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*client.tsx : Interactive UI that relies on hooks (`useState`, `useEffect`, React Query, wallet hooks).

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Icons come from `lucide-react` or the project-specific `…/icons` exports – never embed raw SVG.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
📚 Learning: 2025-07-07T21:21:47.488Z
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Spacing utilities (`px-*`, `py-*`, `gap-*`) are preferred over custom margins.

Applied to files:

  • apps/portal/src/components/Document/Paragraph.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Combine class names via `cn`, expose `className` prop if useful.

Applied to files:

  • apps/portal/src/components/Document/InlineCode.tsx
📚 Learning: 2025-08-29T23:44:47.512Z
Learnt from: MananTank
PR: thirdweb-dev/js#7951
File: apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/_layout/contract-page-layout.tsx:38-38
Timestamp: 2025-08-29T23:44:47.512Z
Learning: The ContractPageLayout component in apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/_layout/contract-page-layout.tsx is not the root layout - it's nested within the dashboard layout which already handles footer positioning with min-h-dvh and AppFooter placement. The ContractPageLayout needs flex flex-col grow to properly participate in the parent's flex layout.

Applied to files:

  • apps/portal/src/components/Document/PageFooter.tsx
  • apps/portal/src/components/others/Feedback.tsx
📚 Learning: 2025-05-29T00:46:09.063Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7188
File: apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/accounts/components/accounts-count.tsx:15-15
Timestamp: 2025-05-29T00:46:09.063Z
Learning: In the accounts component at apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/accounts/components/accounts-count.tsx, the 3-column grid layout (md:grid-cols-3) is intentionally maintained even when rendering only one StatCard, as part of the design structure for this component.

Applied to files:

  • apps/portal/src/app/vault/page.mdx
📚 Learning: 2025-07-18T19:19:55.613Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: CLAUDE.md:0-0
Timestamp: 2025-07-18T19:19:55.613Z
Learning: Applies to apps/{dashboard,playground-web}/**/*.{ts,tsx} : Use `NavLink` for internal navigation with automatic active states in dashboard and playground apps

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-08-29T15:37:38.513Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: AGENTS.md:0-0
Timestamp: 2025-08-29T15:37:38.513Z
Learning: Applies to apps/{dashboard,playground}/**/*.{ts,tsx} : Use `NavLink` for internal navigation to get active state handling

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
🧬 Code graph analysis (7)
apps/portal/src/app/layout.tsx (1)
packages/ui/src/lib/utils.ts (1)
  • cn (4-6)
apps/portal/src/components/others/DocSearch.tsx (1)
apps/playground-web/src/components/ui/dialog.tsx (1)
  • DialogContent (117-117)
apps/portal/src/components/Document/PageFooter.tsx (2)
apps/portal/src/components/Document/AutoNextPageButton.tsx (1)
  • AutoNextPageButton (8-27)
apps/portal/src/components/Document/DocLink.tsx (1)
  • DocLink (4-27)
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)
apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)
  • ArticleIconCard (31-70)
apps/portal/src/app/Header.tsx (3)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
apps/portal/src/components/others/DocSearch.tsx (1)
  • DocSearch (313-389)
apps/portal/src/components/AI/chat-button.tsx (1)
  • ChatButton (13-80)
apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (1)
apps/playground-web/src/components/ui/select.tsx (3)
  • SelectTrigger (155-155)
  • SelectValue (154-154)
  • SelectContent (156-156)
apps/portal/src/components/others/PlatformSelector.tsx (1)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (8)
  • GitHub Check: E2E Tests (pnpm, esbuild)
  • GitHub Check: Size
  • GitHub Check: E2E Tests (pnpm, webpack)
  • GitHub Check: E2E Tests (pnpm, vite)
  • GitHub Check: Unit Tests
  • GitHub Check: Build Packages
  • GitHub Check: Lint Packages
  • GitHub Check: Analyze (javascript)
🔇 Additional comments (24)
apps/portal/src/app/vault/page.mdx (1)

21-48: Vertical stack matches updated spacing system

Switching the feature list to space-y-4 keeps the new vertical rhythm consistent with the rest of the portal refresh. Looks solid.

apps/portal/src/components/others/Subscribe.tsx (1)

38-38: Typography tweak looks good

The muted foreground class aligns the helper copy with the updated palette while keeping layout intact. No issues spotted.

apps/portal/src/components/Document/InlineCode.tsx (1)

7-7: Background-opacity adjustment looks good

The lighter muted tone keeps inline code readable while better matching the updated Portal styling sweep.

apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (1)

76-184: Refined header and dropdown styling look solid

The updated spacing plus the rounded-full/rounded-xl treatments are consistent with the broader visual refresh. No functional concerns here.

apps/portal/src/components/Document/Steps/Steps.tsx (1)

8-8: Dashed rail update looks consistent

The dashed style aligns with the refreshed step indicator treatment and keeps the layout clean.

apps/portal/src/components/Document/Steps/Steps.module.css (1)

3-3: Token swap on the step badge reads well

The new utility mix keeps the badge aligned with the design system while adding the subtle border.

apps/portal/src/components/others/DocSearch.tsx (4)

149-197: Tag pill polish looks great

The tighter spacing plus the muted translucent background/border combo give the tag row a cleaner read without sacrificing clarity. Nice touch anchoring the selected state with border-foreground.


202-258: Appreciate the tightened result stack

Switching to gap-1, the dashed section border, and the slimmer padding sharpen the visual hierarchy and make scanning nested hits much easier. Solid refinement.


379-385: Modal framing update LGTM

Adding rounded-xl and keeping the surface on bg-background aligns this dialog with the rest of the portal polish—ready to ship.


454-495: Search result item styling feels cohesive

The smaller icon, consistent text sizing, and subtle accent hover state tie these cards together nicely. The tag badges with border-border/50 are a thoughtful detail.

apps/portal/src/components/Document/Code.tsx (1)

67-72: Dark-mode code background aligns with the new palette.

dark:bg-background keeps parity with the updated theme variables while preserving the existing light-mode styling. Looks good.

apps/portal/src/components/Document/FeatureCard.tsx (1)

12-12: Rounded-xl matches the refreshed card geometry.

The bump to rounded-xl brings this card in line with the other document surfaces introduced in the PR.

apps/portal/src/components/ui/Anchor.tsx (1)

3-29: Anchor hash icon swap is solid.

Using HashIcon clarifies the in-page link affordance and stays consistent with the lucide naming convention we enforce.

apps/portal/src/components/Document/Paragraph.tsx (1)

8-8: Extra bottom spacing reads well.

mb-5 gives paragraphs a bit more breathing room without affecting the component’s responsibility. All good.

apps/portal/src/components/AI/chat-button.tsx (1)

3-31: Brain icon fits the AI chat affordance.

The icon swap is clear, keeps the suffix convention, and doesn’t alter the interaction logic. Looks great.

apps/portal/src/components/Document/Heading.tsx (1)

17-75: Typography scale adjustment LGTM.

The updated weights and sizes line up with the new Geist scale and keep the heading hierarchy clear.

packages/ui/src/global.css (1)

160-165: Text rendering tweaks look good.

The additional font smoothing settings should produce crisper body copy with the new font stack.

apps/portal/src/components/others/PlatformSelector.tsx (1)

21-59: Styling refinements LGTM.

The trigger/content adjustments keep the selector compact and consistent with the refreshed header.

apps/portal/src/components/others/Feedback.tsx (1)

23-75: Feedback banner update LGTM.

Layout and spacing changes stay aligned with the new portal styling without touching logic.

apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)

43-68: Icon card refresh LGTM.

The richer affordance (rounded icon pill + tighter typography track) reads well with the Geist update.

apps/portal/src/app/Header.tsx (1)

216-429: Header restructure LGTM.

The new two-row layout and control clustering behave well across breakpoints.

apps/portal/src/components/Layouts/DocLayout.tsx (1)

52-54: Add tokenized border color
Replace border-b with border-b border-border to use the design-system token. z-stickyMobileSidebar is already defined (500) in the Tailwind config.

⛔ Skipped due to learnings
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Stick to design-tokens: background (`bg-card`), borders (`border-border`), muted text (`text-muted-foreground`) etc.
Learnt from: CR
PR: thirdweb-dev/js#0
File: CLAUDE.md:0-0
Timestamp: 2025-07-18T19:19:55.613Z
Learning: Applies to apps/{dashboard,playground-web}/**/*.{ts,tsx} : Use design system tokens (e.g., `bg-card`, `border-border`, `text-muted-foreground`)
Learnt from: CR
PR: thirdweb-dev/js#0
File: AGENTS.md:0-0
Timestamp: 2025-08-29T15:37:38.513Z
Learning: Applies to apps/{dashboard,playground}/**/*.{ts,tsx} : Stick to design tokens (e.g., bg-card, border-border, text-muted-foreground)
apps/portal/package.json (1)

20-20: Geist runtime dependency addition looks good.

Aligns with the new font usage introduced elsewhere in the portal.

apps/portal/src/app/globals.css (1)

1-3: Ligature enablement fits the updated typography.

No issues spotted with enabling standard ligatures globally.

@codecov
Copy link

codecov bot commented Sep 25, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 56.27%. Comparing base (95412c7) to head (10fb338).
⚠️ Report is 2 commits behind head on main.

Additional details and impacted files
@@            Coverage Diff             @@
##             main    #8127      +/-   ##
==========================================
- Coverage   56.28%   56.27%   -0.01%     
==========================================
  Files         906      906              
  Lines       59193    59193              
  Branches     4173     4174       +1     
==========================================
- Hits        33316    33311       -5     
- Misses      25772    25777       +5     
  Partials      105      105              
Flag Coverage Δ
packages 56.27% <ø> (-0.01%) ⬇️
see 2 files with indirect coverage changes
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Copy link
Member Author

MananTank commented Sep 25, 2025


How to use the Graphite Merge Queue

Add either label to this PR to merge it via the merge queue:

  • merge-queue - adds this PR to the back of the merge queue
  • hotfix - for urgent hot fixes, skip the queue and merge this PR next

You must have a Graphite account in order to use the merge queue. Sign up using this link.

An organization admin has enabled the Graphite Merge Queue in this repository.

Please do not merge from GitHub as this will restart CI on PRs being processed by the merge queue.

This stack of pull requests is managed by Graphite. Learn more about stacking.

Copy link
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: 1

Caution

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

⚠️ Outside diff range comments (1)
apps/portal/src/components/Document/Code.tsx (1)

67-81: Revert the dark-mode background override

ScrollShadow keeps using hsl(var(--card)) for its fades, so switching the <code> background to var(--background) only in dark mode makes the shadow gradient sit on a different color than the block itself. The mismatch is noticeable in the current dark theme. Please keep the card background (or update both background and shadow together) to avoid the regression.

-          "relative block whitespace-pre rounded-lg border bg-card dark:bg-background font-mono text-sm leading-relaxed",
+          "relative block whitespace-pre rounded-lg border bg-card font-mono text-sm leading-relaxed",
🧹 Nitpick comments (9)
apps/portal/src/components/others/Feedback.tsx (1)

23-23: Restore mobile-friendly column layout for the feedback prompt

Dropping the flex-col/md:flex-row split forces the prompt text and button group to share a single row at all breakpoints. On narrow viewports (e.g., ~320 px wide phones or tighter doc content panes), the two outline buttons keep their whitespace-nowrap footprint, so the parent can’t shrink enough to accommodate the copy without severe wrapping or horizontal overflow. Restoring the previous responsive stack keeps the mobile layout readable while preserving the horizontal alignment on md+.

-      <div className="md:h-16 flex items-center gap-4">
+      <div className="flex flex-col gap-2 md:h-16 md:flex-row md:items-center md:gap-4">
apps/portal/src/components/AI/chat-button.tsx (1)

13-20: Add explicit return types and basic dialog a11y attributes

  • Add return types per TS guidelines.
  • Add aria-haspopup/expanded/controls on the trigger and an id on the sheet container for better a11y.
-export function ChatButton() {
+export function ChatButton(): JSX.Element {
@@
-      <Button
+      <Button
+        aria-controls="chat-modal"
+        aria-expanded={isOpen}
+        aria-haspopup="dialog"
         className="gap-2 rounded-full bg-background"
         onClick={() => {
           setIsOpen(true);
           setHasBeenOpened(true);
         }}
         variant="outline"
       >
@@
-      <div
+      <div
+        id="chat-modal"
         className={cn(
           "slide-in-from-bottom-20 zoom-in-95 fade-in-0 fixed bottom-0 left-0 z-modal flex h-[80vh] w-[100vw] animate-in flex-col overflow-hidden rounded-t-2xl border bg-background shadow-2xl duration-200 lg:right-6 lg:bottom-6 lg:left-auto lg:h-[80vh] lg:max-w-xl lg:rounded-xl",
           !isOpen && "hidden",
         )}
       >
@@
-function ChatLoading() {
+function ChatLoading(): JSX.Element {

Also applies to: 25-33, 35-41, 70-76, 82-89

apps/portal/src/components/Document/Heading.tsx (1)

4-12: Add explicit return type to match TS guidelines

Keeps component signatures consistent.

-export function Heading(props: {
+export function Heading(props: {
   children: React.ReactNode;
   anchorId: string;
   level: number;
   className?: string;
   anchorClassName?: string;
   noIndex?: boolean;
-}) {
+}): JSX.Element {
apps/portal/src/components/others/PlatformSelector.tsx (2)

21-29: Use asChild and a semantic trigger element for focus/a11y

Let the trigger be the actual focusable element so Radix can manage aria-expanded/aria-controls and focus rings. Styling the inner div leaves focus styles invisible.

-      <DropdownMenuTrigger>
-        <div className="flex gap-2 font-medium text-sm text-foreground hover:bg-accent justify-between items-center py-1.5 px-2.5 rounded-lg">
+      <DropdownMenuTrigger asChild>
+        <button
+          type="button"
+          className="flex gap-2 font-medium text-sm text-foreground hover:bg-accent justify-between items-center py-1.5 px-2.5 rounded-lg"
+        >
           <div className="flex gap-2 items-center">
             <platform.icon className="size-4 text-foreground" />
             {platform.name}
           </div>
           <ChevronDownIcon className="w-4 text-muted-foreground opacity-70" />
-        </div>
+        </button>
       </DropdownMenuTrigger>

37-55: Avoid nested interactive elements inside DropdownMenuItem

Make Link the direct child of DropdownMenuItem asChild for correct roles, focus, and click handling.

-            <DropdownMenuItem asChild key={platform.name}>
-              <div
-                className={clsx(
-                  "relative flex cursor-pointer font-medium text-foreground text-lg",
-                  "hover:bg-accent",
-                  props.selected === platform.name &&
-                    "bg-muted text-foreground",
-                )}
-              >
-                <div className="flex gap-2">
-                  <platform.icon className="size-4 text-foreground" />
-                  <Link
-                    className="before:absolute before:inset-0 text-sm"
-                    href={platform.href}
-                  >
-                    {platform.name}
-                  </Link>
-                </div>
-              </div>
-            </DropdownMenuItem>
+            <DropdownMenuItem asChild key={platform.name}>
+              <Link
+                className={clsx(
+                  "relative flex cursor-pointer items-center gap-2 font-medium text-foreground text-sm !rounded-lg px-2 py-1.5",
+                  "hover:bg-accent",
+                  props.selected === platform.name && "bg-muted text-foreground",
+                  "before:absolute before:inset-0",
+                )}
+                href={platform.href}
+                prefetch={false}
+              >
+                <platform.icon className="size-4 text-foreground" />
+                <span>{platform.name}</span>
+              </Link>
+            </DropdownMenuItem>

Also applies to: 46-55

apps/portal/src/components/others/DocSearch.tsx (1)

454-457: Avoid prefetching many result links

Search results can be numerous; disable Next.js prefetch to reduce network noise.

-    <Link
+    <Link
       className="flex gap-3 rounded-lg px-3 py-2.5 text-muted-foreground transition-colors hover:bg-accent/50"
       href={props.href}
+      prefetch={false}
       onClick={props.onClick}
     >
apps/portal/src/app/Header.tsx (3)

257-268: Add menu a11y attributes and link to panel

Expose expanded state and control relationship.

-              <Button
+              <Button
                 className="p-2"
                 onClick={() => setShowBurgerMenu(!showBurgerMenu)}
                 variant="ghost"
+                aria-haspopup="menu"
+                aria-expanded={showBurgerMenu}
+                aria-controls="mobile-menu"
               >
                 <MenuIcon className="size-7" />
               </Button>
-        <div className="fixed inset-0 top-sticky-top-height z-50 overflow-auto bg-card p-6 xl:hidden">
+        <div
+          id="mobile-menu"
+          className="fixed inset-0 top-sticky-top-height z-50 overflow-auto bg-card p-6 xl:hidden"
+        >

Also applies to: 342-345


457-481: Make dropdown items direct Links; add rel for external targets

Avoid nested interactive elements and add rel for security.

-                <DropdownMenuItem asChild key={info.name}>
-                  <div
-                    className={clsx(
-                      "relative flex cursor-pointer gap-3 font-medium text-foreground !rounded-lg px-3 py-2",
-                      "hover:bg-accent",
-                    )}
-                  >
-                    {info.icon && (
-                      <info.icon className="size-5 text-muted-foreground" />
-                    )}
-                    <Link
-                      className="before:absolute before:inset-0"
-                      href={info.href}
-                      prefetch={false}
-                      target={info.href.startsWith("http") ? "_blank" : ""}
-                    >
-                      {info.name}
-                    </Link>
-                  </div>
-                </DropdownMenuItem>
+                <DropdownMenuItem asChild key={info.name}>
+                  <Link
+                    className={clsx(
+                      "relative flex items-center gap-3 font-medium text-foreground !rounded-lg px-3 py-2",
+                      "hover:bg-accent",
+                      "before:absolute before:inset-0",
+                    )}
+                    href={info.href}
+                    prefetch={false}
+                    target={info.href.startsWith("http") ? "_blank" : undefined}
+                    rel={info.href.startsWith("http") ? "noopener noreferrer" : undefined}
+                  >
+                    {info.icon && (
+                      <info.icon className="size-5 text-muted-foreground" />
+                    )}
+                    {info.name}
+                  </Link>
+                </DropdownMenuItem>

527-539: Add rel and consider disabling prefetch for generic nav links

Safer external links; optional prefetch reduction for header links.

     <Link
       className={clsx(
@@
       )}
       href={props.href}
+      prefetch={false}
       onClick={props.onClick}
-      target={props.href.startsWith("http") ? "_blank" : ""}
+      target={props.href.startsWith("http") ? "_blank" : undefined}
+      rel={props.href.startsWith("http") ? "noopener noreferrer" : undefined}
     >
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

Disabled knowledge base sources:

  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 1880b3f and e8ae37d.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (29)
  • apps/portal/package.json (1 hunks)
  • apps/portal/src/app/Header.tsx (2 hunks)
  • apps/portal/src/app/globals.css (1 hunks)
  • apps/portal/src/app/layout.tsx (2 hunks)
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx (2 hunks)
  • apps/portal/src/app/vault/page.mdx (1 hunks)
  • apps/portal/src/components/AI/chat-button.tsx (2 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx (0 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (4 hunks)
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Code.tsx (1 hunks)
  • apps/portal/src/components/Document/EditPage.tsx (1 hunks)
  • apps/portal/src/components/Document/FeatureCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Heading.tsx (4 hunks)
  • apps/portal/src/components/Document/InlineCode.tsx (1 hunks)
  • apps/portal/src/components/Document/NextPageButton.tsx (1 hunks)
  • apps/portal/src/components/Document/PageFooter.tsx (1 hunks)
  • apps/portal/src/components/Document/Paragraph.tsx (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.module.css (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.tsx (1 hunks)
  • apps/portal/src/components/Layouts/DocLayout.tsx (1 hunks)
  • apps/portal/src/components/others/DocSearch.tsx (10 hunks)
  • apps/portal/src/components/others/Feedback.tsx (1 hunks)
  • apps/portal/src/components/others/PlatformSelector.tsx (2 hunks)
  • apps/portal/src/components/others/Sidebar.tsx (3 hunks)
  • apps/portal/src/components/others/Subscribe.tsx (1 hunks)
  • apps/portal/src/components/ui/Anchor.tsx (2 hunks)
  • apps/portal/tailwind.config.ts (1 hunks)
  • packages/ui/src/global.css (1 hunks)
💤 Files with no reviewable changes (1)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx
✅ Files skipped from review due to trivial changes (1)
  • apps/portal/src/components/others/Sidebar.tsx
🚧 Files skipped from review as they are similar to previous changes (11)
  • apps/portal/src/app/vault/page.mdx
  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/components/Document/Paragraph.tsx
  • apps/portal/src/components/Document/EditPage.tsx
  • apps/portal/src/components/Document/Steps/Steps.tsx
  • packages/ui/src/global.css
  • apps/portal/src/app/globals.css
  • apps/portal/src/components/Document/InlineCode.tsx
  • apps/portal/src/components/Document/Steps/Steps.module.css
  • apps/portal/tailwind.config.ts
  • apps/portal/package.json
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (CLAUDE.md)

**/*.{ts,tsx}: Write idiomatic TypeScript with explicit function declarations and return types
Limit each file to one stateless, single-responsibility function for clarity
Re-use shared types from @/types or local types.ts barrels
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Choose composition over inheritance; leverage utility types (Partial, Pick, etc.)
Comment only ambiguous logic; avoid restating TypeScript in prose

**/*.{ts,tsx}: Use explicit function declarations and explicit return types in TypeScript
Limit each file to one stateless, single‑responsibility function
Re‑use shared types from @/types where applicable
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Prefer composition over inheritance; use utility types (Partial, Pick, etc.)
Lazy‑import optional features and avoid top‑level side‑effects to reduce bundle size

Files:

  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/Document/FeatureCard.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/others/Subscribe.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/src/components/Document/Code.tsx
  • apps/portal/src/components/Document/Heading.tsx
**/*.{ts,tsx,js,jsx}

📄 CodeRabbit inference engine (CLAUDE.md)

Load heavy dependencies inside async paths to keep initial bundle lean (lazy loading)

Files:

  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/Document/FeatureCard.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/Document/PageFooter.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/others/Subscribe.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/src/components/Document/Code.tsx
  • apps/portal/src/components/Document/Heading.tsx
🧠 Learnings (10)
📚 Learning: 2025-07-07T21:21:47.488Z
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.

Applied to files:

  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-31T16:17:42.753Z
Learnt from: MananTank
PR: thirdweb-dev/js#7768
File: apps/playground-web/src/app/navLinks.ts:1-1
Timestamp: 2025-07-31T16:17:42.753Z
Learning: Configuration files that import and reference React components (like icon components from lucide-react) need the "use client" directive, even if they primarily export static data, because the referenced components need to be executed in a client context when used by other client components.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*client.tsx : Interactive UI that relies on hooks (`useState`, `useEffect`, React Query, wallet hooks).

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Icons come from `lucide-react` or the project-specific `…/icons` exports – never embed raw SVG.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
📚 Learning: 2025-08-29T23:44:47.512Z
Learnt from: MananTank
PR: thirdweb-dev/js#7951
File: apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/_layout/contract-page-layout.tsx:38-38
Timestamp: 2025-08-29T23:44:47.512Z
Learning: The ContractPageLayout component in apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/_layout/contract-page-layout.tsx is not the root layout - it's nested within the dashboard layout which already handles footer positioning with min-h-dvh and AppFooter placement. The ContractPageLayout needs flex flex-col grow to properly participate in the parent's flex layout.

Applied to files:

  • apps/portal/src/components/Document/PageFooter.tsx
  • apps/portal/src/components/others/Feedback.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/layout.tsx : Building layout shells (`layout.tsx`) and top-level pages that mainly assemble data.

Applied to files:

  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
📚 Learning: 2025-06-18T04:30:04.326Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-06-18T04:27:16.172Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:27:16.172Z
Learning: Next.js Link component supports external URLs without throwing errors. When used with absolute URLs (like https://...), it behaves like a regular anchor tag without client-side routing, but does not cause runtime crashes or errors as previously believed.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Use `NavLink` (`@/components/ui/NavLink`) for internal navigation so active states are handled automatically.

Applied to files:

  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-08-29T15:37:38.513Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: AGENTS.md:0-0
Timestamp: 2025-08-29T15:37:38.513Z
Learning: Applies to apps/{dashboard,playground}/**/*.{ts,tsx} : Use `NavLink` for internal navigation to get active state handling

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
🧬 Code graph analysis (6)
apps/portal/src/app/layout.tsx (1)
packages/ui/src/lib/utils.ts (1)
  • cn (4-6)
apps/portal/src/app/Header.tsx (3)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
apps/portal/src/components/others/DocSearch.tsx (1)
  • DocSearch (313-389)
apps/portal/src/components/AI/chat-button.tsx (1)
  • ChatButton (13-80)
apps/portal/src/components/Document/PageFooter.tsx (1)
apps/portal/src/components/Document/AutoNextPageButton.tsx (1)
  • AutoNextPageButton (8-27)
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)
apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)
  • ArticleIconCard (31-70)
apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (1)
apps/playground-web/src/components/ui/select.tsx (3)
  • SelectTrigger (155-155)
  • SelectValue (154-154)
  • SelectContent (156-156)
apps/portal/src/components/others/PlatformSelector.tsx (1)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
  • GitHub Check: Size
  • GitHub Check: Analyze (javascript)
🔇 Additional comments (13)
apps/portal/src/components/others/Subscribe.tsx (1)

38-38: Keep the muted helper text tweak.

Switching this helper copy to text-muted-foreground (and dropping the medium weight) keeps it aligned with the subtler supporting text style used elsewhere in the PR. Looks good.

apps/portal/src/components/ui/Anchor.tsx (1)

3-28: Icon swap aligns with anchor affordance.

Switching to HashIcon makes the self-link affordance clearer for headings while keeping the hover reveal and spacing intact. Looks good.

apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (1)

76-76: Consistent design token refresh looks solid

The upgraded spacing plus the rounded bg-card triggers / rounded-xl content align cleanly with the refreshed Portal palette and match the other select instances I spot-checked. Looks good to merge.

Also applies to: 112-118, 147-151, 172-176

apps/portal/src/components/Document/FeatureCard.tsx (1)

12-12: Rounded-xl update looks good.

The larger radius aligns with the new card styling direction.

apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)

43-67: Icon card spacing refinements LGTM.

The new layout brings the icon treatment and typography in line with the refreshed design system without changing behavior.

apps/portal/src/components/Document/NextPageButton.tsx (1)

8-11: Chevron-only layout works well.

The simplified link styling and ChevronRightIcon usage match the rest of the refreshed navigation affordances.

apps/portal/src/components/AI/chat-button.tsx (1)

30-31: Icon swap to BrainIcon looks good

Matches the repo’s “Icon”-suffix convention and keeps tree-shaking intact.

apps/portal/src/components/Document/Heading.tsx (1)

17-18: Typography updates look consistent

Heading weight/size tweaks are coherent with the new design system.

Also applies to: 36-37, 55-56, 74-75

apps/portal/src/app/references/components/TDoc/PageLayout.tsx (2)

330-333: Heading style tweak LGTM

The stronger section heading fits the updated typography.


338-370: Add rel="noopener noreferrer" to external links and reuse shared ArticleIconCard

  • Security: add rel={isExternal ? "noopener noreferrer" : undefined} whenever you use target="_blank" to prevent reverse tabnabbing.
  • DRY: remove this local ArticleIconCard and import the shared one from components/Document/Cards/ArticleCard.tsx.
-      target={isExternal ? "_blank" : undefined}
+      target={isExternal ? "_blank" : undefined}
+      rel={isExternal ? "noopener noreferrer" : undefined}
⛔ Skipped due to learnings
Learnt from: MananTank
PR: thirdweb-dev/js#7812
File: apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx:48-60
Timestamp: 2025-08-07T20:43:21.864Z
Learning: In the TokenBanner component at apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx, the Link components use target="_blank" with internal application routes (starting with "/") to open pages in new tabs within the same application. These internal links do not require rel="noopener noreferrer" security attributes, which are only needed for external URLs.
Learnt from: MananTank
PR: thirdweb-dev/js#7984
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/payments/components/FeatureCard.client.tsx:93-99
Timestamp: 2025-09-05T19:45:22.949Z
Learning: In the thirdweb dashboard project, rel="noopener noreferrer" attributes are not required for external links with target="_blank" in Link components, as confirmed by MananTank.
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.
apps/portal/src/components/others/DocSearch.tsx (1)

149-154: Styling/spacing tightening LGTM

Consistent with the broader UI pass; no functional changes observed.

Also applies to: 202-205, 224-252, 279-281, 379-385, 454-495

apps/portal/src/app/Header.tsx (1)

216-231: Header top-row restructure LGTM

Clearer layout with brand, controls split for xl vs mobile; matches the new design tokens.

apps/portal/src/app/layout.tsx (1)

3-4: Approve Geist font wiring Tailwind config (apps/portal/tailwind.config.ts lines 18–19) correctly maps font-sans to var(--font-geist-sans) and font-mono to var(--font-geist-mono).

Copy link
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: 1

Caution

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

⚠️ Outside diff range comments (3)
apps/portal/src/app/Header.tsx (2)

474-478: Harden external dropdown links

These dropdown items also open new tabs without rel="noopener noreferrer". Add the rel attribute when we detect an external URL.

Apply this diff to fix it:

                     <Link
                       className="before:absolute before:inset-0"
                       href={info.href}
                       prefetch={false}
-                      target={info.href.startsWith("http") ? "_blank" : ""}
+                      rel={
+                        info.href.startsWith("http") ? "noreferrer noopener" : undefined
+                      }
+                      target={info.href.startsWith("http") ? "_blank" : undefined}
                     >

536-539: Secure external NavLink targets

NavLink opens externals in a new tab but doesn’t set rel="noopener noreferrer". Please add it when href is off-site.

Apply this diff to fix it:

       href={props.href}
       onClick={props.onClick}
-      target={props.href.startsWith("http") ? "_blank" : ""}
+      rel={props.href.startsWith("http") ? "noreferrer noopener" : undefined}
+      target={props.href.startsWith("http") ? "_blank" : undefined}
apps/portal/src/components/others/PlatformSelector.tsx (1)

37-55: Avoid nested interactive elements in menu items; make Link the direct child of DropdownMenuItem.

Current structure nests a Next.js Link inside a clickable div (and uses a ::before overlay). This hurts accessibility (interactive-in-interactive) and can break keyboard highlight/selection. Use asChild with Link as the immediate child and style via data-[highlighted].

Apply this diff:

-        {connectLinks.map((platform) => {
+        {connectLinks.map((platform) => {
           return (
-            <DropdownMenuItem asChild key={platform.name}>
-              <div
-                className={clsx(
-                  "relative flex cursor-pointer font-medium text-foreground text-lg",
-                  "hover:bg-accent",
-                  props.selected === platform.name &&
-                    "bg-muted text-foreground",
-                )}
-              >
-                <div className="flex gap-2">
-                  <platform.icon className="size-4 text-foreground" />
-                  <Link
-                    className="before:absolute before:inset-0 text-sm"
-                    href={platform.href}
-                  >
-                    {platform.name}
-                  </Link>
-                </div>
-              </div>
-            </DropdownMenuItem>
+            <DropdownMenuItem asChild key={platform.name}>
+              <Link
+                href={platform.href}
+                className={clsx(
+                  "relative flex w-full items-center gap-2 rounded-md px-2 py-1.5 text-sm font-medium text-foreground outline-none",
+                  "hover:bg-accent focus:bg-accent data-[highlighted]:bg-accent",
+                  props.selected === platform.name && "bg-muted text-foreground",
+                )}
+              >
+                <platform.icon className="size-4 text-foreground" />
+                {platform.name}
+              </Link>
+            </DropdownMenuItem>
           );
         })}
🧹 Nitpick comments (3)
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)

338-369: Avoid re‑implementing ArticleIconCard locally

We now have two nearly identical ArticleIconCard implementations (here and in apps/portal/src/components/Document/Cards/ArticleCard.tsx). Any future tweak (padding, icon wrapper, aria attributes, etc.) will have to be applied in both spots, which is a maintenance trap. Can we pull this variant back into the shared component—perhaps via a variant="compact" prop or a small wrapper—or otherwise share the markup so we only have one source of truth?

apps/portal/src/components/Document/NextPageButton.tsx (1)

10-11: Drop the leading whitespace before the label

<span> {props.name}</span> renders an extra space before the text. Tighten it up so the typography stays crisp.

Apply this diff to fix it:

-      <span> {props.name}</span>
+      <span>{props.name}</span>
apps/portal/src/components/others/PlatformSelector.tsx (1)

16-16: Add an explicit return type to comply with TS guidelines.

Declare the component’s return type explicitly.

Apply this diff:

-export function PlatformSelector(props: { selected: Platform }) {
+export function PlatformSelector(props: { selected: Platform }): JSX.Element {
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

Disabled knowledge base sources:

  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between e8ae37d and 76b94eb.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (29)
  • apps/portal/package.json (1 hunks)
  • apps/portal/src/app/Header.tsx (2 hunks)
  • apps/portal/src/app/globals.css (1 hunks)
  • apps/portal/src/app/layout.tsx (2 hunks)
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx (2 hunks)
  • apps/portal/src/app/vault/page.mdx (1 hunks)
  • apps/portal/src/components/AI/chat-button.tsx (2 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx (0 hunks)
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx (4 hunks)
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Code.tsx (1 hunks)
  • apps/portal/src/components/Document/EditPage.tsx (1 hunks)
  • apps/portal/src/components/Document/FeatureCard.tsx (1 hunks)
  • apps/portal/src/components/Document/Heading.tsx (4 hunks)
  • apps/portal/src/components/Document/InlineCode.tsx (1 hunks)
  • apps/portal/src/components/Document/NextPageButton.tsx (1 hunks)
  • apps/portal/src/components/Document/PageFooter.tsx (1 hunks)
  • apps/portal/src/components/Document/Paragraph.tsx (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.module.css (1 hunks)
  • apps/portal/src/components/Document/Steps/Steps.tsx (1 hunks)
  • apps/portal/src/components/Layouts/DocLayout.tsx (1 hunks)
  • apps/portal/src/components/others/DocSearch.tsx (10 hunks)
  • apps/portal/src/components/others/Feedback.tsx (1 hunks)
  • apps/portal/src/components/others/PlatformSelector.tsx (2 hunks)
  • apps/portal/src/components/others/Sidebar.tsx (3 hunks)
  • apps/portal/src/components/others/Subscribe.tsx (1 hunks)
  • apps/portal/src/components/ui/Anchor.tsx (2 hunks)
  • apps/portal/tailwind.config.ts (1 hunks)
  • packages/ui/src/global.css (1 hunks)
💤 Files with no reviewable changes (1)
  • apps/portal/src/components/Document/APIEndpointMeta/ApiEndpoint.tsx
✅ Files skipped from review due to trivial changes (1)
  • apps/portal/src/components/others/Subscribe.tsx
🚧 Files skipped from review as they are similar to previous changes (17)
  • apps/portal/src/components/others/Sidebar.tsx
  • apps/portal/src/components/Document/InlineCode.tsx
  • apps/portal/src/components/others/DocSearch.tsx
  • apps/portal/src/components/Document/Paragraph.tsx
  • packages/ui/src/global.css
  • apps/portal/tailwind.config.ts
  • apps/portal/src/components/Document/Heading.tsx
  • apps/portal/src/components/Document/Steps/Steps.tsx
  • apps/portal/src/components/Document/APIEndpointMeta/RequestExample.tsx
  • apps/portal/src/components/Document/FeatureCard.tsx
  • apps/portal/src/components/Document/EditPage.tsx
  • apps/portal/src/components/Document/Code.tsx
  • apps/portal/src/components/Layouts/DocLayout.tsx
  • apps/portal/src/components/others/Feedback.tsx
  • apps/portal/src/components/Document/Steps/Steps.module.css
  • apps/portal/package.json
  • apps/portal/src/components/Document/PageFooter.tsx
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (CLAUDE.md)

**/*.{ts,tsx}: Write idiomatic TypeScript with explicit function declarations and return types
Limit each file to one stateless, single-responsibility function for clarity
Re-use shared types from @/types or local types.ts barrels
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Choose composition over inheritance; leverage utility types (Partial, Pick, etc.)
Comment only ambiguous logic; avoid restating TypeScript in prose

**/*.{ts,tsx}: Use explicit function declarations and explicit return types in TypeScript
Limit each file to one stateless, single‑responsibility function
Re‑use shared types from @/types where applicable
Prefer type aliases over interface except for nominal shapes
Avoid any and unknown unless unavoidable; narrow generics when possible
Prefer composition over inheritance; use utility types (Partial, Pick, etc.)
Lazy‑import optional features and avoid top‑level side‑effects to reduce bundle size

Files:

  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
**/*.{ts,tsx,js,jsx}

📄 CodeRabbit inference engine (CLAUDE.md)

Load heavy dependencies inside async paths to keep initial bundle lean (lazy loading)

Files:

  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/others/PlatformSelector.tsx
  • apps/portal/src/app/layout.tsx
  • apps/portal/src/app/Header.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
🧠 Learnings (11)
📚 Learning: 2025-07-07T21:21:47.488Z
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.

Applied to files:

  • apps/portal/src/components/Document/NextPageButton.tsx
  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-06-18T04:30:04.326Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.

Applied to files:

  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-06-18T04:27:16.172Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:27:16.172Z
Learning: Next.js Link component supports external URLs without throwing errors. When used with absolute URLs (like https://...), it behaves like a regular anchor tag without client-side routing, but does not cause runtime crashes or errors as previously believed.

Applied to files:

  • apps/portal/src/components/Document/Cards/ArticleCard.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-31T16:17:42.753Z
Learnt from: MananTank
PR: thirdweb-dev/js#7768
File: apps/playground-web/src/app/navLinks.ts:1-1
Timestamp: 2025-07-31T16:17:42.753Z
Learning: Configuration files that import and reference React components (like icon components from lucide-react) need the "use client" directive, even if they primarily export static data, because the referenced components need to be executed in a client context when used by other client components.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*client.tsx : Interactive UI that relies on hooks (`useState`, `useEffect`, React Query, wallet hooks).

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Icons come from `lucide-react` or the project-specific `…/icons` exports – never embed raw SVG.

Applied to files:

  • apps/portal/src/components/AI/chat-button.tsx
  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/*.{tsx,jsx} : Use `NavLink` (`@/components/ui/NavLink`) for internal navigation so active states are handled automatically.

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:19:55.613Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: CLAUDE.md:0-0
Timestamp: 2025-07-18T19:19:55.613Z
Learning: Applies to apps/{dashboard,playground-web}/**/*.{ts,tsx} : Use `NavLink` for internal navigation with automatic active states in dashboard and playground apps

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-08-29T15:37:38.513Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: AGENTS.md:0-0
Timestamp: 2025-08-29T15:37:38.513Z
Learning: Applies to apps/{dashboard,playground}/**/*.{ts,tsx} : Use `NavLink` for internal navigation to get active state handling

Applied to files:

  • apps/portal/src/components/ui/Anchor.tsx
📚 Learning: 2025-07-18T19:20:32.530Z
Learnt from: CR
PR: thirdweb-dev/js#0
File: .cursor/rules/dashboard.mdc:0-0
Timestamp: 2025-07-18T19:20:32.530Z
Learning: Applies to dashboard/**/layout.tsx : Building layout shells (`layout.tsx`) and top-level pages that mainly assemble data.

Applied to files:

  • apps/portal/src/app/references/components/TDoc/PageLayout.tsx
📚 Learning: 2025-05-29T00:46:09.063Z
Learnt from: jnsdls
PR: thirdweb-dev/js#7188
File: apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/accounts/components/accounts-count.tsx:15-15
Timestamp: 2025-05-29T00:46:09.063Z
Learning: In the accounts component at apps/dashboard/src/app/(app)/(dashboard)/(chain)/[chain_id]/[contractAddress]/accounts/components/accounts-count.tsx, the 3-column grid layout (md:grid-cols-3) is intentionally maintained even when rendering only one StatCard, as part of the design structure for this component.

Applied to files:

  • apps/portal/src/app/vault/page.mdx
🧬 Code graph analysis (4)
apps/portal/src/components/others/PlatformSelector.tsx (1)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
apps/portal/src/app/layout.tsx (1)
packages/ui/src/lib/utils.ts (1)
  • cn (4-6)
apps/portal/src/app/Header.tsx (3)
packages/thirdweb/src/react/web/ui/components/text.tsx (1)
  • Link (46-64)
apps/portal/src/components/others/DocSearch.tsx (1)
  • DocSearch (313-389)
apps/portal/src/components/AI/chat-button.tsx (1)
  • ChatButton (13-80)
apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)
apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)
  • ArticleIconCard (31-70)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (8)
  • GitHub Check: Unit Tests
  • GitHub Check: E2E Tests (pnpm, esbuild)
  • GitHub Check: E2E Tests (pnpm, webpack)
  • GitHub Check: E2E Tests (pnpm, vite)
  • GitHub Check: Size
  • GitHub Check: Lint Packages
  • GitHub Check: Build Packages
  • GitHub Check: Analyze (javascript)
🔇 Additional comments (9)
apps/portal/src/app/vault/page.mdx (1)

22-23: Vertical stack aligns with new spacing system

Switching from the responsive grid to a stacked layout with space-y-4 matches the updated spacing approach in this PR and keeps the cards evenly separated.

apps/portal/src/components/Document/Cards/ArticleCard.tsx (1)

43-66: Icon badge refresh aligns with the new card spec

The rounded pill around the icon plus the tightened typography/spacing reads much closer to the updated design tokens—looks good.

apps/portal/src/app/references/components/TDoc/PageLayout.tsx (1)

330-332: Detail heading weight is a nice hierarchy bump

The added font-medium gives those subgroup summaries a clearer visual step—good call.

apps/portal/src/components/ui/Anchor.tsx (1)

28-29: Icon swap LGTM

The hash glyph lines up nicely with the heading anchor affordance; no issues spotted.

apps/portal/src/components/AI/chat-button.tsx (1)

30-31: New icon choice looks good

The BrainIcon reads immediately as “Ask AI” and plugs straight into the existing layout. No concerns.

apps/portal/src/app/globals.css (1)

1-3: Ligatures tweak LGTM

Enabling liga globally meshes well with the new Geist typography—no concerns.

apps/portal/src/app/Header.tsx (1)

236-242: Add rel when opening external links in a new tab

Linking to GitHub with target="_blank" but no rel="noopener noreferrer" exposes us to reverse-tabnabbing. Please include the rel attributes.

Apply this diff to fix it:

               <Link
                 className="text-foreground"
                 href="https://github.com/thirdweb-dev"
-                target="_blank"
+                rel="noreferrer noopener"
+                target="_blank"
               >
⛔ Skipped due to learnings
Learnt from: MananTank
PR: thirdweb-dev/js#7984
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/payments/components/FeatureCard.client.tsx:93-99
Timestamp: 2025-09-05T19:45:22.949Z
Learning: In the thirdweb dashboard project, rel="noopener noreferrer" attributes are not required for external links with target="_blank" in Link components, as confirmed by MananTank.
Learnt from: MananTank
PR: thirdweb-dev/js#7812
File: apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx:48-60
Timestamp: 2025-08-07T20:43:21.864Z
Learning: In the TokenBanner component at apps/dashboard/src/app/(app)/(dashboard)/published-contract/components/token-banner.tsx, the Link components use target="_blank" with internal application routes (starting with "/") to open pages in new tabs within the same application. These internal links do not require rel="noopener noreferrer" security attributes, which are only needed for external URLs.
Learnt from: jnsdls
PR: thirdweb-dev/js#7365
File: apps/dashboard/src/app/(app)/team/[team_slug]/[project_slug]/(sidebar)/components/ProjectFTUX/ProjectFTUX.tsx:16-17
Timestamp: 2025-06-18T04:30:04.326Z
Learning: Next.js Link component fully supports both internal and external URLs and works appropriately with all standard anchor attributes including target="_blank", rel="noopener noreferrer", etc. Using Link for external URLs is completely appropriate and recommended.
Learnt from: saminacodes
PR: thirdweb-dev/js#7543
File: apps/portal/src/app/pay/page.mdx:4-4
Timestamp: 2025-07-07T21:21:47.488Z
Learning: In the thirdweb-dev/js repository, lucide-react icons must be imported with the "Icon" suffix (e.g., ExternalLinkIcon, RocketIcon) as required by the new linting rule, contrary to the typical lucide-react convention of importing without the suffix.
apps/portal/src/app/layout.tsx (1)

3-4: Geist font integration looks correct

Importing the pre-configured Geist font exports and wiring their variable classes into the body ensures Tailwind’s font-sans/font-mono mappings resolve properly. No issues spotted.

Also applies to: 26-26

apps/portal/src/components/others/PlatformSelector.tsx (1)

31-34: LGTM: Content sizing/offsets look good.

min-w and sideOffset align with the updated compact UI.

@graphite-app
Copy link
Contributor

graphite-app bot commented Sep 25, 2025

Merge activity

<!--

## title your PR with this format: "[SDK/Dashboard/Portal] Feature/Fix: Concise title for the changes"

If you did not copy the branch name from Linear, paste the issue tag here (format is TEAM-0000):

## Notes for the reviewer

Anything important to call out? Be sure to also clarify these in your comments.

## How to test

Unit tests, playground, etc.

-->

<!-- start pr-codex -->

---

## PR-Codex overview
This PR introduces several enhancements and styling updates across various components in the application, including adjustments to CSS, layout changes, and the addition of a new package, `geist`. It aims to improve the overall appearance and functionality of the portal.

### Detailed summary
- Added `font-feature-settings` to `globals.css`.
- Updated `text-rendering`, `-webkit-font-smoothing`, and `text-size-adjust` in `global.css`.
- Included `geist` package in `package.json`.
- Modified layout and spacing in `vault/page.mdx`.
- Adjusted classes for `ApiEndpoint.tsx`, `Paragraph.tsx`, and `InlineCode.tsx`.
- Changed text color in `Subscribe.tsx`.
- Revised spacing and border styles in various components.
- Updated icons in `Anchor.tsx` and `ChatButton.tsx`.
- Enhanced styling of buttons and links across multiple components.
- Improved overall layout structure in `Header.tsx` and sidebar components.
- Refined search modal styles and item presentation in `DocSearch.tsx`.

> ✨ Ask PR-Codex anything about this PR by commenting with `/codex {your question}`

<!-- end pr-codex -->

<!-- This is an auto-generated comment: release notes by coderabbit.ai -->
## Summary by CodeRabbit

- Style
  - Switched site typography to Geist, enabled ligatures and improved text rendering.
  - Redesigned header with central branding, consolidated controls, mobile menu and subtle backdrop.
  - Refreshed visuals across search, footer, sidebar, platform selector, steps, cards, code/inline code, and mobile sidebar.
  - Updated icons (chat, next-page, anchors), spacing/typography tweaks; vault features now stack vertically.

- Refactor
  - Localized an article card component and reorganized footer/next-page flows; Edit link now wrapped in a button.

- Chores
  - Added Geist dependency and extended Tailwind font settings; global font/rendering tweaks.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

packages Portal Involves changes to the Portal (docs) codebase.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants