Skip to content

Commit 7360225

Browse files
authored
Merge pull request #10689 from opencrvs/metabase-dashboard-embeds
Metabase: Add support for changing dashboard names and setting up n dashboards
2 parents b03e478 + ef2f685 commit 7360225

File tree

18 files changed

+119
-442
lines changed

18 files changed

+119
-442
lines changed

packages/client/.storybook/preview-head.html

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,7 @@
1111
COUNTRY: 'FAR',
1212
LANGUAGES: 'en,fr',
1313
SENTRY: '',
14-
LEADERBOARDS_DASHBOARD_URL: '',
15-
REGISTRATIONS_DASHBOARD_URL: '',
16-
STATISTICS_DASHBOARD_URL: '',
14+
DASHBOARDS: [],
1715
FEATURES: {}
1816
}
1917
</script>

packages/client/src/App.tsx

Lines changed: 2 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,7 @@ import { OfficeHome } from '@client/views/OfficeHome/OfficeHome'
2424
import { AdministrativeLevels } from '@client/views/Organisation/AdministrativeLevels'
2525
import { PerformanceDashboard } from '@client/views/Performance/Dashboard'
2626
import { FieldAgentList } from '@client/views/Performance/FieldAgentList'
27-
import { Leaderboards } from '@client/views/Performance/Leaderboards'
2827
import { RegistrationList } from '@client/views/Performance/RegistrationsList'
29-
import { PerformanceStatistics } from '@client/views/Performance/Statistics'
3028
import { CollectorForm } from '@client/views/PrintCertificate/collectorForm/CollectorForm'
3129
import { Payment } from '@client/views/PrintCertificate/Payment'
3230
import { VerifyCollector } from '@client/views/PrintCertificate/VerifyCollector'
@@ -148,23 +146,7 @@ export const routesConfig = config.FEATURES.V2_EVENTS
148146
element: <RegistrationList />
149147
},
150148
{
151-
path: routes.PERFORMANCE_STATISTICS,
152-
element: (
153-
<ProtectedRoute scopes={[SCOPES.PERFORMANCE_READ_DASHBOARDS]}>
154-
<PerformanceStatistics />
155-
</ProtectedRoute>
156-
)
157-
},
158-
{
159-
path: routes.PERFORMANCE_LEADER_BOARDS,
160-
element: (
161-
<ProtectedRoute scopes={[SCOPES.PERFORMANCE_READ_DASHBOARDS]}>
162-
<Leaderboards />
163-
</ProtectedRoute>
164-
)
165-
},
166-
{
167-
path: routes.PERFORMANCE_DASHBOARD,
149+
path: routes.DASHBOARD,
168150
element: (
169151
<ProtectedRoute scopes={[SCOPES.PERFORMANCE_READ_DASHBOARDS]}>
170152
<PerformanceDashboard />
@@ -388,23 +370,7 @@ export const routesConfig = config.FEATURES.V2_EVENTS
388370
element: <RegistrationList />
389371
},
390372
{
391-
path: routes.PERFORMANCE_STATISTICS,
392-
element: (
393-
<ProtectedRoute scopes={[SCOPES.PERFORMANCE_READ_DASHBOARDS]}>
394-
<PerformanceStatistics />
395-
</ProtectedRoute>
396-
)
397-
},
398-
{
399-
path: routes.PERFORMANCE_LEADER_BOARDS,
400-
element: (
401-
<ProtectedRoute scopes={[SCOPES.PERFORMANCE_READ_DASHBOARDS]}>
402-
<Leaderboards />
403-
</ProtectedRoute>
404-
)
405-
},
406-
{
407-
path: routes.PERFORMANCE_DASHBOARD,
373+
path: routes.DASHBOARD,
408374
element: (
409375
<ProtectedRoute scopes={[SCOPES.PERFORMANCE_READ_DASHBOARDS]}>
410376
<PerformanceDashboard />

packages/client/src/components/interface/Navigation.test.tsx

Lines changed: 1 addition & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -621,7 +621,7 @@ describe('Given a user with scopes views Navigation', () => {
621621
})
622622

623623
describe('Dashboard', async () => {
624-
const id = `#navigation_${WORKQUEUE_TABS.dashboard}`
624+
const id = `#navigation_${WORKQUEUE_TABS.dashboard}_test`
625625

626626
const requiredScopes = [SCOPES.PERFORMANCE_READ_DASHBOARDS] as Scope[]
627627

@@ -642,73 +642,4 @@ describe('Given a user with scopes views Navigation', () => {
642642
})
643643
})
644644
})
645-
646-
describe('Statistics', async () => {
647-
const id = `#navigation_${WORKQUEUE_TABS.statistics}`
648-
649-
const requiredScopes = [SCOPES.PERFORMANCE_READ] as Scope[]
650-
651-
const allOtherScopes = allScopes.filter(
652-
(scope) => !requiredScopes.includes(scope)
653-
)
654-
655-
const tests = [
656-
[requiredScopes, true],
657-
[allOtherScopes, false]
658-
]
659-
660-
tests.forEach(async ([scopes, exists]) => {
661-
it(`should render when user has correct scopes ${scopes}`, async () => {
662-
setScopes(scopes as Scope[], store)
663-
testComponent = await build()
664-
expect(testComponent.exists(id)).toBe(exists)
665-
})
666-
})
667-
})
668-
669-
describe('Statistics', async () => {
670-
const id = `#navigation_${WORKQUEUE_TABS.statistics}`
671-
672-
const requiredScopes = [SCOPES.PERFORMANCE_READ] as Scope[]
673-
674-
const allOtherScopes = allScopes.filter(
675-
(scope) => !requiredScopes.includes(scope)
676-
)
677-
678-
const tests = [
679-
[requiredScopes, true],
680-
[allOtherScopes, false]
681-
]
682-
683-
tests.forEach(async ([scopes, exists]) => {
684-
it(`should render when user has correct scopes ${scopes}`, async () => {
685-
setScopes(scopes as Scope[], store)
686-
testComponent = await build()
687-
expect(testComponent.exists(id)).toBe(exists)
688-
})
689-
})
690-
})
691-
692-
describe('Statistics', async () => {
693-
const id = `#navigation_${WORKQUEUE_TABS.leaderboards}`
694-
695-
const requiredScopes = [SCOPES.PERFORMANCE_READ] as Scope[]
696-
697-
const allOtherScopes = allScopes.filter(
698-
(scope) => !requiredScopes.includes(scope)
699-
)
700-
701-
const tests = [
702-
[requiredScopes, true],
703-
[allOtherScopes, false]
704-
]
705-
706-
tests.forEach(async ([scopes, exists]) => {
707-
it(`should render when user has correct scopes ${scopes}`, async () => {
708-
setScopes(scopes as Scope[], store)
709-
testComponent = await build()
710-
expect(testComponent.exists(id)).toBe(exists)
711-
})
712-
})
713-
})
714645
})

