إدارة حِمل العمل باستخدام فئات الموارد في Azure Synapse Analytics
إرشادات لاستخدام فئات الموارد لإدارة الذاكرة والتزامن لاستعلامات تجمع Synapse SQL في Azure Synapse.
ما هي فئات الموارد؟
يتم تحديد قدرة أداء الاستعلام بواسطة فئة مورد المستخدم. فئات الموارد هي حدود موارد محددة مسبقاً في تجمع Synapse SQL الذي يحكم الموارد والتزامن لتنفيذ الاستعلام. يمكن أن تساعدك فئات الموارد في تكوين الموارد لطلبات البحث الخاصة بك عن طريق تعيين قيود على عدد الاستعلامات التي يتم تشغيلها بشكل متزامن وعلى موارد الحساب المعينة لكل استعلام. هناك مفاضلة بين الذاكرة والتزامن.
- تعمل فئات الموارد الأصغر على تقليل الحد الأقصى للذاكرة لكل استعلام، ولكنها تزيد من التزامن.
- تعمل فئات الموارد الأكبر على زيادة الحد الأقصى للذاكرة لكل استعلام، ولكنها تقلل التزامن.
هناك نوعان من فئات الموارد:
- فئات الموارد الثابتة، والتي هي مناسبة تماماً لزيادة التزامن على حجم مجموعة البيانات الذي تم إصلاحه.
- فئات الموارد الديناميكية، المناسبة تماماً لمجموعات البيانات التي يتزايد حجمها وتحتاج إلى أداء متزايد مع زيادة مستوى الخدمة.
تستخدم فئات الموارد فتحات التزامن لقياس استهلاك الموارد. تم شرح فتحات التزامن لاحقاً في هذه المقالة.
- لعرض استخدام الموارد لفئات الموارد، راجع حدود الذاكرة والتزامن.
- لضبط فئة المورد، يمكنك تشغيل الاستعلام ضمن مستخدم مختلف أو تغيير عضوية فئة مورد المستخدم الحالي.
فئات الموارد الثابتة
تخصص فئات الموارد الثابتة نفس المقدار من الذاكرة بغض النظر عن مستوى الأداء الحالي، والذي يتم قياسه في وحدات مستودع البيانات. نظراً لأن الاستعلامات تحصل على نفس تخصيص الذاكرة بغض النظر عن مستوى الأداء، فإن توسيع نطاق مستودع البيانات يسمح بتشغيل المزيد من الاستعلامات داخل فئة الموارد. تعد فئات الموارد الثابتة مثالية إذا كان حجم البيانات معروفاً وثابتاً.
يتم تنفيذ فئات الموارد الثابتة باستخدام أدوار قواعد البيانات المحددة مسبقاً:
- staticrc10
- staticrc20
- staticrc30
- staticrc40
- staticrc50
- staticrc60
- staticrc70
- staticrc80
فئات الموارد الديناميكية
تخصص فئات الموارد الديناميكية مقدارا متغيرا من الذاكرة اعتمادا على مستوى الخدمة الحالي. في حين أن فئات الموارد الثابتة مفيدة لأحجام بيانات ثابتة وتزامن أعلى، فإن فئات الموارد الديناميكية مناسبة بشكل أفضل لكمية متزايدة أو متغيرة من البيانات. عندما ترقى إلى مستوى خدمة أكبر، تحصل استفساراتك تلقائياً على ذاكرة أكبر.
باستثناء smallrc، يتم تنفيذ فئات الموارد الديناميكية مع أدوار قاعدة البيانات المحددة مسبقا:
- mediumrc
- largerc
- xlargerc
لا يظهر Smallrc كدور قاعدة بيانات، ولكنه فئة المورد الافتراضي.
تخصيص الذاكرة لكل فئة من فئات الموارد على النحو التالي.
مستوى الخدمة | smallrc | mediumrc | largerc | xlargerc |
---|---|---|---|---|
DW100c | 25% | 25% | 25% | ٪70 |
DW200c | 12.5% | 12.5% | 22% | ٪70 |
DW300c | 8% | 10% | 22% | ٪70 |
DW400c | 6.25% | 10% | 22% | ٪70 |
DW500c | 5% | 10% | 22% | ٪70 |
DW1000c إلى DW30000c |
3% | 10% | 22% | ٪70 |
فئة الموارد الافتراضية
بشكل افتراضي، يكون كل مستخدم عضواً في فئة الموارد الديناميكية smallrc.
صنف المورد لمسؤول الخدمة ثابت في smallrc ولا يمكن تغييره. مسؤول الخدمة هو المستخدم الذي تم إنشاؤه أثناء عملية التوفير. مسؤول الخدمة في هذا السياق هو تسجيل الدخول المحدد لـ "تسجيل دخول مسؤول الخادم" عند إنشاء تجمع Synapse SQL جديد مع خادم جديد.
إشعار
المستخدمون أو المجموعات المحددة كمسؤول Active Directory هم أيضاً مسؤولو الخدمة.
عمليات فئة الموارد
تم تصميم فئات الموارد لتحسين أداء إدارة البيانات وأنشطة المعالجة. يمكن أن تستفيد الاستعلامات المعقدة أيضاً من العمل ضمن فئة موارد كبيرة. على سبيل المثال، يمكن تحسين أداء الاستعلام للصلات والأنواع الكبيرة عندما تكون فئة المورد كبيرة بما يكفي لتمكين الاستعلام من التنفيذ في الذاكرة.
العمليات التي تحكمها فئات الموارد
تخضع هذه العمليات لفئات الموارد:
INSERT
-SELECT
، ،UPDATE
DELETE
SELECT
(عند الاستعلام عن جداول المستخدمين)ALTER INDEX
-REBUILD
أوREORGANIZE
ALTER TABLE REBUILD
CREATE INDEX
CREATE CLUSTERED COLUMNSTORE INDEX
CREATE TABLE AS SELECT
(CTAS)- تحميل البيانات
- عمليات نقل البيانات التي تجريها خدمة نقل البيانات (DMS)
إشعار
لا تخضع عبارات SELECT الخاصة بعروض الإدارة الديناميكية (DMVs) أو طرق عرض النظام الأخرى لأي من حدود التزامن. يمكنك مراقبة النظام بغض النظر عن عدد الاستعلامات المنفذة عليه.
العمليات التي لا تحكمها فئات الموارد
تعمل بعض الاستعلامات دائماً في فئة موارد smallrc رغم أن المستخدم عضو في فئة موارد أكبر. لا تحسب هذه الاستعلامات المعفاة ضمن حد التزامن. على سبيل المثال، إذا كان حد التزامن هو 16، يمكن للعديد من المستخدمين الاختيار من طرق عرض النظام دون التأثير على فتحات التزامن المتوفرة.
العبارات التالية مستثناة من فئات الموارد ويتم تشغيلها دائماً في smallrc:
CREATE
أوDROP TABLE
ALTER TABLE ... SWITCH
وSPLIT
, أوMERGE PARTITION
ALTER INDEX DISABLE
DROP INDEX
CREATE
وUPDATE
, أوDROP STATISTICS
TRUNCATE TABLE
ALTER AUTHORIZATION
CREATE LOGIN
CREATE
وALTER
, أوDROP USER
CREATE
وALTER
, أوDROP PROCEDURE
CREATE
أوDROP VIEW
INSERT VALUES
SELECT
من طرق عرض النظام وDMVsEXPLAIN
DBCC
فتحات التزامن
تعد فتحات التزامن طريقة ملائمة لتتبع الموارد المتاحة لتنفيذ الاستعلام. إنها مثل التذاكر التي تشتريها لحجز المقاعد في حفلة موسيقية لأن المقاعد محدودة. يتم تحديد إجمالي عدد فتحات التزامن لكل مستودع بيانات حسب مستوى الخدمة. قبل أن يبدأ تنفيذ الاستعلام، يجب أن يكون قادراً على حجز فتحات التزامن كافية. عند اكتمال استعلام، فإنه يطلق فتحات التزامن الخاصة به.
- يمكن للاستعلام الذي يتم تشغيله باستخدام 10 فتحات التزامن الوصول إلى موارد حسابية أكثر بخمس مرات من استعلام يتم تشغيله باستخدام فتحتين للتزامن.
- إذا تطلب كل استعلام 10 فتحات للتزامن وكان هناك 40 خانة للتزامن، فيمكن تشغيل 4 استعلامات فقط في نفس الوقت.
تستهلك الاستعلامات الخاضعة للتحكم في الموارد فقط فتحات التزامن. لا تستهلك استعلامات النظام وبعض الاستعلامات التافهة أي فتحات. يتم تحديد العدد الدقيق لفتحات التزامن المستهلكة بواسطة فئة مورد الاستعلام.
عرض فئات الموارد
يتم تنفيذ فئات الموارد كأدوار قاعدة بيانات محددة مسبقا. يوجد نوعان من فئات الموارد: ديناميكي وثابت. لعرض قائمة بفئات الموارد، استخدم الاستعلام التالي:
SELECT name
FROM sys.database_principals
WHERE name LIKE '%rc%' AND type_desc = 'DATABASE_ROLE';
تغيير فئة موارد المستخدم
يتم تنفيذ فئات الموارد من خلال تعيين المستخدمين لأدوار قاعدة البيانات. عندما يقوم المستخدم بتشغيل استعلام، يتم تشغيل الاستعلام مع فئة موارد المستخدم. على سبيل المثال، إذا كان المستخدم عضواً في دور قاعدة بيانات staticrc10، فإن استعلاماته تعمل بكميات صغيرة من الذاكرة. إذا كان مستخدم قاعدة البيانات عضواً في أدوار قاعدة البيانات xlargerc أو staticrc80، فإن استعلاماتهم تعمل بكميات كبيرة من الذاكرة.
لزيادة فئة موارد المستخدم، استخدم sp_addrolemember لإضافة المستخدم إلى دور قاعدة بيانات لفئة موارد كبيرة. تضيف التعليمات البرمجية التالية مستخدما إلى دور قاعدة بيانات largerc. يحصل كل طلب على 22% من ذاكرة النظام.
EXEC sp_addrolemember 'largerc', 'loaduser';
لتقليل فئة المورد، استخدم sp_droprolemember. إذا لم يكن "loaduser" عضواً أو فئة من أي فئات موارد أخرى، فإنهم ينتقلون إلى فئة موارد smallrc الافتراضية مع منحة ذاكرة بنسبة 3%.
EXEC sp_droprolemember 'largerc', 'loaduser';
أسبقية فئة الموارد
يمكن للمستخدمين أن يكونوا أعضاء في فئات موارد متعددة. عندما ينتمي مستخدم إلى أكثر من فئة مورد:
- تحظى فئات الموارد الديناميكية بالأولوية على فئات الموارد الثابتة. على سبيل المثال، إذا كان المستخدم عضوا في كل من القوس المتوسط (الديناميكي) وs staticrc80 (ثابت)، يتم تشغيل الاستعلامات باستخدام القوس المتوسط.
- فئات الموارد الأكبر لها الأسبقية على فئات الموارد الأصغر. على سبيل المثال، إذا كان المستخدم عضواً في mediumrc وأكبر c، فإن الاستعلامات تعمل مع أكبر c. وبالمثل، إذا كان المستخدم عضواً في كل من staticrc20 وstatirc80، يتم تشغيل الاستعلامات مع تخصيصات موارد staticrc80.
التوصيات
إشعار
ضع في اعتبارك الاستفادة من إمكانات إدارة حِمل العمل (عزل حمل العملو التصنيف والأهمية) لمزيد من التحكم في حِمل العمل والأداء المتوقع.
نوصي بإنشاء مستخدم مخصص لتشغيل نوع معين من الاستعلام أو عملية التحميل. امنح هذا المستخدم فئة موارد دائمة بدلاً من تغيير فئة المورد على أساس متكرر. توفر فئات الموارد الثابتة تحكماً عاماً أكبر في حمل العمل، لذلك نقترح استخدام فئات الموارد الثابتة قبل التفكير في فئات الموارد الديناميكية.
فئات الموارد لمستخدمي التحميل
يستخدم CREATE TABLE
فهارس مخزن الأعمدة المتفاوت بشكل افتراضي. يعد ضغط البيانات في مؤشر تخزين الأعمدة عملية تستهلك الكثير من الذاكرة، ويمكن أن يؤدي ضغط الذاكرة إلى تقليل جودة الفهرس. يمكن أن يؤدي ضغط الذاكرة إلى الحاجة إلى فئة موارد أعلى عند تحميل البيانات. للتأكد من أن الأحمال تحتوي على ذاكرة كافية، يمكنك إنشاء مستخدم مخصص لتشغيل الأحمال وتعيين هذا المستخدم إلى فئة موارد أعلى.
تعتمد الذاكرة اللازمة لمعالجة الأحمال بكفاءة على طبيعة الجدول الذي تم تحميله وحجم البيانات. لمزيد من المعلومات حول متطلبات الذاكرة، راجع زيادة جودة rowgroup.
بمجرد تحديد متطلبات الذاكرة، اختر ما إذا كنت تريد تعيين مستخدم التحميل إلى فئة مورد ثابت أو ديناميكي.
- استخدم فئة موارد ثابتة عندما تقع متطلبات ذاكرة الجدول ضمن نطاق معين. تعمل الأحمال مع الذاكرة المناسبة. عندما تقوم بتوسيع نطاق مستودع البيانات، لا تحتاج الأحمال إلى مزيد من الذاكرة. باستخدام فئة موارد ثابتة، تظل تخصيصات الذاكرة ثابتة. يحافظ هذا الاتساق على الذاكرة ويسمح بتشغيل المزيد من الاستعلامات بشكل متزامن. نوصي بأن تستخدم الحلول الجديدة فئات الموارد الثابتة أولاً لأنها توفر تحكماً أكبر.
- استخدم فئة موارد ديناميكية عندما تتباين متطلبات ذاكرة الجدول على نطاق واسع. قد تتطلب الأحمال ذاكرة أكبر مما يوفره مستوى DWU أو cDWU الحالي. يضيف توسيع نطاق مستودع البيانات مزيداً من الذاكرة لتحميل العمليات، ما يسمح للأحمال بأداء أسرع.
فئات الموارد للاستعلامات
بعض الاستعلامات كثيفة الحوسبة والبعض الآخر ليس كذلك.
- اختر فئة موارد ديناميكية عندما تكون الاستعلامات معقدة، ولكنها لا تحتاج إلى تزامن عالٍ. على سبيل المثال، يعد إنشاء تقارير يومية أو أسبوعية حاجة عرضية للموارد. إذا كانت التقارير تعالج كميات كبيرة من البيانات، فإن توسيع نطاق مستودع البيانات يوفر ذاكرة أكبر لفئة الموارد الحالية للمستخدم.
- اختر فئة موارد ثابتة عندما تختلف توقعات الموارد على مدار اليوم. على سبيل المثال، تعمل فئة الموارد الثابتة بشكل جيد عندما يتم الاستعلام عن مستودع البيانات من قبل العديد من الأشخاص. عند توسيع نطاق مستودع البيانات، لا يتغير حجم الذاكرة المخصصة للمستخدم. وبالتالي، يمكن تنفيذ المزيد من الاستعلامات بالتوازي على النظام.
تعتمد منح الذاكرة المناسبة على العديد من العوامل، مثل كمية البيانات التي يتم الاستعلام عنها وطبيعة مخططات الجدول والصلات المختلفة والمسندات المحددة والمجموعة. بشكل عام، يسمح تخصيص المزيد من الذاكرة بإكمال الاستعلامات بشكل أسرع، ولكنه يقلل من التزامن الكلي. إذا لم يكن التزامن مشكلة، فإن الإفراط في تخصيص الذاكرة لا يضر المعدل نقل.
لضبط الأداء، استخدم فئات موارد مختلفة. يقدم القسم التالي إجراءً مخزناً يساعدك في اكتشاف أفضل فئة موارد.
تعليمة برمجية مثال للعثور على أفضل فئة الموارد
prc_workload_management_by_DWU
استخدم الإجراء المخزن من أجل:
- راجع منحة التزامن والذاكرة لكل فئة مورد في SLO معين.
- توفير
NULL
لكل من المخطط واسم الجدول.
- توفير
- راجع أفضل فئة موارد لعمليات CCI كثيفة الذاكرة (التحميل، ونسخ الجدول، وفهرس إعادة البناء، وما إلى ذلك) على جدول CCI غير المقسم في فئة مورد معين.
- يستخدم proc المخزن مخطط الجدول لمعرفة منحة الذاكرة المطلوبة.
للحصول على أمثلة، راجع مثال الاستخدام.
التبعيات والقيود
- لم يتم تصميم هذا الإجراء المخزن لحساب متطلبات الذاكرة لجدول cci مقسم.
- لا يأخذ هذا الإجراء المخزن في الاعتبار متطلبات الذاكرة لجزء SELECT من CTAS/INSERT-SELECT ويفترض أنه SELECT.
- يستخدم هذا الإجراء المخزن جدولاً مؤقتاً، والذي يتوفر في الجلسة حيث تم إنشاء هذا الإجراء المخزن.
- يعتمد هذا الإجراء المخزن على العروض الحالية (على سبيل المثال، تكوين الأجهزة، تكوين DMS)، وإذا تغير أي من هذه التغييرات، فلن يعمل هذا proc المخزن بشكل صحيح.
- يعتمد هذا الإجراء المخزن على عروض حد التزامن الحالية وإذا تغيرت، فلن يعمل هذا الإجراء المخزن بشكل صحيح.
- يعتمد هذا الإجراء المخزن على عروض فئة الموارد الموجودة وإذا كانت هذه التغييرات، فلن يعمل هذا الإجراء المخزن بشكل صحيح.
إشعار
إذا لم تحصل على الإخراج بعد تنفيذ الإجراء المخزن مع توفير المعلمات، فقد تكون هناك حالتان.
- تحتوي إما معلمة DW على قيمة SLO غير صالحة
- أو، لا توجد فئة مورد مطابقة لعملية CCI على الجدول.
على سبيل المثال، في DW100c، أعلى منحة ذاكرة متاحة هي 1 غيغابايت، وإذا كان مخطط الجدول عريضاً بما يكفي لتجاوز متطلبات 1 غيغابايت.
مثال على الاستخدام
بناء الجملة:
EXEC dbo.prc_workload_management_by_DWU @DWU VARCHAR(7), @SCHEMA_NAME VARCHAR(128), @TABLE_NAME VARCHAR(128)
@DWU
: إما توفير معلمةNULL
لاستخراج DWU الحالي من DW DB أو توفير أي DWU مدعومة في شكل "DW100c"@SCHEMA_NAME
: أدخل اسم مخطط للجدول@TABLE_NAME
: أدخل اسم جدول الاهتمام
أمثلة على تنفيذ هذا الإجراء المخزن:
EXEC dbo.prc_workload_management_by_DWU 'DW2000c', 'dbo', 'Table1';
EXEC dbo.prc_workload_management_by_DWU NULL, 'dbo', 'Table1';
EXEC dbo.prc_workload_management_by_DWU 'DW6000c', NULL, NULL;
EXEC dbo.prc_workload_management_by_DWU NULL, NULL, NULL;
تنشئ العبارة Table1
التالية التي يتم استخدامها في الأمثلة السابقة.
CREATE TABLE Table1 (a int, b varchar(50), c decimal (18,10), d char(10), e varbinary(15), f float, g datetime, h date);
تعريف الإجراء المخزن
-------------------------------------------------------------------------------
-- Dropping prc_workload_management_by_DWU procedure if it exists.
-------------------------------------------------------------------------------
IF EXISTS (SELECT * FROM sys.objects WHERE type = 'P' AND name = 'prc_workload_management_by_DWU')
DROP PROCEDURE dbo.prc_workload_management_by_DWU
GO
-------------------------------------------------------------------------------
-- Creating prc_workload_management_by_DWU.
-------------------------------------------------------------------------------
CREATE PROCEDURE dbo.prc_workload_management_by_DWU
(@DWU VARCHAR(8),
@SCHEMA_NAME VARCHAR(128),
@TABLE_NAME VARCHAR(128)
)
AS
IF @DWU IS NULL
BEGIN
-- Selecting proper DWU for the current DB if not specified.
SELECT @DWU = 'DW'+ CAST(CASE WHEN Mem> 4 THEN Nodes*500
ELSE Mem*100
END AS VARCHAR(10)) +'c'
FROM (
SELECT Nodes=count(distinct n.pdw_node_id), Mem=max(i.committed_target_kb/1000/1000/60)
FROM sys.dm_pdw_nodes n
CROSS APPLY sys.dm_pdw_nodes_os_sys_info i
WHERE type = 'COMPUTE')A
END
-- Dropping temp table if exists.
IF OBJECT_ID('tempdb..#ref') IS NOT NULL
BEGIN
DROP TABLE #ref;
END;
-- Creating ref. temp table (CTAS) to hold mapping info.
CREATE TABLE #ref
WITH (DISTRIBUTION = ROUND_ROBIN)
AS
WITH
-- Creating concurrency slots mapping for various DWUs.
alloc
AS
(
SELECT 'DW100c' AS DWU,4 AS max_queries,4 AS max_slots,1 AS slots_used_smallrc,1 AS slots_used_mediumrc,2 AS slots_used_largerc,4 AS slots_used_xlargerc,1 AS slots_used_staticrc10,2 AS slots_used_staticrc20,4 AS slots_used_staticrc30,4 AS slots_used_staticrc40,4 AS slots_used_staticrc50,4 AS slots_used_staticrc60,4 AS slots_used_staticrc70,4 AS slots_used_staticrc80
UNION ALL
SELECT 'DW200c',8,8,1,2,4,8,1,2,4,8,8,8,8,8
UNION ALL
SELECT 'DW300c',12,12,1,2,4,8,1,2,4,8,8,8,8,8
UNION ALL
SELECT 'DW400c',16,16,1,4,8,16,1,2,4,8,16,16,16,16
UNION ALL
SELECT 'DW500c',20,20,1,4,8,16,1,2,4,8,16,16,16,16
UNION ALL
SELECT 'DW1000c',32,40,1,4,8,28,1,2,4,8,16,32,32,32
UNION ALL
SELECT 'DW1500c',32,60,1,6,13,42,1,2,4,8,16,32,32,32
UNION ALL
SELECT 'DW2000c',48,80,2,8,17,56,1,2,4,8,16,32,64,64
UNION ALL
SELECT 'DW2500c',48,100,3,10,22,70,1,2,4,8,16,32,64,64
UNION ALL
SELECT 'DW3000c',64,120,3,12,26,84,1,2,4,8,16,32,64,64
UNION ALL
SELECT 'DW5000c',64,200,6,20,44,140,1,2,4,8,16,32,64,128
UNION ALL
SELECT 'DW6000c',128,240,7,24,52,168,1,2,4,8,16,32,64,128
UNION ALL
SELECT 'DW7500c',128,300,9,30,66,210,1,2,4,8,16,32,64,128
UNION ALL
SELECT 'DW10000c',128,400,12,40,88,280,1,2,4,8,16,32,64,128
UNION ALL
SELECT 'DW15000c',128,600,18,60,132,420,1,2,4,8,16,32,64,128
UNION ALL
SELECT 'DW30000c',128,1200,36,120,264,840,1,2,4,8,16,32,64,128
)
-- Creating workload mapping to their corresponding slot consumption and default memory grant.
,map
AS
(
SELECT CONVERT(varchar(20), 'SloDWGroupSmall') AS wg_name, slots_used_smallrc AS slots_used FROM alloc WHERE DWU = @DWU
UNION ALL
SELECT CONVERT(varchar(20), 'SloDWGroupMedium') AS wg_name, slots_used_mediumrc AS slots_used FROM alloc WHERE DWU = @DWU
UNION ALL
SELECT CONVERT(varchar(20), 'SloDWGroupLarge') AS wg_name, slots_used_largerc AS slots_used FROM alloc WHERE DWU = @DWU
UNION ALL
SELECT CONVERT(varchar(20), 'SloDWGroupXLarge') AS wg_name, slots_used_xlargerc AS slots_used FROM alloc WHERE DWU = @DWU
UNION ALL
SELECT 'SloDWGroupC00',1
UNION ALL
SELECT 'SloDWGroupC01',2
UNION ALL
SELECT 'SloDWGroupC02',4
UNION ALL
SELECT 'SloDWGroupC03',8
UNION ALL
SELECT 'SloDWGroupC04',16
UNION ALL
SELECT 'SloDWGroupC05',32
UNION ALL
SELECT 'SloDWGroupC06',64
UNION ALL
SELECT 'SloDWGroupC07',128
)
-- Creating ref based on current / asked DWU.
, ref
AS
(
SELECT a1.*
, m1.wg_name AS wg_name_smallrc
, m1.slots_used * 250 AS tgt_mem_grant_MB_smallrc
, m2.wg_name AS wg_name_mediumrc
, m2.slots_used * 250 AS tgt_mem_grant_MB_mediumrc
, m3.wg_name AS wg_name_largerc
, m3.slots_used * 250 AS tgt_mem_grant_MB_largerc
, m4.wg_name AS wg_name_xlargerc
, m4.slots_used * 250 AS tgt_mem_grant_MB_xlargerc
, m5.wg_name AS wg_name_staticrc10
, m5.slots_used * 250 AS tgt_mem_grant_MB_staticrc10
, m6.wg_name AS wg_name_staticrc20
, m6.slots_used * 250 AS tgt_mem_grant_MB_staticrc20
, m7.wg_name AS wg_name_staticrc30
, m7.slots_used * 250 AS tgt_mem_grant_MB_staticrc30
, m8.wg_name AS wg_name_staticrc40
, m8.slots_used * 250 AS tgt_mem_grant_MB_staticrc40
, m9.wg_name AS wg_name_staticrc50
, m9.slots_used * 250 AS tgt_mem_grant_MB_staticrc50
, m10.wg_name AS wg_name_staticrc60
, m10.slots_used * 250 AS tgt_mem_grant_MB_staticrc60
, m11.wg_name AS wg_name_staticrc70
, m11.slots_used * 250 AS tgt_mem_grant_MB_staticrc70
, m12.wg_name AS wg_name_staticrc80
, m12.slots_used * 250 AS tgt_mem_grant_MB_staticrc80
FROM alloc a1
JOIN map m1 ON a1.slots_used_smallrc = m1.slots_used and m1.wg_name = 'SloDWGroupSmall'
JOIN map m2 ON a1.slots_used_mediumrc = m2.slots_used and m2.wg_name = 'SloDWGroupMedium'
JOIN map m3 ON a1.slots_used_largerc = m3.slots_used and m3.wg_name = 'SloDWGroupLarge'
JOIN map m4 ON a1.slots_used_xlargerc = m4.slots_used and m4.wg_name = 'SloDWGroupXLarge'
JOIN map m5 ON a1.slots_used_staticrc10 = m5.slots_used and m5.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m6 ON a1.slots_used_staticrc20 = m6.slots_used and m6.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m7 ON a1.slots_used_staticrc30 = m7.slots_used and m7.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m8 ON a1.slots_used_staticrc40 = m8.slots_used and m8.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m9 ON a1.slots_used_staticrc50 = m9.slots_used and m9.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m10 ON a1.slots_used_staticrc60 = m10.slots_used and m10.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m11 ON a1.slots_used_staticrc70 = m11.slots_used and m11.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
JOIN map m12 ON a1.slots_used_staticrc80 = m12.slots_used and m12.wg_name NOT IN ('SloDWGroupSmall','SloDWGroupMedium','SloDWGroupLarge','SloDWGroupXLarge')
WHERE a1.DWU = @DWU
)
SELECT DWU
, max_queries
, max_slots
, slots_used
, wg_name
, tgt_mem_grant_MB
, up1 as rc
, (ROW_NUMBER() OVER(PARTITION BY DWU ORDER BY DWU)) as rc_id
FROM
(
SELECT DWU
, max_queries
, max_slots
, slots_used
, wg_name
, tgt_mem_grant_MB
, REVERSE(SUBSTRING(REVERSE(wg_names),1,CHARINDEX('_',REVERSE(wg_names),1)-1)) as up1
, REVERSE(SUBSTRING(REVERSE(tgt_mem_grant_MBs),1,CHARINDEX('_',REVERSE(tgt_mem_grant_MBs),1)-1)) as up2
, REVERSE(SUBSTRING(REVERSE(slots_used_all),1,CHARINDEX('_',REVERSE(slots_used_all),1)-1)) as up3
FROM ref AS r1
UNPIVOT
(
wg_name FOR wg_names IN (wg_name_smallrc,wg_name_mediumrc,wg_name_largerc,wg_name_xlargerc,
wg_name_staticrc10, wg_name_staticrc20, wg_name_staticrc30, wg_name_staticrc40, wg_name_staticrc50,
wg_name_staticrc60, wg_name_staticrc70, wg_name_staticrc80)
) AS r2
UNPIVOT
(
tgt_mem_grant_MB FOR tgt_mem_grant_MBs IN (tgt_mem_grant_MB_smallrc,tgt_mem_grant_MB_mediumrc,
tgt_mem_grant_MB_largerc,tgt_mem_grant_MB_xlargerc, tgt_mem_grant_MB_staticrc10, tgt_mem_grant_MB_staticrc20,
tgt_mem_grant_MB_staticrc30, tgt_mem_grant_MB_staticrc40, tgt_mem_grant_MB_staticrc50,
tgt_mem_grant_MB_staticrc60, tgt_mem_grant_MB_staticrc70, tgt_mem_grant_MB_staticrc80)
) AS r3
UNPIVOT
(
slots_used FOR slots_used_all IN (slots_used_smallrc,slots_used_mediumrc,slots_used_largerc,
slots_used_xlargerc, slots_used_staticrc10, slots_used_staticrc20, slots_used_staticrc30,
slots_used_staticrc40, slots_used_staticrc50, slots_used_staticrc60, slots_used_staticrc70,
slots_used_staticrc80)
) AS r4
) a
WHERE up1 = up2
AND up1 = up3
;
-- Getting current info about workload groups.
WITH
dmv
AS
(
SELECT
rp.name AS rp_name
, rp.max_memory_kb*1.0/1048576 AS rp_max_mem_GB
, (rp.max_memory_kb*1.0/1024)
*(request_max_memory_grant_percent/100) AS max_memory_grant_MB
, (rp.max_memory_kb*1.0/1048576)
*(request_max_memory_grant_percent/100) AS max_memory_grant_GB
, wg.name AS wg_name
, wg.importance AS importance
, wg.request_max_memory_grant_percent AS request_max_memory_grant_percent
FROM sys.dm_pdw_nodes_resource_governor_workload_groups wg
JOIN sys.dm_pdw_nodes_resource_governor_resource_pools rp ON wg.pdw_node_id = rp.pdw_node_id
AND wg.pool_id = rp.pool_id
WHERE rp.name = 'SloDWPool'
GROUP BY
rp.name
, rp.max_memory_kb
, wg.name
, wg.importance
, wg.request_max_memory_grant_percent
)
-- Creating resource class name mapping.
,names
AS
(
SELECT 'smallrc' as resource_class, 1 as rc_id
UNION ALL
SELECT 'mediumrc', 2
UNION ALL
SELECT 'largerc', 3
UNION ALL
SELECT 'xlargerc', 4
UNION ALL
SELECT 'staticrc10', 5
UNION ALL
SELECT 'staticrc20', 6
UNION ALL
SELECT 'staticrc30', 7
UNION ALL
SELECT 'staticrc40', 8
UNION ALL
SELECT 'staticrc50', 9
UNION ALL
SELECT 'staticrc60', 10
UNION ALL
SELECT 'staticrc70', 11
UNION ALL
SELECT 'staticrc80', 12
)
,base AS
( SELECT schema_name
, table_name
, SUM(column_count) AS column_count
, ISNULL(SUM(short_string_column_count),0) AS short_string_column_count
, ISNULL(SUM(long_string_column_count),0) AS long_string_column_count
FROM ( SELECT sm.name AS schema_name
, tb.name AS table_name
, COUNT(co.column_id) AS column_count
, CASE WHEN co.system_type_id IN (36,43,106,108,165,167,173,175,231,239)
AND co.max_length <= 32
THEN COUNT(co.column_id)
END AS short_string_column_count
, CASE WHEN co.system_type_id IN (165,167,173,175,231,239)
AND co.max_length > 32 and co.max_length <=8000
THEN COUNT(co.column_id)
END AS long_string_column_count
FROM sys.schemas AS sm
JOIN sys.tables AS tb on sm.[schema_id] = tb.[schema_id]
JOIN sys.columns AS co ON tb.[object_id] = co.[object_id]
WHERE tb.name = @TABLE_NAME AND sm.name = @SCHEMA_NAME
GROUP BY sm.name
, tb.name
, co.system_type_id
, co.max_length ) a
GROUP BY schema_name
, table_name
)
, size AS
(
SELECT schema_name
, table_name
, 75497472 AS table_overhead
, column_count*1048576*8 AS column_size
, short_string_column_count*1048576*32 AS short_string_size, (long_string_column_count*16777216) AS long_string_size
FROM base
UNION
SELECT CASE WHEN COUNT(*) = 0 THEN 'EMPTY' END as schema_name
,CASE WHEN COUNT(*) = 0 THEN 'EMPTY' END as table_name
,CASE WHEN COUNT(*) = 0 THEN 0 END as table_overhead
,CASE WHEN COUNT(*) = 0 THEN 0 END as column_size
,CASE WHEN COUNT(*) = 0 THEN 0 END as short_string_size
,CASE WHEN COUNT(*) = 0 THEN 0 END as long_string_size
FROM base
)
, load_multiplier as
(
SELECT CASE
WHEN FLOOR(8 * (CAST (CAST(REPLACE(REPLACE(@DWU,'DW',''),'c','') AS INT) AS FLOAT)/6000)) > 0
AND CHARINDEX(@DWU,'c')=0
THEN FLOOR(8 * (CAST (CAST(REPLACE(REPLACE(@DWU,'DW',''),'c','') AS INT) AS FLOAT)/6000))
ELSE 1
END AS multiplication_factor
)
SELECT r1.DWU
, schema_name
, table_name
, rc.resource_class as closest_rc_in_increasing_order
, max_queries_at_this_rc = CASE
WHEN (r1.max_slots / r1.slots_used > r1.max_queries)
THEN r1.max_queries
ELSE r1.max_slots / r1.slots_used
END
, r1.max_slots as max_concurrency_slots
, r1.slots_used as required_slots_for_the_rc
, r1.tgt_mem_grant_MB as rc_mem_grant_MB
, CAST((table_overhead*1.0+column_size+short_string_size+long_string_size)*multiplication_factor/1048576 AS DECIMAL(18,2)) AS est_mem_grant_required_for_cci_operation_MB
FROM size
, load_multiplier
, #ref r1, names rc
WHERE r1.rc_id=rc.rc_id
AND CAST((table_overhead*1.0+column_size+short_string_size+long_string_size)*multiplication_factor/1048576 AS DECIMAL(18,2)) < r1.tgt_mem_grant_MB
ORDER BY ABS(CAST((table_overhead*1.0+column_size+short_string_size+long_string_size)*multiplication_factor/1048576 AS DECIMAL(18,2)) - r1.tgt_mem_grant_MB)
GO
المحتوى ذو الصلة
لمزيد من المعلومات حول إدارة مستخدمي قاعدة البيانات والأمان، راجع تأمين قاعدة بيانات في Synapse SQL. لمزيد من المعلومات حول كيف يمكن لفئات الموارد الكبيرة تحسين جودة مؤشر تخزين الأعمدة المتفاوت، راجع تحسينات الذاكرة لضغط مخزن الأعمدة.