Как я могу предотвратить добавление appendChild () xmlns = "" - PullRequest
0 голосов
/ 16 ноября 2010

Вот фрагмент моего кода.

FilterText = HttpUtility.UrlDecode(FilterTxt.Value.ToString());
               XmlWriterSettings settings = new XmlWriterSettings();
               settings.Indent = true;
               TextWriter tw = new StreamWriter("D:\\FilterTest.rdl");
               tw.WriteLine(FilterText);
               tw.Close();
               XmlDocument reportrdl = new XmlDocument();
               reportrdl.Load(ReportFile);
               NMS = reportrdl.NamespaceURI;
               XmlNodeList fieldsnode = reportrdl.GetElementsByTagName("DataSet");
               //XmlElement xoo = reportrdl.CreateElement("Filters", NMS);
               //reportrdl.AppendChild(xoo);
               foreach (XmlNode fields in fieldsnode)
               {
                   // second document to merge (the new Filter File)

                   XmlDocument filterrdl = new XmlDocument();
                   filterrdl.Load("D:\\FilterTest.rdl");

                   XmlNode imported = reportrdl.ImportNode(filterrdl.DocumentElement, true);

                   fields.AppendChild(imported);
                   break;
               }
               //XmlNodeList filtersnode = reportrdl.GetElementsByTagName("Filters");
               //foreach (XmlNode filters in filtersnode)
               //{
               //    filters.Attributes.RemoveNamedItem("xmlns");
               // }
               reportrdl.Save("D:\\NewFilter.rdl");

Вот фрагмент файла rdl:

<Report xmlns="http://schemas.microsoft.com/sqlserver/reporting/2005/01/reportdefinition" xmlns:rd="http://schemas.microsoft.com/SQLServer/reporting/reportdesigner">
  <DataSources>
    <DataSource Name="BOSS">
      <rd:DataSourceID>c6a8409e-71a4-4e96-86ad-b300a5b942c3</rd:DataSourceID>
      <ConnectionProperties>
        <DataProvider>SQL</DataProvider>
        <ConnectString>dats a no no</ConnectString>
        <IntegratedSecurity>true</IntegratedSecurity>
      </ConnectionProperties>
    </DataSource>
  </DataSources>

Далее в этом файле после <Query> мне нужно объединить в <Filters>

Вот этот файл:

<Filters>
  <Filter>
    <FilterExpression>=Fields!RoleID.Value</FilterExpression>
    <Operator>Equal</Operator>
    <FilterValues>
      <FilterValue>=27</FilterValue>
    </FilterValues>
  </Filter>
</Filters>

заканчивается <Filters xmlns=""> вместо <Filters>

Спасибо

1 Ответ

2 голосов
/ 16 ноября 2010

Вам нужно показать нам образцы XML двух файлов, которые вы пытаетесь объединить.

Вероятно, происходит то, что в первом файле reportrdl элементы DataSet находятся по умолчаниюобъявление пространства имен, отличное от "".Поэтому каждый элемент под ними, который не имеет префикса пространства имен и не переопределяет объявление пространства имен по умолчанию, будет находиться в пространстве имен по умолчанию, объявленном его предком.

Но вы импортируете Filters элементы, которые не являютсяв этом пространстве имен, и не имеют префикса.Следовательно, , чтобы предотвратить их наследование пространства имен по умолчанию, которое к ним не относится, необходимо отменить объявление пространства имен по умолчанию , что делается с помощью xmlns="".

Если вышеприведенноене в этом случае, предоставьте образцы двух XML-документов, поэтому мы не пытаемся делать операцию в темноте.

Если приведенный выше соответствует , вопрос к вам. почему вы не хотите xmlns="" в выводе?Похоже, это правильный вывод. Но, возможно, вы этого не хотите, потому что хотите, чтобы импортированный элемент Filters находился в том же пространстве имен, что и его родительский элемент;в этом случае вам нужно изменить пространство имен imported.Затем последуют объявления пространства имен.

