在网页上的所有 iframe 中注入 iframe 的内容脚本

Posted

技术标签:

【中文标题】在网页上的所有 iframe 中注入 iframe 的内容脚本【英文标题】:Content script injecting iframe inside all iframes on web page 【发布时间】:2021-07-18 03:27:41 【问题描述】:

我正在尝试创建一个 iframe 并在加载网页时将其注入网页,但是当我尝试这样做时,内容脚本正在网页上的所有 iframe 中注入 iframe,我使用了 @ 987654321@ 用于在用户单击扩展图标时切换 iframe,因此我从后台脚本发送消息来处理此问题,但是我仅从后台脚本发送消息一次,但 chrome.runtime.onMessage.addListener 被解雇多次我不知道为什么

这就是正在发生的事情

这是内容脚本

var iframeContainer = undefined;
window.onload = function () 
  injectPopup();

  chrome.runtime.onMessage.addListener((request, sender, sendResponse) => 
    if (request.message == "togglePopup") 
      console.log("message arrived");
      var appBody = document.getElementById("app-container");
      if (appBody.style.display == "none") 
        console.log("posting message");
        iframeContainer.contentWindow.postMessage(
          JSON.stringify(
            user: request.user,
            token: request.token,
          ),
          "*",
          []
        );
        appBody.style.display = "block";
       else 
        appBody.style.display = "none";
      
    
  );
;

// window.addEventListener("message", function (e) 
//   if (JSON.parse(e.data)) 
//     const data = JSON.parse(e.data);

//     if (data.message) 
//       if (data.message == "toggleApp") 
//         var appBody = document.getElementById("app-container");
//         appBody.style.display = "none";
//       
//     
//   
// );

function injectPopup() 
  console.log("inject popup");
  iframeContainer = document.createElement("iframe");
  console.log(iframeContainer);
  iframeContainer.allowFullscreen = false;
  iframeContainer.src = chrome.runtime.getURL("/index.html");
  iframeContainer.id = "app-container-iframe";
  const appContainer = document.createElement("div");
  appContainer.id = "app-container";
  appContainer.style.display = "none";
  console.log(appContainer);
  const resizeHandle = document.createElement("div");
  resizeHandle.id = "resize-container-handle";
  resizeHandle.classList.add("ui-resizable-handle");
  resizeHandle.classList.add("ui-resizable-w");

  resizeHandle.innerHTML =
    '<div class="resize-handle-horizontal-bar"></div><div class="resize-handle-horizontal-bar"></div><div class="resize-handle-horizontal-bar"></div>';

  appContainer.appendChild(resizeHandle);
  document.querySelector("body").appendChild(appContainer);
  appContainer.appendChild(iframeContainer);
  $("#app-container").resizable(
    handles:  w: "#resize-container-handle" ,
  );


这是我发送消息的后台脚本

var userLoggedIn = ;
const openTabs = [];
const apiUrl = "http://localhost:5000";
var popupOpen = false;
var currentWindow = undefined;

window.onload = () => 
  popupOpen = false;
;

chrome.storage.local.get("token", function (result) 
  userLoggedIn = result.token;

  chrome.browserAction.onClicked.addListener(function (tab) 
    const width = 500;
    const height = 900;
    const left = screen.width / 2 - width / 2;
    const top = screen.height / 2 - height / 2;
    console.log("clicked!");
    if (!userLoggedIn) 
      if (currentWindow == undefined) 
        chrome.windows.create(
          
            url: "/html/auth.html",
            width: width,
            height: height,
            left: left,
            top: top,
            focused: true,
          ,
          (window) => 
            currentWindow = window;
            chrome.windows.onRemoved.addListener(function (id) 
              if (currentWindow.id == id) 
                currentWindow = undefined;
              
            );
          
        );
      
     else 
      console.log("hi!");
      chrome.windows.getCurrent((w) => 
        chrome.tabs.query(
          
            active: true,
            currentWindow: true,
          ,
          function (tabs) 
            const userData = parseJwt(userLoggedIn);
            console.log("sending message");
            chrome.tabs.sendMessage(tabs[0].id, 
              message: "togglePopup",
              user: userData,
              token: userLoggedIn,
            );
          
        );
      );
    
  );

  chrome.runtime.onMessage.addListener((request, sender, sendResponse) => 
    if (request.message === "login") 
      loginUser(request.payload)
        .then(function (res) 
          if (res.ok) 
            return res.json();
           else 
            sendResponse(
              message: "error",
            );
          
        )
        .then(function (data) 
          chrome.storage.local.set( token: data.token , function (result) 
            chrome.windows.remove(currentWindow.id);
            const userData = parseJwt(data.token);
            userLoggedIn = data.token;
            chrome.tabs.query(
              
                active: true,
                currentWindow: true,
              ,
              function (tabs) 
                chrome.tabs.sendMessage(tabs[0].id, 
                  message: "togglePopup",
                  payload: 
                    user: userData,
                    token: userLoggedIn,
                  ,
                );
              
            );

            sendResponse( message: "success" );
          );
        )
        .catch(function (err) 
          console.log(err);
        );
      return true;
     else if (request.message === "register") 
      registerUser(request.payload)
        .then(function (res) 
          if (res.ok) 
            return res.json();
           else 
            sendResponse(
              message: "error",
            );
          
        )
        .then(function (data) 
          console.log(data);
          sendResponse( message: "success" );
        )
        .catch(function (err) 
          console.log(err);
        );
     else if (request.message === "logout") 
     else if (request.message === "userStatus") 
     else if (request.message === "closePopup") 
      const index = getIndexOfTab(sender.tab.id, openTabs);
      openTabs[index].popupOpen = false;
    
  );
);

【问题讨论】:

【参考方案1】:

chrome.tabs.sendMessage 根据documentation 将消息发送到选项卡的所有框架。

您可以通过frameId将其限制在主页:

chrome.tabs.sendMessage(tabId, foo: 'bar', frameId: 0);

【讨论】:

我已经尝试解决这个问题几个星期了,非常感谢!,它成功了!,

以上是关于在网页上的所有 iframe 中注入 iframe 的内容脚本的主要内容,如果未能解决你的问题,请参考以下文章

无法访问 iframe 中加载的自己域上的 httponly 标记 cookie

在 iframe 的文档和/或 shadow-root 中注入 html dom

iframe中字体大小的问题

iframe中嵌套的网页样式修改

iframe jQuery 不会在 Internet Explorer 中执行 [所有版本]

使用 HTML5 替代 iFrame