From f20f6571c261884320fffdda29c14902a40814d0 Mon Sep 17 00:00:00 2001 From: Luca Sacchi Ricciardi Date: Fri, 27 Mar 2026 14:27:12 +0000 Subject: [PATCH] project refactored --- Dockerfile | 26 ++++---- README.md | 146 ++++++++++++++++----------------------------- docker-compose.yml | 33 ++++------ 3 files changed, 78 insertions(+), 127 deletions(-) diff --git a/Dockerfile b/Dockerfile index ed70799..3235d91 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,22 +1,24 @@ -FROM rocm/pytorch:latest +FROM rocm/dev-ubuntu-22.04:latest ENV DEBIAN_FRONTEND=noninteractive -# Specifica l'architettura target per la compilazione dei kernel C++/HIP -ENV PYTORCH_ROCM_ARCH="gfx1100" ENV HSA_OVERRIDE_GFX_VERSION="11.0.0" +ENV AMDGPU_TARGETS="gfx1100" ENV HIP_VISIBLE_DEVICES="0" -RUN apt-get update -y && apt-get install -y git build-essential python3-dev && rm -rf /var/lib/apt/lists/* +RUN apt-get update && apt-get install -y \ + build-essential cmake git libcurl4-openssl-dev \ + && rm -rf /var/lib/apt/lists/* -WORKDIR /workspace +WORKDIR /app -# Clona vLLM e usa un tag stabile recente che supporta GGUF (0.6.0+) -RUN git clone https://github.com/vllm-project/vllm.git . && git checkout v0.6.3 +# Little often: cloniamo e compiliamo +RUN git clone https://github.com/ggerganov/llama.cpp.git . -RUN pip install -U pip && pip install -r requirements-rocm.txt - -# Compilazione (richiederà tempo) -RUN python3 setup.py install +# Compilazione con supporto HIP nativo per AMD +RUN cmake -B build -DGGML_HIP=ON -DAMDGPU_TARGETS=gfx1100 -DCMAKE_BUILD_TYPE=Release +RUN cmake --build build --config Release -j $(nproc) EXPOSE 8000 -ENTRYPOINT ["python3", "-m", "vllm.entrypoints.openai.api_server"] + +# Punto d'ingresso nudo e crudo +ENTRYPOINT ["/app/build/bin/llama-server"] diff --git a/README.md b/README.md index bec41c2..32c6dfa 100644 --- a/README.md +++ b/README.md @@ -1,112 +1,68 @@ -# Local AI Inference Node (Ryzen 7 260 / Radeon 780M) +# llamacpp-qwen3.5-0.8b -Un nodo di inferenza LLM/SLM self-hosted ad alte prestazioni, progettato per architetture AMD APU (Phoenix/Hawk Point) su Ubuntu 24.04 LTS. Il sistema è ottimizzato per fornire API ad alta velocità destinate a pipeline RAG (Retrieval-Augmented Generation), popolamento di Graph DB e integrazione fluida con piattaforme di automazione come n8n. +Un microservizio Docker standalone basato su `llama.cpp` per eseguire il modello Qwen 3.5 0.8B su GPU AMD (ottimizzato per architettura RDNA3 / gfx1100). -## 📐 Specifiche Tecniche (Spec-Driven) +Fornisce un'API HTTP nativa, compatibile al 100% con le specifiche OpenAI. Ideale per l'integrazione diretta con n8n e script Python, mantenendo un'architettura a microservizi pulita e priva di wrapper intermedi. -* **Hardware Host:** AMD Ryzen 7 260 (8C/16T), 64GB RAM Condivisa, Radeon 780M iGPU. -* **Sistema Operativo:** Ubuntu 24.04 LTS (Kernel 6.8+). -* **Accelerazione:** ROCm con spoofing architetturale (`gfx1100`). -* **Motori di Inferenza:** * `vLLM` (compilato da sorgente) per throughput massimizzato su modelli generativi (es. Qwen 3.5 0.8B, Gemma 3 27B). - * `Ollama` per la gestione flessibile degli SLM di embedding (`embeddinggemma`). -* **Memoria:** Allocazione GTT statica a livello di kernel (56GB riservati alla iGPU, 8GB al sistema operativo). +## Prerequisiti -## 🏛️ Filosofia Architetturale +- Docker e Docker Compose installati. +- GPU AMD con driver ROCm installati e funzionanti sul sistema host. +- Accesso ai device `/dev/kfd` e `/dev/dri`. -Il progetto segue tre principi fondamentali per garantire stabilità in un ambiente non-Enterprise: +## Setup (Little Often) -1. **Safety First:** Ambienti containerizzati strettamente isolati (`ipc: host`), filesystem in sola lettura per i pesi dei modelli, pre-allocazione conservativa della VRAM (`gpu-memory-utilization`) per prevenire l'intervento dell'OOM Killer. -2. **Little Often:** Suddivisione dei servizi. Modelli di embedding leggeri su un engine, modelli generativi pesanti su un altro. Build frammentate per isolare i problemi di compilazione dei kernel C++/HIP. -3. **Double Check:** Testing rigoroso (TDD) ad ogni stadio dell'implementazione. Verifica continua dell'allocazione GTT (`rocm-smi`) e del corretto spoofing dell'architettura AMD. +1. **Prepara l'ambiente:** + Clona il repository e crea la directory dedicata ai modelli. + ```bash + mkdir models + ``` ---- +2. **Scarica il modello (formato GGUF):** + Scarica i pesi quantizzati di Qwen 3.5 0.8B all'interno della cartella `models`. Ad esempio, per la versione Q8_0: + ```bash + wget [https://huggingface.co/Qwen/Qwen1.5-0.8B-Chat-GGUF/resolve/main/qwen1_5-0_8b-chat-q8_0.gguf](https://huggingface.co/Qwen/Qwen1.5-0.8B-Chat-GGUF/resolve/main/qwen1_5-0_8b-chat-q8_0.gguf) -P ./models/ + ``` + *Attenzione:* Se scarichi una quantizzazione diversa, aggiorna il nome del file all'interno del parametro `command` nel `docker-compose.yml`. -## 🛠️ Prerequisiti e Configurazione Host +3. **Build e Avvio:** + Lancia il container in background. La prima esecuzione compilerà `llama.cpp` dai sorgenti ottimizzandolo per la tua GPU. + ```bash + docker compose up --build -d + ``` -Prima di avviare l'infrastruttura, l'host Linux deve essere preparato per l'accelerazione hardware. +## Test e Validazione (Double Check) -### 1. Impostazioni BIOS -* `UMA Frame Buffer Size`: Impostato su **Auto** (lasciare la gestione dinamica al driver `amdgpu`). - -### 2. Configurazione Kernel (GRUB) -Aggiungere i seguenti parametri in `/etc/default/grub` per stabilizzare l'iGPU ed espandere la Graphics Translation Table a 56GB: +Verifica che il server sia in ascolto e risponda correttamente utilizzando l'endpoint compatibile OpenAI: ```bash -GRUB_CMDLINE_LINUX_DEFAULT="quiet splash iommu=pt amdgpu.dc=1 amdgpu.bad_page_threshold=0 pcie_aspm=off amdgpu.gttsize=57344" -``` -Applicare con: `sudo update-grub && sudo update-initramfs -u -k all`. - -### 3. Permessi Utente -L'utente che esegue i container deve appartenere ai gruppi hardware: -```bash -sudo usermod -aG render $USER -sudo usermod -aG video $USER +curl http://localhost:8000/v1/chat/completions \ + -H "Content-Type: application/json" \ + -d '{ + "model": "qwen", + "messages": [ + { + "role": "system", + "content": "Sei un assistente AI utile e conciso." + }, + { + "role": "user", + "content": "Quali sono i comandi base di Git?" + } + ] + }' ``` ---- +## Integrazione con n8n -## 🚀 Struttura del Progetto +Per collegare questo servizio a n8n: +1. Aggiungi un nodo **OpenAI** nel tuo workflow. +2. Nelle impostazioni del nodo (Credentials), imposta l'URL di base dell'API in modo che punti a questo container: + `http://:8000/v1` +3. Puoi inserire una stringa fittizia nel campo API Key (es. `sk-xxxx`), poiché il server locale non richiede autenticazione. -```text -/opt/ -├── models/ # Directory condivisa in sola lettura -│ ├── Qwen3.5-0.8B-UD-Q8_K_XL.gguf -│ └── ... -└── vllm-qwen3.5-0.8b/ # Stack di esecuzione vLLM - ├── docker-compose.yml - ├── Dockerfile - ├── test_api.py - └── CHANGELOG.md -``` - -## 📦 Deployment - -### 1. Build del Container vLLM (Custom ROCm) -L'immagine vLLM ufficiale non supporta nativamente la 780M. La compilazione dai sorgenti (`v0.6.3`) per `gfx1100` è gestita automaticamente dal Dockerfile. - -Posizionarsi nella directory operativa e lanciare la build: -```bash -cd /opt/vllm-qwen3.5-0.8b -sudo docker compose up --build -d -``` -*Nota: La compilazione dei kernel PagedAttention richiederà 15-30 minuti impegnando intensamente la CPU.* - -### 2. Monitoraggio -Verificare che l'avvio e la profilazione della memoria vadano a buon fine: -```bash -sudo docker compose logs -f -``` - ---- - -## 🧪 Validazione e Test (TDD) - -Per confermare che l'API sia operativa e conforme allo standard OpenAI, eseguire lo script di test integrato: - -```bash -python3 /opt/vllm-qwen3.5-0.8b/test_api.py -``` -Un output corretto indica che il modello è stato caricato nella VRAM pre-allocata ed è in grado di eseguire inferenza accelerata. - ---- - -## 🔗 Integrazione n8n - -Il server vLLM espone un endpoint standard OpenAI sulla porta `8000`. -In n8n, utilizzare il nodo **HTTP Request** con le seguenti specifiche: - -* **Method:** `POST` -* **URL:** `http://:8000/v1/chat/completions` -* **Headers:** `Content-Type: application/json` -* **Body:** -```json -{ - "model": "/app/models/Qwen3.5-0.8B-UD-Q8_K_XL.gguf", - "messages": [ - {"role": "system", "content": "Sei un estrattore di entità per Graph DB."}, - {"role": "user", "content": "{{$json.chunk_testo}}"} - ], - "temperature": 0.1 -} -``` +## Architettura e Sicurezza (Safety First) +- **Isolamento:** Il container esegue esclusivamente il binario `llama-server`. +- **Compatibilità RDNA3:** Il `Dockerfile` inietta `HSA_OVERRIDE_GFX_VERSION="11.0.0"` e `AMDGPU_TARGETS="gfx1100"` per forzare la compatibilità della iGPU 780M/RDNA3 con le librerie ROCm. +- **Hardware Mapping:** Assicurati che l'utente che esegue Docker abbia i permessi per accedere ai device video (gruppi `render` e `video`). diff --git a/docker-compose.yml b/docker-compose.yml index 0e150d3..05a50df 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,27 +1,20 @@ services: - vllm-qwen: - build: - context: . - dockerfile: Dockerfile - container_name: vllm_qwen_08b + qwen-08b: + build: . + container_name: qwen_08b_server ports: - "8000:8000" - ipc: host devices: - - "/dev/kfd:/dev/kfd" - - "/dev/dri:/dev/dri" - group_add: - - video - - render + - /dev/kfd:/dev/kfd + - /dev/dri:/dev/dri volumes: - # Montaggio in sola lettura del modello - - /opt/models:/app/models:ro - environment: - - HSA_OVERRIDE_GFX_VERSION=11.0.0 - - HIP_VISIBLE_DEVICES=0 + - /opt/models:/models + # -ngl 99 offloada tutti i layer sulla GPU AMD + # --host 0.0.0.0 lo rende accessibile fuori dal container command: > - --model /app/models/Qwen3.5-0.8B-UD-Q8_K_XL.gguf - --quantization gguf - --gpu-memory-utilization 0.06 - --max-model-len 32768 + -m /models/qwen1_5-0_8b-chat-q8_0.gguf + --host 0.0.0.0 + --port 8000 + -ngl 99 + -c 4096 restart: unless-stopped