@splunk/dashboard-studio-extension
v1.0.1
Published
Dashboard Extensions for Splunk Dashboard Studio.
Readme
@splunk/dashboard-studio-extension
API for building custom visualizations that run inside Splunk Dashboard Studio as sandboxed iframe extensions.
Custom visualizations communicate with the Studio host page via postMessage. This package abstracts that entirely — you subscribe to state updates and call methods; the messaging layer is invisible.
Installation
npm install @splunk/dashboard-studio-extensionFor React projects, React and React DOM are required as peer dependencies:
npm install @splunk/dashboard-studio-extension react react-domChoosing an Approach
| | JavaScript | React |
|---|---|---|
| Import from | @splunk/dashboard-studio-extension | @splunk/dashboard-studio-extension/react |
| API style | Event listeners + getters | Hooks + context provider |
| Extra dependencies | None | react, react-dom |
JavaScript Usage
Import VisualizationAPI and use its listeners and methods directly.
import { VisualizationAPI } from '@splunk/dashboard-studio-extension';
// Subscribe to data source updates
VisualizationAPI.addDataSourcesListener(
({ dataSources, loading }) => {
if (loading || !dataSources?.primary?.data) return;
const { fields, columns } = dataSources.primary.data;
render(fields, columns);
},
{ invokeImmediately: true }
);
// Subscribe to option changes
VisualizationAPI.addOptionsListener(({ options }) => {
applyOptions(options);
});
// Update options (edit mode only)
VisualizationAPI.setOptions({ barColor: '#ff0000' });Data Shape
Search results arrive in columnar format:
{
fields: [{ name: 'host' }, { name: 'count' }],
columns: [['web-01', 'web-02'], ['42', '17']],
}
// columns[fieldIndex][rowIndex] — all values are stringsAlways pass { invokeImmediately: true } to addDataSourcesListener so the callback fires immediately with the current state when registered.
React Usage
Wrap your visualization in VisualizationExtensionProvider and access state through hooks.
import {
VisualizationExtensionProvider,
useDataSources,
useOptions,
} from '@splunk/dashboard-studio-extension/react';
import { createRoot } from 'react-dom/client';
function MyVisualization() {
const { dataSources, loading } = useDataSources();
const { options } = useOptions();
if (loading) return <div>Loading...</div>;
const data = dataSources?.primary?.data;
if (!data) return <div>No data</div>;
return <div style={{ color: options.color ?? '#000' }}>...</div>;
}
createRoot(document.getElementById('root')).render(
<VisualizationExtensionProvider>
<MyVisualization />
</VisualizationExtensionProvider>
);Alternatively, use useVisualizationExtension to access all state from a single hook inside the provider:
import { useVisualizationExtension } from '@splunk/dashboard-studio-extension/react';
function MyVisualization() {
const { dataSources, loading, options, theme, mode } = useVisualizationExtension();
// ...
}API Reference
JavaScript — VisualizationAPI
Data Sources
| Method | Description |
|---|---|
| addDataSourcesListener(callback, options?) | Subscribe to data source updates. Pass { invokeImmediately: true } to receive the current state immediately on registration. Returns a cleanup function. |
| getDataSources() | Returns the current { dataSources, loading } state. |
Options
| Method | Description |
|---|---|
| addOptionsListener(callback) | Subscribe to option changes. Returns a cleanup function. |
| getOptions() | Returns the current { options } state. |
| setOptions(options) | Updates visualization options. Only permitted in edit mode. |
Dimensions
| Method | Description |
|---|---|
| addDimensionsListener(callback) | Subscribe to dimension changes. Returns a cleanup function. |
| getDimensions() | Returns the current { width, height } state. |
Mode
| Method | Description |
|---|---|
| addModeListener(callback) | Subscribe to mode changes. Returns a cleanup function. |
| getMode() | Returns the current { mode } state. mode is 'view' or 'edit'. |
Theme
| Method | Description |
|---|---|
| addThemeListener(callback) | Subscribe to theme changes. Returns a cleanup function. |
| getTheme() | Returns the current { theme } state. |
Tokens
| Method | Description |
|---|---|
| addTokensListener(callback) | Subscribe to token changes. Returns a cleanup function. |
| getTokens() | Returns the current { tokens } state. |
Drilldown
| Method | Description |
|---|---|
| addDrilldownListener({ node, action, payloadCallback }) | Registers a DOM node as a drilldown target. |
| triggerDrilldown(drilldownArgs) | Programmatically triggers a drilldown action. |
Error
| Method | Description |
|---|---|
| addErrorListener(callback) | Subscribe to error state changes. Returns a cleanup function. |
| getError() | Returns the current error state. |
| setError(message) | Sets an error message displayed in the Studio UI. |
| clearError() | Clears the current error. |
React — @splunk/dashboard-studio-extension/react
Hooks
| Hook | Returns |
|---|---|
| useDataSources() | { dataSources, loading } |
| useOptions() | { options, setOptions } |
| useDimensions() | { width, height } |
| useMode() | { mode } |
| useTheme() | { theme } |
| useTokens() | { tokens } |
| useError() | { error, setError, clearError } |
| useVisualizationExtension() | All of the above combined (must be used inside VisualizationExtensionProvider) |
Components
| Component | Description |
|---|---|
| VisualizationExtensionProvider | Context provider that makes all hook values available via useVisualizationExtension. Wrap your root component with this. |
Scaffolding a New Project
Use @splunk/create to scaffold a new custom visualization project:
mkdir my-viz
cd my-viz
npm create @splunk/create@latestWhen prompted, select the dashboard-studio-extension mode and choose either the JavaScript or React template.
Architecture
Custom visualizations run inside a sandboxed <iframe> embedded in the dashboard. Dashboard Studio injects a global DashboardExtensionAPI object into the iframe at runtime, which this package wraps into a clean subscribe/get API.
State flows one way: Studio → iframe via postMessage. The visualization pushes state back only via setOptions (edit mode) and drilldown actions.
Because the visualization runs in an isolated iframe:
window.parentis not accessible- CSS custom properties from the host page are not inherited
- The
@splunk/themestoken values are not available at runtime — use hardcoded enterprise theme values for styling
License
Copyright 2026 Splunk Inc.
Use of this software is governed by the Splunk General Terms. See LICENSE for details.
