Skip to content

Commit

Permalink
Adds PrivatePage container to wrap internal components
Browse files Browse the repository at this point in the history
* PrivatePage wraps components that are only accessible when logged in
* PrivatePage contains the toolbar
* It does a cookie-check and redirects to login when no cookie

Fixes #702
Fixes #679
  • Loading branch information
davkal committed Aug 1, 2016
1 parent 5fec4c2 commit c134050
Show file tree
Hide file tree
Showing 6 changed files with 98 additions and 140 deletions.
54 changes: 54 additions & 0 deletions ui-server/client/src/components/private-page.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import React from 'react';

import { getInstance } from '../common/api';
import { trackException } from '../common/tracking';
import Toolbar from './toolbar';

export default class PrivatePage extends React.Component {

constructor() {
super();
this.state = {
instance: null
};

this.handleInstanceSuccess = this.handleInstanceSuccess.bind(this);
this.handleInstanceError = this.handleInstanceError.bind(this);
}

handleInstanceSuccess(instance) {
this.setState({ instance });
}

handleInstanceError(res) {
trackException(res);
}

componentDidMount() {
if (this.props.orgId) {
// includes a cookie check
getInstance(this.props.orgId)
.then(this.handleInstanceSuccess)
.catch(this.handleInstanceError);
}
}

render() {
const styles = {
backgroundContainer: {
height: '100%',
position: 'relative'
}
};

return (
<div style={styles.backgroundContainer}>
<Toolbar
page={this.props.page}
instance={this.state.instance}
orgId={this.props.orgId} />
{this.props.children}
</div>
);
}
}
31 changes: 22 additions & 9 deletions ui-server/client/src/components/toolbar.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,22 +5,23 @@ import Paper from 'material-ui/Paper';
import { encodeURIs } from '../common/request';
import Colors from '../common/colors';

import { Logo } from './logo';

