مدیریت داده‌های تاریک بدون ساختار با Gemini و Knowledge Catalog

۱. مقدمه

بیش از ۸۰٪ از داده‌های سازمانی در قالب‌های بدون ساختار قرار دارند - کتابچه‌های راهنمای مهندسی PDF، رویه‌های عملیاتی استاندارد (SOPs)، گواهی‌های انطباق و طرح‌های تجهیزات ذخیره شده در فضای ذخیره‌سازی ابری . از آنجا که کاتالوگ‌های سنتی فقط طرح‌های جداول رابطه‌ای را فهرست می‌کنند، این اسناد "داده‌های تاریک" باقی می‌مانند: برای جستجوی سازمانی نامرئی، از جداول موجودی ساختاریافته جدا و برای انطباق با مقررات تأیید نشده‌اند.

وقتی یک حسابرس یا عامل هوش مصنوعی می‌پرسد: «کدام SKUهای سخت‌افزاری به گواهینامه ایمنی UL-153 نیاز دارند و سطح خطر حرارتی آنها چقدر است؟» ، کاتالوگی که فقط جداول SQL را فهرست‌بندی می‌کند، نمی‌تواند پاسخ دهد. حقایق در داخل فایل‌های PDF بدون ساختار در فضای ذخیره‌سازی ابری قفل شده‌اند.

راهکار معماری: فراداده چندوجهی به عنوان کد

در این آزمایشگاه کد، شما یک خط لوله فراداده به عنوان کد سرتاسری در Google Cloud می‌سازید که کتابچه‌های راهنمای PDF بدون ساختار در Cloud Storage را با استفاده از پلتفرم Gemini Enterprise Agent ( Google GenAI SDK ، google-genai ) به دارایی‌های کاتالوگ دانش مبتنی بر طرحواره تبدیل می‌کند:

جریان مدیریت داده‌های تاریک بدون ساختار

  1. ثبت مجموعه فایل‌ها ( EntryGroup و Entry ) : فایل‌های PDF بدون ساختار در فضای ذخیره‌سازی ابری را در مجموعه فایل‌های منطقیِ مدیریت‌شده در Knowledge Catalog گروه‌بندی می‌کند.
  2. استخراج چندوجهی Gemini ( Pydantic Schema) : پلتفرم عامل سازمانی Gemini را روی بایت‌های خام PDF با اعتبارسنجی قطعی response_schema فراخوانی می‌کند.
  3. اتصال جنبه صفحه کنترل : بارهای عملیاتی و انطباقی JSON معتبر را به عنوان نمونه‌های Aspect با نوع قوی به ورودی کاتالوگ متصل می‌کند.
  4. کشف یکپارچه کاتالوگ : مجموعه فایل‌های PDF بدون ساختار و فراداده‌های استخراج‌شده از آنها را از طریق SearchEntriesRequest قابل کشف می‌کند.

مفاهیم کلیدی: عناصر اولیه صفحه کنترل کاتالوگ دانش

