Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(nuxt): Use --import as the default installation method #12070

Merged
merged 3 commits into from
Dec 10, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -20,10 +20,12 @@ supported:
When running your application in ESM mode, you will most likely want to <PlatformLink to="/install/esm">follow the ESM instructions</PlatformLink>. However, if you want to avoid using the `--import` command line option, for example if you have no way of configuring a CLI flag, you can also follow an alternative setup that involves importing the `instrument.mjs` file directly in your application.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

does this link exist? I think the link should point to the --import page, right?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Those are the node docs, I just edited those as well as I copied the Alert content from there and I thought I add the suggestions I got in this PR in the Node docs as well.

Or should I rather open a new PR for this?


<Alert level='warning' title='Restrictions of this installation method'>
This installation method has a fundamental restriction: It only supports limited performance instrumentation. Only basic `http` instrumentation will work, and no DB or framework-specific instrumentation will be available.

Because of this, we recommend using this only if the `--import` flag is not an option for you.
This installation method has fundamental restrictions:
- It only supports limited performance instrumentation.
- Only basic `http` instrumentation will work.
- No DB or framework-specific instrumentation will be available.

We recommend using this only if the `--import` flag is not an option for you.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

l: should we link to the --import guide? I know we reference it above but users might not have read it and jumped directly to the alert

</Alert>

You need to create a file named `instrument.mjs` that imports and initializes Sentry:
Expand Down
37 changes: 10 additions & 27 deletions docs/platforms/javascript/guides/nuxt/install/cli-import.mdx
Original file line number Diff line number Diff line change
@@ -1,45 +1,29 @@
---
title: --import CLI flag
sidebar_order: 2
description: "Learn about using the node `--import` CLI flag."
title: --import CLI flag (default)
sidebar_order: 1
description: "Learn how to use the node --import CLI flag."
---

## Understanding the `--import` CLI Flag

