Merge pull request #206 from influxdata/feature/pretty-host

Feature/pretty host
pull/201/head
Andrew Watkins 2016-10-07 09:52:04 -07:00 committed by GitHub
commit 6e6daa5904
8 changed files with 316 additions and 71 deletions

View File

@ -55,18 +55,17 @@ const HostsTable = React.createClass({
const {source} = this.props;
return (
<div>
<div className="host-table-header">
<div className="panel panel-minimal">
<div className="panel-heading u-flex u-ai-center u-jc-space-between">
<h2 className="panel-title">{this.props.hosts.length} Hosts</h2>
<SearchBar onSearch={_.wrap(this.props.hosts, this.filterHosts)} />
<div className="active-source">
Source: {source.name}
</div>
</div>
<div className="panel-body">
<table className="table v-center">
<thead>
<tr>
<th onClick={this.changeSort} className="sortable-header">Hostname</th>
<th>Status</th>
<th className="text-center">Status</th>
<th>CPU</th>
<th>Load</th>
<th>Apps</th>
@ -77,11 +76,11 @@ const HostsTable = React.createClass({
hosts.map(({name, cpu, load}) => {
return (
<tr key={name}>
<td><a href={`/sources/${source.id}/hosts/${name}`}>{name}</a></td>
<td>UP</td>
<td>{`${cpu}%`}</td>
<td>{`${load}`}</td>
<td>influxdb, ntp, system</td>
<td className="monotype"><a href={`/sources/${source.id}/hosts/${name}`}>{name}</a></td>
<td className="text-center"><div className="table-dot dot-success"></div></td>
<td className="monotype">{`${cpu}%`}</td>
<td className="monotype">{`${load}`}</td>
<td className="monotype">influxdb, ntp, system</td>
</tr>
);
})
@ -89,6 +88,7 @@ const HostsTable = React.createClass({
</tbody>
</table>
</div>
</div>
);
},
});
@ -105,16 +105,16 @@ const SearchBar = React.createClass({
render() {
return (
<div className="users__search-widget input-group">
<div className="input-group-addon">
<span className="icon search" aria-hidden="true"></span>
</div>
<input
type="text"
className="form-control"
placeholder="Find host"
placeholder="Filter Hosts"
ref="searchInput"
onChange={this.handleChange}
/>
<div className="input-group-addon">
<span className="icon search" aria-hidden="true"></span>
</div>
</div>
);
},

View File

@ -21,6 +21,7 @@ export const HostPage = React.createClass({
render() {
const autoRefreshMs = 15000;
const source = this.props.source.links.proxy;
const hostID = this.props.params.hostID;
const queries = [
{
text: `SELECT "usage_user" FROM "telegraf".."cpu" WHERE host = '${this.props.params.hostID}' AND time > now() - 15m`,
@ -44,35 +45,37 @@ export const HostPage = React.createClass({
},
{
text: `SELECT "used_percent" FROM "telegraf".."disk" WHERE host = '${this.props.params.hostID}' AND time > now() - 15m`,
name: "Disk usage",
name: "Disk Usage",
},
];
return (
<div className="host">
<div className="enterprise-header">
<div className="host-dashboard hosts-page">
<div className="enterprise-header hosts-dashboard-header">
<div className="enterprise-header__container">
<div className="enterprise-header__left">
<h1>
Host - {this.props.params.hostID}
</h1>
<h1>{hostID}</h1>
</div>
<div className="enterprise-header__right">
<p>Uptime: <strong>2d 4h 33m</strong></p>
</div>
</div>
</div>
<div className="container-fluid">
<div className="container-fluid hosts-dashboard">
<div className="row">
{
queries.map((query) => {
const q = Object.assign({}, query, {host: source});
return (
<div className="col-md-4 graph-panel__graph-container" key={q.name}>
<h2>{q.name}</h2>
<div className="col-xs-12 col-sm-6 col-lg-4" key={q.name}>
<h2 className="hosts-graph-heading">{q.name}</h2>
<div className="hosts-graph graph-panel__graph-container">
<RefreshingLineGraph
queries={[q]}
autoRefresh={autoRefreshMs}
/>
</div>
</div>
);
})
}

View File

@ -51,12 +51,12 @@ export const HostsPage = React.createClass({
render() {
return (
<div className="hosts">
<div className="hosts hosts-page">
<div className="enterprise-header">
<div className="enterprise-header__container">
<div className="enterprise-header__left">
<h1>
Hosts
Host List
</h1>
</div>
</div>
@ -65,15 +65,11 @@ export const HostsPage = React.createClass({
<div className="container-fluid">
<div className="row">
<div className="col-md-12">
<div className="panel panel-minimal">
<div className="panel-body">
<HostsTable source={this.props.source} hosts={this.state.hosts} />
</div>
</div>
</div>
</div>
</div>
</div>
);
},

View File

@ -61,7 +61,7 @@ export const SelectSourcePage = React.createClass({
render() {
const error = !!this.props.location.query.redirectPath;
return (
<div className="page-wrapper" id="select-source-page">
<div id="select-source-page">
<div className="container">
<div className="row">
<div className="col-md-8 col-md-offset-2">

View File

@ -2,10 +2,6 @@
$default-border-radius: 4px;
.dygraph-axis-label {
color: $graph-axis-label;
}
.dygraph-title {
font-weight: 300;
font-size: 0.75em;
@ -37,8 +33,20 @@ $default-border-radius: 4px;
height: 28px;
}
.dygraph-axis-label {
font-size: 13px;
line-height: 13px;
color: $graph-axis-label;
width: 100%;
display: block;
}
.dygraph-axis-label-y {
padding-right: 0.75em;
text-align: left !important;
padding-right: 0.3em;
}
.dygraph-axis-label-x {
padding-top: 0.3em;
text-align: center !important;
}
.line-graph__legend {
@ -59,6 +67,7 @@ $default-border-radius: 4px;
* Only animate position that's controlled during rendering.
* See http://stackoverflow.com/a/17117992
*/
transition: all 0.2s ease;
transition-property: top, right, bottom, left;
@ -91,4 +100,3 @@ $default-border-radius: 4px;
pointer-events: none;
display: none;
}

View File

@ -11,6 +11,7 @@
position: absolute;
top: 0;
left: 0;
background-color: $g1-raven;
&__header {
margin-bottom: 0;

View File

@ -19,7 +19,6 @@ body {
*/
body > #react-root {
width: 100%;
.container {
margin-top: 60px;
}
@ -66,7 +65,7 @@ body > #react-root {
.page-wrapper {
position: relative;
flex-grow: 1;
overflow: auto;
overflow: hidden;
background: $g18-cloud;
background: -moz-linear-gradient(top, $g18-cloud 0%, $g19-ghost 100%);
background: -webkit-linear-gradient(top, $g18-cloud 0%,$g19-ghost 100%);
@ -80,6 +79,15 @@ body > #react-root {
background-size: contain;
}
.page-wrapper > div {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
overflow: hidden;
}
/*
Enterprise Page Header
----------------------------------------------
@ -87,7 +95,7 @@ body > #react-root {
.enterprise-header {
background-color: $g20-white;
height: $enterprise-page-header-height;
margin-bottom: 45px;
margin-bottom: 15px;
padding: 0 $page-wrapper-padding;
display: flex;
justify-content: center;
@ -591,9 +599,6 @@ table.table.error-table {
margin-bottom: 12px;
}
/*
Static Form Controls
----------------------------------------------
@ -605,3 +610,39 @@ table.table.error-table {
padding: 0 18px;
line-height: 36px;
}
/*
Stuff for making Tables of Data more readable
----------------------------------------------
*/
table .monotype {
font-family: Consolas, "Lucida Console", Monaco, monospace;
letter-spacing: 0.69px;
font-size: 12px;
font-weight: 700;
color: $g9-mountain;
}
.table-dot {
display: inline-block;
width: 12px;
height: 12px;
border-radius: 50%;
background-color: $g17-whisper;
&.dot-success {
background-color: $c-rainforest;
}
&.dot-primary {
background-color: $c-pool;
}
&.dot-warning {
background-color: $c-comet;
}
&.dot-danger {
background-color: $c-dreamsicle;
}
&.dot-critical {
background-color: $c-fire;
}
}

View File

@ -1,3 +1,199 @@
/*
Hosts Dashboard
----------------------------------------------
*/
.hosts-page {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
overflow: auto;
background: $g2-kevlar;
background: -moz-linear-gradient(top, $g2-kevlar 0%, $g0-obsidian 100%);
background: -webkit-linear-gradient(top, $g2-kevlar 0%, $g0-obsidian 100%);
background: linear-gradient(to bottom, $g2-kevlar 0%, $g0-obsidian 100%);
filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='$g2-kevlar', endColorstr='$g0-obsidian',GradientType=0 );
color: $g17-whisper;
&::-webkit-scrollbar {
width: 14px;
height: 14px;
&-button {
background-color: $g0-obsidian;
}
&-track {
background-color: $g0-obsidian;
}
&-track-piece {
background: $g0-obsidian;
}
&-thumb {
background-color: $c-pool;
border: 4px solid $g0-obsidian;
border-radius: 7px;
}
&-corner {
background-color: $g0-obsidian;
}
&-resizer {
background-color: $c-pool;
}
}
.enterprise-header {
background-color: $g0-obsidian;
}
.panel-minimal {
border: 0;
.panel-title {
color: $g17-whisper !important;
}
.panel-body {
padding: 30px;
background-color: $g3-castle;
border: 0;
color: $g17-whisper;
> *:first-child {
margin-top: 0;
}
> *:last-child {
margin-bottom: 0;
}
table {
th,td {
border-color: $g5-pepper;
}
th {
color: $g17-whisper;
}
td {
color: $g14-chromium;
}
tbody tr:last-child td {
border-bottom: 2px solid $g5-pepper;
}
}
}
}
.users__search-widget {
position: relative;
input.form-control {
position: relative;
width: 100%;
z-index: 1;
background-color: $g2-kevlar;
border-color: $g5-pepper;
color: $g17-whisper;
border-radius: 4px;
padding-left: 34px;
&:focus {
border-color: $c-pool !important;
color: $c-pool;
&::-webkit-input-placeholder {
color: $c-pool;
}
&::-moz-placeholder {
color: $c-pool;
}
&:-ms-input-placeholder {
color: $c-pool;
}
&:-moz-placeholder {
color: $c-pool;
}
& + .input-group-addon {
color: $c-pool;
}
}
&::-webkit-input-placeholder {
color: $g11-sidewalk;
}
&::-moz-placeholder {
color: $g11-sidewalk;
}
&:-ms-input-placeholder {
color: $g11-sidewalk;
}
&:-moz-placeholder {
color: $g11-sidewalk;
}
}
.input-group-addon {
padding: 0;
text-align: center;
line-height: 38px;
position: absolute;
top: 0;
left: 0;
height: 100%;
z-index: 2;
border: 0;
width: 40px;
background-color: transparent;
transition:
color 0.25s ease;
}
}
}
.hosts-dashboard {
max-width: 100%;
}
.graph-panel__graph-container.hosts-graph {
margin-bottom: 15px;
padding: 9.5px 16px;
}
.hosts-graph-heading {
display: block;
width: 100%;
margin: 15px 0 0 0;
background-color: $g5-pepper;
padding: 9.5px 16px;
font-weight: 500;
font-size: 16px;
color: $g14-chromium;
border-radius: 4px 4px 0 0;
}
.hosts-dashboard-header {
.enterprise-header__container {
max-width: 100%;
}
.enterprise-header__left {
flex-direction: row;
align-items: center;
> * {
margin-right: 15px;
&:last-child {
margin-right: 0;
}
}
}
.enterprise-header__right {
font-size: inherit;
}
}
.host-list--active-source {
text-transform: uppercase;
font-size: 15px;
font-weight: 400;
color: $g17-whisper;
span {
font-weight: 900;
}
}
.sortable-header {
cursor: pointer;
}