> ## Documentation Index
> Fetch the complete documentation index at: https://private-7c7dfe99-mintlify-8c05c8a2.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# أنشئ أول إسقاط لك

> تعرّف على كيفية استخدام الإسقاطات في ClickHouse لتخزين نسخة إضافية مرتبة من بياناتك داخل الجدول نفسه، مما يتيح عمليات بحث سريعة في الأعمدة التي لا يشملها المفتاح الأساسي.

<a href="/ar/get-started/quickstarts/home"><Badge size="lg" color="gray" icon="arrow-left">جميع أدلة البدء السريع</Badge></a>

<div className="mt-2 flex flex-wrap gap-2">
  <Badge size="lg" color="blue">التحليلات اللحظية</Badge>
  <Badge size="lg" color="blue">مستودعات البيانات</Badge>
  <Badge size="lg" color="blue">الرصد</Badge>
  <Badge size="lg" color="blue">AI/ML</Badge>
  <Badge size="lg" color="orange">Cloud</Badge>
  <Badge size="lg" color="orange">Oss</Badge>
</div>

<div id="prerequisites">
  ## المتطلبات الأساسية
</div>

To successfully follow this guide, you'll need the following:

* A running ClickHouse Cloud service. If you don't have one yet, complete the [Create your first Cloud service](/get-started/quickstarts/create-your-first-service-on-cloud) quickstart first.

يجب أيضًا أن تكون قد أكملت أدلة البدء السريع التالية، لأن هذا الدليل يستند مباشرةً إلى جدول `uk_price_paid` والمفاهيم المقدَّمة فيها:

* [أنشئ أول جدول MergeTree](/ar/get-started/quickstarts/create-your-first-mergetree-table)
* [أنشئ أول materialized view](/ar/get-started/quickstarts/create-your-first-materialized-view)

<div id="what-youll-build">
  ## ما الذي ستبنيه
</div>

في دليل البدء السريع لـ MergeTree، رأيت أن الاستعلام عن `uk_price_paid` حسب `town` أو `county` يتطلب فحصًا كاملًا للجدول لأن الجدول مُرتَّب وفق `(postcode, addr1, addr2)`.
في دليل البدء السريع هذا، ستحل هذه المشكلة بإنشاء **إسقاط** — وهو تمثيل إضافي مُرتَّب لبياناتك ومخزَّن *داخل* الجدول نفسه. وخلافًا للعروض المادية، لا تتطلب الإسقاطات أي جدول وجهة منفصل، وتبقى متزامنة مع التعديلات (الحذف والتحديث)، ويستخدمها مُحسِّن الاستعلامات بشفافية، بحيث تواصل الاستعلام باستخدام اسم الجدول نفسه.
وبحلول النهاية، ستفهم كيفية إضافة إسقاط وتفعيل تجسيده، وكيف يختاره ClickHouse تلقائيًا، ومتى تختار الإسقاطات بدلًا من العروض المادية.

