في SQL Server، هل يمكنني إدراج عقد متعددة في XML من جدول؟
-
02-07-2019 - |
سؤال
أريد إنشاء بعض XML في إجراء مخزن بناءً على البيانات الموجودة في الجدول.
يتيح لي الإدخال التالي إضافة العديد من العقد ولكن يجب أن تكون مشفرة أو تستخدم متغيرات (sql:variable):
SET @MyXml.modify('
insert
<myNode>
{sql:variable("@MyVariable")}
</myNode>
into (/root[1]) ')
حتى أتمكن من تكرار كل سجل في جدولي، ووضع القيم التي أحتاجها في المتغيرات وتنفيذ العبارة أعلاه.
ولكن هل هناك طريقة يمكنني من خلالها القيام بذلك من خلال الدمج مع عبارة مختارة وتجنب الحلقة؟
يحرر لقد استخدمت SELECT FOR XML
للقيام بأشياء مماثلة من قبل ولكني أجد دائمًا صعوبة في القراءة عند العمل مع تسلسل هرمي للبيانات من جداول متعددة.كنت آمل أن يكون هناك شيء يستخدم modify
حيث يكون XML الذي تم إنشاؤه أكثر وضوحًا وأكثر قابلية للتحكم.
المحلول
هل جربت التعشيش بالنسبة لوظائف XML PATH ذات القيمة العددية؟باستخدام تقنية التداخل، يمكنك تقسيم SQL الخاص بك إلى أجزاء عنصرية سهلة الإدارة/القراءة
تنصل:ما يلي، رغم أنه مقتبس من مثال عملي، لم يتم اختباره حرفيًا
بعض الروابط المرجعية للجمهور العام
- http://msdn2.microsoft.com/en-us/library/ms178107(SQL.90).aspx
- http://msdn2.microsoft.com/en-us/library/ms189885(SQL.90).aspx
أبسط وأدنى مثال للعقدة المتداخلة
خذ بعين الاعتبار الاستدعاء التالي
DECLARE @NestedInput_SpecificDogNameId int
SET @NestedInput_SpecificDogNameId = 99
SELECT [dbo].[udfGetLowestLevelNestedNode_SpecificDogName]
(@NestedInput_SpecificDogNameId)
لنفترض أنه تم كتابة udfGetLowestLevelNestedNode_SpecificDogName بدون عبارة FOR XML PATH، وبالنسبة لـ @NestedInput_SpecificDogName = 99 فإنه يُرجع سجل مجموعة الصفوف الفردية:
@SpecificDogNameId DogName 99 Astro
ولكن مع جملة FOR XML PATH،
CREATE FUNCTION dbo.udfGetLowestLevelNestedNode_SpecificDogName
(
@NestedInput_SpecificDogNameId
)
RETURNS XML
AS
BEGIN
-- Declare the return variable here
DECLARE @ResultVar XML
-- Add the T-SQL statements to compute the return value here
SET @ResultVar =
(
SELECT
@SpecificDogNameId as "@SpecificDogNameId",
t.DogName
FROM tblDogs t
FOR XML PATH('Dog')
)
-- Return the result of the function
RETURN @ResultVar
END
تُنتج الوظيفة المعرفة من قبل المستخدم ملف XML التالي (تؤدي العلامات @ إلى إرجاع حقل SpecifiqueDogNameId كسمة)
<Dog SpecificDogNameId=99>Astro</Dog>
تداخل الوظائف المعرفة من قبل المستخدم من نوع XML
يمكن دمج الوظائف المعرفة من قبل المستخدم مثل udfGetLowestLevelNestedNode_SpecificDogName أعلاه لتوفير طريقة قوية لإنتاج XML معقد.
على سبيل المثال، الدالة
CREATE FUNCTION [dbo].[udfGetDogCollectionNode]()
RETURNS XML
AS
BEGIN
-- Declare the return variable here
DECLARE @ResultVar XML
-- Add the T-SQL statements to compute the return value here
SET @ResultVar =
(
SELECT
[dbo].[udfGetLowestLevelNestedNode_SpecificDogName]
(t.SpecificDogNameId)
FROM tblDogs t
FOR XML PATH('DogCollection') ELEMENTS
)
-- Return the result of the function
RETURN @ResultVar
END
عندما يتم استدعاؤه كـ
SELECT [dbo].[udfGetDogCollectionNode]()
قد تنتج عقدة XML المعقدة (بالنظر إلى البيانات الأساسية المناسبة)
<DogCollection>
<Dog SpecificDogNameId="88">Dino</Dog>
<Dog SpecificDogNameId="99">Astro</Dog>
</DogCollection>
من هنا، يمكنك الاستمرار في العمل لأعلى في الشجرة المتداخلة لإنشاء بنية XML معقدة كما يحلو لك
CREATE FUNCTION [dbo].[udfGetAnimalCollectionNode]()
RETURNS XML
AS
BEGIN
DECLARE @ResultVar XML
SET @ResultVar =
(
SELECT
dbo.udfGetDogCollectionNode(),
dbo.udfGetCatCollectionNode()
FOR XML PATH('AnimalCollection'), ELEMENTS XSINIL
)
RETURN @ResultVar
END
عندما يتم استدعاؤه كـ
SELECT [dbo].[udfGetAnimalCollectionNode]()
قد ينتج udf عقدة XML الأكثر تعقيدًا (بالنظر إلى البيانات الأساسية المناسبة)
<AnimalCollection>
<DogCollection>
<Dog SpecificDogNameId="88">Dino</Dog>
<Dog SpecificDogNameId="99">Astro</Dog>
</DogCollection>
<CatCollection>
<Cat SpecificCatNameId="11">Sylvester</Cat>
<Cat SpecificCatNameId="22">Tom</Cat>
<Cat SpecificCatNameId="33">Felix</Cat>
</CatCollection>
</AnimalCollection>
نصائح أخرى
هل يمكنك معرفة المزيد حول ما تخطط للقيام به بالضبط؟هل هو ببساطة إنشاء بيانات XML استنادًا إلى محتوى الجدول أو إضافة بعض البيانات من الجدول إلى بنية XML الموجودة؟
هناك سلسلة كبيرة من المقالات فيما يتعلق بموضوع XML في SQLServer الذي كتبه جاكوب سيباستيان، فإنه يبدأ بـ أساسيات توليد XML من البيانات الموجودة في الجدول
استخدم sql:column بدلاً من sql:variable.يمكنك العثور على معلومات مفصلة هنا: http://msdn.microsoft.com/en-us/library/ms191214.aspx