SDK & Frameworks

Feedback Widget — React

Add the FutureBase feedback widget to any React or Next.js application using the @futurebase/feedback package.

Installation

npm install @futurebase/feedback

Quick start

Wrap your app with FeedbackProvider

Import FeedbackProvider from @futurebase/feedback/react and wrap your application. Pass your feedback board slug as the slug prop — you can find it in your FutureBase dashboard under Feedback > Settings.

import { FeedbackProvider } from "@futurebase/feedback/react";

function App() {
  return (
    <FeedbackProvider slug="your-board-slug">
      {/* your app */}
    </FeedbackProvider>
  );
}

Add the FeedbackBubble component

Place FeedbackBubble anywhere inside the provider. It renders a floating feedback button.

import { FeedbackProvider, FeedbackBubble } from "@futurebase/feedback/react";

function App() {
  return (
    <FeedbackProvider slug="your-board-slug">
      <Main />
      <FeedbackBubble />
    </FeedbackProvider>
  );
}

Components

FeedbackProvider

Provides the feedback context to all child components. Must wrap any feedback component.

PropTypeRequiredDescription
slugstringYesYour feedback board slug.
themeFeedbackThemeNoGlobal theme overrides (see Theming).
childrenReactNodeYesChild components to render inside the provider.

FeedbackBubble

A floating button that opens a feedback form popup when clicked.

PropTypeDefaultDescription
positionFeedbackPosition"bottom-right"Screen corner where the bubble appears.
fieldsFeedbackField[]["stars", "text"]Which fields to show in the form.
themeFeedbackThemeTheme overrides for this instance.
labelsFeedbackLabelsCustom label strings.
contextRecord<string, unknown>Additional context metadata sent with each submission.
iconReactNodeCustom icon for the bubble button.
onSubmitSuccess(data: FeedbackData) => voidCalled after successful submission.
onSubmitError(error: Error) => voidCalled if submission fails.

InlineFeedback

An inline feedback form that renders directly in your page content (no floating button).

PropTypeDefaultDescription
fieldsFeedbackField[]["stars", "text"]Which fields to show.
themeFeedbackThemeTheme overrides.
labelsFeedbackLabelsCustom label strings.
contextRecord<string, unknown>Additional context metadata.
compactbooleanfalseUse a more compact layout.
onSubmitSuccess(data: FeedbackData) => voidCalled after successful submission.
onSubmitError(error: Error) => voidCalled if submission fails.
import { FeedbackProvider, InlineFeedback } from "@futurebase/feedback/react";

function HelpPage() {
  return (
    <FeedbackProvider slug="your-board-slug">
      <h2>Was this helpful?</h2>
      <InlineFeedback fields={["stars"]} />
    </FeedbackProvider>
  );
}

FeedbackWrapper

Wraps any element and adds a contextual feedback trigger that appears on hover. Useful for collecting feedback on specific UI components.

PropTypeRequiredDescription
idstringYesA unique identifier for this feedback location. Sent as locationId in the context.
childrenReactNodeYesThe element to wrap.
positionFeedbackPosition"top-right"Position of the feedback trigger relative to the wrapped element.
fieldsFeedbackField[]NoWhich fields to show.
themeFeedbackThemeNoTheme overrides.
labelsFeedbackLabelsNoCustom label strings.
contextRecord<string, unknown>NoAdditional context metadata.
classNamestringNoAdditional CSS class for the wrapper element.
onSubmitSuccess(data: FeedbackData) => voidNoCalled after successful submission.
onSubmitError(error: Error) => voidNoCalled if submission fails.

Compound API

For full control over the feedback form layout, use the compound components:

import {
  FeedbackProvider,
  Feedback,
  FeedbackLabel,
  FeedbackStars,
  FeedbackText,
  FeedbackSubmit,
} from "@futurebase/feedback/react";

function CustomFeedback() {
  return (
    <FeedbackProvider slug="your-board-slug">
      <Feedback id="custom-form">
        <FeedbackLabel>How was your experience?</FeedbackLabel>
        <FeedbackStars />
        <FeedbackText placeholder="Tell us more..." rows={4} />
        <FeedbackSubmit label="Submit" submittingLabel="Submitting..." />
      </Feedback>
    </FeedbackProvider>
  );
}

Feedback (root)

