mirror of
https://github.com/Unleash/unleash.git
synced 2025-05-08 01:15:49 +02:00
Merge branch 'master' into fix/featureView-tab
This commit is contained in:
commit
4d55aab98a
@ -45,7 +45,7 @@
|
|||||||
"@types/enzyme": "3.10.9",
|
"@types/enzyme": "3.10.9",
|
||||||
"@types/enzyme-adapter-react-16": "1.0.6",
|
"@types/enzyme-adapter-react-16": "1.0.6",
|
||||||
"@types/jest": "27.0.2",
|
"@types/jest": "27.0.2",
|
||||||
"@types/node": "14.17.26",
|
"@types/node": "14.17.27",
|
||||||
"@types/react": "17.0.30",
|
"@types/react": "17.0.30",
|
||||||
"@types/react-dom": "17.0.9",
|
"@types/react-dom": "17.0.9",
|
||||||
"@types/react-router-dom": "5.3.1",
|
"@types/react-router-dom": "5.3.1",
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
import { Route, Switch, Redirect } from 'react-router-dom';
|
import { Redirect, Route, Switch } from 'react-router-dom';
|
||||||
import { RouteComponentProps } from 'react-router';
|
import { RouteComponentProps } from 'react-router';
|
||||||
|
|
||||||
import ProtectedRoute from './common/ProtectedRoute/ProtectedRoute';
|
import ProtectedRoute from './common/ProtectedRoute/ProtectedRoute';
|
||||||
@ -13,6 +13,9 @@ import IAuthStatus from '../interfaces/user';
|
|||||||
import { useEffect } from 'react';
|
import { useEffect } from 'react';
|
||||||
import NotFound from './common/NotFound/NotFound';
|
import NotFound from './common/NotFound/NotFound';
|
||||||
import Feedback from './common/Feedback';
|
import Feedback from './common/Feedback';
|
||||||
|
import { SWRConfig } from 'swr';
|
||||||
|
import useToast from '../hooks/useToast';
|
||||||
|
|
||||||
interface IAppProps extends RouteComponentProps {
|
interface IAppProps extends RouteComponentProps {
|
||||||
user: IAuthStatus;
|
user: IAuthStatus;
|
||||||
fetchUiBootstrap: any;
|
fetchUiBootstrap: any;
|
||||||
@ -20,6 +23,7 @@ interface IAppProps extends RouteComponentProps {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const App = ({ location, user, fetchUiBootstrap, feedback }: IAppProps) => {
|
const App = ({ location, user, fetchUiBootstrap, feedback }: IAppProps) => {
|
||||||
|
const { toast, setToastData } = useToast();
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
fetchUiBootstrap();
|
fetchUiBootstrap();
|
||||||
/* eslint-disable-next-line */
|
/* eslint-disable-next-line */
|
||||||
@ -71,27 +75,46 @@ const App = ({ location, user, fetchUiBootstrap, feedback }: IAppProps) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={styles.container}>
|
<SWRConfig value={{
|
||||||
<LayoutPicker location={location}>
|
onError: (error) => {
|
||||||
<Switch>
|
if (!isUnauthorized()) {
|
||||||
<ProtectedRoute
|
if (error.status === 401) {
|
||||||
exact
|
// If we've been in an authorized state,
|
||||||
path="/"
|
// but cookie has been deleted (server or client side,
|
||||||
unauthorized={isUnauthorized()}
|
// perform a window reload to reload app
|
||||||
component={Redirect}
|
window.location.reload();
|
||||||
renderProps={{ to: '/features' }}
|
}
|
||||||
|
setToastData({
|
||||||
|
show: true,
|
||||||
|
type: 'error',
|
||||||
|
text: error.message,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}}>
|
||||||
|
<div className={styles.container}>
|
||||||
|
<LayoutPicker location={location}>
|
||||||
|
<Switch>
|
||||||
|
<ProtectedRoute
|
||||||
|
exact
|
||||||
|
path='/'
|
||||||
|
unauthorized={isUnauthorized()}
|
||||||
|
component={Redirect}
|
||||||
|
renderProps={{ to: '/features' }}
|
||||||
|
/>
|
||||||
|
{renderMainLayoutRoutes()}
|
||||||
|
{renderStandaloneRoutes()}
|
||||||
|
<Route path='/404' component={NotFound} />
|
||||||
|
<Redirect to='/404' />
|
||||||
|
</Switch>
|
||||||
|
<Feedback
|
||||||
|
feedbackId='pnps'
|
||||||
|
openUrl='http://feedback.unleash.run'
|
||||||
/>
|
/>
|
||||||
{renderMainLayoutRoutes()}
|
</LayoutPicker>
|
||||||
{renderStandaloneRoutes()}
|
{toast}
|
||||||
<Route path="/404" component={NotFound} />
|
</div>
|
||||||
<Redirect to="/404" />
|
</SWRConfig>
|
||||||
</Switch>
|
|
||||||
<Feedback
|
|
||||||
feedbackId="pnps"
|
|
||||||
openUrl="http://feedback.unleash.run"
|
|
||||||
/>
|
|
||||||
</LayoutPicker>
|
|
||||||
</div>
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
// Set state to any for now, to avoid typing up entire state object while converting to tsx.
|
// Set state to any for now, to avoid typing up entire state object while converting to tsx.
|
||||||
|
@ -63,7 +63,7 @@ const FeatureOverviewMetrics = () => {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/* We display maxium three environments metrics */
|
/* We display maximum three environments metrics */
|
||||||
if (featureMetrics.length >= 3) {
|
if (featureMetrics.length >= 3) {
|
||||||
return featureMetrics.slice(0, 3).map((metric, index) => {
|
return featureMetrics.slice(0, 3).map((metric, index) => {
|
||||||
if (index === 0) {
|
if (index === 0) {
|
||||||
|
21
frontend/src/hooks/api/getters/httpErrorResponseHandler.ts
Normal file
21
frontend/src/hooks/api/getters/httpErrorResponseHandler.ts
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
const handleErrorResponses = (target: string) => async (res: Response) => {
|
||||||
|
if (!res.ok) {
|
||||||
|
const error = new Error(`An error occurred while trying to get ${target}`);
|
||||||
|
// Try to resolve body, but don't rethrow res.json is not a function
|
||||||
|
try {
|
||||||
|
// @ts-ignore
|
||||||
|
error.info = await res.json();
|
||||||
|
} catch (e) {
|
||||||
|
// @ts-ignore
|
||||||
|
error.info = {};
|
||||||
|
}
|
||||||
|
// @ts-ignore
|
||||||
|
error.status = res.status;
|
||||||
|
// @ts-ignore
|
||||||
|
error.statusText = res.statusText;
|
||||||
|
throw error;
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default handleErrorResponses;
|
@ -1,13 +1,14 @@
|
|||||||
import useSWR, { mutate } from 'swr';
|
import useSWR, { mutate } from 'swr';
|
||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useApiTokens = () => {
|
const useApiTokens = () => {
|
||||||
const fetcher = async () => {
|
const fetcher = async () => {
|
||||||
const path = formatApiPath(`api/admin/api-tokens`);
|
const path = formatApiPath(`api/admin/api-tokens`);
|
||||||
const res = await fetch(path, {
|
const res = await fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
});
|
}).then(handleErrorResponses('Api tokens'));
|
||||||
return res.json();
|
return res.json();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@ import useSWR, { mutate } from 'swr';
|
|||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { IEnvironmentResponse } from '../../../../interfaces/environments';
|
import { IEnvironmentResponse } from '../../../../interfaces/environments';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
export const ENVIRONMENT_CACHE_KEY = `api/admin/environments`;
|
export const ENVIRONMENT_CACHE_KEY = `api/admin/environments`;
|
||||||
|
|
||||||
@ -10,7 +11,7 @@ const useEnvironments = () => {
|
|||||||
const path = formatApiPath(`api/admin/environments`);
|
const path = formatApiPath(`api/admin/environments`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Environments')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const { data, error } = useSWR<IEnvironmentResponse>(
|
const { data, error } = useSWR<IEnvironmentResponse>(
|
||||||
|
@ -4,6 +4,7 @@ import { useState, useEffect } from 'react';
|
|||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { IFeatureToggle } from '../../../../interfaces/featureToggle';
|
import { IFeatureToggle } from '../../../../interfaces/featureToggle';
|
||||||
import { defaultFeature } from './defaultFeature';
|
import { defaultFeature } from './defaultFeature';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
interface IUseFeatureOptions {
|
interface IUseFeatureOptions {
|
||||||
refreshInterval?: number;
|
refreshInterval?: number;
|
||||||
@ -21,25 +22,9 @@ const useFeature = (
|
|||||||
const path = formatApiPath(
|
const path = formatApiPath(
|
||||||
`api/admin/projects/${projectId}/features/${id}`
|
`api/admin/projects/${projectId}/features/${id}`
|
||||||
);
|
);
|
||||||
|
return fetch(path, {
|
||||||
const res = await fetch(path, {
|
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
});
|
}).then(handleErrorResponses('Feature toggle data')).then(res => res.json());
|
||||||
|
|
||||||
|
|
||||||
// If the status code is not in the range 200-299,
|
|
||||||
// we still try to parse and throw it.
|
|
||||||
if (!res.ok) {
|
|
||||||
const error = new Error('An error occurred while fetching the data.')
|
|
||||||
// Attach extra info to the error object.
|
|
||||||
// @ts-ignore
|
|
||||||
error.info = await res.json();
|
|
||||||
// @ts-ignore
|
|
||||||
error.status = res.status;
|
|
||||||
throw error;
|
|
||||||
}
|
|
||||||
|
|
||||||
return res.json()
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const FEATURE_CACHE_KEY = `api/admin/projects/${projectId}/features/${id}`;
|
const FEATURE_CACHE_KEY = `api/admin/projects/${projectId}/features/${id}`;
|
||||||
|
@ -3,6 +3,7 @@ import { useState, useEffect } from 'react';
|
|||||||
|
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { IFeatureStrategy } from '../../../../interfaces/strategy';
|
import { IFeatureStrategy } from '../../../../interfaces/strategy';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
interface IUseFeatureOptions {
|
interface IUseFeatureOptions {
|
||||||
refreshInterval?: number;
|
refreshInterval?: number;
|
||||||
@ -25,7 +26,7 @@ const useFeatureStrategy = (
|
|||||||
);
|
);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses(`Strategies for ${featureId}`)).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const FEATURE_STRATEGY_CACHE_KEY = strategyId;
|
const FEATURE_STRATEGY_CACHE_KEY = strategyId;
|
||||||
|
@ -2,13 +2,14 @@ import useSWR, { mutate } from 'swr';
|
|||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { IFeatureType } from '../../../../interfaces/featureTypes';
|
import { IFeatureType } from '../../../../interfaces/featureTypes';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useFeatureTypes = () => {
|
const useFeatureTypes = () => {
|
||||||
const fetcher = async () => {
|
const fetcher = async () => {
|
||||||
const path = formatApiPath(`api/admin/feature-types`);
|
const path = formatApiPath(`api/admin/feature-types`);
|
||||||
const res = await fetch(path, {
|
const res = await fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
});
|
}).then(handleErrorResponses('Feature types'));
|
||||||
return res.json();
|
return res.json();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -4,6 +4,7 @@ import { IProjectHealthReport } from '../../../../interfaces/project';
|
|||||||
import { fallbackProject } from '../useProject/fallbackProject';
|
import { fallbackProject } from '../useProject/fallbackProject';
|
||||||
import useSort from '../../../useSort';
|
import useSort from '../../../useSort';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useHealthReport = (id: string) => {
|
const useHealthReport = (id: string) => {
|
||||||
const KEY = `api/admin/projects/${id}/health-report`;
|
const KEY = `api/admin/projects/${id}/health-report`;
|
||||||
@ -12,7 +13,7 @@ const useHealthReport = (id: string) => {
|
|||||||
const path = formatApiPath(`api/admin/projects/${id}/health-report`);
|
const path = formatApiPath(`api/admin/projects/${id}/health-report`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Health report')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const [sort] = useSort();
|
const [sort] = useSort();
|
||||||
|
@ -1,11 +1,12 @@
|
|||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
export const getProjectFetcher = (id: string) => {
|
export const getProjectFetcher = (id: string) => {
|
||||||
const fetcher = () => {
|
const fetcher = () => {
|
||||||
const path = formatApiPath(`api/admin/projects/${id}`);
|
const path = formatApiPath(`api/admin/projects/${id}`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Project overview')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const KEY = `api/admin/projects/${id}`;
|
const KEY = `api/admin/projects/${id}`;
|
||||||
|
@ -3,13 +3,14 @@ import { useState, useEffect } from 'react';
|
|||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
|
||||||
import { IProjectCard } from '../../../../interfaces/project';
|
import { IProjectCard } from '../../../../interfaces/project';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useProjects = () => {
|
const useProjects = () => {
|
||||||
const fetcher = () => {
|
const fetcher = () => {
|
||||||
const path = formatApiPath(`api/admin/projects`);
|
const path = formatApiPath(`api/admin/projects`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Projects')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const KEY = `api/admin/projects`;
|
const KEY = `api/admin/projects`;
|
||||||
|
@ -2,12 +2,13 @@ import useSWR from 'swr';
|
|||||||
import useQueryParams from '../../../useQueryParams';
|
import useQueryParams from '../../../useQueryParams';
|
||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const getFetcher = (token: string) => () => {
|
const getFetcher = (token: string) => () => {
|
||||||
const path = formatApiPath(`auth/reset/validate?token=${token}`);
|
const path = formatApiPath(`auth/reset/validate?token=${token}`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Password reset')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const INVALID_TOKEN_ERROR = 'InvalidTokenError';
|
const INVALID_TOKEN_ERROR = 'InvalidTokenError';
|
||||||
|
@ -2,6 +2,7 @@ import useSWR, { mutate } from 'swr';
|
|||||||
import { useEffect, useState } from 'react';
|
import { useEffect, useState } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { IStrategy } from '../../../../interfaces/strategy';
|
import { IStrategy } from '../../../../interfaces/strategy';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
export const STRATEGIES_CACHE_KEY = 'api/admin/strategies';
|
export const STRATEGIES_CACHE_KEY = 'api/admin/strategies';
|
||||||
|
|
||||||
@ -12,7 +13,7 @@ const useStrategies = () => {
|
|||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
credentials: 'include',
|
credentials: 'include',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Strategies')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const { data, error } = useSWR<{ strategies: IStrategy[] }>(
|
const { data, error } = useSWR<{ strategies: IStrategy[] }>(
|
||||||
|
@ -2,13 +2,14 @@ import useSWR, { mutate } from 'swr';
|
|||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { ITagType } from '../../../../interfaces/tags';
|
import { ITagType } from '../../../../interfaces/tags';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useTagTypes = () => {
|
const useTagTypes = () => {
|
||||||
const fetcher = async () => {
|
const fetcher = async () => {
|
||||||
const path = formatApiPath(`api/admin/tag-types`);
|
const path = formatApiPath(`api/admin/tag-types`);
|
||||||
const res = await fetch(path, {
|
const res = await fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
});
|
}).then(handleErrorResponses('Tag types'));
|
||||||
return res.json();
|
return res.json();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -2,13 +2,14 @@ import useSWR, { mutate } from 'swr';
|
|||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { ITag } from '../../../../interfaces/tags';
|
import { ITag } from '../../../../interfaces/tags';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useTags = (featureId: string) => {
|
const useTags = (featureId: string) => {
|
||||||
const fetcher = async () => {
|
const fetcher = async () => {
|
||||||
const path = formatApiPath(`api/admin/features/${featureId}/tags`);
|
const path = formatApiPath(`api/admin/features/${featureId}/tags`);
|
||||||
const res = await fetch(path, {
|
const res = await fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
});
|
}).then(handleErrorResponses('Tags'));
|
||||||
return res.json();
|
return res.json();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -3,6 +3,7 @@ import { useState, useEffect } from 'react';
|
|||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { defaultValue } from './defaultValue';
|
import { defaultValue } from './defaultValue';
|
||||||
import { IUiConfig } from '../../../../interfaces/uiConfig';
|
import { IUiConfig } from '../../../../interfaces/uiConfig';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const REQUEST_KEY = 'api/admin/ui-config';
|
const REQUEST_KEY = 'api/admin/ui-config';
|
||||||
|
|
||||||
@ -13,7 +14,7 @@ const useUiConfig = () => {
|
|||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
credentials: 'include',
|
credentials: 'include',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('configuration')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const { data, error } = useSWR<IUiConfig>(REQUEST_KEY, fetcher);
|
const { data, error } = useSWR<IUiConfig>(REQUEST_KEY, fetcher);
|
||||||
|
@ -1,13 +1,14 @@
|
|||||||
import useSWR, { mutate } from 'swr';
|
import useSWR, { mutate } from 'swr';
|
||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useUnleashContext = (revalidate = true) => {
|
const useUnleashContext = (revalidate = true) => {
|
||||||
const fetcher = () => {
|
const fetcher = () => {
|
||||||
const path = formatApiPath(`api/admin/context`);
|
const path = formatApiPath(`api/admin/context`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Context variables')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const CONTEXT_CACHE_KEY = 'api/admin/context';
|
const CONTEXT_CACHE_KEY = 'api/admin/context';
|
||||||
|
@ -2,6 +2,7 @@ import useSWR, { mutate } from 'swr';
|
|||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
import { IPermission } from '../../../../interfaces/user';
|
import { IPermission } from '../../../../interfaces/user';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useUser = () => {
|
const useUser = () => {
|
||||||
const KEY = `api/admin/user`;
|
const KEY = `api/admin/user`;
|
||||||
@ -9,7 +10,7 @@ const useUser = () => {
|
|||||||
const path = formatApiPath(`api/admin/user`);
|
const path = formatApiPath(`api/admin/user`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('User info')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const { data, error } = useSWR(KEY, fetcher);
|
const { data, error } = useSWR(KEY, fetcher);
|
||||||
|
@ -1,13 +1,14 @@
|
|||||||
import useSWR, { mutate } from 'swr';
|
import useSWR, { mutate } from 'swr';
|
||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { formatApiPath } from '../../../../utils/format-path';
|
import { formatApiPath } from '../../../../utils/format-path';
|
||||||
|
import handleErrorResponses from '../httpErrorResponseHandler';
|
||||||
|
|
||||||
const useUsers = () => {
|
const useUsers = () => {
|
||||||
const fetcher = () => {
|
const fetcher = () => {
|
||||||
const path = formatApiPath(`api/admin/user-admin`);
|
const path = formatApiPath(`api/admin/user-admin`);
|
||||||
return fetch(path, {
|
return fetch(path, {
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
}).then(res => res.json());
|
}).then(handleErrorResponses('Users')).then(res => res.json());
|
||||||
};
|
};
|
||||||
|
|
||||||
const { data, error } = useSWR(`api/admin/user-admin`, fetcher);
|
const { data, error } = useSWR(`api/admin/user-admin`, fetcher);
|
||||||
|
@ -2107,10 +2107,10 @@
|
|||||||
resolved "https://registry.npmjs.org/@types/node/-/node-14.14.37.tgz"
|
resolved "https://registry.npmjs.org/@types/node/-/node-14.14.37.tgz"
|
||||||
integrity sha512-XYmBiy+ohOR4Lh5jE379fV2IU+6Jn4g5qASinhitfyO71b/sCo6MKsMLF5tc7Zf2CE8hViVQyYSobJNke8OvUw==
|
integrity sha512-XYmBiy+ohOR4Lh5jE379fV2IU+6Jn4g5qASinhitfyO71b/sCo6MKsMLF5tc7Zf2CE8hViVQyYSobJNke8OvUw==
|
||||||
|
|
||||||
"@types/node@14.17.26":
|
"@types/node@14.17.27":
|
||||||
version "14.17.26"
|
version "14.17.27"
|
||||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-14.17.26.tgz#47a53c7e7804490155a4646d60c8e194816d073c"
|
resolved "https://registry.yarnpkg.com/@types/node/-/node-14.17.27.tgz#5054610d37bb5f6e21342d0e6d24c494231f3b85"
|
||||||
integrity sha512-eSTNkK/nfmnC7IKpOJZixDgG0W2/eHz1qyFN7o/rwwwIHsVRp+G9nbh4BrQ77kbQ2zPu286AQRxkuRLPcR3gXw==
|
integrity sha512-94+Ahf9IcaDuJTle/2b+wzvjmutxXAEXU6O81JHblYXUg2BDG+dnBy7VxIPHKAyEEDHzCMQydTJuWvrE+Aanzw==
|
||||||
|
|
||||||
"@types/node@^14.14.31":
|
"@types/node@^14.14.31":
|
||||||
version "14.17.19"
|
version "14.17.19"
|
||||||
|
Loading…
Reference in New Issue
Block a user