简体   繁体   English

如何使用 XSLT 从 PHP 插入 xml 数据(作为变量)

[英]How can I insert xml data (as variable) from PHP using XSLT

I have a requirement of generating a master XML file by integrating some XML files.我需要通过集成一些 XML 文件来生成主 XML 文件。 It can be achieved if we have different child XML files stored at some where on the disk.如果我们将不同的子 XML 文件存储在磁盘上的某个位置,就可以实现。 But here in my case child XML files are dynamic XML data.但在我的例子中,子 XML 文件是动态 XML 数据。 They are not stored any where but generating dynamically.它们不存储在任何地方,而是动态生成。 So how can i insert these child XML data to generate a master XML file.那么我如何插入这些子 XML 数据来生成主 XML 文件。

My input is:我的输入是:

<root>
  <element id="1">
  </element>
  <element id="2">
  </element>
</root>

My output would be:我的输出是:

<root>
   <element id="1">
      <section>
         <record>12</record>
      </section>
   </element>
   <element id="2">
      <section>
          <input>menu</input>
      </section>
   </element>
</root>

Here in the above output XML data( <section><record>12</record></section> ) should come from PHP variable.上面输出的 XML 数据 ( <section><record>12</record></section> ) 应该来自 PHP 变量。

You have to pass the two "dynamic" XML documents as parameters to the transformation .您必须将两个“动态”XML 文档作为参数传递给转换

Each of the "dynamic documents" should be already parsed as an XML document (in other XSLT processor APIs there is a method -- for example XmlDocument.LoadXml() -- that takes a string and parses it as XML and creates a (parsed) XML document).每个“动态文档”都应该已经被解析为 XML 文档(在其他 XSLT 处理器 API 中有一个方法——例如XmlDocument.LoadXml() ——接受一个字符串并将其解析为 XML 并创建一个(已解析的) XML 文档)。

Read your XSLT processor documentation to learn what API to use for passing external parameters to a transformation阅读您的 XSLT 处理器文档以了解使用什么 API 将外部参数传递给转换

This is an old thread, but no satisfying answer has been given;这是一个旧线程,但没有给出令人满意的答案; recently I was confronted with a similar situation and I believe the solution is general enough to apply to problems like this one.最近我遇到了类似的情况,我相信该解决方案足够通用,可以适用于此类问题。

Essentially: PHP and the XSLT processor communicate via DOMNode objects (parameters and return values).本质上:PHP 和 XSLT 处理器通过DOMNode对象(参数和返回值)进行通信。 Therefore, it is possible to construct a DOMNode object using PHP, returning it at the request of the XSLT processor.因此,可以使用 PHP 构造一个DOMNode对象,并在 XSLT 处理器的请求下返回它。

Given the above example, we would have the following XSLT:鉴于上面的例子,我们将有以下 XSLT:

<xsl:stylesheet version="1.0"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
                xmlns:php="http://php.net/xsl">
  <xsl:template match="/root">
    <root>
      <xsl:apply-templates select="element" />
    </root>
  </xsl:template>

  <xsl:template match="element">
    <element>
      <!-- Pass the selected id attributes to a PHP callback,
           then literally include the XML as returned from PHP.
           Alternatively, one could use xsl:apply-templates
           to further transform the result. -->
      <xsl:copy-of select="php:function('xslt_callback', @id)" />
    </element>
  </xsl:template>
</xsl:stylesheet>

And the PHP function (this function should be exporteded with the registerPHPFunctions method [ see php manual ]) would be: PHP 函数(该函数应使用registerPHPFunctions方法导出 [ 参见 php 手册])将是:

/**
 * @param  DOMAttr[]  $attr_set An array of DOMAttr objects,
 *                              passed by the XSLT processor.
 * @return DOMElement           The XML to be inserted.
 */
function xslt_callback ($attr_set) {
  $id = $attr_set[0]->value;
  return new DOMElement('section', $id); //whatever operation you fancy
}

Resulting in the following XML:产生以下 XML:

<root>
  <element>
    <section>1</section>
  </element>
  <element>
    <section>2</section>
  </element>
</root>

The php function xslt_callback can do whatever it likes with the selected id. php 函数xslt_callback可以对选定的 id 做任何它喜欢的事情。 We assume in this example that $attr_set always contains exactly one selected attribute.在本例中,我们假设$attr_set始终只包含一个选定的属性。 Depending on the situation, it might be advisable to perform some range or type checking;根据情况,执行一些范围或类型检查可能是明智的; here however, this would only needlessly complicate the example skeleton.然而,在这里,这只会不必要地使示例框架复杂化。

Note: simply returning an XML string from PHP would result in &lt;注意:简单地从 PHP 返回一个 XML 字符串将导致&lt; and &gt; &gt; tags to be inserted for every < and > .为每个<>插入的标签。

I'm still wondering what you wanted from php I assumed that you could reprint and throw something like the following in a loop but I'm happy to dig further to the point of making something website front end with dynamic xml generation.我仍然想知道你想从 php 得到什么我假设你可以重新打印并在循环中抛出类似下面的东西但我很高兴进一步挖掘到使用动态 xml 生成制作网站前端的点。 Changing in this page what scalors option does by switching values is distinct in php there's lots that could be done please tell me further what you Want在此页面中通过切换值更改 scalors 选项的功能在 php 中是不同的有很多可以完成的请进一步告诉我你想要什么

<?php
$i=1;
$option = "default";
$elemental = 1;
$StrRecord = "12";
$StrInput = "menu";
$domdoc = new DOMDocument();
$domdoc->preserveWhiteSpaces = false;
$domdoc->load(realpath('xmlfile.xml'));
$root = new DOMElement('root');
$element = new DOMElement('element');
$section = new DOMElement('section');
$record = new DOMElement('record', $StrRecord);
$elementi = new DOMElement('element');
$sectioni = new DOMElement('section');
$inputi = new DOMElement('input', $StrInput);
$elementid= new DOMAttr('id', $elemental+1);
$elementidi= new DOMAttr('id', $elemental+1);

$domdoc->appendChild($root);
$root->appendChild($element);
$element->appendChild($section);
$section->appendChild($record);
$root->appendChild($elementi);
$elementi->appendChild($sectioni);
$sectioni->appendChild($inputi);
$sectioni->appendChild($inputi);
$element->appendChild($elementid);
$elementi->appendChild($elementidi);
$domdoc->formatOutput = true;
$domdoc->save('xmlfile.xml');

$xmldoc= new DOMDocument();
$xmldoc->load(realpath('xmlfile.xml'));
$xpath = new DOMXpath($xmldoc);

switch($option){
case "record":
$query = ('/root/element/section/record');
break;
case "input":
$query = ('/root/element/section/input');
break;
case "default":
$query = ('/root/element[@id="'. $i.'"]/');
break;
}
$nodeList = $xpath->query($query);
foreach($nodeList as $node){
echo($node->nodeValue);
}
?>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM