Skip to content
Merged
Show file tree
Hide file tree
Changes from 22 commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
8d75fc6
Docs for content page and CRUD operations for context
Aviatorscode2 Oct 10, 2025
8e14aa2
Docs for context
Aviatorscode2 Oct 10, 2025
937af0e
change page description
Aviatorscode2 Oct 10, 2025
8e5201d
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 13, 2025
6b0a85a
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 13, 2025
50e4d96
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 13, 2025
b3cec4c
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 13, 2025
8defd4b
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 13, 2025
3ffe7ac
Update based on feedback
Aviatorscode2 Oct 13, 2025
6fb394e
Update context based on Adam's feedback
Aviatorscode2 Oct 13, 2025
6a609bf
Add new update
Aviatorscode2 Oct 13, 2025
7ddb7f7
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 14, 2025
fb7392f
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 14, 2025
a6ec1aa
Update content/docs/platform/workflow/contexts.mdx
Aviatorscode2 Oct 17, 2025
82ca9c0
Content for the context page in the workflow section
Aviatorscode2 Oct 21, 2025
e4f3589
Docs for the inbox with context page
Aviatorscode2 Oct 21, 2025
74b5e91
Update the JS and React SDK guide
Aviatorscode2 Oct 21, 2025
e6538dc
Update content/docs/platform/workflow/contexts/index.mdx
Aviatorscode2 Oct 21, 2025
a92cebf
Update content/docs/platform/inbox/configuration/inbox-with-context.mdx
Aviatorscode2 Oct 21, 2025
5949cd6
Update content/docs/platform/workflow/contexts/manage-contexts.mdx
Aviatorscode2 Oct 21, 2025
0dc510b
Fixed code errors
Aviatorscode2 Oct 22, 2025
7347e70
Merge branch 'MRK-1074' of https://github.com/novuhq/docs into MRK-1074
Aviatorscode2 Oct 22, 2025
5f64a99
Update docs for workflow trigger and Inbox to not upsert context but …
Aviatorscode2 Oct 24, 2025
db5e4a1
Add contexts image
Aviatorscode2 Oct 24, 2025
f6705f2
Update code block
Aviatorscode2 Oct 24, 2025
5634e12
fix: PR suggestions and issues
jainpawan21 Oct 26, 2025
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
78 changes: 78 additions & 0 deletions content/docs/platform/inbox/configuration/inbox-with-context.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
---
pageTitle: 'Using contexts for Inbox personalization'
title: 'Inbox with context'
description: 'Learn how to use contexts in the Inbox component to filter and personalize notifications for your subscribers.'
icon: 'Package'
---

_Contexts_ let you scope each <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> instance to a specific environment, tenant, or app within your product. When combined with workflow-level contexts, they ensure that each <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> displays only the notifications relevant to that specific context.
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Remove or correct self-referential links to the current page.

Lines 8, 14, 40, and 66 all use <Method href="/platform/inbox/configuration/inbox-with-context"> which links to the current page. Self-referential links don't provide value to readers. Either:

  • Remove the <Method> wrapper and use plain text for the component name, or
  • Link to a related conceptual page (e.g., /platform/inbox/overview or /platform/workflow/contexts)

Example fix for line 8:

-_Contexts_ let you scope each <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> instance to a specific environment, tenant, or app within your product. When combined with workflow-level contexts, they ensure that each <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> displays only the notifications relevant to that specific context.
+_Contexts_ let you scope each {`<Inbox />`} instance to a specific environment, tenant, or app within your product. When combined with workflow-level contexts, they ensure that each {`<Inbox />`} displays only the notifications relevant to that specific context.

Also applies to: 14-14, 40-40, 66-66

🤖 Prompt for AI Agents
In content/docs/platform/inbox/configuration/inbox-with-context.mdx around lines
8, 14, 40, and 66, replace the self-referential <Method
href="/platform/inbox/configuration/inbox-with-context">...</Method> wrappers
with either plain text component names (e.g., `<Inbox />`) or change the href to
a more useful target such as `/platform/inbox/overview` or
`/platform/workflow/contexts`; update each occurrence so the link no longer
points to the current page and preserves surrounding punctuation and formatting.


<Callout type='info'>If you’re new to contexts, start from the [Contexts](/platform/workflow/contexts) section to understand how contexts are created, managed in Novu and how they used in workflows.</Callout>

## How context works in `<Inbox/>`

The <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> uses exact-match context filtering to determine which notifications to display. This means the context provided to the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> must match all the key-value pairs of the context used when the workflow was triggered.

This creates predictable isolation and ensures notifications can't accidentally leak across boundaries. If the contexts do not match exactly, the notification will not be delivered to that Inbox session.