export default class Toolbar extends React.Component {

getLinks() {
return [{
iconClass: 'fa fa-cog',
title: 'Settings for this instance',
route: encodeURIs`#/org/${this.props.organization}`
route: encodeURIs`#/org/${this.props.orgId}`
}, {
title: 'Manage instances',
iconClass: 'fa fa-cubes',
route: encodeURIs`#/instance/${this.props.organization}`
route: encodeURIs`#/instance/${this.props.orgId}`
}, {
title: 'User account',
iconClass: 'fa fa-user',
route: encodeURIs`#/account/${this.props.organization}`
route: encodeURIs`#/account/${this.props.orgId}`
}];
}

Expand Down Expand Up @@ -61,11 +62,19 @@ export default class Toolbar extends React.Component {
height: 50,
},
toolbar: {
display: 'flex',
justifyContent: 'space-between',
width: '100%'
},
toolbarCenter: {
padding: 15
},
toolbarLeft: {
float: 'left',
padding: '16px 24px'
top: 2,
left: 12,
padding: 8,
width: 160,
position: 'relative'
},
toolbarOrganization: {
color: Colors.text2,
Expand All @@ -79,7 +88,6 @@ export default class Toolbar extends React.Component {
marginLeft: '0.5em'
},
toolbarRight: {
float: 'right',
padding: 15,
},
toolbarWrapper: {
Expand All @@ -96,14 +104,19 @@ export default class Toolbar extends React.Component {
<Paper zDepth={1} style={styles.toolbarWrapper}>
<div style={styles.toolbar}>
<div style={styles.toolbarLeft}>
<a href={encodeURIs`#/app/${this.props.organization}`}
<div style={styles.logoWrapper}>
<Logo />
</div>
</div>
<div style={styles.toolbarCenter}>
{this.props.instance && <a href={encodeURIs`#/app/${this.props.orgId}`}
style={styles.toolbarOrganization}>

View Instance
<span style={styles.toolbarOrganizationName}>
{this.props.organization}
{this.props.instance.name}
</span>
</a>
</a>}
</div>
<div style={styles.toolbarRight}>
{links}
Expand Down
24 changes: 4 additions & 20 deletions ui-server/client/src/pages/account/page.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,8 @@ import FontIcon from 'material-ui/FontIcon';

import { FlexContainer } from '../../components/flex-container';
import { Column } from '../../components/column';
import { Logo } from '../../components/logo';
import Logins from './logins';
import Toolbar from '../../components/toolbar';
import PrivatePage from '../../components/private-page';
import { trackView, trackException } from '../../common/tracking';
import { getOrganizations } from '../../common/api';

Expand Down Expand Up @@ -66,14 +65,7 @@ export default class AccountPage extends React.Component {
textAlign: 'center'
},
container: {
marginTop: 128
},
logoWrapper: {
position: 'absolute',
width: 250,
height: 64,
left: 64,
top: 32 + 51 - 3
marginTop: 32
},
avatar: {
top: 19,
Expand All @@ -82,7 +74,6 @@ export default class AccountPage extends React.Component {
}
};

const orgId = this.props.params.orgId;
const logoutButton = (
<RaisedButton
style={{ top: 18, right: 18 }}
Expand All @@ -91,14 +82,7 @@ export default class AccountPage extends React.Component {
label="Logout" />);

return (
<div style={{height: '100%', position: 'relative'}}>
<Toolbar
user={this.state.user}
organization={orgId}
page="Account" />
<div style={styles.logoWrapper}>
<Logo />
</div>
<PrivatePage page="account" {...this.props.params}>
<div style={styles.container}>
<FlexContainer>
<Column minWidth="400">
Expand All @@ -121,7 +105,7 @@ export default class AccountPage extends React.Component {
</Column>
</FlexContainer>
</div>
</div>
</PrivatePage>
);
}

Expand Down
53 changes: 5 additions & 48 deletions ui-server/client/src/pages/instances/page.jsx
Original file line number Diff line number Diff line change
@@ -1,61 +1,25 @@
import React from 'react';
import { hashHistory } from 'react-router';

import { FlexContainer } from '../../components/flex-container';
import { Column } from '../../components/column';
import { Logo } from '../../components/logo';
import InstancesList from '../instances/instances-list';
import Toolbar from '../../components/toolbar';
import { trackView, trackException } from '../../common/tracking';
import { getOrganizations } from '../../common/api';
import PrivatePage from '../../components/private-page';
import { trackView } from '../../common/tracking';

export default class InstancesPage extends React.Component {

constructor() {
super();
this.state = {
user: '',
organizations: [],
};

this.checkCookie = this.checkCookie.bind(this);
this.handleLoginSuccess = this.handleLoginSuccess.bind(this);
this.handleLoginError = this.handleLoginError.bind(this);
}

componentDidMount() {
this.checkCookie();
trackView('Instances');
}

checkCookie() {
return getOrganizations().then(this.handleLoginSuccess, this.handleLoginError);
}

handleLoginSuccess(resp) {
this.setState({
user: resp.email,
organizations: resp.organizations
});
}

handleLoginError(resp) {
if (resp.status === 401) {
hashHistory.push('/login');
} else {
const err = resp.errors[0];
trackException(err.message);
}
}

render() {
const styles = {
activity: {
marginTop: 200,
textAlign: 'center'
},
container: {
marginTop: 128
marginTop: 32
},
logoWrapper: {
position: 'absolute',
Expand All @@ -69,14 +33,7 @@ export default class InstancesPage extends React.Component {
const orgId = this.props.params.orgId;

return (
<div style={{height: '100%', position: 'relative', paddingBottom: 64}}>
<Toolbar
user={this.state.user}
organization={orgId}
page="Instances" />
<div style={styles.logoWrapper}>
<Logo />
</div>
<PrivatePage page="instance" {...this.props.params}>
<div style={styles.container}>
<FlexContainer>
<Column>
Expand All @@ -87,7 +44,7 @@ export default class InstancesPage extends React.Component {
<Column />
</FlexContainer>
</div>
</div>
</PrivatePage>
);
}

Expand Down
20 changes: 4 additions & 16 deletions ui-server/client/src/pages/organization/page.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,10 @@ import { getData, encodeURIs } from '../../common/request';
import { Box } from '../../components/box';
import { FlexContainer } from '../../components/flex-container';
import { Column } from '../../components/column';
import { Logo } from '../../components/logo';
import InstancesDelete from '../instances/instances-delete';
import PrivatePage from '../../components/private-page';
import Probes from './probes';
import Users from './users';
import Toolbar from '../../components/toolbar';
import { trackEvent, trackException, trackView } from '../../common/tracking';

export default class OrganizationPage extends React.Component {
Expand Down Expand Up @@ -140,7 +139,7 @@ export default class OrganizationPage extends React.Component {
marginBottom: 24
},
container: {
marginTop: 96
marginTop: 32
},
help: {
borderTop: `2px dotted ${grey200}`,
Expand All @@ -158,13 +157,6 @@ export default class OrganizationPage extends React.Component {
display: this.state.showHelp ? 'block' : 'none',
marginLeft: '-1em'
},
logoWrapper: {
position: 'absolute',
width: 250,
height: 64,
left: 64,
top: 32 + 51 - 3
},
circle: {
position: 'absolute',
left: -56,
Expand Down Expand Up @@ -192,18 +184,14 @@ export default class OrganizationPage extends React.Component {
};

return (
<div style={{height: '100%', position: 'relative'}}>
<PrivatePage page="organization" {...this.props.params}>
<Snackbar
action="ok"
open={Boolean(this.state.errors)}
message={this.state.errors ? this.state.errors.map(e => e.message).join('. ') : ''}
onActionTouchTap={this.clearErrors}
onRequestClose={this.clearErrors}
/>
<Toolbar user={this.state.user} organization={this.props.params.orgId} />
<div style={styles.logoWrapper}>
<Logo />
</div>
{this.state.id && <div style={styles.container}>
<FlexContainer>
<Column minWidth="500">
Expand Down Expand Up @@ -293,7 +281,7 @@ export default class OrganizationPage extends React.Component {
<CircularProgress mode="indeterminate" />
</div>}
</div>}
</div>
</PrivatePage>
);
}

Expand Down
Loading

0 comments on commit c134050

Please sign in to comment.