import { useState, useEffect } from 'react';
import { Button } from "/components/ui/button";
import { Input } from "/components/ui/input";
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from
"/components/ui/card";
import { Label } from "/components/ui/label";
interface TrackingData {
id: string;
linkName: string;
createdAt: Date;
clicks: ClickData[];
}
interface ClickData {
id: string;
timestamp: Date;
latitude: number | null;
longitude: number | null;
city: string;
country: string;
device: string;
ip: string;
}
export default function TrackingLinkGenerator() {
const [linkName, setLinkName] = useState('');
const [generatedLink, setGeneratedLink] = useState('');
const [trackingLinks, setTrackingLinks] = useState<TrackingData[]>([]);
const [selectedLink, setSelectedLink] = useState<TrackingData | null>(null);
useEffect(() => {
// Load existing tracking links from localStorage
const savedLinks = [Link]('trackingLinks');
if (savedLinks) {
setTrackingLinks([Link](savedLinks));
}
}, []);
const generateTrackingLink = () => {
if (![Link]()) return;
const newLink: TrackingData = {
id: [Link]().toString(36).substr(2, 9),
linkName: [Link](),
createdAt: new Date(),
clicks: []
};
const updatedLinks = [...trackingLinks, newLink];
setTrackingLinks(updatedLinks);
[Link]('trackingLinks', [Link](updatedLinks));
const baseUrl = [Link];
const trackingUrl = `${baseUrl}/track/${[Link]}`;
setGeneratedLink(trackingUrl);
setLinkName('');
};
const copyToClipboard = async (text: string) => {
try {
await [Link](text);
alert('Link copied to clipboard!');
} catch (err) {
[Link]('Failed to copy: ', err);
}
};
const simulateClick = (linkId: string) => {
// Simulate a click with mock location data
const links = [...trackingLinks];
const linkIndex = [Link](link => [Link] === linkId);
if (linkIndex !== -1) {
const mockClick: ClickData = {
id: [Link]().toString(36).substr(2, 9),
timestamp: new Date(),
latitude: 37.7749 + ([Link]() - 0.5) * 0.1,
longitude: -122.4194 + ([Link]() - 0.5) * 0.1,
city: 'San Francisco',
country: 'United States',
device: [Link],
ip: `192.168.${[Link]([Link]() * 255)}.${[Link]([Link]()
* 255)}`
};
links[linkIndex].[Link](mockClick);
setTrackingLinks(links);
[Link]('trackingLinks', [Link](links));
if (selectedLink?.id === linkId) {
setSelectedLink(links[linkIndex]);
}
}
};
return (
<div className="min-h-screen bg-background p-4 md:p-8">
<div className="max-w-6xl mx-auto">
<header className="text-center mb-8">
<h1 className="text-3xl md:text-4xl font-bold text-foreground mb-2">
Location Tracking Link Generator
</h1>
<p className="text-muted-foreground">
Create tracking links that capture location data when opened
</p>
</header>
<div className="grid grid-cols-1 lg:grid-cols-2 gap-8">
{/* Link Generator Section */}
<Card className="lg:col-span-1">
<CardHeader>
<CardTitle>Create Tracking Link</CardTitle>
<CardDescription>
Generate a unique link that will capture location data when clicked
</CardDescription>
</CardHeader>
<CardContent className="space-y-4">
<div className="space-y-2">
<Label htmlFor="linkName">Link Name</Label>
<Input
id="linkName"
placeholder="Enter a name for your tracking link"
value={linkName}
onChange={(e) => setLinkName([Link])}
/>
</div>
<Button
onClick={generateTrackingLink}
disabled={![Link]()}
className="w-full"
>
Generate Tracking Link
</Button>
{generatedLink && (
<div className="space-y-2">
<Label>Generated Tracking Link</Label>
<div className="flex gap-2">
<Input
value={generatedLink}
readOnly
className="flex-1"
/>
<Button
variant="secondary"
onClick={() => copyToClipboard(generatedLink)}
>
Copy
</Button>
</div>
<p className="text-sm text-muted-foreground">
Share this link to track when and where it's opened
</p>
</div>
)}
</CardContent>
</Card>
{/* Tracking Dashboard Section */}
<Card className="lg:col-span-1">
<CardHeader>
<CardTitle>Tracking Dashboard</CardTitle>
<CardDescription>
Monitor your tracking links and view location data
</CardDescription>
</CardHeader>
<CardContent>
{[Link] === 0 ? (
<div className="text-center py-8">
<p className="text-muted-foreground">
No tracking links created yet. Generate one to get started!
</p>
</div>
) : (
<div className="space-y-4">
<div className="space-y-2">
<Label>Your Tracking Links</Label>
<div className="space-y-2 max-h-40 overflow-y-auto">
{[Link]((link) => (
<div
key={[Link]}
className="flex items-center justify-between p-3 border
rounded-lg hover:bg-muted cursor-pointer"
onClick={() => setSelectedLink(link)}
>
<div>
<p className="font-medium">{[Link]}</p>
<p className="text-sm text-muted-foreground">
{[Link]} clicks
</p>
</div>
<Button
variant="outline"
size="sm"
onClick={(e) => {
[Link]();
simulateClick([Link]);
}}
>
Simulate Click
</Button>
</div>
))}
</div>
</div>
{selectedLink && (
<div className="space-y-3">
<Label>Tracking Data for: {[Link]}</Label>
<div className="border rounded-lg p-3">
{[Link] === 0 ? (
<p className="text-muted-foreground text-center py-4">
No clicks recorded yet
</p>
) : (
<div className="space-y-3">
{[Link]((click) => (
<div key={[Link]} className="border-b pb-3
last:border-b-0">
<div className="grid grid-cols-2 gap-2 text-sm">
<div>
<span className="font-medium">Time: </span>
{[Link]()}
</div>
<div>
<span className="font-medium">Location: </span>
{[Link] && [Link]
? `${[Link](4)}, $
{[Link](4)}`
: 'Not available'
}
</div>
<div>
<span className="font-medium">City: </span>
{[Link]}
</div>
<div>
<span className="font-medium">Country: </span>
{[Link]}
</div>
<div className="col-span-2">
<span className="font-medium">IP: </span>
{[Link]}
</div>
</div>
</div>
))}
</div>
)}
</div>
</div>
)}
</div>
)}
</CardContent>
</Card>
</div>
{/* Instructions */}
<Card className="mt-8">
<CardHeader>
<CardTitle>How It Works</CardTitle>
</CardHeader>
<CardContent>
<div className="grid grid-cols-1 md:grid-cols-3 gap-4">
<div className="text-center">
<div className="w-12 h-12 bg-primary rounded-full flex items-center
justify-center mx-auto mb-3">
<span className="text-white font-bold">1</span>
</div>
<h3 className="font-semibold mb-2">Create Link</h3>
<p className="text-sm text-muted-foreground">
Generate a unique tracking link with a descriptive name
</p>
</div>
<div className="text-center">
<div className="w-12 h-12 bg-primary rounded-full flex items-center
justify-center mx-auto mb-3">
<span className="text-white font-bold">2</span>
</div>
<h3 className="font-semibold mb-2">Share Link</h3>
<p className="text-sm text-muted-foreground">
Send the link to others via email, messaging, or social media
</p>
</div>
<div className="text-center">
<div className="w-12 h-12 bg-primary rounded-full flex items-center
justify-center mx-auto mb-3">
<span className="text-white font-bold">3</span>
</div>
<h3 className="font-semibold mb-2">Track Results</h3>
<p className="text-sm text-muted-foreground">
Monitor when and where your links are opened in real-time
</p>
</div>
</div>
</CardContent>
</Card>
</div>
</div>
);
}