import { useState, useEffect } from 'react' import { useParams, useNavigate, Link } from 'react-router-dom' import { motion } from 'framer-motion' import { format } from 'date-fns' import toast from 'react-hot-toast' import { ArrowLeftIcon, ClipboardIcon, ArrowTopRightOnSquareIcon, PencilIcon, ArchiveBoxIcon, ChartBarIcon, CheckIcon, } from '@heroicons/react/24/outline' import { paywallsApi } from '../../services/api' export default function PaywallDetail() { const { id } = useParams() const navigate = useNavigate() const [paywall, setPaywall] = useState(null) const [stats, setStats] = useState(null) const [embedCode, setEmbedCode] = useState(null) const [isLoading, setIsLoading] = useState(true) const [isSaving, setIsSaving] = useState(false) const [activeTab, setActiveTab] = useState('overview') const [editData, setEditData] = useState({}) useEffect(() => { fetchPaywall() fetchEmbed() }, [id]) const fetchPaywall = async () => { try { const response = await paywallsApi.get(id) setPaywall(response.data.paywall) setStats(response.data.stats) setEditData({ title: response.data.paywall.title || '', description: response.data.paywall.description || '', priceSats: response.data.paywall.priceSats || 100, originalUrl: response.data.paywall.originalUrl || '', accessExpirySeconds: response.data.paywall.accessExpirySeconds || null, maxDevices: response.data.paywall.maxDevices || 3, allowEmbed: response.data.paywall.allowEmbed ?? true, customSuccessMessage: response.data.paywall.customSuccessMessage || '', slug: response.data.paywall.slug || '', }) } catch (error) { console.error('Error fetching paywall:', error) toast.error('Failed to load paywall') } finally { setIsLoading(false) } } const handleEditChange = (e) => { const { name, value, type, checked } = e.target setEditData(prev => ({ ...prev, [name]: type === 'checkbox' ? checked : (type === 'number' ? (value === '' ? null : parseInt(value)) : value) })) } const handleSaveSettings = async (e) => { e.preventDefault() setIsSaving(true) try { const updateData = { ...editData, priceSats: parseInt(editData.priceSats), accessExpirySeconds: editData.accessExpirySeconds ? parseInt(editData.accessExpirySeconds) : null, maxDevices: parseInt(editData.maxDevices), } const response = await paywallsApi.update(id, updateData) setPaywall(response.data.paywall) toast.success('Paywall updated successfully!') } catch (error) { console.error('Error updating paywall:', error) toast.error(error.response?.data?.error || 'Failed to update paywall') } finally { setIsSaving(false) } } const fetchEmbed = async () => { try { const response = await paywallsApi.getEmbed(id) setEmbedCode(response.data) } catch (error) { console.error('Error fetching embed:', error) } } const handleCopy = (text, label) => { navigator.clipboard.writeText(text) toast.success(`${label} copied!`) } const handleArchive = async () => { try { await paywallsApi.archive(id) toast.success('Paywall archived') navigate('/dashboard/paywalls') } catch (error) { toast.error('Failed to archive paywall') } } if (isLoading) { return (
{paywall.description}
Price
⚡ {paywall.priceSats.toLocaleString()}
Total Sales
{stats?.salesCount || 0}
Total Revenue
⚡ {(stats?.totalRevenue || 0).toLocaleString()}
Status
{paywall.status}
{paywall.description}
Add this code to your website to embed the paywall directly.
{embedCode.iframe}
Add a button that opens a checkout modal when clicked.
{embedCode.button}
Share this link directly or use it in your own custom integration.