> ## Documentation Index
> Fetch the complete documentation index at: https://docs.usertick.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Install with npm

> Install the @usertick/snippet package and initialize it in React, Next.js, Vue, Nuxt, Angular, Svelte, Astro, Remix, Gatsby or any app with a bundler.

The `@usertick/snippet` package runs the same widget as the script tag, started from your app's code instead of a tag in the page. Both follow client-side route changes, so a survey targeted at `/pricing` also opens after the app navigates to `/pricing`.

## Install the package

```bash npm theme={null}
npm install @usertick/snippet
```

```bash yarn theme={null}
yarn add @usertick/snippet
```

```bash pnpm theme={null}
pnpm add @usertick/snippet
```

```bash bun theme={null}
bun add @usertick/snippet
```

## Initialize the widget

Call `init` once when the app starts, with the site ID from **Settings → Sites** (the file name in the site's install code):

```ts theme={null}
import Usertick from "@usertick/snippet";

Usertick.init({ site_id: "YOUR_SITE_ID" });
```

`init` loads the site's code file from `cdn.usertick.com`, which carries the site's live surveys, so nothing else needs to be configured. When that file can't be loaded, the package uses the copy it saved in the browser during the last 24 hours and keeps trying in the background.

> [!NOTE]
>
> **Check now** in **Settings → Sites** looks for the script tag in the HTML of the home page, so it can't see a package that loads from JavaScript. To connect the site, also add the script tag to the home page. The tag and the package share one widget on the page. See [Check the install](https://docs.usertick.com/installation/website.md#check-the-install).

## Framework examples

```tsx React theme={null}
// App.tsx: initialize once on mount
import { useEffect } from "react";
import Usertick from "@usertick/snippet";

export default function App() {
  useEffect(() => {
    Usertick.init({ site_id: "YOUR_SITE_ID" });
    return () => Usertick.destroy();
  }, []);

  return <main>{/* your app */}</main>;
}
```

```tsx Next.js theme={null}
// app/usertick.tsx: a client component rendered once in app/layout.tsx
"use client";
import { useEffect } from "react";
import Usertick from "@usertick/snippet";

export function UsertickInit() {
  useEffect(() => {
    Usertick.init({ site_id: "YOUR_SITE_ID" });
    return () => Usertick.destroy();
  }, []);
  return null;
}
```

```ts Vue theme={null}
// main.ts: initialize once at app start
import { createApp } from "vue";
import App from "./App.vue";
import Usertick from "@usertick/snippet";

Usertick.init({ site_id: "YOUR_SITE_ID" });
createApp(App).mount("#app");
```

```ts Nuxt theme={null}
// plugins/usertick.client.ts: the .client suffix runs it only in the browser
import Usertick from "@usertick/snippet";

export default defineNuxtPlugin(() => {
  Usertick.init({ site_id: "YOUR_SITE_ID" });
});
```

```ts Angular theme={null}
// app.component.ts: initialize once in the root component
import { Component, OnInit } from "@angular/core";
import Usertick from "@usertick/snippet";

@Component({ selector: "app-root", templateUrl: "./app.component.html" })
export class AppComponent implements OnInit {
  ngOnInit() {
    Usertick.init({ site_id: "YOUR_SITE_ID" });
  }
}
```

```svelte Svelte theme={null}
<!-- src/routes/+layout.svelte: add this script block to the root layout -->
<script>
  import { onMount } from "svelte";
  import Usertick from "@usertick/snippet";

  onMount(() => {
    Usertick.init({ site_id: "YOUR_SITE_ID" });
    return () => Usertick.destroy();
  });
</script>
```

```astro Astro theme={null}
<!-- src/layouts/Layout.astro: add this script to the layout every page uses -->
<script>
  import Usertick from "@usertick/snippet";

  Usertick.init({ site_id: "YOUR_SITE_ID" });
</script>
```

```tsx Remix theme={null}
// app/root.tsx: add the effect to the root component
import { useEffect } from "react";
import { Outlet } from "@remix-run/react";
import Usertick from "@usertick/snippet";

export default function App() {
  useEffect(() => {
    Usertick.init({ site_id: "YOUR_SITE_ID" });
    return () => Usertick.destroy();
  }, []);

  return <Outlet />;
}
```

```js Gatsby theme={null}
// gatsby-browser.js in the project root
import Usertick from "@usertick/snippet";

export const onClientEntry = () => {
  Usertick.init({ site_id: "YOUR_SITE_ID" });
};
```

## Single page app behavior

* **Initialize once.** The widget follows route changes on its own, so `init` doesn't need to run again per route. A second `init` logs a warning and does nothing; to start over, call `destroy()` first.
* **React strict mode.** In development, React mounts, unmounts and mounts an effect again. The `init` and `destroy` pair in the examples handles that cycle.
* **Server rendering.** Importing the package on the server is safe, and `init` does nothing where there is no `window`. Call it from client-only code such as `useEffect`, `onMounted`, `onMount` or a `.client` plugin.
* **Both installs on one page.** When the script tag and the package are both on a page, the second copy finds the first and stays idle, so surveys never show twice.

## Open a survey from your code

When a website survey uses the **Custom event** trigger, your app opens it by sending the event:

```js theme={null}
Usertick.trigger("checkout_completed", { order_id: orderId, plan: "pro" });
```

An event sent before the widget is ready is kept and checked against the surveys for 10 seconds after the widget becomes ready. Every method is described in the [SDK reference](https://docs.usertick.com/developers/sdk/reference.md).


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.