2013-01-05 98 views
3

我正在編寫一個Chrome擴展,它應該將XSLT轉換應用於某些XML文檔。只是爲了測試我使用下面的XML和XSL文件:Chrome擴展中的XSLT:不安全地嘗試加載URL

XML:

<?xml version="1.0" encoding="utf-8" ?> 
<WebServiceMessage> 
<status>timeout</status> 
<message>Nameserver%2520not%2520registered.</message> 
<stepName>Finish</stepName> 
<stepNumber>11</stepNumber> 
<maxStepNumber>11</maxStepNumber> 
<percent>100</percent> 
<session>2fc0f139b88a800151e5f21b9d747919</session> 
</WebServiceMessage> 

XSL:

<?xml version="1.0" ?> 
<xsl:stylesheet version="1.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:template match="/"> 
    <html><head></head> 
    <body> 
     <xsl:apply-templates/> 
    </body> 
    </html> 
    </xsl:template> 
    <xsl:template match="*"> 
    <xsl:for-each select="*"> 
     <p><b><xsl:value-of select ="name(.)"/></b>: 
     <span><xsl:attribute name="id"><xsl:value-of select ="name(.)"/></xsl:attribute><xsl:value-of select="."/></span></p> 
    </xsl:for-each> 
    </xsl:template> 
</xsl:stylesheet> 

如果它是一個測試XML文件中鏈接的tranfromation正常工作本身,即通過:

<?xml-stylesheet type="text/xsl" href="message.xsl"?> 

該擴展應該將相同的xsl鏈接注入到XML文件中。

的manifest.json:

{ 
    "permissions": ["tabs", "<all_urls>"], 
    "content_scripts": 
    [ 
    { 
     "matches": ["<all_urls>"], 
     "js" : ["contentscript.js"] 
    } 
    ], 
    "web_accessible_resources": 
    [ 
    "message.xsl" 
    ], 
    "manifest_version": 2 
} 

contentscript.js:

(function() 
{ 
    if(document.xmlVersion != null) 
    { 
    var e = document.createProcessingInstruction(
       "xml-stylesheet", 
       "type='text/xsl' href='" + chrome.extension.getURL("message.xsl") + "'"); 
    document.insertBefore(e, document.firstChild); 
    } 
})(); 

鉻輸出下列錯誤入控制檯的問題:

不安全嘗試從URL中加載URL chrome-extension://ladfinoepkgipbeooknnklpakoknohjh/message.xsl URL http://localhost/out.xml。域,協議和端口必須匹配。

如何解決這個問題?我在互聯網上看到了一些與類似錯誤有關的報告,這似乎是Chrome中的一個漏洞。

我也將xsl文件放在了web服務器上,並且更改了樣式錶鏈接到web服務器。仍然是相同的錯誤:

不安全的嘗試從URL加載URL http://localhost/message.xsl URL http://localhost/out.xml。域,協議和端口必須匹配。

顯然域名,協議和端口確實匹配

+0

我想這是一個[chrome的安全特性](http://blog.chromium.org/2008/12/security-in-depth-local-web-pages.html)。 – Sudarshan

+0

我用這段代碼沒有任何問題,也許只有當你更新'window.document'時,它纔會這樣做:var documentString = document.firstChild.innerHTML; var docu = new DOMParser()。parseFromString(''+ documentString +'',application/xml「); var e = docu.createProcessingInstruction(」xml-stylesheet「,」type ='text/xsl'href ='「 + chrome.extension.getURL(「message.xsl」)+「'」); docu.insertBefore(e,docu.firstChild);' – jjperezaguinaga

+0

@jjperezaguinaga您已經創建了一個新文檔而不是現有文檔。這與我在下面發佈的解決方法相同 – Stan

回答

1

這是我目前使用一種解決方法:

function loadXMLtext(url) 
{ 
    xhttp = new XMLHttpRequest(); 
    xhttp.open("GET", url, false); 
    xhttp.send(); 
    if(xhttp.responseXML == undefined) throw "XHR failed for " + url; 
    return xhttp.responseXML; 
} 

function transformxml() 
{ 
    var xml = loadXMLtext(document.location.href); 
    var xsl = loadXMLtext(chrome.extension.getURL("message.xsl")); 

    var xsltPrs = new XSLTProcessor(); 
    xsltPrs.importStylesheet(xsl); 

    var result = xsltPrs.transformToFragment(xml, document); 

    var xmlsrv = new XMLSerializer(); 
    var plaintext = xmlsrv.serializeToString(result); 
    document.documentElement.innerHTML = plaintext; 
} 

transformxml(); 
0

您正在要求網頁處理其域外的資源。您可以嘗試通過本地主機「欺騙」瀏覽器,但這與要求facebook執行谷歌腳本相同。這是一個Same Origin policy錯誤和解決它只是將處理從內容腳本移動到背景/事件頁面。處理後您將需要pass結果,但這是正確的方法。

爲什麼大多數處理應該在後臺/活動頁面中完成的另一個原因是爲了優化您的擴展,否則您只是使用當前的window引擎,並且如果它阻塞,那麼它會爲用戶選擇標籤。

+0

感謝你的回答,一些想法1)manifest中的擴展權限必須覆蓋外部站點的策略 - 否則,整個概念(如''等將無效,根本不存在)2)我提到,即使XSL託管在同一個域中,錯誤仍然存​​在,而且我可以' t同意將處理轉換爲bac kground頁面 - 這帶來了太多無用的開銷,並且再次取消了內容腳本的存在,這對於「在頁面中」處理是非常有用的工具,並且在適當時應該使用它。 – Stan

+0

你說得對,只是通過內容腳本中的ajax加載了knockoutjs(我甚至沒有向我的清單中的'http:// knockoutjs.com /'請求權限)。您的擴展程序不是權限和CSP,而不是網頁的?同一個域名是localhost,所以我不確定,嘗試使用你的'/ etc/hosts'並將127.0.0.1更改爲你想測試的域名。在新的[events pages](http://developer.chrome.com/dev/extensions/event_pages.html)中,儘管API仍在開發中,但它並不是一個開銷。 – jjperezaguinaga

+0

將localhost和本地IP從「hosts」更改爲僞造域不會有幫助。 – Stan

-1

爲此,您可以在本地使用Chrome的命令行標誌。

的具體標誌是--allow-file-access-from-files

On OS X: from Terminal.app run /Applications/Google\ Chrome.app/contents/MacOS/Google\ Chrome --allow-file-access-from-files 

On Windows: from the command prompt run C:\Users\USERNAME\AppData\Local\Google\Chrome\Application\chrome.exe --allow-file-access-from-files (replacing USERNAME with your username) 

注意:您可能要退出Chrome,如果它當前正在運行,否則會。確保這一點。

+0

不正確;這與這個問題無關。 – Xan

相關問題