Add `ensureOllamaAvailable` function to lib/ollama.ts for checking and waiting for Ollama server health with configurable timeout. Integrate the check in GET /api/ollama/models route with 3s timeout to prevent UI blocking, and in POST /api/ollama/pull route with 20s timeout to ensure availability before pulling models. Update ChatContainer to always render ModelDropdown for better UX when no model is selected.
67 lines
1.8 KiB
TypeScript
67 lines
1.8 KiB
TypeScript
import { NextRequest } from "next/server";
|
|
import { pullModel, ensureOllamaAvailable } from "@/lib/ollama";
|
|
|
|
export const dynamic = "force-dynamic";
|
|
|
|
export async function POST(req: NextRequest) {
|
|
try {
|
|
const { model } = await req.json();
|
|
|
|
if (!model) {
|
|
return new Response("Missing model", { status: 400 });
|
|
}
|
|
|
|
const stream = new ReadableStream({
|
|
async start(controller) {
|
|
try {
|
|
// Garantir que o servidor esteja disponível antes do pull
|
|
const ok = await ensureOllamaAvailable({ timeoutMs: 20000 });
|
|
if (!ok) {
|
|
controller.enqueue(
|
|
new TextEncoder().encode(
|
|
JSON.stringify({ error: "Ollama indisponível" }) + "\n",
|
|
),
|
|
);
|
|
controller.close();
|
|
return;
|
|
}
|
|
|
|
const response = await pullModel(model);
|
|
|
|
for await (const chunk of response) {
|
|
controller.enqueue(
|
|
new TextEncoder().encode(JSON.stringify(chunk) + "\n"),
|
|
);
|
|
}
|
|
|
|
controller.enqueue(
|
|
new TextEncoder().encode(
|
|
JSON.stringify({ status: "success" }) + "\n",
|
|
),
|
|
);
|
|
controller.close();
|
|
} catch (error) {
|
|
console.error("Pull streaming error:", error);
|
|
controller.enqueue(
|
|
new TextEncoder().encode(
|
|
JSON.stringify({ error: "Failed to pull model" }) + "\n",
|
|
),
|
|
);
|
|
controller.close();
|
|
}
|
|
},
|
|
});
|
|
|
|
return new Response(stream, {
|
|
headers: {
|
|
"Content-Type": "text/event-stream",
|
|
"Cache-Control": "no-cache",
|
|
Connection: "keep-alive",
|
|
},
|
|
});
|
|
} catch (error) {
|
|
console.error("Pull API error:", error);
|
|
return new Response("Internal server error", { status: 500 });
|
|
}
|
|
}
|