Add login page, and auto redirection to/from login page

This commit is contained in:
Itay Mizeretz 2018-02-22 15:23:47 +02:00
parent 52d75de864
commit c9d644f88a
3 changed files with 128 additions and 34 deletions

View File

@ -1,5 +1,5 @@
import React from 'react';
import {NavLink, Route, BrowserRouter as Router} from 'react-router-dom';
import {BrowserRouter as Router, NavLink, Redirect, Route} from 'react-router-dom';
import {Col, Grid, Row} from 'react-bootstrap';
import {Icon} from 'react-fa';
@ -11,6 +11,8 @@ import TelemetryPage from 'components/pages/TelemetryPage';
import StartOverPage from 'components/pages/StartOverPage';
import ReportPage from 'components/pages/ReportPage';
import LicensePage from 'components/pages/LicensePage';
import AuthComponent from 'components/AuthComponent';
import LoginPageComponent from 'components/pages/LoginPage';
require('normalize.css/normalize.css');
require('react-data-components/css/table-twbs.css');
@ -22,21 +24,9 @@ let logoImage = require('../images/monkey-icon.svg');
let infectionMonkeyImage = require('../images/infection-monkey.svg');
let guardicoreLogoImage = require('../images/guardicore-logo.png');
class AppComponent extends React.Component {
constructor(props) {
super(props);
this.state = {
completedSteps: {
run_server: true,
run_monkey: false,
infection_done: false,
report_done: false
}
};
}
class AppComponent extends AuthComponent {
updateStatus = () => {
fetch('/api')
this.authFetch('/api')
.then(res => res.json())
.then(res => {
// This check is used to prevent unnecessary re-rendering
@ -53,6 +43,34 @@ class AppComponent extends React.Component {
});
};
renderRoute = (route_path, page_component, is_exact_path = false) => {
let render_func = (props) => {
if (this.auth.loggedIn()) {
return page_component;
} else {
return <Redirect to={{pathname: '/login'}}/>;
}
};
if (is_exact_path) {
return <Route exact path={route_path} render={render_func}/>;
} else {
return <Route path={route_path} render={render_func}/>;
}
};
constructor(props) {
super(props);
this.state = {
completedSteps: {
run_server: true,
run_monkey: false,
infection_done: false,
report_done: false
}
};
}
componentDidMount() {
this.updateStatus();
this.interval = setInterval(this.updateStatus, 2000);
@ -78,7 +96,7 @@ class AppComponent extends React.Component {
<NavLink to="/" exact={true}>
<span className="number">1.</span>
Run C&C Server
{ this.state.completedSteps.run_server ?
{this.state.completedSteps.run_server ?
<Icon name="check" className="pull-right checkmark text-success"/>
: ''}
</NavLink>
@ -87,7 +105,7 @@ class AppComponent extends React.Component {
<NavLink to="/run-monkey">
<span className="number">2.</span>
Run Monkey
{ this.state.completedSteps.run_monkey ?
{this.state.completedSteps.run_monkey ?
<Icon name="check" className="pull-right checkmark text-success"/>
: ''}
</NavLink>
@ -96,7 +114,7 @@ class AppComponent extends React.Component {
<NavLink to="/infection/map">
<span className="number">3.</span>
Infection Map
{ this.state.completedSteps.infection_done ?
{this.state.completedSteps.infection_done ?
<Icon name="check" className="pull-right checkmark text-success"/>
: ''}
</NavLink>
@ -105,7 +123,7 @@ class AppComponent extends React.Component {
<NavLink to="/report">
<span className="number">4.</span>
Security Report
{ this.state.completedSteps.report_done ?
{this.state.completedSteps.report_done ?
<Icon name="check" className="pull-right checkmark text-success"/>
: ''}
</NavLink>
@ -136,14 +154,15 @@ class AppComponent extends React.Component {
</div>
</Col>
<Col sm={9} md={10} smOffset={3} mdOffset={2} className="main">
<Route exact path="/" render={(props) => ( <RunServerPage onStatusChange={this.updateStatus} /> )} />
<Route path="/configure" render={(props) => ( <ConfigurePage onStatusChange={this.updateStatus} /> )} />
<Route path="/run-monkey" render={(props) => ( <RunMonkeyPage onStatusChange={this.updateStatus} /> )} />
<Route path="/infection/map" render={(props) => ( <MapPage onStatusChange={this.updateStatus} /> )} />
<Route path="/infection/telemetry" render={(props) => ( <TelemetryPage onStatusChange={this.updateStatus} /> )} />
<Route path="/start-over" render={(props) => ( <StartOverPage onStatusChange={this.updateStatus} /> )} />
<Route path="/report" render={(props) => ( <ReportPage onStatusChange={this.updateStatus} /> )} />
<Route path="/license" render={(props) => ( <LicensePage onStatusChange={this.updateStatus} /> )} />
<Route path='/login' render={(props) => (<LoginPageComponent onStatusChange={this.updateStatus}/>)}/>
{this.renderRoute('/', <RunServerPage onStatusChange={this.updateStatus}/>, true)}
{this.renderRoute('/configure', <ConfigurePage onStatusChange={this.updateStatus}/>)}
{this.renderRoute('/run-monkey', <RunMonkeyPage onStatusChange={this.updateStatus}/>)}
{this.renderRoute('/infection/map', <MapPage onStatusChange={this.updateStatus}/>)}
{this.renderRoute('/infection/telemetry', <TelemetryPage onStatusChange={this.updateStatus}/>)}
{this.renderRoute('/start-over', <StartOverPage onStatusChange={this.updateStatus}/>)}
{this.renderRoute('/report', <ReportPage onStatusChange={this.updateStatus}/>)}
{this.renderRoute('/license', <LicensePage onStatusChange={this.updateStatus}/>)}
</Col>
</Row>
</Grid>

View File

@ -0,0 +1,78 @@
import React from 'react';
import {Col} from 'react-bootstrap';
import AuthService from '../../services/AuthService'
class LoginPageComponent extends React.Component {
login = () => {
this.auth.login(this.username, this.password).then(res => {
if (res['result']) {
this.redirectToHome();
} else {
this.setState({failed: true});
}
});
};
updateUsername = (evt) => {
this.username = evt.target.value;
};
updatePassword = (evt) => {
this.password = evt.target.value;
};
redirectToHome = () => {
window.location.href = '/';
};
constructor(props) {
super(props);
this.username = '';
this.password = '';
this.auth = new AuthService();
this.state = {
failed: false
};
if (this.auth.loggedIn()) {
this.redirectToHome();
}
}
render() {
return (
<Col xs={12} lg={8}>
<h1 className="page-title">Login</h1>
<div className="col-sm-6 col-sm-offset-3" style={{'fontSize': '1.2em'}}>
<div className="panel panel-default">
<div className="panel-heading text-center">
<b>Login</b>
</div>
<div className="panel-body">
<div className="input-group center-block text-center">
<input type="text" className="form-control" placeholder="Username"
onChange={evt => this.updateUsername(evt)}/>
<input type="password" className="form-control" placeholder="Password"
onChange={evt => this.updatePassword(evt)}/>
<button type="button" className="btn btn-primary btn-lg" style={{margin: '5px'}}
onClick={() => {
this.login()
}}>
Login
</button>
{
this.state.failed ?
<div className="alert alert-danger" role="alert">Login failed. Bad credentials.</div>
:
''
}
</div>
</div>
</div>
</div>
</Col>
);
}
}
export default LoginPageComponent;

View File

@ -2,22 +2,18 @@ import React from 'react';
import {Col} from 'react-bootstrap';
import {Link} from 'react-router-dom';
import AuthService from '../../services/AuthService'
class RunServerPageComponent extends React.Component {
constructor(props) {
super(props);
}
render() {
// TODO: something real
let auth = new AuthService();
auth.login('monkey', 'infectio1n');
return (
<Col xs={12} lg={8}>
<h1 className="page-title">1. Monkey Island C&C Server</h1>
<div style={{'fontSize': '1.2em'}}>
<p style={{'marginTop': '30px'}}>Congrats! You have successfully set up the Monkey Island server. &#x1F44F; &#x1F44F;</p>
<p style={{'marginTop': '30px'}}>Congrats! You have successfully set up the Monkey Island
server. &#x1F44F; &#x1F44F;</p>
<p>
The Infection Monkey is an open source security tool for testing a data center's resiliency to perimeter
breaches and internal server infections.
@ -25,7 +21,8 @@ class RunServerPageComponent extends React.Component {
center and reports to this Command and Control (C&C) server.
</p>
<p>
To read more about the Monkey, visit <a href="http://infectionmonkey.com" target="_blank">infectionmonkey.com</a>
To read more about the Monkey, visit <a href="http://infectionmonkey.com"
target="_blank">infectionmonkey.com</a>
</p>
<p>
Go ahead and <Link to="/run-monkey">run the monkey</Link>.