-
- Dashboard {isActive('/', fragment) && (current) }
+
+ Requests {isActive('requests', fragment) && (current) }
Status {isActive('status', fragment) && (current) }
-
- Requests {isActive('requests', fragment) && (current) }
-
Tasks {isActive('tasks', fragment) && (current) }
diff --git a/SingularityUI/app/components/dashboard/DashboardPage.jsx b/SingularityUI/app/components/dashboard/DashboardPage.jsx
deleted file mode 100644
index 52a4c74f8b..0000000000
--- a/SingularityUI/app/components/dashboard/DashboardPage.jsx
+++ /dev/null
@@ -1,228 +0,0 @@
-import React, { Component, PropTypes } from 'react';
-import { Row, Col } from 'react-bootstrap';
-import { connect } from 'react-redux';
-import rootComponent from '../../rootComponent';
-import { Link } from 'react-router';
-
-import Utils from '../../utils';
-import Loader from '../common/Loader';
-
-import { refresh } from '../../actions/ui/dashboard';
-import { FetchUserRelevantRequests } from '../../actions/api/requests';
-import UITable from '../common/table/UITable';
-import Column from '../common/table/Column';
-import Section from '../common/Section';
-import RequestTypeIcon from '../common/icons/RequestTypeIcon'
-import * as Cols from '../requests/Columns';
-import RequestSummaryBox from './RequestSummaryBox';
-import RequestFilters from '../requests/RequestFilters';
-
-class DashboardPage extends Component {
- static propTypes = {
- requests: PropTypes.arrayOf(PropTypes.object).isRequired,
- fetchRequests: PropTypes.func.isRequired
- };
-
- constructor(props) {
- super(props);
- this.state = {
- requestTypeFilters: RequestFilters.REQUEST_TYPES,
- loading: false
- };
- }
-
- getCurrentEventAndTime(request) {
- let lastEvent;
- let lastEventTime = 0;
- if (request.requestDeployState && request.requestDeployState.pendingDeploy) {
- const pendingDeploy = request.requestDeployState.pendingDeploy;
- lastEvent = (
-
- Deploy - {pendingDeploy.deployId}{pendingDeploy.user && ` by ${pendingDeploy.user}`} is pending
-
- );
- lastEventTime = request.requestDeployState.pendingDeploy.timestamp
- }
- if (request.requestDeployState && request.requestDeployState.activeDeploy && request.requestDeployState.activeDeploy.timestamp > lastEventTime) {
- const activeDeploy = request.requestDeployState.activeDeploy;
- lastEvent = (
-
- Deployed {Utils.timestampFromNow(activeDeploy.timestamp)}{activeDeploy.user && ` by ${activeDeploy.user}`}
-
- );
- lastEventTime = request.requestDeployState.activeDeploy.timestamp
- }
- if (request.expiringBounce && request.expiringBounce.startMillis > lastEventTime) {
- lastEvent = (
- Bouncing -{request.expiringBounce.user && ` started by ${request.expiringBounce.user}`} {Utils.timestampFromNow(request.expiringBounce.startMillis)}
- );
- lastEventTime = request.expiringBounce.startMillis;
- }
- if (request.expiringPause && request.expiringPause.startMillis > lastEventTime) {
- lastEvent = (
- Paused {request.expiringPause.user && ` by ${request.expiringPause.user}`} {Utils.timestampFromNow(request.expiringPause.startMillis)} will unpause in {Utils.duration(request.expiringPause.expiringAPIRequestObject.durationMillis)}
- );
- lastEventTime = request.expiringPause.startMilli;
- }
- if (request.expiringScale && request.expiringScale.startMillis > lastEventTime) {
- lastEvent = (
- Scaled {request.expiringScale.user && ` by ${request.expiringScale.user}`} to "{request.request.instances}" {Utils.timestampFromNow(request.expiringScale.startMillis)}, will revert to "{request.expiringScale.revertToInstances}" in {Utils.duration(request.expiringScale.expiringAPIRequestObject.durationMillis)}
- );
- lastEventTime = request.expiringScale.startMillis;
- }
- if (request.expiringSkipHealthchecks && request.expiringSkipHealthchecks.startMillis > lastEventTime) {
- lastEvent = (
- Healthchecks disabled {request.expiringSkipHealthchecks.user && ` by ${request.expiringSkipHealthchecks.user}`} {Utils.timestampFromNow(request.expiringSkipHealthchecks.startMillis)}, will enable in {Utils.duration(request.expiringSkipHealthchecks.expiringAPIRequestObject.durationMillis)}
- );
- lastEventTime = request.expiringSkipHealthchecks.startMillis;
- }
- if (request.lastHistory && request.lastHistory.createdAt > lastEventTime) {
- lastEvent = (
- {Utils.humanizeText(request.lastHistory.eventType)} {Utils.timestampFromNow(request.lastHistory.createdAt)} {request.lastHistory.user && `by ${request.lastHistory.user}`}
- );
- lastEventTime = request.lastHistory.createdAt;
- }
- if (request.request.requestType != 'SERVICE' && request.request.requestType != 'WORKER' && request.mostRecentTask && request.mostRecentTask.updatedAt > lastEventTime) {
- lastEvent = (
-
-
- {Utils.humanizeText(request.mostRecentTask.lastTaskState)}
-
- {` ${Utils.timestampFromNow(request.mostRecentTask.updatedAt)}`}
-
- );
- lastEventTime = request.mostRecentTask.updatedAt;
- }
- if (!lastEvent) {
- lastEvent = (No Recent Activity
);
- }
- return {
- lastEvent: lastEvent,
- lastEventTime: lastEventTime
- }
- }
-
- toggleRequestType(requestType) {
- let selected = this.state.requestTypeFilters;
- if (selected.length === RequestFilters.REQUEST_TYPES.length) {
- selected = [requestType];
- } else if (_.isEmpty(_.without(selected, requestType))) {
- selected = RequestFilters.REQUEST_TYPES;
- } else if (_.contains(selected, requestType)) {
- selected = _.without(selected, requestType);
- } else {
- selected.push(requestType);
- }
- this.setState({
- requestTypeFilters: selected,
- loading: true
- })
- this.props.fetchRequests(selected).then(() => {
- this.setState({
- loading: false
- })
- })
-
- }
-
- render() {
- const summaryColumn = (
- this.getCurrentEventAndTime(rowData).lastEventTime}
- cellRender={
- (cellData, rowData) => {
- return (
-
- );
- }
- }
- />
- );
-
- const filterItems = RequestFilters.REQUEST_TYPES.map((requestType, index) => {
- const isActive = _.contains(this.state.requestTypeFilters, requestType);
- return (
-
- this.toggleRequestType(requestType)}>
- {isActive ? : } {Utils.humanizeText(requestType)}
-
-
- );
- });
-
- let table;
-
- if (this.state.loading) {
- table = ;
- } else {
- table = (
- requestParent.request.id}
- paginated={false}
- defaultSortBy="summary"
- defaultSortDirection={UITable.SortDirection.ASC}
- renderAllRows={true}
- >
- {[
- Cols.Starred,
- Cols.Type,
- Cols.State,
- Cols.RequestId,
- summaryColumn,
- Cols.Actions
- ]}
-
- );
- }
-
- return (
-
-
-
-
- My Requests
-
-
-
-
-
-
- {table}
-
- );
- }
-}
-
-function mapStateToProps(state) {
- const modifiedRequests = state.api.userRelevantRequests.data.map((request) => {
- const hasActiveDeploy = !!(request.activeDeploy || (request.requestDeployState && request.requestDeployState.activeDeploy));
- return {
- ...request,
- hasActiveDeploy,
- canBeRunNow: request.state === 'ACTIVE' && _.contains(['SCHEDULED', 'ON_DEMAND'], request.request.requestType) && hasActiveDeploy,
- canBeScaled: _.contains(['ACTIVE', 'SYSTEM_COOLDOWN'], request.state) && hasActiveDeploy && _.contains(['WORKER', 'SERVICE'], request.request.requestType),
- id: request.request ? request.request.id : request.requestId
- };
- });
- return {requests: modifiedRequests}
-}
-
-function mapDispatchToProps(dispatch) {
- return {
- fetchRequests: (requestTypes) => dispatch(FetchUserRelevantRequests.trigger(requestTypes))
- }
-}
-
-export default connect(mapStateToProps, mapDispatchToProps)(rootComponent(DashboardPage, refresh));
diff --git a/SingularityUI/app/components/dashboard/RequestSummaryBox.jsx b/SingularityUI/app/components/dashboard/RequestSummaryBox.jsx
deleted file mode 100644
index c199697589..0000000000
--- a/SingularityUI/app/components/dashboard/RequestSummaryBox.jsx
+++ /dev/null
@@ -1,182 +0,0 @@
-import React, { Component, PropTypes } from 'react';
-import { Glyphicon, PanelGroup, Panel, Well, Button, Col, Row } from 'react-bootstrap'
-import { Link } from 'react-router';
-
-import Utils from '../../utils';
-
-import UITable from '../common/table/UITable';
-import {
- Health,
- InstanceNumberWithHostname,
- DeployId,
- UpdatedAt,
- StartedAt,
- LogLinkAndActions,
- NextRun,
- PendingType,
- PendingDeployId
-} from '../tasks/Columns';
-
-export default class RequestSummaryBox extends Component {
- static propTypes = {
- request: PropTypes.object.isRequired,
- currentEvent: PropTypes.object.isRequired
- };
-
- constructor() {
- super();
- this.state = {
- showTasks: false
- };
- }
-
- getActivityPanelStyle(request) {
- if (request.state === "ACTIVE") {
- if (request.hasActiveDeploy) {
- return "info";
- } else {
- return "default";
- }
- } else if (request.state === "PAUSED") {
- return "warning";
- } else {
- return "info";
- }
- }
-
- getTasksPanelStyle(request) {
- let healthyTasks = 0;
- healthyTasks += this.props.request.taskIds && this.props.request.taskIds.healthy.length || 0
- healthyTasks += this.props.request.taskIds && this.props.request.taskIds.cleaning.length || 0
- if (request.instances > healthyTasks) {
- return "warning"
- } else if (!(this.props.request.requestDeployState && this.props.request.requestDeployState.activeDeploy)) {
- return "default"
- } else {
- return "info"
- }
- }
-
- getTasksHeader(taskIds) {
- const cleaning = this.props.request.taskIds && this.props.request.taskIds.cleaning.length || 0
- const healthy = this.props.request.taskIds && this.props.request.taskIds.healthy.length || 0
- const notYetHealthy = this.props.request.taskIds && this.props.request.taskIds.notYetHealthy.length || 0
- const pending = this.props.request.taskIds && this.props.request.taskIds.pending.length || 0
-
- if (cleaning == 0 && healthy == 0 && notYetHealthy == 0 && pending == 0) {
- return "No Tasks"
- } else {
- let header = "Tasks -";
- if (healthy > 0) {
- header = header + ` ${healthy} Healthy `
- }
- if (notYetHealthy > 0) {
- header = header + ` ${notYetHealthy} Not Yet Healthy `
- }
- if (cleaning > 0) {
- header = header + ` ${cleaning} Cleaning `
- }
- if (pending > 0) {
- header = header + ` ${pending} Pending`
- }
- return header
- }
- }
-
- render() {
- const tasks = [];
- const pendingTasks = [];
- _.each(this.props.request.taskIds, (taskIds, status) => {
- if (status === "pending") {
- taskIds.forEach((taskId) => {
- pendingTasks.push({
- pendingTask: {
- pendingTaskId: taskId
- }
- });
- })
- } else {
- taskIds.forEach((taskId) => {
- tasks.push({
- taskId: taskId,
- instanceNo: taskId.instanceNo,
- health: status
- });
- })
- }
- });
-
- let activeDeploy;
- if (this.props.request.requestDeployState && this.props.request.requestDeployState.activeDeploy) {
- activeDeploy = (
- Active Deploy (
-
- {this.props.request.requestDeployState.activeDeploy.deployId}
-
- )
-
- )
- } else {
- activeDeploy = "No Active Deploy"
- }
-
- const pendingTasksTable = (
- task.pendingTask.pendingTaskId.id}
- emptyTableMessage='No tasks'
- defaultSortBy="instanceNo"
- >
- {NextRun}
- {PendingType}
- {PendingDeployId}
-
- );
-
- const tasksTable = (
- task.taskId.id}
- emptyTableMessage='No tasks'
- defaultSortBy="instanceNo"
- >
- {Health}
- {InstanceNumberWithHostname}
- {DeployId}
- {StartedAt}
- {UpdatedAt}
- {LogLinkAndActions(config.runningTaskLogPath, this.props.request.requestType)}
-
- );
-
- return (
-
-
-
- {activeDeploy}
-
-
- {this.props.currentEvent}
-
-
- {(tasks.length > 0 || pendingTasks.length > 0) &&
-
-
- this.setState({ showTasks: !this.state.showTasks })}>
- {`${this.getTasksHeader(this.props.request.taskIds)}`}
-
-
- {tasks.length > 0 && tasksTable}
- {pendingTasks.length > 0 && pendingTasksTable}
-
-
-
- }
-
- );
- }
-}
diff --git a/SingularityUI/app/components/requests/RequestFilters.jsx b/SingularityUI/app/components/requests/RequestFilters.jsx
index 311eb7532e..d8529e685d 100644
--- a/SingularityUI/app/components/requests/RequestFilters.jsx
+++ b/SingularityUI/app/components/requests/RequestFilters.jsx
@@ -149,7 +149,13 @@ export default class RequestFilters extends React.Component {
placeholder="Filter requests"
value={this.props.filter.searchFilter}
onChange={(...args) => this.handleSearchChange(...args)}
+ autoFocus="true"
maxLength="128"
+ onFocus={function(e) {
+ var val = e.target.value;
+ e.target.value = '';
+ e.target.value = val;
+ }}
/>
this.clearSearch()}>