Skip to content

Commit b9f71d5

Browse files
committed
Redirect to landing page to manage subscription
Handle only there, not on the app anymore Too annoying and error prone having to write the same code on two places Also this makes it easier to experiment with different pricing
1 parent 6de1c56 commit b9f71d5

2 files changed

Lines changed: 141 additions & 102 deletions

File tree

packages/components/src/components/modals/PricingModal.tsx

Lines changed: 130 additions & 78 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ import { contentPadding } from '../../styles/variables'
2424
import { getDefaultDevHubHeaders } from '../../utils/api'
2525
import { ModalColumn } from '../columns/ModalColumn'
2626
import { Button } from '../common/Button'
27+
import { ButtonLink } from '../common/ButtonLink'
2728
import { Spacer } from '../common/Spacer'
2829
import { SubHeader } from '../common/SubHeader'
2930
import { useColumnWidth } from '../context/ColumnWidthContext'
@@ -72,13 +73,16 @@ export function PricingModal(props: PricingModalProps) {
7273
plansToShow.find(p => p.id === userPlan.id)
7374
)
7475

75-
const showUserPlanAtTheTop =
76+
const showUserPlanAtTheTop = true
77+
/*
7678
userPlan &&
7779
((userPlanDetails &&
7880
(userPlanDetails.amount ||
7981
(userPlanDetails.trialPeriodDays && !isPlanExpired(userPlan))) &&
8082
!userPlanStillExist) ||
81-
userPlan.cancelAt)
83+
userPlan.cancelAt ||
84+
userPlan.type === 'team')
85+
*/
8286

8387
const [selectedPlanId, setSelectedPlanId] = useState<PlanID | undefined>(
8488
() =>
@@ -187,7 +191,21 @@ export function PricingModal(props: PricingModalProps) {
187191
],
188192
)
189193

190-
const CancelOrReactivateSubscriptionButton =
194+
const CancelOrReactivateSubscriptionButton = !!(
195+
userPlan && userPlan.amount
196+
) && (
197+
<ButtonLink
198+
analyticsCategory="manage"
199+
analyticsAction="manage"
200+
analyticsLabel="manage"
201+
href={`${constants.DEVHUB_LINKS.ACCOUNT_PAGE}?appToken=${appToken}`}
202+
openOnNewTab
203+
type="neutral"
204+
>
205+
Manage subscription ↗
206+
</ButtonLink>
207+
)
208+
/*
191209
userPlan && userPlan.cancelAtPeriodEnd && userPlan.cancelAt ? (
192210
<Button
193211
analyticsCategory="abort_cancellation"
@@ -276,6 +294,7 @@ export function PricingModal(props: PricingModalProps) {
276294
Cancel subscription
277295
</Button>
278296
)
297+
*/
279298

280299
return (
281300
<ModalColumn
@@ -307,90 +326,123 @@ export function PricingModal(props: PricingModalProps) {
307326
<View style={sharedStyles.marginHorizontal}>
308327
{CancelOrReactivateSubscriptionButton}
309328
</View>
310-
<Spacer height={contentPadding} />
329+
330+
<Spacer height={contentPadding / 2} />
311331
</>
312332
)}
313333
</>
314334
)}
315335

