Cobbl

Script Tag

Add the feedback widget to any HTML page with a simple script tag

The script tag integration is perfect for static sites, WordPress, Webflow, or any HTML page where you can add a script.

Basic Usage

Add the widget container and script to your HTML:

<!DOCTYPE html>
<html>
  <body>
    <h1>AI Response</h1>
    <p>Your AI-generated content here...</p>

    <!-- Widget container with configuration -->
    <div id="cobbl-feedback-widget" data-run-id="your-run-id"></div>

    <!-- Load the widget script -->
    <script src="https://cdn.jsdelivr.net/npm/@cobbl-ai/feedback-widget"></script>
  </body>
</html>

CDN

<script src="https://cdn.jsdelivr.net/npm/@cobbl-ai/feedback-widget"></script>

Data Attributes

Configure the widget using data attributes on the container element:

AttributeTypeRequiredDefaultDescription
data-run-idstringYesRun ID from prompt execution
data-variant'trigger' | 'thumbs' | 'inline'No'trigger'Display variant
data-positionWidgetPositionNo'bottom-right'Flyout position
data-trigger-button-textstringNo'Give Feedback'Trigger button text
data-color-scheme'auto' | 'light' | 'dark'No'auto'Color scheme mode

Display Variants

Trigger Variant (Default)

A text button that opens the feedback flyout when clicked:

<div
  id="cobbl-feedback-widget"
  data-run-id="your-run-id"
  data-variant="trigger"
  data-trigger-button-text="Rate this response"
></div>

Thumbs Variant

Thumbs up/down buttons that immediately register feedback and open the flyout:

<div
  id="cobbl-feedback-widget"
  data-run-id="your-run-id"
  data-variant="thumbs"
></div>

Inline Variant

Full feedback form rendered directly without any flyout:

<div
  id="cobbl-feedback-widget"
  data-run-id="your-run-id"
  data-variant="inline"
></div>

Flyout Positioning

Control where the flyout appears relative to the trigger:

<!-- Bottom right (default) -->
<div
  id="cobbl-feedback-widget"
  data-run-id="..."
  data-position="bottom-right"
></div>

<!-- Top center -->
<div id="cobbl-feedback-widget" data-run-id="..." data-position="top"></div>

<!-- Left side -->
<div id="cobbl-feedback-widget" data-run-id="..." data-position="left"></div>

Available positions:

  • top-left, top, top-right
  • left, right
  • bottom-left, bottom, bottom-right

Dynamic Content

The widget uses a MutationObserver to automatically mount when containers are added dynamically:

<script src="https://cdn.jsdelivr.net/npm/@cobbl-ai/feedback-widget"></script>

<script>
  // Add widget after page load — it auto-mounts!
  const widget = document.createElement('div')
  widget.id = 'cobbl-feedback-widget'
  widget.setAttribute('data-run-id', 'new-run-id')
  document.body.appendChild(widget)
</script>

Color Scheme

Control the widget's color scheme with data-color-scheme:

<!-- Auto (default) - follows system preference -->
<div
  id="cobbl-feedback-widget"
  data-run-id="..."
  data-color-scheme="auto"
></div>

<!-- Force light theme -->
<div
  id="cobbl-feedback-widget"
  data-run-id="..."
  data-color-scheme="light"
></div>

<!-- Force dark theme -->
<div
  id="cobbl-feedback-widget"
  data-run-id="..."
  data-color-scheme="dark"
></div>

See Styling for customizing colors per scheme.

Dynamic Configuration Updates

Change data attributes at runtime — the widget updates automatically:

const widget = document.getElementById('cobbl-feedback-widget')

// Update the run ID
widget.setAttribute('data-run-id', 'new-run-id')

// Change the trigger button text
widget.setAttribute('data-trigger-button-text', 'Updated Text')

// Switch to thumbs variant
widget.setAttribute('data-variant', 'thumbs')

// Switch to dark mode
widget.setAttribute('data-color-scheme', 'dark')

// The MutationObserver detects changes and updates the widget

Using the Global API

When loaded via script tag, the widget exposes a global cobblWidget object for programmatic control:

<script src="https://cdn.jsdelivr.net/npm/@cobbl-ai/feedback-widget"></script>

<script>
  // Create a widget programmatically
  const widget = window.cobblWidget.create({
    runId: 'your-run-id',
    variant: 'thumbs',
  })

  // Mount to a custom container
  widget.mount('#my-container')

  // Update configuration
  widget.update({ runId: 'new-run-id' })

  // Get current config
  console.log(widget.getConfig())

  // Clean up
  widget.destroy()
</script>

Server-Side Rendering

For server-rendered pages where the run ID comes from the server:

<!-- PHP example -->
<div id="cobbl-feedback-widget" data-run-id="<?php echo $runId; ?>"></div>

<!-- Jinja/Django example -->
<div id="cobbl-feedback-widget" data-run-id="{{ run_id }}"></div>

<!-- ERB example -->
<div id="cobbl-feedback-widget" data-run-id="<%= @run_id %>"></div>

Styling

Customize the widget appearance using CSS variables on the container:

<style>
  #cobbl-feedback-widget {
    /* Primary color */
    --cobbl-primary: #0ea5e9;
    --cobbl-primary-hover: #0284c7;

    /* Custom trigger styling */
    --cobbl-trigger-color: #6b7280;
    --cobbl-trigger-font-size: 14px;

    /* Flyout dimensions */
    --cobbl-flyout-width: 400px;
  }
</style>

<div id="cobbl-feedback-widget" data-run-id="your-run-id"></div>

See Styling for the complete list of CSS variables.

Complete Example

<!DOCTYPE html>
<html>
  <head>
    <title>AI Chat</title>
    <style>
      .response {
        padding: 20px;
        background: #f9fafb;
        border-radius: 8px;
        margin: 20px 0;
      }

      .response-footer {
        margin-top: 12px;
        text-align: right;
      }

      #cobbl-feedback-widget {
        --cobbl-primary: #6366f1;
        --cobbl-trigger-text-decoration: none;
        --cobbl-trigger-font-size: 13px;
      }
    </style>
  </head>
  <body>
    <h1>AI Assistant</h1>

    <div class="response">
      <p>Here's your AI-generated response...</p>

      <div class="response-footer">
        <div
          id="cobbl-feedback-widget"
          data-run-id="run_abc123"
          data-trigger-button-text="Was this helpful?"
          data-position="top-right"
        ></div>
      </div>
    </div>

    <script src="https://cdn.jsdelivr.net/npm/@cobbl-ai/feedback-widget"></script>
  </body>
</html>

Next Steps

On this page