@wisdomai/react 0.0.8 → 0.0.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/AGENTS.md CHANGED
@@ -8,13 +8,16 @@ and interactive filtering. This file is a condensed, actionable companion to
8
8
  ## Install
9
9
 
10
10
  ```bash
11
- npm install @wisdomai/react
11
+ npm install @wisdomai/react \
12
+ @mui/material@^7 @mui/x-date-pickers@^7 \
13
+ @emotion/react@^11 @emotion/styled@^11 \
14
+ highcharts@^12 highcharts-react-official@^3 \
15
+ graphql@^16 luxon@^3
12
16
  ```
13
17
 
14
- The host app must provide these peer dependencies: `react` (>=18), `react-dom`
15
- (>=18), `@mui/material` (^7), `@mui/x-date-pickers` (^7), `@emotion/react` (^11),
16
- `@emotion/styled` (^11), `highcharts` (^12), `highcharts-react-official` (^3),
17
- `graphql` (^16), `luxon` (^3).
18
+ Keep the version pins an unpinned `npm install @mui/material …` resolves to
19
+ the latest major and fails `ERESOLVE` against the SDK's peer ranges. The host
20
+ app must additionally provide `react` (>=18) and `react-dom` (>=18).
18
21
 
19
22
  `@wisdomai/react` is **ESM-only**. Pure-CommonJS callers must use dynamic
20
23
  `import()`.
package/README.md CHANGED
@@ -20,10 +20,14 @@ The layout, data, and filter specs come from the dashboard you built in Wisdom;
20
20
  ## Installation
21
21
 
22
22
  ```bash
23
- npm install @wisdomai/react
23
+ npm install @wisdomai/react \
24
+ @mui/material@^7 @mui/x-date-pickers@^7 \
25
+ @emotion/react@^11 @emotion/styled@^11 \
26
+ highcharts@^12 highcharts-react-official@^3 \
27
+ graphql@^16 luxon@^3
24
28
  ```
25
29
 
26
- Provide these peer dependencies from your app: `react` (>=18), `react-dom` (>=18), `@mui/material` (^7), `@mui/x-date-pickers` (^7), `@emotion/react` (^11), `@emotion/styled` (^11), `highcharts` (^12), `highcharts-react-official` (^3), `graphql` (^16), `luxon` (^3).
30
+ Keep the version pins — installing these peers unpinned resolves to their latest majors and fails `ERESOLVE` against the SDK's peer ranges. Your app must additionally provide `react` (>=18) and `react-dom` (>=18).
27
31
 
28
32
  > Using an AI coding agent? The package ships an [`AGENTS.md`](./AGENTS.md) with condensed, copy-ready setup steps — point your agent at it to scaffold the integration.
29
33
 
@@ -223,3 +227,15 @@ All errors thrown by the client extend `WisdomError`:
223
227
  - `WisdomAuthError` — JWT rejected or expired (HTTP 401/403, or GraphQL `UNAUTHENTICATED` / `INVALID_TOKEN`). Consumers should call `refresh()` to re-fetch a token.
224
228
  - `WisdomDashboardNotFoundError` — `dashboards.get(id)` could not return a dashboard because the ID does not exist or the caller lacks access (server emits `NOT_FOUND` or `FORBIDDEN`).
225
229
  - `WisdomError` — everything else (network failure, 5xx, malformed response, uncategorized backend errors). Carries an optional `cause` and, for GraphQL-level failures, an `errors` array.
