允许第三方更改我网站iframe的样式

8

假设我正在托管 site2.com,并且有一个名为 site2.com/frame.html 的文件,它非常简单,如下所示:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>Site2.com frame</title>
  <style>
    body { background-color: yellowgreen; }
  </style>
</head>
<body id="site2-frame-body">
  <h1>This is site2.com frame for 3rd party use</h1>
  <p>Lorem ipsum dolor sit amet consectetur adipisicing elit.</p>
</body>
</html>

现在假设有一个名为site1.com的第三方网站希望通过iframe元素嵌入此内容,代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>Site1</title>
</head>
<body>
  <style>
    #site2frame { border: 2px solid red; }
    #site2frame-body { background-color: blue !important; }
  </style>

  <iframe id="site2frame"
    title="Inline Frame Example"
    width="300"
    height="200"
    src="https://site2.com:3002/frame.html">
  </iframe>
</body>
</html>

当我在Chrome浏览器中打开site1.com时,我会得到这个结果(即site1.com在此处充当第三方站点的角色,而site2.com是托管要嵌入其他网站iframe内的内容的站点):

enter image description here

所以,框架内部的 body 元素的背景颜色设置为 site2.com/frame.html 中的样式为 yellowgreen。当我试图用父网站 site1.com:3002 中指定的 blue 颜色覆盖它时,这不起作用。我甚至使用了带有 !important 属性的 id 选择器,但是这并没有传播到框架内容中。请注意,我能够为 iframe 元素本身(带红色边框)设置样式,但这不是我的问题所在。
那么我该如何启用它呢?是否有某种标准方式,例如启用一些 http 策略或设置一些服务器头 site2.com,告诉浏览器“请允许来自此来源的嵌入式框架上的 CSS 样式?”请注意,框架内容是跨域的。
注:我通过使用 hosts 文件将 site1.comsite2.com 都指向 127.0.0.1 来设置此开发环境,并且我正在运行两个 node express 实例来模拟不同的服务器。

1
尝试使用以下方法覆盖iframe中内容的body样式:https://dev59.com/Vmw15IYBdhLWcg3wntKh - Amir Saleem
1
这可能会有所帮助,基本原理是使用JS更改iframe css:https://www.sitepoint.com/community/t/find-and-change-css-on-elements-within-iframe-with-jquery/37125/3 - TerminalFlow
3个回答

8

由于 '同源策略' 的保护,您无法为第三方 iframe 添加样式。

不过,您可以尝试将样式表的 URL 作为 GET 参数发送,并让 site2.com/frame.html 读取该参数并将其动态添加到其 <head> 中。

例如,site1.com 可以这样创建 iframe:

<iframe id="site2frame"
  title="Inline Frame Example"
  width="300"
  height="200"
  src="https://site2.com:3002/frame.html?css=externalstylesheet.css">
</iframe>

同时,site2.com/frame.html 可以读取 GET 参数,创建一个 link 元素,并将其 href 属性设置为参数的值,然后将其添加到 document.head 中:

var css = new URLSearchParams(location.search).get('css');
var stylesheet = document.createElement("link");
stylesheet.rel = "stylesheet";
stylesheet.href= css;
document.head.append(stylesheet);

Edit pedantic-euclid-m120j


2
这是正确的方法。但是为了尽管如此保护site2.com的安全性,您还应该考虑使用强大的内容安全策略(可以采用HTTP标头或<meta>标签的形式):https://developer.mozilla.org/zh-CN/docs/Web/HTTP/CSP - Sheraff

0

这个脚本会按照你的要求执行

window.onload = function () {
    let myiFrame = document.getElementById("site2frame");
    let doc = myiFrame.contentDocument;
    doc.body.innerHTML =
      doc.body.innerHTML +
      "<style>body { background-color: blue;  !important} /* YOUR CSS*/</style>";
  };

这个例子来自于这篇文章:https://redstapler.co/how-to-apply-css-to-iframe/


0

你不能在其他网站上重写iframe的样式!


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接