Heim >Web-Frontend >js-Tutorial >Erstellen eines benutzerdefinierten Schedulers mit React und Supabase
Planung ist eines der entscheidenden Merkmale moderner Anwendungen. Es kann uns ermöglichen, regelmäßige Aufgaben auszuführen, die automatisiert werden können. Aufgaben wie das Versenden von Erinnerungen, das Planen von Beiträgen, das Aktualisieren von Daten oder das Automatisieren von Arbeitsabläufen.
In diesem Artikel werden wir einen Planer für die Veröffentlichung von Artikeln auf dev.to erstellen. Obwohl dev.to über Planungsfunktionen verfügt, werden wir sie auf unsere Weise implementieren, die zum Erstellen jeder Art von Planungsanwendung verwendet werden kann.
Also, fangen wir an.
Wir werden den folgenden Tech-Stack verwenden:
Das wird ausreichen, um problemlos eine Zeitplaneranwendung zu erstellen.
Lassen Sie uns besprechen, wie die Anwendung funktioniert, wodurch es recht einfach wird, den Ablauf der Anwendung zu verstehen. Hier ist der Ablauf nacheinander:
Das Gebäude-Frontend ist in letzter Zeit ruhig geworden, da viel generative KI zum Einsatz kommt. Eine dieser KIs, die wir verwenden werden, ist Bolt.new. Warum Bolt.new? Es kann vollständige React-Anwendungen mit Abhängigkeiten und allen Konfigurationen wie tailwindcss generieren. Sie können Artikel direkt mit StackBlitz bearbeiten und die Anwendung auch bereitstellen. Bei Bedarf können Sie den Code herunterladen, um ihn lokal auszuführen. Der Bonuspunkt ist, dass es sich recht gut in Supabase integrieren lässt, sodass Sie mit der Supbase-Integration eine funktionierende React-Anwendung generieren können.
Ich habe es verwendet, um die Front zu generieren. Hier sind alle Seiten.
Dadurch wird die Seite für die Anzeige von Komponenten und die Bereitstellung der Zielseite verwaltet.
function App() { const [posts, setPosts] = useState<ScheduledPost[]>([]); const handleSchedulePost = async (data: CreatePostData) => { // In a real app, this would make an API call to your edge function const newPost: ScheduledPost = { content: data.content, scheduled_time: data.scheduledTime, status: 'pending', title: data.title, tags: data.tags }; const { error } = await supabase .from('scheduled_posts') .insert(newPost) if (error){ alert(`Erorr: ${error}`) return } // setPosts((prev) => [...prev, newPost]); }; const fetchScheduedPost = async () => { const { data, error } = await supabase .from('scheduled_posts') .select() if(error){ alert(`Erorr Fetching Data: ${error}`) return } setPosts(data) } useEffect(() => { fetchScheduedPost() },[]) return ( <div className="min-h-screen bg-gray-50"> <header className="bg-white shadow-sm"> <div className="max-w-4xl mx-auto px-4 py-4"> <div className="flex items-center gap-2"> <Newspaper className="h-8 w-8 text-blue-500" /> <h1 className="text-xl font-bold text-gray-900">Dev.to Post Scheduler</h1> </div> </div> </header> <main className="max-w-4xl mx-auto px-4 py-8"> <div className="grid gap-8 md:grid-cols-2"> <div> <h2 className="text-xl font-semibold text-gray-800 mb-4">Schedule New Post</h2> <PostForm onSubmit={handleSchedulePost} /> </div> <div> <ScheduledPosts posts={posts} /> </div> </div> </main> </div> ); } export default App;
Hier werden die geplanten Artikel angezeigt.
const StatusIcon = ({ status }: { status: ScheduledPost['status'] }) => { switch (status) { case 'posted': return <CheckCircle className="h-5 w-5 text-green-500" />; case 'failed': return <XCircle className="h-5 w-5 text-red-500" />; default: return <Clock3 className="h-5 w-5 text-yellow-500" />; } }; export function ScheduledPosts({ posts }: ScheduledPostsProps) { return ( <div className="space-y-4"> <h2 className="text-xl font-semibold text-gray-800">Scheduled Posts</h2> {posts.length === 0 ? ( <p className="text-gray-500 text-center py-8">No scheduled posts yet</p> ) : ( <div className="space-y-4"> {posts.map((post, index) => ( <div key={index} className="bg-white p-4 rounded-lg shadow-md border border-gray-100" > <div className="flex items-start justify-between"> <div className="flex-1"> <p className="text-gray-800 mb-2">{post.title}</p> <div className="flex items-center gap-4 text-sm text-gray-500"> <div className="flex items-center gap-1"> <Calendar className="h-4 w-4" /> {new Date(post.scheduled_time).toLocaleDateString()} </div> <div className="flex items-center gap-1"> <Clock className="h-4 w-4" /> {new Date(post.scheduled_time).toLocaleTimeString()} </div> </div> </div> <StatusIcon status={post.status} /> </div> </div> ))} </div> )} </div> ); }
Hiermit wird das Formular verwaltet, in dem der Benutzer Informationen zum Artikel angeben kann.
function App() { const [posts, setPosts] = useState<ScheduledPost[]>([]); const handleSchedulePost = async (data: CreatePostData) => { // In a real app, this would make an API call to your edge function const newPost: ScheduledPost = { content: data.content, scheduled_time: data.scheduledTime, status: 'pending', title: data.title, tags: data.tags }; const { error } = await supabase .from('scheduled_posts') .insert(newPost) if (error){ alert(`Erorr: ${error}`) return } // setPosts((prev) => [...prev, newPost]); }; const fetchScheduedPost = async () => { const { data, error } = await supabase .from('scheduled_posts') .select() if(error){ alert(`Erorr Fetching Data: ${error}`) return } setPosts(data) } useEffect(() => { fetchScheduedPost() },[]) return ( <div className="min-h-screen bg-gray-50"> <header className="bg-white shadow-sm"> <div className="max-w-4xl mx-auto px-4 py-4"> <div className="flex items-center gap-2"> <Newspaper className="h-8 w-8 text-blue-500" /> <h1 className="text-xl font-bold text-gray-900">Dev.to Post Scheduler</h1> </div> </div> </header> <main className="max-w-4xl mx-auto px-4 py-8"> <div className="grid gap-8 md:grid-cols-2"> <div> <h2 className="text-xl font-semibold text-gray-800 mb-4">Schedule New Post</h2> <PostForm onSubmit={handleSchedulePost} /> </div> <div> <ScheduledPosts posts={posts} /> </div> </div> </main> </div> ); } export default App;
Edge-Funktionen sind serverseitige TypeScript-Funktionen, die global am Edge verteilt werden – in der Nähe Ihrer Benutzer. Sie können zum Abhören von Webhooks oder zur Integration Ihres Supabase-Projekts mit Drittanbietern wie Stripe verwendet werden. Kantenfunktionen werden mit Deno entwickelt.
Um die Edge-Funktion lokal ausführen und bereitstellen zu können, benötigen Sie Folgendes:
Nach der Installation können Sie also Ihr Frontend-Codeverzeichnis oder ein anderes verwenden, um die Supabase Edge-Funktion zu erstellen.
Führen Sie den folgenden Befehl aus, um ein Supabase-Projekt zu starten:
const StatusIcon = ({ status }: { status: ScheduledPost['status'] }) => { switch (status) { case 'posted': return <CheckCircle className="h-5 w-5 text-green-500" />; case 'failed': return <XCircle className="h-5 w-5 text-red-500" />; default: return <Clock3 className="h-5 w-5 text-yellow-500" />; } }; export function ScheduledPosts({ posts }: ScheduledPostsProps) { return ( <div className="space-y-4"> <h2 className="text-xl font-semibold text-gray-800">Scheduled Posts</h2> {posts.length === 0 ? ( <p className="text-gray-500 text-center py-8">No scheduled posts yet</p> ) : ( <div className="space-y-4"> {posts.map((post, index) => ( <div key={index} className="bg-white p-4 rounded-lg shadow-md border border-gray-100" > <div className="flex items-start justify-between"> <div className="flex-1"> <p className="text-gray-800 mb-2">{post.title}</p> <div className="flex items-center gap-4 text-sm text-gray-500"> <div className="flex items-center gap-1"> <Calendar className="h-4 w-4" /> {new Date(post.scheduled_time).toLocaleDateString()} </div> <div className="flex items-center gap-1"> <Clock className="h-4 w-4" /> {new Date(post.scheduled_time).toLocaleTimeString()} </div> </div> </div> <StatusIcon status={post.status} /> </div> </div> ))} </div> )} </div> ); }
Mit dem folgenden Befehl kann die Edge-Funktion erstellt werden
export function PostForm({ onSubmit }: PostFormProps) { const [content, setContent] = useState(''); const [title, setTitle] = useState(''); const [tags, setTags] = useState<string[]>(['javascript', 'react']); const [scheduledTime, setScheduledTime] = useState(''); const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); onSubmit({ content, title, scheduledTime, tags }); setContent(''); setTitle(''); setScheduledTime(''); setTags([]); }; const handleTagChange = (e: React.ChangeEvent<HTMLSelectElement>) => { const selectedOptions = Array.from(e.target.selectedOptions); const selectedTags = selectedOptions.map(option => option.value); if(tags.length<4){ setTags(prevTags => { const newTags = selectedTags.filter(tag => !prevTags.includes(tag)); return [...prevTags, ...newTags]; }); } }; const removeTag = (tagToRemove: string) => { setTags(tags.filter(tag => tag !== tagToRemove)); }; return ( <form onSubmit={handleSubmit} className="space-y-4 bg-white p-6 rounded-lg shadow-md"> <div> <label htmlFor="title" className="block text-sm font-medium text-gray-700 mb-2"> Post Title </label> <input type="text" > <p>I will provide the whole code as a GitHub repository at the end. </p> <p>Now, let’s look at Supbase Integration.</p> <h2> Supabase </h2> <p>First create an account on supabase, if you don’t have one. You can look at this article to get information about the creating an account on Supbase, Using ChatGPT with Your Own Data using LangChain and Supabase.</p> <p>Create the table scheduled_post. You can use the below SQL code to run in the SQL Editor to create the table or you can create the table with Table Editor.<br> </p> <pre class="brush:php;toolbar:false"> create table public.scheduled_posts ( id serial not null, content text not null, scheduled_time timestamp with time zone not null, status text null default 'pending'::text, created_at timestamp without time zone null default now(), title character varying null, devto_article_id character varying null, posted_at character varying null, tags character varying[] null, error_message character varying null, constraint scheduled_posts_pkey primary key (id) ) tablespace pg_default; create index if not exists idx_scheduled_time_status on public.scheduled_posts using btree (scheduled_time, status) tablespace pg_default;
Der obige Befehl erstellt ein Verzeichnis „functions/xscheduler“ innerhalb der Supabase. Dort finden Sie die index.ts. Die Edge-Funktion nutzt die Deno-Umgebung.
Der folgende Code gilt für die Kantenfunktion:
npx supabase init
Für die ENV stehen Ihnen automatisch SUPABASE_URL und SUPABASE_SERVICE_ROLE_KEY zur Verfügung. Für DEVTO_ACCESS_TOKEN können Sie es hier generieren und zu Projekteinstellungen → Kantenfunktionen gehen, um das Token hinzuzufügen. Dieser Token wird in der Deno-Umgebung verfügbar sein.
Sie können diese Anleitung für die Bereitstellung der benötigten Edge-Funktion verwenden.
Supbase hat kürzlich die Cron-Job-Funktionalität aktualisiert. Jetzt können Sie das Dashboard verwenden, um den Maisjob zu erstellen, zuvor mussten Sie dafür Code schreiben. Sie können einen Job erstellen, der Folgendes ausführen kann:
Wir werden die Edge-Funktion verwenden. Sie können die Details der Edge-Funktion wie Name und Autorisierung mit dem Anon-Schlüssel als Bearer-Token hinzufügen.
Da wir nun die Anwendung erstellt haben, werfen wir einen Blick auf die Funktionsweise. Führen Sie fronted mit dem folgenden Befehl aus:
supabase functions new xscheduler
Fügen Sie Details wie Titel, Inhalt, Zeit und Tags hinzu. Klicken Sie nach dem Hinzufügen auf „Beitrag planen“. Der Cron-Job wird jede Minute ausgeführt, sobald die geplante Zeit des Artikels mit der aktuellen Zeit übereinstimmt. Es wird veröffentlicht.
Der Artikel wird auf dev.to veröffentlicht, wenn der Zeitraum übereinstimmt.
Mit der oben genannten Technik können Sie eine Planungsanwendung für alles wie X, Instagram, LinkedIn usw. erstellen. Sie können daran arbeiten und Funktionen wie die folgenden hinzufügen:
Sie können sich den Code dieses Projekts hier auf GitHub ansehen.
Das Erstellen einer Planeranwendung vereinfacht die Automatisierung von Aufgaben wie dem Veröffentlichen von Artikeln, dem Versenden von Erinnerungen und dem Verwalten von Arbeitsabläufen. Mit React für das Frontend und Supabase für das Backend haben wir eine skalierbare Lösung erstellt, die Datenbanken, Cron-Jobs und Edge-Funktionen nutzt. Dieser Ansatz kann für verschiedene Anwendungsfälle angepasst werden und ermöglicht so eine effiziente Automatisierung. Mit diesen Tools sind Sie in der Lage, leistungsstarke Planungsanwendungen zu erstellen, die auf Ihre Bedürfnisse zugeschnitten sind.
Ich hoffe, dieser Artikel hat Ihnen ein Verständnis für den Cron-Job vermittelt. Vielen Dank, dass Sie den Artikel gelesen haben.
Das obige ist der detaillierte Inhalt vonErstellen eines benutzerdefinierten Schedulers mit React und Supabase. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!