* Move Jetpack connection from benefits to profiler completion

* Handle profiler completion and connection URL async

* Update cached components on each profiler step

* Show bundle install UI based on segment

* Create notice on error catch

* Refactor redirect after promise completion

* Fix up accessiblity issues in bundle popover UI
This commit is contained in:
Joshua T Flowers 2020-07-15 17:52:21 +03:00 committed by GitHub
parent 98f09e2b7d
commit 90c1431129
3 changed files with 143 additions and 90 deletions

View File

@ -5,24 +5,26 @@ import { __ } from '@wordpress/i18n';
import { Component, createElement, Fragment } from '@wordpress/element';
import { compose } from '@wordpress/compose';
import { identity, pick } from 'lodash';
import { withDispatch } from '@wordpress/data';
import { withDispatch, __experimentalResolveSelect } from '@wordpress/data';
/**
* WooCommerce dependencies
*/
import { updateQueryString } from '@woocommerce/navigation';
import { getAdminLink } from '@woocommerce/wc-admin-settings';
import {
ONBOARDING_STORE_NAME,
OPTIONS_STORE_NAME,
PLUGINS_STORE_NAME,
withPluginsHydration,
} from '@woocommerce/data';
import { getHistory, getNewPath, updateQueryString } from '@woocommerce/navigation';
/**
* Internal dependencies
*/
import Benefits from './steps/benefits';
import BusinessDetails from './steps/business-details';
import { createNoticesFromResponse } from 'lib/notices';
import Industry from './steps/industry';
import ProductTypes from './steps/product-types';
import ProfileWizardHeader from './header';
@ -36,11 +38,7 @@ import './style.scss';
class ProfileWizard extends Component {
constructor( props ) {
super( props );
this.state = {
cartRedirectUrl: null,
};
this.activePlugins = props.activePlugins;
this.cachedActivePlugins = props.activePlugins;
this.goToNextStep = this.goToNextStep.bind( this );
}
@ -75,7 +73,7 @@ class ProfileWizard extends Component {
}
componentDidMount() {
const { profileItems, updateProfileItems } = this.props;
const { activePlugins, profileItems, updateProfileItems } = this.props;
document.body.classList.remove( 'woocommerce-admin-is-loading' );
document.documentElement.classList.remove( 'wp-toolbar' );
@ -89,8 +87,8 @@ class ProfileWizard extends Component {
// Track plugins if already installed.
if (
this.activePlugins.includes( 'woocommerce-services' ) &&
this.activePlugins.includes( 'jetpack' ) &&
activePlugins.includes( 'woocommerce-services' ) &&
activePlugins.includes( 'jetpack' ) &&
profileItems.plugins !== 'already-installed'
) {
recordEvent(
@ -103,13 +101,6 @@ class ProfileWizard extends Component {
}
componentWillUnmount() {
const { cartRedirectUrl } = this.state;
if ( cartRedirectUrl ) {
document.body.classList.add( 'woocommerce-admin-is-loading' );
window.location = cartRedirectUrl;
}
document.documentElement.classList.add( 'wp-toolbar' );
document.body.classList.remove( 'woocommerce-onboarding' );
document.body.classList.remove( 'woocommerce-profile-wizard__body' );
@ -117,7 +108,8 @@ class ProfileWizard extends Component {
}
getSteps() {
const { profileItems } = this.props;
const { profileItems, query } = this.props;
const { step } = query;
const steps = [];
steps.push( {
@ -162,8 +154,9 @@ class ProfileWizard extends Component {
} );
if (
! this.activePlugins.includes( 'woocommerce-services' ) ||
! this.activePlugins.includes( 'jetpack' )
! this.cachedActivePlugins.includes( 'woocommerce-services' ) ||
! this.cachedActivePlugins.includes( 'jetpack' ) ||
step === 'benefits'
) {
steps.push( {
key: 'benefits',
@ -185,7 +178,7 @@ class ProfileWizard extends Component {
}
async goToNextStep() {
const { dismissedTasks, updateOptions } = this.props;
const { activePlugins, dismissedTasks, updateOptions } = this.props;
const currentStep = this.getCurrentStep();
const currentStepIndex = this.getSteps().findIndex(
( s ) => s.key === currentStep.key
@ -201,6 +194,10 @@ class ProfileWizard extends Component {
} );
}
// Update the activePlugins cache in case plugins were installed
// in the current step that affect the visibility of the next step.
this.cachedActivePlugins = activePlugins;
const nextStep = this.getSteps()[ currentStepIndex + 1 ];
if ( typeof nextStep === 'undefined' ) {
this.completeProfiler();
@ -211,9 +208,18 @@ class ProfileWizard extends Component {
}
completeProfiler() {
const { notes, updateNote, updateProfileItems } = this.props;
updateProfileItems( { completed: true } );
const {
activePlugins,
getJetpackConnectUrl,
getPluginsError,
isJetpackConnected,
notes,
updateNote,
updateProfileItems,
} = this.props;
recordEvent( 'storeprofiler_complete' );
const shouldConnectJetpack =
activePlugins.includes( 'jetpack' ) && ! isJetpackConnected;
const profilerNote = notes.find(
( note ) => note.name === 'wc-admin-onboarding-profiler-reminder'
@ -221,6 +227,40 @@ class ProfileWizard extends Component {
if ( profilerNote ) {
updateNote( profilerNote.id, { status: 'actioned' } );
}
const promises = [
updateProfileItems( { completed: true } ).then( () => {
if ( shouldConnectJetpack ) {
document.body.classList.add(
'woocommerce-admin-is-loading'
);
}
} ),
];
let redirectUrl = null;
if ( shouldConnectJetpack ) {
promises.push(
getJetpackConnectUrl( {
redirect_url: getAdminLink( 'admin.php?page=wc-admin' ),
} ).then( ( jetpackConnectUrl ) => {
const error = getPluginsError( 'getJetpackConnectUrl' );
if ( error ) {
createNoticesFromResponse( error );
return;
}
redirectUrl = jetpackConnectUrl
} )
);
}
Promise.all( promises ).then( () => {
if ( redirectUrl ) {
window.location = redirectUrl;
return;
}
getHistory().push( getNewPath( {}, '/', {} ) );
} );
}
render() {
@ -254,7 +294,11 @@ export default compose(
const { getProfileItems, getOnboardingError } = select(
ONBOARDING_STORE_NAME
);
const { getActivePlugins } = select( PLUGINS_STORE_NAME );
const {
getActivePlugins,
getPluginsError,
isJetpackConnected,
} = select( PLUGINS_STORE_NAME );
const notesQuery = {
page: 1,
@ -269,7 +313,12 @@ export default compose(
return {
dismissedTasks,
getJetpackConnectUrl: __experimentalResolveSelect(
PLUGINS_STORE_NAME
).getJetpackConnectUrl,
getPluginsError,
isError: Boolean( getOnboardingError( 'updateProfileItems' ) ),
isJetpackConnected: isJetpackConnected(),
notes,
profileItems: getProfileItems(),
activePlugins,

View File

@ -5,18 +5,13 @@ import { __, _n, sprintf } from '@wordpress/i18n';
import { Button } from '@wordpress/components';
import { Component } from '@wordpress/element';
import { compose } from '@wordpress/compose';
import {
withDispatch,
withSelect,
__experimentalResolveSelect,
} from '@wordpress/data';
import { withDispatch, withSelect } from '@wordpress/data';
import { filter } from 'lodash';
/**
* WooCommerce dependencies
*/
import { Card, H } from '@woocommerce/components';
import { getAdminLink } from '@woocommerce/wc-admin-settings';
import {
pluginNames,
ONBOARDING_STORE_NAME,
@ -110,7 +105,7 @@ class Benefits extends Component {
woocommerce_setup_jetpack_opted_in: true,
} ),
] )
.then( () => this.connectJetpack() )
.then( goToNextStep )
.catch( ( pluginError, profileError ) => {
if ( pluginError ) {
createNoticesFromResponse( pluginError );
@ -128,33 +123,6 @@ class Benefits extends Component {
} );
}
connectJetpack() {
const {
getJetpackConnectUrl,
getPluginsError,
goToNextStep,
isJetpackConnected,
} = this.props;
if ( isJetpackConnected ) {
goToNextStep();
return;
}
getJetpackConnectUrl( {
redirect_url: getAdminLink(
'admin.php?page=wc-admin&reset_profiler=0'
),
} ).then( ( url ) => {
const error = getPluginsError( 'getJetpackConnectUrl' );
if ( error ) {
createNoticesFromResponse( error );
goToNextStep();
return;
}
window.location = url;
} );
}
renderBenefit( benefit ) {
const { description, icon, title } = benefit;
@ -305,24 +273,16 @@ export default compose(
isOnboardingRequesting,
} = select( ONBOARDING_STORE_NAME );
const {
getActivePlugins,
getPluginsError,
isJetpackConnected,
isPluginsRequesting,
} = select( PLUGINS_STORE_NAME );
const { getActivePlugins, isPluginsRequesting } = select(
PLUGINS_STORE_NAME
);
return {
activePlugins: getActivePlugins(),
getJetpackConnectUrl: __experimentalResolveSelect(
PLUGINS_STORE_NAME
).getJetpackConnectUrl,
getPluginsError,
isProfileItemsError: Boolean(
getOnboardingError( 'updateProfileItems' )
),
profileItems: getProfileItems(),
isJetpackConnected: isJetpackConnected(),
isRequesting: isOnboardingRequesting( 'updateProfileItems' ),
isInstallingActivating:
isPluginsRequesting( 'installPlugins' ) ||

View File

@ -37,7 +37,7 @@ import {
TextControl,
} from '@woocommerce/components';
import { recordEvent } from 'lib/tracks';
import { getCurrencyRegion } from 'dashboard/utils';
import { getCountryCode, getCurrencyRegion } from 'dashboard/utils';
import { CurrencyContext } from 'lib/currency-context';
import { createNoticesFromResponse } from 'lib/notices';
@ -46,7 +46,11 @@ const wcAdminAssetUrl = getSetting( 'wcAdminAssetUrl', '' );
class BusinessDetails extends Component {
constructor( props ) {
super();
const settings = get( props, 'settings', {} );
const profileItems = get( props, 'profileItems', {} );
const industrySlugs = get( profileItems, 'industry', [] ).map(
( industry ) => industry.slug
);
const businessExtensions = get(
profileItems,
'business_extensions',
@ -81,7 +85,10 @@ class BusinessDetails extends Component {
'kliken-marketing-for-google',
];
this.bundleInstall = false;
this.bundleInstall =
getCountryCode( settings.woocommerce_default_country ) === 'US' &&
( industrySlugs.includes( 'fashion-apparel-accessories' ) ||
industrySlugs.includes( 'health-beauty' ) );
this.onContinue = this.onContinue.bind( this );
this.validate = this.validate.bind( this );
this.getNumberRangeString = this.getNumberRangeString.bind( this );
@ -150,13 +157,6 @@ class BusinessDetails extends Component {
const promises = [
updateProfileItems( updates ).catch( () => {
createNotice(
'error',
__(
'There was a problem updating your business details.',
'woocommerce-admin'
)
);
throw new Error();
} ),
];
@ -174,8 +174,18 @@ class BusinessDetails extends Component {
);
}
Promise.all( promises ).then( () => {
Promise.all( promises )
.then( () => {
goToNextStep();
} )
.catch( () => {
createNotice(
'error',
__(
'There was a problem updating your business details.',
'woocommerce-admin'
)
);
} );
}
@ -471,6 +481,10 @@ class BusinessDetails extends Component {
<div className="woocommerce-business-extensions__popover-wrapper">
<Button
isTertiary
label={ __(
'Learn more about recommended free business features',
'woocommerce-admin'
) }
onClick={ () => {
recordEvent(
'storeprofiler_store_business_details_popover'
@ -478,11 +492,17 @@ class BusinessDetails extends Component {
this.setState( { isPopoverVisible: true } );
} }
>
<i className="material-icons-outlined">info</i>
<i
className="material-icons-outlined"
aria-hidden="true"
>
info
</i>
</Button>
{ isPopoverVisible && (
<Popover
className="woocommerce-business-extensions__popover"
focusOnMount="container"
position="top center"
onClose={ () =>
this.setState( { isPopoverVisible: false } )
@ -490,7 +510,10 @@ class BusinessDetails extends Component {
>
<div className="woocommerce-business-extensions__benefits">
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -499,7 +522,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -508,7 +534,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -517,7 +546,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -526,7 +558,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -535,7 +570,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -544,7 +582,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(
@ -553,7 +594,10 @@ class BusinessDetails extends Component {
) }
</div>
<div className="woocommerce-business-extensions__benefit">
<i className="material-icons-outlined">
<i
className="material-icons-outlined"
aria-hidden="true"
>
check
</i>
{ __(