@greatapps/common 1.1.674 → 1.1.676
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/account/ConfigurationsMyAccountModal.mjs +6 -8
- package/dist/components/account/ConfigurationsMyAccountModal.mjs.map +1 -1
- package/dist/components/account/ConfirmDeleteAccountModal.mjs +19 -20
- package/dist/components/account/ConfirmDeleteAccountModal.mjs.map +1 -1
- package/dist/components/account/ConfirmGlobalPreferencesModal.mjs +11 -10
- package/dist/components/account/ConfirmGlobalPreferencesModal.mjs.map +1 -1
- package/dist/components/account/DeleteAccountModal.mjs +28 -34
- package/dist/components/account/DeleteAccountModal.mjs.map +1 -1
- package/dist/components/account/DisableTwoFactorAuthModal.mjs +5 -7
- package/dist/components/account/DisableTwoFactorAuthModal.mjs.map +1 -1
- package/dist/components/account/IsntPossibleDeleteAccountModal.mjs +9 -8
- package/dist/components/account/IsntPossibleDeleteAccountModal.mjs.map +1 -1
- package/dist/components/account/TwoFactorAuthModal.mjs +23 -22
- package/dist/components/account/TwoFactorAuthModal.mjs.map +1 -1
- package/dist/components/account/constants.mjs +4 -4
- package/dist/components/account/constants.mjs.map +1 -1
- package/dist/components/account/hooks/useChangeEmailForm.mjs +3 -5
- package/dist/components/account/hooks/useChangeEmailForm.mjs.map +1 -1
- package/dist/components/account/hooks/useChangePasswordForm.mjs +3 -26
- package/dist/components/account/hooks/useChangePasswordForm.mjs.map +1 -1
- package/dist/components/account/hooks/useChangePhoneForm.mjs +9 -18
- package/dist/components/account/hooks/useChangePhoneForm.mjs.map +1 -1
- package/dist/components/account/hooks/useDisableTwoFactorAuthForm.mjs +3 -26
- package/dist/components/account/hooks/useDisableTwoFactorAuthForm.mjs.map +1 -1
- package/dist/components/account/hooks/useOtpVerification.mjs +3 -19
- package/dist/components/account/hooks/useOtpVerification.mjs.map +1 -1
- package/dist/components/account/hooks/useTwoFactorAuthForm.mjs +4 -27
- package/dist/components/account/hooks/useTwoFactorAuthForm.mjs.map +1 -1
- package/dist/components/account/sections/ChangeEmailModal.mjs +28 -25
- package/dist/components/account/sections/ChangeEmailModal.mjs.map +1 -1
- package/dist/components/account/sections/ChangePasswordSection.mjs +6 -8
- package/dist/components/account/sections/ChangePasswordSection.mjs.map +1 -1
- package/dist/components/account/sections/ChangePhoneModal.mjs +27 -24
- package/dist/components/account/sections/ChangePhoneModal.mjs.map +1 -1
- package/dist/components/account/sections/MyProfileSection.mjs +22 -37
- package/dist/components/account/sections/MyProfileSection.mjs.map +1 -1
- package/dist/components/account/sections/PreferencesSection.mjs +24 -48
- package/dist/components/account/sections/PreferencesSection.mjs.map +1 -1
- package/dist/components/account/sections/SecuritySection.mjs +9 -11
- package/dist/components/account/sections/SecuritySection.mjs.map +1 -1
- package/dist/components/account/sections/TokenSection.mjs +8 -24
- package/dist/components/account/sections/TokenSection.mjs.map +1 -1
- package/dist/components/layouts/AppMobileNavBar.mjs +148 -2
- package/dist/components/layouts/AppMobileNavBar.mjs.map +1 -1
- package/dist/components/layouts/NavBar.mjs +3 -5
- package/dist/components/layouts/NavBar.mjs.map +1 -1
- package/dist/components/layouts/NotificationsPopover.mjs +3 -5
- package/dist/components/layouts/NotificationsPopover.mjs.map +1 -1
- package/dist/components/layouts/ProfilePopover.mjs +4 -6
- package/dist/components/layouts/ProfilePopover.mjs.map +1 -1
- package/dist/components/layouts/UsersSelectorPopover.mjs +7 -9
- package/dist/components/layouts/UsersSelectorPopover.mjs.map +1 -1
- package/dist/components/modals/BuyCreditsModal.mjs +18 -17
- package/dist/components/modals/BuyCreditsModal.mjs.map +1 -1
- package/dist/components/modals/CreditsDisabledModal.mjs +4 -6
- package/dist/components/modals/CreditsDisabledModal.mjs.map +1 -1
- package/dist/components/modals/PaidPlanRequiredModal.mjs +3 -5
- package/dist/components/modals/PaidPlanRequiredModal.mjs.map +1 -1
- package/dist/components/modals/cards/AddCardModal.mjs +24 -27
- package/dist/components/modals/cards/AddCardModal.mjs.map +1 -1
- package/dist/components/modals/cards/CannotDeleteCardModal.mjs +7 -9
- package/dist/components/modals/cards/CannotDeleteCardModal.mjs.map +1 -1
- package/dist/components/modals/cards/CardFormFields.mjs +22 -25
- package/dist/components/modals/cards/CardFormFields.mjs.map +1 -1
- package/dist/components/modals/cards/DeleteCardModal.mjs +8 -10
- package/dist/components/modals/cards/DeleteCardModal.mjs.map +1 -1
- package/dist/components/navigation/CancelledSubscriptionBanner.mjs +2 -4
- package/dist/components/navigation/CancelledSubscriptionBanner.mjs.map +1 -1
- package/dist/components/navigation/OverdueInvoiceBanner.mjs +2 -4
- package/dist/components/navigation/OverdueInvoiceBanner.mjs.map +1 -1
- package/dist/components/navigation/PendingCancellationBanner.mjs +6 -4
- package/dist/components/navigation/PendingCancellationBanner.mjs.map +1 -1
- package/dist/components/navigation/ProjectSelectorPopover.mjs +6 -8
- package/dist/components/navigation/ProjectSelectorPopover.mjs.map +1 -1
- package/dist/components/navigation/UpcomingInvoiceBanner.mjs +6 -4
- package/dist/components/navigation/UpcomingInvoiceBanner.mjs.map +1 -1
- package/dist/components/navigation/subcomponents/BottomLinks.mjs +3 -5
- package/dist/components/navigation/subcomponents/BottomLinks.mjs.map +1 -1
- package/dist/components/navigation/subcomponents/CreditsCard.mjs +1 -3
- package/dist/components/navigation/subcomponents/CreditsCard.mjs.map +1 -1
- package/dist/components/navigation/subcomponents/PlanCard.mjs +1 -3
- package/dist/components/navigation/subcomponents/PlanCard.mjs.map +1 -1
- package/dist/components/navigation/subcomponents/ProjectSelector.mjs +3 -5
- package/dist/components/navigation/subcomponents/ProjectSelector.mjs.map +1 -1
- package/dist/components/pages/NotFoundPage.mjs +3 -5
- package/dist/components/pages/NotFoundPage.mjs.map +1 -1
- package/dist/components/pages/notifications/Notifications.mjs +10 -13
- package/dist/components/pages/notifications/Notifications.mjs.map +1 -1
- package/dist/components/ui/buttons/CopyButton.mjs +5 -9
- package/dist/components/ui/buttons/CopyButton.mjs.map +1 -1
- package/dist/components/ui/data-display/CardItem.mjs +5 -7
- package/dist/components/ui/data-display/CardItem.mjs.map +1 -1
- package/dist/components/ui/data-display/PaymentInfoCard.mjs +8 -10
- package/dist/components/ui/data-display/PaymentInfoCard.mjs.map +1 -1
- package/dist/components/ui/feedback/CircularProgress.mjs.map +1 -1
- package/dist/components/ui/feedback/DefaultCircularProgress.mjs +1 -3
- package/dist/components/ui/feedback/DefaultCircularProgress.mjs.map +1 -1
- package/dist/components/ui/form/ComboboxField.mjs +6 -11
- package/dist/components/ui/form/ComboboxField.mjs.map +1 -1
- package/dist/components/ui/form/DatePicker.mjs +2 -5
- package/dist/components/ui/form/DatePicker.mjs.map +1 -1
- package/dist/components/ui/form/DateRangePicker.mjs +2 -5
- package/dist/components/ui/form/DateRangePicker.mjs.map +1 -1
- package/dist/components/ui/form/PhoneInput.mjs +3 -5
- package/dist/components/ui/form/PhoneInput.mjs.map +1 -1
- package/dist/components/ui/form/SelectField.mjs +3 -6
- package/dist/components/ui/form/SelectField.mjs.map +1 -1
- package/dist/components/widgets/ImageUpload/ImageCropModal.mjs +18 -11
- package/dist/components/widgets/ImageUpload/ImageCropModal.mjs.map +1 -1
- package/dist/components/widgets/ImageUpload/ImageTooSmallModal.mjs +15 -6
- package/dist/components/widgets/ImageUpload/ImageTooSmallModal.mjs.map +1 -1
- package/dist/index.mjs +2 -16
- package/dist/index.mjs.map +1 -1
- package/dist/modules/cards/hooks/handle-delete-card.hook.mjs +1 -2
- package/dist/modules/cards/hooks/handle-delete-card.hook.mjs.map +1 -1
- package/dist/modules/images/utils/validate-image.mjs +8 -8
- package/dist/modules/images/utils/validate-image.mjs.map +1 -1
- package/dist/modules/plans/services/plans.service.mjs +1 -1
- package/dist/modules/plans/services/plans.service.mjs.map +1 -1
- package/dist/modules/plans/types/plan.type.mjs +0 -3
- package/dist/modules/plans/types/plan.type.mjs.map +1 -1
- package/dist/modules/plans/utils/map-api-plan-to-ui.mjs +34 -56
- package/dist/modules/plans/utils/map-api-plan-to-ui.mjs.map +1 -1
- package/dist/modules/subscriptions/utils/periodicity.mjs +14 -20
- package/dist/modules/subscriptions/utils/periodicity.mjs.map +1 -1
- package/dist/providers/auth.provider.mjs +1 -9
- package/dist/providers/auth.provider.mjs.map +1 -1
- package/dist/server.mjs +0 -2
- package/dist/server.mjs.map +1 -1
- package/dist/utils/format/currency.mjs +4 -32
- package/dist/utils/format/currency.mjs.map +1 -1
- package/dist/utils/intl/locales.mjs +2 -3
- package/dist/utils/intl/locales.mjs.map +1 -1
- package/package.json +1 -7
- package/src/components/account/ConfigurationsMyAccountModal.tsx +6 -10
- package/src/components/account/ConfirmDeleteAccountModal.tsx +13 -22
- package/src/components/account/ConfirmGlobalPreferencesModal.tsx +10 -12
- package/src/components/account/DeleteAccountModal.tsx +24 -34
- package/src/components/account/DisableTwoFactorAuthModal.tsx +6 -11
- package/src/components/account/IsntPossibleDeleteAccountModal.tsx +6 -8
- package/src/components/account/TwoFactorAuthModal.tsx +29 -33
- package/src/components/account/constants.ts +5 -8
- package/src/components/account/hooks/useChangeEmailForm.tsx +3 -5
- package/src/components/account/hooks/useChangePasswordForm.tsx +6 -20
- package/src/components/account/hooks/useChangePhoneForm.tsx +10 -16
- package/src/components/account/hooks/useDisableTwoFactorAuthForm.tsx +6 -20
- package/src/components/account/hooks/useOtpVerification.tsx +4 -16
- package/src/components/account/hooks/useTwoFactorAuthForm.tsx +7 -21
- package/src/components/account/sections/ChangeEmailModal.tsx +21 -35
- package/src/components/account/sections/ChangePasswordSection.tsx +6 -10
- package/src/components/account/sections/ChangePhoneModal.tsx +22 -50
- package/src/components/account/sections/MyProfileSection.tsx +23 -37
- package/src/components/account/sections/PreferencesSection.tsx +25 -52
- package/src/components/account/sections/SecuritySection.tsx +10 -19
- package/src/components/account/sections/TokenSection.tsx +10 -22
- package/src/components/layouts/AppMobileNavBar.tsx +154 -1
- package/src/components/layouts/NavBar.tsx +3 -5
- package/src/components/layouts/NotificationsPopover.tsx +3 -5
- package/src/components/layouts/ProfilePopover.tsx +4 -6
- package/src/components/layouts/UsersSelectorPopover.tsx +7 -9
- package/src/components/modals/BuyCreditsModal.tsx +16 -18
- package/src/components/modals/CreditsDisabledModal.tsx +6 -6
- package/src/components/modals/PaidPlanRequiredModal.tsx +3 -5
- package/src/components/modals/cards/AddCardModal.tsx +27 -29
- package/src/components/modals/cards/CannotDeleteCardModal.tsx +8 -9
- package/src/components/modals/cards/CardFormFields.tsx +22 -25
- package/src/components/modals/cards/DeleteCardModal.tsx +8 -10
- package/src/components/navigation/CancelledSubscriptionBanner.tsx +2 -4
- package/src/components/navigation/OverdueInvoiceBanner.tsx +2 -4
- package/src/components/navigation/PendingCancellationBanner.tsx +2 -4
- package/src/components/navigation/ProjectSelectorPopover.tsx +6 -8
- package/src/components/navigation/UpcomingInvoiceBanner.tsx +2 -4
- package/src/components/navigation/subcomponents/BottomLinks.tsx +3 -5
- package/src/components/navigation/subcomponents/CreditsCard.tsx +1 -3
- package/src/components/navigation/subcomponents/PlanCard.tsx +1 -3
- package/src/components/navigation/subcomponents/ProjectSelector.tsx +3 -5
- package/src/components/pages/NotFoundPage.tsx +3 -5
- package/src/components/pages/notifications/Notifications.tsx +10 -13
- package/src/components/ui/buttons/CopyButton.tsx +5 -10
- package/src/components/ui/data-display/CardItem.tsx +5 -7
- package/src/components/ui/data-display/PaymentInfoCard.tsx +8 -10
- package/src/components/ui/feedback/CircularProgress.tsx +0 -4
- package/src/components/ui/feedback/DefaultCircularProgress.tsx +1 -3
- package/src/components/ui/form/ComboboxField.tsx +6 -11
- package/src/components/ui/form/DatePicker.tsx +2 -5
- package/src/components/ui/form/DateRangePicker.tsx +2 -5
- package/src/components/ui/form/PhoneInput.tsx +3 -5
- package/src/components/ui/form/SelectField.tsx +3 -6
- package/src/components/widgets/ImageUpload/ImageCropModal.tsx +11 -19
- package/src/components/widgets/ImageUpload/ImageTooSmallModal.tsx +5 -6
- package/src/index.ts +2 -12
- package/src/modules/cards/hooks/handle-delete-card.hook.ts +3 -8
- package/src/modules/images/utils/validate-image.ts +8 -23
- package/src/modules/plans/services/plans.service.ts +1 -1
- package/src/modules/plans/types/plan.type.ts +0 -3
- package/src/modules/plans/utils/map-api-plan-to-ui.ts +46 -103
- package/src/modules/subscriptions/utils/periodicity.ts +12 -29
- package/src/providers/auth.provider.tsx +1 -13
- package/src/server.ts +0 -2
- package/src/utils/format/currency.ts +7 -62
- package/src/utils/intl/locales.ts +2 -3
- package/dist/i18n/config.mjs +0 -13
- package/dist/i18n/config.mjs.map +0 -1
- package/dist/i18n/country-language.mjs +0 -74
- package/dist/i18n/country-language.mjs.map +0 -1
- package/dist/i18n/messages/en-us.mjs +0 -492
- package/dist/i18n/messages/en-us.mjs.map +0 -1
- package/dist/i18n/messages/es-es.mjs +0 -492
- package/dist/i18n/messages/es-es.mjs.map +0 -1
- package/dist/i18n/messages/index.mjs +0 -16
- package/dist/i18n/messages/index.mjs.map +0 -1
- package/dist/i18n/messages/pt-br.mjs +0 -505
- package/dist/i18n/messages/pt-br.mjs.map +0 -1
- package/dist/i18n/normalize.mjs +0 -12
- package/dist/i18n/normalize.mjs.map +0 -1
- package/dist/i18n/resolve-locale.mjs +0 -42
- package/dist/i18n/resolve-locale.mjs.map +0 -1
- package/dist/i18n.mjs +0 -14
- package/dist/i18n.mjs.map +0 -1
- package/dist/modules/accounts/hooks/use-currency-formatter.hook.mjs +0 -20
- package/dist/modules/accounts/hooks/use-currency-formatter.hook.mjs.map +0 -1
- package/dist/utils/intl/cookie-domain.mjs +0 -17
- package/dist/utils/intl/cookie-domain.mjs.map +0 -1
- package/dist/utils/intl/locale-cookie.mjs +0 -13
- package/dist/utils/intl/locale-cookie.mjs.map +0 -1
- package/src/i18n/config.ts +0 -17
- package/src/i18n/country-language.ts +0 -60
- package/src/i18n/messages/en-us.ts +0 -512
- package/src/i18n/messages/es-es.ts +0 -513
- package/src/i18n/messages/index.ts +0 -24
- package/src/i18n/messages/pt-br.ts +0 -536
- package/src/i18n/normalize.ts +0 -15
- package/src/i18n/resolve-locale.ts +0 -77
- package/src/i18n.ts +0 -10
- package/src/modules/accounts/hooks/use-currency-formatter.hook.tsx +0 -32
- package/src/utils/intl/cookie-domain.ts +0 -29
- package/src/utils/intl/locale-cookie.ts +0 -18
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
3
|
import { useState, useEffect, useRef } from 'react';
|
|
4
|
-
import { useTranslations } from 'next-intl';
|
|
5
4
|
import { AsYouType, CountryCode } from 'libphonenumber-js';
|
|
6
5
|
import { Input, Separator, Popover, PopoverTrigger, PopoverContent, cn } from '@greatapps/common';
|
|
7
6
|
import { IconChevronDown, IconSearch } from '@tabler/icons-react';
|
|
@@ -42,7 +41,6 @@ export default function PhoneInput({
|
|
|
42
41
|
classnameContainer,
|
|
43
42
|
className,
|
|
44
43
|
}: PhoneInputProps) {
|
|
45
|
-
const translate = useTranslations();
|
|
46
44
|
const parsed = parsePhoneValue(value ?? '');
|
|
47
45
|
const [selectedCountry, setSelectedCountry] = useState<Country>(parsed.country);
|
|
48
46
|
const [phoneNumber, setPhoneNumber] = useState(parsed.number);
|
|
@@ -117,7 +115,7 @@ export default function PhoneInput({
|
|
|
117
115
|
{label && (
|
|
118
116
|
<div className="flex items-center gap-1 paragraph-xsmall-semibold">
|
|
119
117
|
<span className="text-zinc-600">{label}</span>
|
|
120
|
-
{optional && <span className="text-zinc-500">
|
|
118
|
+
{optional && <span className="text-zinc-500">(Opcional)</span>}
|
|
121
119
|
{required && <span className="text-red-600">*</span>}
|
|
122
120
|
</div>
|
|
123
121
|
)}
|
|
@@ -150,7 +148,7 @@ export default function PhoneInput({
|
|
|
150
148
|
<input
|
|
151
149
|
type="text"
|
|
152
150
|
className="flex-1 text-sm outline-none placeholder:text-zinc-400"
|
|
153
|
-
placeholder=
|
|
151
|
+
placeholder="Buscar país..."
|
|
154
152
|
value={search}
|
|
155
153
|
onChange={(e) => setSearch(e.target.value)}
|
|
156
154
|
autoFocus
|
|
@@ -177,7 +175,7 @@ export default function PhoneInput({
|
|
|
177
175
|
</button>
|
|
178
176
|
))}
|
|
179
177
|
{filtered.length === 0 && (
|
|
180
|
-
<p className="text-sm text-zinc-500 p-3 text-center">
|
|
178
|
+
<p className="text-sm text-zinc-500 p-3 text-center">Nenhum país encontrado</p>
|
|
181
179
|
)}
|
|
182
180
|
</div>
|
|
183
181
|
</PopoverContent>
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
3
|
import React from 'react';
|
|
4
|
-
import { useTranslations } from 'next-intl';
|
|
5
4
|
import {
|
|
6
5
|
Select,
|
|
7
6
|
SelectContent,
|
|
@@ -42,7 +41,7 @@ export function SelectField({
|
|
|
42
41
|
hintMessage,
|
|
43
42
|
error = false,
|
|
44
43
|
errorMessage,
|
|
45
|
-
placeholder,
|
|
44
|
+
placeholder = 'Selecione uma opção',
|
|
46
45
|
options,
|
|
47
46
|
value,
|
|
48
47
|
defaultValue,
|
|
@@ -52,8 +51,6 @@ export function SelectField({
|
|
|
52
51
|
className,
|
|
53
52
|
containerClassName,
|
|
54
53
|
}: SelectFieldProps) {
|
|
55
|
-
const translate = useTranslations();
|
|
56
|
-
const resolvedPlaceholder = placeholder ?? translate('common.forms.select.placeholder');
|
|
57
54
|
const handleValueChange = (selectedValue: string) => {
|
|
58
55
|
if (!onChange) return;
|
|
59
56
|
const selectedOption = options.find((option) => String(option.value) === selectedValue);
|
|
@@ -70,7 +67,7 @@ export function SelectField({
|
|
|
70
67
|
{label && (
|
|
71
68
|
<div className="flex items-center gap-1 paragraph-xsmall-semibold">
|
|
72
69
|
<span className="text-gray-600">{label}</span>
|
|
73
|
-
{optional && <span className="text-gray-500">
|
|
70
|
+
{optional && <span className="text-gray-500">(Opcional)</span>}
|
|
74
71
|
{required && <span className="text-red-600">*</span>}
|
|
75
72
|
</div>
|
|
76
73
|
)}
|
|
@@ -92,7 +89,7 @@ export function SelectField({
|
|
|
92
89
|
)}
|
|
93
90
|
icon={icon}
|
|
94
91
|
>
|
|
95
|
-
<SelectValue placeholder={
|
|
92
|
+
<SelectValue placeholder={placeholder}>
|
|
96
93
|
{value !== undefined &&
|
|
97
94
|
(() => {
|
|
98
95
|
const selectedOption = options.find((opt) => String(opt.value) === String(value));
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
'use client'
|
|
2
2
|
|
|
3
3
|
import { useEffect, useRef, useState } from 'react'
|
|
4
|
-
import { useTranslations } from 'next-intl'
|
|
5
4
|
import ReactCrop, {
|
|
6
5
|
type Crop,
|
|
7
6
|
centerCrop,
|
|
@@ -179,7 +178,6 @@ export function ImageCropModal({
|
|
|
179
178
|
fileName,
|
|
180
179
|
onSelectAnother,
|
|
181
180
|
}: ImageCropModalProps) {
|
|
182
|
-
const translate = useTranslations()
|
|
183
181
|
const imgRef = useRef<HTMLImageElement>(null)
|
|
184
182
|
const [crop, setCrop] = useState<Crop>()
|
|
185
183
|
const [imageSize, setImageSize] = useState({ width: 0, height: 0 })
|
|
@@ -303,28 +301,22 @@ export function ImageCropModal({
|
|
|
303
301
|
<>
|
|
304
302
|
<DialogHeader className="p-5">
|
|
305
303
|
<DialogTitle className="text-center text-[16px]!">
|
|
306
|
-
{dimensionText
|
|
307
|
-
? translate('common.imageUpload.tooSmallTitleWithDimension', { dimensionText })
|
|
308
|
-
: translate('common.imageUpload.tooSmallTitleGeneric')}
|
|
304
|
+
{dimensionText ? `Foto menor que ${dimensionText}` : 'Foto muito pequena'}
|
|
309
305
|
</DialogTitle>
|
|
310
306
|
</DialogHeader>
|
|
311
307
|
|
|
312
308
|
<div className="px-5 pb-5">
|
|
313
309
|
<p className="paragraph-small-regular text-zinc-600 text-center">
|
|
314
|
-
{fileName
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
? translate('common.imageUpload.tooSmallBodyFileGeneric', { fileName })
|
|
318
|
-
: !fileName && dimensionText
|
|
319
|
-
? translate('common.imageUpload.tooSmallBodyNoFileWithDimension', { dimensionText })
|
|
320
|
-
: translate('common.imageUpload.tooSmallBodyNoFileGeneric')}
|
|
310
|
+
{fileName ? `O arquivo "${fileName}"` : 'A imagem selecionada'} é menor
|
|
311
|
+
{dimensionText ? ` que ${dimensionText}` : ' que o tamanho mínimo exigido'}.
|
|
312
|
+
{' '}Faça envio de uma imagem {dimensionText ? `com pelo menos ${dimensionText}` : 'maior'} para continuar.
|
|
321
313
|
</p>
|
|
322
314
|
</div>
|
|
323
315
|
|
|
324
316
|
<DialogFooter className="flex-row! items-center justify-start! gap-3 p-5 border-t border-zinc-200">
|
|
325
|
-
{onSelectAnother && <Button onClick={onSelectAnother}>
|
|
317
|
+
{onSelectAnother && <Button onClick={onSelectAnother}>Enviar outra</Button>}
|
|
326
318
|
<Button variant="secondary" onClick={handleCancel}>
|
|
327
|
-
|
|
319
|
+
Cancelar
|
|
328
320
|
</Button>
|
|
329
321
|
</DialogFooter>
|
|
330
322
|
</>
|
|
@@ -332,7 +324,7 @@ export function ImageCropModal({
|
|
|
332
324
|
<>
|
|
333
325
|
<DialogHeader className="p-5">
|
|
334
326
|
<DialogTitle className="text-center text-[16px]!">
|
|
335
|
-
|
|
327
|
+
Ajustar imagem
|
|
336
328
|
</DialogTitle>
|
|
337
329
|
</DialogHeader>
|
|
338
330
|
|
|
@@ -352,7 +344,7 @@ export function ImageCropModal({
|
|
|
352
344
|
<img
|
|
353
345
|
ref={imgRef}
|
|
354
346
|
src={imageSrc}
|
|
355
|
-
alt=
|
|
347
|
+
alt="Crop"
|
|
356
348
|
onLoad={onCropImgLoad}
|
|
357
349
|
draggable={false}
|
|
358
350
|
className="max-h-[50vh] object-contain select-none"
|
|
@@ -362,16 +354,16 @@ export function ImageCropModal({
|
|
|
362
354
|
</div>
|
|
363
355
|
|
|
364
356
|
<p className="paragraph-small-regular text-zinc-500 text-center">
|
|
365
|
-
|
|
357
|
+
Arraste para ajustar a área de corte
|
|
366
358
|
</p>
|
|
367
359
|
</div>
|
|
368
360
|
|
|
369
361
|
<DialogFooter className="flex-row! items-center justify-start! gap-3 p-5 border-t border-zinc-200">
|
|
370
362
|
<Button onClick={handleConfirm} disabled={imageStatus !== 'ok' || !crop}>
|
|
371
|
-
|
|
363
|
+
Confirmar
|
|
372
364
|
</Button>
|
|
373
365
|
<Button variant="secondary" onClick={handleCancel}>
|
|
374
|
-
|
|
366
|
+
Cancelar
|
|
375
367
|
</Button>
|
|
376
368
|
</DialogFooter>
|
|
377
369
|
</>
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
'use client'
|
|
2
2
|
|
|
3
|
-
import { useTranslations } from 'next-intl'
|
|
4
3
|
import {
|
|
5
4
|
Dialog,
|
|
6
5
|
DialogContent,
|
|
@@ -29,7 +28,6 @@ export function ImageTooSmallModal({
|
|
|
29
28
|
onSelectAnother,
|
|
30
29
|
onCancel,
|
|
31
30
|
}: ImageTooSmallModalProps) {
|
|
32
|
-
const translate = useTranslations()
|
|
33
31
|
const dimensionText = `${minWidth}x${minHeight}px`
|
|
34
32
|
|
|
35
33
|
return (
|
|
@@ -40,20 +38,21 @@ export function ImageTooSmallModal({
|
|
|
40
38
|
>
|
|
41
39
|
<DialogHeader className="p-5">
|
|
42
40
|
<DialogTitle className="text-center text-[16px]!">
|
|
43
|
-
|
|
41
|
+
Foto menor que {dimensionText}
|
|
44
42
|
</DialogTitle>
|
|
45
43
|
</DialogHeader>
|
|
46
44
|
|
|
47
45
|
<div className="px-5 pb-5">
|
|
48
46
|
<p className="paragraph-small-regular text-zinc-600 text-center">
|
|
49
|
-
|
|
47
|
+
O arquivo "{fileName}" é menor que {dimensionText}. Faça envio de
|
|
48
|
+
uma imagem com pelo menos {dimensionText} para continuar.
|
|
50
49
|
</p>
|
|
51
50
|
</div>
|
|
52
51
|
|
|
53
52
|
<DialogFooter className="flex-row! items-center justify-start! gap-3 p-5 border-t border-zinc-200">
|
|
54
|
-
<Button onClick={onSelectAnother}>
|
|
53
|
+
<Button onClick={onSelectAnother}>Enviar outra</Button>
|
|
55
54
|
<Button variant="secondary" onClick={onCancel}>
|
|
56
|
-
|
|
55
|
+
Cancelar
|
|
57
56
|
</Button>
|
|
58
57
|
</DialogFooter>
|
|
59
58
|
</DialogContent>
|
package/src/index.ts
CHANGED
|
@@ -137,10 +137,7 @@ export type {
|
|
|
137
137
|
PlanTooltips,
|
|
138
138
|
} from "./modules/plans/types/plan.type";
|
|
139
139
|
export { PlanSchema, PlanItemSchema } from "./modules/plans/types/plan.type";
|
|
140
|
-
export {
|
|
141
|
-
mapApiPlanToUiPlan,
|
|
142
|
-
mapApiPlanToUiPlanForCurrency,
|
|
143
|
-
} from "./modules/plans/utils/map-api-plan-to-ui";
|
|
140
|
+
export { mapApiPlanToUiPlan } from "./modules/plans/utils/map-api-plan-to-ui";
|
|
144
141
|
export type { PlanBillingPeriod } from "./modules/plans/utils/map-api-plan-to-ui";
|
|
145
142
|
export {
|
|
146
143
|
usePlans,
|
|
@@ -465,13 +462,7 @@ export {
|
|
|
465
462
|
formatCNPJ,
|
|
466
463
|
formatCardNumber,
|
|
467
464
|
} from "./utils/format/masks";
|
|
468
|
-
export {
|
|
469
|
-
formatCurrency,
|
|
470
|
-
formatCurrencyNumber,
|
|
471
|
-
parseCurrencyToNumber,
|
|
472
|
-
getCurrencyForGateway,
|
|
473
|
-
} from "./utils/format/currency";
|
|
474
|
-
export type { CurrencyCode } from "./utils/format/currency";
|
|
465
|
+
export { formatCurrencyNumber } from "./utils/format/currency";
|
|
475
466
|
export { BR_STATE_OPTIONS } from "./utils/constants/br-states";
|
|
476
467
|
export type { TimezoneOption } from "./modules/accounts/services/timezone.service";
|
|
477
468
|
export {
|
|
@@ -495,7 +486,6 @@ export {
|
|
|
495
486
|
useCurrentAccount,
|
|
496
487
|
ACCOUNT_QUERY_KEY,
|
|
497
488
|
} from "./modules/accounts/hooks/current-account.hook";
|
|
498
|
-
export { useCurrencyFormatter } from "./modules/accounts/hooks/use-currency-formatter.hook";
|
|
499
489
|
export {
|
|
500
490
|
useUpdateAccount,
|
|
501
491
|
useUpdateAccountUser,
|
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
import { useCallback } from 'react';
|
|
4
4
|
import { useModalManager } from '../../../store/useModalManager';
|
|
5
5
|
import { useActiveSubscription } from '../../subscriptions/hooks/find-active-subscription.hook';
|
|
6
|
-
import { hasSubscriptionExpired } from '../../subscriptions/utils/has-subscription-expired';
|
|
7
6
|
import type { Card } from '../types';
|
|
8
7
|
|
|
9
8
|
type UseHandleDeleteCardOptions = {
|
|
@@ -19,15 +18,11 @@ export function useHandleDeleteCard({
|
|
|
19
18
|
|
|
20
19
|
return useCallback(
|
|
21
20
|
(card: Card) => {
|
|
22
|
-
// Só bloqueia a exclusão quando o cartão é o método de pagamento de uma
|
|
23
|
-
// assinatura REALMENTE ativa (mesma definição de ConfigurationsMyAccountModal).
|
|
24
|
-
// Se a assinatura foi cancelada ou já expirou, ela não está mais ativa —
|
|
25
|
-
// pula a verificação e segue direto pra exclusão do cartão.
|
|
26
21
|
const isCardLinkedToSubscription =
|
|
27
22
|
!!activeSubscription &&
|
|
28
|
-
activeSubscription.
|
|
29
|
-
!activeSubscription.
|
|
30
|
-
|
|
23
|
+
!!activeSubscription.date_cancellation &&
|
|
24
|
+
(!activeSubscription.date_due ||
|
|
25
|
+
activeSubscription.date_due < new Date()) &&
|
|
31
26
|
card.id.toString() === activeSubscription.id_card?.toString();
|
|
32
27
|
|
|
33
28
|
if (isCardLinkedToSubscription) {
|
|
@@ -3,24 +3,17 @@ import {
|
|
|
3
3
|
MAX_FILE_SIZE_MB,
|
|
4
4
|
} from '../constants/image.constants'
|
|
5
5
|
|
|
6
|
-
type TranslateFn = (key: any, values?: Record<string, string | number>) => string;
|
|
7
|
-
|
|
8
6
|
export interface ImageValidationResult {
|
|
9
7
|
valid: boolean
|
|
10
8
|
error?: string
|
|
11
9
|
}
|
|
12
10
|
|
|
13
|
-
export function validateImageFormat(
|
|
14
|
-
file: File,
|
|
15
|
-
translate?: TranslateFn
|
|
16
|
-
): ImageValidationResult {
|
|
11
|
+
export function validateImageFormat(file: File): ImageValidationResult {
|
|
17
12
|
// Bloqueia SVG explicitamente (segurança + não funciona com crop)
|
|
18
13
|
if (file.type === 'image/svg+xml' || file.name.toLowerCase().endsWith('.svg')) {
|
|
19
14
|
return {
|
|
20
15
|
valid: false,
|
|
21
|
-
error:
|
|
22
|
-
? translate('common.imageUpload.errorSvg')
|
|
23
|
-
: 'Formato SVG não é suportado. Use PNG, JPEG, WebP ou GIF.',
|
|
16
|
+
error: 'Formato SVG não é suportado. Use PNG, JPEG, WebP ou GIF.',
|
|
24
17
|
}
|
|
25
18
|
}
|
|
26
19
|
|
|
@@ -31,9 +24,7 @@ export function validateImageFormat(
|
|
|
31
24
|
) {
|
|
32
25
|
return {
|
|
33
26
|
valid: false,
|
|
34
|
-
error:
|
|
35
|
-
? translate('common.imageUpload.errorFormat')
|
|
36
|
-
: 'Formato não suportado. Use PNG, JPEG, WebP ou GIF.',
|
|
27
|
+
error: 'Formato não suportado. Use PNG, JPEG, WebP ou GIF.',
|
|
37
28
|
}
|
|
38
29
|
}
|
|
39
30
|
return { valid: true }
|
|
@@ -41,28 +32,22 @@ export function validateImageFormat(
|
|
|
41
32
|
|
|
42
33
|
export function validateImageSize(
|
|
43
34
|
file: File,
|
|
44
|
-
maxSizeMB: number = MAX_FILE_SIZE_MB
|
|
45
|
-
translate?: TranslateFn
|
|
35
|
+
maxSizeMB: number = MAX_FILE_SIZE_MB
|
|
46
36
|
): ImageValidationResult {
|
|
47
37
|
if (file.size > maxSizeMB * 1024 * 1024) {
|
|
48
38
|
return {
|
|
49
39
|
valid: false,
|
|
50
|
-
error:
|
|
51
|
-
? translate('common.imageUpload.errorTooLarge', { maxSize: maxSizeMB })
|
|
52
|
-
: `Arquivo muito grande. Máximo ${maxSizeMB}MB.`,
|
|
40
|
+
error: `Arquivo muito grande. Máximo ${maxSizeMB}MB.`,
|
|
53
41
|
}
|
|
54
42
|
}
|
|
55
43
|
return { valid: true }
|
|
56
44
|
}
|
|
57
45
|
|
|
58
|
-
export function validateImage(
|
|
59
|
-
file
|
|
60
|
-
translate?: TranslateFn
|
|
61
|
-
): ImageValidationResult {
|
|
62
|
-
const formatValidation = validateImageFormat(file, translate)
|
|
46
|
+
export function validateImage(file: File): ImageValidationResult {
|
|
47
|
+
const formatValidation = validateImageFormat(file)
|
|
63
48
|
if (!formatValidation.valid) return formatValidation
|
|
64
49
|
|
|
65
|
-
const sizeValidation = validateImageSize(file
|
|
50
|
+
const sizeValidation = validateImageSize(file)
|
|
66
51
|
if (!sizeValidation.valid) return sizeValidation
|
|
67
52
|
|
|
68
53
|
return { valid: true }
|
|
@@ -32,7 +32,7 @@ class PlansService {
|
|
|
32
32
|
const sort = params?.sort ?? "id:ASC";
|
|
33
33
|
const active = params?.active ?? "";
|
|
34
34
|
const search = params?.search ?? "";
|
|
35
|
-
return `${key}-${idWl}-${idAccount}-${sort}-${active}-${search}-
|
|
35
|
+
return `${key}-${idWl}-${idAccount}-${sort}-${active}-${search}-v4`;
|
|
36
36
|
}
|
|
37
37
|
|
|
38
38
|
/**
|
|
@@ -14,9 +14,6 @@ export const PlanSchema = z.object({
|
|
|
14
14
|
id_plan: z.number().optional(),
|
|
15
15
|
name: z.string(),
|
|
16
16
|
value: z.number().default(0),
|
|
17
|
-
// Preço em USD (conta stripe_usd). Operador cadastra no backend; ausente em planos
|
|
18
|
-
// sem suporte internacional. Espelha a coluna value_usd de gapps-r3-api.
|
|
19
|
-
value_usd: z.number().nullish(),
|
|
20
17
|
type: z.string().optional(),
|
|
21
18
|
discount_semester: z.number().default(0),
|
|
22
19
|
discount_annual: z.number().default(0),
|
|
@@ -6,85 +6,45 @@ import type {
|
|
|
6
6
|
UiPlan,
|
|
7
7
|
} from "../types/plan.type";
|
|
8
8
|
import { ADDON_IDS } from "../../subscriptions/constants/addons.constants";
|
|
9
|
-
import {
|
|
10
|
-
formatCurrencyNumber,
|
|
11
|
-
type CurrencyCode,
|
|
12
|
-
} from "../../../utils/format/currency";
|
|
9
|
+
import { formatCurrencyNumber } from "../../../utils/format/currency";
|
|
13
10
|
|
|
14
11
|
export type PlanBillingPeriod = "monthly" | "semiannual" | "annual";
|
|
15
12
|
|
|
16
|
-
|
|
13
|
+
const BASE_FEATURES: PlanFeature[] = [
|
|
14
|
+
{ icon: "check", text: "Visitas ilimitadas" },
|
|
15
|
+
{ icon: "check", text: "Leads ilimitadas" },
|
|
16
|
+
{ icon: "check", text: "Compartilhar páginas", tooltip: "sharePages" },
|
|
17
|
+
{ icon: "check", text: "Hospedagem inclusa" },
|
|
18
|
+
{ icon: "check", text: "SSL (HTTPS) + CDN" },
|
|
19
|
+
{ icon: "check", text: "Templates gratuitos" },
|
|
20
|
+
];
|
|
17
21
|
|
|
18
|
-
|
|
19
|
-
{ icon: "check", key: "plans.features.unlimitedVisits", fallback: "Visitas ilimitadas" },
|
|
20
|
-
{ icon: "check", key: "plans.features.unlimitedLeads", fallback: "Leads ilimitadas" },
|
|
21
|
-
{ icon: "check", key: "plans.features.sharePages", fallback: "Compartilhar páginas", tooltip: "sharePages" },
|
|
22
|
-
{ icon: "check", key: "plans.features.hosting", fallback: "Hospedagem inclusa" },
|
|
23
|
-
// SSL (HTTPS) + CDN — brand/acronym: never translated
|
|
24
|
-
{ icon: "check", key: null, fallback: "SSL (HTTPS) + CDN" },
|
|
25
|
-
{ icon: "check", key: "plans.features.freeTemplates", fallback: "Templates gratuitos" },
|
|
26
|
-
] as const;
|
|
27
|
-
|
|
28
|
-
function buildBaseFeatures(translate?: TranslateFn): PlanFeature[] {
|
|
29
|
-
return BASE_FEATURES_KEYS.map(({ icon, key, fallback, ...rest }) => {
|
|
30
|
-
const text = key && translate ? translate(`common.${key}`) : fallback;
|
|
31
|
-
const feature: PlanFeature = { icon, text };
|
|
32
|
-
if ("tooltip" in rest && rest.tooltip) feature.tooltip = rest.tooltip;
|
|
33
|
-
return feature;
|
|
34
|
-
});
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
function buildMainFeaturesFromItems(
|
|
38
|
-
items: Plan["items"],
|
|
39
|
-
translate?: TranslateFn
|
|
40
|
-
): PlanMainFeatures {
|
|
22
|
+
function buildMainFeaturesFromItems(items: Plan["items"]): PlanMainFeatures {
|
|
41
23
|
const pagesItem = items.find((i) => i.id_addon === ADDON_IDS.PAGES);
|
|
42
24
|
const domainsItem = items.find((i) => i.id_addon === ADDON_IDS.DOMAINS);
|
|
43
25
|
|
|
44
26
|
const pagesQty = pagesItem?.quantity ?? 0;
|
|
45
27
|
const domainsQty = domainsItem?.quantity ?? 1;
|
|
46
28
|
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
let domains: string;
|
|
63
|
-
if (domainsQty >= 999) {
|
|
64
|
-
domains = translate
|
|
65
|
-
? translate("common.plans.mainFeatures.domainsUnlimited")
|
|
66
|
-
: "Domínios ilimitados";
|
|
67
|
-
} else if (domainsQty === 1) {
|
|
68
|
-
domains = translate
|
|
69
|
-
? translate("common.plans.mainFeatures.domainSingular")
|
|
70
|
-
: "1 domínio externo";
|
|
71
|
-
} else {
|
|
72
|
-
domains = translate
|
|
73
|
-
? translate("common.plans.mainFeatures.domainsPlural", { count: domainsQty })
|
|
74
|
-
: `${domainsQty} domínios externos`;
|
|
75
|
-
}
|
|
76
|
-
|
|
77
|
-
const users = translate
|
|
78
|
-
? translate("common.plans.mainFeatures.usersUnlimited")
|
|
79
|
-
: "Usuários ilimitados";
|
|
80
|
-
|
|
81
|
-
return { pages, domains, users };
|
|
29
|
+
return {
|
|
30
|
+
pages:
|
|
31
|
+
pagesQty === 0
|
|
32
|
+
? "Páginas ilimitadas"
|
|
33
|
+
: pagesQty === 1
|
|
34
|
+
? "1 página"
|
|
35
|
+
: `${pagesQty} páginas`,
|
|
36
|
+
domains:
|
|
37
|
+
domainsQty >= 999
|
|
38
|
+
? "Domínios ilimitados"
|
|
39
|
+
: domainsQty === 1
|
|
40
|
+
? "1 domínio externo"
|
|
41
|
+
: `${domainsQty} domínios externos`,
|
|
42
|
+
users: "Usuários ilimitados",
|
|
43
|
+
};
|
|
82
44
|
}
|
|
83
45
|
|
|
84
|
-
function computePricingByPeriod(apiPlan: Plan
|
|
85
|
-
|
|
86
|
-
// não cadastrou o preço internacional. Os descontos por período são percentuais — aplicam igual.
|
|
87
|
-
const monthly = currency === "usd" ? (apiPlan.value_usd ?? apiPlan.value) : apiPlan.value;
|
|
46
|
+
function computePricingByPeriod(apiPlan: Plan): PlanPricingByPeriod {
|
|
47
|
+
const monthly = apiPlan.value;
|
|
88
48
|
const round2 = (n: number) => Math.round(n * 100) / 100;
|
|
89
49
|
return {
|
|
90
50
|
monthly,
|
|
@@ -93,32 +53,34 @@ function computePricingByPeriod(apiPlan: Plan, currency: CurrencyCode): PlanPric
|
|
|
93
53
|
};
|
|
94
54
|
}
|
|
95
55
|
|
|
96
|
-
function
|
|
56
|
+
export function mapApiPlanToUiPlan(plan: Plan): UiPlan {
|
|
97
57
|
const popular = plan.id === 2 || plan.id_plan === 2;
|
|
98
58
|
const buttonVariant = popular ? "brand" : "default";
|
|
99
59
|
|
|
100
|
-
const pricingByPeriod = computePricingByPeriod(plan
|
|
60
|
+
const pricingByPeriod = computePricingByPeriod(plan);
|
|
101
61
|
const monthlyFinal = pricingByPeriod.monthly;
|
|
102
62
|
|
|
103
63
|
const lowerName = plan.name.toLowerCase();
|
|
104
64
|
const hasProjectAndOnboarding =
|
|
105
65
|
lowerName.includes("agência") || lowerName.includes("agencia");
|
|
106
66
|
|
|
107
|
-
const onboardingText = translate
|
|
108
|
-
? translate("common.plans.features.onboarding")
|
|
109
|
-
: "Reunião de Onboarding";
|
|
110
|
-
const projectMgmtText = translate
|
|
111
|
-
? translate("common.plans.features.projectManagement")
|
|
112
|
-
: "Gestão de projetos";
|
|
113
|
-
|
|
114
67
|
const features: PlanFeature[] = [
|
|
115
|
-
...
|
|
68
|
+
...BASE_FEATURES,
|
|
116
69
|
hasProjectAndOnboarding
|
|
117
|
-
? { icon: "check", text:
|
|
118
|
-
: { icon: "x", text:
|
|
70
|
+
? { icon: "check", text: "Reunião de Onboarding" }
|
|
71
|
+
: { icon: "x", text: "Reunião de Onboarding", disabled: true },
|
|
119
72
|
hasProjectAndOnboarding
|
|
120
|
-
? {
|
|
121
|
-
|
|
73
|
+
? {
|
|
74
|
+
icon: "check",
|
|
75
|
+
text: "Gestão de projetos",
|
|
76
|
+
tooltip: "projectManagement",
|
|
77
|
+
}
|
|
78
|
+
: {
|
|
79
|
+
icon: "x",
|
|
80
|
+
text: "Gestão de projetos",
|
|
81
|
+
disabled: true,
|
|
82
|
+
tooltip: "projectManagement",
|
|
83
|
+
},
|
|
122
84
|
];
|
|
123
85
|
|
|
124
86
|
return {
|
|
@@ -126,30 +88,11 @@ function buildUiPlan(plan: Plan, currency: CurrencyCode, translate?: TranslateFn
|
|
|
126
88
|
name: plan.name,
|
|
127
89
|
isPopular: popular,
|
|
128
90
|
buttonVariant,
|
|
129
|
-
mainFeatures: buildMainFeaturesFromItems(plan.items
|
|
91
|
+
mainFeatures: buildMainFeaturesFromItems(plan.items),
|
|
130
92
|
features,
|
|
131
|
-
originalPrice: formatCurrencyNumber(monthlyFinal
|
|
132
|
-
price: formatCurrencyNumber(monthlyFinal
|
|
93
|
+
originalPrice: formatCurrencyNumber(monthlyFinal),
|
|
94
|
+
price: formatCurrencyNumber(monthlyFinal),
|
|
133
95
|
pricingByPeriod,
|
|
134
96
|
items: plan.items,
|
|
135
97
|
};
|
|
136
98
|
}
|
|
137
|
-
|
|
138
|
-
/**
|
|
139
|
-
* Mapeia um plano da API para UiPlan em BRL.
|
|
140
|
-
* Assinatura de 1 argumento — seguro em `plans.map(mapApiPlanToUiPlan)`.
|
|
141
|
-
* Passa `translate` opcional para i18n; sem ele cai nos literais pt-br (back-compat).
|
|
142
|
-
*/
|
|
143
|
-
export function mapApiPlanToUiPlan(plan: Plan, translate?: TranslateFn): UiPlan {
|
|
144
|
-
return buildUiPlan(plan, "brl", translate);
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
/**
|
|
148
|
-
* Variante currency-aware: a moeda vem do gateway da conta (getCurrencyForGateway).
|
|
149
|
-
* Fábrica para uso ergonômico em `.map`: `plans.map(mapApiPlanToUiPlanForCurrency(currency, translate))`.
|
|
150
|
-
* Mantida separada de mapApiPlanToUiPlan para não quebrar callers que passam a fn direto pro `.map`.
|
|
151
|
-
*/
|
|
152
|
-
export const mapApiPlanToUiPlanForCurrency =
|
|
153
|
-
(currency: CurrencyCode, translate?: TranslateFn) =>
|
|
154
|
-
(plan: Plan): UiPlan =>
|
|
155
|
-
buildUiPlan(plan, currency, translate);
|
|
@@ -1,8 +1,6 @@
|
|
|
1
1
|
import type { BillingPeriod } from '../types/billing-period.type';
|
|
2
2
|
import type { CalculateSubscriptionResponse } from '../types/calculate-subscription.type';
|
|
3
3
|
|
|
4
|
-
type TranslateFn = (key: any, values?: Record<string, string | number>) => string;
|
|
5
|
-
|
|
6
4
|
export function periodicityToBillingPeriod(
|
|
7
5
|
periodicity: number | string | null | undefined
|
|
8
6
|
): BillingPeriod | null {
|
|
@@ -18,38 +16,23 @@ export function billingPeriodToNumeric(billingPeriod: BillingPeriod): 30 | 180 |
|
|
|
18
16
|
return 30;
|
|
19
17
|
}
|
|
20
18
|
|
|
21
|
-
export function getPeriodicityLabel(
|
|
22
|
-
periodicity: number | string | null | undefined,
|
|
23
|
-
translate?: TranslateFn
|
|
24
|
-
): string {
|
|
19
|
+
export function getPeriodicityLabel(periodicity: number | string | null | undefined): string {
|
|
25
20
|
const period = periodicityToBillingPeriod(periodicity);
|
|
26
|
-
if (period === 'semiannual')
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
return translate ? translate('common.periodicity.annual') : 'Anual';
|
|
30
|
-
return translate ? translate('common.periodicity.monthly') : 'Mensal';
|
|
21
|
+
if (period === 'semiannual') return 'Semestral';
|
|
22
|
+
if (period === 'annual') return 'Anual';
|
|
23
|
+
return 'Mensal';
|
|
31
24
|
}
|
|
32
25
|
|
|
33
|
-
export function getBillingPeriodSuffix(
|
|
34
|
-
billingPeriod
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
if (billingPeriod === 'semiannual')
|
|
38
|
-
return translate ? translate('common.periodicity.suffixSemiannual') : '/semestre';
|
|
39
|
-
if (billingPeriod === 'annual')
|
|
40
|
-
return translate ? translate('common.periodicity.suffixAnnual') : '/ano';
|
|
41
|
-
return translate ? translate('common.periodicity.suffixMonthly') : '/mês';
|
|
26
|
+
export function getBillingPeriodSuffix(billingPeriod: BillingPeriod): string {
|
|
27
|
+
if (billingPeriod === 'semiannual') return '/semestre';
|
|
28
|
+
if (billingPeriod === 'annual') return '/ano';
|
|
29
|
+
return '/mês';
|
|
42
30
|
}
|
|
43
31
|
|
|
44
|
-
export function getBillingPeriodLabel(
|
|
45
|
-
billingPeriod
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
if (billingPeriod === 'semiannual')
|
|
49
|
-
return translate ? translate('common.periodicity.labelSemiannual') : 'semestral';
|
|
50
|
-
if (billingPeriod === 'annual')
|
|
51
|
-
return translate ? translate('common.periodicity.labelAnnual') : 'anual';
|
|
52
|
-
return translate ? translate('common.periodicity.labelMonthly') : 'mensal';
|
|
32
|
+
export function getBillingPeriodLabel(billingPeriod: BillingPeriod): string {
|
|
33
|
+
if (billingPeriod === 'semiannual') return 'semestral';
|
|
34
|
+
if (billingPeriod === 'annual') return 'anual';
|
|
35
|
+
return 'mensal';
|
|
53
36
|
}
|
|
54
37
|
|
|
55
38
|
export function getBillingPeriodMonths(billingPeriod: BillingPeriod): number {
|
|
@@ -5,7 +5,6 @@ import {
|
|
|
5
5
|
ReactNode,
|
|
6
6
|
useCallback,
|
|
7
7
|
useContext,
|
|
8
|
-
useEffect,
|
|
9
8
|
useMemo,
|
|
10
9
|
} from "react";
|
|
11
10
|
import { useQueryClient } from "@tanstack/react-query";
|
|
@@ -42,10 +41,8 @@ import {
|
|
|
42
41
|
useCurrentAccount,
|
|
43
42
|
ACCOUNT_QUERY_KEY,
|
|
44
43
|
} from "../modules/accounts/hooks/current-account.hook";
|
|
45
|
-
import { useWhitelabelUrls
|
|
44
|
+
import { useWhitelabelUrls } from "./whitelabel.provider";
|
|
46
45
|
import { useWlQueryKey } from "../hooks/useAuthQueryKey";
|
|
47
|
-
import { normalizeLocale } from "../i18n/normalize";
|
|
48
|
-
import { setLocaleCookie } from "../utils/intl/locale-cookie";
|
|
49
46
|
|
|
50
47
|
interface AuthContextProps extends AuthState {
|
|
51
48
|
login: (credentials: LoginRequest) => Promise<LoginResult>;
|
|
@@ -71,17 +68,8 @@ export function AuthProvider({ children }: AuthProviderProps) {
|
|
|
71
68
|
const queryClient = useQueryClient();
|
|
72
69
|
const setUserData = useSetUserData();
|
|
73
70
|
const { accountsUrl, pagesUrl } = useWhitelabelUrls();
|
|
74
|
-
const { whitelabel } = useWhitelabel();
|
|
75
71
|
const accountKey = useWlQueryKey([...ACCOUNT_QUERY_KEY]);
|
|
76
72
|
|
|
77
|
-
// Mantém o cookie NEXT_LOCALE alinhado à preferência da conta (login, sessão existente,
|
|
78
|
-
// atualização). Compartilhado entre subdomínios via domínio do whitelabel. A próxima
|
|
79
|
-
// navegação/requisição passa a resolver o locale pela preferência do usuário.
|
|
80
|
-
useEffect(() => {
|
|
81
|
-
const locale = normalizeLocale(user?.language);
|
|
82
|
-
if (locale) setLocaleCookie(locale, whitelabel?.domain);
|
|
83
|
-
}, [user?.language, whitelabel?.domain]);
|
|
84
|
-
|
|
85
73
|
const { mutateAsync: loginMutate, isPending: isLogging } = useLogin();
|
|
86
74
|
const { mutateAsync: registerMutate, isPending: isRegistering } =
|
|
87
75
|
useRegister();
|