Add a Feedback Widget to Your Web App in 2 Minutes
Your users find bugs you never will. They're staring at a broken layout on a device you don't own, on a network you can't replicate, in a state your tests never exercise. The feedback loop between "user sees bug" and "you fix it" is where products die.
Most feedback ends up in Slack. "hey the thing is broken" with no screenshot, no URL, no context. Or worse — it just doesn't get reported at all because submitting feedback is too much work.
We built @loupeink/web-sdk to make feedback zero-friction. A floating button in the corner of your app. Click it, annotate the screenshot, type a note, done. It appears instantly in your Loupe dashboard — with the URL, viewport, browser, and annotated screenshot already attached.
Here's how to add it.
Install
If you're using a bundler (Vite, webpack, anything modern):
npm install @loupeink/web-sdk Or if you want to drop it into an existing site without a build step:
<script src="https://cdn.jsdelivr.net/npm/@loupeink/web-sdk/dist/index.global.js"></script> Initialize
One call. That's it.
import { init } from '@loupeink/web-sdk';
init({
apiKey: 'lp_your_project_api_key',
});
Call init() once, early in your app boot — main.ts,
App.tsx, wherever your entry point is. The widget mounts to document.body
automatically. Shadow DOM isolation means it'll never conflict with your styles.
CDN version works the same way:
<script src="https://cdn.jsdelivr.net/npm/@loupeink/web-sdk/dist/index.global.js"></script>
<script>
Loupe.init({ apiKey: 'lp_your_project_api_key' });
</script> Place both tags before </body>.
Getting Your API Key
- Sign in at app.loupe.ink
- Go to Organization Settings → API Keys (top-right menu → Settings → API Keys tab)
- Select a project, optionally add a label, click Generate
- Copy the
lp_…key — it is shown only once - Pass it to
init({ apiKey: '...' })
Customize It
You can adjust position, color, and button label. All optional — defaults work fine for most apps.
init({
apiKey: 'lp_your_project_api_key',
position: 'bottom-left', // 'bottom-right' | 'bottom-left' | 'top-right' | 'top-left'
color: '#6366f1', // any CSS color
buttonLabel: 'Report a bug', // button text
}); Using It with React
Initialize once at the app root. If you're using StrictMode (which double-invokes effects),
clean up with destroy():
import { useEffect } from 'react';
import { init, destroy } from '@loupeink/web-sdk';
export function App() {
useEffect(() => {
init({ apiKey: import.meta.env.VITE_LOUPE_API_KEY });
return () => destroy();
}, []);
return <YourApp />;
}
Store your API key in .env as VITE_LOUPE_API_KEY — never commit it
directly.
What the Widget Actually Does
When a user clicks the feedback button:
- Screenshot capture — captures the visible viewport using
html2canvas. No browser extension, no screen share permission. - Annotation overlay — user can draw, circle, highlight, or blur regions on the screenshot before submitting.
- Context capture — the current URL, page title, viewport size, and user agent are attached automatically.
- Submit — everything POSTs to the Loupe Edge Function, authenticated with your API key. Feedback appears in your dashboard immediately.
Every submission includes the annotated screenshot, the user's comment, a severity level (critical / major / minor / suggestion), and the page context. No configuration needed — that's the default behavior.
Self-Hosting or Custom Endpoints
If you're running a self-hosted Loupe instance or want to route feedback through your own
backend, pass the endpoint option:
init({
apiKey: 'lp_your_key',
endpoint: 'https://your-own-server.com/feedback',
});
Your endpoint will receive a JSON body with apiKey, comment,
severity, screenshotDataUrl (base64 PNG), and a context
object.
Cleanup
If you need to unmount the widget (SPA route changes, test teardown, etc.), call
destroy():
import { destroy } from '@loupeink/web-sdk';
destroy(); // removes the widget from the DOM That's It
Two minutes from npm install to a working feedback widget in your app. Feedback
lands in Loupe with screenshot, URL, and context — ready to triage, link to a Linear issue, or
forward to GitHub.
If you're building something and want to close the feedback loop between your users and your team, this is the fastest way to get started.
Full SDK source is on GitHub. Issues and PRs welcome.
Try Loupe free for 14 days
Download Loupe and start giving frame-precise feedback today. No credit card required.
Download Free Trial