<Steps titleSize="h3">
  <Step>
    ### افهم سبب حاجتك إلى إسقاط

    يُفرز جدول `uk_price_paid` حسب `(postcode, addr1, addr2)`. وهذا يعني أن ClickHouse يستطيع تخطي كتل كبيرة من البيانات عند التصفية حسب `postcode` أو `addr1` أو `addr2`، لكن الاستعلامات التي تُصفّي حسب `town` يجب أن تفحص كل الصفوف — أي 30 مليون صف بالكامل.

    يخزّن **الإسقاط** نسخة إضافية مفروزة من بعض الأعمدة أو كلها *داخل الجدول نفسه*. وعند الاستعلام من الجدول، يتحقق مُحسِّن الاستعلامات تلقائيًا مما إذا كانت القراءة من الإسقاط ستتطلب عددًا أقل من الـ granules مقارنةً بالبيانات الأساسية، ويستخدمه تلقائيًا إذا كان الأمر كذلك.

    الاختلافات الأساسية عن العروض المادية:

    * **لا يوجد جدول منفصل** - فالإسقاط موجود داخل `uk_price_paid` نفسه
    * **تحسين شفاف للاستعلامات** - تستعلم من `uk_price_paid` كالمعتاد، ويتولى ClickHouse اختيار الإسقاط تلقائيًا
    * **يبقى متزامنًا مع mutations** - تنعكس عمليات الحذف والتحديث المطبقة على الجدول في الإسقاط

    اطّلع على المزيد في [الوثائق المرجعية الخاصة بالإسقاطات](/ar/reference/statements/alter/projection).
  </Step>

  <Step>
    ### أضف إسقاطًا إلى جدولك

    عرّف إسقاطًا على `uk_price_paid` يخزّن `town` و`date` و`price` و`type` مرتبةً حسب `(town, date)`:

    ```sql theme={null}
    ALTER TABLE uk_price_paid
        ADD PROJECTION uk_price_paid_by_town
        (
            SELECT town, date, price, type
            ORDER BY (town, date)
        );
    ```

    يؤدي هذا إلى تسجيل الإسقاط في البيانات الوصفية للجدول، لكنه **لا** يُطبَّق ماديًا على البيانات الحالية، وإنما ستقوم فقط عمليات الإدراج المستقبلية بملئه.

    تحقّق من ظهور الإسقاط في تعريف الجدول:

    ```sql theme={null}
    SHOW CREATE TABLE uk_price_paid;
    ```

    يجب أن ترى كتلة `PROJECTION uk_price_paid_by_town` في المخرجات.
  </Step>

  <Step>
    ### تجسيد الإسقاط للبيانات الحالية

    مثل العروض المُجسَّدة، لا يُطبَّق الإسقاط المُضاف حديثًا إلا على عمليات الإدراج اللاحقة. ولملئه بـ30 مليون صف موجودة بالفعل في الجدول، قم بتجسيده صراحةً:

    ```sql theme={null}
    ALTER TABLE uk_price_paid
        MATERIALIZE PROJECTION uk_price_paid_by_town;
    ```

    يُنفَّذ هذا كعملية mutation في الخلفية. يمكنك التحقق من تقدّمه:

    ```sql theme={null}
    SELECT
        mutation_id,
        command,
        is_done
    FROM system.mutations
    WHERE table = 'uk_price_paid'
    ORDER BY create_time DESC
    LIMIT 5;
    ```

    بمجرد أن تصبح `is_done = 1`، يكون الإسقاط قد تم تخزينه فعليًا بالكامل. ويمكنك أيضًا التحقق من ذلك بفحص `system.projection_parts`:

    ```sql theme={null}
    SELECT
        name,
        count() AS parts,
        sum(rows) AS total_rows,
        formatReadableSize(sum(bytes_on_disk)) AS size
    FROM system.projection_parts
    WHERE table = 'uk_price_paid'
      AND active = true
    GROUP BY name;
    ```
  </Step>

  <Step>
    ### نفّذ استعلامًا على الجدول ولاحظ الاستخدام التلقائي للإسقاط

    الآن نفّذ استعلامًا مع التصفية حسب `town` على **نفس الجدول** الذي تجري عليه استعلاماتك دائمًا:

    ```sql theme={null}
    SELECT
        toYear(date) AS year,
        round(avg(price)) AS avg_price,
        count() AS sales
    FROM uk_price_paid
    WHERE town = 'LONDON'
    GROUP BY year
    ORDER BY year DESC;
    ```

    تحقّق من إحصاءات الاستعلام - ستلاحظ أن عدد الصفوف المقروءة أقل بكثير مقارنةً بما كان عليه قبل وجود الإسقاط، لأن ClickHouse اختار تلقائيًا القراءة من الإسقاط `uk_price_paid_by_town` بدلًا من فحص البيانات الأساسية.

    يمكنك التأكد من استخدام الإسقاط عبر `EXPLAIN`:

    ```sql theme={null}
    EXPLAIN
    SELECT
        toYear(date) AS year,
        round(avg(price)) AS avg_price,
        count() AS sales
    FROM uk_price_paid
    WHERE town = 'LONDON'
    GROUP BY year
    ORDER BY year DESC;
    ```

    ابحث في المخرجات عن `ReadFromMergeTree` مع الإشارة إلى اسم الإسقاط. إذا أردت مقارنة الأداء مباشرةً، يمكنك تعطيل تحسين الإسقاط لاستعلام واحد:

    ```sql theme={null}
    SELECT
        toYear(date) AS year,
        round(avg(price)) AS avg_price,
        count() AS sales
    FROM uk_price_paid
    WHERE town = 'LONDON'
    GROUP BY year
    ORDER BY year DESC
    SETTINGS optimize_use_projections = 0;
    ```

    يؤدي هذا إلى إجراء مسح كامل للجدول لكي تتمكن من ملاحظة الفرق في عدد الصفوف المقروءة.
  </Step>

  <Step>
    ### قارن بين الإسقاطات والعروض المادية

    تعالج الإسقاطات والعروض المادية المشكلة نفسها، وهي تسريع عمليات القراءة لأنماط الوصول البديلة، لكن لكلٍّ منهما مفاضلات مختلفة. باختصار، تكون الإسقاطات هي الخيار الأفضل عندما تحتاج فقط إلى ترتيب فرز مختلف للبيانات نفسها؛ أما العروض المادية فهي أكثر مرونة عندما تحتاج إلى تحويل البيانات أو تجميعها أو توجيهها إلى مخطط مختلف. ولمقارنة مفصلة، راجع [العروض المادية مقابل الإسقاطات](/ar/concepts/features/projections/materialized-views-versus-projections).
  </Step>

  <Step>
    ### راقب الأثر الإضافي على التخزين

    تخزّن الإسقاطات نسخةً ثانية من الأعمدة المحددة داخل الجدول نفسه، مما يزيد من استخدام القرص. استعلم من `system.parts` للاطلاع على الحجم الإجمالي لـ `uk_price_paid` (والذي يتضمن الآن بيانات الإسقاط):

    ```sql theme={null}
    SELECT
        table,
        count() AS parts,
        sum(rows) AS total_rows,
        formatReadableSize(sum(bytes_on_disk)) AS compressed_size
    FROM system.parts
    WHERE table = 'uk_price_paid'
      AND active = true
    GROUP BY table;
    ```

    يمكنك أيضًا التحقّق من مساحة التخزين الخاصة بالإسقاطات:

    ```sql theme={null}
    SELECT
        name,
        count() AS parts,
        sum(rows) AS total_rows,
        formatReadableSize(sum(bytes_on_disk)) AS projection_size
    FROM system.projection_parts
    WHERE table = 'uk_price_paid'
      AND active = true
    GROUP BY name;
    ```

    هذه هي المقايضة الجوهرية نفسها كما في العروض المادية: مساحة أكبر على القرص مقابل قراءات أسرع. وقد يكون الإسقاط أصغر من نسخة كاملة لأنه يقتصر على الأعمدة الأربعة المحددة، كما يختلف الضغط باختلاف ترتيب الفرز.
  </Step>
