2010-09-06 14 views
8

我一直在嘗試在Google Chrome上使用XSL,但沒有成功。
我讀到Chrome有XSLT的一些錯誤,其中一個是它不支持xsl:include。錯誤可以在這裏檢查:http://code.google.com/p/chromium/issues/detail?id=8441
經過一番研究,我發現了Daer System的一個新版本的轉換插件,它使得xsl:include在Chrome中工作。xsl:include和xsl:param在谷歌瀏覽器中,使用jQuery變換插件

的jQuery插件變換可以從http://plugins.jquery.com/project/Transform

發現現在我的問題是:
我使用的是默認包括在一些XSL模板,這包括使用傳遞給頂層一個參數。

所以它像我有top.xsl模板聲明瞭一個[XSL:PARAM NAME =「參數」 /],我用這個PARAM與included.xsl,由第一叫一個用[xsl:include href =「included.xsl」]。這適用於Firefox和Internet Explorer,但不適用於Chrome。我在這裏看到了一個關於stackoverflow的問題,其中一些人重新編寫了插件的webkit修復功能,但這種方式不適用於xsl:param。

有沒有人知道在Google Chrome中使用[xsl:param]這種方式?

+0

看起來只有在通過JavaScript運行轉換時才如此。正如你所看到的,我的XML/XSLT驅動的網站工作:www.aranedabienesraices.com.ar – 2010-09-06 19:35:03

+0

嗨亞歷杭德羅,是的,這是通過JavaScript轉換。我需要通過javascript來做到這一點。 – 2010-09-06 19:45:59

+0

user357812:請解釋:該鏈接與此問題有何關係? – jsalonen 2011-05-31 13:04:27

回答

1

你這裏的問題是,谷歌瀏覽器(=鉻)不支持xsl:include

缺少此功能在Chromium項目很好地注意爲"Issue 8441: XSLTProcessor in JS does not permit xsl:include for http"募集。看起來問題是由WebKit(Chrome中使用的渲染引擎)中的一些架構問題引起的。由於此問題源於WebKit,因此該錯誤被標記爲WontFix--隨着WebKit中的原始問題得到解決,未來將提供修復(希望)。

我看到這個問題怎麼能爲您解決三種可能的備選方案:

  1. 一直等到的WebKit/Chrome瀏覽修復此問題補丁(可能需要很長的時間......)
  2. 創建/發現,由鍍鉻/ Webkit的模擬不知何故xsl:include解決此問題的工作,例如一個黑客(可能需要大量的工作/開發一個黑客)
  3. 試圖找到一種方式寫你的軟件,我避免使用XSL:你不需要這個特定的XSL功能(在服務器端運行或者XSL轉換)

我的建議吶的方式包括以xsl:在客戶端PARAM除非你願意給跨瀏覽器的兼容性

+0

嗨jsalonen,謝謝你的回答。由於問題來自sep,2010年,我設法通過「重新編譯」xsl頁面來解決這個問題。當我在服務器端使用.net時,我創建了一個腳本來移除xsl:include並將xsl包含文件連接到調用它的那些文件中。 我敢肯定它可以用javascript來解決這個問題,但正如你所說的那樣,需要很多工作和很多代碼來管理它。所以我只是在服務器上做了這些工作,這樣我仍然可以重新使用xsl:templates編輯原始文件,並且javascript讀取服務器生成的xsl文件。 – 2011-05-31 17:16:03

0

這是一種痛苦,但您也可以使用客戶端填充程序解決此問題,該填充程序可在瀏覽器中預加載任何xsl:import/xsl:include。

以下是TypeScript(基本上是靜態類型的JavaScript,編譯爲JavaScript),並且有幾個引用這些接口的引用。我沒有去掉它,但它似乎可以在Chrome中工作(不確定其他瀏覽器),並且應該足以讓任何人開始解決方案。

module DD.Render.DOM.XSLT { 

export class StandardXSLTDOMTransformerFactory implements IXSLTDOMTransformerFactory { 

    constructor(private _domParser:DOMParser, private _document:Document) { 
    } 

    createTransformerFromPath<T>(xslPath: string, xmlTransformer: IStringTransformer<T>, onSuccess: (transformer: IParameterizedDOMTransformer<T>) => void, onFailure: (e: any) => void): void { 
     DD.Util.readXML(
      xslPath, 
      (node: Node) => { 

       // look up any xsl:import or xsl:includes and pull those in too! 
       var onIncludesPreloaded =() => { 
        console.log(node); 
        var transformer = this.createTransformerFromNode(node, xmlTransformer); 
        onSuccess(transformer); 
       }; 
       this.rewriteIncludes(xslPath, node, {}, onIncludesPreloaded, onFailure); 
      }, function (e: any) { 
       onFailure(e); 
      } 
     ); 
    } 

