diff --git a/backend/MCP_Execution_Server/src/routes/user.routes.ts b/backend/MCP_Execution_Server/src/routes/user.routes.ts index 27b5044..818696e 100644 --- a/backend/MCP_Execution_Server/src/routes/user.routes.ts +++ b/backend/MCP_Execution_Server/src/routes/user.routes.ts @@ -71,8 +71,13 @@ export function userRouter(userService: UserService): Router { router.post( "/unsubscribe/user", async (req: Request, res: Response, next: NextFunction): Promise => { - const { fid } = req.body; + const apiKey = req.header("x-api-key"); + if (!apiKey || apiKey !== process.env.INTERNAL_API_KEY) { + res.status(401).json({ error: "Unauthorized: Invalid API key" }); + return; + } + const { fid } = req.body; if (!fid) { res.status(400).json({ error: "Missing User FID" }); return; diff --git a/frontend/src/app/api/backend/unsubscribe/route.ts b/frontend/src/app/api/backend/unsubscribe/route.ts new file mode 100644 index 0000000..0a8da46 --- /dev/null +++ b/frontend/src/app/api/backend/unsubscribe/route.ts @@ -0,0 +1,36 @@ +import { NextRequest, NextResponse } from "next/server"; + +export async function POST(request: NextRequest) { + try { + const { fid } = await request.json(); + + const response = await fetch( + `${process.env.NEXT_PUBLIC_BACKEND_URL}/api/unsubscribe/user`, + { + method: "POST", + headers: { + "Content-Type": "application/json", + "x-api-key": process.env.INTERNAL_API_KEY!, + }, + body: JSON.stringify({ fid }), + }, + ); + + const data = await response.json(); + + if (!response.ok) { + return NextResponse.json( + { message: data.message || "Unsubscribe failed" }, + { status: response.status }, + ); + } + + return NextResponse.json(data); + } catch (e) { + console.error("Error in unsubscribe route:", e); + return NextResponse.json( + { message: "Internal server error" }, + { status: 500 }, + ); + } +} diff --git a/frontend/src/components/Landing.tsx b/frontend/src/components/Landing.tsx index e4c9143..cd9085e 100644 --- a/frontend/src/components/Landing.tsx +++ b/frontend/src/components/Landing.tsx @@ -74,6 +74,20 @@ const registerUser = async (fid: number) => { return response.json(); }; +const unsubscribeUser = async (fid: number) => { + const response = await fetch(`/api/backend/unsubscribe`, { + method: "POST", + body: JSON.stringify({ fid }), + }); + + if (!response.ok) { + const errorData = await response.json(); + throw new Error(errorData.message || "Unsubscribe failed"); + } + + return response.json(); +}; + export default function Home() { const { context } = useFrame(); const [isSubscribed, setSubscribed] = useState(false); @@ -97,7 +111,6 @@ export default function Home() { }, }); - console.log(fetchUserQuery.data, isSubscribed); const mutation = useMutation({ mutationFn: registerUser, onSuccess: (data) => { @@ -108,10 +121,25 @@ export default function Home() { }); }, onError: (error) => { + setSubscribed(false); console.error("Error registering user:", error); }, }); + const unsubscribeMutation = useMutation({ + mutationFn: unsubscribeUser, + onSuccess: (data) => { + console.log("Unsubscribe successful:", data); + setSubscribed(false); + queryClient.refetchQueries({ + queryKey: ["userSubscription", context?.user?.fid], + }); + }, + onError: (error) => { + console.error("Error unsubscribing user:", error); + }, + }); + const handleComposeMutation = useMutation({ mutationFn: async () => { const result = await sdk.actions.composeCast({ @@ -122,12 +150,17 @@ export default function Home() { }, }); - const handleSubscribe = () => { + const handleSubscribe = async () => { if (!context || !context.user?.displayName) { console.log("User not logged in"); return; } - mutation.mutate(context.user.fid); + await mutation.mutateAsync(context.user.fid); + try { + await sdk.actions.addFrame(); + } catch (error) { + console.log("Error adding frame:", error); + } setSubscribed(true); }; useEffect(() => { @@ -280,18 +313,20 @@ export default function Home() { {mutation.isPending ? "Loading..." : "Count me in !"} ) : ( - <> -

- 🎉 You're already subscribed! -

+
- +

+ We are sad to see you go +

+
)}