Или, может быть, вы хотите, чтобы импортированный узел не находился в пространстве имен, так что вывод уже технически корректен, но вам не нравится эстетика xmlns="".Или, может быть, есть нисходящий потребитель XML, который по какой-то причине душит xmlns="".Расскажите нам больше о своих ограничениях, чтобы мы могли знать, как помочь.

Обновление:

Хорошо, теперь мы знаем, что

  • Элементы в первом файлев пространстве имен определения отчета, URL-адрес которого "http://schemas.microsoft.com/sqlserver/reporting/2009/01/reportdefinition".Мы можем сказать, потому что элемент верхнего уровня, <Report>, имеет объявление пространства имен по умолчанию: xmlns="http://schemas.microsoft.com.../reportdefinition".Это означает, что для <Report> и всех потомков любой элемент без префикса пространства имен считается находящимся в пространстве имен определения отчета.
  • Элементы в импортированном файле, такие как <Filters> , должны находиться в том же пространстве имен определения отчета.Я сделал вывод из MS документации , хотя это не ясно.Большая часть этой документации, к сожалению, ужасна ... полна плохо сформированного XML даже!
  • Однако импортированный элемент <Filters> и его потомки фактически не находятся в пространстве имен (до того, как вы их импортируете)потому что у них нет префикса пространства имен и объявления пространства имен по умолчанию.

Поэтому, когда вы импортируете элемент <Filters>, AppendChild() должен действовать, чтобы сохранить его в том же пространстве имен, в котором он находится (т.е. нетnamespace) - иначе это было бы как смена имени.<Filters> в пространстве имен не отличается от <Filters> в пространстве имен reportdefinition.Если <Filters> был добавлен в <DataSet> как есть, он унаследует объявление пространства имен по умолчанию от своего нового предка <Report>, и, таким образом, его пространство имен будет изменено на пространство имен определения отчета.

Однако вы do хотите, чтобы он был в пространстве имен определения отчета.Самый простой способ сделать это - изменить импортированный файл , чтобы <Filters> было уже в этом пространстве имен:

<Filters xmlns="http://schemas.microsoft.com/sqlserver/reporting/2005/01/reportdefinition">
  <Filter>

Затем AppendChild () будетобратите внимание, что <Filters> уже находится в пространстве имен по умолчанию своих новых предков, и ему не нужно будет объявлять пространство имен по умолчанию.Фактически, он может удалить объявление пространства имен по умолчанию в <Filters>, которое теперь является избыточным.

Однако мы не можем гарантировать , что оно удалит его.Одна важная вещь для понимания пространств имен XML заключается в том, что имеет значение то, в каком пространстве имен находится каждый элемент .Неважно, какой префикс используется для указания этого пространства имен, а также не имеет значения, где и сколько раз этот префикс пространства имен (или пространство имен по умолчанию) объявляется: до тех пор, пока каждый элемент заканчивается вправильное пространство имен.

Таким образом, независимо от того, имеет ли импортированный элемент <Filters> объявление пространства имен по умолчанию (DND) или нет , не должно иметь значения для любого законного потребителя XML.Все, что имеет значение, это то, что он находится в пространстве имен определения отчета.Если процессор Microsoft RDL заглушает DND, это означает, что процессор не соответствует стандартам пространств имен XML.

Я бы действительно рекомендовал прочитать краткое руководство по пространствам имен XML ... Они не такие сложные,несмотря на их репутацию;они почти повсеместны, когда вы работаете со стандартными словарями XML;и понимание того, как работают декларации, может избавить вас от головной боли. Этот не короткий но это хорошо.Я не могу рекомендовать w3schools, потому что он путает префиксы с пространствами имен.: -p

Ничего себе, это стало длинным.Однако я чувствовал, что это необходимо: мы можем удерживать воду в течение всего дня, но я бы предпочел устранить утечку, вызванную непониманием того, как работают объявления пространства имен XML.

...