Change imports with helper plugin

This commit is contained in:
soupette 2019-04-16 11:53:29 +02:00
parent b68a04d0fc
commit 751a794ca8
38 changed files with 405 additions and 324 deletions

View File

@ -11,7 +11,9 @@ import 'sanitize.css/sanitize.css';
import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux';
import { ConnectedRouter } from 'react-router-redux';
import { BrowserRouter } from 'react-router-dom';
// import { ConnectedRouter } from 'react-router-redux';
import basename from './utils/basename';
import { merge } from 'lodash';
import {
@ -126,9 +128,10 @@ const render = messages => {
ReactDOM.render(
<Provider store={store}>
<LanguageProvider messages={messages}>
<ConnectedRouter history={history}>
{/* <ConnectedRouter history={history}> */}
<BrowserRouter basename={basename}>
<App store={store} />
</ConnectedRouter>
</BrowserRouter>
</LanguageProvider>
</Provider>,
MOUNT_NODE,

View File

@ -11,7 +11,7 @@ import { FormattedMessage } from 'react-intl';
import { map, size } from 'lodash';
// Design
import Button from 'components/Button';
import { Button } from 'strapi-helper-plugin';
import Row from '../Row';
import styles from './styles.scss';

View File

@ -14,7 +14,7 @@ import {
DropdownMenu,
DropdownToggle,
} from 'reactstrap';
import auth from 'utils/auth';
import { auth } from 'strapi-helper-plugin';
import styles from './styles.scss';
@ -33,7 +33,7 @@ class Logout extends React.Component {
handleGoToAdministrator = () => {
this.context.router.history.push({
pathname: `/plugins/content-manager/administrator`,
pathname: '/plugins/content-manager/administrator',
search: '?source=admin',
});
};

View File

@ -1,8 +1,8 @@
/**
*
* PluginCard
*
*/
*
* PluginCard
*
*/
import React from 'react';
import PropTypes from 'prop-types';
@ -10,7 +10,7 @@ import cn from 'classnames';
import { isEmpty, replace } from 'lodash';
import { FormattedMessage } from 'react-intl';
import Button from 'components/Button';
import { Button } from 'strapi-helper-plugin';
import InstallPluginPopup from '../InstallPluginPopup';
import styles from './styles.scss';
@ -19,7 +19,7 @@ const PLUGINS_WITH_CONFIG = ['content-manager', 'email', 'upload'];
/* eslint-disable react/no-unused-state */
class PluginCard extends React.Component {
state = {
state = {
boostrapCol: 'col-lg-4',
};
@ -45,7 +45,7 @@ class PluginCard extends React.Component {
}
this.setState({ boostrapCol });
}
};
handleClick = () => {
if (this.props.plugin.id !== 'support-us') {
@ -56,42 +56,72 @@ class PluginCard extends React.Component {
} else {
this.aTag.click();
}
}
};
handleClickSettings = (e) => {
const settingsPath = this.props.plugin.id === 'content-manager' ? '/plugins/content-manager/ctm-configurations' : `/plugins/${this.props.plugin.id}/configurations/${this.props.currentEnvironment}`;
handleClickSettings = e => {
const settingsPath =
this.props.plugin.id === 'content-manager'
? '/plugins/content-manager/ctm-configurations'
: `/plugins/${this.props.plugin.id}/configurations/${
this.props.currentEnvironment
}`;
e.preventDefault();
e.stopPropagation();
this.props.history.push(settingsPath);
}
};
handleDownloadPlugin = (e) => {
if (!this.props.isAlreadyInstalled && this.props.plugin.id !== 'support-us') {
handleDownloadPlugin = e => {
if (
!this.props.isAlreadyInstalled &&
this.props.plugin.id !== 'support-us'
) {
this.props.downloadPlugin(e);
} else if (this.props.plugin.id === 'support-us') {
this.aTag.click();
} else {
this.props.history.push('/list-plugins');
}
}
};
render() {
const buttonClass = !this.props.isAlreadyInstalled ? styles.primary : styles.secondary;
const buttonLabel = this.props.isAlreadyInstalled ? 'app.components.PluginCard.Button.label.install' : 'app.components.PluginCard.Button.label.download';
const buttonClass = !this.props.isAlreadyInstalled
? styles.primary
: styles.secondary;
const buttonLabel = this.props.isAlreadyInstalled
? 'app.components.PluginCard.Button.label.install'
: 'app.components.PluginCard.Button.label.download';
// Display settings link for a selection of plugins.
const settingsComponent = (PLUGINS_WITH_CONFIG.includes(this.props.plugin.id) &&
const settingsComponent = PLUGINS_WITH_CONFIG.includes(
this.props.plugin.id,
) && (
<div className={styles.settings} onClick={this.handleClickSettings}>
<i className='fa fa-cog' />
<FormattedMessage id='app.components.PluginCard.settings' />
<i className="fa fa-cog" />
<FormattedMessage id="app.components.PluginCard.settings" />
</div>
);
const descriptions = {
short: this.props.plugin.id === 'support-us' ? <FormattedMessage id={this.props.plugin.description.short} /> : this.props.plugin.description.short,
long: this.props.plugin.id === 'support-us' ? <FormattedMessage id={this.props.plugin.description.long || this.props.plugin.description.short} /> : this.props.plugin.description.long || this.props.plugin.description.short,
short:
this.props.plugin.id === 'support-us' ? (
<FormattedMessage id={this.props.plugin.description.short} />
) : (
this.props.plugin.description.short
),
long:
this.props.plugin.id === 'support-us' ? (
<FormattedMessage
id={
this.props.plugin.description.long ||
this.props.plugin.description.short
}
/>
) : (
this.props.plugin.description.long ||
this.props.plugin.description.short
),
};
return (
@ -102,7 +132,20 @@ class PluginCard extends React.Component {
<span className={styles.helper} />
<img src={this.props.plugin.logo} alt="icon" />
</div>
<div>{this.props.plugin.name} <i className='fa fa-external-link' onClick={() => window.open(`https://github.com/strapi/strapi/tree/master/packages/strapi-plugin-${this.props.plugin.id}`, '_blank')} /></div>
<div>
{this.props.plugin.name}{' '}
<i
className="fa fa-external-link"
onClick={() =>
window.open(
`https://github.com/strapi/strapi/tree/master/packages/strapi-plugin-${
this.props.plugin.id
}`,
'_blank',
)
}
/>
</div>
</div>
<div className={styles.cardDescription}>
{descriptions.long}
@ -118,30 +161,43 @@ class PluginCard extends React.Component {
<a
href="https://strapi.io/shop"
style={{ display: 'none' }}
ref={(a) => { this.aTag = a; }}
ref={a => {
this.aTag = a;
}}
target="_blank"
>
&nbsp;
</a>
</div>
{this.props.isAlreadyInstalled ?
(
settingsComponent
)
:
(
<div className={styles.compatible}>
<i className={`fa fa-${this.props.plugin.isCompatible ? 'check' : 'times'}`} />
<FormattedMessage id={`app.components.PluginCard.compatible${this.props.plugin.id === 'support-us' ? 'Community' : ''}`} />
</div>
)
}
{this.props.isAlreadyInstalled ? (
settingsComponent
) : (
<div className={styles.compatible}>
<i
className={`fa fa-${
this.props.plugin.isCompatible ? 'check' : 'times'
}`}
/>
<FormattedMessage
id={`app.components.PluginCard.compatible${
this.props.plugin.id === 'support-us' ? 'Community' : ''
}`}
/>
</div>
)}
</div>
</div>
<InstallPluginPopup
history={this.props.history}
isAlreadyInstalled={this.props.isAlreadyInstalled}
isOpen={!isEmpty(this.props.history.location.hash) && replace(this.props.history.location.hash.split('::')[0], '#', '') === this.props.plugin.id}
isOpen={
!isEmpty(this.props.history.location.hash) &&
replace(
this.props.history.location.hash.split('::')[0],
'#',
'',
) === this.props.plugin.id
}
plugin={this.props.plugin}
/>
</div>

View File

@ -1,8 +1,8 @@
/*
*
* Row
*
*/
*
* Row
*
*/
import React from 'react';
import PropTypes from 'prop-types';
@ -11,9 +11,7 @@ import { FormattedMessage } from 'react-intl';
import { includes, isEmpty } from 'lodash';
// Design
import IcoContainer from 'components/IcoContainer';
import ListRow from 'components/ListRow';
import PopUpWarning from 'components/PopUpWarning';
import { IcoContainer, ListRow, PopUpWarning } from 'strapi-helper-plugin';
import styles from './styles.scss';
@ -28,44 +26,53 @@ class Row extends React.Component {
}
}
handleClick = (e) => {
handleClick = e => {
this.setState({ showModal: !this.state.showModal });
this.props.onDeleteClick(e);
}
};
render() {
// const uploadPath = `/plugins/upload/configurations/${this.context.currentEnvironment}`;
// Make sure to match the ctm config URI instead of content-type view URI
const settingsPath = this.props.name === 'content-manager' ? '/plugins/content-manager/ctm-configurations' : `/plugins/${this.props.name}/configurations/${this.context.currentEnvironment}`;
const settingsPath =
this.props.name === 'content-manager'
? '/plugins/content-manager/ctm-configurations'
: `/plugins/${this.props.name}/configurations/${
this.context.currentEnvironment
}`;
// const icons = this.props.name === 'upload' || this.props.name === 'email' ? [
const icons = includes(PLUGINS_WITH_CONFIG, this.props.name) ? [
{
icoType: 'cog',
onClick: (e) => {
e.preventDefault();
e.stopPropagation();
this.context.router.history.push(settingsPath);
const icons = includes(PLUGINS_WITH_CONFIG, this.props.name)
? [
{
icoType: 'cog',
onClick: e => {
e.preventDefault();
e.stopPropagation();
this.context.router.history.push(settingsPath);
},
},
},
{
icoType: 'trash',
id: this.props.name,
onClick: this.handleClick,
},
] : [
{
icoType: 'trash',
id: this.props.name,
onClick: this.handleClick,
},
];
{
icoType: 'trash',
id: this.props.name,
onClick: this.handleClick,
},
]
: [
{
icoType: 'trash',
id: this.props.name,
onClick: this.handleClick,
},
];
return (
<ListRow>
<div className={cn("col-md-11", styles.nameWrapper)}>
<div className={cn('col-md-11', styles.nameWrapper)}>
<div className={styles.icoContainer} style={{ marginRight: '14px' }}>
{!isEmpty(this.props.plugin.logo) && <img src={`${this.props.plugin.logo}`} alt="icon" />}
{ isEmpty(this.props.plugin.logo) && (
{!isEmpty(this.props.plugin.logo) && (
<img src={`${this.props.plugin.logo}`} alt="icon" />
)}
{isEmpty(this.props.plugin.logo) && (
<div className={styles.icoWrapper}>
<i className={`fa fa-${this.props.plugin.icon}`} />
</div>
@ -73,7 +80,10 @@ class Row extends React.Component {
</div>
<div className={styles.pluginContent}>
<span>{this.props.plugin.name} &nbsp;</span>
<FormattedMessage id={`${this.props.plugin.description}.short`} defaultMessage={this.props.plugin.description} />
<FormattedMessage
id={`${this.props.plugin.description}.short`}
defaultMessage={this.props.plugin.description}
/>
</div>
</div>
<div className="col-md-1">
@ -83,7 +93,9 @@ class Row extends React.Component {
</div>
<PopUpWarning
isOpen={this.state.showModal}
toggleModal={() => this.setState({ showModal: !this.state.showModal })}
toggleModal={() =>
this.setState({ showModal: !this.state.showModal })
}
popUpWarningType="danger"
onConfirm={this.props.onDeleteConfirm}
/>

View File

@ -9,7 +9,7 @@ import PropTypes from 'prop-types';
import { FormattedMessage } from 'react-intl';
import { isFunction, isObject } from 'lodash';
import cn from 'classnames';
import LoadingBar from 'components/LoadingBar';
import { LoadingBar } from 'strapi-helper-plugin';
import styles from './styles.scss';
@ -18,7 +18,12 @@ function Sub({ bordered, content, link, name, style, title, underline }) {
return (
<div className={cn(styles.subWrapper, bordered && styles.subBordered)}>
<FormattedMessage {...title}>
{message => <span className={cn(underline && styles.underlinedTitle)}>{message}{name}</span>}
{message => (
<span className={cn(underline && styles.underlinedTitle)}>
{message}
{name}
</span>
)}
</FormattedMessage>
{content()}
</div>
@ -26,13 +31,19 @@ function Sub({ bordered, content, link, name, style, title, underline }) {
}
return (
<a className={cn(styles.subWrapper, bordered && styles.subBordered, styles.link)} href={`https://blog.strapi.io/${link}`} target="_blank">
<a
className={cn(
styles.subWrapper,
bordered && styles.subBordered,
styles.link,
)}
href={`https://blog.strapi.io/${link}`}
target="_blank"
>
<span>{title}</span>
{title === '' && <LoadingBar />}
{content === '' && <LoadingBar style={{ width: '40%' }} />}
<p style={style}>
{isFunction(content) ? content() : content}
</p>
<p style={style}>{isFunction(content) ? content() : content}</p>
</a>
);
}
@ -53,17 +64,11 @@ Sub.defaultProps = {
Sub.propTypes = {
bordered: PropTypes.bool,
content: PropTypes.oneOfType([
PropTypes.func,
PropTypes.string,
]),
content: PropTypes.oneOfType([PropTypes.func, PropTypes.string]),
link: PropTypes.string,
name: PropTypes.string,
style: PropTypes.object,
title: PropTypes.oneOfType([
PropTypes.object,
PropTypes.string,
]),
title: PropTypes.oneOfType([PropTypes.object, PropTypes.string]),
underline: PropTypes.bool,
};

View File

@ -1,6 +1,6 @@
import Loadable from 'react-loadable';
import LoadingIndicator from 'components/LoadingIndicator';
import { LoadingIndicator } from 'strapi-helper-plugin';
export default Loadable({
loader: () => import('./index'),

View File

@ -1,6 +1,6 @@
import Loadable from 'react-loadable';
import LoadingIndicator from 'components/LoadingIndicator';
import { LoadingIndicator } from 'strapi-helper-plugin';
export default Loadable({
loader: () => import('./index'),

View File

@ -13,21 +13,25 @@ import { bindActionCreators, compose } from 'redux';
import { Switch, Route } from 'react-router-dom';
// Components from strapi-helper-plugin
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
import OverlayBlocker from 'components/OverlayBlocker';
import {
LoadingIndicatorPage,
OverlayBlocker,
injectHooks,
} from 'strapi-helper-plugin';
// import OverlayBlocker from 'components/OverlayBlocker';
import injectHooks from 'utils/injectHooks';
// import injectHooks from 'utils/injectHooks';
import Header from '../../components/Header/index';
import Logout from '../../components/Logout';
import ComingSoonPage from '../ComingSoonPage';
import LeftMenu from '../LeftMenu';
import ListPluginsPage from '../ListPluginsPage/Loadable';
import ListPluginsPage from '../ListPluginsPage';
import LocaleToggle from '../LocaleToggle';
import HomePage from '../HomePage/Loadable';
import Marketplace from '../Marketplace/Loadable';
import NotFoundPage from '../NotFoundPage/Loadable';
import HomePage from '../HomePage';
import Marketplace from '../Marketplace';
import NotFoundPage from '../NotFoundPage';
import Onboarding from '../Onboarding';
import PluginDispatcher from '../PluginDispatcher';
@ -87,7 +91,6 @@ export class Admin extends React.Component {
ReactGA.initialize('UA-54313258-9', {
testMode: process.env.NODE_ENV === 'test',
});
// Retrieve the main settings of the application
this.props.getInitData();
}
@ -293,6 +296,10 @@ Admin.childContextTypes = {
updatePlugin: PropTypes.func,
};
Admin.defaultProps = {
getHook: () => {},
};
Admin.propTypes = {
admin: PropTypes.shape({
autoReload: PropTypes.bool,
@ -371,12 +378,12 @@ const withLocaleToggleReducer = injectReducer({
key: 'localeToggle',
reducer: localeToggleReducer,
});
const withHooks = injectHooks({ key: 'admin' });
// const withHooks = injectHooks({ key: 'admin' });
export default compose(
withReducer,
withLocaleToggleReducer,
withSaga,
withConnect,
withHooks,
// withHooks,
)(Admin);

View File

@ -1,5 +1,5 @@
import { all, fork, call, put, select, takeLatest } from 'redux-saga/effects';
import request from 'utils/request';
import { request } from 'strapi-helper-plugin';
import { getInitDataSucceeded, getSecuredDataSucceeded } from './actions';
import { EMIT_EVENT, GET_INIT_DATA, GET_SECURED_DATA } from './constants';

View File

@ -13,8 +13,9 @@
import React from 'react';
import { Switch, Route } from 'react-router-dom';
import PropTypes from 'prop-types';
// From strapi-helper-plugin
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
import { LoadingIndicatorPage } from 'strapi-helper-plugin';
import '../../styles/main.scss';
@ -51,6 +52,9 @@ function App(props) {
);
}
// App.contextTypes = {
// store: PropTypes.object,
// };
App.propTypes = {};
export default App;

View File

@ -18,7 +18,7 @@ const initialState = fromJS({
blockApp: false,
overlayBlockerData: null,
hasUserPlugin: true,
isAppLoading: true,
isAppLoading: false,
plugins: {},
showGlobalAppBlocker: true,
});

View File

@ -8,17 +8,16 @@ import React from 'react';
import { connect } from 'react-redux';
import Helmet from 'react-helmet';
import PluginHeader from 'components/PluginHeader';
import { PluginHeader } from 'strapi-helper-plugin';
import styles from './styles.scss';
export class ComingSoonPage extends React.Component { // eslint-disable-line react/prefer-stateless-function
export class ComingSoonPage extends React.Component {
// eslint-disable-line react/prefer-stateless-function
render() {
return (
<div>
<Helmet
title="Coming soon"
/>
<Helmet title="Coming soon" />
<div>
<div className={`container-fluid ${styles.containerFluid}`}>
<PluginHeader
@ -37,7 +36,6 @@ export class ComingSoonPage extends React.Component { // eslint-disable-line rea
}
}
function mapDispatchToProps(dispatch) {
return {
dispatch,

View File

@ -1,11 +0,0 @@
/**
* Asynchronously loads the component for HomePage
*/
import Loadable from 'react-loadable';
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
export default Loadable({
loader: () => import('./index'),
loading: LoadingIndicatorPage,
});

View File

@ -7,12 +7,12 @@ import React from 'react';
import cn from 'classnames';
import PropTypes from 'prop-types';
import Gh from 'assets/images/social_gh.png';
import Slack from 'assets/images/social_slack.png';
import Medium from 'assets/images/social_medium.png';
import So from 'assets/images/social_so.png';
import Twitter from 'assets/images/social_twitter.png';
import Reddit from 'assets/images/social_reddit.png';
import Gh from '../../assets/images/social_gh.png';
import Slack from '../../assets/images/social_slack.png';
import Medium from '../../assets/images/social_medium.png';
import So from '../../assets/images/social_so.png';
import Twitter from '../../assets/images/social_twitter.png';
import Reddit from '../../assets/images/social_reddit.png';
import styles from './styles.scss';
@ -49,7 +49,11 @@ class SocialLink extends React.PureComponent {
<div className={cn(styles.socialLink, 'col-md-6 col-lg-6')}>
<a href={link} target="_blank">
<div>
{!imgLoaded && <div className={styles.spinner}><div /></div>}
{!imgLoaded && (
<div className={styles.spinner}>
<div />
</div>
)}
<img src={getSrc(name)} onLoad={this.handleImgLoaded} />
</div>
<span>{name}</span>

View File

@ -14,10 +14,12 @@ import PropTypes from 'prop-types';
import { get, isEmpty, upperFirst } from 'lodash';
import cn from 'classnames';
import Button from 'components/Button';
import Input from 'components/InputText';
import auth from 'utils/auth';
import validateInput from 'utils/inputsValidations';
import {
Button,
InputText as Input,
auth,
validateInput,
} from 'strapi-helper-plugin';
import Block from '../../components/HomePageBlock';
import Sub from '../../components/Sub';
@ -158,7 +160,7 @@ export class HomePage extends React.PureComponent {
/* eslint-enable indent */
return (
<a href={data.href} target='_blank'>
<a href={data.href} target="_blank">
<Button className={data.className} primary={data.primary}>
<FormattedMessage id={data.id} />
</Button>
@ -183,9 +185,9 @@ export class HomePage extends React.PureComponent {
return (
<div className={cn('container-fluid', styles.containerFluid)}>
<Helmet title='Home Page' />
<div className='row'>
<div className='col-md-8 col-lg-8'>
<Helmet title="Home Page" />
<div className="row">
<div className="col-md-8 col-lg-8">
<Block>
{this.showFirstBlock() &&
FIRST_BLOCK.map((value, key) => (
@ -217,7 +219,7 @@ export class HomePage extends React.PureComponent {
<Sub {...SECOND_BLOCK} />
<div className={styles.homePageFlex}>
<div
className='row'
className="row"
style={{ width: '100%', marginRight: '0' }}
>
{SOCIAL_LINKS.map((value, key) => (
@ -226,20 +228,20 @@ export class HomePage extends React.PureComponent {
</div>
<div className={styles.newsLetterWrapper}>
<div>
<FormattedMessage id='app.components.HomePage.newsLetter' />
<FormattedMessage id="app.components.HomePage.newsLetter" />
</div>
<form onSubmit={this.handleSubmit}>
<div className={cn(styles.homePageForm, 'row')}>
<div className='col-md-12'>
<div className="col-md-12">
<Input
value={body.email}
onChange={this.props.onChange}
name=''
placeholder='johndoe@gmail.com'
name=""
placeholder="johndoe@gmail.com"
error={!isEmpty(this.state.errors)}
/>
<FormattedMessage id='app.components.HomePage.cta'>
{message => <button type='submit'>{message}</button>}
<FormattedMessage id="app.components.HomePage.cta">
{message => <button type="submit">{message}</button>}
</FormattedMessage>
</div>
</div>
@ -248,11 +250,11 @@ export class HomePage extends React.PureComponent {
</div>
</Block>
</div>
<div className='col-lg-4 col-md-4'>
<div className="col-lg-4 col-md-4">
<Block className={styles.blockShirt}>
<div>
<SupportUsTitle />
<FormattedMessage id='app.components.HomePage.support.content'>
<FormattedMessage id="app.components.HomePage.support.content">
{message => <p>{message}</p>}
</FormattedMessage>
<SupportUsCta />

View File

@ -2,7 +2,7 @@ import 'whatwg-fetch';
import { dropRight, take } from 'lodash';
import removeMd from 'remove-markdown';
import { all, call, fork, put, select, takeLatest } from 'redux-saga/effects';
import request from 'utils/request';
import { request } from 'strapi-helper-plugin';
import { getArticlesSucceeded, submitSucceeded } from './actions';
import { GET_ARTICLES, SUBMIT } from './constants';
import { makeSelectBody } from './selectors';

View File

@ -1,8 +0,0 @@
import Loadable from 'react-loadable';
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
export default Loadable({
loader: () => import('./index'),
loading: LoadingIndicatorPage,
});

View File

@ -13,8 +13,7 @@ import { bindActionCreators, compose } from 'redux';
import { FormattedMessage } from 'react-intl';
import cn from 'classnames';
import PluginHeader from 'components/PluginHeader';
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
import { PluginHeader, LoadingIndicatorPage } from 'strapi-helper-plugin';
import ListPlugins from '../../components/ListPlugins';

View File

@ -1,11 +1,23 @@
import { LOCATION_CHANGE } from 'react-router-redux';
import { get } from 'lodash';
import { all, fork, call, put, select, takeLatest, take, cancel } from 'redux-saga/effects';
import auth from 'utils/auth';
import request from 'utils/request';
import {
all,
fork,
call,
put,
select,
takeLatest,
take,
cancel,
} from 'redux-saga/effects';
import { auth, request } from 'strapi-helper-plugin';
import { pluginDeleted } from '../App/actions';
import { selectLocale } from '../LanguageProvider/selectors';
import { deletePluginSucceeded, getAppCurrentEnvSucceeded, getPluginsSucceeded } from './actions';
import {
deletePluginSucceeded,
getAppCurrentEnvSucceeded,
getPluginsSucceeded,
} from './actions';
import { GET_PLUGINS, ON_DELETE_PLUGIN_CONFIRM } from './constants';
import { makeSelectPluginToDelete } from './selectors';
@ -25,10 +37,11 @@ export function* deletePlugin() {
auth.clearAppStorage();
}
}
} catch(error) {
} catch (error) {
yield put(deletePluginSucceeded(false));
strapi.notification.error('app.components.listPluginsPage.deletePlugin.error');
strapi.notification.error(
'app.components.listPluginsPage.deletePlugin.error',
);
}
}
@ -55,19 +68,27 @@ export function* pluginsGet() {
try {
// Fetch plugins informations.
availablePlugins = yield call(request, 'https://marketplace.strapi.io/plugins', opts);
availablePlugins = yield call(
request,
'https://marketplace.strapi.io/plugins',
opts,
);
} catch (e) {
availablePlugins = [];
}
// Add logo URL to object.
Object.keys(response[0].plugins).map(name => {
response[0].plugins[name].logo = get(availablePlugins.find(plugin => plugin.id === name), 'logo', '');
response[0].plugins[name].logo = get(
availablePlugins.find(plugin => plugin.id === name),
'logo',
'',
);
});
yield put(getPluginsSucceeded(response[0]));
yield put(getAppCurrentEnvSucceeded(response[1].currentEnvironment));
} catch(err) {
} catch (err) {
strapi.notification.error('notification.error');
}
}

View File

@ -1,8 +0,0 @@
import Loadable from 'react-loadable';
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
export default Loadable({
loader: () => import('./index'),
loading: LoadingIndicatorPage,
});

View File

@ -12,9 +12,9 @@ import { FormattedMessage } from 'react-intl';
import { bindActionCreators, compose } from 'redux';
import cn from 'classnames';
import PluginHeader from 'components/PluginHeader';
import { LoadingIndicatorPage, PluginHeader } from 'strapi-helper-plugin';
// Design
import LoadingIndicatorPage from 'components/LoadingIndicatorPage';
import PluginCard from '../../components/PluginCard';
import injectSaga from '../../utils/injectSaga';

View File

@ -10,14 +10,17 @@ import {
takeLatest,
} from 'redux-saga/effects';
import request from 'utils/request';
import { request } from 'strapi-helper-plugin';
import { selectLocale } from '../LanguageProvider/selectors';
import {
getAvailableAndInstalledPluginsSucceeded,
downloadPluginSucceeded,
} from './actions';
import { DOWNLOAD_PLUGIN, GET_AVAILABLE_AND_INSTALLED_PLUGINS } from './constants';
import {
DOWNLOAD_PLUGIN,
GET_AVAILABLE_AND_INSTALLED_PLUGINS,
} from './constants';
import { makeSelectPluginToDownload } from './selectors';
export function* pluginDownload() {
@ -39,13 +42,18 @@ export function* pluginDownload() {
},
};
const response = yield call(request, '/admin/plugins/install', opts, overlayblockerParams);
const response = yield call(
request,
'/admin/plugins/install',
opts,
overlayblockerParams,
);
if (response.ok) {
yield put(downloadPluginSucceeded());
window.location.reload();
}
} catch(err) {
} catch (err) {
// Hide the global OverlayBlocker
strapi.unlockApp();
strapi.notification.error('notification.error');
@ -71,16 +79,24 @@ export function* getData() {
call(request, '/admin/plugins', { method: 'GET' }),
]);
yield put(getAvailableAndInstalledPluginsSucceeded(availablePlugins, Object.keys(plugins)));
} catch(err) {
yield put(
getAvailableAndInstalledPluginsSucceeded(
availablePlugins,
Object.keys(plugins),
),
);
} catch (err) {
strapi.notification.error('notification.error');
}
}
// Individual exports for testing
export default function* defaultSaga() {
const loadDataWatcher = yield fork(takeLatest, GET_AVAILABLE_AND_INSTALLED_PLUGINS, getData);
const loadDataWatcher = yield fork(
takeLatest,
GET_AVAILABLE_AND_INSTALLED_PLUGINS,
getData,
);
yield fork(takeLatest, DOWNLOAD_PLUGIN, pluginDownload);
yield take(LOCATION_CHANGE);

View File

@ -1,8 +0,0 @@
import Loadable from 'react-loadable';
import LoadingIndicator from 'components/LoadingIndicator';
export default Loadable({
loader: () => import('./index'),
loading: LoadingIndicator,
});

View File

@ -12,13 +12,12 @@
import React from 'react';
import PropTypes from 'prop-types';
import NotFound from 'components/NotFound';
import { NotFound } from 'strapi-helper-plugin';
export default class NotFoundPage extends React.Component { // eslint-disable-line react/prefer-stateless-function
export default class NotFoundPage extends React.Component {
// eslint-disable-line react/prefer-stateless-function
render() {
return (
<NotFound {...this.props} />
);
return <NotFound {...this.props} />;
}
}

View File

@ -1,4 +1,4 @@
import request from 'utils/request';
import { request } from 'strapi-helper-plugin';
import { all, call, fork, takeLatest, put } from 'redux-saga/effects';
import { GET_VIDEOS } from './constants';
@ -6,38 +6,43 @@ import { getVideosSucceeded, shouldOpenModal } from './actions';
function* getVideos() {
try {
const data = yield call(request, 'https://strapi.io/videos', {
method: 'GET',
headers: {
'Content-Type': 'application/json',
const data = yield call(
request,
'https://strapi.io/videos',
{
method: 'GET',
headers: {
'Content-Type': 'application/json',
},
},
},
false,
true,
{ noAuth: true },
false,
true,
{ noAuth: true },
);
const storedVideo = JSON.parse(localStorage.getItem('videos')) || null;
const videos = data.map(video => {
const { end, startTime } = storedVideo ? storedVideo.find(v => v.order === video.order) : { end: false, startTime: 0};
const videos = data
.map(video => {
const { end, startTime } = storedVideo
? storedVideo.find(v => v.order === video.order)
: { end: false, startTime: 0 };
return {
...video,
duration: null,
end,
isOpen: false,
key: video.order,
startTime,
};
}).sort((a,b) => (a.order - b.order));
return {
...video,
duration: null,
end,
isOpen: false,
key: video.order,
startTime,
};
})
.sort((a, b) => a.order - b.order);
localStorage.setItem('videos', JSON.stringify(videos));
yield put(
getVideosSucceeded(videos),
);
yield put(getVideosSucceeded(videos));
const isFirstTime = JSON.parse(localStorage.getItem('onboarding')) || null;
if (isFirstTime === null) {
@ -46,19 +51,15 @@ function* getVideos() {
resolve();
}, 500);
});
yield put(
shouldOpenModal(true),
);
yield put(shouldOpenModal(true));
localStorage.setItem('onboarding', true);
}
} catch (err) {
console.log(err); // eslint-disable-line no-console
}
}
function* defaultSaga() {
yield all([fork(takeLatest, GET_VIDEOS, getVideos)]);
}

View File

@ -9,7 +9,7 @@ import PropTypes from 'prop-types';
import { get } from 'lodash';
import Helmet from 'react-helmet';
import BlockerComponent from 'components/BlockerComponent';
import { BlockerComponent } from 'strapi-helper-plugin';
import ErrorBoundary from '../ErrorBoundary';
export function PluginDispatcher(props) {

View File

@ -2,48 +2,17 @@
* Combine all reducers in this file and export the combined reducers.
*/
import { fromJS } from 'immutable';
import { combineReducers } from 'redux-immutable';
import { LOCATION_CHANGE } from 'react-router-redux';
import globalReducer from './containers/App/reducer';
import languageProviderReducer from './containers/LanguageProvider/reducer';
import notificationProviderReducer from './containers/NotificationProvider/reducer';
/*
* routeReducer
*
* The reducer merges route location changes into our immutable state.
* The change is necessitated by moving to react-router-redux@5
*
*/
// Initial routing state
const routeInitialState = fromJS({
location: null,
});
/**
* Merge route into the global application state
*/
function routeReducer(state = routeInitialState, action) {
switch (action.type) {
/* istanbul ignore next */
case LOCATION_CHANGE:
return state.merge({
location: action.payload,
});
default:
return state;
}
}
/**
* Creates the main reducer with the dynamically injected ones
*/
export default function createReducer(injectedReducers) {
return combineReducers({
route: routeReducer,
app: globalReducer,
language: languageProviderReducer,
notification: notificationProviderReducer,

View File

@ -0,0 +1,3 @@
const basename = PUBLIC_PATH.replace(window.location.origin, '');
export default basename;

View File

@ -16,8 +16,9 @@ export default function checkStore(store) {
injectedReducers: isObject,
injectedSagas: isObject,
};
invariant(
conformsTo(store, shape),
'(app/utils...) injectors: Expected a valid redux store'
'(app/utils...) injectors: Expected a valid redux store',
);
}

View File

@ -1,6 +1,6 @@
import { createBrowserHistory } from 'history';
import basename from './basename';
const basename = PUBLIC_PATH.replace(window.location.origin, '');
const history = createBrowserHistory({ basename });
export default history;

View File

@ -11,12 +11,14 @@ import getInjectors from './reducerInjectors';
* @param {function} reducer A reducer that will be injected
*
*/
export default ({ key, reducer, pluginId }) => (WrappedComponent) => {
export default ({ key, reducer, pluginId }) => WrappedComponent => {
class ReducerInjector extends React.Component {
static WrappedComponent = WrappedComponent;
static displayName = `withReducer(${(WrappedComponent.displayName || WrappedComponent.name || 'Component')})`;
static displayName = `withReducer(${WrappedComponent.displayName ||
WrappedComponent.name ||
'Component'})`;
static contextTypes = {
store: PropTypes.object.isRequired,
store: PropTypes.object,
};
componentWillMount() {

View File

@ -15,10 +15,12 @@ import getInjectors from './sagaInjectors';
* - constants.ONCE_TILL_UNMOUNTbehaves like 'RESTART_ON_REMOUNT' but never runs it again.
*
*/
export default ({ key, saga, mode, pluginId }) => (WrappedComponent) => {
export default ({ key, saga, mode, pluginId }) => WrappedComponent => {
class InjectSaga extends React.Component {
static WrappedComponent = WrappedComponent;
static displayName = `withSaga(${(WrappedComponent.displayName || WrappedComponent.name || 'Component')})`;
static displayName = `withSaga(${WrappedComponent.displayName ||
WrappedComponent.name ||
'Component'})`;
static contextTypes = {
store: PropTypes.object.isRequired,
};

View File

@ -12,11 +12,15 @@ export function injectReducerFactory(store, isValid) {
invariant(
isString(key) && !isEmpty(key) && isFunction(reducer),
'(app/utils...) injectReducer: Expected `reducer` to be a reducer function'
'(app/utils...) injectReducer: Expected `reducer` to be a reducer function',
);
// Check `store.injectedReducers[key] === reducer` for hot reloading when a key is the same but a reducer is different
if (Reflect.has(store.injectedReducers, key) && store.injectedReducers[key] === reducer) return;
if (
Reflect.has(store.injectedReducers, key) &&
store.injectedReducers[key] === reducer
)
return;
store.injectedReducers[key] = reducer; // eslint-disable-line no-param-reassign
store.replaceReducer(createReducer(store.injectedReducers));

View File

@ -31,27 +31,34 @@
"crypto": "^1.0.1",
"friendly-errors-webpack-plugin": "^1.7.0",
"history": "^4.9.0",
"hoist-non-react-statics": "^2.5.5",
"html-webpack-plugin": "^3.2.0",
"immutable": "^3.8.2",
"intl": "^1.2.5",
"invariant": "^2.2.4",
"prop-types": "^15.7.2",
"react": "^16.8.6",
"react": "^16.5.2",
"react-copy-to-clipboard": "^5.0.1",
"react-dnd": "^7.4.5",
"react-dnd-html5-backend": "^7.4.4",
"react-dom": "^16.8.6",
"react-dom": "^16.5.2",
"react-ga": "^2.4.1",
"react-helmet": "^5.2.0",
"react-intl": "^2.8.0",
"react-redux": "^7.0.1",
"react-router": "^5.0.0",
"react-router-dom": "^5.0.0",
"react-loadable": "^5.5.0",
"react-router": "^4.3.1",
"react-redux": "^5.0.7",
"react-router-dom": "^4.3.1",
"react-router-redux": "^5.0.0-alpha.9",
"react-transition-group": "^2.9.0",
"reactstrap": "^8.0.0",
"redux": "^4.0.1",
"redux-immutable": "^4.0.0",
"redux-saga": "^1.0.2",
"redux-saga": "^0.16.0",
"remove-markdown": "^0.2.2",
"reselect": "^3.0.1",
"shelljs": "^0.7.8",
"strapi-helper-plugin": "3.0.0-alpha.25.2",
"video-react": "^0.13.2"
},
"devDependencies": {
@ -79,7 +86,6 @@
"sanitize.css": "^4.1.0",
"sass-loader": "^7.1.0",
"simple-progress-webpack-plugin": "^1.1.2",
"strapi-helper-plugin": "3.0.0-alpha.25.2",
"strapi-utils": "3.0.0-alpha.25.2",
"style-loader": "^0.23.1",
"url-loader": "^1.1.2",
@ -105,4 +111,4 @@
"npm": ">= 6.0.0"
},
"license": "MIT"
}
}

View File

@ -26,44 +26,44 @@ const PORT = 4000;
const webpackPlugins = devMode
? [
new WebpackDashboard(),
new DuplicatePckgChecker({
verbose: true,
exclude(instance) {
return instance.name === 'core-js';
},
}),
new OpenBrowserWebpackPlugin({
url: `http://localhost:${PORT}/${URLs.publicPath}`,
}),
]
new WebpackDashboard(),
new DuplicatePckgChecker({
verbose: true,
exclude(instance) {
return instance.name === 'core-js';
},
}),
new OpenBrowserWebpackPlugin({
url: `http://localhost:${PORT}/${URLs.publicPath}`,
}),
]
: [
new webpack.IgnorePlugin({
resourceRegExp: /^\.\/locale$/,
contextRegExp: /moment$/,
}),
new MiniCssExtractPlugin({
new webpack.IgnorePlugin({
resourceRegExp: /^\.\/locale$/,
contextRegExp: /moment$/,
}),
new MiniCssExtractPlugin({
// Options similar to the same options in webpackOptions.output
// both options are optional
filename: devMode ? '[name].css' : '[name].[chunkhash].js',
chunkFilename: devMode
filename: devMode ? '[name].css' : '[name].[chunkhash].js',
chunkFilename: devMode
? '[name].chunk.css'
: '[name].[chunkhash].chunkhash.css',
}),
];
}),
];
// Use style loader in dev mode to optimize compilation
const scssLoader = devMode
? ['style-loader']
: [
{
loader: MiniCssExtractPlugin.loader,
options: {
fallback: require.resolve('style-loader'),
publicPath: URLs.publicPath,
},
{
loader: MiniCssExtractPlugin.loader,
options: {
fallback: require.resolve('style-loader'),
publicPath: URLs.publicPath,
},
];
},
];
module.exports = {
mode: 'development',
@ -154,7 +154,7 @@ module.exports = {
{
loader: require.resolve('css-loader'),
options: {
localIdentName: `$[local]__[path][name]__[hash:base64:5]`,
localIdentName: '$[local]__[path][name]__[hash:base64:5]',
modules: true,
importLoaders: 1,
sourceMap: false,
@ -216,15 +216,15 @@ module.exports = {
],
},
resolve: {
modules: [
// TODO handle resolved paths
path.resolve(__dirname, 'admin/src'),
path.resolve(__dirname, '../strapi-helper-plugin/lib/src'),
path.resolve(__dirname, 'node_modules/strapi-helper-plugin/lib/src'),
path.resolve(__dirname, 'node_modules/strapi-helper-plugin/node_modules'),
path.resolve(__dirname, 'node_modules'),
'node_modules',
],
// modules: [
// // TODO handle resolved paths
// // path.resolve(__dirname, 'admin/src'),
// // path.resolve(__dirname, '../strapi-helper-plugin/lib/src'),
// // path.resolve(__dirname, 'node_modules/strapi-helper-plugin/lib/src'),
// // path.resolve(__dirname, 'node_modules/strapi-helper-plugin/node_modules'),
// // path.resolve(__dirname, 'node_modules'),
// // 'node_modules',
// ],
symlinks: false,
extensions: ['.js', '.jsx', '.react.js'],
},
@ -238,7 +238,7 @@ module.exports = {
new FriendlyErrorsWebpackPlugin({
compilationSuccessInfo: {
messages: [
`Your application is running here http://localhost:4000`,
'Your application is running here http://localhost:4000',
`Compiled in ${Date.now() - startDate} seconds`,
],
},

View File

@ -22,10 +22,10 @@ export { default as InputCheckbox } from './components/InputCheckbox';
export {
default as InputCheckboxWithErrors,
} from './components/InputCheckboxWithErrors';
export { default as InputDate } from './components/InputDate';
export {
default as InputDateWithErrors,
} from './components/InputDateWithErrors';
// export { default as InputDate } from './components/InputDate';
// export {
// default as InputDateWithErrors,
// } from './components/InputDateWithErrors';
export { default as InputEmail } from './components/InputEmail';
export {
default as InputEmailWithErrors,
@ -66,6 +66,7 @@ export {
export { default as Label } from './components/Label';
export { default as LiLink } from './components/LiLink';
export { default as ListRow } from './components/ListRow';
export { default as LoadingBar } from './components/LoadingBar';
export { default as LoadingIndicator } from './components/LoadingIndicator';

View File

@ -33,7 +33,8 @@
"react": "^16.0.0",
"react-router": "^5.0.0",
"react-dom": "^16.0.0",
"react-router-dom": "^5.0.0"
"react-router-dom": "^5.0.0",
"react-intl": "^2.8.0"
},
"devDependencies": {
"@babel/core": "^7.4.3",
@ -68,7 +69,7 @@
"dependencies": {
"bootstrap": "^4.0.0-alpha.6",
"classnames": "^2.2.5",
"immutable": "^4.0.0-rc.12",
"immutable": "^3.8.2",
"imports-loader": "^0.7.1",
"invariant": "2.2.1",
"json-loader": "^0.5.7",
@ -79,7 +80,7 @@
"react-dom": "^16.8.6",
"react-intl": "^2.8.0",
"react-loadable": "^5.5.0",
"react-router-dom": "^5.0.0",
"react-router-dom": "^4.3.1",
"react-router-redux": "^5.0.0-alpha.9",
"react-transition-group": "^2.5.0",
"reactstrap": "^5.0.0",
@ -87,4 +88,4 @@
"styled-components": "^3.2.6",
"whatwg-fetch": "^2.0.3"
}
}
}