atakan commited on
Commit
306a458
·
1 Parent(s): 16e844c

perf: Preload model on container startup and optimize PyTorch CPU multi-threading

Browse files
Files changed (2) hide show
  1. app.py +10 -1
  2. controlai_agent/orchestrator.py +17 -3
app.py CHANGED
@@ -7,6 +7,7 @@ import os
7
  import shutil
8
  import sys
9
  import time
 
10
  from pathlib import Path
11
  from typing import Any
12
 
@@ -25,7 +26,15 @@ from controlai_rag.chunker import chunk_document
25
  from controlai_rag.document_loader import load_single_file
26
  from controlai_rag.index import ControlRAGIndex
27
 
28
- app = FastAPI(title="ControlAI", version="1.0.0")
 
 
 
 
 
 
 
 
29
 
30
  app.add_middleware(
31
  CORSMiddleware,
 
7
  import shutil
8
  import sys
9
  import time
10
+ from contextlib import asynccontextmanager
11
  from pathlib import Path
12
  from typing import Any
13
 
 
26
  from controlai_rag.document_loader import load_single_file
27
  from controlai_rag.index import ControlRAGIndex
28
 
29
+ @asynccontextmanager
30
+ async def lifespan(app: FastAPI):
31
+ print("Pre-loading ControlAI Core Engine on startup...")
32
+ get_agent()
33
+ print("ControlAI Core Engine is online and ready for traffic.")
34
+ yield
35
+
36
+
37
+ app = FastAPI(title="ControlAI", version="1.0.0", lifespan=lifespan)
38
 
39
  app.add_middleware(
40
  CORSMiddleware,
controlai_agent/orchestrator.py CHANGED
@@ -183,11 +183,23 @@ class ControlAIAgent:
183
  self.hf_tokenizer = AutoTokenizer.from_pretrained(model_path)
184
  else:
185
  # Universal PyTorch / Transformers fallback on Linux, Colab, HuggingFace, CUDA
 
 
 
 
 
 
 
186
  hf_id = "Qwen/Qwen2.5-3B-Instruct" if "mlx" in str(model_path) else model_path
 
187
  self.hf_tokenizer = AutoTokenizer.from_pretrained(hf_id, trust_remote_code=True)
 
 
 
188
  self.model = AutoModelForCausalLM.from_pretrained(
189
  hf_id,
190
- torch_dtype="auto",
 
191
  device_map="auto",
192
  trust_remote_code=True,
193
  )
@@ -195,8 +207,10 @@ class ControlAIAgent:
195
  try:
196
  from peft import PeftModel
197
  self.model = PeftModel.from_pretrained(self.model, adapter_path)
198
- except Exception:
199
- pass
 
 
200
 
201
  # Initialize local offline RAG index
202
  try:
 
183
  self.hf_tokenizer = AutoTokenizer.from_pretrained(model_path)
184
  else:
185
  # Universal PyTorch / Transformers fallback on Linux, Colab, HuggingFace, CUDA
186
+ import torch
187
+ num_threads = min(os.cpu_count() or 2, 4)
188
+ try:
189
+ torch.set_num_threads(num_threads)
190
+ except Exception:
191
+ pass
192
+
193
  hf_id = "Qwen/Qwen2.5-3B-Instruct" if "mlx" in str(model_path) else model_path
194
+ print(f"Loading PyTorch model: {hf_id} (CPU threads: {num_threads})...")
195
  self.hf_tokenizer = AutoTokenizer.from_pretrained(hf_id, trust_remote_code=True)
196
+
197
+ # Use bfloat16 on CUDA, float32 on CPU for clean numerical stability
198
+ dtype = torch.bfloat16 if torch.cuda.is_available() else torch.float32
199
  self.model = AutoModelForCausalLM.from_pretrained(
200
  hf_id,
201
+ torch_dtype=dtype,
202
+ low_cpu_mem_usage=True,
203
  device_map="auto",
204
  trust_remote_code=True,
205
  )
 
207
  try:
208
  from peft import PeftModel
209
  self.model = PeftModel.from_pretrained(self.model, adapter_path)
210
+ print(f"Loaded PEFT LoRA adapter from: {adapter_path}")
211
+ except Exception as exc:
212
+ print(f"Warning: Could not load LoRA adapter in PyTorch: {exc}")
213
+ print("PyTorch model loaded successfully.")
214
 
215
  # Initialize local offline RAG index
216
  try: