fleet/frontend/layouts/CoreLayout/CoreLayout.jsx
Martavis Parker bcfac603f0
Added components to Storybook library (#2768)
* added storybook

* added avatar component

* added button story

* added dropdown button story

* removed unused ellipsis component

* cleaned up modal path

* reorganized enroll secrets table file

* added flash story; removed unused persistent flash

* added fleet ace story

* added checkbox story

* added dropdown story

* added input story

* fixed storybook build

* fixed avatar

* added input with icon story

* added radio button story

* added select targets dropdown story

* added slider story

* added tooltip story

* added info banner story

* removed unused loaders; added spinner story

* added modal story

* removed unused NumberPill

* added pagination story

* lint fixes

* added documentation to run

* modified documentation

* fixed corelayout test

* fixed format for date-fns

* fixed date format that breaks tests

* wait for page
2021-11-06 23:41:09 -07:00

213 lines
5.0 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import React, { Component } from "react";
import PropTypes from "prop-types";
import { connect } from "react-redux";
import { logoutUser } from "redux/nodes/auth/actions";
import { push } from "react-router-redux";
import { TableContext } from "context/table";
import { isEqual } from "lodash";
import permissionUtils from "utilities/permissions";
import configInterface from "interfaces/config";
import FlashMessage from "components/FlashMessage";
import SiteTopNav from "components/side_panels/SiteTopNav";
import userInterface from "interfaces/user";
import notificationInterface from "interfaces/notification";
import { hideFlash } from "redux/nodes/notifications/actions";
import { licenseExpirationWarning } from "fleet/helpers";
const expirationMessage = (
<>
Your license for Fleet Premium is about to expire. If youd like to renew or
have questions about downgrading,{" "}
<a
href="https://github.com/fleetdm/fleet/blob/main/docs/01-Using-Fleet/10-Teams.md#expired_license"
target="_blank"
rel="noopener noreferrer"
>
please head to the Fleet documentation
</a>
.
</>
);
export class CoreLayout extends Component {
static propTypes = {
children: PropTypes.node,
config: configInterface,
dispatch: PropTypes.func,
user: userInterface,
fullWidthFlash: PropTypes.bool,
notifications: notificationInterface,
isPremiumTier: PropTypes.bool,
};
constructor(props) {
super(props);
this.state = {
showExpirationFlashMessage: false,
};
}
componentWillReceiveProps(nextProps) {
const { notifications, config } = nextProps;
const table = this.context;
// on success of an action, the table will reset its checkboxes.
// setTimeout is to help with race conditions as table reloads
// in some instances (i.e. Manage Hosts)
if (!isEqual(this.props.notifications, notifications)) {
if (notifications.alertType === "success") {
setTimeout(() => {
table.setResetSelectedRows(true);
setTimeout(() => {
table.setResetSelectedRows(false);
}, 300);
}, 0);
}
}
this.setState({
showExpirationFlashMessage: licenseExpirationWarning(config.expiration),
});
}
onLogoutUser = () => {
const { dispatch } = this.props;
dispatch(logoutUser());
return false;
};
onNavItemClick = (path) => {
return (evt) => {
evt.preventDefault();
const { dispatch } = this.props;
if (path.indexOf("http") !== -1) {
global.window.open(path, "_blank");
return false;
}
dispatch(push(path));
return false;
};
};
onRemoveFlash = () => {
const { dispatch } = this.props;
dispatch(hideFlash);
return false;
};
onRemoveExpirationWarning = () => {
const { showExpirationFlashMessage } = this.state;
this.setState({
showExpirationFlashMessage: !showExpirationFlashMessage,
});
};
onUndoActionClick = (undoAction) => {
return (evt) => {
evt.preventDefault();
const { dispatch } = this.props;
const { onRemoveFlash } = this;
dispatch(undoAction);
return onRemoveFlash();
};
};
static contextType = TableContext;
render() {
const {
fullWidthFlash,
notifications,
children,
config,
user,
isPremiumTier,
} = this.props;
const { showExpirationFlashMessage } = this.state;
const {
onRemoveFlash,
onRemoveExpirationWarning,
onUndoActionClick,
} = this;
const expirationNotification = {
alertType: "warning-filled",
isVisible: true,
message: expirationMessage,
};
if (!user) return false;
const { onLogoutUser, onNavItemClick } = this;
const { pathname } = global.window.location;
return (
<div className="app-wrap">
<nav className="site-nav">
<SiteTopNav
config={config}
onLogoutUser={onLogoutUser}
onNavItemClick={onNavItemClick}
pathname={pathname}
user={user}
/>
</nav>
<div className="core-wrapper">
{isPremiumTier && showExpirationFlashMessage && (
<FlashMessage
fullWidth={fullWidthFlash}
notification={expirationNotification}
onRemoveFlash={onRemoveExpirationWarning}
/>
)}
<FlashMessage
fullWidth={fullWidthFlash}
notification={notifications}
onRemoveFlash={onRemoveFlash}
onUndoActionClick={onUndoActionClick}
/>
{children}
</div>
</div>
);
}
}
const mapStateToProps = (state) => {
const {
app: { config },
auth: { user },
notifications,
} = state;
const isPremiumTier = permissionUtils.isPremiumTier(state.app.config);
const fullWidthFlash = !user;
return {
config,
fullWidthFlash,
notifications,
user,
isPremiumTier,
};
};
export default connect(mapStateToProps)(CoreLayout);