2016-03-16 5 views
0

Цель: импортировать XML-файл odata xml в XML-блок преобразования XML.сгладить XML-вложенный узел с XSLT

SSIS контрсилами:

  • только одно пространство имен
  • не вложенные узлы
  • удалить "ип необходимости" ссылка узла

упрощенный источник XML ввода

<?xml version="1.0" encoding="utf-8" standalone="yes"?> 
<feed xml:base="https://XXXXXXXXXX/XRMServices/2011/OrganizationData.svc/" xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices" xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" xmlns="http://www.w3.org/2005/Atom"> 
    <title type="text">allianceSet</title> 
    <entry> 
    <link rel="edit" title="be_alliance" href="be_allianceSet(guid'429352cb-deca-e311-80c0-00155d5682af')" /> 
    <link rel="XXXX" type="application/atom+xml;type=entry" title="lk_be_alliance_createdby" href="be_allianceSet/lk_be_alliance_createdby" /> 
    <link rel="XXXX" type="application/atom+xml;type=entry" title="lk_be_alliance_createdonbehalfby" href="be_allianceSet(/lk_be_alliance_createdonbehalfby" /> 
    <content type="application/xml"> 
     <m:properties> 
     <d:ModifiedOn m:type="Edm.DateTime">2015-10-30T13:06:31Z</d:ModifiedOn> 
     <d:CreatedBy m:type="Microsoft.Crm.Sdk.Data.Services.EntityReference" m:null="true"> 
      <d:Id m:type="Edm.Guid">40f20074-ede3-48cc-aafc-750a1275b99b</d:Id> 
      <d:LogicalName>systemuser</d:LogicalName> 
     </d:CreatedBy> 
     <d:statecode m:type="Microsoft.Crm.Sdk.Data.Services.OptionSetValue"> 
      <d:Value m:type="Edm.Int32">0</d:Value> 
     </d:statecode> 
     </m:properties> 
    </content> 
    </entry> 
</feed> 

XSL 1,0

<?xml version="1.0"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 

    <xsl:output indent="yes" method="xml" encoding="utf-8" omit-xml-declaration="yes"/> 

    <xsl:template match="*[name() != 'link']"> 
     <xsl:element name="{local-name()}"> 
      <xsl:apply-templates select="@* | node()"/> 
     </xsl:element> 
    </xsl:template> 

    <!-- template to copy attributes --> 
    <xsl:template match="@*"> 
     <xsl:attribute name="{local-name()}"> 
      <xsl:value-of select="."/> 
     </xsl:attribute> 
    </xsl:template> 
</xsl:stylesheet> 

выше xsl отлично удаляет пространства имен. Однако я пытаюсь преобразовать/расплющить каждый узел типа = «Microsoft.Crm.Sdk.Data.Services.EntityReference» только с одним значением Guid

...  
<CreatedBy type="Microsoft.Crm.Sdk.Data.Services.EntityReference" null="true"> 
    <Id type="Edm.Guid">40f20074-ede3-48cc-aafc-750a1275b99b</Id> 
    <LogicalName>systemuser</LogicalName> 
    </CreatedBy> 
... 

в

... 
    <CreatedBy>40f20074-ede3-48cc-aafc-750a1275b99b</CreatedBy> 
... 

до сих пор не любая удача ... любая помощь оценили

ответ

1

Похоже, вы избегаете ссылки на какое-либо конкретное пространство имен в XSLT. Если это так, чтобы соответствовать узлу с аа атрибута типа из «Microsoft.Crm.Sdk.Data.Services.EntityReference», вы бы матч шаблон, как это:

<xsl:template match="*[@*[local-name() = 'type']='Microsoft.Crm.Sdk.Data.Services.EntityReference']"> 

Попробуйте этот XSLT

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output indent="yes" method="xml" encoding="utf-8" omit-xml-declaration="yes"/> 

    <xsl:template match="*"> 
     <xsl:element name="{local-name()}"> 
      <xsl:apply-templates select="@* | node()"/> 
     </xsl:element> 
    </xsl:template> 

    <xsl:template match="*[local-name() = 'link']" /> 

    <xsl:template match="*[@*[local-name() = 'type']='Microsoft.Crm.Sdk.Data.Services.EntityReference']"> 
     <xsl:element name="{local-name()}"> 
      <xsl:value-of select="*[local-name() = 'Id']" /> 
     </xsl:element> 
    </xsl:template> 

    <!-- template to copy attributes --> 
    <xsl:template match="@*"> 
     <xsl:attribute name="{local-name()}"> 
      <xsl:value-of select="."/> 
     </xsl:attribute> 
    </xsl:template> 
</xsl:stylesheet> 

Обратите внимание, что я создал отдельный шаблон для удаления элементов link. С вашим текущим XSLT элемент ссылки фактически будет соответствовать встроенным шаблонам XSLT, который выводит любые текстовые узлы под link, если они есть (что может быть не так для вас, но может быть лучше для кода для него) ,

Конечно, если вы имели дело с XML-документами с теми же пространствами имен все время, вы можете ссылаться на них в вашем XSLT, как это так, что немного аккуратнее:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices" 
    xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" 
    xmlns:atom="http://www.w3.org/2005/Atom"> 

    <xsl:output indent="yes" method="xml" encoding="utf-8" omit-xml-declaration="yes"/> 

    <xsl:template match="*"> 
     <xsl:element name="{local-name()}"> 
      <xsl:apply-templates select="@* | node()"/> 
     </xsl:element> 
    </xsl:template> 

    <xsl:template match="atom:link" /> 

    <xsl:template match="*[@m:type='Microsoft.Crm.Sdk.Data.Services.EntityReference']"> 
     <xsl:element name="{local-name()}"> 
      <xsl:value-of select="d:Id" /> 
     </xsl:element> 
    </xsl:template> 

    <!-- template to copy attributes --> 
    <xsl:template match="@*"> 
     <xsl:attribute name="{local-name()}"> 
      <xsl:value-of select="."/> 
     </xsl:attribute> 
    </xsl:template> 
</xsl:stylesheet> 
+0

это была трудная борьба за совпадающий узел с пространством имен с моими низкими навыками в xslt (я использую xslt каждые 5 лет ...). Ваше решение отлично работает, и вся информация сглажена, как ожидалось. – camous