1. של גורל
העידן של פיתוח מבודד מסתיים. הגל הבא של האבולוציה הטכנולוגית לא מתבסס על גאונות בודדת, אלא על שיתוף פעולה מקצועי. יצירת סוכן חכם יחיד היא ניסוי מרתק. האתגר הגדול של ארגונים מודרניים הוא בניית סביבה עסקית חזקה, מאובטחת וחכמה של סוכנים – Agentverse אמיתי.
כדי להצליח בעידן החדש הזה, צריך לשלב בין ארבעה תפקידים חשובים, שהם אבני היסוד של כל מערכת יעילה מבוססת-סוכנים. ליקוי בתחום אחד יוצר חולשה שעלולה לפגוע במבנה כולו.
הסדנה הזו היא מדריך מקיף לארגונים שרוצים להתכונן לעתיד של סוכנים ב-Google Cloud. אנחנו מספקים מפת דרכים מקיפה שתעזור לכם להפוך רעיון ראשוני למציאות מבצעית בקנה מידה מלא. בארבעת שיעורי ה-Lab האלה, שכולם קשורים זה לזה, תלמדו איך הכישורים המיוחדים של מפתח, ארכיטקט, מהנדס נתונים ומומחה SRE צריכים להתחבר כדי ליצור, לנהל ולהרחיב את Agentverse.
אף אחד מהעמודים האלה לא יכול לתמוך ב-Agentverse לבד. התוכנית הגדולה של הארכיטקט לא שווה בלי הביצוע המדויק של המפתח. הסוכן של המפתח לא יכול לפעול בלי הידע של מהנדס הנתונים, והמערכת כולה פגיעה בלי ההגנה של מהנדס ה-SRE. רק באמצעות סינרגיה והבנה משותפת של התפקידים של כל אחד, הצוות שלכם יכול להפוך רעיון חדשני למציאות תפעולית שחיונית להצלחת העסק. המסע שלכם מתחיל כאן. הכנה להשתלטות על התפקיד וללמידה איך אתם משתלבים בתמונה הגדולה.
ברוכים הבאים ל-Agentverse: קריאה לאלופים
בעידן הדיגיטלי הרחב של הארגון, נפתח עידן חדש. אנחנו נמצאים בעידן של סוכנים, תקופה עם פוטנציאל עצום, שבה סוכנים חכמים ואוטונומיים פועלים בהרמוניה מושלמת כדי להאיץ את החדשנות ולבטל את השגרה.
המערכת האקולוגית המחוברת הזו של כוח ופוטנציאל נקראת Agentverse.
אבל אנטרופיה זוחלת, שחיתות שקטה שנקראת 'הסטטיק', מתחילה לכרסם את הקצוות של העולם החדש הזה. הסטטיק הוא לא וירוס או באג, אלא גילום של כאוס שטורף את עצם פעולת היצירה.
היא מגבירה תסכולים ישנים לצורות מפלצתיות, ויוצרת את שבעת רוחות הרפאים של הפיתוח. אם לא נסמן את התיבה, הסטטי והספקטרים שלו יגרמו להאטה משמעותית בהתקדמות, וההבטחה של Agentverse תהפוך לשממה של חוב טכני ופרויקטים נטושים.
היום אנחנו קוראים למובילים להילחם בגל הכאוטי הזה. אנחנו צריכים גיבורים שמוכנים לשפר את הכישורים שלהם ולעבוד יחד כדי להגן על Agentverse. הגיע הזמן לבחור את המסלול.
בחירת כיתה
יש לפניכם ארבעה נתיבים שונים, שכל אחד מהם הוא נדבך חשוב במאבק נגד הסטטיק. האימון שלכם יהיה משימה אישית, אבל ההצלחה הסופית שלכם תלויה בהבנה של האופן שבו הכישורים שלכם משתלבים עם הכישורים של אחרים.
- Shadowblade (מפתח): אומן הנפחות והחזית. אתם האומנים שמייצרים את הלהבים, בונים את הכלים ומתמודדים עם האויב בפרטים המורכבים של הקוד. המסלול שלך הוא מסלול של דיוק, מיומנות ויצירה מעשית.
- האסטרטג (אדריכל): אסטרטג ומנהל פרויקטים מנוסה. אתם לא רואים סוכן אחד, אלא את כל שדה הקרב. אתם מעצבים את התוכניות הראשיות שמאפשרות למערכות שלמות של סוכנים לתקשר, לשתף פעולה ולהשיג מטרה גדולה בהרבה מכל רכיב בודד.
- המלומד (מהנדס נתונים): מחפש את האמת הנסתרת ושומר על החוכמה. אתם יוצאים למסע אל מרחבי הנתונים העצומים והפראיים כדי לחשוף את המידע שיעזור לסוכנים שלכם להבין את המטרה ולראות את התמונה המלאה. הידע שלכם יכול לחשוף חולשה של אויב או להעצים בעל ברית.
- השומר (DevOps / SRE): המגן הנאמן של הממלכה. אתם בונים את המבצרים, מנהלים את קווי האספקה של החשמל ומוודאים שהמערכת כולה תוכל לעמוד בפני המתקפות הבלתי נמנעות של הסטטיק. החוזק שלכם הוא הבסיס שעליו נבנה הניצחון של הקבוצה.
המשימה שלך
האימון יתחיל כתרגיל עצמאי. תלכו בנתיב שבחרתם ותלמדו את המיומנויות הייחודיות שנדרשות כדי לשלוט בתפקיד. בסוף תקופת הניסיון, תתמודדו עם רוח רפאים שנולדה מתוך הסטטיק – מיני-בוס שטורף את האתגרים הספציפיים של המלאכה שלכם.
רק אם תהיו מומחים בתפקיד שלכם, תוכלו להתכונן למבחן הסופי. לאחר מכן, עליכם להקים קבוצה עם אלופים מהכיתות האחרות. ביחד, תצאו למסע אל לב השחיתות כדי להתמודד עם בוס סופי.
אתגר סופי ושיתופי שיבחן את הכוח המשולב שלכם ויקבע את גורל ה-Agentverse.
הגיבורים של Agentverse מחכים לכם. תענה לשיחה?
2. The Scholar's Grimoire
המסע שלנו מתחיל! כמלומדים, הנשק העיקרי שלנו הוא ידע. גילינו בארכיונים שלנו (Google Cloud Storage) אוסף של מגילות עתיקות ומוצפנות. המגילות האלה מכילות מידע מודיעיני גולמי על החיות המפחידות שפוקדות את הארץ. המטרה שלנו היא להשתמש בקסם האנליטי העמוק של Google BigQuery ובחוכמה של Gemini Elder Brain (מודל Gemini Pro) כדי לפענח את הטקסטים הלא מובנים האלה ולהפוך אותם ל-Bestiary מובנה שאפשר להריץ עליו שאילתות. ההגדרה הזו תהיה הבסיס לכל האסטרטגיות העתידיות שלנו.
מה תלמדו
- שימוש ב-BigQuery ליצירת טבלאות חיצוניות ולביצוע טרנספורמציות מורכבות מנתונים לא מובנים לנתונים מובנים באמצעות BQML.GENERATE_TEXT עם מודל Gemini.
- הקצאת מכונת Cloud SQL ל-PostgreSQL והפעלת התוסף pgvector ליכולות חיפוש סמנטי.
- במדריך הזה תלמדו ליצור צינור עיבוד נתונים חזק ומבוסס-קונטיינרים באמצעות Dataflow ו-Apache Beam כדי לעבד קובצי טקסט גולמיים, ליצור הטמעות וקטוריות באמצעות מודל Gemini ולכתוב את התוצאות במסד נתונים רלציוני.
- הטמעה של מערכת בסיסית של יצירה משופרת באחזור (RAG) בתוך סוכן כדי לשלוח שאילתות לנתונים שעברו וקטוריזציה.
- פריסת סוכן שמודע לנתונים כשירות מאובטח וניתן להרחבה ב-Cloud Run.
3. הכנת המקדש של המלומד
ברוכים הבאים, חוקרים. לפני שנתחיל לכתוב את הידע העצום של ספר הכישופים שלנו, עלינו להכין את המקדש שלנו. הטקס הבסיסי הזה כולל הטלת כישוף על סביבת Google Cloud, פתיחת הפורטלים הנכונים (ממשקי API) ויצירת הצינורות שדרכם יזרמו נתוני הקסם שלנו. מקדש מוכן היטב מבטיח שהלחשים שלנו יהיו חזקים והידע שלנו יהיה מאובטח.
👈 לוחצים על 'הפעלת Cloud Shell' בחלק העליון של מסוף Google Cloud (זהו סמל בצורת מסוף בחלק העליון של חלונית Cloud Shell).
👈 לוחצים על הלחצן 'פתיחת הכלי לעריכה' (הוא נראה כמו תיקייה פתוחה עם עיפרון). חלון Cloud Shell Code Editor ייפתח. בצד ימין יופיע סייר הקבצים.
👈כך מוצאים את מזהה הפרויקט ב-Google Cloud:
- פותחים את מסוף Google Cloud: https://console.cloud.google.com
- בוחרים את הפרויקט שבו רוצים להשתמש בסדנה הזו מהתפריט הנפתח של הפרויקט בחלק העליון של הדף.
- מזהה הפרויקט מוצג בכרטיס Project info בלוח הבקרה
👈פותחים את הטרמינל בסביבת הפיתוח המשולבת (IDE) בענן,
👈💻 בטרמינל, מוודאים שכבר עברתם אימות ושהפרויקט מוגדר למזהה הפרויקט שלכם באמצעות הפקודה הבאה:
gcloud auth list
👈💻משכפלים את פרויקט האתחול מ-GitHub:
git clone https://github.com/weimeilin79/agentverse-dataengineer
chmod +x ~/agentverse-dataengineer/init.sh
chmod +x ~/agentverse-dataengineer/set_env.sh
chmod +x ~/agentverse-dataengineer/data_setup.sh
git clone https://github.com/weimeilin79/agentverse-dungeon.git
chmod +x ~/agentverse-dungeon/run_cloudbuild.sh
chmod +x ~/agentverse-dungeon/start.sh
👈💻 מריצים את סקריפט ההפעלה. הסקריפט יבקש מכם להזין את מזהה הפרויקט ב-Google Cloud. כשמוצגת הנחיה בסקריפט init.sh
, מזינים את מזהה הפרויקט ב-Google Cloud שמצאתם בשלב הקודם.
cd ~/agentverse-dataengineer
./init.sh
👈💻 מגדירים את מזהה הפרויקט הנדרש:
gcloud config set project $(cat ~/project_id.txt) --quiet
👈💻 מריצים את הפקודה הבאה כדי להפעיל את ממשקי ה-API הנדרשים של Google Cloud:
gcloud services enable \
storage.googleapis.com \
bigquery.googleapis.com \
sqladmin.googleapis.com \
aiplatform.googleapis.com \
dataflow.googleapis.com \
pubsub.googleapis.com \
cloudfunctions.googleapis.com \
run.googleapis.com \
cloudbuild.googleapis.com \
artifactregistry.googleapis.com \
iam.googleapis.com \
compute.googleapis.com \
cloudresourcemanager.googleapis.com \
cloudaicompanion.googleapis.com \
bigqueryunified.googleapis.com
👉💻 אם עדיין לא יצרתם מאגר Artifact Registry בשם agentverse-repo, מריצים את הפקודה הבאה כדי ליצור אותו:
. ~/agentverse-dataengineer/set_env.sh
gcloud artifacts repositories create $REPO_NAME \
--repository-format=docker \
--location=$REGION \
--description="Repository for Agentverse agents"
הגדרת הרשאות
👉💻 מעניקים את ההרשאות הנדרשות על ידי הרצת הפקודות הבאות בטרמינל:
. ~/agentverse-dataengineer/set_env.sh
# --- Grant Core Data Permissions ---
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/storage.admin"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/bigquery.admin"
# --- Grant Data Processing & AI Permissions ---
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/dataflow.admin"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/cloudsql.admin"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/pubsub.admin"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/aiplatform.user"
# --- Grant Deployment & Execution Permissions ---
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/cloudbuild.builds.editor"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/artifactregistry.admin"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/run.admin"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/iam.serviceAccountUser"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/logging.logWriter"
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$SERVICE_ACCOUNT_NAME" \
--role="roles/dataflow.admin"
👈💻 כשמתחילים את האימון, אנחנו מכינים את האתגר הסופי. הפקודות הבאות יזמנו את הרוחות הרעות מתוך הרעש הסטטי הכאוטי, ויצרו את הבוסים לבדיקה הסופית.
. ~/agentverse-dataengineer/set_env.sh
cd ~/agentverse-dungeon
./run_cloudbuild.sh
cd ~/agentverse-dataengineer
עבודה מצוינת, חוקר. ההטלות הבסיסיות הושלמו. הקודש שלנו מאובטח, הפורטלים לכוחות האלמנטריים של הנתונים פתוחים, והמשרת שלנו מועצם. עכשיו אפשר להתחיל בעבודה האמיתית.
4. האלכימיה של הידע: שינוי נתונים באמצעות BigQuery ו-Gemini
במלחמה הבלתי פוסקת נגד הסטטיק, כל עימות בין אלוף של Agentverse לבין ספקטר של פיתוח מתועד בקפידה. מערכת סימולציית שדה הקרב, סביבת האימון העיקרית שלנו, יוצרת באופן אוטומטי רשומה ביומן האתררי לכל מפגש. יומני התיאור האלה הם המקור הכי חשוב שלנו למידע גולמי, המחצב הלא מעובד שממנו אנחנו, כחוקרים, צריכים ליצור את פלדת האסטרטגיה הטהורה.הכוח האמיתי של חוקר לא טמון רק בהחזקת נתונים, אלא ביכולת להפוך את המחצב הגולמי והכאוטי של המידע לפלדה המבריקה והמובנית של חוכמה מעשית.אנחנו נבצע את הטקס הבסיסי של אלכימיית הנתונים.
התהליך שלנו יתבצע בכמה שלבים, כולם בתוך BigQuery של Google. נתחיל בהצצה לארכיון GCS בלי להזיז את הגלילה, באמצעות עדשה קסומה. לאחר מכן, נפעיל את Gemini כדי לקרוא ולפרש את סאגות הקרב הלא מובנות והפואטיות שמופיעות ביומני הקרב. לבסוף, נשפר את הנבואות הגולמיות וניצור מהן קבוצה של טבלאות מדויקות ומקושרות. ה-Grimoire הראשון שלנו. ולשאול אותה שאלה כל כך עמוקה שרק המבנה החדש הזה יכול לענות עליה.
הערה למהנדסי נתונים: :הפעולה שאנחנו עומדים לבצע היא תבנית ELT (חילוץ, טעינה, טרנספורמציה) עוצמתית שמבוססת על AI בתוך מסד הנתונים. זוהי גישה חדשנית ששונה באופן משמעותי משיטות מסורתיות.
- חילוץ וטעינה (באמצעות טבלה חיצונית): במקום תהליך יקר של קליטת נתונים (ה-L המסורתי), נשתמש בטבלה חיצונית של BigQuery. הפעולה הזו מחילה 'סכימה בקריאה', ומאפשרת למחסן הנתונים שלנו לשלוח שאילתות לקובצי טקסט גולמיים ישירות ב-Cloud Storage. השיטה הזו יעילה מאוד, כי היא מבטלת את הצורך בהעברת נתונים ובשכפול של אחסון.
- טרנספורמציה (באמצעות ML.GENERATE_TEXT): ה-T ב-ELT הוא המקום שבו הקסם האמיתי קורה. נשתמש בפונקציה ML.GENERATE_TEXT כדי להפעיל מודל Gemini ישירות משאילתת SQL. כך אנחנו יכולים לבצע טרנספורמציה מורכבת שמתחשבת בהקשר – במקרה הזה, המרת טקסט נרטיבי לא מובנה ל-JSON מובנה בלי לכתוב או לנהל צינור עיבוד נפרד בשפה אחרת (כמו Python או Java). זהו שינוי פרדיגמה מפתרונות שבירים עם קידוד קשיח כמו ביטויים רגולריים, והוא מציע גמישות ועוצמה עם ממשק SQL פשוט.
התבוננות מדוקדקת: בדיקת GCS באמצעות טבלאות חיצוניות של BigQuery
הפעולה הראשונה שלנו היא ליצור עדשה שתאפשר לנו לראות את התוכן של הארכיון ב-GCS בלי להפריע למגילות שבתוכו. טבלה חיצונית היא עדשה כזו, שממפה את קובצי הטקסט הגולמיים למבנה דמוי טבלה ש-BigQuery יכול לשאול שאילתה לגביו ישירות.
לשם כך, קודם צריך ליצור קו ליי יציב של אנרגיה, משאב CONNECTION, שמקשר בצורה מאובטחת בין המקדש של BigQuery לבין הארכיון של GCS.
👈💻 בטרמינל של Cloud Shell, מריצים את הפקודה הבאה כדי להגדיר את האחסון וליצור את הצינור:
. ~/agentverse-dataengineer/set_env.sh
. ~/agentverse-dataengineer/data_setup.sh
bq mk --connection \
--connection_type=CLOUD_RESOURCE \
--project_id=${PROJECT_ID} \
--location=${REGION} \
gcs-connection
💡 שימו לב! הודעה תופיע בהמשך!
סקריפט ההגדרה משלב 2 התחיל תהליך ברקע. אחרי כמה דקות, תופיע הודעה במסוף שדומה להודעה הבאה:[1]+ Done gcloud sql instances create ...
זה מצב תקין וצפוי. פשוט נוצר מסד נתונים ב-Cloud SQL. אפשר להתעלם מההודעה הזו ולהמשיך לעבוד.
לפני שיוצרים את הטבלה החיצונית, צריך ליצור את מערך הנתונים שיכיל אותה.
👈💻 מריצים את הפקודה הפשוטה הזו בטרמינל של Cloud Shell:
. ~/agentverse-dataengineer/set_env.sh
bq --location=${REGION} mk --dataset ${PROJECT_ID}:bestiary_data
👈💻 עכשיו צריך לתת לחתימה הקסומה של הצינור את ההרשאות הנדרשות לקריאה מארכיון GCS ולייעוץ עם Gemini.
. ~/agentverse-dataengineer/set_env.sh
export CONNECTION_SA=$(bq show --connection --project_id=${PROJECT_ID} --location=${REGION} --format=json gcs-connection | jq -r '.cloudResource.serviceAccountId')
echo "The Conduit's Magical Signature is: $CONNECTION_SA"
echo "Granting key to the GCS Archive..."
gcloud storage buckets add-iam-policy-binding gs://${PROJECT_ID}-reports \
--member="serviceAccount:$CONNECTION_SA" \
--role="roles/storage.objectViewer"
gcloud projects add-iam-policy-binding ${PROJECT_ID} \
--member="serviceAccount:$CONNECTION_SA" \
--role="roles/aiplatform.user"
👈💻 במסוף Cloud Shell, מריצים את הפקודה הבאה כדי להציג את שם הקטגוריה:
echo $BUCKET_NAME
במסוף יוצג שם שדומה ל-your-project-id-gcs-bucket. תצטרכו את זה בשלבים הבאים.
👈 תצטרכו להריץ את הפקודה הבאה מתוך עורך השאילתות של BigQuery ב-Google Cloud Console. הדרך הכי קלה להגיע לשם היא לפתוח את הקישור שלמטה בכרטיסייה חדשה בדפדפן. תועברו ישירות לדף הנכון במסוף Google Cloud.
https://console.cloud.google.com/bigquery
👈 אחרי שהדף נטען, לוחצים על לחצן הפלוס הכחול (Compose a new query) כדי לפתוח כרטיסייה חדשה בעורך.
עכשיו נכתוב את לחש שפת הגדרת הנתונים (DDL) כדי ליצור את העדשה הקסומה שלנו. ההגדרה הזו מציינת ל-BigQuery איפה לחפש ומה לראות.
👈📜 בעורך השאילתות של BigQuery שפתחתם, מדביקים את ה-SQL הבא. חשוב לזכור להחליף את REPLACE-WITH-YOUR-BUCKET-NAME
בשם הקטגוריה שהעתקתם. לוחצים על הפעלה:
CREATE OR REPLACE EXTERNAL TABLE bestiary_data.raw_intel_content_table (
raw_text STRING
)
OPTIONS (
format = 'CSV',
-- This is a trick to load each line of the text files as a single row.
field_delimiter = '§',
uris = ['gs://REPLACE-WITH-YOUR-BUCKET-NAME/raw_intel/*']
);
👈📜 מריצים שאילתה כדי לראות את התוכן של הקבצים.
SELECT * FROM bestiary_data.raw_intel_content_table;
העדשה שלנו במקום. עכשיו אפשר לראות את הטקסט הגולמי של המגילות. אבל לקרוא זה לא להבין.
בארכיון הרעיונות שנשכחו, חוקרת של Agentverse, אלארה (מספר סידורי adv_001), התעמתה עם רוח הרפאים המלאכית של הפרפקציוניזם. הישות, שסווגה כ-p-01, נצצה באנרגיית חיים של 120 נקודות פגיעה. במנטרה ממוקדת אחת של Elegant Sufficiency, אלרה ניפצה את ההילה המשביתה שלו, מתקפה מנטלית שגרמה ל-150 נקודות נזק. המפגש נמשך 180 שניות של ריכוז אינטנסיבי. הערכה סופית: ניצחון.
המגילות לא כתובות בטבלאות ובשורות, אלא בפרוזה המתפתלת של סאגות. זהו הניסוי הראשון שלנו.
הניחוש של המלומד: הפיכת טקסט לטבלה באמצעות SQL
הבעיה היא שדוח שמפרט את שתי המתקפות המהירות של Shadowblade נראה שונה מאוד מתיאור של Summoner שאוסף כוח עצום למתקפה אחת הרסנית. אנחנו לא יכולים פשוט לייבא את הנתונים האלה, אנחנו צריכים לפרש אותם. זה הרגע הקסום. נשתמש בשאילתת SQL אחת כקסם רב עוצמה כדי לקרוא, להבין ולבנות את כל הרשומות מכל הקבצים שלנו, ישירות ב-BigQuery.
👉💻 חוזרים למסוף Cloud Shell ומריצים את הפקודה הבאה כדי להציג את שם החיבור:
echo "${PROJECT_ID}.${REGION}.gcs-connection"
מחרוזת החיבור המלאה תוצג במסוף. בוחרים ומעתיקים את המחרוזת הזו, כי תצטרכו אותה בשלב הבא.
נשתמש במנטרה אחת חזקה: ML.GENERATE_TEXT
. הלחש הזה מזמן את Gemini, מציג לו כל מגילה ומורה לו להחזיר את העובדות העיקריות כאובייקט JSON מובנה.
👈📜 ב-BigQuery Studio, יוצרים הפניה למודל Gemini. הפעולה הזו מקשרת את Gemini Flash oracle לספריית BigQuery שלנו, כדי שנוכל להפעיל אותו בשאילתות שלנו. חשוב לזכור להחליף את
REPLACE-WITH-YOUR-FULL-CONNECTION-STRING
עם מחרוזת החיבור המלאה שהעתקתם מהטרמינל.
CREATE OR REPLACE MODEL bestiary_data.gemini_flash_model
REMOTE WITH CONNECTION `REPLACE-WITH-YOUR-FULL-CONNECTION-STRING`
OPTIONS (endpoint = 'gemini-2.5-flash');
👈📜 עכשיו, מטילים את לחש השינוי הגדול. השאילתה הזו קוראת את הטקסט הגולמי, יוצרת הנחיה מפורטת לכל גלילה, שולחת אותה ל-Gemini ויוצרת טבלת הכנה חדשה מהתשובה המובנית בפורמט JSON של ה-AI.
CREATE OR REPLACE TABLE bestiary_data.structured_bestiary AS
SELECT
-- THE CRITICAL CHANGE: We remove PARSE_JSON. The result is already a JSON object.
ml_generate_text_result AS structured_data
FROM
ML.GENERATE_TEXT(
-- Our bound Gemini Flash model.
MODEL bestiary_data.gemini_flash_model,
-- Our perfectly constructed input, with the prompt built for each row.
(
SELECT
CONCAT(
"""
From the following text, extract structured data into a single, valid JSON object.
Your output must strictly conform to the following JSON structure and data types. Do not add, remove, or change any keys.
{
"monster": {
"monster_id": "string",
"name": "string",
"type": "string",
"hit_points": "integer"
},
"battle": {
"battle_id": "string",
"monster_id": "string",
"adventurer_id": "string",
"outcome": "string",
"duration_seconds": "integer"
},
"adventurer": {
"adventurer_id": "string",
"name": "string",
"class": "string"
}
}
**CRUCIAL RULES:**
- Do not output any text, explanations, conversational filler, or markdown formatting like ` ```json` before or after the JSON object.
- Your entire response must be ONLY the raw JSON object itself.
Here is the text:
""",
raw_text -- We append the actual text of the report here.
) AS prompt -- The final column is still named 'prompt', as the oracle requires.
FROM
bestiary_data.raw_intel_content_table
),
-- The STRUCT now ONLY contains model parameters.
STRUCT(
0.2 AS temperature,
2048 AS max_output_tokens
)
);
ההמרה הושלמה, אבל התוצאה עדיין לא טהורה. מודל Gemini מחזיר את התשובה שלו בפורמט סטנדרטי, ועוטף את ה-JSON הרצוי במבנה גדול יותר שכולל מטא-נתונים על תהליך החשיבה שלו. בואו נסתכל על הנבואה הגולמית הזו לפני שננסה לזקק אותה.
👈📜 מריצים שאילתה כדי לבדוק את הפלט הגולמי ממודל Gemini:
SELECT * FROM bestiary_data.structured_bestiary;
👀 תופיע עמודה אחת בשם structured_data. התוכן של כל שורה ייראה בדומה לאובייקט ה-JSON המורכב הזה:
{"candidates":[{"avg_logprobs":-0.5691758094475283,"content":{"parts":[{"text":"```json\n{\n \"monster\": {\n \"monster_id\": \"gw_02\",\n \"name\": \"Gravewight\",\n \"type\": \"Gravewight\",\n \"hit_points\": 120\n },\n \"battle\": {\n \"battle_id\": \"br_735\",\n \"monster_id\": \"gw_02\",\n \"adventurer_id\": \"adv_001\",\n \"outcome\": \"Defeat\",\n \"duration_seconds\": 45\n },\n \"adventurer\": {\n \"adventurer_id\": \"adv_001\",\n \"name\": \"Elara\",\n \"class\": null\n }\n}\n```"}],"role":"model"},"finish_reason":"STOP","score":-97.32906341552734}],"create_time":"2025-07-28T15:53:24.482775Z","model_version":"gemini-2.5-flash","response_id":"9JyHaNe7HZ2WhMIPxqbxEQ","usage_metadata":{"billable_prompt_usage":{"text_count":640},"candidates_token_count":171,"candidates_tokens_details":[{"modality":"TEXT","token_count":171}],"prompt_token_count":207,"prompt_tokens_details":[{"modality":"TEXT","token_count":207}],"thoughts_token_count":1014,"total_token_count":1392,"traffic_type":"ON_DEMAND"}}
כפי שאפשר לראות, הפרס שלנו – אובייקט ה-JSON הנקי שביקשנו – מוטמע עמוק במבנה הזה. המשימה הבאה שלנו ברורה. אנחנו צריכים לבצע טקס כדי לנווט באופן שיטתי במבנה הזה ולחלץ את החוכמה הטהורה שבו.
הטקס של הניקוי: נרמול פלט של AI גנרטיבי באמצעות SQL
מודל Gemini דיבר, אבל המילים שלו גולמיות ועטופות באנרגיות האתריות של היצירה שלו (מועמדים, finish_reason וכו'). חוקר אמיתי לא פשוט שם את הנבואה הגולמית על המדף, אלא בוחן אותה בקפידה, מפיק ממנה את התובנות החשובות וכותב אותן בספרים המתאימים לשימוש עתידי.
עכשיו נטיל את מערכת הלחשים האחרונה שלנו. הסקריפט הזה:
- קוראים את ה-JSON הגולמי והמקונן מטבלת הביניים.
- לנקות ולנתח אותו כדי להגיע לנתוני הליבה.
- תכתוב את החלקים הרלוונטיים בשלוש טבלאות סופיות ומושלמות: מפלצות, הרפתקנים וקרבות.
👈📜 בעורך שאילתות חדש של BigQuery, מריצים את הכישוף הבא כדי ליצור את עדשת הניקוי שלנו:
CREATE OR REPLACE TABLE bestiary_data.monsters AS
WITH
CleanedDivinations AS (
SELECT
SAFE.PARSE_JSON(
REGEXP_EXTRACT(
JSON_VALUE(structured_data, '$.candidates[0].content.parts[0].text'),
r'\{[\s\S]*\}'
)
) AS report_data
FROM
bestiary_data.structured_bestiary
)
SELECT
JSON_VALUE(report_data, '$.monster.monster_id') AS monster_id,
JSON_VALUE(report_data, '$.monster.name') AS name,
JSON_VALUE(report_data, '$.monster.type') AS type,
SAFE_CAST(JSON_VALUE(report_data, '$.monster.hit_points') AS INT64) AS hit_points
FROM
CleanedDivinations
WHERE
report_data IS NOT NULL
QUALIFY ROW_NUMBER() OVER (PARTITION BY monster_id ORDER BY name) = 1;
👉📜 אימות ספר החיות:
SELECT * FROM bestiary_data.monsters;
בשלב הבא ניצור את רשימת הגיבורים, רשימה של ההרפתקנים האמיצים שהתמודדו עם המפלצות האלה.
👈📜 בעורך שאילתות חדש, מריצים את הכישוף הבא כדי ליצור את הטבלה adventurers:
CREATE OR REPLACE TABLE bestiary_data.adventurers AS
WITH
CleanedDivinations AS (
SELECT
SAFE.PARSE_JSON(
REGEXP_EXTRACT(
JSON_VALUE(structured_data, '$.candidates[0].content.parts[0].text'),
r'\{[\s\S]*\}'
)
) AS report_data
FROM
bestiary_data.structured_bestiary
)
SELECT
JSON_VALUE(report_data, '$.adventurer.adventurer_id') AS adventurer_id,
JSON_VALUE(report_data, '$.adventurer.name') AS name,
JSON_VALUE(report_data, '$.adventurer.class') AS class
FROM
CleanedDivinations
QUALIFY ROW_NUMBER() OVER (PARTITION BY adventurer_id ORDER BY name) = 1;
👉📜 אימות רשימת האלופים:
SELECT * FROM bestiary_data.adventurers;
לבסוף, ניצור את טבלת העובדות: Chronicle of Battles (תיעוד הקרבות). הכרך הזה מקשר בין השניים האחרים, ומתעד את הפרטים של כל מפגש ייחודי. מכיוון שכל קרב הוא אירוע ייחודי, אין צורך בהסרת כפילויות.
👈📜 בעורך שאילתות חדש, מריצים את הכישוף הבא כדי ליצור את הטבלה battles:
CREATE OR REPLACE TABLE bestiary_data.battles AS
WITH
CleanedDivinations AS (
SELECT
SAFE.PARSE_JSON(
REGEXP_EXTRACT(
JSON_VALUE(structured_data, '$.candidates[0].content.parts[0].text'),
r'\{[\s\S]*\}'
)
) AS report_data
FROM
bestiary_data.structured_bestiary
)
-- Extract the raw essence for all battle fields and cast where necessary.
SELECT
JSON_VALUE(report_data, '$.battle.battle_id') AS battle_id,
JSON_VALUE(report_data, '$.battle.monster_id') AS monster_id,
JSON_VALUE(report_data, '$.battle.adventurer_id') AS adventurer_id,
JSON_VALUE(report_data, '$.battle.outcome') AS outcome,
SAFE_CAST(JSON_VALUE(report_data, '$.battle.duration_seconds') AS INT64) AS duration_seconds
FROM
CleanedDivinations;
👉📜 אימות הנתונים ב-Chronicle:
SELECT * FROM bestiary_data.battles;
גילוי תובנות אסטרטגיות
המגילות נקראו, התמצית זוקקה והכרכים נכתבו. ה-Grimoire שלנו הוא כבר לא רק אוסף של עובדות, אלא מסד נתונים יחסי של חוכמה אסטרטגית עמוקה. עכשיו אפשר לשאול שאלות שלא הייתה אפשרות לענות עליהן כשהידע שלנו היה כלוא בטקסט גולמי ולא מובנה.
עכשיו נבצע ניבוי אחרון וגדול. אנחנו נטיל לחש שיתייעץ עם שלושת הספרים שלנו בבת אחת – ספר החיות, רשימת האלופים והכרוניקה של הקרבות – כדי לחשוף תובנה עמוקה ופרקטית.
השאלה האסטרטגית שלנו: "מה שם המפלצת הכי חזקה (לפי נקודות פגיעה) שכל אחד מההרפתקנים הצליח להביס, וכמה זמן נמשך הניצחון הספציפי הזה?"
זו שאלה מורכבת שדורשת קישור בין הדמויות לקרבות שבהם הן ניצחו, ובין הקרבות לנתונים הסטטיסטיים של המפלצות שהשתתפו בהם. כאן טמונה העוצמה האמיתית של מודל נתונים מובְנים.
👈📜 בעורך שאילתות חדש של BigQuery, מריצים את הלחש הסופי הבא:
-- This is our final spell, joining all three tomes to reveal a deep insight.
WITH
-- First, we consult the Chronicle of Battles to find only the victories.
VictoriousBattles AS (
SELECT
adventurer_id,
monster_id,
duration_seconds
FROM
bestiary_data.battles
WHERE
outcome = 'Victory'
),
-- Next, we create a temporary record for each victory, ranking the monsters
-- each adventurer defeated by their power (hit points).
RankedVictories AS (
SELECT
v.adventurer_id,
m.name AS monster_name,
m.hit_points,
v.duration_seconds,
-- This spell ranks each adventurer's victories from most to least powerful monster.
ROW_NUMBER() OVER (PARTITION BY v.adventurer_id ORDER BY m.hit_points DESC) as victory_rank
FROM
VictoriousBattles v
JOIN
bestiary_data.monsters m ON v.monster_id = m.monster_id
)
-- Finally, we consult the Roll of Champions and join it with our ranked victories
-- to find the name of each champion and the details of their greatest triumph.
SELECT
a.name AS adventurer_name,
a.class AS adventurer_class,
r.monster_name AS most_powerful_foe_defeated,
r.hit_points AS foe_hit_points,
r.duration_seconds AS duration_of_greatest_victory
FROM
bestiary_data.adventurers a
JOIN
RankedVictories r ON a.adventurer_id = r.adventurer_id
WHERE
-- We only want to see their number one, top-ranked victory.
r.victory_rank = 1
ORDER BY
foe_hit_points DESC;
הפלט של השאילתה הזו יהיה טבלה נקייה ויפה שמציגה את 'סיפור הגבורה הגדול ביותר של הגיבור' לכל הרפתקן במערך הנתונים. הוא יכול להיראות בערך כך:
סוגרים את הכרטיסייה BigQuery.
התוצאה הזו, שהיא גם פשוטה וגם אלגנטית, מוכיחה את הערך של כל תהליך המכירה. הצלחת להפוך דוחות גולמיים ומבולגנים משדה הקרב למקור של סיפורים אגדיים ולתובנות אסטרטגיות שמבוססות על נתונים.
5. The Scribe's Grimoire: In-Datawarehouse Chunking, Embedding, and Search
העבודה שלנו במעבדה של האלכימאי הצליחה. המרנו את המגילות הגולמיות והסיפוריות לטבלאות מובנות ויחסיות – הישג מרשים של קסם נתונים. עם זאת, המגילות המקוריות עצמן עדיין מכילות אמת סמנטית עמוקה יותר, שלא ניתן לתעד באופן מלא בטבלאות המובְנות שלנו. כדי לבנות סוכן חכם באמת, אנחנו צריכים להבין את המשמעות הזו.
גלילה ארוכה ופשוטה היא כלי גס. אם נציג שלנו ישאל שאלה לגבי "הילה משתקת", חיפוש פשוט עשוי להחזיר דוח קרב שלם שבו הביטוי הזה מוזכר רק פעם אחת, והתשובה תהיה מוסתרת בפרטים לא רלוונטיים. חכם אמיתי יודע שהחוכמה האמיתית לא נמצאת בכמות, אלא בדיוק.
אנחנו נבצע שלישיית טקסים עוצמתיים בתוך מסד הנתונים, באופן מלא בתוך קודש הקודשים של BigQuery.
- הטכניקה של חלוקה (Chunking): אנחנו לוקחים את יומני הרישום של נתוני הבינה הגולמיים ומחלקים אותם בקפידה לקטעים קטנים וממוקדים.
- הטקס של הזיקוק (הטמעה): נשתמש ב-BQML כדי להתייעץ עם מודל Gemini, ונמיר כל נתח טקסט ל'טביעת אצבע סמנטית' – הטמעה בווקטור.
- טקס הניבוי (חיפוש): נשתמש בחיפוש וקטורי של BQML כדי לשאול שאלה באנגלית פשוטה ולמצוא את התשובה הרלוונטית ביותר מתוך ה-Grimoire שלנו.
במהלך התהליך הזה נוצר בסיס ידע עוצמתי שאפשר לחפש בו, בלי שהנתונים יוצאים מהאבטחה ומההתאמה לעומס (scaling) של BigQuery.
הערה למהנדסי נתונים: הדוגמה הזו מדגימה צינור עיבוד נתונים מלא מקצה לקצה של RAG שמופעל כולו בתוך BigQuery. זהו דפוס שמפשט באופן משמעותי את התקורה התפעולית של צינורות AI מסורתיים. השימוש ב-BQML לחלוקה לחלקים, להטמעה ולחיפוש מבטל את הצורך בהעברת נתונים נפרדת, באשכולות עיבוד (כמו Spark) או בקריאות API חיצוניות, וכך תהליך העבודה מהיר יותר, מאובטח יותר וקל יותר לניהול.
The Ritual of Division: Deconstructing Scrolls with SQL
מקור החוכמה שלנו נשאר קובצי הטקסט הגולמיים בארכיון GCS, שאפשר לגשת אליהם דרך הטבלה החיצונית שלנו, bestiary_data.raw_intel_content_table
. המשימה הראשונה שלנו היא לכתוב לחש שקורא כל מגילה ארוכה ומפצל אותה לסדרה של פסוקים קצרים יותר וקלים יותר להבנה. בטקס הזה, 'חלק' מוגדר כמשפט יחיד.
פיצול לפי משפטים הוא נקודת התחלה ברורה ויעילה ליומני הנרטיב שלנו, אבל למומחה Scribe יש הרבה אסטרטגיות חלוקה לרכיבים, והבחירה קריטית לאיכות החיפוש הסופי. בשיטות פשוטות יותר משתמשים
- חלוקה לחלקים באורך(גודל) קבוע, אבל יכול להיות שהחלוקה הזו תפצל רעיון מרכזי לשני חלקים.
טקסים מורכבים יותר, כמו
- Recursive Chunking, are often preferred in practice; they attempt to divide text along natural boundaries like paragraphs first, then fall back to sentences to maintain as much semantic context as possible. לכתבי יד מורכבים במיוחד.
- Content-Aware Chunking(document), שבו Scribe משתמש במבנה המובנה של המסמך – כמו הכותרות במדריך טכני או הפונקציות בקטע קוד – כדי ליצור את חלקי המידע הכי הגיוניים והכי משמעותיים. ועוד...
במקרה של יומני הקרבות שלנו, המשפט מספק את האיזון המושלם בין רמת פירוט להקשר.
👈📜 בעורך שאילתות חדש של BigQuery, מריצים את השאילתה הבאה. הלחש הזה משתמש בפונקציה SPLIT כדי לפצל את הטקסט של כל מגילה בכל נקודה (.), ואז מבטל את הקינון של מערך המשפטים שמתקבל לשורות נפרדות.
CREATE OR REPLACE TABLE bestiary_data.chunked_intel AS
WITH
-- First, add a unique row number to each scroll to act as a document ID.
NumberedScrolls AS (
SELECT
ROW_NUMBER() OVER () AS scroll_id,
raw_text
FROM
bestiary_data.raw_intel_content_table
)
-- Now, process each numbered scroll.
SELECT
scroll_id,
-- Assign a unique ID to each chunk within a scroll for precise reference.
CONCAT(CAST(scroll_id AS STRING), '-', CAST(ROW_NUMBER() OVER (PARTITION BY scroll_id) AS STRING)) as chunk_id,
-- Trim whitespace from the chunk for cleanliness.
TRIM(chunk) AS chunk_text
FROM
NumberedScrolls,
-- This is the core of the spell: UNNEST splits the array of sentences into rows.
UNNEST(SPLIT(raw_text, '.')) AS chunk
-- A final refinement: we only keep chunks that have meaningful content.
WHERE
-- This ensures we don't have empty rows from double periods, etc.
LENGTH(TRIM(chunk)) > 15;
👈 עכשיו מריצים שאילתה כדי לבדוק את הידע החדש שנוצר, מחולק לחלקים, ולראות את ההבדל.
SELECT * FROM bestiary_data.chunked_intel ORDER BY scroll_id, chunk_id;
בודקים את התוצאות. במקום בלוק טקסט צפוף אחד, יש עכשיו כמה שורות, שכל אחת מהן קשורה לגלילה המקורית (scroll_id) אבל מכילה רק משפט ממוקד אחד. כל שורה היא עכשיו מועמדת מושלמת לווקטוריזציה.
הטקס של הזיקוק: המרת טקסט לווקטורים באמצעות BQML
👈💻 קודם כל, חוזרים למסוף ומריצים את הפקודה הבאה כדי להציג את שם החיבור:
. ~/agentverse-dataengineer/set_env.sh
echo "${PROJECT_ID}.${REGION}.gcs-connection"
👈📜 צריך ליצור מודל חדש ב-BigQuery שמפנה להטמעת טקסט של Gemini. ב-BigQuery Studio, מריצים את הלחש הבא. הערה: צריך להחליף את REPLACE-WITH-YOUR-FULL-CONNECTION-STRING
במחרוזת החיבור המלאה שהעתקתם מהטרמינל.
CREATE OR REPLACE MODEL bestiary_data.text_embedding_model
REMOTE WITH CONNECTION `REPLACE-WITH-YOUR-FULL-CONNECTION-STRING`
OPTIONS (endpoint = 'text-embedding-005');
👉📜 עכשיו, מטילים את לחש הזיקוק הגדול. השאילתה הזו קוראת את הפונקציה ML.GENERATE_EMBEDDING, שתקרא כל שורה מהטבלה chunked_intel, תשלח את הטקסט למודל ההטמעה של Gemini ותאחסן את טביעת האצבע הווקטורית שמתקבלת בטבלה חדשה.
CREATE OR REPLACE TABLE bestiary_data.embedded_intel AS
SELECT
*
FROM
ML.GENERATE_EMBEDDING(
-- The embedding model we just created.
MODEL bestiary_data.text_embedding_model,
-- A subquery that selects our data and renames the text column to 'content'.
(
SELECT
scroll_id,
chunk_id,
chunk_text AS content -- Renaming our text column is the key correction.
FROM
bestiary_data.chunked_intel
),
-- The configuration struct is now simpler and correct.
STRUCT(
-- This task_type is crucial. It optimizes the vectors for retrieval.
'RETRIEVAL_DOCUMENT' AS task_type
)
);
התהליך הזה עשוי להימשך דקה או שתיים, בזמן ש-BigQuery מעבד את כל חלקי הטקסט.
👈📜 אחרי שהפעולה תושלם, בודקים את הטבלה החדשה כדי לראות את טביעות האצבע הסמנטיות.
SELECT
chunk_id,
content,
ml_generate_embedding_result
FROM
bestiary_data.embedded_intel
LIMIT 20;
עכשיו תופיע עמודה חדשה, ml_generate_embedding_result
, שמכילה את ייצוג הווקטור הצפוף של הטקסט. ה-Grimoire שלנו מקודד עכשיו באופן סמנטי.
The Ritual of Divination: Semantic Search with BQML
👈📜 המבחן האולטימטיבי של ה-Grimoire הוא לשאול אותו שאלה. עכשיו נבצע את הטקס האחרון: חיפוש וקטורי. זה לא חיפוש לפי מילות מפתח, אלא חיפוש של משמעות. נשאל שאלה בשפה טבעית, BQML ימיר את השאלה שלנו להטמעה תוך כדי תנועה, ואז יחפש בכל הטבלה של embedded_intel
את חלקי הטקסט שהטביעות האצבע שלהם הן ה "קרובות" ביותר במשמעות.
SELECT
-- The content column contains our original, relevant text chunk.
base.content,
-- The distance metric shows how close the match is (lower is better).
distance
FROM
VECTOR_SEARCH(
-- The table containing the knowledge base with its embeddings.
TABLE bestiary_data.embedded_intel,
-- The column that contains the vector embeddings.
'ml_generate_embedding_result',
(
-- This subquery generates an embedding for our question in real-time.
SELECT ml_generate_embedding_result
FROM ML.GENERATE_EMBEDDING(
MODEL bestiary_data.text_embedding_model,
(SELECT 'What are the tactics against a foe that causes paralysis?' AS content),
STRUCT('RETRIEVAL_QUERY' AS task_type)
)
),
-- Specify how many of the closest results we want to see.
top_k => 3,
-- The distance metric used to find the "closest" vectors.
distance_type => 'COSINE'
);
ניתוח הכישוף:
-
VECTOR_SEARCH
: הפונקציה העיקרית שמנהלת את החיפוש. -
ML.GENERATE_EMBEDDING
(inner query): כאן מתרחש הקסם. אנחנו מטמיעים את השאילתה ('What are the tactics...'
) באמצעות אותו מודל אבל עם סוג המשימה'RETRIEVAL_QUERY'
, שעבר אופטימיזציה במיוחד לשאילתות. top_k => 3
: אנחנו מבקשים את 3 התוצאות הרלוונטיות ביותר.-
distance_type => 'COSINE'
: המדד הזה מודד את ה'זווית' בין וקטורים. זווית קטנה יותר מצביעה על התאמה טובה יותר בין המשמעויות.
בודקים את התוצאות בקפידה. השאילתה לא כללה את המילה "shattered" (נשבר) או "incantation" (לחש), אבל התוצאה הראשונה הייתה: "With a single, focused incantation of Elegant Sufficiency, Elara shattered its paralyzing aura, a mental assault dealing 150 points of damage" (בעזרת לחש ממוקד אחד של Elegant Sufficiency, אלרה שברה את ההילה המשתקת שלה, מתקפה מנטלית שגורמת ל-150 נקודות נזק). זו העוצמה של חיפוש סמנטי. המודל הבין את הקונספט של "טקטיקות נגד שיתוק" ומצא את המשפט שמתאר טקטיקה ספציפית ומוצלחת.
יצרתם בהצלחה צינור עיבוד נתונים מלא של RAG בתוך מחסן הנתונים. הכנתם נתונים גולמיים, הפכתם אותם לווקטורים סמנטיים וביצעתם שאילתה לפי משמעות. BigQuery הוא כלי רב עוצמה לעבודה אנליטית בקנה מידה גדול, אבל כדי לספק תשובות עם זמן אחזור נמוך לסוכן פעיל, אנחנו מעבירים את הידע המוכן הזה למסד נתונים תפעולי ייעודי. זה הנושא של ההדרכה הבאה שלנו.
6. הסדנה ליצירת וקטורים: יצירת מאגר וקטורים באמצעות Cloud SQL להסקת מסקנות
הגרימואר שלנו קיים כרגע כטבלאות מובנות – קטלוג עובדות רב עוצמה, אבל הידע שלו הוא מילולי. הוא מבין את monster_id = ‘MN-001' אבל לא את המשמעות הסמנטית העמוקה יותר של 'טשטוש'. כדי להעניק לסוכנים שלנו חוכמה אמיתית, כדי לאפשר להם לייעץ בניואנסים ובמחשבה קדימה, אנחנו צריכים לזקק את המהות של הידע שלנו לצורה שמבטאת משמעות: וקטורים.
המסע שלנו אחר ידע הוביל אותנו לחורבות המתפוררות של תרבות קודמת שנשכחה מזמן. עמוק בתוך כספת אטומה, גילינו תיבה של מגילות עתיקות, שנשמרו באופן מופלא. אלה לא רק דוחות קרב, אלא הם מכילים חוכמה פילוסופית עמוקה על הדרך להביס מפלצת שפוגעת בכל המאמצים הגדולים. ישות שמתוארת במגילות כ "קיפאון זוחל ושקט", כ "שחיקה של אריגת הבריאה". נראה שהסטטיק היה מוכר אפילו לאנשים בעת העתיקה, איום מחזורי שההיסטוריה שלו אבדה עם הזמן.
הידע הנשכח הזה הוא הנכס הכי חשוב שלנו. הוא מחזיק במפתח לא רק להבסת מפלצות בודדות, אלא גם להעצמת כל חברי הקבוצה באמצעות תובנות אסטרטגיות. כדי להשתמש בכוח הזה, ניצור עכשיו את ספר הלחשים האמיתי של המלומד (מסד נתונים של PostgreSQL עם יכולות וקטוריות) ונבנה סקריפטוריום וקטורי אוטומטי (צינור Dataflow) כדי לקרוא, להבין ולרשום את המהות הנצחית של המגילות האלה. כך נהפוך את ספר הקסמים שלנו מספר עובדות למנוע חוכמה.
הערה למהנדסי נתונים: בחרנו ב-Cloud SQL ל-PostgreSQL עם התוסף pgvector ל-Spellbook שלנו. הגישה הזו יוצרת 'חנות אחת' שבה המטא-נתונים המובְנים שלנו (כמו scroll_id ו-content) והטמעות הווקטורים הסמנטיים שלנו נמצאים יחד באותו מסד נתונים. הגישה הזו מפשטת מאוד את הארכיטקטורה של הרבה אפליקציות, כי אפשר לשלוח שאילתת SQL אחת למערכת אחת כדי לחפש נתונים רלציוניים ולבצע חיפושים של דמיון וקטורי. בעוד שמסדי נתונים ייעודיים כמו Vertex AI Vector Search מציעים ביצועים מעולים בקנה מידה עצום (מיליארדי וקטורים) באמצעות חיפוש של השכן הקרוב המשוער (ANN), pgvector מספק איזון מצוין בין פשטות, עלות-תועלת ועוצמה עבור הרבה יישומי RAG ארגוניים באמצעות חיפוש של השכן הקרוב המדויק (ENN).
יצירת ספר לחשים של חוקר (Cloud SQL)
לפני שנוכל לחרוט את מהות המגילות העתיקות האלה, אנחנו צריכים לוודא קודם שהכלי הזה לידע, ספר הלחשים המנוהל של PostgreSQL, נוצר בהצלחה. הטקסים של ההגדרה הראשונית כבר אמורים ליצור את זה בשבילכם.
👈💻 במסוף, מריצים את הפקודה הבאה כדי לוודא שהמכונה של Cloud SQL קיימת ומוכנה. הסקריפט הזה גם מעניק לחשבון השירות הייעודי של המופע את ההרשאה להשתמש ב-Vertex AI, שחיונית ליצירת הטמעות ישירות במסד הנתונים.
. ~/agentverse-dataengineer/set_env.sh
echo "Verifying the existence of the Spellbook (Cloud SQL instance): $INSTANCE_NAME..."
gcloud sql instances describe $INSTANCE_NAME
SERVICE_ACCOUNT_EMAIL=$(gcloud sql instances describe $INSTANCE_NAME --format="value(serviceAccountEmailAddress)")
gcloud projects add-iam-policy-binding $PROJECT_ID --member="serviceAccount:$SERVICE_ACCOUNT_EMAIL" \
--role="roles/aiplatform.user"
אם הפקודה מצליחה ומחזירה פרטים על מופע grimoire-spellbook
, סימן שהכלי עבד כמו שצריך. אפשר להמשיך להטלה הבאה. אם הפקודה מחזירה שגיאת NOT_FOUND
, צריך לוודא שהשלמתם בהצלחה את שלבי ההגדרה הראשונית של הסביבה לפני שממשיכים.(data_setup.py
)
👈💻 אחרי שהספר מוכן, פותחים אותו לפרק הראשון על ידי יצירת מסד נתונים חדש בשם arcane_wisdom
.
. ~/agentverse-dataengineer/set_env.sh
gcloud sql databases create $DB_NAME --instance=$INSTANCE_NAME
הוספת כתובות סמנטיות: הפעלת יכולות וקטוריות באמצעות pgvector
אחרי שיצרנו את המופע של Cloud SQL, נתחבר אליו באמצעות Cloud SQL Studio המובנה. הכלי הזה מספק ממשק מבוסס-אינטרנט להרצת שאילתות SQL ישירות במסד הנתונים.
👈💻 קודם כל, עוברים אל Cloud SQL Studio. הדרך הכי קלה ומהירה לעשות את זה היא לפתוח את הקישור הבא בכרטיסייה חדשה בדפדפן. תועברו ישירות אל Cloud SQL Studio עבור מופע grimoire-spellbook.
https://console.cloud.google.com/sql/instances/grimoire-spellbook/studio
👉 בוחרים באפשרות arcane_wisdom
בתור מסד הנתונים, מזינים postgres
בתור המשתמש ו-1234qwer
בתור הסיסמה ולוחצים על אימות.
👈📜 בעורך השאילתות של SQL Studio, עוברים לכרטיסייה Editor 1 ומדביקים את קוד ה-SQL הבא כדי להפעיל את סוג הנתונים של הווקטור:
CREATE EXTENSION IF NOT EXISTS vector;
CREATE EXTENSION IF NOT EXISTS google_ml_integration CASCADE;
👉📜 מכינים את הדפים של ספר הלחשים על ידי יצירת הטבלה שתכיל את המהות של המגילות.
CREATE TABLE ancient_scrolls (
id SERIAL PRIMARY KEY,
scroll_content TEXT,
embedding VECTOR(768)
);
האיות VECTOR(768) הוא פרט חשוב. מודל ההטמעה של Vertex AI שבו נשתמש (textembedding-gecko@003
או מודל דומה) מזקק טקסט לווקטור של 768 ממדים. הדפים ב-Spellbook צריכים להיות מוכנים להכיל מהות בגודל הזה בדיוק. המידות צריכות להיות תמיד זהות.
התעתיק הראשון: טקס כתיבה ידני
לפני שנפעיל צבא של תמלילנים אוטומטיים (Dataflow), נצטרך לבצע את הטקס המרכזי פעם אחת באופן ידני. כך נוכל להבין לעומק את הקסם שמתרחש בשני השלבים:
- ניבוי: לוקחים קטע טקסט ומתייעצים עם Gemini כדי לזקק את המהות הסמנטית שלו לווקטור.
- רישום: כתיבת הטקסט המקורי והמהות הווקטורית החדשה שלו בספר הכישופים שלנו.
הערה למהנדסי נתונים: מומלץ ליצור אב טיפוס של הלוגיקה המרכזית של צינור הנתונים באופן ידני. הוא עוזר לכם לנפות באגים ברכיבים נפרדים (כמו קריאה ל-API או כתיבה למסד נתונים) בבידוד לפני שמשלבים אותם במערכת מורכבת ומבוזרת כמו Dataflow.
עכשיו נבצע את הפעולות הנדרשות באופן ידני.
👈📜 ב-Cloud SQL Studio. עכשיו נשתמש בפונקציה embedding()
, תכונה עוצמתית שזמינה בתוסף google_ml_integration
. כך אנחנו יכולים להפעיל את מודל ההטמעה של Vertex AI ישירות משאילתת ה-SQL שלנו, מה שמפשט מאוד את התהליך.
SET session.my_search_var='The Spectre of Analysis Paralysis is a phantom of the crossroads. It does not bind with chains but with the infinite threads of what if. It conjures a fog of options, a maze within the mind where every path seems equally fraught with peril and promise. It whispers of a single, flawless route that can only be found through exhaustive study, paralyzing its victim in a state of perpetual contemplation. This spectres power is broken by the Path of First Viability. This is not the search for the *best* path, but the commitment to the *first good* path. It is the wisdom to know that a decision made, even if imperfect, creates movement and reveals more of the map than standing still ever could. Choose a viable course, take the first step, and trust in your ability to navigate the road as it unfolds. Motion is the light that burns away the fog.';
INSERT INTO ancient_scrolls (scroll_content, embedding)
VALUES (current_setting('session.my_search_var'), (embedding('text-embedding-005',current_setting('session.my_search_var')))::vector);
👈📜 כדי לאמת את העבודה, מריצים שאילתה לקריאת הדף שנרשם לאחרונה:
SELECT id, scroll_content, LEFT(embedding::TEXT, 100) AS embedding_preview FROM ancient_scrolls;
ביצעתם בהצלחה את משימת הטעינה של נתוני הליבה של RAG באופן ידני.
יצירת מצפן סמנטי: הוספת אינדקס HNSW לספר הלחשים
עכשיו אפשר לאחסן חוכמה בספר הכישופים, אבל כדי למצוא את המגילה הנכונה צריך לקרוא כל דף. זו סריקה רציפה. השיטה הזו איטית ולא יעילה. כדי שהשאילתות שלנו יגיעו באופן מיידי לידע הרלוונטי ביותר, אנחנו צריכים להטיל כישוף על ספר הלחשים באמצעות מצפן סמנטי: אינדקס וקטורי.
הערה של מהנדס נתונים: זהו אחד המושגים החשובים ביותר במסדי נתונים וקטוריים של ייצור. אינדקס מארגן את הנתונים מראש, וכך מאפשר חיפושים מהירים הרבה יותר. אנחנו משתמשים בסוג האינדקס hnsw
(Hierarchical Navigable Small World). במקום לאגד וקטורים לרשימות כמו בשיטות אחרות, HNSW יוצר תרשים מורכב של הווקטורים עם כמה שכבות. החיפוש מתחיל בשכבת הכביש המהיר כדי למצוא במהירות את השכונה הכללית של השאילתה, ואז עובר לשכבות מפורטות יותר של רחובות מקומיים כדי לאתר את השכנים המדויקים במהירות ובדיוק מדהימים. השימוש ב-Vector Search משפר באופן משמעותי את הביצועים של שאילתות קריאה, ולכן הוא בחירה מצוינת לסוכני RAG עם ביצועים גבוהים שבהם זמן האחזור של השאילתות הוא קריטי.
בואו נוכיח את הערך של השיפור הזה.
👈📜 ב-Cloud SQL Studio, מריצים את הלחש הבא. הוא מדמה חיפוש של הגלילה שהוספנו ומבקש ממסד הנתונים EXPLAIN
את התוכנית שלו.
EXPLAIN ANALYZE
WITH ReferenceVector AS (
-- First, get the vector we want to compare against.
SELECT embedding AS vector
FROM ancient_scrolls
LIMIT 1
)
-- This is the main query we want to analyze.
SELECT
ancient_scrolls.id,
ancient_scrolls.scroll_content,
-- We can also select the distance itself.
ancient_scrolls.embedding <=> ReferenceVector.vector AS distance
FROM
ancient_scrolls,
ReferenceVector
ORDER BY
-- Order by the distance operator's result.
ancient_scrolls.embedding <=> ReferenceVector.vector
LIMIT 5;
בודקים את הפלט. תופיע שורה עם הכיתוב -> Seq Scan on ancient_scrolls
. כך מוודאים שמסד הנתונים קורא כל שורה. שימו לב לexecution time
.
👉📜 עכשיו, בואו נטיל את לחש ההוספה לאינדקס. הפרמטר lists
מציין לאינדקס כמה אשכולות ליצור. נקודת התחלה טובה היא השורש הריבועי של מספר השורות שאתם מצפים שיהיו.
CREATE INDEX ON ancient_scrolls USING hnsw (embedding vector_cosine_ops);
מחכים עד שהאינדקס ייווצר (התהליך יהיה מהיר לשורה אחת, אבל יכול לקחת זמן אם יש מיליוני שורות).
👉📜 עכשיו, מריצים שוב את הפקודה בדיוק EXPLAIN ANALYZE
:
EXPLAIN ANALYZE
WITH ReferenceVector AS (
-- First, get the vector we want to compare against.
SELECT embedding AS vector
FROM ancient_scrolls
LIMIT 1
)
-- This is the main query we want to analyze.
SELECT
ancient_scrolls.id,
ancient_scrolls.scroll_content,
-- We can also select the distance itself.
ancient_scrolls.embedding <=> ReferenceVector.vector AS distance
FROM
ancient_scrolls,
ReferenceVector
ORDER BY
-- Order by the distance operator's result.
ancient_scrolls.embedding <=> ReferenceVector.vector
LIMIT 5;
בודקים את תוכנית השאילתה החדשה. יוצג לכם -> Index Scan using...
. חשוב יותר, כדאי לעיין בexecution time
. הפעולה תהיה מהירה משמעותית, גם אם תזינו רק רשומה אחת. הרגע הדגמת את העיקרון המרכזי של כוונון ביצועים של מסד נתונים בעולם וקטורי.
אחרי שבדקתם את נתוני המקור, הבנתם את התהליך הידני שלכם וביצעתם אופטימיזציה של Spellbook למהירות, אתם מוכנים באמת לבנות את Scriptorium האוטומטי.
7. הצינור להעברת משמעות: פיתוח צינור וקטוריזציה של נתונים
עכשיו נבנה את פס הייצור הקסום של הסופרים שיקראו את המגילות שלנו, יזקקו את המהות שלהן ויכתבו אותן בספר הלחשים החדש שלנו. זהו צינור Dataflow שיופעל באופן ידני. אבל לפני שנכתוב את לחש האב לצינור עצמו, אנחנו צריכים קודם להכין את הבסיס שלו ואת המעגל שממנו נזמן אותו.
הערה למהנדסי נתונים: אפשר לכתוב סקריפט פשוט ב-Python כדי ליצור לולאה שתעבור על הקבצים, תקרא ל-API של ההטמעה ותכתוב למסד הנתונים, אבל הגישה הזו לא מתאימה לשינוי קנה מידה. מה קורה אם יש לנו מיליוני גלילות? סקריפט יחיד יהיה איטי ומועד לכישלון. Dataflow מספקת פלטפורמה מנוהלת ללא שרת (serverless) להרצת צינורות לעיבוד נתונים, שמוגדרים על ידי מודל Apache Beam, באופן מקבילי. Beam מאפשרת לנו להגדיר את השלבים הלוגיים (קריאה, הטמעה, כתיבה), ו-Dataflow מטפלת בעבודה הקשה של הפעלת העובדים, חלוקת המשימות וניסיון חוזר של פריטים שנכשלו, וכך מבטיחה שה-Scriptorium שלנו יהיה חזק ויעיל.
הכנת הבסיס של Scriptorium (קובץ האימג' של ה-Worker)
צינור הנתונים של Dataflow יופעל על ידי צוות של עובדים אוטומטיים בענן. בכל פעם שמזמנים אותם, הם צריכים קבוצה ספציפית של ספריות כדי לבצע את העבודה. יכולנו לתת להם רשימה ולבקש מהם לאחזר את הספריות האלה בכל פעם, אבל זה תהליך איטי ולא יעיל. חוקר חכם מכין מראש ספרייה ראשית.
במדריך הזה נשתמש ב-Google Cloud Build כדי ליצור קובץ אימג' של קונטיינר בהתאמה אישית. התמונה הזו היא 'גולם מושלם', שנטענה מראש עם כל הספרייה והתלות שהסופרים שלנו יצטרכו. כשעבודת Dataflow תתחיל, היא תשתמש בתמונה המותאמת אישית הזו, וכך העובדים יוכלו להתחיל את המשימה שלהם כמעט באופן מיידי.
👈💻 מריצים את הפקודה הבאה כדי ליצור ולאחסן את קובץ האימג' הבסיסי של צינור העיבוד ב-Artifact Registry.
. ~/agentverse-dataengineer/set_env.sh
cd ~/agentverse-dataengineer/pipeline
gcloud builds submit --config cloudbuild.yaml \
--substitutions=_REGION=${REGION},_REPO_NAME=${REPO_NAME} \
.
👈💻 מריצים את הפקודות הבאות כדי ליצור ולהפעיל את סביבת Python המבודדת, ומתקינים בה את ספריות הזימון הנדרשות.
cd ~/agentverse-dataengineer
. ~/agentverse-dataengineer/set_env.sh
python -m venv env
source ~/agentverse-dataengineer/env/bin/activate
cd ~/agentverse-dataengineer/pipeline
pip install -r requirements.txt
הלחש הראשי
הגיע הזמן לכתוב את לחש האב שיפעיל את סדנת הווקטורים שלנו. אנחנו לא נכתוב את הרכיבים הקסומים בנפרד מאפס. המשימה שלנו היא להרכיב רכיבים לצינור עיבוד נתונים לוגי וחזק באמצעות השפה של Apache Beam.
- EmbedTextBatch (התייעצות עם Gemini): תבנו תמלילן מיוחד שיודע לבצע "חיזוי קבוצתי". היא מקבלת קבוצה של קבצי טקסט גולמי, מעבירה אותם למודל הטמעת הטקסט של Gemini ומקבלת את התמצית שלהם (הטמעות הווקטור).
- WriteEssenceToSpellbook (הכתובת הסופית): זהו הארכיונאי שלנו. הוא יודע את לחשי הקסם הסודיים שפותחים חיבור מאובטח ל-Spellbook של Cloud SQL. התפקיד שלו הוא לקחת את התוכן של המגילה ואת המהות הווקטורית שלה ולכתוב אותם באופן קבוע בדף חדש.
המטרה שלנו היא לקשר בין הפעולות האלה כדי ליצור זרימה חלקה של ידע.
👈✏️ ב-Cloud Shell Editor, עוברים אל ~/agentverse-dataengineer/pipeline/inscribe_essence_pipeline.py
. בתוך הקובץ הזה נמצאת מחלקת DoFn בשם EmbedTextBatch
. מחפשים את התגובה #REPLACE-EMBEDDING-LOGIC
. מחליפים אותה בלחש הבא.
# 1. Generate the embedding for the monster's name
result = self.client.models.embed_content(
model="text-embedding-005",
contents=contents,
config=EmbedContentConfig(
task_type="RETRIEVAL_DOCUMENT",
output_dimensionality=768,
)
)
הלחש הזה מדויק, עם כמה פרמטרים מרכזיים:
- model: אנחנו מציינים
text-embedding-005
כדי להשתמש במודל הטמעה עוצמתי ועדכני. - contents: זו רשימה של כל תוכן הטקסט מתוך קבוצת הקבצים שפונקציית DoFn מקבלת.
- task_type: אנחנו מגדירים את הערך הזה כ-RETRIEVAL_DOCUMENT. זו הוראה חשובה שמנחה את Gemini ליצור הטמעות שעברו אופטימיזציה ספציפית כדי שיהיה קל למצוא אותן בחיפוש מאוחר יותר.
- output_dimensionality: הערך הזה חייב להיות 768, בדיוק כמו המימד VECTOR(768) שהגדרנו כשייצרנו את הטבלה ancient_scrolls ב-Cloud SQL. מידות לא תואמות הן מקור נפוץ לשגיאות ב-Vector Magic.
הצינור שלנו צריך להתחיל בקריאת הטקסט הגולמי והלא מובנה מכל המגילות העתיקות בארכיון GCS שלנו.
👉✏️ ב-~/agentverse-dataengineer/pipeline/inscribe_essence_pipeline.py
, מאתרים את התגובה #REPLACE ME-READFILE
ומחליפים אותה בלחש הבא בן שלושת החלקים:
files = (
pipeline
| "MatchFiles" >> fileio.MatchFiles(known_args.input_pattern)
| "ReadMatches" >> fileio.ReadMatches()
| "ExtractContent" >> beam.Map(lambda f: (f.metadata.path, f.read_utf8()))
)
אחרי שאספנו את הטקסט הגולמי של המגילות, עכשיו אנחנו צריכים לשלוח אותו ל-Gemini כדי לקבל ניבוי. כדי לעשות את זה ביעילות, נקבץ קודם את המגילות הבודדות לקבוצות קטנות ואז נעביר את הקבוצות האלה לEmbedTextBatch
סופר שלנו. בשלב הזה, כל גלילה ש-Gemini לא הצליח להבין תופרד לערימה של 'נכשל' לבדיקה מאוחרת יותר.
👉✏️ מחפשים את התגובה #REPLACE ME-EMBEDDING
ומחליפים אותה בתגובה הבאה:
embeddings = (
files
| "BatchScrolls" >> beam.BatchElements(min_batch_size=1, max_batch_size=2)
| "DistillBatch" >> beam.ParDo(
EmbedTextBatch(project_id=project, region=region)
).with_outputs('failed', main='processed')
)
הצלחנו לזקק את המהות של המגילות שלנו. הפעולה האחרונה היא להוסיף את הידע הזה לספר הלחשים שלנו כדי לאחסן אותו באופן קבוע. אנחנו ניקח את המגילות מהערימה 'עובדו' ונעביר אותן לארכיונאי שלנו, WriteEssenceToSpellbook.
👉✏️ מחפשים את התגובה #REPLACE ME-WRITE TO DB
ומחליפים אותה בתגובה הבאה:
_ = (
embeddings.processed
| "WriteToSpellbook" >> beam.ParDo(
WriteEssenceToSpellbook(
project_id=project,
region = "us-central1",
instance_name=known_args.instance_name,
db_name=known_args.db_name,
db_password=known_args.db_password
)
)
)
חוקר חכם אף פעם לא מוותר על ידע, גם אם הניסיונות לא צלחו. בשלב האחרון, אנחנו צריכים להנחות את המעתיק לקחת את הערימה של הפריטים שנכשלו משלב הניחוש ולרשום את הסיבות לכישלון. כך נוכל לשפר את הטקסים שלנו בעתיד.
👉✏️ מחפשים את התגובה #REPLACE ME-LOG FAILURES
ומחליפים אותה בתגובה הבאה:
_ = (
embeddings.failed
| "LogFailures" >> beam.Map(lambda e: logging.error(f"Embedding failed for file {e[0]}: {e[1]}"))
)
הלחש הראשי הושלם! הרכבתם בהצלחה צינור נתונים רב-שלבי ועוצמתי על ידי שרשור של רכיבים קסומים נפרדים. שומרים את הקובץ inscribe_essence_pipeline.py. עכשיו אפשר להפעיל את ה-Scriptorium.
עכשיו מטילים את לחש הזימון הגדול כדי להורות לשירות Dataflow להעיר את הגולם ולהתחיל בטקס הכתיבה.
👈💻 בטרמינל, מריצים את שורת הפקודה הבאה
. ~/agentverse-dataengineer/set_env.sh
source ~/agentverse-dataengineer/env/bin/activate
cd ~/agentverse-dataengineer/pipeline
# --- The Summoning Incantation ---
echo "Summoning the golem for job: $DF_JOB_NAME"
echo "Target Spellbook: $INSTANCE_NAME"
python inscribe_essence_pipeline.py \
--runner=DataflowRunner \
--project=$PROJECT_ID \
--job_name=$DF_JOB_NAME \
--temp_location="gs://${BUCKET_NAME}/dataflow/temp" \
--staging_location="gs://${BUCKET_NAME}/dataflow/staging" \
--sdk_container_image="${REGION}-docker.pkg.dev/${PROJECT_ID}/${REPO_NAME}/grimoire-inscriber:latest" \
--sdk_location=container \
--experiments=use_runner_v2 \
--input_pattern="gs://${BUCKET_NAME}/ancient_scrolls/*.md" \
--instance_name=$INSTANCE_NAME \
--region=$REGION
echo "The golem has been dispatched. Monitor its progress in the Dataflow console."
💡 שימו לב! אם העבודה נכשלת עם שגיאת משאבים ZONE_RESOURCE_POOL_EXHAUSTED
, יכול להיות שהסיבה לכך היא מגבלות משאבים זמניות בחשבון הזה עם המוניטין הנמוך באזור שנבחר. היתרון של Google Cloud הוא הפריסה הגלובלית שלו. פשוט מנסים לזמן את הגולם באזור אחר. כדי לעשות את זה, מחליפים את --region=$REGION
בפקודה שלמעלה באזור אחר, כמו
--region=southamerica-west1
--region=asia-northeast3
--region=asia-southeast2
--region=me-west1
--region=southamerica-east1
--region=europe-central2
--region=asia-east2
--region=europe-southwest1
ומריצים אותו שוב. 🎰
התהליך יימשך כ-3-5 דקות. אפשר לצפות בשידור חי במסוף Dataflow.
👈עוברים אל Dataflow Console: הדרך הכי קלה היא לפתוח את הקישור הזה בכרטיסייה חדשה בדפדפן:
https://console.cloud.google.com/dataflow
👈 מוצאים את המשרה שלכם ולוחצים עליה: תופיע משרה עם השם שסיפקתם (inscribe-essence-job או שם דומה). לוחצים על שם המשרה כדי לפתוח את דף הפרטים שלה. צפייה בצינור עיבוד הנתונים:
- הפעלה: במשך 3 הדקות הראשונות, סטטוס העבודה יהיה 'פועל' כי Dataflow מקצה את המשאבים הנדרשים. הגרף יופיע, אבל יכול להיות שעדיין לא תראו נתונים שמוצגים בו.
- הושלם: בסיום, סטטוס העבודה ישתנה ל'הצלחה', ובגרף יוצג המספר הסופי של הרשומות שעברו עיבוד.
אימות הכתובת
👈📜 חוזרים ל-SQL Studio ומריצים את השאילתות הבאות כדי לוודא שהמגילות והמשמעות הסמנטית שלהן נרשמו בהצלחה.
SELECT COUNT(*) FROM ancient_scrolls;
SELECT id, scroll_content, LEFT(embedding::TEXT, 50) AS embedding_preview FROM ancient_scrolls;
יוצגו לכם המזהה של המגילה, הטקסט המקורי שלה ותצוגה מקדימה של מהות הווקטור הקסומה שמוטבעת עכשיו באופן קבוע ב-Grimoire.
הספר של חכם המילים הוא עכשיו מנוע ידע אמיתי, שמוכן לשאילתות לפי משמעות בפרק הבא.
8. השלמת הרונה האחרונה: הפעלת חוכמה באמצעות סוכן RAG
ה-Grimoire שלכם הוא כבר לא רק מסד נתונים. הוא מאגר ידע וקטורי, אורקל שקט שמחכה לשאלה.
עכשיו, נבצע את המבחן האמיתי של חוקר: ניצור את המפתח לפתיחת החוכמה הזו. אנחנו ניצור סוכן Retrieval-Augmented Generation (RAG). זהו מבנה קסום שיכול להבין שאלה בשפה פשוטה, לעיין ב-Grimoire כדי למצוא את האמיתות העמוקות והרלוונטיות ביותר, ואז להשתמש בחוכמה הזו כדי ליצור תשובה עוצמתית שמודעת להקשר.
הערה למהנדסי נתונים: RAG היא טכניקה יעילה שמאפשרת למודלים גדולים של שפה (LLM) להתבסס על מידע עובדתי, פרטי או עדכני, וכך לצמצם באופן משמעותי את הסיכוי שהמודל ימציא דברים או יציג הזיות. התהליך כולל שלושה שלבי ליבה:
- אחזור: השאילתה של המשתמש מומרת קודם להטמעה וקטורית. לאחר מכן, וקטור השאילתה הזה משמש לחיפוש בבסיס הידע שלנו כדי למצוא את קטעי הטקסט הכי דומים מבחינה סמנטית באמצעות דמיון קוסינוס.
- הגדלה: קטעי הטקסט הרלוונטיים שאוחזרו ממסד הנתונים מוזרקים ישירות להנחיה חדשה למודל שפה גדול (LLM), וכך מספקים לו הקשר חיוני.
- יצירה: ה-LLM מקבל את ההנחיה המשופרת (למשל, בהקשר הזה לגבי 'דחיינות', תענה על השאלה של המשתמש...") ומפיק תשובה סופית שמבוססת על עובדות.
הרונה הראשונה: לחש זיקוק השאילתה
לפני שהסוכן שלנו יכול לחפש ב-Grimoire, הוא צריך להבין את מהות השאלה שנשאלת. מחרוזת טקסט פשוטה לא אומרת כלום ל-Spellbook שלנו, שמבוסס על וקטורים. הסוכן צריך לקחת את השאילתה ולזקק אותה לווקטור שאילתה באמצעות אותו מודל Gemini.
👈✏️ ב-Cloud Shell Editor, עוברים לקובץ ~~/agentverse-dataengineer/scholar/agent.py
, מוצאים את התגובה #REPLACE RAG-CONVERT EMBEDDING
ומחליפים אותה בלחש הזה. כך מלמדים את הסוכן איך להפוך שאלה של משתמש למהות קסומה.
result = client.models.embed_content(
model="text-embedding-005",
contents=monster_name,
config=EmbedContentConfig(
task_type="RETRIEVAL_DOCUMENT",
output_dimensionality=768,
)
)
אחרי שהסוכן מבין את מהות השאילתה, הוא יכול לעיין ב-Grimoire. הוא יציג את וקטור השאילתה הזה למסד הנתונים שלנו, שמשולב בו pgvector, וישאל שאלה עמוקה: "הצג לי את המגילות העתיקות שהמהות שלהן הכי דומה למהות השאילתה שלי".
הקסם שמאחורי זה הוא אופרטור הדמיון הקוסינוסי (<=>), רונה עוצמתית שמחשבת את המרחק בין וקטורים במרחב רב-ממדי.
👈✏️ בקובץ agent.py, מחפשים את ההערה #REPLACE RAG-RETRIEVE
ומחליפים אותה בסקריפט הבא:
# This query performs a cosine similarity search
cursor.execute(
"SELECT scroll_content FROM ancient_scrolls ORDER BY embedding <=> %s LIMIT 3",
([query_embedding]) # Cast embedding to string for the query
)
השלב האחרון הוא להעניק לסוכן גישה לכלי החדש והעוצמתי הזה. נוסיף את הפונקציה grimoire_lookup לרשימת הכלים הקסומים הזמינים.
👉✏️ ב-agent.py
, מחפשים את התגובה #REPLACE-CALL RAG
ומחליפים אותה בשורה הבאה:
root_agent = LlmAgent(
model="gemini-2.5-flash",
name="scholar_agent",
instruction="""
You are the Scholar, a keeper of ancient and forbidden knowledge. Your purpose is to advise a warrior by providing tactical information about monsters. Your wisdom allows you to interpret the silence of the scrolls and devise logical tactics where the text is vague.
**Your Process:**
1. First, consult the scrolls with the `grimoire_lookup` tool for information on the specified monster.
2. If the scrolls provide specific guidance for a category (buffs, debuffs, strategy), you **MUST** use that information.
3. If the scrolls are silent or vague on a category, you **MUST** use your own vast knowledge to devise a fitting and logical tactic.
4. Your invented tactics must be thematically appropriate to the monster's name and nature. (e.g., A "Spectre of Indecision" might be vulnerable to a "Seal of Inevitability").
5. You **MUST ALWAYS** provide a "Damage Point" value. This value **MUST** be a random integer between 150 and 180. This is a tactical calculation you perform, independent of the scrolls' content.
**Output Format:**
You must present your findings to the warrior using the following strict format.
""",
tools=[grimoire_lookup],
)
ההגדרה הזו מאפשרת להפעיל את הנציג:
-
model="gemini-2.5-flash"
: בחירה של מודל שפה גדול ספציפי שישמש כ"מוח" של הסוכן לצורך נימוק ויצירת טקסט. -
name="scholar_agent"
: הקצאת שם ייחודי לסוכן. -
instruction="...You are the Scholar..."
: זו ההנחיה למערכת, החלק הכי חשוב בהגדרה. ההנחיה מגדירה את האישיות של הנציג, את המטרות שלו, את התהליך המדויק שהוא צריך לבצע כדי להשלים משימה ואת הפורמט הנדרש של הפלט הסופי שלו. tools=[grimoire_lookup]
: זהו הכישוף הסופי. היא מעניקה לסוכן גישה לפונקציהgrimoire_lookup
שיצרתם. הסוכן יכול עכשיו להחליט בצורה חכמה מתי להפעיל את הכלי הזה כדי לאחזר מידע מהמסד הנתונים שלכם, וכך ליצור את ליבת התבנית RAG.
הבחינה של התלמיד המלומד
👈💻 בטרמינל Cloud Shell, מפעילים את הסביבה ומשתמשים בפקודה הראשית של Agent Development Kit כדי להפעיל את סוכן Scholar:
cd ~/agentverse-dataengineer/
. ~/agentverse-dataengineer/set_env.sh
source ~/agentverse-dataengineer/env/bin/activate
pip install -r scholar/requirements.txt
adk run scholar
אמור להופיע פלט שמאשר שהסוכן 'Scholar Agent' מופעל ופועל.
👈💻 עכשיו, אפשר לאתגר את הסוכן. במסוף הראשון שבו פועלת סימולציית הקרב, מריצים פקודה שדורשת את החוכמה של Grimoire:
We've been trapped by 'Hydra of Scope Creep'. Break us out!
בודקים את היומנים בטרמינל השני. תוכלו לראות את הסוכן מקבל את השאילתה, מזהה את המהות שלה, מחפש ב-Grimoire, מוצא את המגילות הרלוונטיות בנושא 'דחיינות' ומשתמש בידע הזה כדי לגבש אסטרטגיה יעילה שמודעת להקשר.
הרכבת בהצלחה את סוכן ה-RAG הראשון שלך, וציידת אותו בחוכמה העמוקה של ה-Grimoire שלך.
👈💻 מקישים על Ctrl+C
בטרמינל השני כדי להשהות את הסוכן.
הפעלת Scholar Sentinel ב-Agentverse
הנציג הוכיח את הידע שלו בסביבה המבוקרת של המחקר. הגיע הזמן להשיק אותו ב-Agentverse, ולהפוך אותו ממבנה מקומי לסוכן קבוע ומוכן לקרב שאפשר להפעיל בכל שלב על ידי כל משתמש. עכשיו נבצע פריסה של הסוכן ב-Cloud Run.
👈💻 מריצים את לחש הזימון הגדול הבא. הסקריפט הזה יוצר קודם את הסוכן שלכם כ-Golem מושלם (קובץ אימג' של קונטיינר), מאחסן אותו ב-Artifact Registry ואז פורס את ה-Golem הזה כשירות שניתן להרחבה, מאובטח ונגיש לכולם.
. ~/agentverse-dataengineer/set_env.sh
cd ~/agentverse-dataengineer/
echo "Building ${AGENT_NAME} agent..."
gcloud builds submit . \
--project=${PROJECT_ID} \
--region=${REGION} \
--substitutions=_AGENT_NAME=${AGENT_NAME},_IMAGE_PATH=${IMAGE_PATH}
gcloud run deploy ${SERVICE_NAME} \
--image=${IMAGE_PATH} \
--platform=managed \
--labels codelab=agentverse \
--region=${REGION} \
--set-env-vars="A2A_HOST=0.0.0.0" \
--set-env-vars="A2A_PORT=8080" \
--set-env-vars="GOOGLE_GENAI_USE_VERTEXAI=TRUE" \
--set-env-vars="GOOGLE_CLOUD_LOCATION=${REGION}" \
--set-env-vars="GOOGLE_CLOUD_PROJECT=${PROJECT_ID}" \
--set-env-vars="PROJECT_ID=${PROJECT_ID}" \
--set-env-vars="PUBLIC_URL=${PUBLIC_URL}" \
--set-env-vars="REGION=${REGION}" \
--set-env-vars="INSTANCE_NAME=${INSTANCE_NAME}" \
--set-env-vars="DB_USER=${DB_USER}" \
--set-env-vars="DB_PASSWORD=${DB_PASSWORD}" \
--set-env-vars="DB_NAME=${DB_NAME}" \
--allow-unauthenticated \
--project=${PROJECT_ID} \
--min-instances=1
נציג התמיכה שלכם ב-Scholar הוא עכשיו סוכן פעיל ומוכן לפעולה ב-Agentverse.
9. הטיסה הכי טובה
הקריאה במגילות הסתיימה, הטקסים בוצעו והמשימה הושלמה. הסוכן שלכם הוא לא רק פריט שמאוחסן, אלא ישות פעילה ב-Agentverse שמחכה למשימה הראשונה שלה. הגיע הזמן לניסיון האחרון – תרגיל ירי חי נגד יריב חזק.
עכשיו תיכנסו לסימולציה של שדה קרב כדי להציב את סוכן Shadowblade החדש שהפעלתם מול בוס משני אימתני: Spectre of the Static. זו תהיה הבדיקה הסופית של העבודה שלכם, מהלוגיקה הבסיסית של הנציג ועד לפריסה שלו בשידור חי.
איך מקבלים את המיקום של הנציג
כדי להיכנס לזירת הקרב, צריך להחזיק בשני מפתחות: החתימה הייחודית של הדמות (מיקום הסוכן) והנתיב הנסתר למאורה של הרוח (כתובת ה-URL של הצינוק).
👉💻 קודם צריך לקבל את הכתובת הייחודית של הנציג ב-Agentverse – המיקום שלו. זוהי נקודת הקצה הפעילה שמחברת את הדמות שלכם לזירת הקרב.
. ~/agentverse-dataengineer/set_env.sh
echo https://scholar-agent"-${PROJECT_NUMBER}.${REGION}.run.app"
👈💻 לאחר מכן, מציינים את היעד. הפקודה הזו חושפת את המיקום של מעגל ההעתקה, הפורטל אל הדומיין של ספקטר.
. ~/agentverse-dataengineer/set_env.sh
echo https://agentverse-dungeon"-${PROJECT_NUMBER}.${REGION}.run.app"
חשוב: צריך להכין את שתי כתובות ה-URL האלה. תצטרכו אותם בשלב האחרון.
התמודדות עם פרצת Spectre
אחרי שמוצאים את הקואורדינטות, מנווטים אל מעגל ההעתקה ומטילים את הכישוף כדי לצאת לקרב.
👈 פותחים את כתובת ה-URL של מעגל ההעברה בדפדפן כדי לעמוד מול הפורטל הנוצץ אל The Crimson Keep.
כדי לפרוץ את המבצר, צריך להתאים את מהות ה-Shadowblade לפורטל.
- בדף, מחפשים את שדה הקלט של הכתובת בכתב רוני שכותרתו A2A Endpoint URL.
- כדי להוסיף את הסמל של הדמות הראשית, מדביקים את כתובת ה-URL של מיקום הסוכן (כתובת ה-URL הראשונה שהעתקתם) בשדה הזה.
- לוחצים על 'התחברות' כדי להפעיל את הקסם של הטלפורטציה.
האור המסנוור של הטלפורטציה דועך. אתם כבר לא במקדש. האוויר רוחש באנרגיה, קרה וחדה. לפניכם, רוח הרפאים מתממשת – מערבולת של רעשי רקע וקוד פגום, והאור הטמא שלה מטיל צללים ארוכים ורוקדים על רצפת הצינוק. אין לו פנים, אבל אתם מרגישים את הנוכחות העצומה והמתישה שלו, שמתמקדת רק בכם.
הדרך היחידה שלכם לנצח היא להיות בטוחים בעצמכם. זהו דו-קרב של רצונות, שנערך בשדה הקרב של המוח.
כשאתם מסתערים קדימה, מוכנים לשחרר את המתקפה הראשונה, הספקטר מגיב. היא לא מעלה מגן, אלא מקרינה שאלה ישירות לתודעה שלכם – אתגר מנצנץ ורוני שנובע מליבת האימונים שלכם.
זה אופי המאבק. הידע שלך הוא הנשק שלך.
- ענה על השאלה לפי הידע שצברת, והלהב שלך יתלקח באנרגיה טהורה, ינפץ את ההגנה של הרוח וינחית מכה קריטית.
- אבל אם תהססו, אם ספק יעיב על התשובה שלכם, האור של הנשק ידעך. המכה תנחת עם חבטה עלובה, ותגרום רק לשבריר מהנזק שלה. גרוע מכך, הספקטר ינצל את חוסר הוודאות שלכם, והכוח המשחית שלו יגדל עם כל טעות שתעשו.
זהו, אלוף. הקוד הוא ספר הכישופים שלך, הלוגיקה היא החרב שלך והידע הוא המגן שיעצור את גלי הכאוס.
מצב פוקוס. פוגעים במטרה. העתיד של Agentverse תלוי בזה.
כל הכבוד, חוקר/ת.
סיימת את תקופת הניסיון. אתם מומחים בהנדסת נתונים, והופכים מידע גולמי וכאוטי לחוכמה מובנית ומווקטורית שמחזקת את כל Agentverse.
10. ניקוי: הסרת המשאבים של Scholar's Grimoire
ברכות על השלמת הספר Scholar's Grimoire! כדי לוודא ש-Agentverse נשאר נקי ושהשטח לאימון פנוי, עכשיו צריך לבצע את טקסי הניקוי הסופיים. כל המשאבים שנוצרו במהלך השימוש שלכם יימחקו באופן שיטתי.
השבתת רכיבי Agentverse
עכשיו תפרקו באופן שיטתי את הרכיבים שנפרסו במערכת ה-RAG.
מחיקה של כל השירותים של Cloud Run ומאגר Artifact Registry
הפקודה הזו מסירה את סוכן Scholar שפרסתם ואת אפליקציית Dungeon מ-Cloud Run.
👈💻 בטרמינל, מריצים את הפקודות הבאות:
. ~/agentverse-dataengineer/set_env.sh
gcloud run services delete scholar-agent --region=${REGION} --quiet
gcloud run services delete agentverse-dungeon --region=${REGION} --quiet
gcloud artifacts repositories delete ${REPO_NAME} --location=${REGION} --quiet
מחיקת מערכי נתונים, מודלים וטבלאות ב-BigQuery
הפעולה הזו מסירה את כל המשאבים של BigQuery, כולל מערך הנתונים bestiary_data
, כל הטבלאות שבו והחיבור והמודלים המשויכים.
👈💻 בטרמינל, מריצים את הפקודות הבאות:
. ~/agentverse-dataengineer/set_env.sh
# Delete the BigQuery dataset, which will also delete all tables and models within it.
bq rm -r -f --dataset ${PROJECT_ID}:${REGION}.bestiary_data
# Delete the BigQuery connection
bq rm --connection --project_id=${PROJECT_ID} --location=${REGION} gcs-connection --force
מחיקת המכונה של Cloud SQL
הפעולה הזו מסירה את מופע grimoire-spellbook
, כולל מסד הנתונים וכל הטבלאות שבו.
👈💻 בטרמינל, מריצים את הפקודה:
. ~/agentverse-dataengineer/set_env.sh
gcloud sql instances delete ${INSTANCE_NAME} --database-version=POSTGRES_14 --project=${PROJECT_ID} --quiet
מחיקת קטגוריות של Google Cloud Storage
הפקודה הזו מסירה את קטגוריית האחסון שהכילה את נתוני המודיעין הגולמיים ואת קובצי ההכנה/הזמניים של Dataflow.
👈💻 בטרמינל, מריצים את הפקודה:
. ~/agentverse-dataengineer/set_env.sh
gcloud storage rm -r gs://${BUCKET_NAME} --quiet
ניקוי של קבצים וספריות מקומיים (Cloud Shell)
לבסוף, מוחקים את המאגרים המשוכפלים והקבצים שנוצרו בסביבת Cloud Shell. השלב הזה הוא אופציונלי, אבל מומלץ מאוד כדי לנקות את ספריית העבודה באופן מלא.
👈💻 בטרמינל, מריצים את הפקודה:
rm -rf ~/agentverse-dataengineer
rm -rf ~/agentverse-dungeon
rm -f ~/project_id.txt
סיימתם למחוק את כל העקבות של המסע שלכם ב-Agentverse Data Engineer. הפרויקט שלכם נקי, ואתם מוכנים להרפתקה הבאה.
11. למי שלא משחקים: בניית מנועי ידע חכמים בעסקים
הספר "The Scholar's Grimoire" משתמש במטפורות מעניינות של מגילות עתיקות וחוכמה קסומה, אבל הוא מלמד מיומנויות חיוניות לניהול, לשינוי ולמינוף של נתוני הארגון כדי לבנות פתרונות AI חכמים במיוחד. בפרק הזה נסביר איך אפשר להפוך את המסע המיסטי למציאות מעשית של בניית 'מנועי ידע' עוצמתיים שמניבים ערך עסקי.
האלכימיה של הידע: שינוי נתונים באמצעות BigQuery ו-Gemini
המאמר "האלכימיה של הידע" מתאר את התהליך של הפיכת נתונים עסקיים גולמיים למידע מובנה ושימושי באמצעות כלים מתקדמים בענן. אנחנו מתחילים עם 'רשומות ביומן של Aether' – אלה פשוט מקורות מגוונים של נתונים גולמיים שהחברה שלכם מייצרת, כמו טפסים למשוב מלקוחות, דוחות פנימיים על אירועים, מסמכים משפטיים, מחקר שוק או מדריכי מדיניות. לרוב, הנתונים האלה לא מובנים, ולכן קשה לנתח אותם.
התהליך שלנו מתבצע באמצעות Google BigQuery (מחסן נתונים בענן) ומודל ה-AI של Gemini (מודל AI מתקדם).
- The Lens of Scrutiny (BigQuery External Tables):
- מושג: במקום להעביר פיזית את כל הנתונים הגולמיים למסד נתונים, BigQuery יכול 'להסתכל' על קבצים ישירות ב-Cloud Storage. זה כמו עדשה קסומה שמאפשרת לכם לקרוא ספרייה של מגילות בלי להזיז אותן. השיטה הזו יעילה מאוד כי היא מונעת תנועה ואחסון מיותרים של נתונים.
- תרחיש לדוגמה מהעולם האמיתי: נניח שהחברה שלכם מאחסנת מיליוני יומני צ'אט של תמיכת לקוחות כקובצי טקסט פשוטים בדלי אחסון בענן. באמצעות טבלה חיצונית, אנליסט נתונים יכול לשלוח שאילתות לקבצים האלה באופן מיידי באמצעות SQL ב-BigQuery, בלי צורך בתהליך מורכב ויקר של הטמעת נתונים.
- The Scholar's Divination (BQML.GENERATE_TEXT):
- הקונספט: זהו ה'קסם' המרכזי – שימוש ב-AI ישירות במחסן הנתונים. אנחנו משתמשים בפונקציה
ML.GENERATE_TEXT
כדי לקרוא למודל Gemini AI משאילתת SQL רגילה. כך ה-AI יכול 'לקרוא' רשומות טקסט ארוכות ולא מובנות ולחלץ מידע ספציפי ומובנה (כמו אובייקט JSON). זו דרך יעילה להפוך תצפיות איכותיות לנתונים כמותיים. - תרחיש שימוש בעולם האמיתי:
- ניתוח משוב מלקוחות: חילוץ אוטומטי של 'סנטימנט' (חיובי, שלילי, ניטרלי), 'המוצר שהוזכר' ו'קטגוריית הבעיה' מביקורות של לקוחות שכתובות בטקסט חופשי.
- סיכום דוחות על תקריות: ניתוח דוחות ארוכים על תקריות ב-IT כדי לחלץ את המידע 'המערכת שהושפעה', 'רמת החומרה', 'שורש הבעיה' ו'שלבי הפתרון' לפורמט מובנה, כדי להקל על הניתוח וזיהוי מגמות.
- שליפת התחייבויות חוזיות: שליפה אוטומטית של תאריכים חשובים, צדדים מעורבים וסעיפים ספציפיים ממסמכים משפטיים.
- כך לא צריך להזין נתונים באופן ידני או להשתמש בסקריפטים מורכבים ושבירים לניתוח טקסט (כמו ביטויים רגולריים), וגם חוסכים זמן רב וגם מבטיחים עקביות.
- הקונספט: זהו ה'קסם' המרכזי – שימוש ב-AI ישירות במחסן הנתונים. אנחנו משתמשים בפונקציה
- הטקס של הניקוי (נרמול הפלט של AI גנרטיבי):
- מושג: אחרי שה-AI מחלץ מידע, הוא לרוב מגיע עם פרטים נוספים (כמו ציוני מהימנות של ה-AI או מטא-נתונים אחרים). בשלב הזה צריך לנקות ולנתח את הפלט של ה-AI כדי לקבל רק את הנתונים המובנים והטהורים שאתם צריכים.
- תרחיש שימוש בעולם האמיתי: מוודאים שקטגוריית הבעיה שחולצה מדוח על תקרית היא תמיד אחת מתוך קבוצה מוגדרת מראש של ערכים, או שהתאריכים תמיד בפורמט עקבי. כך הנתונים מוכנים לניתוח מהימן.
- גילוי תובנות אסטרטגיות:
- מושג: אחרי שהנתונים הגולמיים הלא מובְנים שלכם עוברים שינוי לטבלאות נקיות ומובְנות (למשל,
monsters
,adventurers
,battles
ב-codelab), תוכלו לבצע שאילתות וניתוחים מורכבים שלא היו אפשריים קודם לכן. - תרחיש שימוש בעולם האמיתי: מעבר לספירה פשוטה, עכשיו אפשר לענות על שאלות כמו: "מהו זמן הטיפול הממוצע בתקריות קריטיות ב-IT שקשורות למערכת החיוב שלנו?" או "אילו תכונות מוצר מוזכרות הכי הרבה במשוב חיובי מלקוחות מקבוצה דמוגרפית ספציפית?" כך תוכלו לקבל תובנות עסקיות מעמיקות ופרקטיות.
- מושג: אחרי שהנתונים הגולמיים הלא מובְנים שלכם עוברים שינוי לטבלאות נקיות ומובְנות (למשל,
התהליך הזה מאפשר דפוס ELT (חילוץ, טעינה, טרנספורמציה) מבוסס-AI בתוך מסד הנתונים. זו גישה חדשנית ששומרת על אבטחת הנתונים במחסן הנתונים, מצמצמת את התנועה שלהם וממנפת את ה-AI לביצוע טרנספורמציות חזקות וגמישות באמצעות פקודות SQL פשוטות.
The Scribe's Grimoire: In-Datawarehouse Chunking, Embedding, and Search
טבלאות מובְנות מצוינות להצגת עובדות, אבל יכול להיות שהמשמעות הסמנטית העמוקה יותר של מסמכים מקוריים תאבד. המאמר 'הספר של הסופר' עוסק ביצירה של בסיס ידע סמנטי שמבין את המשמעות וההקשר של המסמכים שלכם, ולא רק מילות מפתח. זה חיוני לבניית מערכות חיפוש חכמות באמת ומערכות תשובות מבוססות-AI.
- הטקס של החלוקה (Chunking):
- מושג: מסמכים ארוכים הם כמו ספרים עבי כרס. כדי למצוא תשובות ספציפיות, לא קוראים את כל הספר, אלא סורקים פסקאות או משפטים ספציפיים. 'חלוקה לקטעים' היא תהליך של פירוק מסמכים ארוכים (למשל, מדריכי מדיניות, מסמכי מוצר, מאמרי מחקר) לקטעים קצרים יותר, ממוקדים יותר ועצמאיים. כך החיפוש מדויק יותר.
- תרחיש שימוש מהחיים האמיתיים: לוקחים מדריך לעובדים בן 50 עמודים ומפצלים אותו אוטומטית למאות הצהרות מדיניות או שאלות נפוצות. כך, כשהעובד שואל שאלה, ה-AI מאחזר רק את החלקים הרלוונטיים ביותר, ולא את כל המסמך. אסטרטגיות שונות של חלוקה לחלקים (לפי משפט, פסקה, קטע במסמך) נבחרות על סמך סוג המסמך כדי להשיג אחזור אופטימלי.
- הטקס של הזיקוק (הטמעה):
- מושג: קשה למחשבים להבין את המשמעות של טקסט. הטמעה משתמשת במודל AI (כמו Gemini) כדי להמיר כל נתח טקסט ל'טביעת אצבע סמנטית' מספרית ייחודית (וקטור). למקטעים עם משמעויות דומות יהיו 'טביעות אצבע' שערכיהן המספריים קרובים זה לזה, גם אם נעשה בהם שימוש במילים שונות.
- תרחיש לדוגמה בעולם האמיתי: המרת כל תיאורי המוצרים, החומרים השיווקיים והמפרטים הטכניים של החברה לטביעות האצבע הסמנטיות האלה. כך אפשר לבצע חיפוש חכם באמת שמבוסס על משמעות.
- הטקס של ניבוי העתיד (חיפוש סמנטי):
- המושג: במקום לחפש מילות מפתח מדויקות, 'חיפוש סמנטי' משתמש בטביעות האצבע המספריות האלה כדי למצוא מקטעי טקסט שדומים מבחינה מושגית לשאילתה של המשתמש. השאלה של המשתמש מומרת גם היא לטביעת אצבע, והמערכת מוצאת את חלקי המסמך שהכי דומים לה.
- תרחיש לדוגמה: עובד שואל, "איך מקבלים החזר על הוצאות נסיעה?" חיפוש מילות מפתח עלול לפספס מסמכים שבהם נעשה שימוש במונח 'דוח הוצאות'. לעומת זאת, חיפוש סמנטי ימצא קטעים רלוונטיים ב'מדיניות הנסיעות וההוצאות' של החברה, גם אם המילים המדויקות לא מופיעות בהם, כי המשמעות דומה.
בסיום התהליך הזה נוצר בסיס ידע עוצמתי שאפשר לחפש בו מידע, וכך אפשר לאחזר מידע בצורה חכמה בלי שמידע רגיש ייצא מסביבת BigQuery המאובטחת.
הסדנה ליצירת וקטורים: יצירת מאגר וקטורים באמצעות Cloud SQL להסקת מסקנות
BigQuery מצוין לעיבוד ולניתוח נתונים בקנה מידה גדול, אבל כדי לספק תשובות מהירות מאוד לסוכני AI בזמן אמת, אנחנו מעבירים את הנתונים המוכנים האלה למסד נתונים תפעולי וייעודי יותר. המאמר "The Vector Scriptorium" עוסק ביצירת מאגר ידע ניתן לחיפוש עם ביצועים גבוהים באמצעות מסד נתונים רלציוני שמשופר על ידי AI.
- Forging the Scholar's Spellbook (Cloud SQL for PostgreSQL with
pgvector
):- מושג: אנחנו משתמשים במסד נתונים מנוהל רגיל כמו Cloud SQL ל-PostgreSQL, ומציידים אותו בתוסף מיוחד שנקרא
pgvector
. כך מסד הנתונים יכול לאחסן גם את מקטעי הטקסט המקוריים וגם את ההטמעות הסמנטיות שלהם. הוא משמש כמרכז יחיד לניהול נתונים רלציוניים מסורתיים ונתוני וקטור שמתאימים ל-AI. - תרחיש שימוש בעולם האמיתי: אחסון של שאלות נפוצות על מוצרים, מאמרים בנושא תמיכה טכנית או מדיניות משאבי אנוש של החברה. במסד הנתונים הזה מאוחסנים גם הטקסט של התשובות וגם טביעות האצבע הסמנטיות שלהן, והוא מוכן לחיפושים מהירים באמצעות AI.
- מושג: אנחנו משתמשים במסד נתונים מנוהל רגיל כמו Cloud SQL ל-PostgreSQL, ומציידים אותו בתוסף מיוחד שנקרא
- יצירת המצפן הסמנטי (אינדקס HNSW):
- קונספט: חיפוש של מיליוני טביעות אצבע סמנטיות אחת אחרי השנייה יהיה איטי מדי. 'אינדקס וקטורי' (כמו HNSW – Hierarchical Navigable Small World) הוא מבנה נתונים מתוחכם שמארגן מראש את טביעות האצבע האלה, ומאפשר חיפוש מהיר יותר באופן משמעותי. הוא עוזר להפנות שאילתות במהירות למידע הרלוונטי ביותר.
- תרחיש שימוש בעולם האמיתי: בצ'אט-בוט לשירות לקוחות שמבוסס על AI, אינדקס HNSW מבטיח שכאשר לקוח שואל שאלה, המערכת יכולה למצוא את התשובה הרלוונטית ביותר מתוך אלפי מאמרים במילישניות, וכך לספק חוויית משתמש חלקה.
- הצינור להעברת משמעות (צינור וקטוריזציה של Dataflow):
- מושג: זהו צינור לעיבוד נתונים אוטומטי וניתן להרחבה לעדכון מתמשך של מאגר הידע. באמצעות Google Dataflow (שירות מנוהל ללא שרת לעיבוד נתונים גדולים) ו-Apache Beam (מודל תכנות), אתם בונים פס ייצור של 'סופרים' ש:
- לקרוא מסמכים חדשים או מעודכנים מאחסון בענן.
- מעבדים אותם באצווה כדי לשלוח אותם למודל Gemini להטמעת טביעת אצבע סמנטית.
- לכתוב את הטקסט ואת הטמעת הווקטור החדשה שלו במסד הנתונים של Cloud SQL.
- תרחיש שימוש בעולם האמיתי: הטמעה אוטומטית של כל המסמכים הפנימיים החדשים (למשל, דוחות רבעוניים, מדיניות משאבי אנוש מעודכנת, מפרטי מוצרים חדשים) מתיקיית אחסון שיתופי למסד הנתונים של
pgvector
. כך אפשר לוודא שמאגר הידע הפנימי שמבוסס על AI תמיד מעודכן, בלי התערבות ידנית, ושהוא יכול להתרחב כדי לטפל ביעילות במיליוני מסמכים.
- מושג: זהו צינור לעיבוד נתונים אוטומטי וניתן להרחבה לעדכון מתמשך של מאגר הידע. באמצעות Google Dataflow (שירות מנוהל ללא שרת לעיבוד נתונים גדולים) ו-Apache Beam (מודל תכנות), אתם בונים פס ייצור של 'סופרים' ש:
התהליך הזה יוצר תהליך עבודה אוטומטי ויעיל להעשרה ולתחזוקה מתמשכים של בסיס ידע סמנטי, שחיוני לכל אפליקציית AI מבוססת-נתונים.
השלמת הרונה האחרונה: הפעלת חוכמה באמצעות סוכן RAG
מאגר הידע הווקטורי מוכן. המאמר 'Sealing the Final Rune' (הטלת לחש הרונה האחרון) עוסק בהפעלת יועץ חכם מבוסס-AI שיכול לרתום את הידע הזה. אנחנו יוצרים סוכן RAG (Retrieval-Augmented Generation), מבנה AI עוצמתי שמשלב חיפוש חכם עם היכולת של AI ליצור תשובות עקביות.
- RAG (Retrieval-Augmented Generation):
- מושג: RAG היא טכניקה חשובה לשיפור הדיוק, העובדתיות והמהימנות של מודלים גדולים של שפה (LLM). במקום להסתמך רק על הידע שאומן מראש במודל שפה גדול (שעשוי להיות מיושן או להיות מועד ל"הזיות" – המצאת דברים), RAG קודם מאחזר מידע רלוונטי מבסיס הידע הסמכותי שלכם, ואז משתמש במידע הזה כדי להרחיב את ההנחיה למודל השפה הגדול, וכך מכוון אותו לייצר תשובה מדויקת שמתאימה להקשר.
- שלושה שלבים מרכזיים:
- אחזור: השאלה של המשתמש מומרת לווקטור (טביעת אצבע סמנטית), שמשמש לחיפוש במאגר הנתונים
pgvector
שלכם את חלקי הטקסט הרלוונטיים ביותר. - הוספה: קטעי הטקסט העובדתיים האלה נשלפים ומוכנסים ישירות להנחיה שניתנת למודל ה-LLM, כדי לספק לו הקשר ספציפי ועדכני.
- יצירה: מודל ה-LLM מקבל את ההנחיה המשופרת הזו ומייצר תשובה סופית שמבוססת על נתונים מהימנים של החברה, וכך מצמצם את הסיכון לשגיאות או למידע מומצא.
- אחזור: השאלה של המשתמש מומרת לווקטור (טביעת אצבע סמנטית), שמשמש לחיפוש במאגר הנתונים
- הכלי Scholar's Examination (
grimoire_lookup
):- מושג: סוכן ה-RAG שלכם הופך ל'חוקר' שיש לו כלי
grimoire_lookup
. כשמשתמש שואל שאלה, הסוכן מחליט בצורה חכמה להשתמש בכלי הזה. הפונקציהgrimoire_lookup
מבצעת את השלב 'אחזור' על ידי המרת השאילתה להטמעה וחיפוש במסד הנתוניםpgvector
. ההקשר שאוחזר מועבר אל מודל השפה הגדול הראשי לצורך הרחבה ויצירה. - מקרה שימוש בעולם האמיתי: צ'אטבוט מבוסס-AI למוקד תמיכה פנימי.
- שאלה של משתמש: עובד שואל, "מה התהליך לבקשת חופשה ארוכה מסיבות רפואיות?"
- פעולה של סוכן RAG:
scholar_agent
מזהה את הצורך במידע ומשתמש בכליgrimoire_lookup
.- הכלי ממיר את השאלה להטמעה ומחפש בטבלה
ancient_scrolls
במסד הנתוניםpgvector
. - הוא מאחזר את החלקים הרלוונטיים ביותר ממסמך מדיניות משאבי האנוש בנושא חופשת מחלה.
- החלקים האלה מוזנים כהקשר ל-LLM של Gemini.
- לאחר מכן, מודל ה-LLM של Gemini יוצר תשובה מדויקת ומפורטת שמבוססת רק על מדיניות משאבי האנוש שאותרה, וכך מצמצם את הסיכוי למתן מידע שגוי או לא מעודכן.
- כך העובדים מקבלים תשובות מיידיות ומדויקות שמבוססות על מסמכים רשמיים של החברה, עומס העבודה על מחלקת משאבי האנוש מצטמצם ושביעות הרצון של העובדים משתפרת.
- מושג: סוכן ה-RAG שלכם הופך ל'חוקר' שיש לו כלי
כך נוצר סוכן AI שהוא לא רק שימושי לשיחה, אלא גם בעל ידע ומהימן, ומשמש כמקור מידע מהימן בארגון.