{"id":27209267,"url":"https://github.com/braze-inc/braze-web-sdk","last_synced_at":"2026-06-10T20:24:46.242Z","repository":{"id":31927362,"uuid":"35496795","full_name":"braze-inc/braze-web-sdk","owner":"braze-inc","description":"Public repo for the Braze Web SDK","archived":false,"fork":false,"pushed_at":"2026-04-17T17:01:24.000Z","size":1605,"stargazers_count":83,"open_issues_count":8,"forks_count":31,"subscribers_count":34,"default_branch":"master","last_synced_at":"2026-04-17T17:11:15.013Z","etag":null,"topics":["braze","customer-engagement","javascript","marketing-automation","sdk","typescript"],"latest_commit_sha":null,"homepage":"https://www.braze.com","language":"HTML","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/braze-inc.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2015-05-12T15:34:56.000Z","updated_at":"2026-04-17T17:01:28.000Z","dependencies_parsed_at":"2023-02-17T09:01:13.800Z","dependency_job_id":"ed45de1d-8fb2-4886-9ab4-d926877ce1d7","html_url":"https://github.com/braze-inc/braze-web-sdk","commit_stats":{"total_commits":188,"total_committers":12,"mean_commits":"15.666666666666666","dds":0.3191489361702128,"last_synced_commit":"b24e8d79a0761ac754f1322f241ce71b4acb6145"},"previous_names":["appboy/appboy-web-sdk"],"tags_count":145,"template":false,"template_full_name":null,"purl":"pkg:github/braze-inc/braze-web-sdk","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/braze-inc%2Fbraze-web-sdk","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/braze-inc%2Fbraze-web-sdk/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/braze-inc%2Fbraze-web-sdk/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/braze-inc%2Fbraze-web-sdk/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/braze-inc","download_url":"https://codeload.github.com/braze-inc/braze-web-sdk/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/braze-inc%2Fbraze-web-sdk/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34170158,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-10T02:00:07.152Z","response_time":89,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["braze","customer-engagement","javascript","marketing-automation","sdk","typescript"],"created_at":"2025-04-10T00:40:43.633Z","updated_at":"2026-06-10T20:24:46.236Z","avatar_url":"https://github.com/braze-inc.png","language":"HTML","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cp align=\"center\"\u003e\n  \u003cimg width=\"480\" alt=\"Braze Logo\" src=\".github/assets/logo-light.png#gh-light-mode-only\" /\u003e\n  \u003cimg width=\"480\" alt=\"Braze Logo\" src=\".github/assets/logo-dark.png#gh-dark-mode-only\" /\u003e\n\u003c/p\u003e\n\n# Braze Web SDK [![latest](https://img.shields.io/github/v/tag/braze-inc/braze-web-sdk?label=latest%20release\u0026color=300266)](https://github.com/braze-inc/braze-web-sdk/releases) [![Static Badge](https://img.shields.io/badge/TSDoc-801ed7)](https://js.appboycdn.com/web-sdk/latest/doc/modules/braze.html) ![lighthouse score](.github/assets/lighthouse-score.svg)\n\n- [Braze User Guide](https://www.braze.com/docs/user_guide/introduction/ \"Braze User Guide\")\n- [Braze Developer Guide](https://www.braze.com/docs/developer_guide/sdk_integration/?sdktab=web \"Braze Developer Guide\")\n\n## About the Braze Web SDK\n\nThe Braze Web SDK enables you to integrate Braze's customer engagement platform directly into your web applications. Built with TypeScript and designed for modern web development, this SDK provides comprehensive tools for user management, messaging, analytics, and feature flagging.\n\n### What You Can Do\n\n- **User Management**: Track and manage user identities, attributes, and behavior across your web application\n- **In-App Messaging**: Display targeted messages and notifications to users while they're actively using your site\n- **Content Cards**: Show personalized content feeds and promotional cards that update in real-time\n- **Banners**: Show banner messaging in specific placements within your site\n- **Push Notifications**: Send web push notifications to engage users even when they're not on your site\n- **Feature Flags**: Control feature rollouts and A/B testing with server-side feature flag management\n- **Analytics**: Track custom events, user interactions, and conversion metrics\n- **Session Management**: Monitor user sessions and engagement patterns\n\nWhether you're building a single-page application, e-commerce site, or content platform, the Braze Web SDK provides the tools you need to create personalized, engaging user experiences that drive growth and retention.\n\n## Prerequisites\n\nBefore integrating the Braze Web SDK, you'll need:\n\n- **Braze Account**: A Braze account with API access\n- **API Key**: Your app's API key from the Braze dashboard\n- **SDK Endpoint**: Your Braze SDK endpoint URL (e.g., `sdk.iad-01.braze.com`)\n\n### Getting Your Credentials\n\n1. **API Key**: Found in your Braze dashboard under Settings → API Keys\n2. **SDK Endpoint**: Located in Settings → SDK Authentication → Endpoints\n3. **Service Worker**: Required for push notifications (see Push Notifications section)\n\n## Table of Contents\n\n1. [Prerequisites](#prerequisites)\n2. [Installation](#installation)\n3. [Quick Start](#quick-start)\n4. [Configuration Reference](#configuration-reference)\n5. [Core Features](#core-features)\n   - [Initialization \u0026 Setup](#initialization--setup)\n   - [User Management](#user-management)\n   - [In-App Messages](#in-app-messages)\n   - [Content Cards](#content-cards)\n   - [Push Notifications](#push-notifications)\n   - [Feature Flags](#feature-flags)\n   - [Banners](#banners)\n   - [Analytics \u0026 Events](#analytics--events)\n   - [Session Management](#session-management)\n   - [Data Management](#data-management)\n6. [Integration Patterns](#integration-patterns)\n7. [Error Handling](#error-handling)\n8. [Libraries](#libraries)\n9. [Supported Browsers](#supported-browsers)\n10. [Debugging \u0026 Troubleshooting](#debugging--troubleshooting)\n11. [Additional Resources](#additional-resources)\n\n---\n\n## Installation\n\n```shell\nnpm install --save @braze/web-sdk\n# or, using yarn:\n# yarn add @braze/web-sdk\n```\n\n## Quick Start\n\n```typescript\nimport * as braze from \"@braze/web-sdk\";\n\n// Initialize the SDK\nbraze.initialize('YOUR-API-KEY-HERE', {\n    baseUrl: \"YOUR-SDK-ENDPOINT-HERE\",\n});\n\nbraze.changeUser('Jane Doe');\n```\n\n## Configuration Reference\n\n### Initialization Options\n\nThe `initialize` function accepts an options object with the following properties:\n\n| Option | Type | Default | Description |\n|--------|------|---------|-------------|\n| `baseUrl` | `string` | **Required** | This option is required to configure the Braze Web SDK to use the appropriate endpoint for your integration - for example: `braze.initialize('YOUR-API-KEY-HERE', { baseUrl: 'sdk.iad-03.braze.com' })` |\n| `enableLogging` | `boolean` | `false` | Set to true to enable logging by default. Note that this will cause Braze to log to the javascript console, which is visible to all users! You should probably remove this or provide an alternate logger with setLogger before you release your page to production. |\n| `allowUserSuppliedJavascript` | `boolean` | `false` | By default, the Braze Web SDK does not allow user-supplied Javascript click actions, or enable HTML in-app messages and Banners, as they allow Braze dashboard users to run Javascript on your site. To indicate that you trust the Braze dashboard users to write non-malicious Javascript click actions, set this property to true. |\n| `doNotLoadFontAwesome` | `boolean` | `false` | Braze uses Font Awesome for in-app message icons. By default, Braze will automatically load FontAwesome 4.7.0 from the FontAwesome CDN. To disable this behavior (e.g. because your site uses a customized version of FontAwesome), set this option to `true`. Note that if you do this, you are responsible for ensuring that FontAwesome is loaded on your site - otherwise in-app messages may not render correctly. |\n| `inAppMessageZIndex` | `number` | `999999` | By default, the Braze SDK will show In-App Messages with a z-index of 999999. Provide a value for this option to override that default. |\n| `sessionTimeoutInSeconds` | `number` | `30` | By default, a session times out after 30 seconds of inactivity. Provide a value for this option to override that default. |\n| `deviceId` | `string` | Auto-generated | By default, Braze will assign a random guid as the device ID. Provide a value for this configuration option to override that default with a value of your own. |\n| `appVersion` | `string` | `undefined` | If you provide a value for this option, user events sent to Braze will be associated with the given version, which can be used for user segmentation. |\n| `appVersionNumber` | `string` | `undefined` | A numerical app version value which can be used for user segmentation. This value must be sent with four fields, such as \"1.2.3.4\", otherwise it will be ignored. Note: `appVersion` must also be set, either with the same value or a unique name for this version. |\n| `contentSecurityNonce` | `string` | `undefined` | If you provide a value for this option, the Braze SDK will add the nonce to any `\u003cscript\u003e` and `\u003cstyle\u003e` elements created by the SDK. This can be used to permit the Braze SDK to work with your website's Content Security Policy. Note that in addition to setting this nonce, you may also need to allow FontAwesome to load, which you can do by either adding `use.fontawesome.com` to your Content Security Policy allowlist or by using the `doNotLoadFontAwesome` option and loading it manually. |\n| `noCookies` | `boolean` | `false` | By default, the Braze Web SDK uses cookies. To disable cookie usage, set this option to true. Note that disabling cookies may impact the SDK's ability to remember users' identities between sessions. |\n| `allowCrawlerActivity` | `boolean` | `false` | By default, the Braze Web SDK ignores activity from known spiders or web crawlers, such as Google, based on the user agent string. This saves data points, makes analytics more accurate, and may improve page rank. However, if you want Braze to log activity from these crawlers instead, you may set this option to true. |\n| `disablePushTokenMaintenance` | `boolean` | `false` | By default, users who have already granted web push permission (e.g. through requestPushPermission or from a prior push provider) will sync their push token with the Braze backend automatically on new session to ensure deliverability. To disable this behavior, set this option to true. |\n| `enableSdkAuthentication` | `boolean` | `false` | Set to true to enable the SDK Authentication feature. For more information about SDK Authentication, see our Product Documentation. |\n| `manageServiceWorkerExternally` | `boolean` | `false` | By default, the Braze Web SDK manages its own service worker for push notifications. If you are already managing a service worker in your application and would like to incorporate the Braze service worker functionality into it, set this option to true and include the Braze service worker code in your service worker file. |\n| `minimumIntervalBetweenTriggerActionsInSeconds` | `number` | `30` | By default, trigger actions (e.g., displaying an in-app message) can be fired at most once every 30 seconds per user. Provide a value for this option to override that default. |\n| `serviceWorkerLocation` | `string` | `undefined` | By default, the Braze Web SDK will look for its service worker file at the root of your domain. Provide a value for this option to override that default and specify a custom location for the service worker file. |\n| `safariWebsitePushId` | `string` | `undefined` | Required for Safari push notifications. This value can be found in your Apple Developer account. For more information about setting up Safari push notifications, see our Product Documentation. |\n| `localization` | `string` | `undefined` | If you provide a value for this option, the Braze SDK will attempt to display in-app messages and content cards in that locale. |\n| `openInAppMessagesInNewTab` | `boolean` | `false` | By default, links in in-app messages open in the same tab. Set this option to true to make them open in a new tab instead. |\n| `openCardsInNewTab` | `boolean` | `false` | By default, links in content cards open in the same tab. Set this option to true to make them open in a new tab instead. |\n| `requireExplicitInAppMessageDismissal` | `boolean` | `false` | By default, in-app messages can be dismissed by clicking outside of them or pressing the escape key. Set this option to true to require users to explicitly click a dismiss button or action button to dismiss the message. |\n| `devicePropertyAllowlist` | `string[]` | `undefined` | By default, the Braze SDK automatically detects and collects all device properties in DeviceProperties. To override this behavior, provide an array of DeviceProperties. To disable all properties being sent to Braze servers, provide an empty array. Note that without some properties, not all features will function properly. For instance, without the time zone, local timezone delivery will not function. |\n| `serviceWorkerScope` | `string` | `undefined` | By default, the Braze Web SDK will register its service worker with the default scope (the service worker's directory). Provide a value for this option to override that default and specify a custom scope for the service worker. |\n\n---\n\n## Core Features\n\n### Initialization \u0026 Setup\n\n#### Basic Initialization\n\n```typescript\nimport * as braze from \"@braze/web-sdk\";\n\n// Initialize the SDK\nbraze.initialize('YOUR-API-KEY-HERE', {\n    baseUrl: 'YOUR-SDK-ENDPOINT-HERE',\n    enableLogging: true // Remove in production\n});\n\n// Start a session\nbraze.openSession();\n```\n\n#### Advanced Initialization Options\n\n```typescript\nimport * as braze from \"@braze/web-sdk\";\n\nbraze.initialize('YOUR-API-KEY-HERE', {\n    baseUrl: 'YOUR-SDK-ENDPOINT-HERE',\n    enableLogging: true,\n    allowUserSuppliedJavascript: true,\n    doNotLoadFontAwesome: false,\n    inAppMessageZIndex: 999999,\n    sessionTimeoutInSeconds: 30,\n    deviceId: 'custom-device-id',\n    appVersion: '1.0.0',\n    contentSecurityNonce: 'your-nonce-here'\n});\n```\n\n### User Management\n\n#### Change User\n\n```typescript\nimport { changeUser } from \"@braze/web-sdk\";\n\n// Change to a new user\nchangeUser('user-123');\n```\n\n#### Set User Attributes\n\n```typescript\nimport { getUser } from \"@braze/web-sdk\";\n\nconst user = getUser();\nif (user) {\n    user.setEmail('user@example.com');\n    user.setFirstName('John');\n    user.setLastName('Doe');\n    user.setCustomUserAttribute('subscription_tier', 'premium');\n    user.setCustomUserAttribute('last_login', new Date());\n}\n```\n\n#### Set User Location\n\n```typescript\nimport { getUser } from \"@braze/web-sdk\";\n\nconst user = getUser();\nif (user) {\n    user.setCountry('US');\n    user.setHomeCity('San Francisco');\n    user.setLanguage('en');\n    user.setCustomLocationAttribute('latitude', 37.7749);\n    user.setCustomLocationAttribute('longitude', -122.4194);\n}\n```\n\n#### User Aliases and Subscription Groups\n\n```typescript\nimport { getUser } from \"@braze/web-sdk\";\n\nconst user = getUser();\nif (user) {\n    // Add alias\n    user.addAlias('external_id', '12345');\n\n    // Add to subscription group\n    user.addToSubscriptionGroup('newsletter_subscribers');\n\n    // Remove from subscription group\n    user.removeFromSubscriptionGroup('old_subscribers');\n}\n```\n\n#### User Logout\n\n```typescript\nimport { wipeData } from \"@braze/web-sdk\";\n\n// There is no explicit method to logout. To \"forget\" the current users entirely, use wipeData().\n// This is a complete data wipe (use with caution, this wipes things such as device ID)\nwipeData();\n```\n\n### In-App Messages\n\n#### Automatic Display\n\n```typescript\nimport { automaticallyShowInAppMessages } from \"@braze/web-sdk\";\n\n// Automatically show in-app messages\nautomaticallyShowInAppMessages();\n```\n\n#### Manual Display\n\n```typescript\nimport { subscribeToInAppMessage, showInAppMessage } from \"@braze/web-sdk\";\n\n// Subscribe to in-app messages\nsubscribeToInAppMessage((inAppMessage) =\u003e {\n    // Show the message\n    showInAppMessage(inAppMessage);\n});\n```\n\n#### Custom In-App Message Handling\n\n```typescript\nimport { subscribeToInAppMessage, showInAppMessage } from \"@braze/web-sdk\";\n\nsubscribeToInAppMessage((inAppMessage) =\u003e {\n    // Custom logic before showing\n    if (inAppMessage.getExtras()['priority'] === 'high') {\n        showInAppMessage(inAppMessage);\n    }\n});\n```\n\n#### Log In-App Message Interactions\n\n```typescript\nimport {\n    logInAppMessageClick,\n    logInAppMessageImpression,\n    logInAppMessageButtonClick\n} from \"@braze/web-sdk\";\n\n// Log when user sees the message\nlogInAppMessageImpression(inAppMessage);\n\n// Log when user clicks the message\nlogInAppMessageClick(inAppMessage);\n\n// Log when user clicks a button in the message\nlogInAppMessageButtonClick(inAppMessage, button);\n```\n\n#### Custom HTML In-App Messages\n\n```typescript\nimport { subscribeToInAppMessage, logInAppMessageImpression, logInAppMessageClick } from \"@braze/web-sdk\";\n\n// Don't call automaticallyShowInAppMessages() when using custom rendering\n// braze.automaticallyShowInAppMessages(); // Comment this out\n\nsubscribeToInAppMessage((inAppMessage) =\u003e {\n    // Extract message data\n    const messageData = {\n        title: inAppMessage.getMessage(),\n        body: inAppMessage.getBody(),\n        imageUrl: inAppMessage.getImageUrl(),\n        buttons: inAppMessage.getButtons(),\n        deepLink: inAppMessage.getExtras()['deep_link_url']\n    };\n\n    // Define your own HTML structure, using messageData\n    const customHTML = ` \u003c!-- Add your custom styling and structure --\u003e`;\n\n    /* Render the In-App Message here */\n\n    // Here we naively log an impression once the message is rendered.\n    // Be precise about exactly when you want to log an impression (ie. only the first time it enters the view port).\n    logInAppMessageImpression(inAppMessage);\n});\n\n// Handle button clicks and deep linking\nconst handleButtonClick = (button, inAppMessage) =\u003e {\n    logInAppMessageClick(inAppMessage);\n    // Handle additional click actions (ie. deep linking)\n};\n```\n\n### Content Cards\n\n#### Display Content Cards\n\n```typescript\nimport { showContentCards } from \"@braze/web-sdk\";\n\n// Show content cards in default location\nshowContentCards();\n\n// Show in specific container\nconst container = document.getElementById('content-cards-container');\nshowContentCards(container);\n```\n\n#### Subscribe to Content Cards Updates\n\n```typescript\nimport { subscribeToContentCardsUpdates } from \"@braze/web-sdk\";\n\nsubscribeToContentCardsUpdates((cards) =\u003e {\n    console.log('Content cards updated:', cards);\n    // Display cards or update UI\n});\n```\n\n#### Log Content Card Interactions\n\n```typescript\nimport {\n    logContentCardClick,\n    logContentCardImpressions,\n    logCardDismissal\n} from \"@braze/web-sdk\";\n\n// Log card impressions\nlogContentCardImpressions(cards);\n\n// Log card clicks\nlogContentCardClick(card);\n\n// Log card dismissals\nlogCardDismissal(card);\n```\n\n#### Filter Content Cards\n\n```typescript\nimport { showContentCards } from \"@braze/web-sdk\";\n\n// Show only pinned cards\n// You can also provide a parent element instead of null\nshowContentCards(null, (cards) =\u003e {\n    return cards.filter(card =\u003e card.getIsPinned());\n});\n```\n\n#### Request Content Cards Refresh\n\n```typescript\nimport { requestContentCardsRefresh } from \"@braze/web-sdk\";\n\nrequestContentCardsRefresh(\n    () =\u003e console.log('Content cards refreshed'),\n    () =\u003e console.log('Failed to refresh content cards')\n);\n```\n\n#### Custom Content Cards\n\n```typescript\nimport { subscribeToContentCardsUpdates, logContentCardClick, logContentCardImpressions, requestContentCardsRefresh } from \"@braze/web-sdk\";\n\n// State for impression de-duping\nconst loggedImpressions = new Set();\nconst idToCard = new Map();\n\nsubscribeToContentCardsUpdates((cards) =\u003e {\n    // Build cards one by one\n    cards.getCards().forEach(card =\u003e {\n        // Skip control cards\n        if (card.getIsControl()) return;\n\n        // Extract card data\n        const cardData = {\n            id: card.getId(),\n            title: card.getTitle(),\n            description: card.getDescription(),\n            imageUrl: card.getImageUrl(),\n            url: card.getUrl(),\n            extras: card.getExtras()\n        };\n\n        // Define your own HTML structure, using cardData\n        const customHTML = ` \u003c!-- Add your custom styling and structure --\u003e`;\n\n        /* Render each card here */\n\n        // Basic observer for impression logging.\n        // Be precise about exactly when you want to log an impression (ie. only the first time it enters the view port).\n        const observer = new IntersectionObserver((entries) =\u003e {\n            entries.forEach(entry =\u003e {\n                if (entry.isIntersecting) {\n                    logContentCardImpressions([card]);\n                }\n            });\n        });\n\n        // Observe card element when rendered\n        // observer.observe(cardElement);\n    });\n});\n\n// Handle card clicks\nconst handleCardClick = (card) =\u003e {\n    logContentCardClick(card);\n    // Handle additional click actions (ie. navigation)\n};\n\n```\n\n### Push Notifications\n\n#### Request Push Permission\n\n```typescript\nimport { requestPushPermission } from \"@braze/web-sdk\";\n\nrequestPushPermission(\n    () =\u003e console.log('Push permission granted'),\n    () =\u003e console.log('Push permission denied')\n);\n```\n\n#### Check Push Support\n\n```typescript\nimport { isPushSupported, isPushPermissionGranted } from \"@braze/web-sdk\";\n\nif (isPushSupported()) {\n    if (isPushPermissionGranted()) {\n        console.log('Push notifications are enabled');\n    } else {\n        console.log('Push permission not granted');\n    }\n}\n```\n\n#### Unregister Push\n\n```typescript\nimport { unregisterPush } from \"@braze/web-sdk\";\n\nunregisterPush(\n    () =\u003e console.log('Successfully unregistered'),\n    () =\u003e console.log('Failed to unregister')\n);\n```\n\n### Feature Flags\n\n#### Get Feature Flag\n\n```typescript\nimport { getFeatureFlag } from \"@braze/web-sdk\";\n\nconst featureFlag = getFeatureFlag('new_checkout_flow');\nif (featureFlag) {\n    const isEnabled = featureFlag.getBooleanProperty('enabled', false);\n    const rolloutPercentage = featureFlag.getNumberProperty('rollout_percentage', 0);\n\n    if (isEnabled) {\n        // Enable new checkout flow\n    }\n}\n```\n\n#### Subscribe to Feature Flag Updates\n\n```typescript\nimport { subscribeToFeatureFlagsUpdates } from \"@braze/web-sdk\";\n\nsubscribeToFeatureFlagsUpdates((featureFlags) =\u003e {\n    featureFlags.forEach(flag =\u003e {\n        console.log(`Feature flag ${flag.getId()}: ${flag.getBooleanProperty('enabled')}`);\n    });\n});\n```\n\n#### Log Feature Flag Impressions\n\n```typescript\nimport { logFeatureFlagImpression } from \"@braze/web-sdk\";\n\nconst featureFlag = getFeatureFlag('new_feature');\nif (featureFlag) {\n    logFeatureFlagImpression(featureFlag);\n}\n```\n\n#### Request Feature Flags Refresh\n\n```typescript\nimport { refreshFeatureFlags } from \"@braze/web-sdk\";\n\nrefreshFeatureFlags(\n    () =\u003e console.log('Feature flags refreshed'),\n    () =\u003e console.log('Failed to refresh feature flags')\n);\n```\n\n### Banners\n\n#### Get and Display Banners\n\n```typescript\nimport { getBanner, insertBanner } from \"@braze/web-sdk\";\n\nconst banner = getBanner('homepage_banner');\nif (banner) {\n    // Insert banner into specific element\n    const container = document.getElementById('banner-container');\n    insertBanner(banner, container);\n}\n```\n\n#### Subscribe to Banner Updates\n\n```typescript\nimport { subscribeToBannersUpdates } from \"@braze/web-sdk\";\n\nsubscribeToBannersUpdates((banners) =\u003e {\n    Object.entries(banners).forEach(([placementId, banner]) =\u003e {\n        if (banner) {\n            console.log(`Banner for ${placementId}:`, banner);\n\n            // Insert banner into specific element\n            const container = document.getElementById(`banner-container-${placementId}`);\n            insertBanner(banner, container);\n        }\n    });\n});\n```\n\n#### Request Banner Refresh\n\n```typescript\nimport { requestBannersRefresh } from \"@braze/web-sdk\";\n\nrequestBannersRefresh(\n    [\"placement_1\", \"placement_2\"],\n    () =\u003e console.log('Banners refreshed'),\n    () =\u003e console.log('Failed to refresh banners')\n);\n```\n\n### Analytics \u0026 Events\n\n#### Log Custom Events\n\n```typescript\nimport { logCustomEvent } from \"@braze/web-sdk\";\n\n// Simple event\nlogCustomEvent('button_clicked');\n\n// Event with properties\nlogCustomEvent('purchase', {\n    product_id: '123',\n    price: 29.99,\n    currency: 'USD'\n});\n```\n\n#### Log Purchases\n\n```typescript\nimport { logPurchase } from \"@braze/web-sdk\";\n\nlogPurchase('product-123', 29.99, 'USD', 1, {\n    category: 'electronics',\n    brand: 'Apple'\n});\n```\n\n#### Request Data Flush\n\n```typescript\nimport { requestImmediateDataFlush } from \"@braze/web-sdk\";\n\n// Force immediate data send\nrequestImmediateDataFlush();\n```\n\n### Session Management\n\n#### Open Session\n\n```typescript\nimport { openSession } from \"@braze/web-sdk\";\n\n// Start a new session\nopenSession();\n```\n\n#### Check SDK Status\n\n```typescript\nimport { isInitialized, isDisabled } from \"@braze/web-sdk\";\n\nif (isInitialized()) {\n    console.log('SDK is initialized');\n\n    if (isDisabled()) {\n        console.log('SDK is disabled');\n    }\n}\n```\n\n#### Enable/Disable SDK\n\n```typescript\nimport { enableSDK, disableSDK } from \"@braze/web-sdk\";\n\n// Disable SDK\ndisableSDK();\n\n// Re-enable SDK\nenableSDK();\n```\n\n### Data Management\n\n#### Wipe Data\n\n```typescript\nimport { wipeData } from \"@braze/web-sdk\";\n\n// Remove all locally stored data\nwipeData();\n```\n\n#### Destroy SDK\n\n```typescript\nimport { destroy } from \"@braze/web-sdk\";\n\n// Clean up SDK resources\ndestroy();\n```\n\n#### Get Device ID\n\n```typescript\nimport { getDeviceId } from \"@braze/web-sdk\";\n\nconst deviceId = getDeviceId();\nconsole.log('Device ID:', deviceId);\n```\n\n#### SDK Authentication\n\n```typescript\nimport { setSdkAuthenticationSignature } from \"@braze/web-sdk\";\n\n// Set authentication signature\nsetSdkAuthenticationSignature('your-signature-here');\n```\n\n#### Subscribe to Authentication Failures\n\n```typescript\nimport { subscribeToSdkAuthenticationFailures } from \"@braze/web-sdk\";\n\nsubscribeToSdkAuthenticationFailures((error) =\u003e {\n    console.log('Authentication failed:', error);\n    // Provide new signature\n    setSdkAuthenticationSignature('new-signature');\n});\n```\n\n---\n\n## Integration Patterns\n\n### SSR Frameworks\n\nIf you use a Server-Side Rendering (SSR) framework such as Next.js, you may encounter errors because the SDK is meant to be run in a browser environment. You can resolve these issues by dynamically importing the SDK.\n\nYou can retain the benefits of tree-shaking when doing so by exporting the parts of the SDK that you need in a separate file and then dynamically importing that file into your component.\n\n```javascript\n// MyComponent/braze-exports.js\n// export the parts of the SDK you need here\nexport { initialize, openSession } from \"@braze/web-sdk\";\n\n// MyComponent/MyComponent.js\n// import the functions you need from the braze exports file\nuseEffect(() =\u003e {\n    import(\"./braze-exports.js\").then(({ initialize, openSession }) =\u003e {\n        initialize(\"YOUR-API-KEY-HERE\", {\n            baseUrl: \"YOUR-SDK-ENDPOINT\",\n            enableLogging: true,\n        });\n        openSession();\n    });\n}, []);\n```\n\nAlternatively, if you're using webpack to bundle your app, you can take advantage of its magic comments to dynamically import only the parts of the SDK that you need.\n\n```javascript\n// MyComponent.js\nuseEffect(() =\u003e {\n    import(\n        /* webpackExports: [\"initialize\", \"openSession\"] */\n        \"@braze/web-sdk\"\n    ).then(({ initialize, openSession }) =\u003e {\n        initialize(\"YOUR-API-KEY-HERE\", {\n            baseUrl: \"YOUR-SDK-ENDPOINT\",\n            enableLogging: true,\n        });\n        openSession();\n    });\n}, []);\n```\n\n### Vite\n\nIf you use Vite and see a warning around circular dependencies or `Uncaught TypeError: Class extends value undefined is not a constructor or null`, you may need to exclude the Braze SDK from its dependency discovery:\n\n```javascript\nexport default {\n    optimizeDeps: {\n        exclude: ['@braze/web-sdk']\n    }\n}\n```\n\n### Jest Framework\n\nWhen using Jest, you may see an error similar to `SyntaxError: Unexpected token 'export'`. To fix this, adjust your configuration in `package.json` to ignore the Braze SDK:\n\n```json\n{\n  \"jest\": {\n    \"transformIgnorePatterns\": [\n      \"/node_modules/(?!@braze)\"\n    ]\n  }\n}\n```\n\n### Asynchronous Module Definition (AMD)\n\n#### Disable AMD Support\n\nIf your site uses RequireJS or another AMD module-loader, but you prefer to load the Braze Web SDK through the CDN, you can load a version of the library that does not include AMD support. This version of the library can be loaded from the CDN location: `https://js.appboycdn.com/web-sdk/6.3/braze.no-amd.min.js`\n\n#### Module Loader\n\nIf you use RequireJS or other AMD module-loaders, we recommend self-hosting a copy of our library and referencing it as you would with other resources:\n\n```javascript\nrequire(['path/to/braze.min.js'], function(braze) {\n  braze.initialize('YOUR-API-KEY-HERE', { baseUrl: 'YOUR-SDK-ENDPOINT' });\n  braze.automaticallyShowInAppMessages();\n  braze.openSession();\n});\n```\n\n### Accelerated Mobile Pages (AMP)\n\nFor AMP integration, you'll need to:\n\n1. **Include AMP web push script**: Add the async script tag to your head\n2. **Add subscription widgets**: Add widgets to allow users to subscribe/unsubscribe\n3. **Add helper files**: Include `helper-iframe.html` and `permission-dialog.html`\n4. **Create service worker**: Add the Braze service worker file\n5. **Configure AMP web push element**: Add the `amp-web-push` element with your API key and base URL as query parameters\n\nFor detailed AMP integration instructions, see the [Braze Developer Guide](https://www.braze.com/docs/developer_guide/sdk_integration/?sdktab=web#amp).\n\n### Electron\n\nElectron does not officially support web push notifications (see: this [GitHub issue](https://github.com/electron/electron/issues/6697)). There are other [open source workarounds](https://github.com/MatthieuLemoine/electron-push-receiver) you may try that have not been tested by Braze.\n\n### CDN Integration\n\n- **Script Loading**: Initialize after the script tag loads by placing initialization code after the script tag, or use the script tag's `onload` event handler\n- **Global Access**: SDK is available as `window.braze` when loaded via CDN\n\n### Service Worker (Push Notifications)\n\n- **Required**: Must include Braze service worker for push notifications to work\n- **Registration**: Register the service worker in your website code using `navigator.serviceWorker.register()`\n- **Push Permissions**: Call `braze.requestPushPermission()` in response to user interactions (e.g., button clicks). Use soft push prompts (custom UI) before requesting browser permission\n\n### Tag Managers\n\n#### Tealium iQ\n\nTealium iQ offers a basic turnkey Braze integration. To configure the integration, search for Braze in the Tealium Tag Management interface, and provide the Web SDK API key from your dashboard. For more details or in-depth Tealium configuration support, check out our [integration documentation](https://www.braze.com/docs/partners/data_and_infrastructure_agility/customer_data_platform/tealium/#about-tealium) or reach out to your Tealium account manager.\n\n#### Other Tag Managers\n\nBraze may also be compatible with other tag management solutions by following our integration instructions within a custom HTML tag. Reach out to a Braze representative if you need help evaluating these solutions.\n\n---\n\n## Libraries\n\n| Name | Description | npm | CDN URL\n| ---- | ----------- | --- | -------\n| Full | Full SDK with UI. When using the npm version, Javascript bundlers will remove any unused code including the UI. | `@braze/web-sdk` | https://js.appboycdn.com/web-sdk/6.8/braze.min.js\n| Core | Contains the SDK without UI. You will need to implement your own UI for In-App Messaging and Content Cards when using this version of the SDK. Our UI elements are fully customizable via css, so we generally recommend integration of the full library instead. | N/A | https://js.appboycdn.com/web-sdk/6.8/braze.core.min.js\n| No-AMD | Contains the full SDK without AMD support. This is useful if your site uses RequireJS or another AMD module-loader, but you prefer to load the SDK through the CDN. | N/A | https://js.appboycdn.com/web-sdk/6.8/braze.no-amd.min.js\n\n## Supported Browsers\n\n- Modern Chromium based browsers (Chrome, Edge, Opera)\n- Firefox\n- Safari\n\n## Debugging \u0026 Troubleshooting\n\nPass the option `enableLogging: true` to the initialize function (`braze.initialize('YOUR-API-KEY-HERE', { baseUrl: 'YOUR-SDK-ENDPOINT', enableLogging: true });`) to cause Braze to log to the javascript console. This is valuable for development but is visible to all users, so remove this option or [provide an alternate logger](https://js.appboycdn.com/web-sdk/6.8/doc/modules/braze.html#setlogger) before you release your page to production.\n\n## Font Awesome\n\nBraze uses [Font Awesome](http://fortawesome.github.io/Font-Awesome/) 4.7.0 for in-app message icons. To disable loading Font Awesome, use the `doNotLoadFontAwesome` initialization option. Check out the [cheat sheet](http://fortawesome.github.io/Font-Awesome/cheatsheet/) to browse available icons.\n\n## Additional Resources\n\n- [Braze Developer Guide](https://www.braze.com/docs/developer_guide/sdk_integration/?sdktab=web)\n- [SDK Documentation](https://js.appboycdn.com/web-sdk/latest/doc/modules/braze.html)\n- [Sample Builds](./sample-builds/)\n\n## Contact\n\nIf you have questions, please contact [support@braze.com](mailto:support@braze.com).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbraze-inc%2Fbraze-web-sdk","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbraze-inc%2Fbraze-web-sdk","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbraze-inc%2Fbraze-web-sdk/lists"}