Bagikan melalui


Membuat dan mencatat agen AI

Penting

Fitur ini ada di Pratinjau Publik.

Artikel ini menunjukkan kepada Anda cara membuat dan mencatat agen AI seperti aplikasi RAG menggunakan Mosaic AI Agent Framework.

Apa itu rantai dan agen?

Sistem AI sering memiliki banyak komponen. Misalnya, sistem AI mungkin mengambil dokumen dari indeks vektor, menggunakan dokumen tersebut untuk melengkapi teks perintah, dan menggunakan model fondasi untuk meringkas respons. Kode yang menautkan komponen-komponen ini, juga disebut langkah-langkah, bersama-sama disebut rantai.

Agen adalah sistem AI yang jauh lebih canggih yang bergantung pada model bahasa besar untuk membuat keputusan tentang langkah-langkah mana yang harus diambil berdasarkan input. Sebaliknya, rantai adalah urutan langkah-langkah yang dikodekan secara permanen yang dimaksudkan untuk mencapai hasil tertentu.

Dengan Agent Framework, Anda dapat menggunakan pustaka atau paket apa pun untuk membuat kode. Agent Framework juga memudahkan untuk melakukan iterasi pada kode Saat Anda mengembangkan dan mengujinya. Anda dapat menyiapkan file konfigurasi yang memungkinkan Anda mengubah parameter kode dengan cara yang dapat dilacak tanpa harus mengubah kode aktual.

Persyaratan

Untuk agen yang menggunakan indeks pencarian vektor yang dikelola Databricks, mlflow versi 2.13.1 atau lebih tinggi diperlukan untuk menggunakan otorisasi otomatis dengan indeks vektor.

Skema input untuk agen RAG

Berikut ini adalah format input yang didukung untuk rantai Anda.

  • (Disarankan) Kueri menggunakan skema penyelesaian obrolan OpenAI. Ini harus memiliki array objek sebagai messages parameter. Format ini terbaik untuk aplikasi RAG.

    question = {
        "messages": [
            {
                "role": "user",
                "content": "What is Retrieval-Augmented Generation?",
            },
            {
                "role": "assistant",
                "content": "RAG, or Retrieval Augmented Generation, is a generative AI design pattern that combines a large language model (LLM) with external knowledge retrieval. This approach allows for real-time data connection to generative AI applications, improving their accuracy and quality by providing context from your data to the LLM during inference. Databricks offers integrated tools that support various RAG scenarios, such as unstructured data, structured data, tools & function calling, and agents.",
            },
            {
                "role": "user",
                "content": "How to build RAG for unstructured data",
            },
        ]
    }
    
  • SplitChatMessagesRequest. Direkomendasikan untuk aplikasi obrolan multi-giliran, terutama ketika Anda ingin mengelola kueri dan riwayat saat ini secara terpisah.

    {
    "query": "What is MLflow",
    "history": [
      {
      "role": "user",
      "content": "What is Retrieval-augmented Generation?"
      },
      {
      "role": "assistant",
      "content": "RAG is"
      }
      ]
    }
    

Untuk LangChain, Databricks merekomendasikan penulisan rantai Anda dalam Bahasa Ekspresi LangChain. Dalam kode definisi rantai, Anda dapat menggunakan itemgetter untuk mendapatkan pesan atau query objek history tergantung pada format input mana yang Anda gunakan.

Skema output untuk agen RAG

Kode Anda harus mematuhi salah satu format output yang didukung berikut:

  • (Disarankan) ChatCompletionResponse. Format ini direkomendasikan untuk pelanggan dengan interoperabilitas format respons OpenAI.
  • StringResponse. Format ini adalah kemudahan dan paling sederhana untuk ditafsirkan.

Untuk LangChain, gunakan StrOutputParser() sebagai langkah rantai terakhir Anda. Output Anda harus mengembalikan satu nilai string.

  chain = (
      {
          "user_query": itemgetter("messages")
          | RunnableLambda(extract_user_query_string),
          "chat_history": itemgetter("messages") | RunnableLambda(extract_chat_history),
      }
      | RunnableLambda(fake_model)
      | StrOutputParser()
  )