The [`--import` CLI flag](https://nodejs.org/api/cli.html#--importmodule) in Node allows you to preload modules before the application starts.
The [`--import` CLI flag](https://nodejs.org/api/cli.html#--importmodule) in Node is the default way in ESM to preload a module before the application starts.
If you cannot use the SDK's <PlatformLink to="/install/dynamic-import/">default dynamic import behaviour</PlatformLink>, setting
this flag is crucial for ensuring proper server-side initialization, as Sentry needs to be initialized before the rest of the application runs.

## Scenarios where `--import` does not work

- You're not able to add Node CLI flags or environment variables that are scoped to the function runtime
- As of now, Netlify only supports adding scoped environment variables in the paid plan
- As of now, Vercel does not provide an option for scoping environment variables
- **Netlify** only allows scoped environment variables on its paid plans at this time
- **Vercel** doesn't currently provide an option for scoping environment variables

If any of those points apply to you, you cannot use the `--import` flag to initialize Sentry on the server-side.
Check out the guide for using <PlatformLink to="/install/dynamic-import/">dynamic import</PlatformLink> instead.
Check out the guide for using <PlatformLink to="/install/top-level-import/">a top-level import</PlatformLink> or a <PlatformLink to="/install/dynamic-import/">dynamic import</PlatformLink> instead.

## Initializing Sentry with `--import`

To successfully use the `--import` flag, follow these steps:
By default, the SDK will add the Sentry server config to the build output (typically, `.output/server/sentry.server.config.mjs`).

### 1. Disable Dynamic Import

First, disable the dynamic import by setting `dynamicImportForServerEntry` to `false`:

```javascript {filename: nuxt.config.ts} {5}
export default defineNuxtConfig({
modules: ["@sentry/nuxt/module"],

sentry: {
dynamicImportForServerEntry: false,
},
});
```

By disabling the dynamic import, the SDK will add the Sentry server config to the build output (typically `.output/server/sentry.server.config.mjs`).

### 2. Adding `--import` to `node` command
### 1. Adding `--import` to `node` command

After building your Nuxt app with `nuxi build`, add the `--import` flag followed by the Sentry server config path to the `node` command.
With the default Nitro Node preset, this typically looks like this:
Expand All @@ -57,13 +41,12 @@ To make things easier, add a script in the `package.json`:
```json {filename:package.json}
{
"scripts": {
"preview": "NODE_OPTIONS='--import .//server/sentry.server.config.mjs' nuxt preview",
"start": "node --import ./.output/server/sentry.server.config.mjs .output/server/index.mjs"
}
}
```

### 3. Adding `--import` flag in production
### 2. Adding `--import` flag in production

To be able to set up Sentry in production, the `--import` flag needs to be added wherever you run your application's production build output.
Consult your hosting provider's documentation for specific implementation details.
Expand Down
37 changes: 25 additions & 12 deletions docs/platforms/javascript/guides/nuxt/install/dynamic-import.mdx
Original file line number Diff line number Diff line change
@@ -1,24 +1,36 @@
---
title: Dynamic Import (default)
sidebar_order: 1
title: Dynamic Import (experimental)
sidebar_order: 3
description: "Learn about how the Nuxt SDK leverages dynamic input() in the build output."
---

## Understanding the `import()` expression

The `import()` expression (also called "dynamic import") allows conditional and flexible module loading in ESM.
For the Sentry Nuxt SDK, it provides an approach to initialize server-side configuration before application startup.

The Sentry Nuxt SDK will be initialized before any other code runs and the Nitro server runtime code will be loaded later because of `import()`ing it.
This early initialization is required to set up the SDK's instrumentation of various libraries correctly.
Comment on lines 8 to 13
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
The `import()` expression (also called "dynamic import") allows conditional and flexible module loading in ESM.
For the Sentry Nuxt SDK, it provides an approach to initialize server-side configuration before application startup.
The Sentry Nuxt SDK will be initialized before any other code runs and the Nitro server runtime code will be loaded later because of `import()`ing it.
This early initialization is required to set up the SDK's instrumentation of various libraries correctly.
The `import()` expression, or dynamic import, enables flexible, conditional module loading in ESM.
For the Sentry Nuxt SDK, this means that server-side configuration is set up before the app starts. This early initialization is crucial for properly instrumenting various libraries, as the Nitro server runtime loads after the SDK.

Copy link
Member Author

@s1gr1d s1gr1d Dec 10, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know the text might be a bit complicated, but I think the suggestion is missing some crucial parts. It makes the impression that Nitro is initialized early anyways. It's important to point out that the SDK adds this dynamic import to load the server-side code after Sentry.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to the suggestion missing info.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, that makes sense. I think in that case, it's fine to keep this as is :)


## Initializing Sentry with Dynamic `import()`

By default, the Sentry Nuxt SDK includes a Rollup plugin which wraps the server entry file with a dynamic `import()`.
Enable the dynamic `import()` by setting `autoInjectServerSentry`:

```typescript {filename:nuxt.config.ts} {3}
export default defineNuxtConfig({
sentry: {
autoInjectServerSentry: 'experimental_dynamic-import'
},
})
```

After setting this, the Sentry Nuxt SDK adds some build-time configuration to ensure your app is wrapped with `import()`.
With this, Sentry can be initialized before all other modules of the application.

The server entry file will look something like this:
The Nuxt server entry file will look something like this:

```javascript {filename:.output/server/index.mjs}
// Note: file may have some imports and code related to debug IDs
// Note: The file may have some imports and code, related to debug IDs
Sentry.init({
dsn: "..."
});
Expand All @@ -28,8 +40,11 @@ import('./chunks/nitro/nitro.mjs').then(function (n) { return n.r; });

## Scenarios where `import()` doesn't work

We are currently investigating an issue where the server-side is not correctly initialized with a recent update of Nitro (the server-side toolkit in Nuxt).
We are working on figuring this out ([see issue here](https://github.com/getsentry/sentry-javascript/issues/14514)). As a temporary workaround, you can add the following overrides to your application:
Depending on your setup and which version of Nitro is used, the server-side is sometimes not correctly initialized.
The build output **must not** include a regular `import` of the Nitro runtime (e.g. `import './chunks/nitro/nitro.mjs'`).
andreiborza marked this conversation as resolved.
Show resolved Hide resolved
See the ([GitHub issue here](https://github.com/getsentry/sentry-javascript/issues/14514)) for more information.

As a temporary workaround, you can add the following overrides in your application:

```json {tabTitle:npm} {filename:package.json}
"overrides": {
Expand All @@ -52,16 +67,14 @@ We are working on figuring this out ([see issue here](https://github.com/getsent
}
```

You can also check out the guide for using the <PlatformLink to="/install/cli-import//">CLI flag `--import`</PlatformLink> as this might be a better choice for you.

You can also check out the guide for installing the SDK with a <PlatformLink to="/install/cli-import">CLI flag `--import`</PlatformLink> or a <PlatformLink to="/install/top-level-import/">top-level import</PlatformLink>.

## Re-exporting serverless handler functions

Sentry automatically detects serverless handler functions in the build output and re-exports them from the server entry file.

By default, Sentry re-exports functions named `handler`, `server`, and `default` exports. This will work in most cases and no other action is required.
In case your serverless function has another, custom name you can override this with `entrypointWrappedFunctions`:

If your serverless function has a custom name, you can override it with `experimental_entrypointWrappedFunctions`:

```javascript {filename: nuxt.config.ts} {7}
export default defineNuxtConfig({
Expand All @@ -70,7 +83,7 @@ export default defineNuxtConfig({
sentry: {
// Customize detected function names
// Default value: ['default', 'handler', 'server']
entrypointWrappedFunctions: ['customFunctionName']
experimental_entrypointWrappedFunctions: ['customFunctionName']
},
});
```
42 changes: 42 additions & 0 deletions docs/platforms/javascript/guides/nuxt/install/top-level-import.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
---
title: Top-level import
sidebar_order: 2
description: "Learn about how the Nuxt SDK adds a top-level import to the build output."
---

## Understanding Top-level `import`

Sentry needs to be initialized before the application starts.
If the default way of adding an <PlatformLink to="/install/cli-import">`--import` CLI flag</PlatformLink> flag does not work for you,
set up the SDK for adding a top-level `import`. This will import the Sentry server-side config at the top of the Nuxt server entry file.
In this case, Sentry isn’t initialized before the app starts, but is set up as early as possible.

<Alert level='warning' title='Restrictions of this installation method'>
This installation method has fundamental restrictions:
- It only supports limited performance instrumentation.
- Only basic `http` instrumentation will work.
- No DB or framework-specific instrumentation will be available.

We recommend using this only if the `--import` flag is not an option for you.
</Alert>

## Initializing Sentry With a Top-level `import`

Enable the top-level `import` by setting `autoInjectServerSentry`:

```typescript {filename:nuxt.config.ts} {3}
export default defineNuxtConfig({
sentry: {
autoInjectServerSentry: 'top-level-import'
},
})
```

By default, the SDK will add the Sentry server config to the build output (typically, `.output/server/sentry.server.config.mjs`).

With the top-level `import`, the Nuxt server entry file will look something like this:

```javascript {filename:.output/server/index.mjs}
import './sentry.server.config.mjs';
// Note: The file may have some imports and code, related to debug IDs
```
6 changes: 6 additions & 0 deletions docs/platforms/javascript/guides/nuxt/manual-setup.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,12 @@ dotenv.config();
// ... rest of the file
```

#### Load Sentry config

Sentry can only be loaded on the server-side by being explicitly added via `--import`.

Check out the <PlatformLink to="/install/cli-import">`--import` CLI flag</PlatformLink> docs for setup instructions.

<Alert level="warning">
In the beta state of the Nuxt SDK, some features may not work with certain deployment providers. Check the progress on GitHub: [Compatibility with different Deployment Platforms](https://github.com/getsentry/sentry-javascript/issues/14029)
</Alert>
Expand Down
Loading