Installation

Installing the widget takes one snippet. Paste it near the end of your page, just before the closing </body> tag:

<script>
  window.uj ||= new Proxy({}, { get: (_, p) => p == 'then' ? 0 : (...a) => { (window.$ujq ||= []).push([p, ...a]) } });
  uj.init('YOUR_PROJECT_ID');
</script>
<script type="module" async src="https://cdn.userjot.com/sdk/v3/uj.js"></script>

Replace YOUR_PROJECT_ID with the project ID from your UserJot dashboard.

That is the whole install. The launcher appears in the bottom right corner of your page.

The first script sets up window.uj and queues any calls you make. The second script loads the SDK, which then replays those calls. This means you never have to wait for the SDK to load before calling it.

Call order does not matter

You can call init, identify, and open on the same tick, in any order relative to the SDK loading. The SDK queues everything and runs it once ready.

<script>
  window.uj ||= new Proxy({}, { get: (_, p) => p == 'then' ? 0 : (...a) => { (window.$ujq ||= []).push([p, ...a]) } });
  uj.init('YOUR_PROJECT_ID');
  uj.identify({ user: { id: 'user-123', email: 'user@example.com' } });
</script>
<script type="module" async src="https://cdn.userjot.com/sdk/v3/uj.js"></script>

No inline scripts (strict CSP)

If your site does not allow inline scripts, use the single-tag install instead. Put your project ID in the data-project attribute and the SDK initializes itself:

<script type="module" async src="https://cdn.userjot.com/sdk/v3/uj.js" data-project="YOUR_PROJECT_ID"></script>

With this variant you can still call window.uj methods from your own scripts after the SDK loads. If you also call uj.init(...) yourself, your call wins and the attribute is ignored.

Configuration

Pass options as the second argument to init:

uj.init('YOUR_PROJECT_ID', {
  widget: {
    position: 'right', // 'left' or 'right'
    theme: 'auto',     // 'auto', 'light', or 'dark'
    launcher: true     // false hides the default button
  },
  locale: 'en-US'      // optional, defaults to your workspace language settings
});

Everything is optional. uj.init('YOUR_PROJECT_ID') with no options shows the default launcher on the right with automatic theming.

Set launcher: false when you want to open the widget from your own button instead of the default one. See Controlling the widget for a full example.

Verify the install

After loading the page:

  1. The launcher button appears on your page.
  2. Clicking it opens the widget.
  3. You can move between feedback, roadmap, and updates inside the widget.

If your workspace has Conversations enabled, the Messages surface appears in the widget as well, with no extra installation.

Common issues

The widget does not appear

Check these first:

  • Both script tags are on the page, or the single tag with data-project.
  • The project ID is correct.
  • You did not pass widget: false or launcher: false in the init options.

Calls seem to do nothing

If you call uj.open() or uj.identify(...) and nothing happens, make sure uj.init(...) runs somewhere on the page. Calls made before init wait until init happens. The SDK logs a warning in the console if calls are pending and init never ran.

Next step

Tie the widget to your signed-in users with Identify users.