Jika Anda menggunakan PyFunc, Databricks merekomendasikan penggunaan petunjuk jenis untuk membuat anotasi predict() fungsi dengan kelas data input dan output yang merupakan subkelas kelas yang ditentukan dalam mlflow.models.rag_signatures.

Anda dapat membuat objek output dari kelas data di dalamnya predict() untuk memastikan format diikuti. Objek yang dikembalikan harus diubah menjadi representasi kamus untuk memastikan objek tersebut dapat diserialisasikan.

Menggunakan parameter untuk mengontrol perulangan kualitas

Dalam Kerangka Kerja Agen, Anda dapat menggunakan parameter untuk mengontrol bagaimana agen dijalankan. Ini memungkinkan Anda untuk dengan cepat melakukan iterasi dengan berbagai karakteristik agen Anda tanpa mengubah kode. Parameter adalah pasangan kunci-nilai yang Anda tentukan dalam kamus Python atau .yaml file.

Untuk mengonfigurasi kode, Anda membuat ModelConfig, sekumpulan parameter kunci-nilai. ModelConfig adalah kamus Python atau .yaml file. Misalnya, Anda dapat menggunakan kamus selama pengembangan lalu mengonversinya ke .yaml file untuk penyebaran produksi dan CI/CD. Untuk detail tentang ModelConfig, lihat dokumentasi MLflow.

Contoh ModelConfig ditunjukkan di bawah ini.

llm_parameters:
  max_tokens: 500
  temperature: 0.01
model_serving_endpoint: databricks-dbrx-instruct
vector_search_index: ml.docs.databricks_docs_index
prompt_template: 'You are a hello world bot. Respond with a reply to the user''s
  question that indicates your prompt template came from a YAML file. Your response
  must use the word "YAML" somewhere. User''s question: {question}'
prompt_template_input_vars:
- question

Untuk memanggil konfigurasi dari kode Anda, gunakan salah satu hal berikut:

# Example for loading from a .yml file
config_file = "configs/hello_world_config.yml"
model_config = mlflow.models.ModelConfig(development_config=config_file)

# Example of using a dictionary
config_dict = {
    "prompt_template": "You are a hello world bot. Respond with a reply to the user's question that is fun and interesting to the user. User's question: {question}",
    "prompt_template_input_vars": ["question"],
    "model_serving_endpoint": "databricks-dbrx-instruct",
    "llm_parameters": {"temperature": 0.01, "max_tokens": 500},
}

model_config = mlflow.models.ModelConfig(development_config=config_dict)

# Use model_config.get() to retrieve a parameter value
value = model_config.get('sample_param')

Catat agen

Pengelogan agen adalah dasar dari proses pengembangan. Pengelogan menangkap "titik waktu" kode dan konfigurasi agen sehingga Anda dapat mengevaluasi kualitas konfigurasi. Saat mengembangkan agen, Databricks merekomendasikan agar Anda menggunakan pengelogan berbasis kode alih-alih pengelogan berbasis serialisasi. Untuk informasi selengkapnya tentang pro dan kontra dari setiap jenis pengelogan, lihat Pengelogan berbasis kode vs. berbasis serialisasi.

Bagian ini mencakup cara menggunakan pengelogan berbasis kode. Untuk detail tentang cara menggunakan pengelogan berbasis serialisasi, lihat Alur kerja pengelogan berbasis serialisasi.

Alur kerja pengelogan berbasis kode

Untuk pengelogan berbasis kode, kode yang mencatat agen atau rantai Anda harus berada di notebook terpisah dari kode rantai Anda. Buku catatan ini disebut buku catatan driver. Untuk contoh buku catatan, lihat Contoh buku catatan.

