@object-ui/plugin-charts 0.3.0 → 0.5.0

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/src/index.test.ts CHANGED
@@ -1,3 +1,11 @@
1
+ /**
2
+ * ObjectUI
3
+ * Copyright (c) 2024-present ObjectStack Inc.
4
+ *
5
+ * This source code is licensed under the MIT license found in the
6
+ * LICENSE file in the root directory of this source tree.
7
+ */
8
+
1
9
  import { describe, it, expect, beforeAll } from 'vitest';
2
10
  import { ComponentRegistry } from '@object-ui/core';
3
11
 
@@ -5,16 +13,16 @@ describe('Plugin Charts', () => {
5
13
  // Import all renderers to register them
6
14
  beforeAll(async () => {
7
15
  await import('./index');
8
- });
16
+ }, 60000);
9
17
 
10
- describe('chart-bar component', () => {
18
+ describe('bar-chart component', () => {
11
19
  it('should be registered in ComponentRegistry', () => {
12
- const chartBarRenderer = ComponentRegistry.get('chart-bar');
20
+ const chartBarRenderer = ComponentRegistry.get('bar-chart');
13
21
  expect(chartBarRenderer).toBeDefined();
14
22
  });
15
23
 
16
24
  it('should have proper metadata', () => {
17
- const config = ComponentRegistry.getConfig('chart-bar');
25
+ const config = ComponentRegistry.getConfig('bar-chart');
18
26
  expect(config).toBeDefined();
19
27
  expect(config?.label).toBe('Bar Chart');
20
28
  expect(config?.category).toBe('plugin');
@@ -23,7 +31,7 @@ describe('Plugin Charts', () => {
23
31
  });
24
32
 
25
33
  it('should have expected inputs', () => {
26
- const config = ComponentRegistry.getConfig('chart-bar');
34
+ const config = ComponentRegistry.getConfig('bar-chart');
27
35
  const inputNames = config?.inputs?.map((input: any) => input.name) || [];
28
36
 
29
37
  expect(inputNames).toContain('data');
@@ -34,7 +42,7 @@ describe('Plugin Charts', () => {
34
42
  });
35
43
 
36
44
  it('should have data as required input', () => {
37
- const config = ComponentRegistry.getConfig('chart-bar');
45
+ const config = ComponentRegistry.getConfig('bar-chart');
38
46
  const dataInput = config?.inputs?.find((input: any) => input.name === 'data');
39
47
 
40
48
  expect(dataInput).toBeDefined();
@@ -43,7 +51,7 @@ describe('Plugin Charts', () => {
43
51
  });
44
52
 
45
53
  it('should have sensible default props', () => {
46
- const config = ComponentRegistry.getConfig('chart-bar');
54
+ const config = ComponentRegistry.getConfig('bar-chart');
47
55
  const defaults = config?.defaultProps;
48
56
 
49
57
  expect(defaults).toBeDefined();
package/src/index.tsx CHANGED
@@ -1,52 +1,32 @@
1
- import React, { Suspense } from 'react';
1
+ /**
2
+ * ObjectUI
3
+ * Copyright (c) 2024-present ObjectStack Inc.
4
+ *
5
+ * This source code is licensed under the MIT license found in the
6
+ * LICENSE file in the root directory of this source tree.
7
+ */
8
+
2
9
  import { ComponentRegistry } from '@object-ui/core';
3
- import { Skeleton } from '@object-ui/components';
10
+ import { ChartBarRenderer, ChartRenderer } from './ChartRenderer';
11
+ import './ObjectChart'; // Import for side-effects (registration of object-chart)
4
12
 
5
13
  // Export types for external use
6
14
  export type { BarChartSchema } from './types';
15
+ export { ChartBarRenderer, ChartRenderer };
16
+ export { ObjectChart } from './ObjectChart';
7
17
 
8
- // 🚀 Lazy load the implementation files
9
- // This ensures Recharts is only loaded when the component is actually rendered
10
- const LazyChart = React.lazy(() => import('./ChartImpl'));
11
- const LazyAdvancedChart = React.lazy(() => import('./AdvancedChartImpl'));
12
-
13
- export interface ChartBarRendererProps {
14
- schema: {
15
- type: string;
16
- id?: string;
17
- className?: string;
18
- data?: Array<Record<string, any>>;
19
- dataKey?: string;
20
- xAxisKey?: string;
21
- height?: number;
22
- color?: string;
23
- };
24
- }
25
-
26
- /**
27
- * ChartBarRenderer - The public API for the bar chart component
28
- * This wrapper handles lazy loading internally using React.Suspense
29
- */
30
- export const ChartBarRenderer: React.FC<ChartBarRendererProps> = ({ schema }) => {
31
- return (
32
- <Suspense fallback={<Skeleton className="w-full h-[400px]" />}>
33
- <LazyChart
34
- data={schema.data}
35
- dataKey={schema.dataKey}
36
- xAxisKey={schema.xAxisKey}
37
- height={schema.height}
38
- className={schema.className}
39
- color={schema.color}
40
- />
41
- </Suspense>
42
- );
18
+ // Standard Export Protocol - for manual integration
19
+ export const chartComponents = {
20
+ 'bar-chart': ChartBarRenderer,
21
+ 'chart': ChartRenderer,
43
22
  };
44
23
 
45
24
  // Register the component with the ComponentRegistry
46
25
  ComponentRegistry.register(
47
- 'chart-bar',
26
+ 'bar-chart',
48
27
  ChartBarRenderer,
49
28
  {
29
+ namespace: 'plugin-charts',
50
30
  label: 'Bar Chart',
51
31
  category: 'plugin',
52
32
  inputs: [
@@ -72,86 +52,12 @@ ComponentRegistry.register(
72
52
  }
73
53
  );
74
54
 
75
- // Advanced Chart Renderer with multiple chart types
76
- export interface ChartRendererProps {
77
- schema: {
78
- type: string;
79
- id?: string;
80
- className?: string;
81
- chartType?: 'bar' | 'line' | 'area';
82
- data?: Array<Record<string, any>>;
83
- config?: Record<string, any>;
84
- xAxisKey?: string;
85
- series?: Array<{ dataKey: string }>;
86
- };
87
- }
88
-
89
- /**
90
- * ChartRenderer - The public API for the advanced chart component
91
- * Supports multiple chart types (bar, line, area) with full configuration
92
- */
93
- export const ChartRenderer: React.FC<ChartRendererProps> = ({ schema }) => {
94
- // ⚡️ Adapter: Normalize JSON schema to Recharts Props
95
- const props = React.useMemo(() => {
96
- // 1. Defaults
97
- let series = schema.series;
98
- let xAxisKey = schema.xAxisKey;
99
- let config = schema.config;
100
-
101
- // 2. Adapt Tremor/Simple format (categories -> series, index -> xAxisKey)
102
- if (!xAxisKey) {
103
- if ((schema as any).index) xAxisKey = (schema as any).index;
104
- else if ((schema as any).category) xAxisKey = (schema as any).category; // Support Pie/Donut category
105
- }
106
-
107
- if (!series) {
108
- if ((schema as any).categories) {
109
- series = (schema as any).categories.map((cat: string) => ({ dataKey: cat }));
110
- } else if ((schema as any).value) {
111
- // Single value adapter (for Pie/Simple charts)
112
- series = [{ dataKey: (schema as any).value }];
113
- }
114
- }
115
-
116
- // 3. Auto-generate config/colors if missing
117
- if (!config && series) {
118
- const colors = (schema as any).colors || ['hsl(var(--chart-1))', 'hsl(var(--chart-2))', 'hsl(var(--chart-3))'];
119
- config = {};
120
- series.forEach((s: any, idx: number) => {
121
- config[s.dataKey] = { label: s.dataKey, color: colors[idx % colors.length] };
122
- });
123
- }
124
-
125
- return {
126
- chartType: schema.chartType,
127
- data: schema.data,
128
- config,
129
- xAxisKey,
130
- series,
131
- className: schema.className
132
- };
133
- }, [schema]);
134
-
135
- return (
136
- <Suspense fallback={<Skeleton className="w-full h-[400px]" />}>
137
- <LazyAdvancedChart
138
- // Pass adapted props
139
- chartType={props.chartType}
140
- data={props.data}
141
- config={props.config}
142
- xAxisKey={props.xAxisKey}
143
- series={props.series}
144
- className={props.className}
145
- />
146
- </Suspense>
147
- );
148
- };
149
-
150
55
  // Register the advanced chart component
151
56
  ComponentRegistry.register(
152
57
  'chart',
153
58
  ChartRenderer,
154
59
  {
60
+ namespace: 'plugin-charts',
155
61
  label: 'Chart',
156
62
  category: 'plugin',
157
63
  inputs: [
@@ -162,7 +68,11 @@ ComponentRegistry.register(
162
68
  enum: [
163
69
  { label: 'Bar', value: 'bar' },
164
70
  { label: 'Line', value: 'line' },
165
- { label: 'Area', value: 'area' }
71
+ { label: 'Area', value: 'area' },
72
+ { label: 'Pie', value: 'pie' },
73
+ { label: 'Donut', value: 'donut' },
74
+ { label: 'Radar', value: 'radar' },
75
+ { label: 'Scatter', value: 'scatter' }
166
76
  ],
167
77
  defaultValue: 'bar'
168
78
  },
@@ -194,8 +104,58 @@ ComponentRegistry.register(
194
104
  }
195
105
  );
196
106
 
197
- // Standard Export Protocol - for manual integration
198
- export const chartComponents = {
199
- 'chart-bar': ChartBarRenderer,
200
- 'chart': ChartRenderer,
201
- };
107
+ // Alias for CRM App compatibility
108
+ ComponentRegistry.register(
109
+ 'chart:bar',
110
+ ChartRenderer,
111
+ {
112
+ namespace: 'plugin-charts',
113
+ label: 'Bar Chart (Alias)',
114
+ category: 'plugin',
115
+ defaultProps: { chartType: 'bar' }
116
+ }
117
+ );
118
+
119
+ ComponentRegistry.register(
120
+ 'pie-chart',
121
+ ChartRenderer,
122
+ {
123
+ namespace: 'plugin-charts',
124
+ label: 'Pie Chart',
125
+ category: 'plugin',
126
+ defaultProps: { chartType: 'pie' }
127
+ }
128
+ );
129
+
130
+ ComponentRegistry.register(
131
+ 'donut-chart',
132
+ ChartRenderer,
133
+ {
134
+ namespace: 'plugin-charts',
135
+ label: 'Donut Chart',
136
+ category: 'plugin',
137
+ defaultProps: { chartType: 'donut' }
138
+ }
139
+ );
140
+
141
+ ComponentRegistry.register(
142
+ 'radar-chart',
143
+ ChartRenderer,
144
+ {
145
+ namespace: 'plugin-charts',
146
+ label: 'Radar Chart',
147
+ category: 'plugin',
148
+ defaultProps: { chartType: 'radar' }
149
+ }
150
+ );
151
+
152
+ ComponentRegistry.register(
153
+ 'scatter-chart',
154
+ ChartRenderer,
155
+ {
156
+ namespace: 'plugin-charts',
157
+ label: 'Scatter Chart',
158
+ category: 'plugin',
159
+ defaultProps: { chartType: 'scatter' }
160
+ }
161
+ );
@@ -0,0 +1,22 @@
1
+ import React from 'react';
2
+ import { render, screen } from '@testing-library/react';
3
+ import { describe, it, expect, vi, beforeAll } from 'vitest';
4
+ import { ComponentRegistry } from '@object-ui/core';
5
+
6
+ describe('Plugin Charts Registration', () => {
7
+ beforeAll(async () => {
8
+ await import('./index');
9
+ }, 30000);
10
+
11
+ it('registers bar-chart component', () => {
12
+ const config = ComponentRegistry.get('bar-chart');
13
+ expect(config).toBeDefined();
14
+ });
15
+
16
+ it('registers chart component types', () => {
17
+ expect(ComponentRegistry.get('chart')).toBeDefined(); // Assuming base
18
+ // Verify aliases if they exist
19
+ expect(ComponentRegistry.get('pie-chart')).toBeDefined();
20
+ expect(ComponentRegistry.get('donut-chart')).toBeDefined();
21
+ });
22
+ });
package/src/types.ts CHANGED
@@ -1,3 +1,11 @@
1
+ /**
2
+ * ObjectUI
3
+ * Copyright (c) 2024-present ObjectStack Inc.
4
+ *
5
+ * This source code is licensed under the MIT license found in the
6
+ * LICENSE file in the root directory of this source tree.
7
+ */
8
+
1
9
  /**
2
10
  * TypeScript type definitions for @object-ui/plugin-charts
3
11
  *
@@ -16,7 +24,7 @@ import type { BaseSchema } from '@object-ui/types';
16
24
  * import type { BarChartSchema } from '@object-ui/plugin-charts';
17
25
  *
18
26
  * const chartSchema: BarChartSchema = {
19
- * type: 'chart-bar',
27
+ * type: 'bar-chart',
20
28
  * data: [
21
29
  * { name: 'Jan', value: 400 },
22
30
  * { name: 'Feb', value: 300 }
@@ -27,7 +35,7 @@ import type { BaseSchema } from '@object-ui/types';
27
35
  * ```
28
36
  */
29
37
  export interface BarChartSchema extends BaseSchema {
30
- type: 'chart-bar';
38
+ type: 'bar-chart';
31
39
 
32
40
  /**
33
41
  * Array of data points to display in the chart.
package/vite.config.ts CHANGED
@@ -1,3 +1,11 @@
1
+ /**
2
+ * ObjectUI
3
+ * Copyright (c) 2024-present ObjectStack Inc.
4
+ *
5
+ * This source code is licensed under the MIT license found in the
6
+ * LICENSE file in the root directory of this source tree.
7
+ */
8
+
1
9
  import { defineConfig } from 'vite';
2
10
  import react from '@vitejs/plugin-react';
3
11
  import dts from 'vite-plugin-dts';
@@ -9,11 +17,20 @@ export default defineConfig({
9
17
  dts({
10
18
  insertTypesEntry: true,
11
19
  include: ['src'],
20
+ exclude: ['**/*.test.ts', '**/*.test.tsx', 'node_modules'],
21
+ skipDiagnostics: true,
12
22
  }),
13
23
  ],
14
24
  resolve: {
15
25
  alias: {
16
26
  '@': resolve(__dirname, './src'),
27
+ '@object-ui/core': resolve(__dirname, '../core/src'),
28
+ '@object-ui/types': resolve(__dirname, '../types/src'),
29
+ '@object-ui/react': resolve(__dirname, '../react/src'),
30
+ '@object-ui/components': resolve(__dirname, '../components/src'),
31
+ '@object-ui/fields': resolve(__dirname, '../fields/src'),
32
+ '@object-ui/plugin-dashboard': resolve(__dirname, '../plugin-dashboard/src'),
33
+ '@object-ui/plugin-grid': resolve(__dirname, '../plugin-grid/src'),
17
34
  },
18
35
  },
19
36
  build: {
@@ -35,4 +52,10 @@ export default defineConfig({
35
52
  },
36
53
  },
37
54
  },
55
+ test: {
56
+ globals: true,
57
+ environment: 'happy-dom',
58
+ setupFiles: ['../../vitest.setup.tsx'],
59
+ passWithNoTests: true,
60
+ },
38
61
  });
@@ -0,0 +1,13 @@
1
+ /// <reference types="vitest" />
2
+ import { defineConfig } from 'vite';
3
+ import react from '@vitejs/plugin-react';
4
+ import path from 'path';
5
+
6
+ export default defineConfig({
7
+ plugins: [react()],
8
+ test: {
9
+ environment: 'happy-dom',
10
+ globals: true,
11
+ setupFiles: ['./vitest.setup.ts'],
12
+ },
13
+ });
@@ -0,0 +1 @@
1
+ import '@testing-library/jest-dom';