316-
<SubHeader
317-
title={
318-
userPlanDetails && userPlanDetails.amount
319-
? 'CHANGE PLAN'
320-
: 'SELECT A PLAN'
321-
}
322-
/>
323-
324-
<FlatList
325-
ref={flatListRef}
326-
contentContainerStyle={{
327-
paddingHorizontal: (contentPadding * 3) / 4,
328-
}}
329-
data={plansToShow}
330-
extraData={selectedPlanId}
331-
getItemLayout={getItemLayout}
332-
horizontal
333-
onLayout={onLayout}
334-
onScrollToIndexFailed={onScrollToIndexFailed}
335-
renderItem={renderItem}
336-
style={[sharedStyles.flexNoGrow, sharedStyles.fullWidth]}
337-
/>
338-
339-
{sizename <= '2-medium' ? (
340-
<Spacer flex={1} minHeight={contentPadding * 2} />
336+
{showUserPlanAtTheTop ? (
337+
<View
338+
style={[sharedStyles.fullWidth, sharedStyles.paddingHorizontal]}
339+
>
340+
<ButtonLink
341+
analyticsCategory="switch"
342+
analyticsAction="switch"
343+
analyticsLabel="switch"
344+
href={`${constants.DEVHUB_LINKS.PRICING_PAGE}?appToken=${appToken}`}
345+
openOnNewTab
346+
type="neutral"
347+
>
348+
{userPlan && userPlan.amount
349+
? 'Switch plan ↗'
350+
: 'Select a plan ↗'}
351+
</ButtonLink>
352+
</View>
341353
) : (
342-
<Spacer height={contentPadding * 2} />
343-
)}
354+
<>
355+
<Spacer height={contentPadding / 2} />
344356

345-
<View style={[sharedStyles.fullWidth, sharedStyles.paddingHorizontal]}>
346-
<Button
347-
analyticsCategory="subscribe"
348-
analyticsAction="subscribe"
349-
analyticsLabel="subscribe"
350-
disabled={!selectedPlan}
351-
onPress={() => {
352-
if (!(selectedPlan && selectedPlan.id)) return
353-
354-
if (Platform.OS !== 'web') {
355-
Browser.openURLOnNewTab(
356-
`${constants.DEVHUB_LINKS.SUBSCRIBE_PAGE}?plan=${selectedPlan.cannonicalId}&appToken=${appToken}`,
357-
)
358-
return
357+
<SubHeader
358+
title={
359+
userPlanDetails && userPlanDetails.amount
360+
? 'CHANGE PLAN'
361+
: 'SELECT A PLAN'
359362
}
360-
361-
dispatch(
362-
actions.pushModal({
363-
name: 'SUBSCRIBE',
364-
params: { planId: selectedPlan.id },
365-
}),
366-
)
367-
}}
368-
type="primary"
369-
>
370-
{selectedPlan
371-
? selectedPlan.amount > 0
372-
? userPlan && userPlan.id === selectedPlan.id
373-
? userPlan.type === 'team'
374-
? 'Update plan'
375-
: 'Change credit card'
376-
: 'Continue'
377-
: userPlan && userPlan.amount > 0
378-
? 'Downgrade to free plan'
379-
: 'Select another plan'
380-
: 'Continue'}
381-
</Button>
382-
383-
<Spacer height={contentPadding} />
384-
385-
{!(freePlan && !freePlan.trialPeriodDays) &&
386-
!showUserPlanAtTheTop &&
387-
!!(userPlan && userPlan.amount) && (
388-
<>
389-
{CancelOrReactivateSubscriptionButton}
390-
<Spacer height={contentPadding} />
391-
</>
363+
/>
364+
365+
<FlatList
366+
ref={flatListRef}
367+
contentContainerStyle={{
368+
paddingHorizontal: (contentPadding * 3) / 4,
369+
}}
370+
data={plansToShow}
371+
extraData={selectedPlanId}
372+
getItemLayout={getItemLayout}
373+
horizontal
374+
onLayout={onLayout}
375+
onScrollToIndexFailed={onScrollToIndexFailed}
376+
renderItem={renderItem}
377+
style={[sharedStyles.flexNoGrow, sharedStyles.fullWidth]}
378+
/>
379+
380+
{sizename <= '2-medium' ? (
381+
<Spacer flex={1} minHeight={contentPadding * 2} />
382+
) : (
383+
<Spacer height={contentPadding * 2} />
392384
)}
393-
</View>
385+
386+
<View
387+
style={[sharedStyles.fullWidth, sharedStyles.paddingHorizontal]}
388+
>
389+
<Button
390+
analyticsCategory="subscribe"
391+
analyticsAction="subscribe"
392+
analyticsLabel="subscribe"
393+
disabled={!selectedPlan}
394+
onPress={() => {
395+
if (!(selectedPlan && selectedPlan.id)) return
396+
397+
if (Platform.OS !== 'web' || selectedPlan.type === 'team') {
398+
Browser.openURLOnNewTab(
399+
`${constants.DEVHUB_LINKS.SUBSCRIBE_PAGE}?plan=${selectedPlan.cannonicalId}&appToken=${appToken}`,
400+
)
401+
return
402+
}
403+
404+
dispatch(
405+
actions.pushModal({
406+
name: 'SUBSCRIBE',
407+
params: { planId: selectedPlan.id },
408+
}),
409+
)
410+
}}
411+
type="primary"
412+
>
413+
{`${
414+
selectedPlan
415+
? selectedPlan.amount > 0
416+
? userPlan && userPlan.id === selectedPlan.id
417+
? userPlan.type === 'team'
418+
? 'Update plan'
419+
: 'Change credit card'
420+
: 'Continue'
421+
: userPlan && userPlan.amount > 0
422+
? 'Downgrade to free plan'
423+
: 'Select another plan'
424+
: 'Continue'
425+
}${
426+
Platform.OS !== 'web' ||
427+
(selectedPlan && selectedPlan.type === 'team')
428+
? ' ↗'
429+
: ''
430+
}`}
431+
</Button>
432+
433+
<Spacer height={contentPadding} />
434+
435+
{!(freePlan && !freePlan.trialPeriodDays) &&
436+
!showUserPlanAtTheTop &&
437+
!!(userPlan && userPlan.amount) && (
438+
<>
439+
{CancelOrReactivateSubscriptionButton}
440+
<Spacer height={contentPadding} />
441+
</>
442+
)}
443+
</View>
444+
</>
445+
)}
394446
</>
395447
</ModalColumn>
396448
)

packages/components/src/hooks/use-cards-props.tsx

Lines changed: 11 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ import {
3434
import { EmptyCards } from '../components/cards/EmptyCards'
3535
import { ColumnLoadingIndicator } from '../components/columns/ColumnLoadingIndicator'
3636
import { Button } from '../components/common/Button'
37+
import { ButtonLink } from '../components/common/ButtonLink'
3738
import { QuickFeedbackRow } from '../components/common/QuickFeedbackRow'
3839
import { RefreshControl } from '../components/common/RefreshControl'
3940
import { useAppLayout } from '../components/context/LayoutContext'
@@ -71,6 +72,7 @@ export function useCardsProps<ItemT extends EnhancedItem>({
7172
const { column, columnIndex, headerDetails } = useColumn(columnId || '')
7273

7374
const dispatch = useDispatch()
75+
const appToken = useReduxState(selectors.appTokenSelector)
7476
const plan = useReduxState(selectors.currentUserPlanSelector)
7577
const isPlanExpired = useReduxState(selectors.isPlanExpiredSelector)
7678

@@ -362,20 +364,12 @@ export function useCardsProps<ItemT extends EnhancedItem>({
362364
emoji="lock"
363365
errorButtonView={
364366
<View>
365-
<Button
367+
<ButtonLink
366368
analyticsCategory="plan_expired"
367369
analyticsLabel="select_a_plan_button"
368-
children="Select a plan"
369-
onPress={() => {
370-
dispatch(
371-
actions.pushModal({
372-
name: 'PRICING',
373-
params: {
374-
highlightFeature: 'columnsLimit',
375-
},
376-
}),
377-
)
378-
}}
370+
children="Select a plan ↗"
371+
href={`${constants.DEVHUB_LINKS.PRICING_PAGE}?appToken=${appToken}`}
372+
openOnNewTab
379373
/>
380374
</View>
381375
}
@@ -449,20 +443,12 @@ export function useCardsProps<ItemT extends EnhancedItem>({
449443
columnId={column.id}
450444
emoji="lock"
451445
errorButtonView={
452-
<Button
446+
<ButtonLink
453447
analyticsLabel="select_a_plan_button"
454448
analyticsCategory="invalid_plan"
455-
children="Select a plan"
456-
onPress={() => {
457-
dispatch(
458-
actions.pushModal({
459-
name: 'PRICING',
460-
params: {
461-
highlightFeature: 'columnsLimit',
462-
},
463-
}),
464-
)
465-
}}
449+
children="Select a plan ↗"
450+
href={`${constants.DEVHUB_LINKS.PRICING_PAGE}?appToken=${appToken}`}
451+
openOnNewTab
466452
/>
467453
}
468454
errorMessage="You need a paid plan to keep using DevHub."
@@ -483,6 +469,7 @@ export function useCardsProps<ItemT extends EnhancedItem>({
483469
isOverMaxColumnLimit,
484470
isOverPlanColumnLimit,
485471
isPlanExpired,
472+
appToken,
486473
])
487474

488475
return {

0 commit comments

Comments
 (0)