Ваш подход с использованием FROM OPENXML
вместе с SP для подготовки и удаления документа устарел и больше не должен использоваться (существуют редкие исключения).
В течение примерно 15 лет SQL -Server поддерживает родные XML методы для XPath и XQuery:
Попробуйте это так (я предполагаю, что содержимое вашего файла загружено в @xml
):
(Подсказка: у меня было исправить некоторые ошибки ... Ваш XML не был правильно сформирован ...)
DECLARE @xml XML=
N'<HRD>
<Search>ER-0002</Search>
<SubCHD>
<APPR_PROC_CD>ADR</APPR_PROC_CD>
<Line_Items>
<APPRVL_EMPL_ID>119845</APPRVL_EMPL_ID>
<APPRVL_SEQ_NO>23358960</APPRVL_SEQ_NO>
<APPRVL_DTT>2019-18-05T13:19:27</APPRVL_DTT>
</Line_Items>
<Line_Items>
<APPRVL_EMPL_ID>788270</APPRVL_EMPL_ID>
<APPRVL_SEQ_NO>287360</APPRVL_SEQ_NO>
<APPRVL_DTT>2014-11-05T13:19:27</APPRVL_DTT>
</Line_Items>
<Line_Items>
<APPRVL_EMPL_ID>72987437</APPRVL_EMPL_ID>
<APPRVL_SEQ_NO>23484580</APPRVL_SEQ_NO>
<APPRVL_DTT>2013-11-05T13:19:27</APPRVL_DTT>
</Line_Items>
<RQ_Sub>
<Delta>N</Delta>
<LN_Act>
<ACCT_ID>ABDSNJD1267</ACCT_ID>
</LN_Act>
</RQ_Sub>
</SubCHD>
</HRD>';
- Запрос будет использовать некоторые вызовы .value()
для самой переменной (неповторяющиеся элементы ) и будет использовать .nodes()
для возврата повторяющихся элементов (вашего <Line_Items>
) в качестве производного набора.
SELECT @xml.value('(/HRD/Search/text())[1]','varchar(100)') AS Search
,@xml.value('(/HRD/SubCHD/APPR_PROC_CD/text())[1]','varchar(100)') AS ApprProcCd
,li.value('(APPRVL_EMPL_ID/text())[1]','bigint') AS EmplId
,li.value('(APPRVL_SEQ_NO/text())[1]','bigint') AS SeqNo
,li.value('(APPRVL_DTT/text())[1]','varchar(100)') AS Dtt --Attention!!!!!
,@xml.value('(/HRD/SubCHD/RQ_Sub/Delta/text())[1]','varchar(100)') AS Delta
,@xml.value('(/HRD/SubCHD/RQ_Sub/LN_Act/ACCT_ID/text())[1]','varchar(100)') AS AcctId
FROM @xml.nodes('/HRD/SubCHD/Line_Items') A(li)
Результат
ER-0002 ADR 119845 23358960 2019-18-05T13:19:27 N ABDSNJD1267
ER-0002 ADR 788270 287360 2014-11-05T13:19:27 N ABDSNJD1267
ER-0002 ADR 72987437 23484580 2013-11-05T13:19:27 N ABDSNJD1267
Очень важно: Значения даты и времени выглядят так, как если бы они были ISO8601 (T
в середине), но формат даты - ydm, для которого должно быть ymd. В противном случае мы могли бы указать datetime
в качестве целевого типа в .value()
.