Add namespace support to ComponentRegistry to prevent naming conflicts#290
Add namespace support to ComponentRegistry to prevent naming conflicts#290
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
- Add namespace field to ComponentMeta type - Update Registry.register() to support namespace option and construct full type as namespace:type - Update Registry.get(), getConfig(), and has() to support namespace lookup with fallback to non-namespaced - Add deprecation warning for non-namespaced registrations - Add comprehensive tests for namespace functionality (23 tests, all passing) Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
- plugin-grid: use 'plugin-grid' and 'view' namespaces - plugin-aggrid: use 'plugin-aggrid' namespace - plugin-charts: use 'plugin-charts' and 'chart' namespaces - plugin-kanban: use 'plugin-kanban' namespace - plugin-form: use 'plugin-form' namespace - plugin-view: use 'plugin-view' and 'view' namespaces - plugin-calendar: use 'plugin-calendar' namespace - plugin-dashboard: use 'plugin-dashboard' namespace - plugin-editor: use 'plugin-editor' namespace - plugin-gantt: use 'plugin-gantt' namespace - plugin-map: use 'plugin-map' namespace - plugin-markdown: use 'plugin-markdown' namespace - plugin-timeline: use 'plugin-timeline' namespace - plugin-chatbot: use 'plugin-chatbot' namespace Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
- components: Add 'ui' namespace to component registrations - fields: Replace field: prefix with namespace: 'field' parameter - All field types now use field:name format via namespace parameter - Removed deprecated field: string prefix in favor of namespace approach - Maintains backward compatibility through fallback lookup Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
- Store namespaced components under both full type (namespace:name) and simple name - This allows non-namespaced lookups to find namespaced components - When namespace is explicitly provided, only look in that namespace (no fallback) - Updated all Registry tests to reflect new behavior - All 24 Registry tests now passing Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
- Fix toast.tsx: Move namespace from toast function call to ComponentRegistry metadata - Fix fields/index.tsx: Remove duplicate field registrations (lines 871-900) - These were overwriting the wrapped versions registered earlier - Wrapped versions (with createFieldRenderer) are the correct approach Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
📦 Bundle Size Report
Size Limits
|
|
✅ All checks passed!
|
Increase wait time from 100ms to 110ms in the second timeout to ensure the total elapsed time exceeds the 200ms TTL, accounting for JavaScript timer precision variability. Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
📦 Bundle Size Report
Size Limits
|
|
✅ All checks passed!
|
There was a problem hiding this comment.
Pull request overview
Introduces optional namespaces to ComponentRegistry registrations to reduce component type naming collisions across plugins, while maintaining backward compatibility for existing un-namespaced lookups.
Changes:
- Added
namespace?: stringsupport to the coreRegistryand updated lookup APIs to accept an optional namespace. - Updated plugin, field, and multiple UI component registrations to pass a namespace in metadata.
- Added comprehensive unit tests for namespaced registration/lookup behavior and adjusted a cache TTL test to reduce timing flakiness.
Reviewed changes
Copilot reviewed 34 out of 34 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
| packages/core/src/registry/Registry.ts | Adds namespace to ComponentMeta and implements namespaced register/get/has behavior with backward-compatible aliasing and deprecation warnings. |
| packages/core/src/registry/tests/Registry.test.ts | Adds unit tests covering namespaced registration, lookup rules, and backward compatibility behavior. |
| packages/plugin-view/src/index.tsx | Updates plugin-view registrations to use namespacing (including view namespace for the simple view alias). |
| packages/plugin-timeline/src/renderer.tsx | Adds plugin-timeline namespace to the timeline component registration. |
| packages/plugin-markdown/src/index.tsx | Adds plugin-markdown namespace to the markdown component registration. |
| packages/plugin-map/src/index.tsx | Adds plugin-map namespace to the map component registration. |
| packages/plugin-kanban/src/index.tsx | Adds plugin-kanban namespace to the kanban component registration. |
| packages/plugin-grid/src/index.tsx | Adds plugin-grid namespace and migrates the view alias registration to namespace: 'view'. |
| packages/plugin-gantt/src/index.tsx | Adds plugin-gantt namespace to the gantt component registration. |
| packages/plugin-form/src/index.tsx | Adds plugin-form namespace to the object-form component registration. |
| packages/plugin-editor/src/index.tsx | Adds plugin-editor namespace to the code editor component registration. |
| packages/plugin-dashboard/src/index.tsx | Adds plugin-dashboard namespace to dashboard/metric registrations. |
| packages/plugin-chatbot/src/renderer.tsx | Adds plugin-chatbot namespace to chatbot registration. |
| packages/plugin-charts/src/index.tsx | Adds plugin-charts namespace to chart registrations and migrates an alias to a namespaced registration. |
| packages/plugin-calendar/src/index.tsx | Adds plugin-calendar namespace to calendar component registration. |
| packages/plugin-aggrid/src/index.tsx | Adds plugin-aggrid namespace to AG Grid registrations. |
| packages/fields/src/index.tsx | Migrates field registrations to { namespace: 'field' } and removes explicit field:* prefixed registrations. |
| packages/components/src/renderers/layout/stack.tsx | Adds ui namespace to Stack registration. |
| packages/components/src/renderers/layout/semantic.tsx | Adds ui namespace to semantic layout tag registrations. |
| packages/components/src/renderers/layout/page.tsx | Adds ui namespace to Page registration. |
| packages/components/src/renderers/layout/container.tsx | Adds ui namespace to Container registration. |
| packages/components/src/renderers/layout/card.tsx | Adds ui namespace to Card registration. |
| packages/components/src/renderers/form/input.tsx | Adds ui namespace to Input registration. |
| packages/components/src/renderers/form/button.tsx | Adds ui namespace to Button registration. |
| packages/components/src/renderers/feedback/toaster.tsx | Adds ui namespace to Toaster registration. |
| packages/components/src/renderers/feedback/toast.tsx | Adds ui namespace to Toast registration. |
| packages/components/src/renderers/data-display/statistic.tsx | Adds ui namespace to Statistic registration. |
| packages/components/src/renderers/complex/data-table.tsx | Adds ui namespace to DataTable registration. |
| packages/components/src/renderers/basic/span.tsx | Adds ui namespace to Span registration. |
| packages/components/src/renderers/basic/separator.tsx | Adds ui namespace to Separator registration. |
| packages/components/src/renderers/basic/icon.tsx | Adds ui namespace to Icon registration. |
| packages/components/src/renderers/basic/div.tsx | Adds ui namespace to Div registration. |
| packages/components/src/renderers/basic/button-group.tsx | Adds ui namespace to Button Group registration. |
| packages/data-objectstack/src/cache/MetadataCache.test.ts | Tweaks TTL timing to reduce flakiness and updates test comments accordingly. |
Comments suppressed due to low confidence (1)
packages/plugin-grid/src/index.tsx:35
- Registering the view alias as
register('grid', ..., { namespace: 'view' })will also write an un-namespacedgridentry (due to the registry’s backward-compat aliasing). That can overwrite the existing layoutgridcomponent registered in@object-ui/components(seepackages/components/src/renderers/layout/grid.tsx) depending on import/plugin load order.
To avoid breaking type: 'grid' layouts, consider keeping this alias registered under the fully-qualified key ('view:grid') without creating a global grid alias, or introduce a registry option to disable the un-namespaced alias for specific registrations. Also update the comment below—this plugin now effectively does affect the grid key.
// Alias for view:grid
ComponentRegistry.register('grid', ObjectGridRenderer, {
namespace: 'view',
label: 'Data Grid',
category: 'view'
});
// Note: 'grid' type is handled by @object-ui/components Grid layout component
// This plugin only handles 'object-grid' which integrates with ObjectQL/ObjectStack
| // Access again after another 110ms (total 210ms from first, ensuring TTL has passed) | ||
| await new Promise(resolve => setTimeout(resolve, 110)); | ||
|
|
||
| // Should still be in cache because we're checking timestamp, not last accessed | ||
| // Actually, the implementation uses timestamp for expiration, not lastAccessed |
There was a problem hiding this comment.
This test’s description/comments say the cache uses a creation timestamp for expiration (i.e., TTL does not extend on cache hits), but the test name is still "should update timestamp on cache hit". Rename the test (or adjust the expectation) so the intent matches the behavior being asserted.
| ComponentRegistry.register('input', InputRenderer, { | ||
| namespace: 'ui', | ||
| label: 'Input Field', | ||
| inputs: [ |
There was a problem hiding this comment.
Only the base input registration was migrated to { namespace: 'ui' } here, but this file still registers other related input components (e.g., email, password) without a namespace. With the new registry behavior, those registrations will now emit deprecation warnings and can still collide with other packages’ component types.
Either migrate the remaining registrations in this file to the same ui namespace (preferred), or explicitly document/handle them as legacy un-namespaced aliases.
| if (!namespace && typeof console !== 'undefined' && console.warn) { | ||
| console.warn( | ||
| `[ObjectUI] Registering component "${type}" without a namespace is deprecated. ` + | ||
| `Please provide a namespace via the meta.namespace option. ` + | ||
| `Example: ComponentRegistry.register('${type}', component, { namespace: 'ui' })` |
There was a problem hiding this comment.
The deprecation warning currently triggers for any registration that omits meta.namespace, even when the type string is already in namespace:type form (e.g., page:header in @object-ui/layout). This will produce misleading warnings and noisy logs for existing namespaced-type registrations.
Consider treating type strings that already contain : as namespaced (skip the deprecation warning, and optionally parse them into { namespace, type } for consistent handling). Also consider gating this warning to non-production builds to avoid flooding production logs during initialization.
ComponentRegistry currently uses a flat namespace for 100+ components, risking conflicts when multiple plugins register components with identical names (e.g.,
gridfrom both plugin-grid and plugin-aggrid).Changes
Core Registry
namespaceoptional field toComponentMetanamespace:typeandtypekeys for backward compatibilityComponent Registrations
plugin-grid,plugin-aggrid, etc.)uinamespacefield:prefix tonamespace: 'field'parameterTesting
Example
Migration
Non-namespaced registrations continue working with deprecation warnings. Full type will be
namespace:typeformat. Plan to remove non-namespaced support in v2.0.Original prompt
💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.