abanm commited on
Commit
0c172ff
·
1 Parent(s): ba5ad28

Initial commit: Add Dockerfile, app.py, and requirements.txt

Browse files
Files changed (3) hide show
  1. Dockerfile +61 -0
  2. app.py +47 -0
  3. requirements.txt +3 -0
Dockerfile ADDED
@@ -0,0 +1,61 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # ----------------------------------------------------------
2
+ # 1. Base image
3
+ # ----------------------------------------------------------
4
+ FROM ubuntu:22.04
5
+
6
+ # Avoid interactive prompts during build
7
+ ENV DEBIAN_FRONTEND=noninteractive
8
+
9
+ # ----------------------------------------------------------
10
+ # 2. Install dependencies
11
+ # ----------------------------------------------------------
12
+ RUN apt-get update && apt-get install -y --no-install-recommends \
13
+ wget \
14
+ curl \
15
+ ca-certificates \
16
+ git \
17
+ build-essential \
18
+ python3 \
19
+ python3-pip \
20
+ && rm -rf /var/lib/apt/lists/*
21
+
22
+ # ----------------------------------------------------------
23
+ # 3. Install Ollama
24
+ # Check https://github.com/jmorganca/ollama/releases for the latest version
25
+ # ----------------------------------------------------------
26
+ ARG OLLAMA_VERSION="v0.0.14"
27
+ RUN wget -q \
28
+ https://github.com/jmorganca/ollama/releases/download/${OLLAMA_VERSION}/ollama-linux-x64 \
29
+ -O /usr/local/bin/ollama && \
30
+ chmod +x /usr/local/bin/ollama
31
+
32
+ # ----------------------------------------------------------
33
+ # 4. Copy Python requirements and install
34
+ # ----------------------------------------------------------
35
+ WORKDIR /app
36
+ COPY requirements.txt /app/requirements.txt
37
+ RUN pip3 install --no-cache-dir -r requirements.txt
38
+
39
+ # ----------------------------------------------------------
40
+ # 5. Copy application files
41
+ # ----------------------------------------------------------
42
+ COPY app.py /app/app.py
43
+
44
+ # ----------------------------------------------------------
45
+ # 6. Environment variables & expose port
46
+ # ----------------------------------------------------------
47
+ # By default, set an example API key (override at runtime/Secrets)
48
+ ENV OLLAMA_API_KEY=change_me
49
+
50
+ # We must expose 7860 for Hugging Face Spaces
51
+ EXPOSE 7860
52
+
53
+ # ----------------------------------------------------------
54
+ # 7. Start Ollama in background and then run the FastAPI server
55
+ # ----------------------------------------------------------
56
+ # The model is pulled from HF: abanm/Dubs-Q8_0-GGUF
57
+ #
58
+ # "ollama serve" runs on default port 11411. We'll run that in the background,
59
+ # then run uvicorn on 7860.
60
+ CMD [ "sh", "-c", "ollama serve --model https://huggingface.co/abanm/Dubs-Q8_0-GGUF & uvicorn app:app --host 0.0.0.0 --port 7860" ]
61
+ "https://huggingface.co/your-account/your-model"]
app.py ADDED
@@ -0,0 +1,47 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import os
2
+ import subprocess
3
+
4
+ from fastapi import FastAPI, Request, HTTPException
5
+ import uvicorn
6
+
7
+ app = FastAPI()
8
+
9
+ # Load your API key from environment (set this in HF Secrets for security)
10
+ OLLAMA_API_KEY = os.environ.get("OLLAMA_API_KEY", "change_me")
11
+
12
+ @app.post("/generate")
13
+ async def generate(request: Request):
14
+ """Endpoint that generates text based on the prompt."""
15
+ # 1. Check API key
16
+ auth_header = request.headers.get("Authorization")
17
+ if not auth_header or not auth_header.startswith("Bearer "):
18
+ raise HTTPException(status_code=401, detail="Missing or invalid Authorization header")
19
+
20
+ token = auth_header.split(" ")[1]
21
+ if token != OLLAMA_API_KEY:
22
+ raise HTTPException(status_code=401, detail="Invalid API key")
23
+
24
+ # 2. Parse the request JSON
25
+ body = await request.json()
26
+ prompt_text = body.get("prompt", "")
27
+ if not prompt_text:
28
+ raise HTTPException(status_code=400, detail="No prompt provided")
29
+
30
+ # 3. Option A: Call Ollama via its CLI directly
31
+ # (The model is served in the background via `ollama serve`)
32
+ process = subprocess.Popen(
33
+ ["ollama", "run", prompt_text],
34
+ stdout=subprocess.PIPE,
35
+ stderr=subprocess.PIPE,
36
+ text=True
37
+ )
38
+ output, error = process.communicate()
39
+
40
+ if process.returncode != 0 or error:
41
+ raise HTTPException(status_code=500, detail=f"Ollama error: {error.strip()}")
42
+
43
+ return {"response": output.strip()}
44
+
45
+
46
+ if __name__ == "__main__":
47
+ uvicorn.run(app, host="0.0.0.0", port=7860)
requirements.txt ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ fastapi
2
+ uvicorn
3
+ httpx