تصور کنید تیم شما صدها دفترچه راهنمای محصول PDF را در فضای ذخیره‌سازی ابری ذخیره می‌کند. برای اینکه بتوانید این فایل‌ها را به راحتی پیدا کنید و در کاتالوگ دانش بررسی کنید، به پنج بلوک سازنده مانند سازماندهی دفترچه‌های راهنمای کاغذی در یک کابینت بایگانی اداری فکر کنید:

  • EntryGroup (یک کابینت قفل‌شده برای یک تیم): کابینتی با قفل روی آن. فقط هم‌تیمی‌های دارای مجوز ( roles/dataplex.entryCreator ) می‌توانند پوشه‌ها را داخل آن قرار دهند. قبل از اینکه بتوانید خود کابینت را بردارید، باید تمام پوشه‌های داخل کابینت را خالی کنید.
  • EntryType (برچسب دسته‌بندی پوشه): برچسبی که به افراد می‌گوید یک پوشه نشان‌دهنده چه نوع دارایی است - برای مثال، به جای «جدول پایگاه داده» ، «مجموعه کتابچه راهنمای PDF» را انتخاب کنید .
  • Entry (یک پوشه فایل با لینک ذخیره‌سازی): پوشه کاتالوگ برای کتابچه‌های راهنمای PDF شما. این پوشه به جای نگه‌داری نسخه‌های کاغذی ضخیم، یک کارت مکان را در خود جای می‌دهد که دقیقاً به محل ذخیره‌سازی ابری ( gs://... ) که فایل‌های PDF واقعی در آن قرار دارند، اشاره می‌کند.
  • AspectType (فرم چک‌لیست خالی): یک فرم خالی قابل استفاده مجدد با کادرهای از پیش چاپ شده (برای مثال، یک "چک‌لیست ایمنی" که operational_hazard_level به صورت متن و confidence_score به صورت عددی از 0.0 تا 1.0 درخواست می‌کند). شما این فرم خالی را یک بار ایجاد می‌کنید و آن را در هزاران پوشه دوباره استفاده می‌کنید.
  • Aspect (یک چک لیست تکمیل شده که به یک پوشه متصل شده است): پس از اینکه Gemini Enterprise Agent Platform دفترچه راهنمای PDF را می‌خواند و جاهای خالی را پر می‌کند، آن چک لیست تکمیل شده به پوشه Entry متصل می‌شود. از آنجا که هر چک لیست کلید مخصوص به خود ( aspect_keys ) را دارد، تیم مهندسی و تیم حقوقی می‌توانند هر کدام چک لیست خود را بدون رونویسی کار یکدیگر به همان پوشه متصل کنند.

هر پنج منبع منطقه‌ای در مسیر projects/{project}/locations/{location}/ قرار دارند:

مسیر اولیه و نسبی

نقش در کاتالوگ دانش

حذف و قانون IAM

EntryGroup
.../entryGroups/{id}

یک کانتینر منطقی که ورودی‌ها را گروه‌بندی کرده و دسترسی تیمی ( roles/dataplex.entryCreator ) را کنترل می‌کند.

قبل از حذف، باید حاوی منابع Entry بدون فرزند باشد.

EntryType
.../entryTypes/{id}

تعریف دسته‌بندی برای یک کلاس از دارایی‌ها ( entry.entry_type ، مانند مجموعه فایل‌های PDF بدون ساختار).

فقط پس از حذف تمام ورودی‌هایی که از این نوع استفاده می‌کنند، حذف کنید.

Entry (مجموعه فایل)
.../entries/{entry_id}

رکورد کاتالوگ که یک URI فیزیکی فضای ذخیره‌سازی ابری ( entry_source.resource ) را به یک نام منطقی ( gcs:{bucket} ) پیوند می‌دهد.

درون یک EntryGroup قرار دارد و رکوردهای Aspect پیوست شده را نگهداری می‌کند.

AspectType
.../aspectTypes/{id}

الگوی طرحواره قابل استفاده مجدد که record_fields نوع‌دار ( string ، enum ، double ) و شماره‌های فیلد مبتنی بر ۱ ( index ) را تعریف می‌کند.

یک بار در هر منطقه ایجاد شده و در بین ورودی‌ها به اشتراک گذاشته می‌شود.

Aspect
Entry.aspects[key]

متادیتای JSON اعتبارسنجی شده که با یک AspectType مطابقت دارد و از طریق UpdateEntryRequest به یک Entry متصل شده است.

با استفاده از update_mask و aspect_keys به‌روزرسانی شد تا خطوط لوله جداگانه روی هم بازنویسی نشوند.

آنچه خواهید ساخت

با استفاده از اسکریپت‌های همراه در codelabs/metadata-as-code-lab ، یک خط لوله ۷ مرحله‌ای را اجرا و بررسی خواهید کرد:

  1. schemas.py — طرحواره‌های دوگانه Pydantic BaseModel ( DarkDataExtractedMetadata و DocumentGovernanceMetadata ) که به صورت ۱:۱ با الگوهای Knowledge Catalog AspectType جفت شده‌اند.
  2. step2_provision.py — آماده‌سازی خودبه‌خودی طرح‌های سفارشی EntryGroup ، EntryType و AspectType .
  3. step3_register_fileset.py — آپلود فایل LUM-LIG-DES-8G8J_manual.pdf در فضای ابری و ثبت آن به عنوان یک Entry مجموعه فایل تحت مدیریت.
  4. step4_extract_metadata.py — کشف مدل دینامیکی پرچمدار جمینی و استخراج چندوجهی PDF با استفاده از google-genai .
  5. step5_attach_aspects.py ، step6_search_catalog.py ، و step7_verify_assertions.py — پیوست جراحی جنبه، جستجوی کاتالوگ با پس‌روی نمایی، و ادعاهای صفحه کنترل سرتاسری.

پیش‌نیازها و آنچه نیاز خواهید داشت

  • یک پروژه گوگل کلود با قابلیت پرداخت و پوسته گوگل کلود (از پیش نصب شده با gcloud ، git ، python3 و pip ).
  • مجوزهای IAM برای مدیریت منابع کاتالوگ دانش ( roles/dataplex.admin )، فراهم کردن سطل‌ها و اشیاء ذخیره‌سازی ابری ( roles/storage.admin ) و فراخوانی پلتفرم عامل سازمانی Gemini ( roles/aiplatform.user ).
  • یک مرورگر وب مانند گوگل کروم .

۲. تنظیمات و الزامات

مخزن همراه را در Cloud Shell کلون کنید

کنسول گوگل کلود را باز کنید، کلود شل را اجرا کنید و یک بررسی پراکنده از codelabs/metadata-as-code-lab انجام دهید که شامل نمونه راهنمای مهندسی PDF ( LUM-LIG-DES-8G8J_manual.pdf ) و تمام اسکریپت‌های پایتون است:

git clone --branch main --depth 1 --filter=blob:none --sparse \
  https://github.com/GoogleCloudPlatform/devrel-demos.git
cd devrel-demos
git sparse-checkout set codelabs/metadata-as-code-lab
cd codelabs/metadata-as-code-lab
ls -la

پیکربندی متغیرهای محیطی

شناسه پروژه، موقعیت صفحه کنترل منطقه‌ای و مخزن ذخیره‌سازی ابری هدف خود را در Cloud Shell تنظیم کنید:

export PROJECT_ID="${PROJECT_ID:-$(gcloud config get-value project)}"
gcloud config set project $PROJECT_ID

export REGION="us-central1"
export BUCKET_NAME="${PROJECT_ID}-dark-data-manuals"
export GEMINI_LOCATION="global"

echo "Configured Project ID        : $PROJECT_ID"
echo "Knowledge Catalog Region     : $REGION"
echo "Gemini Endpoint Location     : $GEMINI_LOCATION"
echo "Target Cloud Storage Bucket  : $BUCKET_NAME"

فعال کردن APIها و نصب وابستگی‌ها

APIهای مورد نیاز Google Cloud را فعال کنید و وابستگی‌های پایتون ( google-genai ، google-cloud-dataplex ، pydantic و pandas ) را از requirements.txt نصب کنید:

gcloud services enable \
  dataplex.googleapis.com \
  storage.googleapis.com \
  aiplatform.googleapis.com \
  --quiet
python3 -m pip install --upgrade --quiet --user --break-system-packages -r requirements.txt

۳. طرحواره‌های پیدانتیک و الگوهای جنبه را تعریف کنید

schemas.py دو قرارداد مکمل تعریف می‌کند که اعتبارسنجی Pydantic سمت کلاینت را با قالب‌های Knowledge Catalog AspectType سمت سرور جفت می‌کند:

  1. DarkDataExtractedMetadata : ویژگی‌های عملیاتی استخراج‌شده از PDF (عنوان سند، هستی‌شناسی دامنه، سطح خطر ایمنی، منشأ نگارش/نسخه، خلاصه اجرایی و امتیاز اطمینان استخراج).
  2. DocumentGovernanceMetadata : کدهای انطباق با مقررات (UL-153، FCC Part 15، CE-LVD، RoHS)، مالک ناظر، سیاست نگهداری، و یک رشته شناسه جدول مرجع ( lakehouse_cross_ref_table ) برای پیوند دادن دفترچه راهنمای PDF به جداول موجودی پایین‌دستی.

بررسی schemas.py

اول، DarkDataExtractedMetadata از محدودیت‌های Pydantic Field ( ge=0.0, le=1.0 ، به معنی بزرگتر/کوچکتر یا مساوی، در confidence_score ) برای محدود کردن خروجی JSON پلتفرم Gemini Enterprise Agent استفاده می‌کند:

class DarkDataExtractedMetadata(BaseModel):
    document_title: str = Field(
        description="Official document title or product model name extracted from the PDF manual."
    )
    # ... domain_ontology, operational_hazard_level, author_provenance ...
    version_provenance: str = Field(
        description="Document version, revision code, or publication standard identifier."
    )
    # ... document_summary ...
    confidence_score: float = Field(
        ge=0.0,
        le=1.0,
        description="AI extraction confidence metric between 0.0 and 1.0.",
    )

دوم، extracted_aspect_template دقیقاً همان نام فیلدها را منعکس می‌کند و انواع str و float پایتون را به string و double مربوط record_fields مربوط به Knowledge Catalog نگاشت می‌کند. توجه داشته باشید که قرارداد AspectType.MetadataTemplate protobuf ایجاب می‌کند که هر فیلد در record_fields یک index عدد صحیح منحصر به فرد و کاملاً مثبت مبتنی بر ۱ ( 1 تا 7 ) اعلام کند - حذف یا تکرار index باعث می‌شود create_aspect_type با خطای 400 INVALID_ARGUMENT مواجه شود:

extracted_aspect_template = {
    "name": "DarkDataExtractedMetadata",
    "type": "record",
    "record_fields": [
        {
            "name": "document_title",
            "type": "string",
            "index": 1,
            "annotations": {"description": "Official document title or product model name."},
        },
        # ... fields 2 through 6 (string) ...
        {
            "name": "confidence_score",
            "type": "double",
            "index": 7,
            # ... annotations ...
        },
    ],
}

اعتبارسنجی ماژول طرحواره

برای تأیید پیکربندی محیط و کامپایل هر دو طرحواره، schemas.py را اجرا کنید:

python3 schemas.py
Configured Project ID         : your-project-id
Knowledge Catalog Region      : us-central1
Gemini Endpoint Location      : global
Governed Fileset Storage URI  :
  gs://your-project-id-dark-data-manuals/sop-pdfs/LUM-LIG-DES-8G8J_manual.pdf
Target Fileset Entry ID       : sop-manuals-fileset-lum8g8j
✓ Defined DarkDataExtractedMetadata and DocumentGovernanceMetadata
  Pydantic schemas.
✓ Prepared Knowledge Catalog AspectType metadata templates.

۴. ارائه فضاهای نام و انواع جنبه‌های سفارشی

قبل از ثبت ورودی‌های مجموعه فایل یا پیوست کردن فراداده، step2_provision.py سه منبع صفحه کنترل را در کاتالوگ دانش فراهم می‌کند:

  • EntryGroup : dark-data-fileset-group
  • EntryType : unstructured-pdf-fileset
  • طرح‌های AspectType : dark-data-extracted-metadata و document-governance-aspect

تأمین خودکار در step2_provision.py

هر فراخوانی ساخت در step2_provision.py عملیات طولانی‌مدت ( op.result() ) را در یک بلوک try / except AlreadyExists قرار می‌دهد تا اسکریپت بتواند بدون خطا روی منابع موجود، دوباره و با خیال راحت اجرا شود:

# Provision AspectType 1: dark-data-extracted-metadata
try:
    at1_op = catalog_client.create_aspect_type(
        parent=parent_location,
        aspect_type_id=EXTRACTED_ASPECT_TYPE_ID,
        aspect_type=AspectType(
            name=extracted_aspect_type_name,
            display_name="Dark Data Multimodal Extracted Metadata",
            # ... description ...
            metadata_template=extracted_aspect_template,
        ),
    )
    if hasattr(at1_op, "result"):
        at1_op.result()
    print(f"Created AspectType: {extracted_aspect_type_name}")
except AlreadyExists:
    print(f"AspectType already exists; retrieving live resource: {extracted_aspect_type_name}")

live_extracted_aspect_type = catalog_client.get_aspect_type(name=extracted_aspect_type_name)

پس از ثبت metadata_template=extracted_aspect_template ، کاتالوگ دانش ، طرحواره را در مرز API اعمال می‌کند - هرگونه فراخوانی بعدی update_entry() که رشته‌ای را به confidence_score ( double ) ارسال کند، رد می‌شود.

اجرای step2_provision.py

اسکریپت تأمین را اجرا کنید و تأیید کنید که انواع جنبه‌های سفارشی در منطقه شما ثبت شده‌اند:

python3 step2_provision.py
gcloud dataplex aspect-types list --location=$REGION
Created EntryGroup:
  projects/your-project-id/locations/us-central1/entryGroups/
  dark-data-fileset-group
Created EntryType :
  projects/your-project-id/locations/us-central1/entryTypes/
  unstructured-pdf-fileset
Created AspectType:
  projects/your-project-id/locations/us-central1/aspectTypes/
  dark-data-extracted-metadata
Created AspectType:
  projects/your-project-id/locations/us-central1/aspectTypes/
  document-governance-aspect
✓ All Knowledge Catalog namespaces and AspectType blueprints are active.

۵. ثبت ورودی‌های بدون ساختار مجموعه فایل‌ها

به جای شلوغ کردن کاتالوگ با میلیون‌ها اشاره‌گر فایل مجزا، کاتالوگ دانش ، اسناد مرتبط در فضای ذخیره‌سازی ابری ( gs://YOUR_BUCKET/sop-pdfs/*.pdf ) را در ورودی‌های منطقی مجموعه فایل گروه‌بندی می‌کند - یا از طریق اسکن‌های کشف خودکار ( DataScanServiceClient ) یا ثبت مستقیم برنامه‌نویسی ( CatalogServiceClient.create_entry ).

چگونه step3_register_fileset.py فضای ذخیره‌سازی را به کاتالوگ نگاشت می‌کند؟

step3_register_fileset.py فایل LUM-LIG-DES-8G8J_manual.pdf را در gs://${BUCKET_NAME}/sop-pdfs/LUM-LIG-DES-8G8J_manual.pdf آپلود می‌کند و Entry کنترل‌شده را ثبت می‌کند:

fully_qualified_fileset_uri = f"gcs:{BUCKET_NAME}"
fileset_entry_spec = Entry(
    name=fileset_entry_name,
    entry_type=entry_type_resource_name,
    fully_qualified_name=fully_qualified_fileset_uri,
    entry_source=EntrySource(
        resource=VIRTUAL_STORAGE_URI,
        system="Cloud Storage",
        platform="Google Cloud",
        display_name="LUM-LIG-DES-8G8J Unstructured SOP & Technical Manual Fileset",
        # ... description ...
        location=REGION,
    ),
)

create_entry_op = catalog_client.create_entry(
    parent=entry_group_resource_name,
    entry_id=FILESET_ENTRY_ID,
    entry=fileset_entry_spec,
)

به نقش‌های متمایز دو فیلد URI در Entry توجه کنید:

  • fully_qualified_name=fully_qualified_fileset_uri ( f"gcs:{BUCKET_NAME}" ): از طرح FQN استاندارد gcs:{bucket_name} که توسط Knowledge Catalog مورد نیاز است، برای مرتبط کردن ورودی منطقی کاتالوگ با باکت Cloud Storage زیرین استفاده می‌کند.
  • entry_source.resource=VIRTUAL_STORAGE_URI : آدرس فیزیکی gs:// شیء که توسط کارگران استخراج پایین‌دستی بررسی شده است را ذخیره می‌کند.

اجرای step3_register_fileset.py

python3 step3_register_fileset.py
Created Cloud Storage bucket:
  gs://your-project-id-dark-data-manuals in us-central1
Uploaded unstructured PDF manual to:
  gs://your-project-id-dark-data-manuals/sop-pdfs/LUM-LIG-DES-8G8J_manual.pdf
Registered governed Fileset Entry:
  projects/your-project-id/locations/us-central1/entryGroups/
  dark-data-fileset-group/entries/sop-manuals-fileset-lum8g8j
  -> Fully Qualified Name : gcs:your-project-id-dark-data-manuals
  -> Physical Resource URI:
  gs://your-project-id-dark-data-manuals/sop-pdfs/LUM-LIG-DES-8G8J_manual.pdf
  -> Source System        : Cloud Storage

۶. استخراج فراداده‌های سند با Gemini

step4_extract_metadata.py بایت‌های خام PDF را می‌خواند و با استفاده از دو الگوی کلیدی، Gemini Enterprise Agent Platform ( genai_client.models.generate_content ) را فراخوانی می‌کند:

۱. کشف مدل پرچمدار پویا

به جای کدگذاری رشته‌های نسخه مدل شکننده، اسکریپت از genai_client.models.list() پرس‌وجو می‌کند و نامزدهای فعال را بر اساس (is_ga_channel, semantic_version_tuple) مرتب می‌کند تا جدیدترین مدل flash دسترسی عمومی (GA) را انتخاب کند:

genai_client = genai.Client(
    vertexai=True,
    project=PROJECT_ID,
    location=GEMINI_LOCATION,
)

for model_obj in genai_client.models.list():
    raw_id = (model_obj.name or "").split("/")[-1]
    # Filter to flagship Gemini Flash models (version >= 3.0) and prioritize GA over preview
    ...
    discovered_candidates.append((is_ga_channel, ver_tuple, raw_id))

discovered_candidates.sort(key=lambda item: (item[0], item[1]), reverse=True)

۲. استخراج چندوجهی با محدودیت طرحواره ( Part.from_bytes + response_schema )

ارسال response_mime_type="application/json" و response_schema=DarkDataExtractedMetadata (و به دنبال آن DocumentGovernanceMetadata ) رمزگشایی توکن را مستقیماً به طرح JSON مربوط به Pydantic محدود می‌کند:

with open(LOCAL_PDF_PATH, "rb") as pdf_file:
    raw_pdf_bytes = pdf_file.read()

extraction_response = genai_client.models.generate_content(
    model=candidate_model,
    contents=[
        types.Part.from_bytes(data=raw_pdf_bytes, mime_type="application/pdf"),
        extraction_prompt,
    ],
    config=types.GenerateContentConfig(
        response_mime_type="application/json",
        response_schema=DarkDataExtractedMetadata,
        temperature=0.1,
    ),
)

extracted_dark_data = json.loads(extraction_response.text)
validated_extraction = DarkDataExtractedMetadata(**extracted_dark_data)

اجرای step4_extract_metadata.py

python3 step4_extract_metadata.py
Dynamically discovered active GA model currency :
  gemini-3.8-flash (version (3, 8))
Loaded unstructured PDF manual at: LUM-LIG-DES-8G8J_manual.pdf
Read unstructured PDF document (1184 bytes).
  Executing multimodal extraction with gemini-3.8-flash...
✓ Multimodal extraction completed using model: gemini-3.8-flash
✓ Governance classification completed using model: gemini-3.8-flash

--- Extracted Multimodal Operational Metadata ---
Extracted Attribute    Multimodal Value
document_title    LUM-LIG-DES-8G8J Contemporary Linen Desk Lamp
domain_ontology    Electrical Hardware & Lighting Systems
operational_hazard_level    MEDIUM
author_provenance    Global Hardware Safety & Lighting Systems Engin
version_provenance    Rev 4.2
document_summary    This document outlines standard operating proce
confidence_score    0.99

--- Extracted Governance & Inventory Cross-Reference Metadata ---
Governance Attribute    Classification Value
compliance_classifications    UL-153 Portable Luminaires, FCC Part 15, CE-LVD
stewardship_owner    Global Hardware Safety & Lighting Systems Engin
retention_policy    10-Year Active Product Lifecycle Archival
lakehouse_cross_ref_table    lakehouse.your-project-id.retail_hardware
governance_status    VERIFIED_PRODUCTION

۷. جنبه‌های اعتبارسنجی‌شده را به ورودی‌های کاتالوگ اضافه کنید

step5_attach_aspects.py داده‌های JSON معتبر ( extracted_metadata.json و governance_metadata.json ) را از طریق catalog_client.update_entry() به ورودی sop-manuals-fileset-lum8g8j متصل می‌کند.

جهش جنبه جراحی در step5_attach_aspects.py

extracted_aspect_key = f"{PROJECT_ID}.{REGION}.{EXTRACTED_ASPECT_TYPE_ID}"
governance_aspect_key = f"{PROJECT_ID}.{REGION}.{GOVERNANCE_ASPECT_TYPE_ID}"

updated_entry_payload = Entry(
    name=fileset_entry_name,
    entry_type=entry_type_resource_name,
    fully_qualified_name=fully_qualified_fileset_uri,
    aspects={
        extracted_aspect_key: Aspect(
            aspect_type=extracted_aspect_type_name,
            data=extracted_data,
        ),
        governance_aspect_key: Aspect(
            aspect_type=governance_aspect_type_name,
            data=governance_data,
        ),
    },
)

update_op = catalog_client.update_entry(
    request=dataplex_v1.UpdateEntryRequest(
        entry=updated_entry_payload,
        update_mask={"paths": ["aspects"]},
        aspect_keys=[extracted_aspect_key, governance_aspect_key],
    )
)

ارسال هر دو update_mask={"paths": ["aspects"]} و aspect_keys=[extracted_aspect_key, governance_aspect_key] جهش را منحصراً به این دو کلید جنبه محدود می‌کند - entry_source و هر جنبه‌ای که متعلق به تیم‌های دیگر است دست نخورده باقی می‌ماند.

اجرای step5_attach_aspects.py

python3 step5_attach_aspects.py
Successfully bound 2 Aspect(s) to Entry:
  projects/your-project-id/locations/us-central1/entryGroups/
  dark-data-fileset-group/entries/sop-manuals-fileset-lum8g8j

=== Live Attached Aspect: document-governance-aspect ===
Catalog Field    Authoritative Stored Value
compliance_classifications    UL-153 Portable Luminaires, FCC Part 15, CE-LVD
stewardship_owner    Global Hardware Safety & Lighting Systems Engin
retention_policy    10-Year Active Product Lifecycle Archival
lakehouse_cross_ref_table    lakehouse.your-project-id.retail_hardware
governance_status    VERIFIED_PRODUCTION

=== Live Attached Aspect: dark-data-extracted-metadata ===
Catalog Field    Authoritative Stored Value
document_title    LUM-LIG-DES-8G8J Contemporary Linen Desk Lamp
domain_ontology    Electrical Hardware & Lighting Systems
operational_hazard_level    MEDIUM
author_provenance    Global Hardware Safety & Lighting Systems Engin
version_provenance    Rev 4.2
document_summary    This document outlines standard operating proce
confidence_score    0.99

تأیید دو مرحله‌ای

  • مسیر ۱ (تأیید CLI): ورودی را با تمام جنبه‌های پیوست شده از طریق gcloud بررسی کنید:
    gcloud dataplex entries describe sop-manuals-fileset-lum8g8j \
      --entry-group=dark-data-fileset-group \
      --location=$REGION \
      --view=ALL
    
  • مسیر ۲ (بازرسی رابط کاربری کنسول):
    1. کنسول جستجوی کاتالوگ دانش را باز کنید، مجموعه فایل راهنمای فنی و دستورالعمل‌های عملیاتی بدون ساختار LUM-LIG-DES-8G8J ( sop-manuals-fileset-lum8g8j ) را جستجو کنید و ورودی منطبق را از نتایج انتخاب کنید.
    2. در بخش برچسب‌ها و جنبه‌های اختیاری (Optional tags and aspects )، تأیید کنید که هر دو بخش Dark Data Multimodal Extracted Metadata و Document Governance & Inventory Cross-Reference Aspect ، سطح خطر استخراج‌شده ( MEDIUM )، کدهای انطباق ( UL-153, FCC Part 15, CE-LVD, RoHS ) و رشته جدول ارجاع متقابل ( lakehouse_cross_ref_table ) را نمایش می‌دهند.

۸. داده‌های تاریکِ تحت کنترل پرس‌وجو در کاتالوگ

پس از پیوست شدن جنبه‌های سفارشی، کتابچه‌های راهنمای PDF بدون ساختار در فضای ذخیره‌سازی ابری از طریق جستجوی کاتالوگ دانش ( catalog_client.search_entries() ) قابل کشف می‌شوند.

نمونه‌برداری از search_entries() در step6_search_catalog.py

step6_search_catalog.py polls search_entries() را با backoff نمایی اجرا می‌کند و کلیدهای جنبه استاندارد شده را از طریق .endswith() می‌خواند:

search_query = f"entrygroup={entry_group_resource_name} name:{FILESET_ENTRY_ID}"

while elapsed_seconds < max_wait_seconds:
    catalog_search_results = list(
        catalog_client.search_entries(
            request=dataplex_v1.SearchEntriesRequest(
                name=parent_location,
                query=search_query,
            )
        )
    )
    if catalog_search_results:
        break
    backoff_seconds = min(5 * (2 ** attempt), 30)
    time.sleep(backoff_seconds)
    ...

for k, asp in detailed_entry.aspects.items():
    if k.endswith(f".{REGION}.{EXTRACTED_ASPECT_TYPE_ID}"):
        print(f"    Domain Ontology     : {asp.data.get('domain_ontology')}")
        print(f"    Hazard Level        : {asp.data.get('operational_hazard_level')}")
    elif k.endswith(f".{REGION}.{GOVERNANCE_ASPECT_TYPE_ID}"):
        print(f"    Compliance Codes    : {asp.data.get('compliance_classifications')}")
        print(f"    Lakehouse Join Table: {asp.data.get('lakehouse_cross_ref_table')}")

اجرای step6_search_catalog.py

python3 step6_search_catalog.py
Executing Knowledge Catalog search query:
  'entrygroup=projects/your-project-id/locations/us-central1/entryGroups/
  dark-data-fileset-group name:sop-manuals-fileset-lum8g8j'...

✓ Discovered 1 governed asset(s) in Knowledge Catalog:

[1] Entry Resource Name :
    projects/your-project-id/locations/us-central1/entryGroups/
    dark-data-fileset-group/entries/sop-manuals-fileset-lum8g8j
    Fully Qualified Name: gcs:your-project-id-dark-data-manuals
    Entry Type :
    projects/your-project-id/locations/us-central1/entryTypes/
    unstructured-pdf-fileset
    Physical Storage URI:
    gs://your-project-id-dark-data-manuals/sop-pdfs/LUM-LIG-DES-8G8J_manual.pdf
    Domain Ontology     : Electrical Hardware & Lighting Systems
    Hazard Level        : MEDIUM
    Compliance Codes    : UL-153 Portable Luminaires, FCC Part 15, CE-LVD, RoHS
    Lakehouse Join Table:
    lakehouse.your-project-id.retail_hardware.luminaire_sku_inventory_iceberg

تأیید دو مرحله‌ای

  • مسیر ۱ (جستجوی CLI): جستجوی فهرست جستجو مستقیماً از طریق gcloud :
    gcloud dataplex entries search "name:sop-manuals-fileset-lum8g8j" --project=$PROJECT_ID
    
  • مسیر ۲ (جستجوی زبان طبیعی رابط کاربری کنسول):
    1. کنسول جستجوی کاتالوگ دانش را باز کنید و عبارت LUM-LIG-DES-8G8J یا UL-153 را جستجو کنید.
    2. مشاهده کنید که چگونه کاتالوگ دانش، ورودی مجموعه فایل‌های PDF ذخیره سازی ابری تحت مدیریت و جنبه‌های فراداده پیوست شده به آن را نمایش می‌دهد.

۹. تأیید ادعاهای حاکمیتی سرتاسری

step7_verify_assertions.py ادعاهای قطعی را در برابر پاسخ‌های صفحه کنترل کاتالوگ دانش زنده اجرا می‌کند تا تأیید کند که EntryGroup ، EntryType ، هر دو طرح سفارشی AspectType ، بارهای جنبه محدود EntryView.ALL (محدوده‌های confidence_score و رشته lakehouse_cross_ref_table ) و کشف شاخص جستجو، همگی با موفقیت انجام می‌شوند:

verify_eg = catalog_client.get_entry_group(name=entry_group_resource_name)
assert verify_eg.name == entry_group_resource_name, "EntryGroup resource name mismatch."

verify_entry = catalog_client.get_entry(
    request=dataplex_v1.GetEntryRequest(
        name=fileset_entry_name,
        view=dataplex_v1.EntryView.ALL,
    )
)
bound_extracted = next(
    (
        asp for k, asp in verify_entry.aspects.items()
        if k.endswith(f".{REGION}.{EXTRACTED_ASPECT_TYPE_ID}")
    ),
    None,
)
bound_governance = next(
    (
        asp for k, asp in verify_entry.aspects.items()
        if k.endswith(f".{REGION}.{GOVERNANCE_ASPECT_TYPE_ID}")
    ),
    None,
)

assert bound_extracted is not None, f"Aspect '{EXTRACTED_ASPECT_TYPE_ID}' not found on live Entry."
assert bound_governance is not None, (
    f"Aspect '{GOVERNANCE_ASPECT_TYPE_ID}' not found on live Entry."
)
assert (
    bound_extracted.data.get("document_title") == expected_extraction["document_title"]
), "Extracted title mismatch."
assert (
    0.0 <= float(bound_extracted.data.get("confidence_score", -1.0)) <= 1.0
), "Invalid confidence score in catalog."
assert (
    "lakehouse" in str(bound_governance.data.get("lakehouse_cross_ref_table", "")).lower()
), "Missing Lakehouse cross-reference."
...
assert len(search_results) >= 1, "Expected at least 1 search result in Knowledge Catalog."

اجرای step7_verify_assertions.py

python3 step7_verify_assertions.py && echo "Verification exit code: $?"
Running substantive end-to-end verification assertions...
✓ All 5 substantive verification assertions passed
  against live Google Cloud control plane state!
Verification exit code: 0

۱۰. یک خط تولید رویداد محور طراحی کنید

اگرچه اجرای اسکریپت‌های پایتون به صورت تعاملی در Cloud Shell برای ساخت و آزمایش قراردادهای نظارتی شما ایده‌آل است، اما محیط‌های سازمانی روزانه هزاران کتابچه راهنمای مهندسی PDF جدید یا اصلاح‌شده، گواهی‌های انطباق با الزامات تأمین‌کنندگان و اسناد SOP را از ERP، مدیریت چرخه عمر محصول (PLM) و پورتال‌های فروشندگان دریافت می‌کنند. اجرای دستی اسکریپت‌های دسته‌ای به سرعت نقاط کور نظارتی بین آپلود سند و فهرست‌بندی کاتالوگ ایجاد می‌کند.

در مرحله تولید، تیم‌های پلتفرم دقیقاً همان کدی را که در مراحل ۴ و ۵ اجرا کردید، به عنوان یک خط لوله رویدادمحور و بدون نیاز به لمس، عملیاتی می‌کنند:

خط لوله داده تاریک مبتنی بر رویداد

  1. دریافت مداوم سند ( Cloud Storage → Eventarc ) : هر زمان که یک کتابچه راهنمای PDF جدید آپلود می‌شود یا یک نسخه جدید، یک شیء موجود در Cloud Storage را رونویسی می‌کند، باکت یک google.cloud.storage.object.v1.finalized CloudEvent منتشر می‌کند که حاوی شناسه باکت، مسیر شیء و شماره تولید شیء است.
  2. استخراج چندوجهی بدون وضعیت ( Eventarc → Cloud Run → Gemini Enterprise Agent Platform ) : Eventarc، CloudEvent را به یک Worker بدون سرور Cloud Run به نام‌های schemas.py ، step4_extract_metadata.py و step5_attach_aspects.py هدایت می‌کند. Worker بایت‌های PDF را با اعمال response_schema به Gemini Enterprise Agent Platform ارسال می‌کند و تضمین می‌کند که هر ویژگی استخراج‌شده با DarkDataExtractedMetadata و DocumentGovernanceMetadata مطابقت داشته باشد.
  3. به‌روزرسانی صفحه کنترل جراحی ( Cloud Run → Knowledge Catalog ) : کارگر Entry Fileset والد را حل می‌کند و catalog_client.update_entry() را با update_mask={"paths": ["aspects"]} و aspect_keys صریح اجرا می‌کند. حتی اگر ده‌ها سند به طور همزمان پردازش را تمام کنند، هر جهش فقط کلیدهای جنبه تعیین شده خود را به‌روزرسانی می‌کند.
  4. قرنطینه‌ی ناظر با درِ اطمینان : اگر یک فایل PDF اسکن‌شده‌ی قدیمی، confidence_score استخراجی پایین‌تر از آستانه‌ی عملیاتی شما (برای مثال، < 0.85 ) داشته باشد، ناظر governance_status = "PENDING_STEWARD_REVIEW" را روی جنبه‌ی پیوست‌شده تنظیم می‌کند تا ناظرین داده بتوانند کاتالوگ دانش را برای دارایی‌های با اعتماد پایین که نیاز به بررسی انسانی دارند، جستجو کنند.

چگونه شرکت‌ها این الگو را در تولید به کار می‌گیرند

مورد استفاده سازمانی

نحوه عملکرد فراداده به عنوان کد در عمل

تأثیر تجاری و عملیاتی

ممیزی‌های نظارتی خودکار و آمادگی برای فراخوان
(تولید، سخت‌افزار و انرژی)

سیستم‌های انطباق، جنبه‌های ایمنی PDF بدون ساختار ( compliance_classifications ، operational_hazard_level ) را با جداول موجودی SKU ساختار یافته ( lakehouse_cross_ref_table ) در BigQuery و Lakehouse برای Apache Iceberg پیوند می‌دهند.

وقتی استانداردی مانند UL-153 یا CE-LVD به‌روزرسانی می‌شود، حسابرسان به جای باز کردن دستی هزاران پوشه PDF، هر SKU سخت‌افزاری آسیب‌دیده و محل انبار را در عرض چند ثانیه شناسایی می‌کنند.

عوامل هوش مصنوعی زمینی و پیش فیلترینگ RAG
(دستیاران دانش سازمانی)

قبل از اینکه یک عامل بازیابی-تقویت‌شده (RAG) در پلتفرم Gemini Enterprise Agent به سوال یک مهندس میدانی پاسخ دهد، ورودی‌های کاتالوگ دانش را بر اساس governance_status = "VERIFIED_PRODUCTION" و version_provenance فیلتر می‌کند.

مانع از آن می‌شود که دستیاران هوش مصنوعی دچار توهم شوند یا به پیش‌نویس‌های مهندسی منسوخ‌شده، SOPهای منقضی‌شده یا دستورالعمل‌های شخص ثالث تأییدنشده استناد کنند.

غنی‌سازی همزمان چند تیمی
(شبکه داده غیرمتمرکز)

چندین خط لوله مستقل، Entry Fileset یکسانی را غنی می‌کنند: مهندس هوش مصنوعی، dark-data-extracted-metadata را به‌روزرسانی می‌کند، بخش حقوقی، سیاست‌های نگهداری را از طریق document-governance-aspect پیوست می‌کند و بخش امنیتی، جنبه‌های حساسیت DLP را پیوست می‌کند.

از آنجا که دامنه‌های UpdateEntryRequest از طریق aspect_keys تغییر می‌کنند، هر تیم دامنه، خط لوله فراداده خود را به‌طور مستقل و بدون بازنویسی داده‌های مدیریتی تیم‌های دیگر، مستقر و به‌روزرسانی می‌کند.

تکامل طرحواره CI/CD از طریق GitOps
(مهندسی پلتفرم و داده)

تیم‌های پلتفرم schemas.py در کنار تعاریف google_dataplex_aspect_type در Terraform در Git ذخیره می‌کنند. درخواست‌های pull قبل از استقرار، اعتبارسنجی می‌کنند که هر فیلد جدید Pydantic دارای یک index منطبق مبتنی بر ۱ در الگوی AspectType باشد.

انحراف طرحواره بین کد استخراج برنامه و صفحه کنترل کاتالوگ دانش در پروژه‌های dev ، staging و prod را از بین می‌برد.

۱۱. تمیز کردن محیط زیست

در Knowledge Catalog ، کانتینرهای والد و قالب‌های طرحواره را نمی‌توان حذف کرد، در حالی که ورودی‌های فرزند هنوز به آنها ارجاع می‌دهند. cleanup.py منابع را به ترتیب وابستگی معکوس حذف می‌کند ( Entry → EntryGroup → EntryType → AspectTypes → Cloud Storage bucket objects → temporary JSON files):

# 1. Delete Fileset Entry first
catalog_client.delete_entry(name=target_entry_path)

# 2. Delete EntryGroup container
del_eg_op = catalog_client.delete_entry_group(name=target_eg_path)
if hasattr(del_eg_op, "result"):
    del_eg_op.result()

# 3. Delete EntryType and Custom AspectTypes
del_et_op = catalog_client.delete_entry_type(name=target_et_path)
if hasattr(del_et_op, "result"):
    del_et_op.result()
for aspect_id_val in (EXTRACTED_ASPECT_TYPE_ID, GOVERNANCE_ASPECT_TYPE_ID):
    target_at_path = f"{active_parent}/aspectTypes/{aspect_id_val}"
    del_at_op = catalog_client.delete_aspect_type(name=target_at_path)
    if hasattr(del_at_op, "result"):
        del_at_op.result()

اجرای cleanup.py

python3 cleanup.py
Starting reverse-dependency resource cleanup in Knowledge Catalog...
Deleted Fileset Entry:
  projects/your-project-id/locations/us-central1/entryGroups/
  dark-data-fileset-group/entries/sop-manuals-fileset-lum8g8j
Deleted EntryGroup   :
  projects/your-project-id/locations/us-central1/entryGroups/
  dark-data-fileset-group
Deleted EntryType    :
  projects/your-project-id/locations/us-central1/entryTypes/
  unstructured-pdf-fileset
Deleted AspectType   :
  projects/your-project-id/locations/us-central1/aspectTypes/
  dark-data-extracted-metadata
Deleted AspectType   :
  projects/your-project-id/locations/us-central1/aspectTypes/
  document-governance-aspect
Deleted Cloud Storage object :
  gs://your-project-id-dark-data-manuals/sop-pdfs/LUM-LIG-DES-8G8J_manual.pdf
Deleted Cloud Storage bucket : gs://your-project-id-dark-data-manuals
Removed local temporary file : extracted_metadata.json
Removed local temporary file : governance_metadata.json
✓ Standalone teardown complete. Environment cleanly reset.

پوشه مخزن کلون شده را حذف کنید

پس از اینکه cleanup.py حذف منابع ابری را به پایان رساند، به دایرکتوری خانگی خود برگردید و پوشه مخزن devrel-demos کلون شده را از Cloud Shell حذف کنید:

cd ~
rm -rf ~/devrel-demos

۱۲. تبریک می‌گویم!

شما یک خط لوله مدیریت فراداده به عنوان کد (Metadata-as-Code) سرتاسری ساخته و تأیید کرده‌اید که فایل‌های PDF بدون ساختار را در فضای ذخیره‌سازی ابری (Cloud Storage) با استفاده از پلتفرم Gemini Enterprise Agent به دارایی‌های کاتالوگ دانش قابل کشف و مبتنی بر طرحواره تبدیل می‌کند.

بعدش چی؟

  • خودکارسازی با Terraform : منابع google_dataplex_aspect_type و google_dataplex_entry_group را به صورت اعلانی در خطوط لوله CI/CD مدیریت کنید.
  • استقرار Eventarc + Cloud Run Workers : step4_extract_metadata.py و step5_attach_aspects.py را در یک سرویس Cloud Run مبتنی بر رویداد، کانتینر کنید.
  • اتصالات موجودی پایین‌دستی در BigQuery : فراداده‌های حاکمیتی استخراج‌شده ( lakehouse_cross_ref_table ) را صادر کنید تا ویژگی‌های انطباق سند بدون ساختار را با جداول موجودی SKU ساختاریافته پیوند دهید.

اسناد مرجع