new features context to render features correctly on change
This commit is contained in:
parent
f17bac399a
commit
e71f262b79
46
src/App.tsx
46
src/App.tsx
@ -1,4 +1,4 @@
|
||||
import React from 'react';
|
||||
import React, {useContext} from 'react';
|
||||
import HomePage from './pages/HomePage/HomePage';
|
||||
import RandomPage from './pages/RandomPage/RandomPage';
|
||||
import GlobalInfos from './utils/GlobalInfos';
|
||||
@ -18,6 +18,7 @@ import AuthenticationPage from './pages/AuthenticationPage/AuthenticationPage';
|
||||
import TVShowPage from './pages/TVShowPage/TVShowPage';
|
||||
import TVPlayer from './pages/TVShowPage/TVPlayer';
|
||||
import {LoginContextProvider} from './utils/context/LoginContextProvider';
|
||||
import {FeatureContext} from './utils/context/FeatureContext';
|
||||
|
||||
interface state {
|
||||
mediacentername: string;
|
||||
@ -48,13 +49,7 @@ class App extends React.Component<{}, state> {
|
||||
<LoginContextProvider>
|
||||
<Switch>
|
||||
<Route path='/login'>
|
||||
<AuthenticationPage
|
||||
onSuccessLogin={(): void => {
|
||||
// this.setState({password: false});
|
||||
// reinit general infos
|
||||
// this.initialAPICall();
|
||||
}}
|
||||
/>
|
||||
<AuthenticationPage />
|
||||
</Route>
|
||||
<Route path='/media'>
|
||||
{this.navBar()}
|
||||
@ -63,32 +58,10 @@ class App extends React.Component<{}, state> {
|
||||
</Switch>
|
||||
</LoginContextProvider>
|
||||
);
|
||||
|
||||
// if (this.state.password === true) {
|
||||
// // render authentication page if auth is neccessary
|
||||
// return (
|
||||
// <AuthenticationPage
|
||||
// onSuccessLogin={(): void => {
|
||||
// this.setState({password: false});
|
||||
// // reinit general infos
|
||||
// this.initialAPICall();
|
||||
// }}
|
||||
// />
|
||||
// );
|
||||
// } else if (this.state.password === false) {
|
||||
// return (
|
||||
// <Router>
|
||||
// <div className={style.app}>
|
||||
// {this.navBar()}
|
||||
// {this.routing()}
|
||||
// </div>
|
||||
// </Router>
|
||||
// );
|
||||
// } else {
|
||||
// return <>still loading...</>;
|
||||
// }
|
||||
}
|
||||
|
||||
static contextType = FeatureContext;
|
||||
|
||||
/**
|
||||
* render the top navigation bar
|
||||
*/
|
||||
@ -115,7 +88,7 @@ class App extends React.Component<{}, state> {
|
||||
Categories
|
||||
</NavLink>
|
||||
|
||||
{GlobalInfos.isTVShowEnabled() ? (
|
||||
{this.context.TVShowEnabled ? (
|
||||
<NavLink
|
||||
className={[style.navitem, themeStyle.navitem].join(' ')}
|
||||
to={'/media/tvshows'}
|
||||
@ -137,6 +110,7 @@ class App extends React.Component<{}, state> {
|
||||
|
||||
const MyRouter = (): JSX.Element => {
|
||||
const match = useRouteMatch();
|
||||
const features = useContext(FeatureContext);
|
||||
|
||||
return (
|
||||
<Switch>
|
||||
@ -159,13 +133,13 @@ const MyRouter = (): JSX.Element => {
|
||||
<ActorPage />
|
||||
</Route>
|
||||
|
||||
{GlobalInfos.isTVShowEnabled() ? (
|
||||
<Route exact path={`${match.url}/tvshows`}>
|
||||
{features.TVShowEnabled ? (
|
||||
<Route path={`${match.url}/tvshows`}>
|
||||
<TVShowPage />
|
||||
</Route>
|
||||
) : null}
|
||||
|
||||
{GlobalInfos.isTVShowEnabled() ? (
|
||||
{features.TVShowEnabled ? (
|
||||
<Route exact path={`${match.url}/tvplayer/:id`}>
|
||||
<TVPlayer />
|
||||
</Route>
|
||||
|
@ -2,6 +2,7 @@ import React from 'react';
|
||||
import ReactDOM from 'react-dom';
|
||||
import App from './App';
|
||||
import {BrowserRouter} from 'react-router-dom';
|
||||
import {FeatureContextProvider} from './utils/context/FeatureContext';
|
||||
|
||||
// don't allow console logs within production env
|
||||
global.console.log = process.env.NODE_ENV !== 'development' ? (_: string | number | boolean): void => {} : global.console.log;
|
||||
@ -9,7 +10,9 @@ global.console.log = process.env.NODE_ENV !== 'development' ? (_: string | numbe
|
||||
ReactDOM.render(
|
||||
<React.StrictMode>
|
||||
<BrowserRouter>
|
||||
<App />
|
||||
<FeatureContextProvider>
|
||||
<App />
|
||||
</FeatureContextProvider>
|
||||
</BrowserRouter>
|
||||
</React.StrictMode>,
|
||||
document.getElementById('root')
|
||||
|
@ -13,9 +13,7 @@ interface state {
|
||||
wrongPWDInfo: boolean;
|
||||
}
|
||||
|
||||
interface Props {
|
||||
onSuccessLogin: () => void;
|
||||
}
|
||||
interface Props {}
|
||||
|
||||
class AuthenticationPage extends React.Component<Props, state> {
|
||||
constructor(props: Props) {
|
||||
|
@ -22,6 +22,7 @@ import {Button} from '../../elements/GPElements/Button';
|
||||
import {VideoTypes} from '../../types/ApiTypes';
|
||||
import GlobalInfos from '../../utils/GlobalInfos';
|
||||
import {ButtonPopup} from '../../elements/Popups/ButtonPopup/ButtonPopup';
|
||||
import {FeatureContext} from '../../utils/context/FeatureContext';
|
||||
|
||||
interface Props extends RouteComponentProps<{id: string}> {}
|
||||
|
||||
@ -65,6 +66,8 @@ export class Player extends React.Component<Props, mystate> {
|
||||
this.quickAddTag = this.quickAddTag.bind(this);
|
||||
}
|
||||
|
||||
static contextType = FeatureContext;
|
||||
|
||||
componentDidMount(): void {
|
||||
// initial fetch of current movie data
|
||||
this.fetchMovieData();
|
||||
@ -205,7 +208,7 @@ export class Player extends React.Component<Props, mystate> {
|
||||
}
|
||||
|
||||
renderDeletePopup(): JSX.Element {
|
||||
if (GlobalInfos.isVideoFulldeleteable()) {
|
||||
if (this.context.VideosFullyDeleteable) {
|
||||
return (
|
||||
<ButtonPopup
|
||||
onDeny={(): void => this.setState({deletepopupvisible: false})}
|
||||
|
@ -1,9 +1,10 @@
|
||||
import React from 'react';
|
||||
import React, {useContext} from 'react';
|
||||
import MovieSettings from './MovieSettings';
|
||||
import GeneralSettings from './GeneralSettings';
|
||||
import style from './SettingsPage.module.css';
|
||||
import GlobalInfos from '../../utils/GlobalInfos';
|
||||
import {NavLink, Redirect, Route, Switch, useRouteMatch} from 'react-router-dom';
|
||||
import {FeatureContext} from '../../utils/context/FeatureContext';
|
||||
|
||||
/**
|
||||
* The Settingspage handles all kinds of settings for the mediacenter
|
||||
@ -12,6 +13,7 @@ import {NavLink, Redirect, Route, Switch, useRouteMatch} from 'react-router-dom'
|
||||
const SettingsPage = (): JSX.Element => {
|
||||
const themestyle = GlobalInfos.getThemeStyle();
|
||||
const match = useRouteMatch();
|
||||
const features = useContext(FeatureContext);
|
||||
|
||||
return (
|
||||
<div>
|
||||
@ -23,7 +25,7 @@ const SettingsPage = (): JSX.Element => {
|
||||
<NavLink to='/media/settings/movies'>
|
||||
<div className={style.SettingSidebarElement}>Movies</div>
|
||||
</NavLink>
|
||||
{GlobalInfos.isTVShowEnabled() ? (
|
||||
{features.TVShowEnabled ? (
|
||||
<NavLink to='/media/settings/tv'>
|
||||
<div className={style.SettingSidebarElement}>TV Shows</div>
|
||||
</NavLink>
|
||||
@ -37,7 +39,7 @@ const SettingsPage = (): JSX.Element => {
|
||||
<Route path={`${match.url}/movies`}>
|
||||
<MovieSettings />
|
||||
</Route>
|
||||
{GlobalInfos.isTVShowEnabled() ? (
|
||||
{features.TVShowEnabled ? (
|
||||
<Route path={`${match.url}/tv`}>
|
||||
<span />
|
||||
</Route>
|
||||
|
@ -72,7 +72,7 @@ export default function (): JSX.Element {
|
||||
|
||||
return (
|
||||
<Switch>
|
||||
<Route path={`${match.path}/:id`}>
|
||||
<Route exact path={`${match.path}/:id`}>
|
||||
<EpisodePage />
|
||||
</Route>
|
||||
<Route path={match.path}>
|
||||
|
@ -1,4 +1,3 @@
|
||||
import GlobalInfos from './GlobalInfos';
|
||||
import {cookie} from './context/Cookie';
|
||||
|
||||
const APIPREFIX: string = '/api/';
|
||||
@ -84,13 +83,7 @@ function generalAPICall<T>(
|
||||
}
|
||||
} else if (response.status === 400) {
|
||||
// Bad Request --> invalid token
|
||||
console.log('loading Password page.');
|
||||
// load password page
|
||||
if (GlobalInfos.loadPasswordPage) {
|
||||
GlobalInfos.loadPasswordPage(() => {
|
||||
callAPI(apinode, fd, callback, errorcallback);
|
||||
});
|
||||
}
|
||||
console.log('bad request todo sth here');
|
||||
} else {
|
||||
console.log('Error: ' + response.statusText);
|
||||
if (errorcallback) {
|
||||
|
@ -49,6 +49,7 @@ class StaticInfos {
|
||||
/**
|
||||
* set the current videopath
|
||||
* @param vidpath videopath with beginning and ending slash
|
||||
* @param tvshowpath
|
||||
*/
|
||||
setVideoPaths(vidpath: string, tvshowpath: string): void {
|
||||
this.videopath = vidpath;
|
||||
@ -68,27 +69,6 @@ class StaticInfos {
|
||||
getTVShowPath(): string {
|
||||
return this.tvshowpath;
|
||||
}
|
||||
|
||||
/**
|
||||
* load the Password page manually
|
||||
*/
|
||||
loadPasswordPage: ((callback?: () => void) => void) | undefined = undefined;
|
||||
|
||||
setTVShowsEnabled(TVShowEnabled: boolean): void {
|
||||
this.TVShowsEnabled = TVShowEnabled;
|
||||
}
|
||||
|
||||
isTVShowEnabled(): boolean {
|
||||
return this.TVShowsEnabled;
|
||||
}
|
||||
|
||||
setFullDeleteEnabled(FullDeleteEnabled: boolean): void {
|
||||
this.fullDeleteable = FullDeleteEnabled;
|
||||
}
|
||||
|
||||
isVideoFulldeleteable(): boolean {
|
||||
return this.fullDeleteable;
|
||||
}
|
||||
}
|
||||
|
||||
export default new StaticInfos();
|
||||
|
32
src/utils/context/FeatureContext.tsx
Normal file
32
src/utils/context/FeatureContext.tsx
Normal file
@ -0,0 +1,32 @@
|
||||
import React, {FunctionComponent, useState} from 'react';
|
||||
|
||||
export interface FeatureContextType {
|
||||
setTVShowEnabled: (enabled: boolean) => void;
|
||||
TVShowEnabled: boolean;
|
||||
setVideosFullyDeleteable: (fullyDeletable: boolean) => void;
|
||||
VideosFullyDeleteable: boolean;
|
||||
}
|
||||
|
||||
/**
|
||||
* A global context providing a way to interact with user login states
|
||||
*/
|
||||
export const FeatureContext = React.createContext<FeatureContextType>({
|
||||
setTVShowEnabled: (_) => {},
|
||||
TVShowEnabled: false,
|
||||
setVideosFullyDeleteable: (_) => {},
|
||||
VideosFullyDeleteable: false
|
||||
});
|
||||
|
||||
export const FeatureContextProvider: FunctionComponent = (props): JSX.Element => {
|
||||
const [tvshowenabled, settvshowenabled] = useState(false);
|
||||
const [fullydeletablevids, setfullydeleteable] = useState(false);
|
||||
|
||||
const value: FeatureContextType = {
|
||||
VideosFullyDeleteable: fullydeletablevids,
|
||||
TVShowEnabled: tvshowenabled,
|
||||
setTVShowEnabled: (e) => settvshowenabled(e),
|
||||
setVideosFullyDeleteable: (e) => setfullydeleteable(e)
|
||||
};
|
||||
|
||||
return <FeatureContext.Provider value={value}>{props.children}</FeatureContext.Provider>;
|
||||
};
|
@ -5,18 +5,21 @@ import {cookie} from './Cookie';
|
||||
import {APINode, callAPI} from '../Api';
|
||||
import {SettingsTypes} from '../../types/ApiTypes';
|
||||
import GlobalInfos from '../GlobalInfos';
|
||||
import {FeatureContext} from './FeatureContext';
|
||||
|
||||
export const LoginContextProvider: FunctionComponent = (props): JSX.Element => {
|
||||
let initialLoginState = LoginState.LoggedIn;
|
||||
let initialUserPerm = LoginPerm.User;
|
||||
|
||||
const features = useContext(FeatureContext);
|
||||
|
||||
const t = cookie.Load();
|
||||
// we are already logged in so we can set the token and redirect to dashboard
|
||||
if (t !== null) {
|
||||
initialLoginState = LoginState.LoggedIn;
|
||||
}
|
||||
|
||||
const initialAPICall = (): void => {
|
||||
useEffect(() => {
|
||||
// this is the first api call so if it fails we know there is no connection to backend
|
||||
callAPI(
|
||||
APINode.Settings,
|
||||
@ -27,9 +30,9 @@ export const LoginContextProvider: FunctionComponent = (props): JSX.Element => {
|
||||
|
||||
GlobalInfos.setVideoPaths(result.VideoPath, result.TVShowPath);
|
||||
|
||||
GlobalInfos.setTVShowsEnabled(result.TVShowEnabled);
|
||||
GlobalInfos.setFullDeleteEnabled(result.FullDeleteEnabled);
|
||||
//
|
||||
features.setTVShowEnabled(result.TVShowEnabled);
|
||||
features.setVideosFullyDeleteable(result.FullDeleteEnabled);
|
||||
|
||||
// this.setState({
|
||||
// mediacentername: result.MediacenterName
|
||||
// });
|
||||
@ -42,11 +45,7 @@ export const LoginContextProvider: FunctionComponent = (props): JSX.Element => {
|
||||
setLoginState(LoginState.LoggedOut);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
initialAPICall();
|
||||
}, []);
|
||||
}, [features]);
|
||||
|
||||
const [loginState, setLoginState] = useState<LoginState>(initialLoginState);
|
||||
const [permission, setPermission] = useState<LoginPerm>(initialUserPerm);
|
||||
|
Loading…
Reference in New Issue
Block a user