</Steps>

## الخطوات التالية

في دليل البدء السريع هذا، أضفتَ إسقاط إلى `uk_price_paid` يخزّن البيانات مرتبةً حسب `(town, date)`، مما يتيح عمليات lookup سريعة حسب البلدة دون إنشاء table منفصل. وتعلّمتَ أن مُحسِّن الاستعلامات يختار إسقاط تلقائيًا، وأنها تبقى متزامنة مع mutations، وتستبدل مساحة disk بأداء read أفضل.

اطّلع بعد ذلك على أدلة البدء السريع التالية:

أو تعمّق أكثر بالرجوع إلى وثائق Reference:

* [عرض مادي مقابل إسقاط](/ar/concepts/features/projections/materialized-views-versus-projections)
* [مرجع إسقاط](/ar/reference/statements/alter/projection)
* [محرك table من MergeTree](/ar/reference/engines/table-engines/mergetree-family/mergetree)

<Frame caption="Check out the ClickHouse academy for on-demand and live training">
  <a href="https://learn.clickhouse.com/" target="_blank">
    <img src="https://mintcdn.com/private-7c7dfe99-mintlify-8c05c8a2/GaEHa-fd8w_5w7tQ/images/academy.png?fit=max&auto=format&n=GaEHa-fd8w_5w7tQ&q=85&s=46be2d7327e98b07a2a4b1a422642a30" alt="ClickHouse Academy — Master ClickHouse with expert-designed training for every skill level" width="560" noZoom data-path="images/academy.png" />
  </a>
</Frame>

<div className="mt-8">
  <a href="/ar/get-started/quickstarts/home"><Badge size="lg" color="gray" icon="arrow-left">جميع أدلة البدء السريع</Badge></a>
</div>