Alur kerja pengelogan berbasis kode dengan LangChain

  1. Buat buku catatan atau file Python dengan kode Anda. Untuk tujuan contoh ini, buku catatan atau file diberi nama chain.py. Notebook atau file harus berisi rantai LangChain, yang disebut di sini sebagai lc_chain.
  2. Sertakan mlflow.models.set_model(lc_chain) dalam buku catatan atau file.
  3. Buat buku catatan baru untuk berfungsi sebagai buku catatan driver (dipanggil driver.py dalam contoh ini).
  4. Di buku catatan driver, sertakan panggilan mlflow.lang_chain.log_model(lc_model=”/path/to/chain.py”). Panggilan ini menjalankan chain.py dan mencatat hasil ke model MLflow.
  5. Sebarkan model.
  6. Ketika lingkungan penyajian dimuat, chain.py dijalankan.
  7. Ketika permintaan penyajian masuk, lc_chain.invoke(...) dipanggil.

Alur kerja pengelogan berbasis kode dengan PyFunc

  1. Buat buku catatan atau file Python dengan kode Anda. Untuk tujuan contoh ini, buku catatan atau file diberi nama chain.py. Buku catatan atau file harus berisi kelas PyFunc, yang disebut di sini sebagai PyFuncClass.
  2. Sertakan mlflow.models.set_model(PyFuncClass) dalam buku catatan atau file.
  3. Buat buku catatan baru untuk berfungsi sebagai buku catatan driver (dipanggil driver.py dalam contoh ini).
  4. Di buku catatan driver, sertakan panggilan mlflow.pyfunc.log_model(python_model=”/path/to/chain.py”). Panggilan ini menjalankan chain.py dan mencatat hasil ke model MLflow.
  5. Sebarkan model.
  6. Ketika lingkungan penyajian dimuat, chain.py dijalankan.
  7. Ketika permintaan penyajian masuk, PyFuncClass.predict(...) dipanggil.

Contoh kode untuk rantai pengelogan

import mlflow

code_path = "/Workspace/Users/first.last/chain.py"
config_path = "/Workspace/Users/first.last/config.yml"

input_example = {
    "messages": [
        {
            "role": "user",
            "content": "What is Retrieval-augmented Generation?",
        }
    ]
}

# example using LangChain
with mlflow.start_run():
  logged_chain_info = mlflow.langchain.log_model(
    lc_model=code_path,
    model_config=config_path, # If you specify this parameter, this is the configuration that is used for training the model. The development_config is overwritten.
    artifact_path="chain", # This string is used as the path inside the MLflow model where artifacts are stored
    input_example=input_example, # Must be a valid input to your chain
    example_no_conversion=True, # Required
  )

# or use a PyFunc model
# with mlflow.start_run():
#   logged_chain_info = mlflow.pyfunc.log_model(
#     python_model=chain_notebook_path,
#     artifact_path="chain",
#     input_example=input_example,
#     example_no_conversion=True,
#   )

print(f"MLflow Run: {logged_chain_info.run_id}")
print(f"Model URI: {logged_chain_info.model_uri}")

Untuk memverifikasi bahwa model telah dicatat dengan benar, muat rantai dan panggil invoke:

# Using LangChain
model = mlflow.langchain.load_model(logged_chain_info.model_uri)
model.invoke(example)

# Using PyFunc
model = mlflow.pyfunc.load_model(logged_chain_info.model_uri)
model.invoke(example)

Daftarkan rantai ke Katalog Unity

Sebelum menyebarkan rantai, Anda harus mendaftarkan rantai ke Unity Catalog. Saat Anda mendaftarkan rantai, rantai dimas sebagai model di Unity Catalog, dan Anda dapat menggunakan izin Katalog Unity untuk otorisasi sumber daya dalam rantai.

import mlflow

mlflow.set_registry_uri("databricks-uc")

catalog_name = "test_catalog"
schema_name = "schema"
model_name = "chain_name"

model_name = catalog_name + "." + schema_name + "." + model_name
uc_model_info = mlflow.register_model(model_uri=logged_chain_info.model_uri, name=model_name)

Contoh buku catatan

Notebook ini membuat rantai "Halo, dunia" sederhana untuk menggambarkan cara membuat aplikasi rantai di Databricks. Contoh pertama membuat rantai sederhana. Contoh notebook kedua menggambarkan cara menggunakan parameter untuk meminimalkan perubahan kode selama pengembangan.