PropTypeRequiredDescription
idstringYesA unique identifier for this feedback form.
childrenReactNodeYesCompound child components.
contextRecord<string, unknown>NoAdditional context metadata.
themeFeedbackThemeNoTheme overrides.
successMessagestringNoMessage shown after successful submission (default: "Thank you for your feedback!").
onSubmitSuccess(data: FeedbackData) => voidNoCalled after successful submission.
onSubmitError(error: Error) => voidNoCalled if submission fails.

FeedbackLabel

Renders a heading for the feedback form. Accepts children (ReactNode).

FeedbackStars

Renders an interactive star rating input. No props required — if no FeedbackSubmit is present, selecting a star auto-submits the form.

FeedbackText

PropTypeDefaultDescription
placeholderstring"Tell us what you think..."Placeholder text for the textarea.
rowsnumber3Number of visible text rows.

FeedbackSubmit

PropTypeDefaultDescription
labelstring"Send feedback"Button text.
submittingLabelstring"Sending..."Button text while submitting.

StarRating

A standalone star rating input component. Use it when you need a star rating outside of the feedback form context.

PropTypeDefaultDescription
valuenumberCurrent selected value (required).
onChange(value: number) => voidCalled when a star is clicked (required).
maxnumber5Maximum number of stars.
import { StarRating } from "@futurebase/feedback/react";

function MyRating() {
  const [rating, setRating] = useState(0);
  return <StarRating value={rating} onChange={setRating} />;
}

useFeedback() hook

Access the feedback context programmatically from any component inside FeedbackProvider:

import { useFeedback } from "@futurebase/feedback/react";

function MyComponent() {
  const { slug, boardInfo, loading, submitFeedback, theme } = useFeedback();

  const handleCustomSubmit = async () => {
    await submitFeedback(
      { rating: 5, text: "Great product!" },
      { page: "/pricing" }
    );
  };

  return <button onClick={handleCustomSubmit}>Rate us 5 stars</button>;
}

Return value

PropertyTypeDescription
slugstringThe feedback board slug.
boardInfoBoardInfoOutput | nullBoard metadata from the server.
loadingbooleanWhether the initial board info is still loading.
submitFeedback(data: FeedbackData, context?: Record<string, unknown>) => Promise<{ feedbackId: string }>Submit feedback programmatically.
themeFeedbackThemeThe resolved theme (merged from provider props and board settings).

Theming

Customize the look of the feedback widget by passing a FeedbackTheme object to FeedbackProvider or to individual components:

<FeedbackProvider
  slug="your-board-slug"
  theme={{
    primaryColor: "#6366f1",
    backgroundColor: "#ffffff",
    textColor: "#1f2937",
    borderColor: "#e5e7eb",
    borderRadius: "8px",
    fontFamily: "Inter, sans-serif",
  }}
>

FeedbackTheme

PropertyTypeDescription
primaryColorstringAccent color for buttons, stars, and interactive elements.
backgroundColorstringBackground color of the feedback form.
textColorstringText color.
borderColorstringBorder color for inputs and the form container.
borderRadiusstringBorder radius for the form and inputs.
fontFamilystringFont family for all text in the widget.

Dark mode

The widget automatically adapts to dark mode if your page uses a .dark class on the <html> or <body> element, or a [data-theme="dark"] attribute. No additional configuration is needed.

Types reference

FeedbackField

type FeedbackField = "stars" | "text";

FeedbackPosition

type FeedbackPosition = "bottom-right" | "bottom-left" | "top-right" | "top-left";

FeedbackLabels

type FeedbackLabels = {
  title?: string;
  placeholder?: string;
  submit?: string;
  success?: string;
};

FeedbackData

type FeedbackData = {
  rating?: number;
  text?: string;
};

Usage with Next.js

All components exported from @futurebase/feedback/react are client components — the "use client" directive is already included in the package exports. In a Next.js App Router project, import them normally with no extra setup:

app/layout.tsx
import { FeedbackProvider, FeedbackBubble } from "@futurebase/feedback/react";

export default function RootLayout({ children }: { children: React.ReactNode }) {
  return (
    <html lang="en">
      <body>
        <FeedbackProvider slug="your-board-slug">
          {children}
          <FeedbackBubble />
        </FeedbackProvider>
      </body>
    </html>
  );
}

On this page