docs: Configure Segment (#8996)

This commit is contained in:
Ronnie Miller 2025-07-10 21:39:19 -07:00 committed by GitHub
commit c38df91841
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 152 additions and 25 deletions

View file

@ -85,6 +85,7 @@ jobs:
env:
BASE_URL: /langflow-drafts/${{ steps.extract_branch.outputs.draft_directory }}
FORCE_COLOR: 0 # Disable color output
SEGMENT_PUBLIC_WRITE_KEY: ${{ vars.DOCS_DRAFT_SEGMENT_PUBLIC_WRITE_KEY }}
- name: Check Build Result
id: buildLogFail

View file

@ -25,6 +25,8 @@ jobs:
run: cd docs && yarn install
- name: Build website
run: cd docs && yarn build
env:
SEGMENT_PUBLIC_WRITE_KEY: ${{ vars.DOCS_PROD_SEGMENT_PUBLIC_WRITE_KEY }}
# Popular action to deploy to GitHub Pages:
# Docs: https://github.com/peaceiris/actions-gh-pages#%EF%B8%8F-docusaurus

View file

@ -130,6 +130,7 @@ const config = {
plugins: [
["docusaurus-node-polyfills", { excludeAliases: ["console"] }],
"docusaurus-plugin-image-zoom",
["./src/plugins/segment", { segmentPublicWriteKey: process.env.SEGMENT_PUBLIC_WRITE_KEY, allowedInDev: true }],
[
"@docusaurus/plugin-client-redirects",
{
@ -335,6 +336,8 @@ const config = {
className: "header-github-link",
target: "_blank",
rel: null,
'data-event': 'Docs.langflow.org - Social Clicked',
'data-platform': 'github'
},
{
position: "right",
@ -342,6 +345,8 @@ const config = {
className: "header-twitter-link",
target: "_blank",
rel: null,
'data-event': 'Docs.langflow.org - Social Clicked',
'data-platform': 'x'
},
{
position: "right",
@ -349,6 +354,8 @@ const config = {
className: "header-discord-link",
target: "_blank",
rel: null,
'data-event': 'Docs.langflow.org - Social Clicked',
'data-platform': 'discord'
},
],
},

View file

@ -0,0 +1,15 @@
import ExecutionEnvironment from '@docusaurus/ExecutionEnvironment';
// Client module for tracking page views on route changes
export function onRouteDidUpdate({location, previousLocation}) {
// Only track page views in the browser and when the path actually changes
if (
ExecutionEnvironment.canUseDOM &&
previousLocation &&
location.pathname !== previousLocation.pathname &&
window.analytics &&
window.analytics.page
) {
window.analytics.page();
}
}

View file

@ -0,0 +1,81 @@
import ExecutionEnvironment from '@docusaurus/ExecutionEnvironment';
let isDataAttributeTrackingInitialized = false;
/**
* Automatic click tracking using data attributes for Docusaurus
*
* Usage: Add data-event and other data-* attributes to any clickable element.
* The tracker will automatically send events to Segment when clicked.
*
* Example in navbar config:
* {
* href: "https://github.com/langflow-ai/langflow",
* 'data-event': 'GitHub Link Clicked',
* 'data-source': 'navbar',
* 'data-category': 'social'
* }
*
* This will automatically call:
* window.analytics.track("GitHub Link Clicked", {
* source: "navbar",
* category: "social",
* url: "https://github.com/langflow-ai/langflow",
* page: "/current-page"
* })
*/
function initializeDataAttributeTracking() {
// Only run on client side and prevent duplicate initialization
if (!ExecutionEnvironment.canUseDOM || isDataAttributeTrackingInitialized) return;
const handleClick = (event) => {
const target = event.target;
const trackingElement = target.closest('[data-event]');
if (!trackingElement) return;
const eventName = trackingElement.dataset.event;
if (!eventName) return;
// Extract all data-* attributes (except data-event itself)
const properties = {};
Object.keys(trackingElement.dataset).forEach(key => {
if (key !== 'event') {
// Convert camelCase to snake_case for consistency
const snakeKey = key.replace(/([A-Z])/g, '_$1').toLowerCase();
properties[snakeKey] = trackingElement.dataset[key];
}
});
// Track the event
if (window.analytics && typeof window.analytics.track === 'function') {
window.analytics.track(eventName, properties);
} else {
console.warn('Analytics not available for tracking:', eventName, properties);
}
};
// Remove existing listener if it exists
document.removeEventListener('click', handleClick);
// Add the new listener
document.addEventListener('click', handleClick);
// Mark as initialized
isDataAttributeTrackingInitialized = true;
}
// Initialize on DOM ready
if (ExecutionEnvironment.canUseDOM) {
if (document.readyState === 'loading') {
document.addEventListener('DOMContentLoaded', initializeDataAttributeTracking);
} else {
initializeDataAttributeTracking();
}
// Re-initialize on route changes for SPA navigation
window.addEventListener('popstate', () => {
setTimeout(initializeDataAttributeTracking, 100);
});
}

View file

@ -0,0 +1,40 @@
// Custom Docusaurus plugin to inject Segment analytics
function pluginSegment(context, options = {}) {
const isProd = process.env.NODE_ENV === "production" || options.allowedInDev;
const segmentPublicWriteKey = options.segmentPublicWriteKey;
if (!segmentPublicWriteKey) {
console.warn('Segment plugin: No write key provided. Analytics will not be initialized.');
return { name: 'docusaurus-plugin-segment' };
}
return {
name: 'docusaurus-plugin-segment',
getClientModules() {
return isProd ? [require.resolve('./analytics-page'), require.resolve('./data-attribute-tracking')] : [];
},
injectHtmlTags() {
if (!isProd) {
return {};
}
return {
headTags: [
{
tagName: 'script',
innerHTML: `
!function(){var i="analytics",analytics=window[i]=window[i]||[];if(!analytics.initialize)if(analytics.invoked)window.console&&console.error&&console.error("Segment snippet included twice.");else{analytics.invoked=!0;analytics.methods=["trackSubmit","trackClick","trackLink","trackForm","pageview","identify","reset","group","track","ready","alias","debug","page","screen","once","off","on","addSourceMiddleware","addIntegrationMiddleware","setAnonymousId","addDestinationMiddleware","register"];analytics.factory=function(e){return function(){if(window[i].initialized)return window[i][e].apply(window[i],arguments);var n=Array.prototype.slice.call(arguments);if(["track","screen","alias","group","page","identify"].indexOf(e)>-1){var c=document.querySelector("link[rel='canonical']");n.push({__t:"bpc",c:c&&c.getAttribute("href")||void 0,p:location.pathname,u:location.href,s:location.search,t:document.title,r:document.referrer})}n.unshift(e);analytics.push(n);return analytics}};for(var n=0;n<analytics.methods.length;n++){var key=analytics.methods[n];analytics[key]=analytics.factory(key)}analytics.load=function(key,n){var t=document.createElement("script");t.type="text/javascript";t.async=!0;t.setAttribute("data-global-segment-analytics-key",i);t.src="https://cdn.segment.com/analytics.js/v1/" + key + "/analytics.min.js";var r=document.getElementsByTagName("script")[0];r.parentNode.insertBefore(t,r);analytics._loadOptions=n};analytics._writeKey="${segmentPublicWriteKey}";;analytics.SNIPPET_VERSION="5.2.0";
analytics.load("${segmentPublicWriteKey}");
analytics.page();
}}();
`,
},
],
};
},
};
}
module.exports = pluginSegment;

View file

@ -3894,7 +3894,7 @@ ccount@^2.0.0:
resolved "https://registry.yarnpkg.com/ccount/-/ccount-2.0.1.tgz#17a3bf82302e0870d6da43a01311a8bc02a3ecf5"
integrity sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==
chalk@^4.0.0, chalk@^4.1.0, chalk@^4.1.2:
chalk@^4.0.0, chalk@^4.1.2:
version "4.1.2"
resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01"
integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==
@ -4394,7 +4394,7 @@ create-require@^1.1.0:
resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333"
integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==
cross-spawn@^7.0.0, cross-spawn@^7.0.3:
cross-spawn@^7.0.3, cross-spawn@^7.0.6:
version "7.0.6"
resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.6.tgz#8a58fe78f00dcd70c370451759dfbfaf03e8ee9f"
integrity sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==
@ -4617,7 +4617,7 @@ debounce@^1.2.1:
resolved "https://registry.yarnpkg.com/debounce/-/debounce-1.2.1.tgz#38881d8f4166a5c5848020c11827b834bcb3e0a5"
integrity sha512-XRRe6Glud4rd/ZGQfiV1ruXSfbvfJedlV9Y6zOlP+2K04vBYiJEte6stfFkCP03aMnY5tsipamumUjL14fofug==
debug@2.6.9, debug@^2.6.0:
debug@2.6.9:
version "2.6.9"
resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f"
integrity sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==
@ -5826,7 +5826,7 @@ globals@^11.1.0:
resolved "https://registry.yarnpkg.com/globals/-/globals-11.12.0.tgz#ab8795338868a0babd8525758018c2a7eb95c42e"
integrity sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==
globby@^11.0.1, globby@^11.0.4, globby@^11.1.0:
globby@^11.1.0:
version "11.1.0"
resolved "https://registry.yarnpkg.com/globby/-/globby-11.1.0.tgz#bd4be98bb042f83d796f7e3811991fbe82a0d34b"
integrity sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==
@ -8380,7 +8380,7 @@ minimalistic-crypto-utils@^1.0.1:
resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a"
integrity sha512-JIYlbt6g8i5jKfJ3xz7rF0LXmv2TkDxBLUkiBeZ7bAx4GnnNMr8xFpGnOxn6GhTEHx3SjRrZEoU+j04prX1ktg==
minimatch@3.1.2, minimatch@^3.0.4, minimatch@^3.1.1:
minimatch@3.1.2, minimatch@^3.1.1:
version "3.1.2"
resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b"
integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==
@ -10325,18 +10325,6 @@ regenerate@^1.4.2:
resolved "https://registry.yarnpkg.com/regenerate/-/regenerate-1.4.2.tgz#b9346d8827e8f5a32f7ba29637d398b69014848a"
integrity sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==
regenerator-runtime@^0.14.0:
version "0.14.1"
resolved "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.1.tgz"
integrity sha512-dYnhHh0nJoMfnkZs6GmmhFknAGRrLznOu5nc9ML+EJxGvrx6H7teuevqVqCuPcPK//3eDrrjQhehXVx9cnkGdw==
regenerator-transform@^0.15.2:
version "0.15.2"
resolved "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.15.2.tgz"
integrity sha512-hfMp2BoF0qOk3uc5V20ALGDS2ddjQaLrdl7xrGXvAIow7qeWRM2VA2HuCHkUKk9slq3VwEwLNK3DFBqDfPGYtg==
dependencies:
"@babel/runtime" "^7.8.4"
regexpu-core@^6.2.0:
version "6.2.0"
resolved "https://registry.yarnpkg.com/regexpu-core/-/regexpu-core-6.2.0.tgz#0e5190d79e542bf294955dccabae04d3c7d53826"
@ -11240,7 +11228,7 @@ stringify-object@^3.3.0:
is-obj "^1.0.1"
is-regexp "^1.0.0"
"strip-ansi-cjs@npm:strip-ansi@^6.0.1", strip-ansi@^6.0.0, strip-ansi@^6.0.1:
"strip-ansi-cjs@npm:strip-ansi@^6.0.1":
version "6.0.1"
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
@ -12263,13 +12251,6 @@ which-typed-array@^1.1.16, which-typed-array@^1.1.2:
gopd "^1.2.0"
has-tostringtag "^1.0.2"
which@^1.3.1:
version "1.3.1"
resolved "https://registry.yarnpkg.com/which/-/which-1.3.1.tgz#a45043d54f5805316da8d62f9f50918d3da70b0a"
integrity sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==
dependencies:
isexe "^2.0.0"
which@^2.0.1:
version "2.0.2"
resolved "https://registry.yarnpkg.com/which/-/which-2.0.2.tgz#7c6a8dd0a636a0327e10b59c9286eee93f3f51b1"