-
Notifications
You must be signed in to change notification settings - Fork 477
[Dashboard][UI][storeDescription] #972
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: dev
Are you sure you want to change the base?
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
WalkthroughReplaced empty or missing Changes
Sequence Diagram(s)sequenceDiagram
participant Store as ALL_APPS_FRONTEND
participant AppEntry as AppStoreEntry (render)
rect rgba(55,126,184,0.06)
note right of Store: storeDescription values updated to JSX fragments\nfor many app entries
end
AppEntry->>Store: read appFrontend.storeDescription
alt storeDescription present
AppEntry->>AppEntry: render JSX fragment (3 paragraphs)
else storeDescription absent
AppEntry->>AppEntry: render nothing (no fallback)
Note right of AppEntry: previously rendered fallback paragraph\n"No additional information available."
end
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes
Possibly related PRs
Poem
Pre-merge checks and finishing touches❌ Failed checks (2 warnings, 1 inconclusive)
✨ Finishing touches
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Greptile Overview
Summary
Replaced empty storeDescription fields with descriptive JSX content for 11 dashboard apps (authentication, teams, rbac, api-keys, payments, emails, email-api, data-vault, workflows, webhooks, launch-checklist).
- Each description contains 3 concise paragraphs explaining the app's purpose, key features, and value
- Proper HTML entity escaping used (
'for apostrophes) - Consistent JSX fragment structure with
<p>tags - No functional changes or security implications
Confidence Score: 5/5
- This PR is safe to merge with no risk - it only adds descriptive UI content
- Score reflects that changes are purely content additions with no logic, security, or functional modifications. All JSX is properly structured with correct HTML entity escaping
- No files require special attention
Important Files Changed
File Analysis
| Filename | Score | Overview |
|---|---|---|
| apps/dashboard/src/lib/apps-frontend.tsx | 5/5 | Added descriptive store descriptions for 11 apps (authentication, teams, rbac, api-keys, payments, emails, email-api, data-vault, workflows, webhooks, launch-checklist) - all changes are purely content additions with proper JSX structure and HTML entity escaping |
Sequence Diagram
sequenceDiagram
participant User
participant AppStoreEntry
participant ALL_APPS_FRONTEND
participant DOM
User->>AppStoreEntry: Views app in store
AppStoreEntry->>ALL_APPS_FRONTEND: Retrieves appFrontend[appId]
ALL_APPS_FRONTEND-->>AppStoreEntry: Returns app config with storeDescription
AppStoreEntry->>DOM: Renders storeDescription JSX
DOM-->>User: Displays app description with <p> tags
1 file reviewed, no comments
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 2
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/src/lib/apps-frontend.tsx(11 hunks)
🧰 Additional context used
📓 Path-based instructions (3)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Use ES6 Maps instead of Records wherever possible in TypeScript code
Files:
apps/dashboard/src/lib/apps-frontend.tsx
apps/{dashboard,dev-launchpad}/**/*.{tsx,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
For blocking alerts and errors in the UI, never use toast; use alerts instead
Files:
apps/dashboard/src/lib/apps-frontend.tsx
apps/{dashboard,dev-launchpad}/**/*.{css,tsx,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
Animations: keep hover/click transitions snappy; do not delay actions with pre-hover transitions; apply transitions after the action (e.g., fade-out on hover end)
Files:
apps/dashboard/src/lib/apps-frontend.tsx
⏰ 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). (11)
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: lint_and_build (latest)
- GitHub Check: all-good
- GitHub Check: build (22.x)
- GitHub Check: build (22.x)
- GitHub Check: setup-tests
- GitHub Check: docker
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: restart-dev-and-test
- GitHub Check: Security Check
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (4)
apps/dashboard/src/components/app-store-entry.tsx (4)
56-60: Use a stable key for screenshot items.Index keys can cause unnecessary re-renders on reordering. Prefer the URL as a stable key.
- {appFrontend.screenshots.map((screenshot: string, index: number) => ( + {appFrontend.screenshots.map((screenshot: string, index: number) => ( <div - key={index} + key={screenshot} className="relative h-48 w-72 rounded-lg shadow-md flex-shrink-0 overflow-hidden" >
8-8: TypetitleComponentas React.ElementType for broader compatibility.
ElementTypecleanly supports intrinsic tags and components without the union.-import { FunctionComponent } from "react"; +import type { ElementType } from "react"; @@ onEnable: () => Promise<void>, - titleComponent?: FunctionComponent<any> | string, + titleComponent?: ElementType, }) {Also applies to: 14-18
38-44: Guard against double-clicks; surface pending state.
onEnableis async; disable the button while pending to prevent duplicate enables and addaria-busyfor a11y.- <Button - onClick={onEnable} - size="lg" - className="px-8" - > + <Button + onClick={onEnable} + size="lg" + className="px-8" + aria-busy={false /* wire up if you add pending state */} + /* disabled={pending} */ + >Tip: Use React 19’s
useTransitionor a simpleuseStateto trackpending, and setdisabled/aria-busyaccordingly.
80-89: Alpha/Beta notices: consider an Alert component/roles for accessibility.If these are “blocking” notices, render via an Alert (role=alert/aria-live) instead of styled paragraphs for better semantics.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/src/components/app-store-entry.tsx(1 hunks)
🧰 Additional context used
📓 Path-based instructions (3)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Use ES6 Maps instead of Records wherever possible in TypeScript code
Files:
apps/dashboard/src/components/app-store-entry.tsx
apps/{dashboard,dev-launchpad}/**/*.{tsx,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
For blocking alerts and errors in the UI, never use toast; use alerts instead
Files:
apps/dashboard/src/components/app-store-entry.tsx
apps/{dashboard,dev-launchpad}/**/*.{css,tsx,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
Animations: keep hover/click transitions snappy; do not delay actions with pre-hover transitions; apply transitions after the action (e.g., fade-out on hover end)
Files:
apps/dashboard/src/components/app-store-entry.tsx
⏰ 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). (12)
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: all-good
- GitHub Check: Vercel Agent Review
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: lint_and_build (latest)
- GitHub Check: restart-dev-and-test
- GitHub Check: build (22.x)
- GitHub Check: build (22.x)
- GitHub Check: docker
- GitHub Check: setup-tests
- GitHub Check: build (22.x)
- GitHub Check: Security Check
🔇 Additional comments (1)
apps/dashboard/src/components/app-store-entry.tsx (1)
90-90: Confirm behavior change for empty descriptionsDirectly rendering
appFrontend.storeDescriptionmeans the apps “tv-mode”, “catalyst”, “neon”, and “convex” will now show no description. Ensure this is intended or add an accessible placeholder (e.g., visually hidden text) for screen readers.
| </p> | ||
| )} | ||
| {appFrontend.storeDescription || <p>No additional information available.</p>} | ||
| {appFrontend.storeDescription} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fallback text removed without ensuring all apps have descriptions. Several apps (tv-mode, catalyst, neon, convex) still have empty descriptions, resulting in blank UI sections instead of the previous "No additional information available" message.
View Details
📝 Patch Details
diff --git a/apps/dashboard/src/components/app-store-entry.tsx b/apps/dashboard/src/components/app-store-entry.tsx
index 6fb95a90..20e3b3f5 100644
--- a/apps/dashboard/src/components/app-store-entry.tsx
+++ b/apps/dashboard/src/components/app-store-entry.tsx
@@ -5,7 +5,22 @@ import { ALL_APPS_FRONTEND } from "@/lib/apps-frontend";
import { ALL_APPS, ALL_APP_TAGS, AppId } from "@stackframe/stack-shared/dist/apps/apps-config";
import { Badge, Button, ScrollArea } from "@stackframe/stack-ui";
import Image from "next/image";
-import { FunctionComponent } from "react";
+import React, { FunctionComponent } from "react";
+
+function isEmptyReactContent(element: React.ReactNode): boolean {
+ // Null, undefined, or empty string
+ if (!element || element === '') return true;
+
+ // React Fragment with no children or empty children
+ if (typeof element === 'object' && 'type' in element && element.type === React.Fragment) {
+ const children = (element.props as any)?.children;
+ if (!children) return true;
+ if (Array.isArray(children) && children.length === 0) return true;
+ if (children === '' || children === null || children === undefined) return true;
+ }
+
+ return false;
+}
export function AppStoreEntry({
appId,
@@ -87,7 +102,9 @@ export function AppStoreEntry({
IMPORTANT: This app is in beta. You may still experience some bugs and issues.
</p>
)}
- {appFrontend.storeDescription}
+ {isEmptyReactContent(appFrontend.storeDescription)
+ ? <p>No additional information available.</p>
+ : appFrontend.storeDescription}
</div>
</ScrollArea>
</div>
Analysis
Empty app descriptions render as blank UI sections instead of fallback text
What fails: AppStoreEntry component in apps/dashboard/src/components/app-store-entry.tsx shows empty sections for apps with empty storeDescription fragments, instead of helpful fallback text
How to reproduce:
- Navigate to app store entries for tv-mode, catalyst, neon, or convex apps
- Observe the description section in the UI
- See completely blank section where description should appear
Result: Empty <div class="prose dark:prose-invert max-w-none"></div> renders, providing no information to users
Expected: Should display "No additional information available." message for apps without descriptions, as originally intended by the fallback code that was removed in commit c460b0d7
Root cause: Apps with storeDescription: <></> (empty React fragments) in apps-frontend.tsx render as empty content, and the recent "fix lint" commit removed the fallback logic without addressing the underlying issue that React elements are always truthy, making || fallback logic ineffective
There was a problem hiding this 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
♻️ Duplicate comments (2)
apps/dashboard/src/lib/apps-frontend.tsx (2)
203-209: Remove extraneous comma in Workflows sentence.
Keeps the sentence smooth.- <p>Duplication, and toggles live in the dashboard so iteration stays fast.</p> + <p>Duplication and toggles live in the dashboard so iteration stays fast.</p>
218-224: Clarify Webhooks phrasing.
Fix “users and teams events” → smoother wording.- <p>Webhooks are used to sync users and teams events from Stack to your own servers.</p> + <p>Webhooks keep user and team events in sync between Stack and your own servers.</p>
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/src/lib/apps-frontend.tsx(11 hunks)
🧰 Additional context used
📓 Path-based instructions (3)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Use ES6 Maps instead of Records wherever possible in TypeScript code
Files:
apps/dashboard/src/lib/apps-frontend.tsx
apps/{dashboard,dev-launchpad}/**/*.{tsx,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
For blocking alerts and errors in the UI, never use toast; use alerts instead
Files:
apps/dashboard/src/lib/apps-frontend.tsx
apps/{dashboard,dev-launchpad}/**/*.{css,tsx,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
Animations: keep hover/click transitions snappy; do not delay actions with pre-hover transitions; apply transitions after the action (e.g., fade-out on hover end)
Files:
apps/dashboard/src/lib/apps-frontend.tsx
⏰ 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). (12)
- GitHub Check: Vercel Agent Review
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: build (22.x)
- GitHub Check: all-good
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test
- GitHub Check: lint_and_build (latest)
- GitHub Check: setup-tests
- GitHub Check: docker
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: Security Check
🔇 Additional comments (8)
apps/dashboard/src/lib/apps-frontend.tsx (8)
76-82: Authentication copy—LGTM.
Clear, concise, on-brand.
92-98: Teams copy—LGTM.
Reads well and sets expectations.
108-114: RBAC copy—LGTM.
Accurate and developer-friendly.
140-146: Payments copy—LGTM.
Covers core tasks without fluff.
158-164: Emails copy—LGTM.
Good clarity and flow.
173-179: Email API copy—LGTM.
Clear value prop.
188-194: Data Vault copy—LGTM.
Accurate and security-minded.
242-248: Launch Checklist copy—LGTM.
Crisp and informative.
| storeDescription: ( | ||
| <> | ||
| <p>API Keys keeps every environment credentialized without sacrificing control.</p> | ||
| <p>Issue publishable client keys or secret server keys with configurable expirations and copy the values before they disappear.</p> | ||
| <p>When a credential is no longer trusted, revoke or rotate it instantly from the dashboard.</p> | ||
| </> | ||
| ), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Word choice: “credentialized” → “credentialed”.
Simpler, more common phrasing.
- <p>API Keys keeps every environment credentialized without sacrificing control.</p>
+ <p>API Keys keeps every environment credentialed without sacrificing control.</p>🤖 Prompt for AI Agents
In apps/dashboard/src/lib/apps-frontend.tsx around lines 123 to 129, replace the
uncommon word "credentialized" with the simpler, more common "credentialed" in
the storeDescription JSX paragraph; update the text so it reads "API Keys keeps
every environment credentialed without sacrificing control." and leave the rest
unchanged.
Summary by CodeRabbit