@jmruthers/pace-core 0.5.34 → 0.5.36
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/dist/{DataTable-CGX3WTZR.js → DataTable-BC4UXGIK.js} +3 -2
- package/dist/{chunk-Q4U5PCOY.js → chunk-6Z3XT4BB.js} +22 -182
- package/dist/chunk-6Z3XT4BB.js.map +1 -0
- package/dist/{chunk-FBRFVBSW.js → chunk-GEJMGKZW.js} +34 -77
- package/dist/chunk-GEJMGKZW.js.map +1 -0
- package/dist/{chunk-2ZWMQGNE.js → chunk-KXXVMXZ7.js} +2 -2
- package/dist/components.js +3 -2
- package/dist/components.js.map +1 -1
- package/dist/index.js +4 -4
- package/dist/rbac/index.d.ts +1 -1
- package/dist/rbac/index.js +1 -1
- package/dist/utils.js +4 -4
- package/docs/api/classes/ErrorBoundary.md +1 -1
- package/docs/api/classes/InvalidScopeError.md +1 -1
- package/docs/api/classes/MissingUserContextError.md +1 -1
- package/docs/api/classes/OrganisationContextRequiredError.md +1 -1
- package/docs/api/classes/PermissionDeniedError.md +1 -1
- package/docs/api/classes/PublicErrorBoundary.md +1 -1
- package/docs/api/classes/RBACAuditManager.md +1 -1
- package/docs/api/classes/RBACCache.md +1 -1
- package/docs/api/classes/RBACEngine.md +1 -1
- package/docs/api/classes/RBACError.md +1 -1
- package/docs/api/classes/RBACNotInitializedError.md +1 -1
- package/docs/api/classes/SecureSupabaseClient.md +1 -1
- package/docs/api/interfaces/AggregateConfig.md +1 -1
- package/docs/api/interfaces/ButtonProps.md +1 -1
- package/docs/api/interfaces/CardProps.md +1 -1
- package/docs/api/interfaces/ColorPalette.md +1 -1
- package/docs/api/interfaces/ColorShade.md +1 -1
- package/docs/api/interfaces/DataAccessRecord.md +1 -1
- package/docs/api/interfaces/DataTableAction.md +1 -1
- package/docs/api/interfaces/DataTableColumn.md +1 -1
- package/docs/api/interfaces/DataTableProps.md +1 -1
- package/docs/api/interfaces/DataTableToolbarButton.md +1 -1
- package/docs/api/interfaces/EmptyStateConfig.md +1 -1
- package/docs/api/interfaces/EnhancedNavigationMenuProps.md +1 -1
- package/docs/api/interfaces/EventContextType.md +1 -1
- package/docs/api/interfaces/EventLogoProps.md +1 -1
- package/docs/api/interfaces/EventProviderProps.md +1 -1
- package/docs/api/interfaces/FileSizeLimits.md +1 -1
- package/docs/api/interfaces/FileUploadProps.md +1 -1
- package/docs/api/interfaces/FooterProps.md +1 -1
- package/docs/api/interfaces/InactivityWarningModalProps.md +1 -1
- package/docs/api/interfaces/InputProps.md +1 -1
- package/docs/api/interfaces/LabelProps.md +1 -1
- package/docs/api/interfaces/LoginFormProps.md +1 -1
- package/docs/api/interfaces/NavigationAccessRecord.md +1 -1
- package/docs/api/interfaces/NavigationContextType.md +1 -1
- package/docs/api/interfaces/NavigationGuardProps.md +1 -1
- package/docs/api/interfaces/NavigationItem.md +1 -1
- package/docs/api/interfaces/NavigationMenuProps.md +1 -1
- package/docs/api/interfaces/NavigationProviderProps.md +1 -1
- package/docs/api/interfaces/Organisation.md +1 -1
- package/docs/api/interfaces/OrganisationContextType.md +1 -1
- package/docs/api/interfaces/OrganisationMembership.md +1 -1
- package/docs/api/interfaces/OrganisationProviderProps.md +1 -1
- package/docs/api/interfaces/OrganisationSecurityError.md +1 -1
- package/docs/api/interfaces/PaceAppLayoutProps.md +1 -1
- package/docs/api/interfaces/PaceLoginPageProps.md +1 -1
- package/docs/api/interfaces/PageAccessRecord.md +1 -1
- package/docs/api/interfaces/PagePermissionContextType.md +1 -1
- package/docs/api/interfaces/PagePermissionGuardProps.md +1 -1
- package/docs/api/interfaces/PagePermissionProviderProps.md +1 -1
- package/docs/api/interfaces/PaletteData.md +1 -1
- package/docs/api/interfaces/PermissionEnforcerProps.md +1 -1
- package/docs/api/interfaces/PublicErrorBoundaryProps.md +1 -1
- package/docs/api/interfaces/PublicErrorBoundaryState.md +1 -1
- package/docs/api/interfaces/PublicLoadingSpinnerProps.md +1 -1
- package/docs/api/interfaces/PublicPageFooterProps.md +1 -1
- package/docs/api/interfaces/PublicPageHeaderProps.md +1 -1
- package/docs/api/interfaces/PublicPageLayoutProps.md +1 -1
- package/docs/api/interfaces/RBACConfig.md +1 -1
- package/docs/api/interfaces/RBACContextType.md +1 -1
- package/docs/api/interfaces/RBACLogger.md +1 -1
- package/docs/api/interfaces/RBACProviderProps.md +1 -1
- package/docs/api/interfaces/RoleBasedRouterContextType.md +1 -1
- package/docs/api/interfaces/RoleBasedRouterProps.md +1 -1
- package/docs/api/interfaces/RouteAccessRecord.md +1 -1
- package/docs/api/interfaces/RouteConfig.md +1 -1
- package/docs/api/interfaces/SecureDataContextType.md +1 -1
- package/docs/api/interfaces/SecureDataProviderProps.md +1 -1
- package/docs/api/interfaces/StorageConfig.md +1 -1
- package/docs/api/interfaces/StorageFileInfo.md +1 -1
- package/docs/api/interfaces/StorageFileMetadata.md +1 -1
- package/docs/api/interfaces/StorageListOptions.md +1 -1
- package/docs/api/interfaces/StorageListResult.md +1 -1
- package/docs/api/interfaces/StorageUploadOptions.md +1 -1
- package/docs/api/interfaces/StorageUploadResult.md +1 -1
- package/docs/api/interfaces/StorageUrlOptions.md +1 -1
- package/docs/api/interfaces/StyleImport.md +1 -1
- package/docs/api/interfaces/ToastActionElement.md +1 -1
- package/docs/api/interfaces/ToastProps.md +1 -1
- package/docs/api/interfaces/UnifiedAuthContextType.md +1 -1
- package/docs/api/interfaces/UnifiedAuthProviderProps.md +1 -1
- package/docs/api/interfaces/UseInactivityTrackerOptions.md +1 -1
- package/docs/api/interfaces/UseInactivityTrackerReturn.md +1 -1
- package/docs/api/interfaces/UsePublicEventLogoOptions.md +1 -1
- package/docs/api/interfaces/UsePublicEventLogoReturn.md +1 -1
- package/docs/api/interfaces/UsePublicEventOptions.md +1 -1
- package/docs/api/interfaces/UsePublicEventReturn.md +1 -1
- package/docs/api/interfaces/UsePublicRouteParamsReturn.md +1 -1
- package/docs/api/interfaces/UserEventAccess.md +1 -1
- package/docs/api/interfaces/UserMenuProps.md +1 -1
- package/docs/api/interfaces/UserProfile.md +1 -1
- package/docs/api/modules.md +5 -5
- package/package.json +1 -1
- package/src/components/DataTable/components/DataTableCore.tsx +46 -82
- package/src/rbac/components/PagePermissionGuard.tsx +6 -190
- package/dist/chunk-FBRFVBSW.js.map +0 -1
- package/dist/chunk-Q4U5PCOY.js.map +0 -1
- package/docs/troubleshooting/cake-infinite-rerender-debugging.md +0 -284
- package/docs/troubleshooting/cake-infinite-rerender-summary.md +0 -117
- package/docs/troubleshooting/cake-rerender-diagnostic.js +0 -162
- package/docs/troubleshooting/page-permission-guard-diagnostic.js +0 -129
- package/docs/troubleshooting/page-permission-guard-ui-debugging.md +0 -353
- package/docs/troubleshooting/rbac-critical-fixes-summary.md +0 -260
- /package/dist/{DataTable-CGX3WTZR.js.map → DataTable-BC4UXGIK.js.map} +0 -0
- /package/dist/{chunk-2ZWMQGNE.js.map → chunk-KXXVMXZ7.js.map} +0 -0
package/docs/api/modules.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
[@jmruthers/pace-core - v0.5.
|
|
1
|
+
[@jmruthers/pace-core - v0.5.36](README.md) / Exports
|
|
2
2
|
|
|
3
|
-
# @jmruthers/pace-core - v0.5.
|
|
3
|
+
# @jmruthers/pace-core - v0.5.36
|
|
4
4
|
|
|
5
5
|
**`File`**
|
|
6
6
|
|
|
@@ -5036,7 +5036,7 @@ ___
|
|
|
5036
5036
|
|
|
5037
5037
|
### PagePermissionGuard
|
|
5038
5038
|
|
|
5039
|
-
▸ **PagePermissionGuard**(`props`): `Element`
|
|
5039
|
+
▸ **PagePermissionGuard**(`props`): ``null`` \| `string` \| `number` \| `boolean` \| `Iterable`\<`ReactNode`, `any`, `any`\> \| `Element`
|
|
5040
5040
|
|
|
5041
5041
|
PagePermissionGuard - Enforces page-level permissions
|
|
5042
5042
|
|
|
@@ -5052,13 +5052,13 @@ prevent apps from bypassing permission checks.
|
|
|
5052
5052
|
|
|
5053
5053
|
#### Returns
|
|
5054
5054
|
|
|
5055
|
-
`Element`
|
|
5055
|
+
``null`` \| `string` \| `number` \| `boolean` \| `Iterable`\<`ReactNode`, `any`, `any`\> \| `Element`
|
|
5056
5056
|
|
|
5057
5057
|
React element with permission enforcement
|
|
5058
5058
|
|
|
5059
5059
|
#### Defined in
|
|
5060
5060
|
|
|
5061
|
-
[packages/core/src/rbac/components/PagePermissionGuard.tsx:
|
|
5061
|
+
[packages/core/src/rbac/components/PagePermissionGuard.tsx:489](https://github.com/jmruthers/pace-core/blob/main/packages/core/src/rbac/components/PagePermissionGuard.tsx#L489)
|
|
5062
5062
|
|
|
5063
5063
|
___
|
|
5064
5064
|
|
package/package.json
CHANGED
|
@@ -50,6 +50,7 @@ import { AccessDeniedPage } from './AccessDeniedPage';
|
|
|
50
50
|
import { useCan } from '../../../rbac/hooks';
|
|
51
51
|
import { useUnifiedAuth } from '../../../providers/UnifiedAuthProvider';
|
|
52
52
|
import { Scope } from '../../../rbac/types';
|
|
53
|
+
import { getCurrentAppName } from '../../../utils/appNameResolver';
|
|
53
54
|
|
|
54
55
|
import type {
|
|
55
56
|
DataRecord,
|
|
@@ -332,13 +333,6 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
332
333
|
// Get scope from useUnifiedAuth hook instead of user metadata
|
|
333
334
|
const { selectedOrganisationId, selectedEventId, supabase } = useUnifiedAuth();
|
|
334
335
|
|
|
335
|
-
// DEBUG: Log what we get from useUnifiedAuth
|
|
336
|
-
console.log('[DataTable] useUnifiedAuth values:', {
|
|
337
|
-
selectedOrganisationId,
|
|
338
|
-
selectedEventId,
|
|
339
|
-
hasUser: !!user,
|
|
340
|
-
userId: user?.id
|
|
341
|
-
});
|
|
342
336
|
|
|
343
337
|
// Create scope the same way as PagePermissionGuard - with event-based resolution
|
|
344
338
|
const [resolvedScope, setResolvedScope] = useState<Scope | null>(null);
|
|
@@ -377,12 +371,49 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
377
371
|
|
|
378
372
|
useEffect(() => {
|
|
379
373
|
const resolveScope = async () => {
|
|
374
|
+
// Get app ID from package.json or environment (SAME AS PagePermissionGuard)
|
|
375
|
+
let appId: string | undefined = undefined;
|
|
376
|
+
|
|
377
|
+
// Try to resolve from database
|
|
378
|
+
if (supabase) {
|
|
379
|
+
const appName = getCurrentAppName();
|
|
380
|
+
if (appName) {
|
|
381
|
+
try {
|
|
382
|
+
const { data: app, error } = await supabase
|
|
383
|
+
.from('rbac_apps')
|
|
384
|
+
.select('id, name, is_active')
|
|
385
|
+
.eq('name', appName)
|
|
386
|
+
.eq('is_active', true)
|
|
387
|
+
.single() as { data: { id: string; name: string; is_active: boolean } | null; error: any };
|
|
388
|
+
|
|
389
|
+
if (error) {
|
|
390
|
+
// Check if app exists but is inactive
|
|
391
|
+
const { data: inactiveApp } = await supabase
|
|
392
|
+
.from('rbac_apps')
|
|
393
|
+
.select('id, name, is_active')
|
|
394
|
+
.eq('name', appName)
|
|
395
|
+
.single() as { data: { id: string; name: string; is_active: boolean } | null };
|
|
396
|
+
|
|
397
|
+
if (inactiveApp) {
|
|
398
|
+
console.error(`[DataTable] App "${appName}" exists but is inactive (is_active: ${inactiveApp.is_active})`);
|
|
399
|
+
} else {
|
|
400
|
+
console.error(`[DataTable] App "${appName}" not found in rbac_apps table`);
|
|
401
|
+
}
|
|
402
|
+
} else if (app) {
|
|
403
|
+
appId = app.id;
|
|
404
|
+
}
|
|
405
|
+
} catch (error) {
|
|
406
|
+
console.error('[DataTable] Unexpected error resolving app ID:', error);
|
|
407
|
+
}
|
|
408
|
+
}
|
|
409
|
+
}
|
|
410
|
+
|
|
380
411
|
// If we have both organisation and event, use them directly
|
|
381
412
|
if (selectedOrganisationId && selectedEventId) {
|
|
382
413
|
setResolvedScope({
|
|
383
414
|
organisationId: selectedOrganisationId,
|
|
384
415
|
eventId: selectedEventId,
|
|
385
|
-
appId:
|
|
416
|
+
appId: appId
|
|
386
417
|
});
|
|
387
418
|
return;
|
|
388
419
|
}
|
|
@@ -392,7 +423,7 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
392
423
|
setResolvedScope({
|
|
393
424
|
organisationId: selectedOrganisationId,
|
|
394
425
|
eventId: selectedEventId || undefined,
|
|
395
|
-
appId:
|
|
426
|
+
appId: appId
|
|
396
427
|
});
|
|
397
428
|
return;
|
|
398
429
|
}
|
|
@@ -407,7 +438,11 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
407
438
|
setResolvedScope(null);
|
|
408
439
|
return;
|
|
409
440
|
}
|
|
410
|
-
|
|
441
|
+
// Preserve the resolved app ID
|
|
442
|
+
setResolvedScope({
|
|
443
|
+
...eventScope,
|
|
444
|
+
appId: appId || eventScope.appId
|
|
445
|
+
});
|
|
411
446
|
} catch (error) {
|
|
412
447
|
console.error('[DataTable] Error resolving scope from event:', error);
|
|
413
448
|
setResolvedScope(null);
|
|
@@ -423,39 +458,11 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
423
458
|
resolveScope();
|
|
424
459
|
}, [selectedOrganisationId, selectedEventId, supabase]);
|
|
425
460
|
|
|
426
|
-
// DEBUG: Log the exact parameters being passed to useCan
|
|
427
|
-
console.log('[DataTable] useCan parameters:', {
|
|
428
|
-
userId: user?.id || '',
|
|
429
|
-
stableScope,
|
|
430
|
-
permission: `read:page.${effectivePageId}`,
|
|
431
|
-
effectivePageId,
|
|
432
|
-
useCache: true,
|
|
433
|
-
hasValidScope: !!(stableScope && stableScope.organisationId)
|
|
434
|
-
});
|
|
435
|
-
|
|
436
|
-
// DEBUG: Log stableScope details separately to avoid console collapsing
|
|
437
|
-
console.log('[DataTable] stableScope details:');
|
|
438
|
-
console.log(' organisationId:', stableScope?.organisationId);
|
|
439
|
-
console.log(' eventId:', stableScope?.eventId);
|
|
440
|
-
console.log(' appId:', stableScope?.appId);
|
|
441
|
-
console.log(' stableScope type:', typeof stableScope);
|
|
442
|
-
console.log(' stableScope keys:', stableScope ? Object.keys(stableScope) : 'null');
|
|
443
|
-
|
|
444
461
|
// Always call useCan hooks (React rules), but use a fallback scope if needed
|
|
445
462
|
const fallbackScope = { organisationId: '', eventId: undefined, appId: undefined };
|
|
446
463
|
const effectiveScope = stableScope && stableScope.organisationId ? stableScope : fallbackScope;
|
|
447
464
|
|
|
448
|
-
|
|
449
|
-
const testBypass = true; // Set to true to test bypassing useCan
|
|
450
|
-
|
|
451
|
-
const permissions = testBypass ? {
|
|
452
|
-
canRead: { can: true, isLoading: false, error: null, refetch: async () => {} },
|
|
453
|
-
canCreate: { can: true, isLoading: false, error: null, refetch: async () => {} },
|
|
454
|
-
canUpdate: { can: true, isLoading: false, error: null, refetch: async () => {} },
|
|
455
|
-
canDelete: { can: true, isLoading: false, error: null, refetch: async () => {} },
|
|
456
|
-
canExport: { can: true, isLoading: false, error: null, refetch: async () => {} },
|
|
457
|
-
canImport: { can: true, isLoading: false, error: null, refetch: async () => {} },
|
|
458
|
-
} : {
|
|
465
|
+
const permissions = {
|
|
459
466
|
canRead: useCan(user?.id || '', effectiveScope, `read:page.${effectivePageId}` as any, effectivePageId, true),
|
|
460
467
|
canCreate: useCan(user?.id || '', effectiveScope, `create:page.${effectivePageId}` as any, effectivePageId, true),
|
|
461
468
|
canUpdate: useCan(user?.id || '', effectiveScope, `update:page.${effectivePageId}` as any, effectivePageId, true),
|
|
@@ -463,10 +470,6 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
463
470
|
canExport: useCan(user?.id || '', effectiveScope, `manage:page.${effectivePageId}` as any, effectivePageId, true), // Using manage for export/import
|
|
464
471
|
canImport: useCan(user?.id || '', effectiveScope, `manage:page.${effectivePageId}` as any, effectivePageId, true), // Using manage for export/import
|
|
465
472
|
};
|
|
466
|
-
|
|
467
|
-
if (testBypass) {
|
|
468
|
-
console.log('[DataTable] TEST BYPASS: Using hardcoded can: true for all permissions');
|
|
469
|
-
}
|
|
470
473
|
|
|
471
474
|
// ============================================================================
|
|
472
475
|
// CONFIGURATION RESOLUTION - ALWAYS call these hooks
|
|
@@ -900,50 +903,11 @@ function DataTableInternal<TData extends DataRecord>({
|
|
|
900
903
|
throw new Error('DataTable requires authenticated user for RBAC');
|
|
901
904
|
}
|
|
902
905
|
|
|
903
|
-
const scope = {
|
|
904
|
-
organisationId: user?.user_metadata?.organisationId || user?.app_metadata?.organisationId,
|
|
905
|
-
eventId: user?.user_metadata?.eventId || user?.app_metadata?.eventId,
|
|
906
|
-
appId: user?.user_metadata?.appId || user?.app_metadata?.appId,
|
|
907
|
-
};
|
|
908
906
|
|
|
909
907
|
// MANDATORY: No data access without read permission
|
|
910
|
-
console.log('[DataTable] RBAC DEBUG - Basic Info:', {
|
|
911
|
-
effectivePageId,
|
|
912
|
-
pageId,
|
|
913
|
-
pageName,
|
|
914
|
-
userId: user?.id,
|
|
915
|
-
permission: `read:page.${effectivePageId}`
|
|
916
|
-
});
|
|
917
|
-
|
|
918
|
-
console.log('[DataTable] RBAC DEBUG - CanRead Details:');
|
|
919
|
-
console.log(' can:', permissions.canRead.can);
|
|
920
|
-
console.log(' isLoading:', permissions.canRead.isLoading);
|
|
921
|
-
console.log(' error:', permissions.canRead.error);
|
|
922
|
-
console.log(' refetch type:', typeof permissions.canRead.refetch);
|
|
923
|
-
|
|
924
|
-
console.log('[DataTable] RBAC DEBUG - Scope (FIXED):');
|
|
925
|
-
console.log(' resolvedScope:', resolvedScope);
|
|
926
|
-
console.log(' stableScope:', stableScope);
|
|
927
|
-
console.log(' organisationId:', stableScope?.organisationId);
|
|
928
|
-
console.log(' eventId:', stableScope?.eventId);
|
|
929
|
-
console.log(' appId:', stableScope?.appId);
|
|
930
|
-
|
|
931
908
|
if (!permissions.canRead.can) {
|
|
932
|
-
console.error('[DataTable] ACCESS DENIED - DataTable RBAC failing!');
|
|
933
|
-
console.error(' effectivePageId:', effectivePageId);
|
|
934
|
-
console.error(' canRead.can:', permissions.canRead.can);
|
|
935
|
-
console.error(' canRead.isLoading:', permissions.canRead.isLoading);
|
|
936
|
-
console.error(' canRead.error:', permissions.canRead.error);
|
|
937
|
-
console.error(' permission:', `read:page.${effectivePageId}`);
|
|
938
|
-
console.error(' Full canRead object:', permissions.canRead);
|
|
939
909
|
return <AccessDeniedPage resource={effectivePageId || 'unknown-page'} operation="read" />;
|
|
940
910
|
}
|
|
941
|
-
|
|
942
|
-
console.log('[DataTable] ACCESS GRANTED - DataTable RBAC working!');
|
|
943
|
-
console.log(' effectivePageId:', effectivePageId);
|
|
944
|
-
console.log(' canRead.can:', permissions.canRead.can);
|
|
945
|
-
console.log(' canRead.isLoading:', permissions.canRead.isLoading);
|
|
946
|
-
console.log(' canRead.error:', permissions.canRead.error);
|
|
947
911
|
|
|
948
912
|
// ============================================================================
|
|
949
913
|
// RENDER
|