Cómo crear un chatbot de IA con Milvus y Towhee
Milvus, una base de datos vectorial de código abierto, es la columna vertebral perfecta para cualquier aplicación de IA que requiera capacidades de búsqueda vectorial eficientes y escalables, lo que la convierte en una opción destacada para la gestión de datos de tu chatbot. Towhee es un framework emergente para flujos de trabajo de machine learning que simplifica el proceso de implementar y orquestar modelos de ML complejos. También hace que el desarrollo de tu aplicación sea manejable y fácil de entender.
En este tutorial, aprenderás a crear un chatbot de IA sencillo con Python usando Milvus y Towhee. Te centrarás en cómo ingerir datos no estructurados, analizarlos, almacenarlos con embeddings y procesar consultas.
Configurar tu entorno
Primero, crea un entorno virtual de Python para ejecutar tu chatbot.
Aquí tienes una sesión de shell de Linux. Crea el entorno, lo activa y actualiza pip a la última versión.
[egoebelbecker@ares milvus_chatbot]$ python -m venv ./chatbot_venv
[egoebelbecker@ares milvus_chatbot]$ source chatbot_venv/bin/activate
(chatbot_venv) [egoebelbecker@ares milvus_chatbot]$ pip install --upgrade pip
Requirement already satisfied: pip in ./chatbot_venv/lib64/python3.11/site-packages (22.2.2)
Collecting pip
Using cached pip-23.1.2-py3-none-any.whl (2.1 MB)
Installing collected packages: pip
Attempting uninstall: pip
Found existing installation: pip 22.2.2
Uninstalling pip-22.2.2:
Successfully uninstalled pip-22.2.2
Successfully installed pip-23.1.2
A continuación, instala los paquetes que necesitas para ejecutar el código: pandas, jupyter, langchain, towhee, unstructured, milvus, pymilvus, sentence_transformers y gradio.
(chatbot_venv) [egoebelbecker@ares milvus_chatbot]$ pip install pandas jupyter langchain towhee unstructured milvus pymilvus sentence_transformers gradio
Recolectando pandas
Obteniendo información de dependencias para pandas desde https://files.pythonhosted.org/packages/d0/28/88b81881c056376254618fad622a5e94b5126db8c61157ea1910cd1c040a/pandas-2.0.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.metadata
Usando pandas-2.0.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.metadata en caché (18 kB)
Recolectando jupyter
Usando jupyter-1.0.0-py2.py3-none-any.whl en caché (2.7 kB)
(recorte)
Instalando paquetes recolectados: webencodings, wcwidth, pytz, pure-eval, ptyprocess, pickleshare, json5, ipython-genutils, filetype, fastjsonschema, executing, backcall, zipp, XlsxWriter, xlrd, widgetsnbextension, websocket-client, webcolors, urllib3, uri-template, tzdata, typing-extensions, traitlets, tqdm, tornado, tinycss2, tenacity, tabulate, soupsieve, sniffio, six, send2trash, rpds-py, rfc3986-validator, rfc3986, regex, pyzmq, PyYAML, python-magic, python-json-logger, pypandoc, pygments, pycparser, psutil, prompt-toolkit, prometheus-client, platformdirs, pkginfo, pillow, pexpect, parso, pandocfilters, packaging, overrides, olefile, numpy, nest-asyncio, mypy-extensions, multidict, more-itertools, mistune, mdurl, markupsafe, markdown, lxml, jupyterlab-widgets, jupyterlab-pygments, jsonpointer, joblib, jeepney, idna, greenlet, frozenlist, fqdn, et-xmlfile, docutils, defusedxml, decorator, debugpy, click, charset-normalizer, chardet, certifi, babel, attrs, async-timeout, async-lru, yarl, typing-inspect, terminado, SQLAlchemy, rfc3339-validator, requests, referencing, qtpy, python-pptx, python-docx, python-dateutil, pydantic, pdf2image, openpyxl, numexpr, nltk, msg-parser, matplotlib-inline, marshmallow, markdown-it-py, jupyter-core, jinja2, jedi, jaraco.classes, importlib-metadata, comm, cffi, bleach, beautifulsoup4, asttokens, anyio, aiosignal, stack-data, rich, requests-toolbelt, readme-renderer, pandas, openapi-schema-pydantic, langsmith, jupyter-server-terminals, jupyter-client, jsonschema-specifications, dataclasses-json, cryptography, arrow, argon2-cffi-bindings, aiohttp, SecretStorage, pdfminer.six, langchain, jsonschema, isoduration, ipython, argon2-cffi, unstructured, nbformat, keyring, ipykernel, twine, qtconsole, nbclient, jupyter-events, jupyter-console, ipywidgets, towhee, nbconvert, jupyter-server, notebook-shim, jupyterlab-server, jupyter-lsp, jupyterlab, notebook, jupyter
Instalado correctamente PyYAML-6.0.1 SQLAlchemy-2.0.19 SecretStorage-3.3.3 XlsxWriter-3.1.2 aiohttp-3.8.5 aiosignal-1.3.1 anyio-3.7.1 argon2-cffi-21.3.0 argon2-cffi-bindings-21.2.0 arrow-1.2.3 asttokens-2.2.1 async-lru-2.0.4 async-timeout-4.0.2 attrs-23.1.0 babel-2.12.1 backcall-0.2.0 beautifulsoup4-4.12.2 bleach-6.0.0 certifi-2023.7.22 cffi-1.15.1 chardet-5.1.0 charset-normalizer-3.2.0 click-8.1.6 comm-0.1.3 cryptography-41.0.2 dataclasses-json-0.5.14 debugpy-1.6.7 decorator-5.1.1 defusedxml-0.7.1 docutils-0.20.1 et-xmlfile-1.1.0 executing-1.2.0 fastjsonschema-2.18.0 filetype-1.2.0 fqdn-1.5.1 frozenlist-1.4.0 greenlet-2.0.2 idna-3.4 importlib-metadata-6.8.0 ipykernel-6.25.0 ipython-8.14.0 ipython-genutils-0.2.0 ipywidgets-8.0.7 isoduration-20.11.0 jaraco.classes-3.3.0 jedi-0.19.0 jeepney-0.8.0 jinja2-3.1.2 joblib-1.3.1 json5-0.9.14 jsonpointer-2.4 jsonschema-4.18.4 jsonschema-specifications-2023.7.1 jupyter-1.0.0 jupyter-client-8.3.0 jupyter-console-6.6.3 jupyter-core-5.3.1 jupyter-events-0.7.0 jupyter-lsp-2.2.0 jupyter-server-2.7.0 jupyter-server-terminals-0.4.4 jupyterlab-4.0.3 jupyterlab-pygments-0.2.2 jupyterlab-server-2.24.0 jupyterlab-widgets-3.0.8 keyring-24.2.0 langchain-0.0.248 langsmith-0.0.15 lxml-4.9.3 markdown-3.4.4 markdown-it-py-3.0.0 markupsafe-2.1.3 marshmallow-3.20.1 matplotlib-inline-0.1.6 mdurl-0.1.2 mistune-3.0.1 more-itertools-10.0.0 msg-parser-1.2.0 multidict-6.0.4 mypy-extensions-1.0.0 nbclient-0.8.0 nbconvert-7.7.3 nbformat-5.9.2 nest-asyncio-1.5.7 nltk-3.8.1 notebook-7.0.1 notebook-shim-0.2.3 numexpr-2.8.4 numpy-1.25.2 olefile-0.46 openapi-schema-pydantic-1.2.4 openpyxl-3.1.2 overrides-7.3.1 packaging-23.1 pandas-2.0.3 pandocfilters-1.5.0 parso-0.8.3 pdf2image-1.16.3 pdfminer.six-20221105 pexpect-4.8.0 pickleshare-0.7.5 pillow-10.0.0 pkginfo-1.9.6 platformdirs-3.10.0 prometheus-client-0.17.1 prompt-toolkit-3.0.39 psutil-5.9.5 ptyprocess-0.7.0 pure-eval-0.2.2 pycparser-2.21 pydantic-1.10.12 pygments-2.15.1 pypandoc-1.11 python-dateutil-2.8.2 python-docx-0.8.11 python-json-logger-2.0.7 python-magic-0.4.27 python-pptx-0.6.21 pytz-2023.3 pyzmq-25.1.0 qtconsole-5.4.3 qtpy-2.3.1 readme-renderer-40.0 referencing-0.30.0 regex-2023.6.3 requests-2.31.0 requests-toolbelt-1.0.0 rfc3339-validator-0.1.4 rfc3986-2.0.0 rfc3986-validator-0.1.1 rich-13.5.1 rpds-py-0.9.2 send2trash-1.8.2 six-1.16.0 sniffio-1.3.0 soupsieve-2.4.1 stack-data-0.6.2 tabulate-0.9.0 tenacity-8.2.2 terminado-0.17.1 tinycss2-1.2.1 tornado-6.3.2 towhee-1.1.1 tqdm-4.65.0 traitlets-5.9.0 twine-4.0.2 typing-extensions-4.7.1 typing-inspect-0.9.0 tzdata-2023.3 unstructured-0.8.7 uri-template-1.3.0 urllib3-2.0.4 wcwidth-0.2.6 webcolors-1.13 webencodings-0.5.1 websocket-client-1.6.1 widgetsnbextension-4.0.8 xlrd-2.0.1 yarl-1.9.2 zipp-3.16.2
(chatbot_venv) [egoebelbecker@ares milvus_chatbot]$
Puedes encontrar un notebook de Jupyter con el código para este tutorial aquí. Descárgalo, inicia Jupyter y carga el notebook:
chatbot_venv) [egoebelbecker@ares milvus_chatbot]$ jupyter notebook milvus_chatbot.ipynb
[I 2023-07-31 11:29:01.748 ServerApp] Package notebook took 0.0000s to import
[I 2023-07-31 11:29:01.759 ServerApp] Package jupyter_lsp took 0.0108s to import
[W 2023-07-31 11:29:01.759 ServerApp] A `_jupyter_server_extension_points` function was not found in jupyter_lsp. Instead, a `_jupyter_server_extension_paths` function was found and will be used for now. This function name will be deprecated in future releases of Jupyter Server.
[I 2023-07-31 11:29:01.764 ServerApp] Package jupyter_server_terminals took 0.0045s to import
[I 2023-07-31 11:29:01.765 ServerApp] Package jupyterlab took 0.0000s to import
[I 2023-07-31 11:29:02.124 ServerApp] Package notebook_shim took 0.0000s to import
Crear un chatbot
Ahora, pongámonos a trabajar en el chatbot.
Almacén de documentos
El bot necesita almacenar fragmentos de documentos y los embeddings que Towhee extrae de ellos. Para eso usarás Milvus. Ya instalaste Milvus Lite, una versión ligera de Milvus, arriba con la biblioteca milvus.
Puedes ejecutar un servidor desde la línea de comandos:
(chatbot_venv) [egoebelbecker@ares milvus_chatbot]$ milvus-server
__ _________ _ ____ ______
/ |/ / _/ /| | / / / / / __/
/ /|_/ // // /_| |/ / /_/ /\ \
/_/ /_/___/____/___/\____/___/ {Lite}
Welcome to use Milvus!
Version: v2.2.12-lite
Process: 139309
Started: 2023-07-31 12:43:43
Config: /home/egoebelbecker/.milvus.io/milvus-server/2.2.12/configs/milvus.yaml
Logs: /home/egoebelbecker/.milvus.io/milvus-server/2.2.12/logs
Ctrl+C to exit …
O, como parte del código de tu aplicación, como se muestra en el notebook:
from milvus import default_server
# Start Milvus service
default_server.start()
# # Stop Milvus service
# default_server.stop()
Establecer variables de la aplicación y obtener la clave de API de OpenAI
A continuación, establece algunas variables y limpia cualquier archivo SQLite restante. Usaremos SQLite más abajo para el historial de chat.
- MILVUS_URI - la información de conexión para los servidores Milvus. Analizada en host y puerto.
- MILVUS_HOST - el host donde se está ejecutando Milvus.
- MILVUS_PORT - el puerto en el que escucha el servidor.
- DROP_EXIST - eliminar las colecciones existentes de Milvus al iniciar.
- EMBED_MODEL - el modelo sentence_transformers que el código usará para crear embeddings
- COLLECTION_NAME - nombre de la colección de Milvus para datos y embeddings
- DIM - la dimensión de los embeddings que el modelo crea para cada fragmento de texto
- OPENAI_API_KEY - clave para la API del LLM
import getpass
import os
MILVUS_URI = 'http://localhost:19530'
[MILVUS_HOST, MILVUS_PORT] = MILVUS_URI.split('://')[1].split(':')
DROP_EXIST = True
EMBED_MODEL = 'all-mpnet-base-v2'
COLLECTION_NAME = 'chatbot_demo'
DIM = 768
OPENAI_API_KEY = getpass.getpass('Enter your OpenAI API key: ')
if os.path.exists('./sqlite.db'):
os.remove('./sqlite.db')
Ejecuta este código para definir las variables y responder al prompt para la clave de API.
Pipeline de ejemplo
A continuación, es momento de descargar algunos datos y almacenarlos en Milvus. Pero antes de hacerlo, veamos un pipeline de ejemplo para descargar y procesar datos no estructurados.
Usarás las páginas de documentación de Towhee para este ejemplo. Puedes probar diferentes sitios para ver cómo el código procesa diferentes conjuntos de datos.
Este código usa pipelines de Towhee:
- input - comienza un nuevo pipeline con la fuente que se le pasa
- map - usa ops.text_loader() para recuperar la URL y asignarla a 'doc'
- flat_map - usa ops.text_splitter() para procesar el documento en "fragmentos" para su almacenamiento
- output - cierra y prepara el pipeline para su uso
Pasa este pipeline a DataCollection para ver cómo funciona.
from towhee import pipe, ops, DataCollection
pipe_load = (
pipe.input('source')
.map('source', 'doc', ops.text_loader())
.flat_map('doc', 'doc_chunks', ops.text_splitter(chunk_size=300))
.output('source', 'doc_chunks')
)
DataCollection(pipe_load('https://towhee.io')).show()
Aquí está la salida de show():
La pipeline creó cinco fragmentos a partir del documento.
Pipeline de embeddings de ejemplo
La pipeline recuperó los datos y creó fragmentos. También necesitas crear embeddings. Echemos un vistazo a otra pipeline de ejemplo.
Esta usa map() para ejecutar ops.sentence_embedding.sbert() en cada fragmento. En este ejemplo, estamos pasando un único bloque de texto.
pipe_embed = (
pipe.input('doc_chunk')
.map('doc_chunk', 'vec', ops.sentence_embedding.sbert(model_name=EMBED_MODEL))
.map('vec', 'vec', ops.np_normalize())
.output('doc_chunk', 'vec')
)
text = '''SOTA Models
We provide 700+ pre-trained embedding models spanning 5 fields (CV, NLP, Multimodal, Audio, Medical), 15 tasks, and 140+ model architectures.
These include BERT, CLIP, ViT, SwinTransformer, data2vec, etc.
'''
DataCollection(pipe_embed(text)).show()
Ejecuta este código para ver cómo la pipeline procesa el único bloque de texto.
Preparar Milvus
Ahora necesitas una colección para almacenar los datos. Este bloque define create_collection(), que usa MILVUS_HOST y MILVUS_PORT para conectarse a Milvus, eliminar cualquier colección existente con el nombre especificado y crear una nueva con este esquema:
- id - un identificador entero
- embedding - un vector de flotantes para los embeddings
- text - el texto correspondiente para los embeddings
from pymilvus import (
connections, utility, Collection,
CollectionSchema, FieldSchema, DataType
)
def create_collection(collection_name):
connections.connect(host=MILVUS_HOST, port=MILVUS_PORT)
has_collection = utility.has_collection(collection_name)
if has_collection:
collection = Collection(collection_name)
if DROP_EXIST:
collection.drop()
else:
return collection
# Create collection
fields = [
FieldSchema(name='id', dtype=DataType.INT64, is_primary=True, auto_id=True),
FieldSchema(name='embedding', dtype=DataType.FLOAT_VECTOR, dim=DIM),
FieldSchema(name='text', dtype=DataType.VARCHAR, max_length=500)
]
schema = CollectionSchema(
fields=fields,
description="Towhee demo",
enable_dynamic_field=True
)
collection = Collection(name=collection_name, schema=schema)
index_params = {
'metric_type': 'IP',
'index_type': 'IVF_FLAT',
'params': {'nlist': 1024}
}
collection.create_index(
field_name='embedding',
index_params=index_params
)
return collection
Pipeline de inserción
Es hora de procesar tu texto de entrada e insertarlo en Milvus. Empecemos con una pipeline que resume lo que aprendiste arriba.
Esta función:
- Crea la nueva colección
- Recupera los datos
- Los divide en fragmentos
- Crea embeddings usando EMBED_MODEL
- Inserta el texto y los embeddings en Milvus
load_data = (
pipe.input('collection_name', 'source')
.map('collection_name', 'collection', create_collection)
.map('source', 'doc', ops.text_loader())
.flat_map('doc', 'doc_chunk', ops.text_splitter(chunk_size=300))
.map('doc_chunk', 'vec', ops.sentence_embedding.sbert(model_name=EMBED_MODEL))
.map('vec', 'vec', ops.np_normalize())
.map(('collection_name', 'vec', 'doc_chunk'), 'mr',
ops.ann_insert.osschat_milvus(host=MILVUS_HOST, port=MILVUS_PORT))
.output('mr')
)
Aquí está en acción. Ejecútala contra la página de Wikipedia de Frodo Baggins.
project_name = 'towhee_demo'
data_source = 'https://en.wikipedia.org/wiki/Frodo_Baggins'
mr = load_data(COLLECTION_NAME, data_source)
print('Fragmentos de documento insertados:', len(mr.to_list()))
Inserta 408 fragmentos con embeddings:
2023-07-31 16:50:53,369 - 139993906521792 - node.py-node:167 - INFO: Begin to run Node-_input
2023-07-31 16:50:53,371 - 139993906521792 - node.py-node:167 - INFO: Begin to run Node-create_collection-0
2023-07-31 16:50:53,373 - 139993881343680 - node.py-node:167 - INFO: Begin to run Node-text-loader-1
2023-07-31 16:50:53,374 - 139993898129088 - node.py-node:167 - INFO: Begin to run Node-text-splitter-2
2023-07-31 16:50:53,376 - 139993872950976 - node.py-node:167 - INFO: Begin to run Node-sentence-embedding/sbert-3
2023-07-31 16:50:53,377 - 139993385268928 - node.py-node:167 - INFO: Begin to run Node-np-normalize-4
2023-07-31 16:50:53,378 - 139993376876224 - node.py-node:167 - INFO: Begin to run Node-ann-insert/osschat-milvus-5
2023-07-31 16:50:53,379 - 139993368483520 - node.py-node:167 - INFO: Begin to run Node-_output
(snip)
Categories:
2023-07-31 18:07:53,530 - 140552729257664 - logger.py-logger:14 - DETAIL: Skipping sentence because does not exceed 5 word tokens
Categories
2023-07-31 18:07:53,532 - 140552729257664 - logger.py-logger:14 - DETAIL: Skipping sentence because does not exceed 3 word tokens
Hidden categories
2023-07-31 18:07:53,533 - 140552729257664 - logger.py-logger:14 - DETAIL: Skipping sentence because does not exceed 3 word tokens
Hidden categories
2023-07-31 18:07:53,533 - 140552729257664 - logger.py-logger:14 - DETAIL: Not narrative. Text does not contain a verb:
Hidden categories:
2023-07-31 18:07:53,534 - 140552729257664 - logger.py-logger:14 - DETAIL: Skipping sentence because does not exceed 5 word tokens
Hidden categories
Fragmentos de documento insertados: 408
Buscar en la base de conocimientos
Ahora, con los embeddings y el texto almacenados en Milvus, puedes buscarlos.
Esta función crea un pipeline de consulta. El paso más importante es este:
ops.ann_search.osschat_milvus(host=MILVUS_HOST, port=MILVUS_PORT,
**{'metric_type': 'IP', 'limit': 3, 'output_fields': ['text']}))
El osschat_milvus busca coincidencias en los embeddings para el texto enviado.
Aquí está el pipeline completo:
pipe_search = (
pipe.input('collection_name', 'query')
.map('query', 'query_vec', ops.sentence_embedding.sbert(model_name=EMBED_MODEL))
.map('query_vec', 'query_vec', ops.np_normalize())
.map(('collection_name', 'query_vec'), 'search_res',
ops.ann_search.osschat_milvus(host=MILVUS_HOST, port=MILVUS_PORT,
**{'metric_type': 'IP', 'limit': 3, 'output_fields': ['text']}))
.flat_map('search_res', ('id', 'score', 'text'), lambda x: (x[0], x[1], x[2]))
.output('query', 'text', 'score')
)
Pruébalo:
query = 'Who is Frodo Baggins?'
DataCollection(pipe_search(project_name, query)).show()
El modelo hace un buen trabajo al extraer tres nodos estrechamente coincidentes:
Añadir un LLM
Ahora es momento de añadir un modelo de lenguaje grande (LLM) para que los usuarios puedan mantener una conversación con el chatbot. Usaremos ChatGPT y la API de OpenAI para este ejemplo.
Historial de chat
Para obtener mejores resultados del LLM, necesitas almacenar el historial de chat y presentarlo con las consultas. Usarás SQLite para este paso.
Aquí tienes una función para recuperar el historial:
pipe_get_history = (
pipe.input('collection_name', 'session')
.map(('collection_name', 'session'), 'history', ops.chat_message_histories.sql(method='get'))
.output('collection_name', 'session', 'history')
)
Aquí tienes la que lo almacena:
pipe_add_history = (
pipe.input('collection_name', 'session', 'question', 'answer')
.map(('collection_name', 'session', 'question', 'answer'), 'history', ops.chat_message_histories.sql(method='add'))
.output('history')
)
Canalización de consultas LLM
Ahora, necesitamos una canalización para enviar consultas a ChatGPT.
Esta canalización:
- busca en Milvus usando la consulta del usuario
- recopila el historial de chat actual
- envía la consulta, la búsqueda de Milvus y el historial de chat a ChatGPT
- Anexa el resultado de ChatGPT al historial de chat
- Devuelve el resultado al llamador
chat = (
pipe.input('collection_name', 'query', 'session')
.map('query', 'query_vec', ops.sentence_embedding.sbert(model_name=EMBED_MODEL))
.map('query_vec', 'query_vec', ops.np_normalize())
.map(('collection_name', 'query_vec'), 'search_res',
ops.ann_search.osschat_milvus(host=MILVUS_HOST,
port=MILVUS_PORT,
**{'metric_type': 'IP', 'limit': 3, 'output_fields': ['text']}))
.map('search_res', 'knowledge', lambda y: [x[2] for x in y])
.map(('collection_name', 'session'), 'history', ops.chat_message_histories.sql(method='get'))
.map(('query', 'knowledge', 'history'), 'messages', ops.prompt.question_answer())
.map('messages', 'answer', ops.LLM.OpenAI(api_key=OPENAI_API_KEY,
model_name='gpt-3.5-turbo',
temperature=0.8))
.map(('collection_name', 'session', 'query', 'answer'), 'new_history', ops.chat_message_histories.sql(method='add'))
.output('query', 'history', 'answer', )
)
Probemos esta canalización antes de conectarla a una GUI:
new_query = 'Where did Frodo take the ring?'
DataCollection(chat(COLLECTION_NAME, new_query, session_id)).show()
Aquí está la salida y los resultados en el notebook:
La canalización funciona. Preparemos una interfaz de Gradio.
GUI de Gradio
Primero, necesitas funciones para crear un identificador de sesión y para responder a las consultas desde la interfaz.
Estas funciones crean un ID de sesión usando un UUID, y aceptan una sesión y una consulta para la canalización de consultas.
import uuid
import io
def create_session_id():
uid = str(uuid.uuid4())
suid = ''.join(uid.split('-'))
return 'sess_' + suid
def respond(session, query):
res = chat(COLLECTION_NAME, query, session).get_dict()
answer = res['answer']
response = res['history']
response.append((query, answer))
return response
A continuación, la interfaz de Gradio usa estas funciones para crear un chatbot.
Usa la API Blocks para crear una interfaz de ChatBot. El botón Send Message usa la función respond para enviar solicitudes a ChatGPT.
import gradio as gr
with gr.Blocks() as demo:
session_id = gr.State(create_session_id)
with gr.Row():
with gr.Column(scale=2):
gr.Markdown('''## Chat''')
conversation = gr.Chatbot(label='conversation').style(height=300)
question = gr.Textbox(label='question', value=None)
send_btn = gr.Button('Send Message')
send_btn.click(
fn=respond,
inputs=[
session_id,
question
],
outputs=conversation,
)
demo.launch(server_name='127.0.0.1', server_port=8902)
Aquí está:
¡Ahora tienes un chatbot inteligente basado en LLM con Milvus!
Resumen
En esta publicación, creamos canalizaciones de Towhee para ingerir datos no estructurados, procesarlos para embeddings y almacenar esos embeddings en Milvus. Luego, creamos una canalización de consultas para la función de chat y conectamos el chatbot con un LLM. Finalmente, obtuvimos un chatbot inteligente.
Este tutorial demuestra lo fácil que es crear aplicaciones con Milvus. Milvus aporta numerosas ventajas cuando se integra en aplicaciones, especialmente aquellas que dependen del aprendizaje automático y la inteligencia artificial. Ofrece capacidades de búsqueda de similitud vectorial y análisis altamente eficientes, escalables y fiables, fundamentales en aplicaciones como chatbots, sistemas de recomendación y reconocimiento de imágenes o texto.
Esta publicación fue escrita por Eric Goebelbecker. Eric ha trabajado en los mercados financieros de la ciudad de Nueva York durante 25 años, desarrollando infraestructura para datos de mercado y redes del protocolo de intercambio de información financiera (FIX). Le encanta hablar sobre qué hace que los equipos sean eficaces (¡o no tan eficaces!).
Sigue leyendo

Introducing Customer-Managed Encryption Keys (CMEK) on Zilliz Cloud
We're announcing the general availability of Customer-Managed Encryption Keys (CMEK) on Zilliz Cloud.

Announcing the General Availability of Zilliz Cloud BYOC on Google Cloud Platform
Zilliz Cloud BYOC on GCP offers enterprise vector search with full data sovereignty and seamless integration.

8 Latest RAG Advancements Every Developer Should Know
Explore eight advanced RAG variants that can solve real problems you might be facing: slow retrieval, poor context understanding, multimodal data handling, and resource optimization.