230
+
231
+ ## Releasing
232
+
233
+ The SDK ships a frozen set of GraphQL operations to consumers who cannot re-run codegen, so a backend schema change that removes a field one of those operations uses will hard-fail every dashboard with HTTP 400. To guard against that, the published operation set is snapshotted to `published-operations.graphql` and the `sdk-schema-compat` CI gate validates it against the live app-server schema on every change.
234
+
235
+ When cutting a release, after bumping the version:
236
+
237
+ ```bash
238
+ pnpm run sdk:snapshot-operations # from the javascript/ root — refreshes published-operations.graphql
239
+ ```
240
+
241
+ Commit the refreshed snapshot alongside the version bump, then publish. Skipping this only weakens protection for newly-added operations; it never produces a false CI failure.
@@ -0,0 +1,20 @@
1
+ import { Component, type ErrorInfo, type ReactNode } from 'react';
2
+ interface SdkErrorBoundaryProps {
3
+ /** Rendered in place of the children after a render error. */
4
+ fallback: (error: Error) => ReactNode;
5
+ children: ReactNode;
6
+ }
7
+ interface SdkErrorBoundaryState {
8
+ error: Error | null;
9
+ }
10
+ /**
11
+ * Internal boundary so a render error in one SDK widget degrades to an error
12
+ * card instead of unmounting the embedding host's entire React tree.
13
+ */
14
+ export declare class SdkErrorBoundary extends Component<SdkErrorBoundaryProps, SdkErrorBoundaryState> {
15
+ state: SdkErrorBoundaryState;
16
+ static getDerivedStateFromError(error: Error): SdkErrorBoundaryState;
17
+ componentDidCatch(error: Error, info: ErrorInfo): void;
18
+ render(): ReactNode;
19
+ }
20
+ export {};
@@ -3,4 +3,4 @@ export interface DashboardWidgetProps {
3
3
  /** Optional — when omitted, reads the id from `<DashboardProvider>`. */
4
4
  dashboardId?: string;
5
5
  }
6
- export declare function DashboardWidget({ widgetId, dashboardId: dashboardIdProp }: DashboardWidgetProps): import("@emotion/react/jsx-runtime").JSX.Element;
6
+ export declare function DashboardWidget(props: DashboardWidgetProps): import("@emotion/react/jsx-runtime").JSX.Element;
@@ -4154,6 +4154,8 @@ export declare enum FilterType {
4154
4154
  }
