From 031aa5f2bcf514e45fd553464e644ec98e4e1533 Mon Sep 17 00:00:00 2001 From: Rishabh Date: Tue, 12 Apr 2022 19:54:25 +0530 Subject: [PATCH] Added newsletter selection for signup flows refs https://github.com/TryGhost/Team/issues/1490 Adds newsletter subscription preference page as an intermediary step before signing up as paid or free member. --- ghost/portal/src/AppContext.js | 1 + ghost/portal/src/actions.js | 11 +- .../src/components/common/ActionButton.js | 2 +- .../src/components/pages/AccountEmailPage.js | 51 ++++--- .../src/components/pages/AccountHomePage.js | 54 +++++--- .../pages/NewsletterSelectionPage.js | 129 ++++++++++++++++++ .../portal/src/components/pages/SignupPage.js | 58 ++++++-- ghost/portal/src/pages.js | 2 + ghost/portal/src/utils/api.js | 6 +- ghost/portal/src/utils/fixtures.js | 6 +- 10 files changed, 261 insertions(+), 59 deletions(-) create mode 100644 ghost/portal/src/components/pages/NewsletterSelectionPage.js diff --git a/ghost/portal/src/AppContext.js b/ghost/portal/src/AppContext.js index 90eb346460..f402b7d5d7 100644 --- a/ghost/portal/src/AppContext.js +++ b/ghost/portal/src/AppContext.js @@ -7,6 +7,7 @@ const AppContext = React.createContext({ action: '', lastPage: '', brandColor: '', + pageData: {}, onAction: (action, data) => { return {action, data}; } diff --git a/ghost/portal/src/actions.js b/ghost/portal/src/actions.js index 3e5d07590c..880718d49c 100644 --- a/ghost/portal/src/actions.js +++ b/ghost/portal/src/actions.js @@ -1,10 +1,11 @@ import {createPopupNotification, getMemberEmail, getMemberName, removePortalLinkFromUrl} from './utils/helpers'; -function switchPage({data}) { +function switchPage({data, state}) { return { page: data.page, popupNotification: null, - lastPage: data.lastPage || null + lastPage: data.lastPage || null, + pageData: data.pageData || state.pageData }; } @@ -94,11 +95,13 @@ async function signin({data, api, state}) { async function signup({data, state, api}) { try { - const {plan, email, name, offerId} = data; + const {plan, email, name, newsletters, offerId} = data; if (plan.toLowerCase() === 'free') { + /*eslint-disable no-console */ + console.log('Sending data', data); await api.member.sendMagicLink(data); } else { - await api.member.checkoutPlan({plan, email, name, offerId}); + await api.member.checkoutPlan({plan, email, name, newsletters, offerId}); } return { page: 'magiclink', diff --git a/ghost/portal/src/components/common/ActionButton.js b/ghost/portal/src/components/common/ActionButton.js index f7585ba07c..745c7d7591 100644 --- a/ghost/portal/src/components/common/ActionButton.js +++ b/ghost/portal/src/components/common/ActionButton.js @@ -78,7 +78,7 @@ const Styles = ({brandColor, retry, disabled, style = {}, isPrimary}) => { }; }; -function ActionButton({label, type = undefined, onClick, disabled = false, retry = false, brandColor, isRunning, isPrimary = true, isDestructive = false, classes, style = {}, tabindex = undefined}) { +function ActionButton({label, type = undefined, onClick, disabled = false, retry = false, brandColor, isRunning, isPrimary = true, isDestructive = false, classes = '', style = {}, tabindex = undefined}) { let Style = Styles({disabled, retry, brandColor, style, isPrimary}); let className = 'gh-portal-btn'; diff --git a/ghost/portal/src/components/pages/AccountEmailPage.js b/ghost/portal/src/components/pages/AccountEmailPage.js index b48fecc6fb..651ae424a8 100644 --- a/ghost/portal/src/components/pages/AccountEmailPage.js +++ b/ghost/portal/src/components/pages/AccountEmailPage.js @@ -1,7 +1,7 @@ import AppContext from '../../AppContext'; import CloseButton from '../common/CloseButton'; import BackButton from '../common/BackButton'; -import {useContext} from 'react'; +import {useContext, useState} from 'react'; import Switch from '../common/Switch'; import {getSiteNewsletters} from '../../utils/helpers'; import ActionButton from '../common/ActionButton'; @@ -20,10 +20,8 @@ function AccountHeader() { ); } -function NewsletterPrefSection({newsletter}) { - const {onAction, member} = useContext(AppContext); - let newsletters = [...(member.newsletters || [])]; - const isChecked = newsletters.some((d) => { +function NewsletterPrefSection({newsletter, subscribedNewsletters, setSubscribedNewsletters}) { + const isChecked = subscribedNewsletters.some((d) => { return d.id === newsletter?.id; }); return ( @@ -34,45 +32,53 @@ function NewsletterPrefSection({newsletter}) {
{ - onAction('showPopupNotification', { - action: 'updated:success', - message: `${newsletter.name} newsletter preference updated.` - }); + let updatedNewsletters = []; if (!checked) { - newsletters = newsletters.filter((d) => { + updatedNewsletters = subscribedNewsletters.filter((d) => { return d.id !== newsletter.id; }); } else { - newsletters = newsletters.filter((d) => { + updatedNewsletters = subscribedNewsletters.filter((d) => { return d.id !== newsletter.id; }).concat(newsletter); } - onAction('updateNewsletterPreference', {newsletters}); + setSubscribedNewsletters(updatedNewsletters); }} checked={isChecked} />
); } -function NewsletterPrefs() { +function NewsletterPrefs({subscribedNewsletters, setSubscribedNewsletters}) { const {site} = useContext(AppContext); const newsletters = getSiteNewsletters({site}); return newsletters.map((newsletter) => { return ( - + ); }); } export default function AccountEmailPage() { - const {brandColor} = useContext(AppContext); + const {brandColor, member, onAction} = useContext(AppContext); + const defaultSubscribedNewsletters = [...(member.newsletters || [])]; + const [subscribedNewsletters, setSubscribedNewsletters] = useState(defaultSubscribedNewsletters); + return (
- +