Buku catatan rantai sederhana

Dapatkan buku catatan

Notebook driver rantai sederhana

Dapatkan buku catatan

Buku catatan rantai berparameter

Dapatkan buku catatan

Notebook driver rantai berparameter

Dapatkan buku catatan

Pengelogan berbasis kode vs. berbasis serialisasi

Untuk membuat dan mencatat rantai, Anda dapat menggunakan pengelogan MLflow berbasis kode atau pengelogan MLflow berbasis serialisasi. Databricks merekomendasikan agar Anda menggunakan pengelogan berbasis kode.

Dengan pengelogan MLflow berbasis Kode, kode rantai diambil sebagai file Python. Lingkungan Python ditangkap sebagai daftar paket. Ketika rantai disebarkan, lingkungan Python dipulihkan, dan kode rantai dijalankan untuk memuat rantai ke dalam memori sehingga dapat dipanggil ketika titik akhir dipanggil.

Dengan pengelogan MLflow berbasis Serialisasi, kode rantai dan status saat ini di lingkungan Python diserialisasikan ke disk, sering menggunakan pustaka seperti pickle atau joblib. Ketika rantai disebarkan, lingkungan Python dipulihkan, dan objek berseri dimuat ke dalam memori sehingga dapat dipanggil saat titik akhir dipanggil.

Tabel menunjukkan kelebihan dan kekurangan dari setiap metode.

Metode Kelebihan Kerugian
Pengelogan MLflow berbasis kode * Mengatasi batasan serialisasi yang melekat, yang tidak didukung oleh banyak pustaka GenAI populer.
* Menyimpan salinan kode asli untuk referensi nanti.
* Tidak perlu merestrukturisasi kode Anda menjadi satu objek yang dapat diserialisasikan.
log_model(...) harus dipanggil dari notebook yang berbeda dari kode rantai (disebut notebook driver).
Pengelogan MLflow berbasis serialisasi log_model(...) dapat dipanggil dari notebook yang sama tempat model ditentukan. * Kode asli tidak tersedia.
* Semua pustaka dan objek yang digunakan dalam rantai harus mendukung serialisasi.

Alur kerja pengelogan berbasis serialisasi

Databricks merekomendasikan agar Anda menggunakan pengelogan berbasis kode alih-alih pengelogan berbasis serialisasi. Untuk detail tentang cara menggunakan pengelogan berbasis kode, lihat Alur kerja pengelogan berbasis kode.

Bagian ini menjelaskan cara menggunakan pengelogan berbasis serialisasi.

Alur kerja pengelogan berbasis serialisasi dengan LangChain

  1. Buat buku catatan atau file Python dengan kode Anda. Notebook atau file harus berisi rantai LangChain, yang disebut di sini sebagai lc_chain.
  2. Sertakan mlflow.lang_chain.log_model(lc_model=lc_chain) dalam buku catatan atau file.
  3. Salinan PyFuncClass() serial dicatat ke Model MLflow.
  4. Sebarkan model.
  5. Ketika lingkungan penyajian dimuat, PyFuncClass diserialisasikan.
  6. Ketika permintaan penyajian masuk, lc_chain.invoke(...) dipanggil.

Alur kerja pengelogan berbasis serialisasi dengan PyFunc

  1. Buat buku catatan atau file Python dengan kode Anda. Untuk tujuan contoh ini, buku catatan atau file diberi nama notebook.py. Buku catatan atau file harus berisi kelas PyFunc, yang disebut di sini sebagai PyFuncClass.
  2. Sertakan mlflow.pyfunc.log_model(python_model=PyFuncClass()) dalam notebook.py.
  3. Salinan PyFuncClass() serial dicatat ke Model MLflow.
  4. Sebarkan model.
  5. Ketika lingkungan penyajian dimuat, PyFuncClass diserialisasikan.
  6. Ketika permintaan penyajian masuk, PyFuncClass.predict(...) dipanggil.