From 2889b562e64993482bd13fd806af8ed0865bab8b Mon Sep 17 00:00:00 2001
From: nsfisis <nsfisis@gmail.com>
Date: Sat, 14 Feb 2026 11:52:56 +0900
Subject: refactor: migrate API from GraphQL to REST (TypeSpec/OpenAPI)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Replace the entire GraphQL stack (gqlgen, urql, graphql-codegen) with a
TypeSpec → OpenAPI 3.x pipeline using oapi-codegen for Go server stubs
and openapi-fetch + openapi-typescript for the frontend client.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
---
 frontend/src/components/AddFeedForm.tsx | 20 +++++++++++---------
 1 file changed, 11 insertions(+), 9 deletions(-)

(limited to 'frontend/src/components/AddFeedForm.tsx')

diff --git a/frontend/src/components/AddFeedForm.tsx b/frontend/src/components/AddFeedForm.tsx
index 9a56574..a60d86d 100644
--- a/frontend/src/components/AddFeedForm.tsx
+++ b/frontend/src/components/AddFeedForm.tsx
@@ -1,31 +1,31 @@
 import { faPlus, faSpinner } from "@fortawesome/free-solid-svg-icons";
 import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
 import { useState } from "react";
-import { useMutation } from "urql";
-import { AddFeedDocument } from "../graphql/generated/graphql";
+import { api } from "../services/api-client";
 
 interface Props {
 	onFeedAdded?: () => void;
 }
 
-const urqlContextFeed = { additionalTypenames: ["Feed"] };
-
 export function AddFeedForm({ onFeedAdded }: Props) {
 	const [url, setUrl] = useState("");
 	const [error, setError] = useState<string | null>(null);
-	const [{ fetching }, addFeed] = useMutation(AddFeedDocument);
+	const [fetching, setFetching] = useState(false);
 
 	const handleSubmit = async (e: React.FormEvent) => {
 		e.preventDefault();
 		if (!url.trim()) return;
 
 		setError(null);
+		setFetching(true);
 
 		try {
-			const result = await addFeed({ url: url.trim() }, urqlContextFeed);
-			if (result.error) {
-				setError(result.error.message);
-			} else if (result.data) {
+			const { data, error: fetchError } = await api.POST("/api/feeds", {
+				body: { url: url.trim() },
+			});
+			if (fetchError) {
+				setError(fetchError.message);
+			} else if (data) {
 				setUrl("");
 				onFeedAdded?.();
 			}
@@ -33,6 +33,8 @@ export function AddFeedForm({ onFeedAdded }: Props) {
 			setError(
 				error instanceof Error ? error.message : "Failed to subscribe to feed",
 			);
+		} finally {
+			setFetching(false);
 		}
 	};
 
-- 
cgit v1.3-1-g0d28

