import { redirect, data } from "react-router"; import { getOrigin } from "~/lib/config.server"; import type { Route } from "./+types/api.sync.push.$provider.$routeId"; import { requireSessionUser } from "~/lib/auth/session.server"; import { getManifest } from "~/lib/connected-services"; import { pushRouteToProvider } from "~/lib/connected-services/push-action.server"; import { encodeOAuthState } from "~/lib/connected-services/oauth-state.server"; export async function action({ params, request }: Route.ActionArgs) { const user = await requireSessionUser(request); const manifest = getManifest(params.provider); if (!manifest) return data({ error: "Unknown provider" }, { status: 404 }); const returnTo = `/routes/${params.routeId}`; const outcome = await pushRouteToProvider({ userId: user.id, providerId: manifest.id, routeId: params.routeId, }); switch (outcome.status) { case "success": return redirect(`${returnTo}?push=success`); case "scope_missing": { if (!manifest.buildAuthUrl) { return redirect(`${returnTo}?push=needs_permission`); } const origin = getOrigin(); const redirectUri = `${origin}/api/sync/callback/${manifest.id}`; const state = encodeOAuthState({ pushAfter: { routeId: params.routeId }, returnTo, }); return redirect(manifest.buildAuthUrl(redirectUri, state)); } case "needs_relink": return redirect(`${returnTo}?push=needs_permission`); case "no_connection": return redirect(`${returnTo}?push=no_connection`); case "no_geometry": return redirect(`${returnTo}?push=no_geometry`); case "not_owner": return data({ error: "Forbidden" }, { status: 403 }); case "not_found": return data({ error: "Not found" }, { status: 404 }); case "unsupported_provider": return data({ error: "Provider does not support push" }, { status: 400 }); case "error": return redirect(`${returnTo}?push=error&code=${outcome.code}`); } } export function loader() { return data({ error: "Method not allowed" }, { status: 405 }); }