Files
digicraft-fe/components/CreditButton.tsx
Fahri Can Seçer 6e3bee17ef
Some checks failed
Deploy Frontend / deploy (push) Has been cancelled
main
2026-02-05 01:34:13 +03:00

87 lines
2.6 KiB
TypeScript

import React, { useEffect, useState } from 'react';
type ActionType = 'GENERATE_MASTER' | 'GENERATE_VARIANT' | 'GENERATE_MOCKUP' | 'GENERATE_PROMPT';
const DEFAULT_CREDITS: Record<ActionType, number> = {
GENERATE_PROMPT: 1,
GENERATE_MASTER: 10,
GENERATE_VARIANT: 5,
GENERATE_MOCKUP: 2
};
// Global pricing cache to avoid fetching every button render
let pricingCache: any = null;
interface CreditButtonProps {
action?: ActionType;
cost?: number; // Direct cost override (for backward compatibility)
onClick: () => void;
disabled?: boolean;
className?: string; // Additional classes for styling
children?: React.ReactNode; // Custom text if needed (e.g. "Generate")
hideCost?: boolean;
}
export const CreditButton: React.FC<CreditButtonProps> = ({
action,
cost: directCost,
onClick,
disabled = false,
className = "",
children,
hideCost = false
}) => {
const [price, setPrice] = useState<number>(directCost ?? (action ? DEFAULT_CREDITS[action] : 0));
useEffect(() => {
// If directCost is provided, use it directly
if (directCost !== undefined) {
setPrice(directCost);
return;
}
// If no action, skip fetching
if (!action) return;
const fetchPrices = async () => {
// Use cache if exists
if (pricingCache && pricingCache[`PRICE_${action}`]) {
setPrice(Number(pricingCache[`PRICE_${action}`]));
return;
}
try {
const res = await fetch('http://localhost:3001/api/config/prices');
if (res.ok) {
const data = await res.json();
pricingCache = data;
const dynamicPrice = data[`PRICE_${action}`];
if (dynamicPrice) {
setPrice(Number(dynamicPrice));
}
}
} catch (err) {
console.warn("Failed to fetch dynamic prices", err);
}
};
fetchPrices();
}, [action, directCost]);
return (
<button
onClick={onClick}
disabled={disabled}
className={`flex items-center justify-center gap-2 group ${className}`}
>
{children || <span>Generate</span>}
{!hideCost && (
<span className="bg-white/20 px-2 py-0.5 rounded text-xs font-mono font-bold opacity-90 group-hover:bg-white/30 transition-colors">
{price} 🪙
</span>
)}
</button>
);
};