Skip to content
This repository was archived by the owner on Jan 9, 2026. It is now read-only.

Commit 26031b7

Browse files
dtrawinspgladkowsmzegla
authored
preparing rag demo (#103)
* preparing rag demo Co-authored-by: Patrycja Gładkowska <patrycja.gladkowska@intel.com> Co-authored-by: Miłosz Żeglarski <milosz.zeglarski@intel.com> * documentation updates * SDL related updates
1 parent 005ea19 commit 26031b7

10 files changed

Lines changed: 266 additions & 63 deletions

File tree

bundle/manifests/intel.com_model_servers.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,12 @@ spec:
114114
xpu_device_quantity:
115115
type: string
116116
default: "1"
117+
extra_envs_secret:
118+
type: string
119+
description: Secret name including extra environment variables to be applied in the deployed pods
120+
extra_envs_configmap:
121+
type: string
122+
description: ConfigMap name including extra environment variables to be applied in the deployed pods
117123
service_parameters:
118124
type: object
119125
description: Fill service settings

bundle/manifests/openvino-operator.clusterserviceversion.yaml

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -305,6 +305,18 @@ spec:
305305
x-descriptors:
306306
- 'urn:alm:descriptor:com.tectonic.ui:updateStrategy'
307307
- 'urn:alm:descriptor:com.tectonic.ui:advanced'
308+
- description: >-
309+
Secret name including extra environment variables to be applied in the deployed pods `oc create secret generic env_secret --from-file envfile.txt`
310+
displayName: Extra environment variables form a secret
311+
path: deployment_parameters.extra_envs_secret
312+
x-descriptors:
313+
- 'urn:alm:descriptor:io.kubernetes:Secret'
314+
- description: >-
315+
ConfigMap name including extra environment variables to be applied in the deployed pods `oc create configmap env_configmap --from-file envfile.txt`
316+
displayName: Extra environment variables form a configmap
317+
path: deployment_parameters.extra_envs_configmap
318+
x-descriptors:
319+
- 'urn:alm:descriptor:io.kubernetes:ConfigMap'
308320
- description: Number of gRPC servers. Default 1. Increase for multi client, high throughput scenarios
309321
displayName: GRPC workers
310322
path: server_settings.grpc_workers

docker/Dockerfile

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -36,13 +36,13 @@ RUN GOOS=linux GOARCH=$TARGETARCH make build
3636
RUN GOOS=linux GOARCH=$TARGETARCH make test-unit
3737

3838
# Final image.
39-
FROM registry.access.redhat.com/ubi8/ubi-minimal:8.8
39+
FROM registry.access.redhat.com/ubi8/ubi-minimal:8.9
4040
### Required OpenShift Labels
4141
LABEL name="OpenVINO toolkit operator" \
4242
maintainer="dariusz.trawinski@intel.com" \
4343
vendor="Intel Corporation" \
44-
version="1.1.0" \
45-
release="1.1" \
44+
version="1.2.0" \
45+
release="1.2" \
4646
summary="OpenVINO(TM) Toolkit Operator" \
4747
description="An Operator for managing OpenVINO Toolkit in OpenShift and Kubernetes"
4848

docs/RAG_serving_demo.md

Lines changed: 223 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,223 @@
1+
# Retrieval Augmented Generation with OpenVINO Model Server demo
2+
3+
This demo shows how to deploy in Kubernetes or OpenShift a service based on OpenVINO Model Server with a generative use cases. OpenVINO Model Server has a feature of serving MediaPipe graphs. Here we are going to use a graph with a Python calculator analyzing documents based on RAG algorithm. It indexes the documents provided to the service and expose KServe gRPC endpoint which can be used to query about content. The response is generated by the server using LLM model and Hugging Face library powered by OpenVINO Runtime.
4+
5+
Here are the steps we are going to follow:
6+
- building the container image of the model server together with required python dependencies (public image has minimal server of python components)
7+
- adding the RAG servable configuration to a ConfigMap (it includes the model server configuraiton, MediaPipe graph, python code and also a list of documents to be analysed)
8+
- optionally adding Hugging Face token to a secret, it will be attached to the deployed service to pull the models in case they requires authentication
9+
- deploying the service via the operator and ModelServer custom resource
10+
- running the client to query the document
11+
- online updates of the documents and rerunning the client query
12+
13+
14+
## Building the container image of the model server
15+
16+
The public image of Model Server is enabled for python execution but it has a minimal list of python dependencies. Depending on the use cases, a custom dependencies might need to be included in the image. Follow the instructions from https://github.com/openvinotoolkit/model_server/tree/main/demos/python_demos/rag_chatbot
17+
18+
```bash
19+
git clone https://github.com/openvinotoolkit/model_server.git
20+
cd model_server
21+
# for ubi base image
22+
make python_image BASE_OS=redhat OVMS_CPP_DOCKER_IMAGE=registry.connect.redhat.com/intel/openvino-model-server OVMS_CPP_IMAGE_TAG=2024.1-gpu
23+
# or for ubuntu22 base image
24+
make python_image BASE_OS=ubuntu OVMS_CPP_DOCKER_IMAGE=openvino/model_server OVMS_CPP_IMAGE_TAG=2024.1-gpu
25+
```
26+
Push the build image to your image registry.
27+
28+
In case of OpenShift, this build operation can be automated using a BuildConfig resource. After creating an ImageStream called `ovms`, create build config with the below spec:
29+
30+
```
31+
spec:
32+
nodeSelector: null
33+
output:
34+
to:
35+
kind: ImageStreamTag
36+
name: 'ovms:py'
37+
resources: {}
38+
strategy:
39+
type: Docker
40+
dockerStrategy:
41+
dockerfilePath: Dockerfile.redhat
42+
buildArgs:
43+
- name: IMAGE_NAME
44+
value: 'registry.connect.redhat.com/intel/openvino-model-server@sha256:b8721a65da98bd9b354680ecb2dca8a4d60a1097babe9822ab264f8e951190f7'
45+
postCommit: {}
46+
source:
47+
type: Git
48+
git:
49+
uri: 'https://github.com/openvinotoolkit/model_server'
50+
ref: main
51+
contextDir: demos/python_demos
52+
```
53+
After triggering the build for that configuration, an image will be automatically pushed to the local cluster container registry in the OpenShift.
54+
55+
## Adding the RAG servable configuration to a ConfigMap
56+
57+
The Model Server configuration including servable configuration needs to be attached to deployed pods. In this demo they will be passed via a ConfigMap which can store arbitrary files. The operator automatically mounts the content of a ConfigMap to the serving pod.
58+
59+
```bash
60+
pushd $(pwd)
61+
cd model_server/demos/python_demos/rag_chatbot/servable_stream
62+
echo https://gist.githubusercontent.com/ryanloney/42b8ebe29f95ebd4382ee0b2bb50bea2/raw/cfbb679fefb6babec675c7806254a5fff29a5e6b/aipc.txt > docs.txt
63+
oc create configmap rag-demo --from-file=config.json=config.json --from-file=graph.pbtxt=graph.pbtxt --from-file=model.py=model.py \
64+
--from-file=config.py=config.py --from-file=ov_embedding_model.py=ov_embedding_model.py \
65+
--from-file=ov_llm_model.py=ov_llm_model.py --from-file=docs.txt=docs.txt
66+
popd
67+
```
68+
69+
## Adding Hugging Face token to a Secret and the model name to the ConfigMap
70+
The RAG demo can work with several models and it can be defined as an environment variable passed to the pod. Some models might require a token to authorize the model pull from Hugging Face hub. Extra environment variables can be added to the deployment via a ConfigMap or a secret.
71+
72+
```bash
73+
oc create secret generic rag-env --from-literal=HF_TOKEN=hf_GFb...
74+
oc create configmap rag-env --from-literal=SELECTED_MODEL=tiny-llama-2-chat-7b
75+
```
76+
77+
## Deploying the service
78+
79+
Now we can deploy the Model Server by applying the custom resource:
80+
```bash
81+
oc apply -f - <<EOF
82+
apiVersion: intel.com/v1alpha1
83+
kind: ModelServer
84+
metadata:
85+
name: ovms-rag
86+
spec:
87+
image_name: image-registry.openshift-image-registry.svc:5000/<your project name>/ovms:py
88+
deployment_parameters:
89+
replicas: 1
90+
extra_envs_secret: "rag-env"
91+
extra_envs_configmap: "rag-env"
92+
models_settings:
93+
single_model_mode: false
94+
config_configmap_name: "rag-demo"
95+
server_settings:
96+
log_level: "INFO"
97+
service_parameters:
98+
grpc_port: 8080
99+
rest_port: 8081
100+
EOF
101+
```
102+
It will deploy new pod and service `ovms-rag`. In the pod initialization, it will pull and load the LLM and embedding models from Hugging Face. Then the documents from provided docs.txt file will be downloaded and analyzed. The server will be updating the analysis when the docs.txt file is modified.
103+
104+
## Running the client
105+
106+
Confirm if the RAG servable is ready for processing. Below is a command to be executed from a client Pod in the same namespace:
107+
```bash
108+
curl http://ovms-rag:8081/v2/models/python_model/ready
109+
```
110+
111+
The query can be also executed via a gRPC client with steaming capabilities. That way you can read the text as it gets generated.
112+
113+
```bash
114+
pushd $(pwd)
115+
cd model_server/demos/python_demos/llm_text_generation
116+
pip install -r client_requirements.txt
117+
python3 client_stream.py --url ovms-rag:8080 --prompt "Summarize what is AIPC."
118+
popd
119+
```
120+
121+
Alternatively, deploy a service based on `gradio` component, which provide easy to use GUI interface.
122+
In Openshift you can build the image with gradio client using the following BuildConfig spec. It assumes the image stream name `rag-gradio`:
123+
```
124+
spec:
125+
nodeSelector: null
126+
output:
127+
to:
128+
kind: ImageStreamTag
129+
name: 'rag-gradio:latest'
130+
resources: {}
131+
successfulBuildsHistoryLimit: 5
132+
failedBuildsHistoryLimit: 5
133+
strategy:
134+
type: Docker
135+
dockerStrategy:
136+
dockerfilePath: Dockerfile.gradio
137+
postCommit: {}
138+
source:
139+
type: Git
140+
git:
141+
uri: 'https://github.com/openvinotoolkit/model_server'
142+
ref: main
143+
contextDir: demos/python_demos/rag_chatbot
144+
```
145+
146+
Launch the pod:
147+
```bash
148+
oc run gradio --image image-registry.openshift-image-registry.svc:5000/<your project name>/rag-gradio --port 9000 --command -- python app.py --ovms_url ovms-rag:8080 --web_url 0.0.0.0:7860
149+
150+
oc apply -f - <<EOF
151+
kind: Service
152+
apiVersion: v1
153+
metadata:
154+
name: rag-gradio
155+
spec:
156+
ports:
157+
- protocol: TCP
158+
port: 80
159+
targetPort: 7860
160+
type: ClusterIP
161+
selector:
162+
run: gradio
163+
EOF
164+
```
165+
The created service can be not exposed via Routes resources to connect to gradio interface from the browser:
166+
167+
![gradio](./rag-gradio.png)
168+
169+
## Updating the documents
170+
Sometimes you might want to change the scope of the RAG analysis and change the documents. It can be done without reloading of the model and restarting the service.
171+
Just the `docs.txt` needs to be updated. The RAG servable has an extra thread checking regularly if the file is modified. In such case documentes are downloaded and indexed again.
172+
173+
```bash
174+
pushd $(pwd)
175+
cd model_server/demos/python_demos/rag_chatbot/servable_stream
176+
echo https://gist.githubusercontent.com/dtrawins/2956a7a77aa6732b52b8ae6eab0be205/raw/e05f2ab8fea9c8631ac5f20b8dd640074ae429c7/genai.txt > docs.txt
177+
oc delete configmap rag-demo && \
178+
oc create configmap rag-demo --from-file=config.json=config.json --from-file=graph.pbtxt=graph.pbtxt --from-file=model.py=model.py \
179+
--from-file=config.py=config.py --from-file=ov_embedding_model.py=ov_embedding_model.py \
180+
--from-file=ov_llm_model.py=ov_llm_model.py --from-file=docs.txt=docs.txt
181+
popd
182+
```
183+
184+
Wait a few moments and rerun the query:
185+
```bash
186+
pushd $(pwd)
187+
cd model_server/demos/python_demos/llm_text_generation
188+
python3 client_stream.py --url ovms-rag:8080 --prompt "What are the features of Gaudi3?"
189+
popd
190+
```
191+
192+
## Deploying on GPU
193+
194+
The same demo can be adjusted to run the inference on GPU cards. It would require the following changes:
195+
- installing [Intel Device Plugin for Kubernetes](https://github.com/intel/intel-device-plugins-for-kubernetes)
196+
- adding to the ModelServer resource requirements
197+
- adding extra environment variable DEVICE=gpu
198+
199+
```
200+
deployment_parameters:
201+
resources:
202+
limits:
203+
xpu_device: gpu.intel.com/i915
204+
xpu_device_quantity: "1"
205+
```
206+
- added extra environment variable `DEVICE=gpu` to the configmap `rag-env`.
207+
208+
## Deploying on Persistent Volume Claim
209+
210+
The demo can be used also with the cluster storage and PVC in the cluster. In such scenario the model can be stored in the same location with the servable configuration files. That way model downloading Hugging Face hub is needed. Locally stored model can be in compressed IR format. It speeds up the model loading time.
211+
212+
In such scenario, copy the content of `servable_stream` from the [RAG demo](https://github.com/openvinotoolkit/model_server/tree/main/demos/python_demos/rag_chatbot) to the volume claim togather with the downloaded and compressed models in IR format.
213+
It can be then mounted to the model server containers using the parameter with dropped `config_configmap_name`:
214+
215+
```
216+
models_repository:
217+
models_volume_claim: <pvc name>
218+
models_settings:
219+
config_path: /models/<path in pvc>/config.json
220+
```
221+
222+
223+

docs/modelserver_params.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
|image_name| model server docker image. The default is the latest public docker image |
66
|deployment_parameters.replicas| number if model server replicas to be used. In case if enabled autoscaling, it defines the initial number of replicas|
77
|deployment_parameters.openshift_service_mesh| When the value is `true`, it adds the annotations enabling the models server deployment for [OpenShift Service Mesh](https://docs.openshift.com/container-platform/4.10/service_mesh/v2x/ossm-about.html)|
8+
|deployment_parameters.extra_envs_secret| Secret name including extra environment variabled to be applied in the deployed pods `oc create secret generic env_secret --from-file envfile.txt`|
9+
|deployment_parameters.extra_envs_configmap| Configmap name including extra environment variabled to be applied in the deployed pods `oc create configmap env_configmap --from-literal=ENVNAME=VALUE`|
810
|service_parameters.grpc_port| gRPC service port; the default value is 8080|
911
|service_parameters.rest_port| REST API service port; the default value is 8081|
1012
|service_parameters.service_type| [service type](https://kubernetes.io/docs/concepts/services-networking/service/#publishing-services-service-types); the default value is ClusterIP|

docs/rag-gradio.png

108 KB
Loading

go.mod

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -139,6 +139,7 @@ require (
139139
)
140140

141141
require (
142+
github.com/go-task/slim-sprig v0.0.0-20230315185526-52ccab3ef572
142143
github.com/onsi/ginkgo v1.16.5
143144
github.com/onsi/ginkgo/v2 v2.14.0
144145
)
@@ -156,7 +157,6 @@ require (
156157
github.com/felixge/httpsnoop v1.0.3 // indirect
157158
github.com/go-gorp/gorp/v3 v3.1.0 // indirect
158159
github.com/go-logr/stdr v1.2.2 // indirect
159-
github.com/go-task/slim-sprig v0.0.0-20230315185526-52ccab3ef572 // indirect
160160
github.com/gofrs/uuid v4.0.0+incompatible // indirect
161161
github.com/google/cel-go v0.17.7 // indirect
162162
github.com/google/gnostic-models v0.6.8 // indirect
@@ -184,6 +184,5 @@ require (
184184
google.golang.org/genproto/googleapis/rpc v0.0.0-20231212172506-995d672761c0 // indirect
185185
gotest.tools/v3 v3.5.1 // indirect
186186
oras.land/oras-go v1.2.4 // indirect
187-
)
188-
189-
replace github.com/docker/distribution => github.com/docker/distribution v0.0.0-20191216044856-a8371794149d
187+
rsc.io/letsencrypt v0.0.3 // indirect
188+
)

0 commit comments

Comments
 (0)