    rewriteIncludes(path:string, node: Node, imported: { [_: string]: boolean }, onRewritten:()=>void, onFailure:(e:any)=>void): void { 
     var result; 
     var element = <Element>node; 
     var importNodes = element.querySelectorAll("import,include"); 
     if (importNodes.length == 0) { 
      onRewritten(); 
      result = false; 
     } else { 
      var rewrittenNodes = 0; 
      // load imports 
      for (var i = 0; i < importNodes.length; i++) { 
       var importElement = <Element>importNodes.item(i); 
       var href = importElement.getAttribute("href"); 
       // TODO work out relative path 
       var relativePath = DD.Util.appendRelativePath(path, href); 
       console.log("importing " + href +" + "+path+" -> "+relativePath); 
       if (!imported[relativePath]) { 
        var e = importElement; 
        imported[relativePath] = true; 
        DD.Util.readXML(relativePath, (importedStylesheet: Node) => { 
         this.rewriteIncludes(relativePath, importedStylesheet, imported, function() { 
          // replace the import with this node (minus stylesheet container) 
          for (var j = 0; j < importedStylesheet.firstChild.childNodes.length; j++) { 
           var templateNode = importedStylesheet.firstChild.childNodes.item(j); 
           if (templateNode.nodeName.indexOf("template") >= 0) { 
            e.parentNode.insertBefore(templateNode, e); 
           } 
          } 
          e.parentNode.removeChild(e); 
          rewrittenNodes++; 
          if (rewrittenNodes == importNodes.length) { 
           if (onRewritten) { 
            onRewritten(); 
           } 
          } 
         }, onFailure); 
        }, onFailure); 
       } else { 
        importElement.parentNode.removeChild(importElement); 
       } 
      } 
      result = true; 
     } 
     return result; 
    } 

    createTransformerFromNode<T>(xsl: Node, xmlTransformer: IStringTransformer<T>): IParameterizedDOMTransformer<T> { 
     var nodeTransformer = new DOMParserDOMTransformer(this._domParser, xmlTransformer); 
     var xsltProcessor = new XSLTProcessor(); 
     xsltProcessor.importStylesheet(xsl); 
     return new StandardXSLTDOMTransformer<T>(xsltProcessor, nodeTransformer, this._document); 
    } 

} 

} 

module DD.Util { 

export function readXML(path: string, onSuccess: (node: Node) => void, onFailure: (e: any) => void) { 
    var xhr = new XMLHttpRequest(); 
    xhr.onload = function() { 
     onSuccess(xhr.responseXML); 
    }; 
    xhr.onerror = function (e: ErrorEvent) { 
     onFailure(e); 
    }; 
    xhr.open("GET", path, true); 
    xhr.send(null); 
} 

export function appendRelativePath(originalPath: string, relativePath: string, originalPathIsDirectory?: boolean) { 
    if (originalPathIsDirectory == null) { 
     originalPathIsDirectory = originalPath.charAt(originalPath.length - 1) == '/'; 
    } 
    if (!originalPathIsDirectory) { 
     // remove file imediately 
     var lastSlash = originalPath.lastIndexOf('/'); 
     if (lastSlash >= 0) { 
      originalPath = originalPath.substring(0, lastSlash + 1); 
     } else { 
      originalPath = ""; 
     } 
    } 
    var slashIndex = relativePath.indexOf('/'); 
    if (slashIndex >= 0) { 
     var relativeDirectory = relativePath.substring(0, slashIndex + 1); 
     var relativeRemainder = relativePath.substring(slashIndex + 1); 
     if (relativeDirectory == "../") { 
      // trim off a directory on the original path 
      if (originalPath.charAt(originalPath.length - 1) == '/') { 
       originalPath = originalPath.substring(0, originalPath.length - 1); 
      } 
      var dirIndex = originalPath.lastIndexOf('/'); 
      if (dirIndex >= 0) { 
       originalPath = originalPath.substring(0, dirIndex + 1); 
      } else { 
       originalPath = ""; 
      } 
     } else { 
      // append to the original path 
      if (originalPath.charAt(originalPath.length - 1) != '/') { 
       originalPath += '/'; 
      } 
      originalPath += relativeDirectory; 
     } 
     appendRelativePath(originalPath, relativeRemainder, true); 
    } else { 
     // append and be done 
     if (originalPath.charAt(originalPath.length - 1) != '/') { 
      originalPath += '/'; 
     }    
     return originalPath + relativePath; 
    } 
} 

} 
1

舊主題我知道,但在這裏查看是否問題已經解決。

我再次測試,它至少在Chrome版本47中。最後你可以使用xsl:include。