| Workflow Context | Inbox Context | Displayed? |
| ------------------------------------------ | ------------------------ | ---------- |
| `{ "tenant": "acme" }` | `{ "tenant": "acme" }` | ✅ Yes |
| `{ "tenant": "acme" }` | `{ "tenant": "globex" }` | ❌ No |
| `{ "tenant": "acme", "app": "dashboard" }` | `{ "tenant": "acme" }` | ❌ No |
| `{}` | `{}` | ✅ Yes |


### Creating context via `<Inbox/>`

If a new context is passed from the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> that doesn’t already exist, Novu will automatically create it. This means you don’t have to manually set up contexts before using them, they are created just in time.

This is particularly useful for:

- **Dynamic tenants or organizations**: When users join or switch organizations.
- **Per-environment views**: Isolating notifications for staging, production, or preview.
- **Feature-specific dashboards**: Where each section of your app has its own notification scope.
Comment on lines 34 to 35
Copy link
Contributor

Choose a reason for hiding this comment

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

Not sure if this is accurate use of context - to distinguish Inbox per environment and organization we already use applicationIdentifier


You can view all automatically created contexts under the Contexts section of your Novu dashboard.

## Applying context to the Inbox

You can filter the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> notifications to a specific context, by passing a context prop to the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> component.

This prop's value defines the filter for that session, and it will only request and show notifications that match this context.

```typescript
import { Inbox } from '@novu/react';

<Inbox
applicationIdentifier="APPLICATION_IDENTIFIER"
subscriber="SUBSCRIBER_ID"
context={{
tenant: {
id: 'acme-corp',
data: {
name: 'Acme Corporation',
plan: 'enterprise',
},
},
}}
/>
```

When a workflow with these exact context is triggered, as seen below
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Fix subject-verb number agreement.

Line 64 reads "When a workflow with these exact context is triggered" but should use plural "contexts" to match the concept of multiple key-value pairs.

Apply this diff:

-When a workflow with these exact context is triggered, as seen below
+When a workflow with these exact contexts is triggered, as seen below
🧰 Tools
🪛 LanguageTool

[grammar] ~64-~64: Ensure spelling is correct
Context: ... }, }} /> ``` When a workflow with these exact context is triggered, as seen bel...

(QB_NEW_EN_ORTHOGRAPHY_ERROR_IDS_1)

🤖 Prompt for AI Agents
In content/docs/platform/inbox/configuration/inbox-with-context.mdx around line
64, fix the subject-verb agreement by changing "When a workflow with these exact
context is triggered" to use the plural noun "contexts" (i.e., "When a workflow
with these exact contexts is triggered") so the sentence correctly refers to
multiple key-value pairs; update the text accordingly and run a quick
spell/grammar check on nearby sentences for consistency.


![Context in trigger](/images/inbox/context-trigger.png)

Then, the notifications will be delivered to the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method>.

![Inbox with context](/images/inbox/context.png)

<Callout>To learn how to use context with the Novu SDKs, visit the <Method href="/platform/sdks/javascript">{`Context`}</Method> documentation.</Callout>

## How to secure your context

Because the context prop is set on the client-side, a malicious user could potentially tamper with it to view notifications from a different tenant.

To prevent this, you must validate the session using HMAC encryption. This ensures that the context data comes from your server and has not been altered.

<Callout>Learn how to secure your <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> with HMAC encryption, refer to the [Prepare for Production](/platform/inbox/prepare-for-production) documentation.</Callout>
4 changes: 2 additions & 2 deletions content/docs/platform/inbox/configuration/meta.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"title": "Customize and configure",
"icon": "SlidersHorizontal",
"pages": ["styling", "icons", "tabs", "preferences", "data-object"],
"description": "Learn how to configure your inbox with styling, tabs, preferences, data objects, and snooze functionality"
"pages": ["styling", "tabs", "preferences", "data-object", "inbox-with-context", "icons"],
"description": "Learn how to configure your inbox with styling, tabs, preferences, data objects, icons and context functionality"
}
1 change: 1 addition & 0 deletions content/docs/platform/meta.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
"workflow/step-conditions",
"workflow/tags",
"workflow/translations",
"workflow/contexts",
"---Channels---",
"...integrations",
"---Account---",
Expand Down
33 changes: 32 additions & 1 deletion content/docs/platform/sdks/javascript/index.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,13 @@ The Novu client provides methods to interact with notifications, preferences, an
"description": "",
"type": "string"
},
"context": {
"description": "A context object to filter notifications for this session.",
"type": "object"
},
"contextHash": {
"description": "The HMAC-SHA256 hash of the context object. Required if context is provided and HMAC is enabled.", "type": "string"
},
"apiUrl": {
"description": "",
"type": "string"
Expand All @@ -50,7 +57,7 @@ The Novu client provides methods to interact with notifications, preferences, an

### Usage

<Tabs items={['US', 'EU', 'HMAC Encryption']}>
<Tabs items={['US', 'EU', 'Using Context', 'HMAC Encryption']}>
<Tab value="US">
```typescript
import { Novu } from "@novu/js";
Expand All @@ -73,6 +80,30 @@ The Novu client provides methods to interact with notifications, preferences, an
});
```
</Tab>
<Tab value="Using Context">
<Callout type="info"> Learn how Context is used to filter Inbox notifications in the [Inbox with Context](/platform/inbox/customization-and-configuration/inbox-with-context) guide. </Callout>
```tsx
import { Novu } from '@novu/js';