4155
4155
  export type Folder = {
4156
4156
  __typename?: 'Folder';
4157
+ accessLevel: FolderScope;
4158
+ canManage: Scalars['Boolean']['output'];
4157
4159
  createdAt: Scalars['DateTime']['output'];
4158
4160
  deletedAt?: Maybe<Scalars['DateTime']['output']>;
4159
4161
  folderType: FolderType;
@@ -4198,6 +4200,11 @@ export declare enum FolderResourceType {
4198
4200
  DASHBOARD = "DASHBOARD",
4199
4201
  DOMAIN = "DOMAIN"
4200
4202
  }
4203
+ export declare enum FolderScope {
4204
+ EDITOR = "EDITOR",
4205
+ NO_ACCESS = "NO_ACCESS",
4206
+ VIEWER = "VIEWER"
4207
+ }
4201
4208
  export type FolderTreeNode = {
4202
4209
  __typename?: 'FolderTreeNode';
4203
4210
  children: Array<FolderTreeNode>;
@@ -6133,6 +6140,7 @@ export type Mutation = {
6133
6140
  triggerQueryHistoryMining: TriggerQueryHistoryMiningResponse;
6134
6141
  triggerSSOSync: ResponseStatus;
6135
6142
  triggerSchedule: TriggerScheduleResponse;
6143
+ triggerUserAuthoredContextVerify: TriggerUserAuthoredContextVerifyResult;
6136
6144
  unarchiveWorkspace: ResponseStatus;
6137
6145
  unassignRole: UnassignRoleResponse;
6138
6146
  undoModelingSuggestions: Array<ApplyModelingSuggestionResult>;
@@ -7395,6 +7403,10 @@ export type MutationTriggerScheduleArgs = {
7395
7403
  parameterValueSets?: InputMaybe<Array<AgentParameterValueSetInput>>;
7396
7404
  parameterValues?: InputMaybe<Array<AgentParameterValueInput>>;
7397
7405
  };
7406
+ export type MutationTriggerUserAuthoredContextVerifyArgs = {
7407
+ contextId: Scalars['String']['input'];
7408
+ domainId: Scalars['String']['input'];
7409
+ };
7398
7410
  export type MutationUnarchiveWorkspaceArgs = {
7399
7411
  input: UnarchiveWorkspaceInput;
7400
7412
  };
@@ -8462,6 +8474,7 @@ export type Query = {
8462
8474
  * the user has access to. Optional domainId narrows the result to a single domain.
8463
8475
  */
8464
8476
  currentUserReviewedQueries: Array<UserReviewedQueryItemWithDomainContext>;
8477
+ currentUserRootFolder: Folder;
8465
8478
  dashboard: Dashboard;
8466
8479
  dashboardAppWidgetData?: Maybe<Scalars['JSON']['output']>;
8467
8480
  dashboardBundle: DataBundle;
@@ -8549,6 +8562,7 @@ export type Query = {
8549
8562
  expandVirtualDomainId: Array<Scalars['String']['output']>;
8550
8563
  fileBlueprints: Array<FileBlueprint>;
8551
8564
  filesForDataset: Array<DatasetFile>;
8565
+ folderBreadcrumb: Array<Folder>;
8552
8566
  folderContents: FolderWithContents;
8553
8567
  folderContentsPage: FolderContentsResponse;
8554
8568
  folderTree: Array<FolderTreeNode>;
@@ -8575,6 +8589,7 @@ export type Query = {
8575
8589
  getReviewedQueryItemsCount: Scalars['Int']['output'];
8576
8590
  getScheduleOverride: ScheduleOverrideResponse;
8577
8591
  getSynonymSets: SynonymSetsResponse;
8592
+ getUserAuthoredContextVerifyStatus: UserAuthoredContextVerifyStatus;
8578
8593
  getVerboseSemanticEngineRuntimeInfo: Scalars['String']['output'];
8579
8594
  hitsForContainer: Array<Hit>;
8580
8595
  impersonateUser: Scalars['String']['output'];
@@ -8716,9 +8731,9 @@ export type Query = {
8716
8731
  workspace: Workspace;
8717
8732
  workspaceExists: Scalars['Boolean']['output'];
8718
8733
  workspaces: Array<Workspace>;
8719
- writableFolderDestinationsForCreate: Array<Folder>;
8720
- writableFolderDestinationsForFolderMove: Array<Folder>;
8721
- writableFolderDestinationsForResourceMove: Array<Folder>;
8734
+ writableFolderDestinationsForCreate: Array<WritableFolderDestination>;
8735
+ writableFolderDestinationsForFolderMove: Array<WritableFolderDestination>;
8736
+ writableFolderDestinationsForResourceMove: Array<WritableFolderDestination>;
8722
8737
  };
8723
8738
  export type QueryAdminConversationsArgs = {
8724
8739
  filter?: InputMaybe<AllConversationFilterInput>;
@@ -8861,6 +8876,10 @@ export type QueryCreateVisualizationArgs = {
8861
8876
  export type QueryCurrentUserReviewedQueriesArgs = {
8862
8877
  domainId?: InputMaybe<Scalars['ID']['input']>;
8863
8878
  };
8879
+ export type QueryCurrentUserRootFolderArgs = {
8880
+ resourceScope: FolderResourceType;
8881
+ workspaceID?: InputMaybe<Scalars['ID']['input']>;
8882
+ };
8864
8883
  export type QueryDashboardArgs = {
8865
8884
  id: Scalars['String']['input'];
8866
8885
  scope: DashboardScope;
@@ -9084,6 +9103,10 @@ export type QueryFilesForDatasetArgs = {
9084
9103
  domainId: Scalars['ID']['input'];
9085
9104
  prefixSearch?: InputMaybe<Scalars['String']['input']>;
9086
9105
  };
9106
+ export type QueryFolderBreadcrumbArgs = {
9107
+ folderID: Scalars['ID']['input'];
9108
+ workspaceID?: InputMaybe<Scalars['ID']['input']>;
9109
+ };
9087
9110
  export type QueryFolderContentsArgs = {
9088
9111
  folderID: Scalars['ID']['input'];
9089
9112
  workspaceID?: InputMaybe<Scalars['ID']['input']>;
@@ -9173,6 +9196,9 @@ export type QueryGetSynonymSetsArgs = {
9173
9196
  domainId: Scalars['String']['input'];
9174
9197
  draftId?: InputMaybe<Scalars['ID']['input']>;
9175
9198
  };
9199
+ export type QueryGetUserAuthoredContextVerifyStatusArgs = {
9200
+ domainId: Scalars['String']['input'];
9201
+ };
9176
9202
  export type QueryGetVerboseSemanticEngineRuntimeInfoArgs = {
9177
9203
  columnFilters?: InputMaybe<Array<Scalars['String']['input']>>;
9178
9204
  domainId: Scalars['ID']['input'];
@@ -9595,10 +9621,9 @@ export type RefreshBundleResponse = {
9595
9621
  };
9596
9622
  export type RefreshContextStalenessResult = {
9597
9623
  __typename?: 'RefreshContextStalenessResult';
9624
+ jobRunId: Scalars['String']['output'];
9598
9625
  previousStaleMeasureCount: Scalars['Int']['output'];
9599
9626
  previousStaleQueryCount: Scalars['Int']['output'];
9600
- staleMeasureCount: Scalars['Int']['output'];
9601
- staleQueryCount: Scalars['Int']['output'];
9602
9627
  };
9603
9628
  export type RefreshWidgetTrajectoryMutationInput = {
9604
9629
  dashboardId: Scalars['String']['input'];
@@ -9722,6 +9747,7 @@ export declare enum RequestChannelType {
9722
9747
  DOMAIN_HEALTH = "DOMAIN_HEALTH",
9723
9748
  DOMAIN_KNOWLEDGE_AGENT = "DOMAIN_KNOWLEDGE_AGENT",
9724
9749
  EMBEDDED_IFRAMES = "EMBEDDED_IFRAMES",
9750
+ EVAL_JOB = "EVAL_JOB",
9725
9751
  MCP = "MCP",
9726
9752
  REPORT_WRITER = "REPORT_WRITER",
9727
9753
  SCHEDULED_CONVERSATION = "SCHEDULED_CONVERSATION",
@@ -10482,14 +10508,16 @@ export type SqlServerConnectionConfig = {
10482
10508
  host: Scalars['String']['output'];
10483
10509
  password: Scalars['String']['output'];
10484
10510
  port: Scalars['Int']['output'];
10511
+ servicePrincipalClientSecretAuth?: Maybe<AzureServicePrincipalClientSecretAuth>;
10485
10512
  username: Scalars['String']['output'];
10486
10513
  };
10487
10514
  export type SqlServerConnectionConfigInput = {
10488
10515
  databaseFilters?: InputMaybe<Array<Scalars['String']['input']>>;
10489
10516
  host: Scalars['String']['input'];
10490
- password: Scalars['String']['input'];
10517
+ password?: InputMaybe<Scalars['String']['input']>;
10491
10518
  port: Scalars['Int']['input'];
10492
- username: Scalars['String']['input'];
10519
+ servicePrincipalClientSecretAuth?: InputMaybe<AzureServicePrincipalClientSecretAuthInput>;
10520
+ username?: InputMaybe<Scalars['String']['input']>;
10493
10521
  };
10494
10522
  export type SshTunnelConfig = {
10495
10523
  __typename?: 'SshTunnelConfig';
@@ -10633,6 +10661,7 @@ export type SubscriptionRunAgentAnalysisArgs = {
10633
10661
  agentInput?: InputMaybe<Scalars['String']['input']>;
10634
10662
  auth: SubscriptionAuthInput;
10635
10663
  inlineAnalysisTask: AnalysisScheduleTaskInput;
10664
+ parameterValues?: InputMaybe<Array<AgentParameterValueInput>>;
10636
10665
  };
10637
10666
  export type SubscriptionStreamAgentPreviewRunArgs = {
10638
10667
  auth: SubscriptionAuthInput;
@@ -11129,6 +11158,12 @@ export type TriggerScheduleResponse = {
11129
11158
  message: Scalars['String']['output'];
11130
11159
  runId?: Maybe<Scalars['String']['output']>;
11131
11160
  };
11161
+ export type TriggerUserAuthoredContextVerifyResult = {
11162
+ __typename?: 'TriggerUserAuthoredContextVerifyResult';
11163
+ jobRunId?: Maybe<Scalars['String']['output']>;
11164
+ message: Scalars['String']['output'];
11165
+ status: UserAuthoredContextVerifyTriggerStatus;
11166
+ };
11132
11167
  export type TrinoConnectionConfig = {
11133
11168
  __typename?: 'TrinoConnectionConfig';
11134
11169
  catalogSchemaFilters?: Maybe<Array<CatalogSchemaFilterKv>>;
@@ -11449,6 +11484,26 @@ export type UserAuthoredContextVerificationSourceInfo = {
11449
11484
  newContextId: Scalars['String']['output'];
11450
11485
  rationale: Scalars['String']['output'];
11451
11486
  };
11487
+ export type UserAuthoredContextVerifyRun = {
11488
+ __typename?: 'UserAuthoredContextVerifyRun';
11489
+ contextId: Scalars['String']['output'];
11490
+ /** True for a recently-failed run (show 'couldn't complete'); false while verifying. */
11491
+ failed: Scalars['Boolean']['output'];
11492
+ jobRunId: Scalars['String']['output'];
11493
+ progressDone: Scalars['Int']['output'];
11494
+ progressTotal: Scalars['Int']['output'];
11495
+ };
11496
+ export type UserAuthoredContextVerifyStatus = {
11497
+ __typename?: 'UserAuthoredContextVerifyStatus';
11498
+ /** The domain's single in-flight (or failed) verification, if any. */
11499
+ activeRun?: Maybe<UserAuthoredContextVerifyRun>;
11500
+ };
11501
+ export declare enum UserAuthoredContextVerifyTriggerStatus {
11502
+ USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_ERROR = "USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_ERROR",
11503
+ USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_INVALID_INPUT = "USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_INVALID_INPUT",
11504
+ USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_OK = "USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_OK",
11505
+ USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_UNSPECIFIED = "USER_AUTHORED_CONTEXT_VERIFY_TRIGGER_STATUS_UNSPECIFIED"
11506
+ }
11452
11507
  /** One entry per FE inline-edit save. Lives inside EditableStringFieldHistory on each editable leaf task. */
11453
11508
  export type UserEditEvent = {
11454
11509
  __typename?: 'UserEditEvent';
@@ -11881,6 +11936,11 @@ export type WorkspacesFilterInput = {
11881
11936
  statusFilter?: InputMaybe<Array<WorkspaceStatus>>;
11882
11937
  uris?: InputMaybe<Array<Scalars['String']['input']>>;
11883
11938
  };
11939
+ export type WritableFolderDestination = {
11940
+ __typename?: 'WritableFolderDestination';
11941
+ folder: Folder;
11942
+ selectable: Scalars['Boolean']['output'];
11943
+ };
11884
11944
  export type SdkColumnFragmentFragment = {
11885
11945
  __typename?: 'DataframeColumn';
11886
11946
  name: string;
package/dist/index.js CHANGED
@@ -737,6 +737,27 @@ var WisdomClient = class {
737
737
  }
738
738
  };
739
739
 
740
+ // src/SdkErrorBoundary.tsx
741
+ import { Component } from "react";
742
+ var SdkErrorBoundary = class extends Component {
743
+ constructor() {
744
+ super(...arguments);
745
+ this.state = { error: null };
746
+ }
747
+ static getDerivedStateFromError(error) {
748
+ return { error };
749
+ }
750
+ componentDidCatch(error, info) {
751
+ console.error("[@wisdomai/react] Render error caught by SDK boundary:", error, info.componentStack);
752
+ }
753
+ render() {
754
+ if (this.state.error) {
755
+ return this.props.fallback(this.state.error);
756
+ }
757
+ return this.props.children;
758
+ }
759
+ };
760
+
740
761
  // src/dashboard/DashboardContext.tsx
741
762
  import { createContext, useContext } from "react";
742
763
  var DashboardContext = createContext(null);
@@ -19762,7 +19783,20 @@ function WisdomVisualization({ visualization, fetchMore }) {
19762
19783
 
19763
19784
  // src/dashboard/DashboardWidget.tsx
19764
19785
  import { jsx as jsx32 } from "@emotion/react/jsx-runtime";
19765
- function DashboardWidget({ widgetId, dashboardId: dashboardIdProp }) {
19786
+ function DashboardWidget(props) {
19787
+ return (
19788
+ // Keyed by widget identity so swapping widgets clears a prior error.
19789
+ /* @__PURE__ */ jsx32(
19790
+ SdkErrorBoundary,
19791
+ {
19792
+ fallback: () => /* @__PURE__ */ jsx32(WidgetCard, { title: "", children: /* @__PURE__ */ jsx32(WidgetErrorBody, { message: "Something went wrong rendering this widget" }) }),
19793
+ children: /* @__PURE__ */ jsx32(DashboardWidgetBody, { ...props })
19794
+ },
19795
+ props.widgetId
19796
+ )
19797
+ );
19798
+ }
19799
+ function DashboardWidgetBody({ widgetId, dashboardId: dashboardIdProp }) {
19766
19800
  const { status: dashboardStatus, error: dashboardError, dashboard } = useDashboard();
19767
19801
  const { widget, status, error, fetchMore } = useDashboardWidget(widgetId, dashboardIdProp);
19768
19802
  const captureRef = useRef6(null);
@@ -19896,10 +19930,21 @@ function DashboardLayout() {
19896
19930
  ] });
19897
19931
  }
19898
19932
  function Dashboard(props) {
19899
- if (props.dashboardId !== void 0) {
19900
- return /* @__PURE__ */ jsx34(DashboardProvider, { dashboardId: props.dashboardId, scope: props.scope, children: /* @__PURE__ */ jsx34(DashboardLayout, {}) });
19901
- }
19902
- return /* @__PURE__ */ jsx34(DashboardProvider, { dashboard: props.dashboard, children: /* @__PURE__ */ jsx34(DashboardLayout, {}) });
19933
+ const dashboardKey = props.dashboardId ?? props.dashboard.id;
19934
+ return (
19935
+ // Keyed by dashboard identity so switching dashboards clears a prior error.
19936
+ /* @__PURE__ */ jsx34(
19937
+ SdkErrorBoundary,
19938
+ {
19939
+ fallback: (error) => /* @__PURE__ */ jsxs20("p", { role: "alert", style: { color: "crimson", margin: 0 }, children: [
19940
+ "Failed to render dashboard: ",
19941
+ error.message
19942
+ ] }),
19943
+ children: props.dashboardId !== void 0 ? /* @__PURE__ */ jsx34(DashboardProvider, { dashboardId: props.dashboardId, scope: props.scope, children: /* @__PURE__ */ jsx34(DashboardLayout, {}) }) : /* @__PURE__ */ jsx34(DashboardProvider, { dashboard: props.dashboard, children: /* @__PURE__ */ jsx34(DashboardLayout, {}) })
19944
+ },
19945
+ dashboardKey
19946
+ )
19947
+ );
19903
19948
  }
19904
19949
 
19905
19950
  // src/dashboard/useDashboardsList.ts
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@wisdomai/react",
3
- "version": "0.0.8",
3
+ "version": "0.0.10",
4
4
  "description": "Wisdom AI React SDK",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -45,8 +45,8 @@
45
45
  "react-markdown": "^9.0.1",
46
46
  "react-resizable": "^3.0.5",
47
47
  "remark-gfm": "^4.0.0",
48
- "@wisdomai/visualization": "^0.3.3",
49
- "@wisdomai/ui-kit": "^0.1.8"
48
+ "@wisdomai/ui-kit": "^0.1.10",
49
+ "@wisdomai/visualization": "^0.3.5"
50
50
  },
51
51
  "devDependencies": {
52
52
  "esbuild": "^0.27.0"