packages/client/src/components/interface/Navigation.tsx

Lines changed: 28 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,8 @@ import {
6161
import * as routes from '@client/navigation/routes'
6262
import { stringify } from 'query-string'
6363
import { useHasAccessToNavigationItem } from './useHasAccessToNavigationItem'
64+
import { SCOPES } from '@opencrvs/commons/client'
65+
import { usePermissions } from '@client/hooks/useAuthorization'
6466

6567
const SCREEN_LOCK = 'screenLock'
6668

@@ -143,16 +145,6 @@ const getSettingsAndLogout = (props: IFullProps) => {
143145
)
144146
}
145147

146-
export const showRegDashboard =
147-
!IS_PROD_ENVIRONMENT ||
148-
(IS_PROD_ENVIRONMENT && window.config.REGISTRATIONS_DASHBOARD_URL)
149-
export const showLeaderboard =
150-
!IS_PROD_ENVIRONMENT ||
151-
(IS_PROD_ENVIRONMENT && window.config.LEADERBOARDS_DASHBOARD_URL)
152-
export const showStatistics =
153-
!IS_PROD_ENVIRONMENT ||
154-
(IS_PROD_ENVIRONMENT && window.config.STATISTICS_DASHBOARD_URL)
155-
156148
const NavigationView = (props: IFullProps) => {
157149
const {
158150
intl,
@@ -191,6 +183,8 @@ const NavigationView = (props: IFullProps) => {
191183
const [isCommunationExpanded, setIsCommunationExpanded] =
192184
React.useState(false)
193185

186+
const { hasScope } = usePermissions()
187+
194188
const { data, initialSyncDone } = workqueue
195189
const filteredData = filterProcessingDeclarationsFromQuery(
196190
data,
@@ -596,55 +590,33 @@ const NavigationView = (props: IFullProps) => {
596590
)}
597591
</NavigationGroup>
598592
)}
599-
{hasAccess(TAB_GROUPS.performance) && (
593+
{hasScope(SCOPES.PERFORMANCE_READ_DASHBOARDS) && (
600594
<NavigationGroup>
601595
{
602596
<>
603-
{showRegDashboard && hasAccess(WORKQUEUE_TABS.dashboard) && (
604-
<NavigationItem
605-
icon={() => <Icon name="ChartLine" size="small" />}
606-
label={intl.formatMessage(navigationMessages['dashboard'])}
607-
onClick={() =>
608-
router.navigate(routes.PERFORMANCE_DASHBOARD, {
609-
state: { isNavigatedInsideApp: true }
610-
})
611-
}
612-
id={`navigation_${WORKQUEUE_TABS.dashboard}`}
613-
isSelected={
614-
enableMenuSelection && activeMenuItem === 'dashboard'
615-
}
616-
/>
617-
)}
618-
{showStatistics && hasAccess(WORKQUEUE_TABS.statistics) && (
619-
<NavigationItem
620-
icon={() => <Icon name="Activity" size="small" />}
621-
label={intl.formatMessage(navigationMessages['statistics'])}
622-
onClick={() =>
623-
router.navigate(routes.PERFORMANCE_STATISTICS, {
624-
state: { isNavigatedInsideApp: true }
625-
})
626-
}
627-
id={`navigation_${WORKQUEUE_TABS.statistics}`}
628-
isSelected={
629-
enableMenuSelection && activeMenuItem === 'statistics'
630-
}
631-
/>
632-
)}
633-
{showLeaderboard && hasAccess(WORKQUEUE_TABS.leaderboards) && (
634-
<NavigationItem
635-
icon={() => <Icon name="Medal" size="small" />}
636-
label={intl.formatMessage(navigationMessages['leaderboards'])}
637-
onClick={() =>
638-
router.navigate(routes.PERFORMANCE_LEADER_BOARDS, {
639-
state: { isNavigatedInsideApp: true }
640-
})
641-
}
642-
id={`navigation_${WORKQUEUE_TABS.leaderboards}`}
643-
isSelected={
644-
enableMenuSelection && activeMenuItem === 'leaderboards'
645-
}
646-
/>
647-
)}
597+
{(window.config.DASHBOARDS || []).map((config) => {
598+
return (
599+
<NavigationItem
600+
key={config.id}
601+
icon={() => <Icon name="ChartLine" size="small" />}
602+
label={intl.formatMessage(config.title)}
603+
onClick={() =>
604+
router.navigate(
605+
formatUrl(routes.DASHBOARD, {
606+
id: config.id
607+
}),
608+
{
609+
state: { isNavigatedInsideApp: true }
610+
}
611+
)
612+
}
613+
id={`navigation_dashboard_${config.id}`}
614+
isSelected={
615+
enableMenuSelection && activeMenuItem === 'dashboard'
616+
}
617+
/>
618+
)
619+
})}
648620
</>
649621
}
650622
</NavigationGroup>

packages/client/src/components/interface/WorkQueueTabs.tsx

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ export const WORKQUEUE_TABS = {
2727
vsexports: 'vsexports',
2828
team: 'team',
2929
config: 'config',
30+
dashboard: 'dashboard',
3031
organisation: 'organisation',
3132
application: 'application',
3233
certificate: 'certificate',
@@ -37,10 +38,7 @@ export const WORKQUEUE_TABS = {
3738
communications: 'communications',
3839
informantNotification: 'informantnotification',
3940
emailAllUsers: 'emailAllUsers',
40-
readyToIssue: 'readyToIssue',
41-
dashboard: 'dashboard',
42-
statistics: 'statistics',
43-
leaderboards: 'leaderboards'
41+
readyToIssue: 'readyToIssue'
4442
} as const
4543

4644
export const TAB_GROUPS = {

packages/client/src/hooks/useHomePage.ts

Lines changed: 2 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,7 @@ import {
1414
TEAM_USER_LIST,
1515
SYSTEM_LIST,
1616
ALL_USER_EMAIL,
17-
PERFORMANCE_LEADER_BOARDS,
18-
PERFORMANCE_STATISTICS,
19-
PERFORMANCE_DASHBOARD
17+
DASHBOARD
2018
} from '@client/navigation/routes'
2119
import { Path, useLocation } from 'react-router'
2220
import { useNavigation } from './useNavigation'
@@ -78,13 +76,7 @@ export const useHomePage = () => {
7876
path = ALL_USER_EMAIL
7977
break
8078
case WORKQUEUE_TABS.dashboard:
81-
path = PERFORMANCE_DASHBOARD
82-
break
83-
case WORKQUEUE_TABS.statistics:
84-
path = PERFORMANCE_STATISTICS
85-
break
86-
case WORKQUEUE_TABS.leaderboards:
87-
path = PERFORMANCE_LEADER_BOARDS
79+
path = DASHBOARD
8880
break
8981
case WORKQUEUE_TABS.performance:
9082
path = generatePerformanceHomeUrl({

packages/client/src/hooks/useNavigation.ts

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -157,14 +157,6 @@ const routeAccess: NavigationConfig[] = [
157157
name: WORKQUEUE_TABS.dashboard,
158158
scopes: [SCOPES.PERFORMANCE_READ_DASHBOARDS]
159159
},
160-
{
161-
name: WORKQUEUE_TABS.statistics,
162-
scopes: [SCOPES.PERFORMANCE_READ]
163-
},
164-
{
165-
name: WORKQUEUE_TABS.leaderboards,
166-
scopes: [SCOPES.PERFORMANCE_READ]
167-
},
168160
{
169161
name: WORKQUEUE_TABS.performance,
170162
scopes: [SCOPES.PERFORMANCE_READ]

packages/client/src/i18n/messages/views/dashboard.ts

Lines changed: 0 additions & 50 deletions
This file was deleted.

packages/client/src/i18n/messages/views/navigation.ts

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -162,16 +162,6 @@ const messagesToDefine: INavigationMessages = {
162162
description: 'Analytic Group',
163163
id: 'navigation.analytic'
164164
},
165-
statistics: {
166-
defaultMessage: 'Statistics',
167-
description: 'Statistics Dashboard Section',
168-
id: 'navigation.performanceStatistics'
169-
},
170-
leaderboards: {
171-
defaultMessage: 'Leaderboards',
172-
description: 'Leaderboards Dashboard Section',
173-
id: 'navigation.leaderboards'
174-
},
175165
dashboard: {
176166
defaultMessage: 'Dashboard',
177167
description: 'Dashboard Section',

0 commit comments

Comments
 (0)