Graphical PDS migrator for AT Protocol

remove alpha, fix mobile button

Changed files
+45 -34
islands
routes
+6 -15
README.md
···
Airport is a web application built with Fresh and Deno that helps users safely migrate and backup their Bluesky PDS data. It provides a user-friendly interface for managing your AT Protocol data.
-
⚠️ **Alpha Status**: Airport is currently in alpha. Please use migration tools at your own risk and avoid using with main accounts during this phase.
-
## Features
- PDS migration between servers
···
- User-friendly interface
- Coming soon: PLC Key retrieval, data backup
-
## Technology Stack
+
## Tech Stack
-
- [Fresh](https://fresh.deno.dev/) - The next-gen web framework
-
- [Deno](https://deno.com/) - A modern runtime for JavaScript and TypeScript
-
- [Tailwind CSS](https://tailwindcss.com/) - For styling
-
- AT Protocol Integration
+
- [Fresh](https://fresh.deno.dev/) - Web Framework
+
- [Deno](https://deno.com/) - Runtime
+
- [Tailwind](https://tailwindcss.com/) - Styling
-
## Getting Started
+
## Development
-
### Prerequisites
-
-
Make sure to install Deno:
+
Make sure you have Deno installed:
https://docs.deno.com/runtime/getting_started/installation
-
-
### Development
Start the project in development mode:
```
deno task dev
```
-
-
This will watch the project directory and restart as necessary.
## About
+35
islands/LoginButton.tsx
···
+
import { useEffect, useState } from "preact/hooks";
+
import { Button } from "../components/Button.tsx";
+
+
export default function LoginButton() {
+
const [isMobile, setIsMobile] = useState(true); // Default to mobile for SSR
+
+
useEffect(() => {
+
const checkMobile = () => {
+
setIsMobile(globalThis.innerWidth < 640);
+
};
+
+
// Check on mount
+
checkMobile();
+
+
// Listen for resize events
+
globalThis.addEventListener('resize', checkMobile);
+
return () => globalThis.removeEventListener('resize', checkMobile);
+
}, []);
+
+
return (
+
<div class="mt-6 sm:mt-8 text-center w-fit mx-auto">
+
<Button
+
href={isMobile ? undefined : "/login"}
+
color="blue"
+
label={isMobile ? "MOBILE NOT SUPPORTED" : "GET STARTED"}
+
className={isMobile ? "opacity-50 cursor-not-allowed" : "opacity-100 cursor-pointer"}
+
onClick={(e: MouseEvent) => {
+
if (isMobile) {
+
e.preventDefault();
+
}
+
}}
+
/>
+
</div>
+
);
+
}
+2 -2
islands/MigrationSetup.tsx
···
// Get PDS URL from the current service
const pdsResponse = await fetch(`/api/resolve-pds?did=${userData.did}`);
const pdsData = await pdsResponse.json();
-
+
setPassport({
did: userData.did,
handle: userData.handle,
···
<div class="text-center mb-4 mt-6">
<h3 class="text-2xl font-bold text-red-600 mb-2 tracking-wide">Final Boarding Call</h3>
<p class="text-gray-700 dark:text-gray-300 mb-2 text-base">
-
<span class="font-semibold text-red-500">Warning:</span> This migration process can be <strong>irreversible</strong>.<br />Airport is in <strong>alpha</strong> currently, and we don't recommend it for main accounts. Migrate at your own risk. We reccomend backing up your data before proceeding.
+
<span class="font-semibold text-red-500">Warning:</span> This migration is <strong>irreversible</strong> if coming from Bluesky servers.<br />Bluesky does not recommend it for main accounts. Migrate at your own risk. We reccomend backing up your data before proceeding.
</p>
<p class="text-gray-700 dark:text-gray-300 mb-4 text-base">
Please type <span class="font-mono font-bold text-blue-600">MIGRATE</span> below to confirm and proceed.
+2 -17
routes/index.tsx
···
import Ticket from "../islands/Ticket.tsx";
import AirportSign from "../components/AirportSign.tsx";
import SocialLinks from "../islands/SocialLinks.tsx";
-
import { Button } from "../components/Button.tsx";
+
import LoginButton from "../islands/LoginButton.tsx";
export default function Home() {
return (
···
<p class="font-mono text-lg sm:text-xl font-bold mb-4 sm:mb-6 mt-0 text-center text-gray-600 dark:text-gray-300">
Your terminal for seamless AT Protocol PDS migration and backup.
</p>
-
<p class="font-mono mb-4 sm:mb-6 mt-0 text-center text-gray-600 dark:text-gray-300">
-
Airport is in <strong>alpha</strong> currently, and we don't recommend it for main accounts. <br/> Please use its migration tools at your own risk.
-
</p>
<Ticket />
-
<div class="mt-6 sm:mt-8 text-center w-fit mx-auto">
-
<Button
-
href="/login"
-
color="blue"
-
label="MOBILE NOT SUPPORTED"
-
className="opacity-50 cursor-not-allowed sm:opacity-100 sm:cursor-pointer"
-
onClick={(e: MouseEvent) => {
-
if (globalThis.innerWidth < 640) {
-
e.preventDefault();
-
}
-
}}
-
/>
-
</div>
+
<LoginButton />
<p class="font-mono text-lg sm:text-xl mb-4 mt-4 sm:mb-6 text-center text-gray-600 dark:text-gray-300">
Airport is made with love by <a class="text-blue-500 hover:underline" href="https://bsky.app/profile/knotbin.com">Roscoe</a> for <a class="text-blue-500 hover:underline" href="https://sprk.so">Spark</a>, a new short-video platform for AT Protocol.
</p>