const novu = new Novu({
applicationIdentifier: 'YOUR_APP_ID',
subscriberId: 'user-123',
context: {
tenant: { id: 'org-123', data: { name: 'Acme Corp' } },
team: 'team-456',
},
});

// Access the current context
console.log(novu.context);
// → { tenant: { id: 'org-123', data: { name: 'Acme Corp' } }, team: 'team-456' }

// Get a stable string key (used internally for caching/filtering)
console.log(novu.contextKey);
// → "team:team-456,tenant:org-123"

```
</Tab>
<Tab value="HMAC Encryption">
```typescript
import { Novu } from "@novu/js";
Expand Down
39 changes: 37 additions & 2 deletions content/docs/platform/sdks/react/hooks/novu-provider.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,14 @@ Usually, it's placed somewhere in the root of your application, which makes the
type: "string",
description: "HMAC encryption hash for the subscriber",
},
context: {
type: "object",
description: "Defines contextual attributes (for example, tenant, app, team) for filtering and personalizing notifications.",
},
contextHash: {
type: "string",
description: "The HMAC-SHA256 hash of the context object. Required if context is provided and HMAC is enabled."
},
apiUrl: {
type: "string",
description: "Custom backend URL for self-hosted instances",
Expand All @@ -43,7 +51,7 @@ Usually, it's placed somewhere in the root of your application, which makes the

## Example Usage

<Tabs items={['US', 'EU', 'HMAC Encryption']}>
<Tabs items={['US', 'EU', 'Using Context', 'HMAC Encryption']}>
<Tab value="US">
```tsx
import { NovuProvider } from '@novu/react';
Expand Down Expand Up @@ -80,6 +88,33 @@ Usually, it's placed somewhere in the root of your application, which makes the
```

</Tab>
<Tab value="Using Context">
<Callout type="info"> Learn how to use Context for filtering and personalization in the [Inbox withContext](/platform/inbox/configuration/inbox-with-context) guide.</Callout>
```tsx
import { NovuProvider, useNovu } from '@novu/react';

function App() {
return (
<NovuProvider
applicationIdentifier="APPLICATION_IDENTIFIER"
subscriber="SUBSCRIBER_ID"
context={{
tenant: { id: "org-123" }
}}
>
<App />
</NovuProvider>
);
}

// In child components
const MyComponent = () => {
const novu = useNovu();
console.log(novu.context);
// Logs: { tenant: { id: "org-123" } }
};
```
</Tab>
<Tab value="HMAC Encryption">
<Callout type="info">
Read more about [HMAC Encryption](/platform/inbox/prepare-for-production#secure-your-inbox-with-hmac-encryption).
Expand All @@ -102,4 +137,4 @@ Usually, it's placed somewhere in the root of your application, which makes the
```

</Tab>
</Tabs>
</Tabs>
79 changes: 79 additions & 0 deletions content/docs/platform/workflow/contexts/contexts-in-workflows.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
---
pageTitle: 'Personalize workflows and templates in Novu using context'
title: 'Applying context'
description: 'Learn how to use contexts in Novu to personalize notification templates, control workflow logic, and customize the Inbox. Understand supported data formats and how to debug context usage from the activity feed.'
---

Contexts let you personalize how notifications are rendered and delivered by making contextual data available inside template editors, step conditions, and the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> component.

## How to use context

Once a context is created either through the Novu dashboard or API, its data becomes available for use in your templates editors, step conditions, and for customizing the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> component.

### Using context data in the template editor

Use the `{{context}}` Handlebars helper to access context data in any template editor. The context key you provide while creating the context (for example, tenant, region) becomes the accessor.


For example, if a context with this data is created:

```json
context: {
tenant: {
id: 'acme-corp',
data: {
name: 'Acme Corporation',
plan: 'enterprise'
}
}
}
```

You can access the `name` and `plan` in your in-app, email, SMS, or push template like this:

```html
<p>Welcome, new user from {{context.tenant.data.name}}!</p>
<p>Your account is on the {{context.tenant.data.plan}} plan.</p>
```
Or

```text
Welcome, new user from {{context.tenant.data.name}}!
Your account is on the {{context.tenant.data.plan}} plan.
```

![Using context data in the template editor](/images/workflows/contexts/context.gif)

<Callout>Refer to the Inbox documentation, to learn how to use context in the <Method href="/platform/inbox/configuration/inbox-with-context">{`<Inbox />`}</Method> component. </Callout>

### Using context in step conditions

You can use context variables in the **Step conditions** tab of a workflow step to add conditional logic to your notifications. For example, only send a "Feature X is now enabled" email if `context.tenant.data.plan` is `enterprise`.
![Context step conditions](/images/workflows/context-step-conditions.png)

To learn how contexts are structured or how to define them, refer to the [Managing Contexts](/platform/workflow/contexts/manage-contexts) documentation.

## Viewing and debugging contexts

Once you start using contexts in your workflows, Novu provides full observability so you can monitor and debug your context usage after a workflow has been triggered.

### Searching for workflow runs

You can filter your workflow runs to find all executions associated with a specific context.

1. Navigate to the **Activity Feed** in your Novu dashboard.
2. Select the **Workflow Runs** tab.
3. In the search bar, click **Context** and enter the context `type` and `id` using the format `type:id`.

![Searching for workflow runs](/images/workflows/search-context-activityfeed.png)

### Verifying the resolved context

To confirm that Novu received and processed your context data correctly, you can inspect the API traces for a specific run.

1. From the **Activity Feed**, select the relevant workflow run from the list in the **Requests** tab.
2. In the workflow run details, go to the **API Traces** tab.

Here, you will see the full context object that was resolved and attached to that specific workflow execution.

![Verifying the resolved context](/images/workflows/resolved-context.png)
71 changes: 71 additions & 0 deletions content/docs/platform/workflow/contexts/index.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
---
pageTitle: 'Context'
title: 'Context'
description: "Learn what Contexts are in Novu, how they differ from payloads, and how they help you organize and personalize notifications across workflows."
icon: 'Package'
---

_Contexts_ are flexible, user-defined data objects that help you organize and personalize your notifications. They let you attach metadata, such as tenant, region, or app details, and enable contextual behavior to workflows, notifications, and other entities across Novu.

In simple terms, a context acts like an extended version of the payload. While the payload exists only for the duration of a single workflow execution, contexts are persistent and can be reused across multiple workflows or API calls. This makes them ideal for multi-tenant environments, dynamic branding, and use cases where notifications depend on shared or reusable data.

## How context works

Context solves the common problem of sending differentiated notifications to the same subscriber without creating duplicate subscriber records or complex workarounds.

For example, if you have a single subscriber entity, `[email protected]`, who uses two different applications you offer: "Notion Email" and "Notion Calendar". You want to send notifications specific to each application.

Without context, you might have to create two different subscribers or use workarounds with subscriber ID prefixes to differentiate the notifications.

```javascript
// Problem: How does Novu know which app is sending the notification?

// Notion Email notification
await novu.trigger('new-email-received', {
to: '[email protected]',
payload: { title: 'You have 1 new email' }
});

// Notion Calendar notification
await novu.trigger('new-calendar-event', {
to: '[email protected]',
payload: { title: 'You have a new meeting invite' }
});
```

However, with context, you can provide this metadata directly in the trigger. This allows you to use a single workflow and subscriber entity, while dynamically changing content or logic based on the context.

```javascript
// Solution: Pass an 'app' context to differentiate triggers.

// Notion Email notification
await novu.trigger('new-email-received', {
to: '[email protected]',
payload: { title: 'You have 1 new email' },
context: {
app: 'notion-email',
branding: {
logo: "url_for_email_logo.png"
}
}
});

// Notion Calendar notification
await novu.trigger('new-calendar-event', {
to: '[email protected]',
payload: { title: 'You have a new meeting invite' },
context: {
app: 'notion-calendar',
branding: {
logo: "url_for_calendar_logo.png"
}
}
});
```

Here are some ways that you can use contexts:

- **Multi-tenancy and app routing**: Use a tenant or app context to dynamically alter notification content, branding, or logic for different customers or applications from a single workflow.
- **Shared chat credentials**: For chat providers like Slack or MS Teams, store workspace-level credentials (for example, a bot token) in a context. This allows multiple subscribers within that workspace to receive notifications without each subscriber needing to store the shared token.
- **A/B testing**: Pass a campaign identifier in a context (for example, campaign: 'new-welcome-email-v2'). Use this in a condition step to split users into different notification paths and measure which performs better.
- **Data residency and compliance**: Use a region context to tag notifications with their origin. This can help in applying data retention policies or filtering data for compliance audits.
Comment on lines 68 to 72
Copy link
Contributor

Choose a reason for hiding this comment

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

This was listed as "Other potential use-cases" in the DX guide just to hint what we could do with it in the future, not that it works right away - e.g. "Shared chat credentials" this is not yet implemented.

I would suggest listing actual customer use-cases / recipes, as I suggested in the last review.

Loading
Loading