@greatapps/common 1.1.707 → 1.1.709
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/ui/data-display/PaymentInfoCard.mjs +1 -1
- package/dist/components/ui/data-display/PaymentInfoCard.mjs.map +1 -1
- package/dist/modules/ia-credits/hooks/ia-credits.hook.mjs +3 -2
- package/dist/modules/ia-credits/hooks/ia-credits.hook.mjs.map +1 -1
- package/package.json +1 -1
- package/src/components/ui/data-display/PaymentInfoCard.tsx +2 -2
- package/src/modules/ia-credits/hooks/ia-credits.hook.ts +6 -1
|
@@ -113,7 +113,7 @@ function PaymentInfoCard({
|
|
|
113
113
|
/* @__PURE__ */ jsxs(
|
|
114
114
|
"div",
|
|
115
115
|
{
|
|
116
|
-
className: `flex flex-col gap-2 px-4
|
|
116
|
+
className: `flex flex-col gap-2 px-4 transition-all duration-300 ease-in-out ${isExpanded ? "max-h-[167px] overflow-y-auto pb-4 opacity-100" : "max-h-0 overflow-hidden pb-0 opacity-0"}`,
|
|
117
117
|
children: [
|
|
118
118
|
displayedCards.map((card) => /* @__PURE__ */ jsx(
|
|
119
119
|
CardItem,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/components/ui/data-display/PaymentInfoCard.tsx"],"sourcesContent":["'use client';\n\nimport { useCallback, useState } from 'react';\nimport { IconChevronDown, IconPlus } from '@tabler/icons-react';\nimport { CardBrandIcon } from './CardBrandIcons';\nimport { CardItem } from './CardItem';\nimport useIsMobile from '../../../hooks/useIsMobile';\nimport { useCards } from '../../../modules/cards/hooks/cards.hook';\nimport { useModalManager } from '../../../store/useModalManager';\nimport { useIsDefaultWhitelabel } from '../../../providers/whitelabel.provider';\nimport type { Card } from '../../../modules/cards/types';\nimport { useTranslations } from 'next-intl';\n\ntype PaymentInfoCardProps = {\n email?: string;\n selectedCardId: string;\n onCardSelect: (cardId: string) => void;\n onManageCards?: () => void;\n onOpenAddCard?: () => void;\n hideDelete?: boolean;\n hideSetDefault?: boolean;\n};\n\nexport function PaymentInfoCard({\n email,\n selectedCardId,\n onCardSelect,\n onManageCards,\n onOpenAddCard,\n hideDelete,\n hideSetDefault,\n}: PaymentInfoCardProps) {\n const translate = useTranslations();\n const isMobile = useIsMobile();\n const { openModal } = useModalManager();\n const isDefaultWl = useIsDefaultWhitelabel();\n\n const [isExpanded, setIsExpanded] = useState(false);\n\n const { data: cardsData } = useCards();\n const cards = cardsData?.data ?? [];\n\n const selectedCard = cards.find(\n (card) => card.id.toString() === selectedCardId.toString(),\n );\n\n const hasCards = cards.length > 0;\n\n const hasMoreThan3Cards = cards.length > 3;\n const shouldShowManageButton = isMobile && hasMoreThan3Cards;\n const displayedCards = shouldShowManageButton ? cards.slice(0, 3) : cards;\n\n const handleOpenAddCardModal = useCallback(() => {\n if (onOpenAddCard) {\n onOpenAddCard();\n return;\n }\n openModal('addCardModal', {\n onCardAdded: (cardId: string) => onCardSelect(cardId),\n });\n }, [openModal, onOpenAddCard, onCardSelect]);\n\n const handleSelectCard = useCallback(\n (cardId: string) => {\n onCardSelect(cardId);\n setIsExpanded(false);\n },\n [onCardSelect],\n );\n\n const handleAfterDelete = useCallback(\n (card: Card) => {\n if (card.id.toString() === selectedCardId.toString()) {\n const remaining = cards.filter((c) => c.id !== card.id);\n if (remaining.length > 0) {\n onCardSelect(remaining[0].id.toString());\n }\n }\n },\n [cards, selectedCardId, onCardSelect],\n );\n\n if (!hasCards) {\n return (\n <div className=\"border border-zinc-200 rounded-lg overflow-hidden\">\n {email && (\n <div className=\"flex items-center h-[60px] px-4 border-b border-zinc-200 gap-3\">\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.email')}</span>\n <span className=\"paragraph-small-medium text-zinc-950 flex-1\">{email}</span>\n </div>\n )}\n <div className=\"flex items-center h-[60px] px-4 gap-3\">\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.payment')}</span>\n <button\n type=\"button\"\n onClick={handleOpenAddCardModal}\n className=\"flex items-center h-8 px-2 paragraph-small-semibold text-zinc-950 border border-zinc-200 rounded-md hover:border-zinc-400 transition-colors cursor-pointer w-fit\"\n >\n <IconPlus className=\"size-[18px]\" />\n <span className=\"px-1.5\">{translate('common.cards.paymentInfo.addCard')}</span>\n </button>\n </div>\n </div>\n );\n }\n\n return (\n <div className=\"flex flex-col gap-3\">\n <div className=\"border border-zinc-200 rounded-lg overflow-hidden\">\n {email && (\n <div className=\"flex items-center h-[60px] px-4 border-b border-zinc-200 gap-3\">\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.email')}</span>\n <span className=\"paragraph-small-medium text-zinc-950 flex-1\">{email}</span>\n </div>\n )}\n\n <div\n className=\"flex items-center px-4 py-4 cursor-pointer gap-3\"\n onClick={() => setIsExpanded((prev) => !prev)}\n >\n {!isExpanded ? (\n <>\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.payment')}</span>\n <div className=\"flex flex-col gap-0.5 flex-1 min-w-0\">\n <span className=\"paragraph-small-semibold text-zinc-950 truncate\">\n {selectedCard?.name}\n </span>\n <span className=\"paragraph-small-medium text-zinc-950\">\n •••• {selectedCard?.number?.replaceAll(/\\D/g, '')?.slice(-4)}\n </span>\n </div>\n {selectedCard && <CardBrandIcon brand={selectedCard.brand} />}\n <div className=\"size-8 flex items-center justify-center rounded-lg\">\n <IconChevronDown className=\"size-[18px] text-zinc-500\" />\n </div>\n </>\n ) : (\n <>\n <span className=\"paragraph-small-semibold text-zinc-950 flex-1\">\n {translate('common.cards.paymentInfo.selectPaymentMethod')}\n </span>\n <div className=\"size-8 flex items-center justify-center rounded-lg\">\n <IconChevronDown className=\"size-[18px] text-zinc-500 rotate-180\" />\n </div>\n </>\n )}\n </div>\n\n <div\n className={`flex flex-col gap-2 px-4 overflow-hidden transition-all duration-300 ease-in-out ${\n isExpanded ? 'max-h-[500px] pb-4 opacity-100' : 'max-h-0 pb-0 opacity-0'\n }`}\n >\n {displayedCards.map((card) => (\n <CardItem\n key={card.id}\n card={card}\n isSelected={card.id.toString() === selectedCardId.toString()}\n onSelect={() => handleSelectCard(card.id.toString())}\n hideDelete={hideDelete}\n hideSetDefault={hideSetDefault}\n onAfterDelete={handleAfterDelete}\n />\n ))}\n {shouldShowManageButton && onManageCards && (\n <button\n type=\"button\"\n onClick={onManageCards}\n className={`flex items-center justify-center h-10 px-4 paragraph-small-semibold rounded-lg transition-colors cursor-pointer mt-2 ${\n isDefaultWl\n ? 'text-cyan-600 border border-cyan-200 hover:bg-cyan-50'\n : 'text-zinc-600 border border-zinc-200 hover:bg-zinc-50'\n }`}\n >\n {translate('common.cards.paymentInfo.manageCards')}\n </button>\n )}\n </div>\n </div>\n\n <button\n type=\"button\"\n onClick={handleOpenAddCardModal}\n className=\"flex items-center h-8 px-2 paragraph-small-semibold text-zinc-950 border border-zinc-200 rounded-md hover:border-zinc-400 transition-colors cursor-pointer w-fit\"\n >\n <IconPlus className=\"size-[18px]\" />\n <span className=\"px-1.5\">\n {isExpanded ? translate('common.cards.paymentInfo.addCard') : translate('common.cards.paymentInfo.newPaymentMethod')}\n </span>\n </button>\n </div>\n );\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../../../src/components/ui/data-display/PaymentInfoCard.tsx"],"sourcesContent":["'use client';\n\nimport { useCallback, useState } from 'react';\nimport { IconChevronDown, IconPlus } from '@tabler/icons-react';\nimport { CardBrandIcon } from './CardBrandIcons';\nimport { CardItem } from './CardItem';\nimport useIsMobile from '../../../hooks/useIsMobile';\nimport { useCards } from '../../../modules/cards/hooks/cards.hook';\nimport { useModalManager } from '../../../store/useModalManager';\nimport { useIsDefaultWhitelabel } from '../../../providers/whitelabel.provider';\nimport type { Card } from '../../../modules/cards/types';\nimport { useTranslations } from 'next-intl';\n\ntype PaymentInfoCardProps = {\n email?: string;\n selectedCardId: string;\n onCardSelect: (cardId: string) => void;\n onManageCards?: () => void;\n onOpenAddCard?: () => void;\n hideDelete?: boolean;\n hideSetDefault?: boolean;\n};\n\nexport function PaymentInfoCard({\n email,\n selectedCardId,\n onCardSelect,\n onManageCards,\n onOpenAddCard,\n hideDelete,\n hideSetDefault,\n}: PaymentInfoCardProps) {\n const translate = useTranslations();\n const isMobile = useIsMobile();\n const { openModal } = useModalManager();\n const isDefaultWl = useIsDefaultWhitelabel();\n\n const [isExpanded, setIsExpanded] = useState(false);\n\n const { data: cardsData } = useCards();\n const cards = cardsData?.data ?? [];\n\n const selectedCard = cards.find(\n (card) => card.id.toString() === selectedCardId.toString(),\n );\n\n const hasCards = cards.length > 0;\n\n const hasMoreThan3Cards = cards.length > 3;\n const shouldShowManageButton = isMobile && hasMoreThan3Cards;\n const displayedCards = shouldShowManageButton ? cards.slice(0, 3) : cards;\n\n const handleOpenAddCardModal = useCallback(() => {\n if (onOpenAddCard) {\n onOpenAddCard();\n return;\n }\n openModal('addCardModal', {\n onCardAdded: (cardId: string) => onCardSelect(cardId),\n });\n }, [openModal, onOpenAddCard, onCardSelect]);\n\n const handleSelectCard = useCallback(\n (cardId: string) => {\n onCardSelect(cardId);\n setIsExpanded(false);\n },\n [onCardSelect],\n );\n\n const handleAfterDelete = useCallback(\n (card: Card) => {\n if (card.id.toString() === selectedCardId.toString()) {\n const remaining = cards.filter((c) => c.id !== card.id);\n if (remaining.length > 0) {\n onCardSelect(remaining[0].id.toString());\n }\n }\n },\n [cards, selectedCardId, onCardSelect],\n );\n\n if (!hasCards) {\n return (\n <div className=\"border border-zinc-200 rounded-lg overflow-hidden\">\n {email && (\n <div className=\"flex items-center h-[60px] px-4 border-b border-zinc-200 gap-3\">\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.email')}</span>\n <span className=\"paragraph-small-medium text-zinc-950 flex-1\">{email}</span>\n </div>\n )}\n <div className=\"flex items-center h-[60px] px-4 gap-3\">\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.payment')}</span>\n <button\n type=\"button\"\n onClick={handleOpenAddCardModal}\n className=\"flex items-center h-8 px-2 paragraph-small-semibold text-zinc-950 border border-zinc-200 rounded-md hover:border-zinc-400 transition-colors cursor-pointer w-fit\"\n >\n <IconPlus className=\"size-[18px]\" />\n <span className=\"px-1.5\">{translate('common.cards.paymentInfo.addCard')}</span>\n </button>\n </div>\n </div>\n );\n }\n\n return (\n <div className=\"flex flex-col gap-3\">\n <div className=\"border border-zinc-200 rounded-lg overflow-hidden\">\n {email && (\n <div className=\"flex items-center h-[60px] px-4 border-b border-zinc-200 gap-3\">\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.email')}</span>\n <span className=\"paragraph-small-medium text-zinc-950 flex-1\">{email}</span>\n </div>\n )}\n\n <div\n className=\"flex items-center px-4 py-4 cursor-pointer gap-3\"\n onClick={() => setIsExpanded((prev) => !prev)}\n >\n {!isExpanded ? (\n <>\n <span className=\"paragraph-small-medium text-zinc-500 w-[100px]\">{translate('common.cards.paymentInfo.payment')}</span>\n <div className=\"flex flex-col gap-0.5 flex-1 min-w-0\">\n <span className=\"paragraph-small-semibold text-zinc-950 truncate\">\n {selectedCard?.name}\n </span>\n <span className=\"paragraph-small-medium text-zinc-950\">\n •••• {selectedCard?.number?.replaceAll(/\\D/g, '')?.slice(-4)}\n </span>\n </div>\n {selectedCard && <CardBrandIcon brand={selectedCard.brand} />}\n <div className=\"size-8 flex items-center justify-center rounded-lg\">\n <IconChevronDown className=\"size-[18px] text-zinc-500\" />\n </div>\n </>\n ) : (\n <>\n <span className=\"paragraph-small-semibold text-zinc-950 flex-1\">\n {translate('common.cards.paymentInfo.selectPaymentMethod')}\n </span>\n <div className=\"size-8 flex items-center justify-center rounded-lg\">\n <IconChevronDown className=\"size-[18px] text-zinc-500 rotate-180\" />\n </div>\n </>\n )}\n </div>\n\n <div\n className={`flex flex-col gap-2 px-4 transition-all duration-300 ease-in-out ${\n isExpanded ? 'max-h-[167px] overflow-y-auto pb-4 opacity-100' : 'max-h-0 overflow-hidden pb-0 opacity-0'\n }`}\n >\n {displayedCards.map((card) => (\n <CardItem\n key={card.id}\n card={card}\n isSelected={card.id.toString() === selectedCardId.toString()}\n onSelect={() => handleSelectCard(card.id.toString())}\n hideDelete={hideDelete}\n hideSetDefault={hideSetDefault}\n onAfterDelete={handleAfterDelete}\n />\n ))}\n {shouldShowManageButton && onManageCards && (\n <button\n type=\"button\"\n onClick={onManageCards}\n className={`flex items-center justify-center h-10 px-4 paragraph-small-semibold rounded-lg transition-colors cursor-pointer mt-2 ${\n isDefaultWl\n ? 'text-cyan-600 border border-cyan-200 hover:bg-cyan-50'\n : 'text-zinc-600 border border-zinc-200 hover:bg-zinc-50'\n }`}\n >\n {translate('common.cards.paymentInfo.manageCards')}\n </button>\n )}\n </div>\n </div>\n\n <button\n type=\"button\"\n onClick={handleOpenAddCardModal}\n className=\"flex items-center h-8 px-2 paragraph-small-semibold text-zinc-950 border border-zinc-200 rounded-md hover:border-zinc-400 transition-colors cursor-pointer w-fit\"\n >\n <IconPlus className=\"size-[18px]\" />\n <span className=\"px-1.5\">\n {isExpanded ? translate('common.cards.paymentInfo.addCard') : translate('common.cards.paymentInfo.newPaymentMethod')}\n </span>\n </button>\n </div>\n );\n}\n"],"mappings":"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","names":[]}
|
|
@@ -48,7 +48,7 @@ function calculateSummary(operations) {
|
|
|
48
48
|
nextExpirationInDays
|
|
49
49
|
};
|
|
50
50
|
}
|
|
51
|
-
function useIaCredits() {
|
|
51
|
+
function useIaCredits(options = {}) {
|
|
52
52
|
const { data: subscriptionData, isPending: isSubscriptionLoading } = useActiveSubscription();
|
|
53
53
|
const subscription = subscriptionData?.data?.[0] ?? null;
|
|
54
54
|
const subscriptionId = subscription?.id;
|
|
@@ -59,7 +59,8 @@ function useIaCredits() {
|
|
|
59
59
|
`/api/subscriptions/${subscriptionId}/ia-credits`,
|
|
60
60
|
{ signal }
|
|
61
61
|
),
|
|
62
|
-
enabled: subscriptionId != null
|
|
62
|
+
enabled: subscriptionId != null,
|
|
63
|
+
refetchInterval: options.refetchInterval ?? false
|
|
63
64
|
});
|
|
64
65
|
const operations = query.data?.data ?? [];
|
|
65
66
|
const summary = useMemo(() => calculateSummary(operations), [operations]);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/modules/ia-credits/hooks/ia-credits.hook.ts"],"sourcesContent":["'use client';\n\nimport { useMemo } from 'react';\nimport { useQuery } from '@tanstack/react-query';\nimport { apiFetch } from '../../../infra/http/api-fetch';\nimport type { PaginatedSuccessResult } from '../../../infra/api/types';\nimport type { IaCreditOperation, IaCreditsSummary } from '../types';\nimport { useActiveSubscription } from '../../subscriptions/hooks/find-active-subscription.hook';\nimport { useAuthQueryKey } from '../../../hooks/useAuthQueryKey';\n\nfunction calculateSummary(operations: IaCreditOperation[]): IaCreditsSummary {\n const today = new Date();\n const todayDate = new Date(today.getFullYear(), today.getMonth(), today.getDate());\n\n const adds = operations.filter((op) => op.operation === 'add');\n const subtracts = operations.filter((op) => op.operation === 'subtract');\n\n let totalCredits = 0;\n let usedCredits = 0;\n let nextExpirationInDays: number | null = null;\n let nextExpiringCredits: number | null = null;\n\n for (const add of adds) {\n const expirationRaw = add.expiration_time;\n if (!expirationRaw) continue;\n\n const expiration = new Date(expirationRaw);\n const expirationDate = new Date(\n expiration.getFullYear(),\n expiration.getMonth(),\n expiration.getDate()\n );\n\n const expiredByDate = expirationDate.getTime() < todayDate.getTime();\n const hasExpired = add.has_expired || expiredByDate;\n\n if (hasExpired) continue;\n\n const addedCredits = add.operation_value;\n\n const consumedForAdd = subtracts\n .filter((sub) => String(sub.consumed_from_add_id) === String(add.id))\n .reduce((sum, sub) => sum + sub.operation_value, 0);\n\n const remainingForAdd = Math.max(0, addedCredits - consumedForAdd);\n\n totalCredits += addedCredits;\n usedCredits += consumedForAdd;\n\n const diffMs = expirationDate.getTime() - todayDate.getTime();\n const days = Math.max(0, Math.ceil(diffMs / (1000 * 60 * 60 * 24)));\n\n if (remainingForAdd > 0) {\n if (nextExpirationInDays === null || days < nextExpirationInDays) {\n nextExpirationInDays = days;\n nextExpiringCredits = remainingForAdd;\n }\n }\n }\n\n const availableCredits = Math.max(0, totalCredits - usedCredits);\n\n return {\n totalCredits,\n usedCredits,\n availableCredits,\n nextExpiringCredits,\n nextExpirationInDays,\n };\n}\n\nexport function useIaCredits() {\n const { data: subscriptionData, isPending: isSubscriptionLoading } = useActiveSubscription();\n const subscription = subscriptionData?.data?.[0] ?? null;\n const subscriptionId = subscription?.id;\n const queryKey = useAuthQueryKey(['ia-credits', subscriptionId]);\n\n const query = useQuery({\n queryKey,\n queryFn: ({ signal }) =>\n apiFetch<PaginatedSuccessResult<IaCreditOperation>>(\n `/api/subscriptions/${subscriptionId}/ia-credits`,\n { signal }\n ),\n enabled: subscriptionId != null,\n });\n\n const operations = query.data?.data ?? [];\n\n // eslint-disable-next-line react-hooks/exhaustive-deps\n const summary = useMemo(() => calculateSummary(operations), [operations]);\n\n return {\n subscription,\n operations,\n summary,\n isLoading: isSubscriptionLoading || query.isPending,\n isSubscriptionLoading,\n isCreditsLoading: query.isPending,\n isError: query.isError,\n error: query.error,\n };\n}\n"],"mappings":";AAEA,SAAS,eAAe;AACxB,SAAS,gBAAgB;AACzB,SAAS,gBAAgB;AAGzB,SAAS,6BAA6B;AACtC,SAAS,uBAAuB;AAEhC,SAAS,iBAAiB,YAAmD;AAC3E,QAAM,QAAQ,oBAAI,KAAK;AACvB,QAAM,YAAY,IAAI,KAAK,MAAM,YAAY,GAAG,MAAM,SAAS,GAAG,MAAM,QAAQ,CAAC;AAEjF,QAAM,OAAO,WAAW,OAAO,CAAC,OAAO,GAAG,cAAc,KAAK;AAC7D,QAAM,YAAY,WAAW,OAAO,CAAC,OAAO,GAAG,cAAc,UAAU;AAEvE,MAAI,eAAe;AACnB,MAAI,cAAc;AAClB,MAAI,uBAAsC;AAC1C,MAAI,sBAAqC;AAEzC,aAAW,OAAO,MAAM;AACtB,UAAM,gBAAgB,IAAI;AAC1B,QAAI,CAAC,cAAe;AAEpB,UAAM,aAAa,IAAI,KAAK,aAAa;AACzC,UAAM,iBAAiB,IAAI;AAAA,MACzB,WAAW,YAAY;AAAA,MACvB,WAAW,SAAS;AAAA,MACpB,WAAW,QAAQ;AAAA,IACrB;AAEA,UAAM,gBAAgB,eAAe,QAAQ,IAAI,UAAU,QAAQ;AACnE,UAAM,aAAa,IAAI,eAAe;AAEtC,QAAI,WAAY;AAEhB,UAAM,eAAe,IAAI;AAEzB,UAAM,iBAAiB,UACpB,OAAO,CAAC,QAAQ,OAAO,IAAI,oBAAoB,MAAM,OAAO,IAAI,EAAE,CAAC,EACnE,OAAO,CAAC,KAAK,QAAQ,MAAM,IAAI,iBAAiB,CAAC;AAEpD,UAAM,kBAAkB,KAAK,IAAI,GAAG,eAAe,cAAc;AAEjE,oBAAgB;AAChB,mBAAe;AAEf,UAAM,SAAS,eAAe,QAAQ,IAAI,UAAU,QAAQ;AAC5D,UAAM,OAAO,KAAK,IAAI,GAAG,KAAK,KAAK,UAAU,MAAO,KAAK,KAAK,GAAG,CAAC;AAElE,QAAI,kBAAkB,GAAG;AACvB,UAAI,yBAAyB,QAAQ,OAAO,sBAAsB;AAChE,+BAAuB;AACvB,8BAAsB;AAAA,MACxB;AAAA,IACF;AAAA,EACF;AAEA,QAAM,mBAAmB,KAAK,IAAI,GAAG,eAAe,WAAW;AAE/D,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;
|
|
1
|
+
{"version":3,"sources":["../../../../src/modules/ia-credits/hooks/ia-credits.hook.ts"],"sourcesContent":["'use client';\n\nimport { useMemo } from 'react';\nimport { useQuery } from '@tanstack/react-query';\nimport { apiFetch } from '../../../infra/http/api-fetch';\nimport type { PaginatedSuccessResult } from '../../../infra/api/types';\nimport type { IaCreditOperation, IaCreditsSummary } from '../types';\nimport { useActiveSubscription } from '../../subscriptions/hooks/find-active-subscription.hook';\nimport { useAuthQueryKey } from '../../../hooks/useAuthQueryKey';\n\nfunction calculateSummary(operations: IaCreditOperation[]): IaCreditsSummary {\n const today = new Date();\n const todayDate = new Date(today.getFullYear(), today.getMonth(), today.getDate());\n\n const adds = operations.filter((op) => op.operation === 'add');\n const subtracts = operations.filter((op) => op.operation === 'subtract');\n\n let totalCredits = 0;\n let usedCredits = 0;\n let nextExpirationInDays: number | null = null;\n let nextExpiringCredits: number | null = null;\n\n for (const add of adds) {\n const expirationRaw = add.expiration_time;\n if (!expirationRaw) continue;\n\n const expiration = new Date(expirationRaw);\n const expirationDate = new Date(\n expiration.getFullYear(),\n expiration.getMonth(),\n expiration.getDate()\n );\n\n const expiredByDate = expirationDate.getTime() < todayDate.getTime();\n const hasExpired = add.has_expired || expiredByDate;\n\n if (hasExpired) continue;\n\n const addedCredits = add.operation_value;\n\n const consumedForAdd = subtracts\n .filter((sub) => String(sub.consumed_from_add_id) === String(add.id))\n .reduce((sum, sub) => sum + sub.operation_value, 0);\n\n const remainingForAdd = Math.max(0, addedCredits - consumedForAdd);\n\n totalCredits += addedCredits;\n usedCredits += consumedForAdd;\n\n const diffMs = expirationDate.getTime() - todayDate.getTime();\n const days = Math.max(0, Math.ceil(diffMs / (1000 * 60 * 60 * 24)));\n\n if (remainingForAdd > 0) {\n if (nextExpirationInDays === null || days < nextExpirationInDays) {\n nextExpirationInDays = days;\n nextExpiringCredits = remainingForAdd;\n }\n }\n }\n\n const availableCredits = Math.max(0, totalCredits - usedCredits);\n\n return {\n totalCredits,\n usedCredits,\n availableCredits,\n nextExpiringCredits,\n nextExpirationInDays,\n };\n}\n\nexport interface UseIaCreditsOptions {\n refetchInterval?: number | false;\n}\n\nexport function useIaCredits(options: UseIaCreditsOptions = {}) {\n const { data: subscriptionData, isPending: isSubscriptionLoading } = useActiveSubscription();\n const subscription = subscriptionData?.data?.[0] ?? null;\n const subscriptionId = subscription?.id;\n const queryKey = useAuthQueryKey(['ia-credits', subscriptionId]);\n\n const query = useQuery({\n queryKey,\n queryFn: ({ signal }) =>\n apiFetch<PaginatedSuccessResult<IaCreditOperation>>(\n `/api/subscriptions/${subscriptionId}/ia-credits`,\n { signal }\n ),\n enabled: subscriptionId != null,\n refetchInterval: options.refetchInterval ?? false,\n });\n\n const operations = query.data?.data ?? [];\n\n // eslint-disable-next-line react-hooks/exhaustive-deps\n const summary = useMemo(() => calculateSummary(operations), [operations]);\n\n return {\n subscription,\n operations,\n summary,\n isLoading: isSubscriptionLoading || query.isPending,\n isSubscriptionLoading,\n isCreditsLoading: query.isPending,\n isError: query.isError,\n error: query.error,\n };\n}\n"],"mappings":";AAEA,SAAS,eAAe;AACxB,SAAS,gBAAgB;AACzB,SAAS,gBAAgB;AAGzB,SAAS,6BAA6B;AACtC,SAAS,uBAAuB;AAEhC,SAAS,iBAAiB,YAAmD;AAC3E,QAAM,QAAQ,oBAAI,KAAK;AACvB,QAAM,YAAY,IAAI,KAAK,MAAM,YAAY,GAAG,MAAM,SAAS,GAAG,MAAM,QAAQ,CAAC;AAEjF,QAAM,OAAO,WAAW,OAAO,CAAC,OAAO,GAAG,cAAc,KAAK;AAC7D,QAAM,YAAY,WAAW,OAAO,CAAC,OAAO,GAAG,cAAc,UAAU;AAEvE,MAAI,eAAe;AACnB,MAAI,cAAc;AAClB,MAAI,uBAAsC;AAC1C,MAAI,sBAAqC;AAEzC,aAAW,OAAO,MAAM;AACtB,UAAM,gBAAgB,IAAI;AAC1B,QAAI,CAAC,cAAe;AAEpB,UAAM,aAAa,IAAI,KAAK,aAAa;AACzC,UAAM,iBAAiB,IAAI;AAAA,MACzB,WAAW,YAAY;AAAA,MACvB,WAAW,SAAS;AAAA,MACpB,WAAW,QAAQ;AAAA,IACrB;AAEA,UAAM,gBAAgB,eAAe,QAAQ,IAAI,UAAU,QAAQ;AACnE,UAAM,aAAa,IAAI,eAAe;AAEtC,QAAI,WAAY;AAEhB,UAAM,eAAe,IAAI;AAEzB,UAAM,iBAAiB,UACpB,OAAO,CAAC,QAAQ,OAAO,IAAI,oBAAoB,MAAM,OAAO,IAAI,EAAE,CAAC,EACnE,OAAO,CAAC,KAAK,QAAQ,MAAM,IAAI,iBAAiB,CAAC;AAEpD,UAAM,kBAAkB,KAAK,IAAI,GAAG,eAAe,cAAc;AAEjE,oBAAgB;AAChB,mBAAe;AAEf,UAAM,SAAS,eAAe,QAAQ,IAAI,UAAU,QAAQ;AAC5D,UAAM,OAAO,KAAK,IAAI,GAAG,KAAK,KAAK,UAAU,MAAO,KAAK,KAAK,GAAG,CAAC;AAElE,QAAI,kBAAkB,GAAG;AACvB,UAAI,yBAAyB,QAAQ,OAAO,sBAAsB;AAChE,+BAAuB;AACvB,8BAAsB;AAAA,MACxB;AAAA,IACF;AAAA,EACF;AAEA,QAAM,mBAAmB,KAAK,IAAI,GAAG,eAAe,WAAW;AAE/D,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;AAMO,SAAS,aAAa,UAA+B,CAAC,GAAG;AAC9D,QAAM,EAAE,MAAM,kBAAkB,WAAW,sBAAsB,IAAI,sBAAsB;AAC3F,QAAM,eAAe,kBAAkB,OAAO,CAAC,KAAK;AACpD,QAAM,iBAAiB,cAAc;AACrC,QAAM,WAAW,gBAAgB,CAAC,cAAc,cAAc,CAAC;AAE/D,QAAM,QAAQ,SAAS;AAAA,IACrB;AAAA,IACA,SAAS,CAAC,EAAE,OAAO,MACjB;AAAA,MACE,sBAAsB,cAAc;AAAA,MACpC,EAAE,OAAO;AAAA,IACX;AAAA,IACF,SAAS,kBAAkB;AAAA,IAC3B,iBAAiB,QAAQ,mBAAmB;AAAA,EAC9C,CAAC;AAED,QAAM,aAAa,MAAM,MAAM,QAAQ,CAAC;AAGxC,QAAM,UAAU,QAAQ,MAAM,iBAAiB,UAAU,GAAG,CAAC,UAAU,CAAC;AAExE,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA,WAAW,yBAAyB,MAAM;AAAA,IAC1C;AAAA,IACA,kBAAkB,MAAM;AAAA,IACxB,SAAS,MAAM;AAAA,IACf,OAAO,MAAM;AAAA,EACf;AACF;","names":[]}
|
package/package.json
CHANGED
|
@@ -147,8 +147,8 @@ export function PaymentInfoCard({
|
|
|
147
147
|
</div>
|
|
148
148
|
|
|
149
149
|
<div
|
|
150
|
-
className={`flex flex-col gap-2 px-4
|
|
151
|
-
isExpanded ? 'max-h-[
|
|
150
|
+
className={`flex flex-col gap-2 px-4 transition-all duration-300 ease-in-out ${
|
|
151
|
+
isExpanded ? 'max-h-[167px] overflow-y-auto pb-4 opacity-100' : 'max-h-0 overflow-hidden pb-0 opacity-0'
|
|
152
152
|
}`}
|
|
153
153
|
>
|
|
154
154
|
{displayedCards.map((card) => (
|
|
@@ -69,7 +69,11 @@ function calculateSummary(operations: IaCreditOperation[]): IaCreditsSummary {
|
|
|
69
69
|
};
|
|
70
70
|
}
|
|
71
71
|
|
|
72
|
-
export
|
|
72
|
+
export interface UseIaCreditsOptions {
|
|
73
|
+
refetchInterval?: number | false;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
export function useIaCredits(options: UseIaCreditsOptions = {}) {
|
|
73
77
|
const { data: subscriptionData, isPending: isSubscriptionLoading } = useActiveSubscription();
|
|
74
78
|
const subscription = subscriptionData?.data?.[0] ?? null;
|
|
75
79
|
const subscriptionId = subscription?.id;
|
|
@@ -83,6 +87,7 @@ export function useIaCredits() {
|
|
|
83
87
|
{ signal }
|
|
84
88
|
),
|
|
85
89
|
enabled: subscriptionId != null,
|
|
90
|
+
refetchInterval: options.refetchInterval ?? false,
|
|
86
91
|
});
|
|
87
92
|
|
|
88
93
|
const operations = query.data?.data ?? [];
|