Skip to content

Commit 9ae3c17

Browse files
committed
Don't even render components if the user doesn't have permission
1 parent 54f9c5f commit 9ae3c17

File tree

4 files changed

+43
-14
lines changed

4 files changed

+43
-14
lines changed

resources/scripts/components/screens/ScreenBlock.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,8 +52,8 @@ export default ({ title, image, message, onBack, onRetry }: Props) => (
5252
</ActionButton>
5353
</div>
5454
}
55-
<img src={image} css={tw`w-2/3 h-auto select-none`}/>
56-
<h2 css={tw`mt-6 text-neutral-900 font-bold`}>{title}</h2>
55+
<img src={image} css={tw`w-2/3 h-auto select-none mx-auto`}/>
56+
<h2 css={tw`mt-10 text-neutral-900 font-bold text-4xl`}>{title}</h2>
5757
<p css={tw`text-sm text-neutral-700 mt-2`}>
5858
{message}
5959
</p>

resources/scripts/components/server/network/NetworkContainer.tsx

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ const Code = styled.code`${tw`font-mono py-1 px-2 bg-neutral-900 rounded text-sm
2424
const Label = styled.label`${tw`uppercase text-xs mt-1 text-neutral-400 block px-1 select-none transition-colors duration-150`}`;
2525

2626
const NetworkContainer = () => {
27-
const { uuid, allocations, name: serverName } = useServer();
27+
const { uuid, allocations } = useServer();
2828
const { clearFlashes, clearAndAddHttpError } = useFlash();
2929
const [ loading, setLoading ] = useState<false | number>(false);
3030
const { data, error, mutate } = useSWR<Allocation[]>(uuid, key => getServerAllocations(key), { initialData: allocations });
@@ -61,10 +61,7 @@ const NetworkContainer = () => {
6161
}, [ error ]);
6262

6363
return (
64-
<PageContentBlock showFlashKey={'server:network'}>
65-
<Helmet>
66-
<title> {serverName} | Network </title>
67-
</Helmet>
64+
<PageContentBlock showFlashKey={'server:network'} title={'Network'}>
6865
{!data ?
6966
<Spinner size={'large'} centered/>
7067
:
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import React from 'react';
2+
import Can from '@/components/elements/Can';
3+
import NotFound from '@/components/screens/NotFound';
4+
import ScreenBlock from '@/components/screens/ScreenBlock';
5+
6+
const requireServerPermission = (Component: React.ComponentType<any>, permissions: string | string[]) => {
7+
return class extends React.Component<any, any> {
8+
render () {
9+
return (
10+
<Can
11+
action={permissions}
12+
renderOnError={
13+
<ScreenBlock
14+
image={'/assets/svgs/server_error.svg'}
15+
title={'Access Denied'}
16+
message={'You do not have permission to access this page.'}
17+
/>
18+
}
19+
>
20+
<Component/>
21+
</Can>
22+
);
23+
}
24+
};
25+
};
26+
27+
export default requireServerPermission;

resources/scripts/routers/ServerRouter.tsx

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ import SubNavigation from '@/components/elements/SubNavigation';
2828
import NetworkContainer from '@/components/server/network/NetworkContainer';
2929
import InstallListener from '@/components/server/InstallListener';
3030
import StartupContainer from '@/components/server/startup/StartupContainer';
31+
import requireServerPermission from '@/hoc/requireServerPermission';
3132

3233
const ServerRouter = ({ match, location }: RouteComponentProps<{ id: string }>) => {
3334
const { rootAdmin } = useStoreState(state => state.user.data!);
@@ -121,7 +122,11 @@ const ServerRouter = ({ match, location }: RouteComponentProps<{ id: string }>)
121122
<TransitionRouter>
122123
<Switch location={location}>
123124
<Route path={`${match.path}`} component={ServerConsole} exact/>
124-
<Route path={`${match.path}/files`} component={FileManagerContainer} exact/>
125+
<Route
126+
path={`${match.path}/files`}
127+
component={requireServerPermission(FileManagerContainer, 'file.*')}
128+
exact
129+
/>
125130
<Route
126131
path={`${match.path}/files/:action(edit|new)`}
127132
render={props => (
@@ -131,17 +136,17 @@ const ServerRouter = ({ match, location }: RouteComponentProps<{ id: string }>)
131136
)}
132137
exact
133138
/>
134-
<Route path={`${match.path}/databases`} component={DatabasesContainer} exact/>
135-
<Route path={`${match.path}/schedules`} component={ScheduleContainer} exact/>
139+
<Route path={`${match.path}/databases`} component={requireServerPermission(DatabasesContainer, 'database.*')} exact/>
140+
<Route path={`${match.path}/schedules`} component={requireServerPermission(ScheduleContainer, 'schedule.*')} exact/>
136141
<Route
137142
path={`${match.path}/schedules/:id`}
138143
component={ScheduleEditContainer}
139144
exact
140145
/>
141-
<Route path={`${match.path}/users`} component={UsersContainer} exact/>
142-
<Route path={`${match.path}/backups`} component={BackupContainer} exact/>
143-
<Route path={`${match.path}/network`} component={NetworkContainer} exact/>
144-
<Route path={`${match.path}/startup`} component={StartupContainer} exact/>
146+
<Route path={`${match.path}/users`} component={requireServerPermission(UsersContainer, 'user.*')} exact/>
147+
<Route path={`${match.path}/backups`} component={requireServerPermission(BackupContainer, 'backup.*')} exact/>
148+
<Route path={`${match.path}/network`} component={requireServerPermission(NetworkContainer, 'allocation.*')} exact/>
149+
<Route path={`${match.path}/startup`} component={requireServerPermission(StartupContainer, 'startup.*')} exact/>
145150
<Route path={`${match.path}/settings`} component={SettingsContainer} exact/>
146151
<Route path={'*'} component={NotFound}/>
147152
</Switch>

0 commit comments

Comments
 (0)