Rid3 commited on
Commit
462abf2
·
verified ·
1 Parent(s): 599a0f5

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +65 -45
app.py CHANGED
@@ -1,12 +1,11 @@
 
 
1
  from fastapi import FastAPI, HTTPException
2
  from fastapi.middleware.cors import CORSMiddleware
3
  from pydantic import BaseModel
4
  from llama_cpp import Llama
5
- from huggingface_hub import hf_hub_download
6
- import gc
7
- import os
8
 
9
- app = FastAPI(title="Xtime AI API")
10
 
11
  app.add_middleware(
12
  CORSMiddleware,
@@ -16,85 +15,106 @@ app.add_middleware(
16
  allow_headers=["*"],
17
  )
18
 
19
- REPO_ID = "Rid3/xtime-v1beta-gguf-storage"
 
 
20
 
21
  current_llm = None
22
  current_model_name = ""
23
 
24
- MODELS = {
25
- "medium": "xtime-v1beta-n-m_1p.gguf",
26
- "small": "xtime-v1beta-xp-r_2.gguf",
27
- "large": "xtime-v1beta-q4_K_M.gguf"
28
- }
29
 
30
- def load_model(model_key: str):
31
  global current_llm, current_model_name
32
- filename = MODELS.get(model_key)
33
- if not filename:
34
- raise HTTPException(status_code=404, detail="Model not found")
 
 
35
 
36
- if current_model_name == model_key and current_llm is not None:
37
- return
38
 
39
- print(f"--- Loading model: {filename} ({model_key}) ---")
40
 
 
41
  if current_llm is not None:
42
  del current_llm
43
  gc.collect()
44
 
45
  try:
46
- model_path = hf_hub_download(repo_id=REPO_ID, filename=filename)
47
-
48
  current_llm = Llama(
49
  model_path=model_path,
50
- n_ctx=2048,
51
  n_threads=os.cpu_count() or 4,
52
- n_gpu_layers=0,
53
- verbose=False,
54
- chat_format=None # важно! для Phi-2 не используем llama-3
55
  )
56
- current_model_name = model_key
57
- print(f"✅ Модель {model_key} успешно загружена")
58
  except Exception as e:
59
- print(f"❌ Ошибка загрузки {model_key}: {e}")
60
  raise HTTPException(status_code=500, detail=str(e))
61
 
62
-
63
- @app.on_event("startup")
64
- async def startup_event():
65
- load_model("medium") # по умолчанию самая стабильная
66
-
67
-
68
  class ChatRequest(BaseModel):
69
  prompt: str
70
- model_type: str = "medium"
71
- api_key: str = ""
72
-
 
 
 
 
 
 
 
 
 
73
 
74
  @app.post("/chat")
75
  async def chat(request: ChatRequest):
76
- if request.model_type != current_model_name:
77
- load_model(request.model_type)
 
 
 
 
 
 
 
 
 
 
 
78
 
79
  try:
80
- # Для Phi-2 лучше использовать обычный create_completion
81
- prompt = f"User: {request.prompt}\nAssistant:"
 
82
 
83
  output = current_llm.create_completion(
84
  prompt=prompt,
85
- max_tokens=512,
86
- temperature=0.7,
87
- stop=["User:", "<|endoftext|>"]
88
  )
89
 
90
  response_text = output["choices"][0]["text"].strip()
91
- return {"response": response_text}
 
 
 
92
 
93
  except Exception as e:
94
  print(f"Ошибка при генерации: {e}")
95
  raise HTTPException(status_code=500, detail="Ошибка генерации ответа")
96
 
97
-
98
  @app.get("/")
99
  async def health():
100
- return {"status": "online", "model": current_model_name}
 
 
 
 
 
1
+ import os
2
+ import gc
3
  from fastapi import FastAPI, HTTPException
4
  from fastapi.middleware.cors import CORSMiddleware
5
  from pydantic import BaseModel
6
  from llama_cpp import Llama
 
 
 
7
 
8
+ app = FastAPI(title="My Local Brains API")
9
 
10
  app.add_middleware(
11
  CORSMiddleware,
 
15
  allow_headers=["*"],
16
  )
17
 
18
+ # Папка, где будут лежать ваши .gguf файлы
19
+ MODELS_DIR = "./models"
20
+ os.makedirs(MODELS_DIR, exist_ok=True)
21
 
22
  current_llm = None
23
  current_model_name = ""
24
 
25
+ def get_local_models():
26
+ """Возвращает список всех .gguf файлов в папке models"""
27
+ return [f for f in os.listdir(MODELS_DIR) if f.endswith('.gguf')]
 
 
28
 
29
+ def load_model(model_filename: str):
30
  global current_llm, current_model_name
31
+
32
+ model_path = os.path.join(MODELS_DIR, model_filename)
33
+
34
+ if not os.path.exists(model_path):
35
+ raise HTTPException(status_code=404, detail=f"Модель {model_filename} не найдена в папке {MODELS_DIR}")
36
 
37
+ if current_model_name == model_filename and current_llm is not None:
38
+ return # Модель уже загружена
39
 
40
+ print(f"--- Загрузка мозга: {model_filename} ---")
41
 
42
+ # Освобождаем память от предыдущей модели
43
  if current_llm is not None:
44
  del current_llm
45
  gc.collect()
46
 
47
  try:
 
 
48
  current_llm = Llama(
49
  model_path=model_path,
50
+ n_ctx=4096, # Размер контекста (можно увеличить до 8192, если хватает памяти)
51
  n_threads=os.cpu_count() or 4,
52
+ n_gpu_layers=-1, # -1 означает выгрузку всех возможных слоев на видеокарту (GPU)
53
+ verbose=False
 
54
  )
55
+ current_model_name = model_filename
56
+ print(f"✅ Мозг '{model_filename}' успешно подключен!")
57
  except Exception as e:
58
+ print(f"❌ Ошибка загрузки {model_filename}: {e}")
59
  raise HTTPException(status_code=500, detail=str(e))
60
 
 
 
 
 
 
 
61
  class ChatRequest(BaseModel):
62
  prompt: str
63
+ model: str = "" # Имя файла, например: "my_brain_v1.gguf". Если пусто, возьмет первую доступную.
64
+ system_prompt: str = "Ты полезный, умный ИИ-ассистент."
65
+ max_tokens: int = 512
66
+ temperature: float = 0.7
67
+
68
+ @app.get("/models")
69
+ async def list_models():
70
+ """Посмотреть все доступные модели"""
71
+ return {
72
+ "available_models": get_local_models(),
73
+ "current_loaded_model": current_model_name
74
+ }
75
 
76
  @app.post("/chat")
77
  async def chat(request: ChatRequest):
78
+ global current_model_name
79
+
80
+ # Определяем, какую модель грузить
81
+ target_model = request.model
82
+ if not target_model:
83
+ models = get_local_models()
84
+ if not models:
85
+ raise HTTPException(status_code=404, detail="В папке ./models нет ни одного .gguf файла!")
86
+ target_model = models[0] # Берем первую попавшуюся
87
+
88
+ # Загружаем, если еще не загружена
89
+ if target_model != current_model_name:
90
+ load_model(target_model)
91
 
92
  try:
93
+ # Универсальный шаблон промпта (System + User).
94
+ # Если вы используете модели формата Llama-3 или ChatML, шаблон можно поменять.
95
+ prompt = f"System: {request.system_prompt}\nUser: {request.prompt}\nAssistant:"
96
 
97
  output = current_llm.create_completion(
98
  prompt=prompt,
99
+ max_tokens=request.max_tokens,
100
+ temperature=request.temperature,
101
+ stop=["User:", "System:", "<|endoftext|>", "<|im_end|>"]
102
  )
103
 
104
  response_text = output["choices"][0]["text"].strip()
105
+ return {
106
+ "response": response_text,
107
+ "model_used": current_model_name
108
+ }
109
 
110
  except Exception as e:
111
  print(f"Ошибка при генерации: {e}")
112
  raise HTTPException(status_code=500, detail="Ошибка генерации ответа")
113
 
 
114
  @app.get("/")
115
  async def health():
116
+ return {
117
+ "status": "online",
118
+ "active_brain": current_model_name,
119
+ "instruction": f"Положите ваши .gguf файлы в папку {os.path.abspath(MODELS_DIR)}"
120
+ }