All files / laravel-saas/resources/js/Pages/Billing Subscribe.tsx

0% Statements 0/95
100% Branches 1/1
100% Functions 1/1
0% Lines 0/95

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112                                                                                                                                                                                                                               
import React from 'react';
import { Head, router } from '@inertiajs/react';
import AuthenticatedLayout from '@/Components/Layout/AuthenticatedLayout';
import { SubscribePageProps } from '@/types';
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/Components/ui/card';
import StripeProvider from '@/Components/billing/StripeProvider';
import PaymentForm from '@/Components/billing/PaymentForm';
import { ArrowLeft } from 'lucide-react';
import { Button } from '@/Components/ui/button';
 
export default function Subscribe({ price, product, intent }: SubscribePageProps) {
    const handleSuccess = () => {
        router.visit('/billing', {
            preserveScroll: true,
        });
    };
 
    return (
        <AuthenticatedLayout>
            <Head title={`Subscribe to ${product.name}`} />
 
            <div className="mx-auto max-w-2xl px-4 sm:px-6 lg:px-8">
                <div className="mb-8">
                    <Button
                        variant="ghost"
                        onClick={() => router.visit('/billing/plans')}
                        className="mb-4"
                    >
                        <ArrowLeft className="mr-2 h-4 w-4" />
                        Back to plans
                    </Button>
                    
                    <h1 className="text-3xl font-bold">Complete Your Subscription</h1>
                    <p className="mt-2 text-gray-600">
                        You're subscribing to {product.name} at ${(price.unit_amount / 100).toFixed(2)}/{price.interval}
                    </p>
                </div>
 
                <div className="grid gap-6 lg:grid-cols-3">
                    <div className="lg:col-span-2">
                        <Card>
                            <CardHeader>
                                <CardTitle>Payment Details</CardTitle>
                                <CardDescription>
                                    Enter your payment information to complete your subscription.
                                </CardDescription>
                            </CardHeader>
                            <CardContent>
                                <StripeProvider
                                    options={{
                                        mode: 'subscription',
                                        amount: price.unit_amount,
                                        currency: price.currency,
                                        setupFutureUsage: 'off_session',
                                        paymentMethodCreation: 'manual',
                                        clientSecret: intent.client_secret,
                                    }}
                                >
                                    <PaymentForm
                                        returnUrl={route('billing.index')}
                                        onSuccess={handleSuccess}
                                        submitText="Subscribe"
                                    />
                                </StripeProvider>
                            </CardContent>
                        </Card>
                    </div>
 
                    <div>
                        <Card>
                            <CardHeader>
                                <CardTitle>Order Summary</CardTitle>
                            </CardHeader>
                            <CardContent>
                                <div className="space-y-3">
                                    <div>
                                        <h4 className="font-semibold">{product.name}</h4>
                                        <p className="text-sm text-gray-600">{product.description}</p>
                                    </div>
                                    
                                    <div className="border-t pt-3">
                                        <div className="flex justify-between">
                                            <span>Subtotal</span>
                                            <span>${(price.unit_amount / 100).toFixed(2)}</span>
                                        </div>
                                        {price.trial_period_days && (
                                            <p className="mt-2 text-sm text-green-600">
                                                Includes {price.trial_period_days} day free trial
                                            </p>
                                        )}
                                    </div>
                                    
                                    <div className="border-t pt-3">
                                        <div className="flex justify-between font-semibold">
                                            <span>Total</span>
                                            <span>${(price.unit_amount / 100).toFixed(2)}/{price.interval}</span>
                                        </div>
                                    </div>
                                </div>
 
                                <div className="mt-6 text-xs text-gray-600">
                                    <p>By subscribing, you agree to our terms of service and privacy policy.</p>
                                    <p className="mt-2">You can cancel your subscription at any time.</p>
                                </div>
                            </CardContent>
                        </Card>
                    </div>
                </div>
            </div>
        </AuthenticatedLayout>
    );
}