Làm cách nào để sử dụng jQuery trong phần mở rộng chrome?


128

Tôi đang viết một phần mở rộng chrome. Và tôi muốn sử dụng jQuerytrong phần mở rộng của tôi. Tôi không sử dụng bất kỳ trang nền nào , chỉ là một kịch bản nền .

Đây là tập tin của tôi:

manifest.json

{
    "manifest_version": 2,

    "name": "Extension name",
    "description": "This extension does something,",
    "version": "0.1",

    "permissions": [
        "activeTab"
    ],

    "browser_action": {
        "default_icon": "images/icon_128.png"
    },

    "background": {
        "scripts": ["background.js"],
        "persistent": false
    },

    "icons": {
        "16": "images/icon_16.png",
        "48": "images/icon_48.png",
        "128": "images/icon_128.png"
    }
}

background.jsTệp của tôi chỉ chạy một tệp khác có tênwork.js

// Respond to the click on extension Icon
chrome.browserAction.onClicked.addListener(function (tab) {
    chrome.tabs.executeScript({
        file: 'work.js'
    });
});

Logic chính của phần mở rộng của tôi là bên trong work.js. Nội dung mà tôi không nghĩ là vấn đề ở đây cho câu hỏi này.

Điều tôi muốn hỏi là làm thế nào tôi có thể sử dụng jQuery trong tiện ích mở rộng của mình. Vì tôi không sử dụng bất kỳ trang nền nào. Tôi không thể thêm jQuery vào nó. Vậy làm thế nào tôi có thể thêm và sử dụng jQuery vào tiện ích mở rộng của mình?

Tôi đã thử chạy jQuery cùng với tệp work.js của mình từ background.jstệp.

// Respond to the click on extension Icon
chrome.browserAction.onClicked.addListener(function (tab) {
    chrome.tabs.executeScript({
        file: 'thirdParty/jquery-2.0.3.js'
    });
    chrome.tabs.executeScript({
        file: 'work.js'
    });
});

Và nó hoạt động tốt, nhưng tôi lo ngại liệu các tập lệnh được thêm vào sẽ được thực thi theo cách này có được thực thi không đồng bộ hay không. Nếu có thì có thể xảy ra rằng work.js chạy ngay cả trước đó jQuery (hoặc các thư viện khác mà tôi có thể thêm vào trong tương lai).

Và tôi cũng muốn biết cách chính xác và tốt nhất để sử dụng thư viện của bên thứ ba, trong tiện ích mở rộng chrome của tôi.


2
Cách chính xác là đi vani!
bjb568

Nếu bạn đang ở đây để tìm cách thêm jQuery vào tiện ích mở rộng (như tôi), hãy xem câu hỏi này: stackoverflow.com/questions/12035242/ Lỗi
Pro Q

Câu trả lời:


124

Bạn phải thêm tập lệnh jquery của bạn vào dự án tiện ích mở rộng chrome và vào backgroundphần của manifest.json như thế này:

  "background":
    {
        "scripts": ["thirdParty/jquery-2.0.3.js", "background.js"]
    }

Nếu bạn cần jquery trong content_scripts, bạn cũng phải thêm nó trong tệp kê khai:

"content_scripts": 
    [
        {
            "matches":["http://website*"],
            "js":["thirdParty/jquery.1.10.2.min.js", "script.js"],
            "css": ["css/style.css"],
            "run_at": "document_end"
        }
    ]

Đây là những gì tôi đã làm.

Ngoài ra, nếu tôi nhớ chính xác, các tập lệnh nền được thực thi trong cửa sổ nền mà bạn có thể mở qua chrome://extensions.


7
Vâng, ý bạn chính xác là You have to add your jquery script to your chrome-extension projectgì? Tôi đã làm điều này: manifest.json: "background": { `" scripts ": [" thirdParty / jquery-2.0.3.js "," background.js "],` `" kiên trì ": false``}, `và tôi đã tải xuống jQuery đến thư mục thirdParty. Tuy nhiên tôi vẫn không thể sử dụng jQuery. Nó báo lỗi: Uncaught ReferenceError: $ is not defined tôi đã thêm nó vào work.jstập tin của mình để kiểm tra. $("body").html("Foo!");
Ishan

Nhận xét trên trông giống như một mớ hỗn độn nhưng trong khi thêm phần xem trước bình luận không được hiển thị. Xin hãy tha thứ cho tôi vì điều đó.
Ishan

Tôi có nghĩa là thêm nó vào thư mục chrome-extension của bạn. Giống như /home/you/chromxetension_source_files/thirdParty/jquery-2.0.3.js. Bạn nên làm điều tương tự với work.js của bạn.
Nico

1
Tôi đã cố gắng làm những gì bạn nói. Nhưng tôi vẫn nhận được cùng một lỗi là không thể truy cập jquery từ work.jstệp của tôi . Uncaught ReferenceError: $ is not defined. Nếu bạn có thể, bạn có thể vui lòng tải lên một ví dụ làm việc ở đâu đó. Chỉ là một ví dụ đơn giản như làm '$ ("cơ thể"). Html ("Foo!");' trong work.js.
Ishan

7
Tôi cũng gặp khó khăn để được jQueryhoặc $được công nhận. Hóa ra tôi đã tham khảo jQuery lần cuối trong mảng tệp kê khai. Khi tôi đặt nó đầu tiên, nó đã được công nhận.
BenR

18

Nó rất dễ dàng chỉ cần làm như sau:

thêm dòng sau vào manifest.json của bạn

"content_security_policy": "script-src 'self' https://ajax.googleapis.com; object-src 'self'",

Bây giờ bạn có thể tải jQuery trực tiếp từ url

  <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.2/jquery.min.js"></script>

Nguồn: tài liệu google


1
Điều gì nếu bạn có nhiều tập lệnh để tải?
một

1
Câu trả lời tuyệt vời nếu bạn muốn tải tập lệnh của mình từ một máy chủ từ xa (điều này đòi hỏi bạn phải tin tưởng máy chủ từ xa với tiện ích mở rộng của mình và mọi thứ mà nó có quyền truy cập).
Nathaniel Verhaaren

1
@NathanielVerhaaren Đây là một điểm hợp lý để nâng cao, nhưng nó có thể được giảm thiểu bằng cách xác minh nguồn bằng cách sử dụng subresource integrity(SRI).
Dan Atkinson

13

Và nó hoạt động tốt, nhưng tôi lo ngại liệu các tập lệnh được thêm vào sẽ được thực thi theo cách này có được thực thi không đồng bộ hay không. Nếu có thì có thể xảy ra rằng work.js chạy ngay cả trước jQuery (hoặc các thư viện khác mà tôi có thể thêm vào trong tương lai).

Điều đó thực sự không phải là một mối quan tâm: bạn xếp hàng các tập lệnh sẽ được thực thi trong một bối cảnh JS nhất định và bối cảnh đó không thể có một điều kiện cuộc đua như là một luồng đơn.

Tuy nhiên, cách thích hợp để loại bỏ mối quan tâm này là xâu chuỗi các cuộc gọi:

chrome.browserAction.onClicked.addListener(function (tab) {
    chrome.tabs.executeScript({
        file: 'thirdParty/jquery-2.0.3.js'
    }, function() {
        // Guaranteed to execute only after the previous script returns
        chrome.tabs.executeScript({
            file: 'work.js'
        });
    });
});

Hoặc, khái quát:

function injectScripts(scripts, callback) {
  if(scripts.length) {
    var script = scripts.shift();
    chrome.tabs.executeScript({file: script}, function() {
      if(chrome.runtime.lastError && typeof callback === "function") {
        callback(false); // Injection failed
      }
      injectScripts(scripts, callback);
    });
  } else {
    if(typeof callback === "function") {
      callback(true);
    }
  }
}

injectScripts(["thirdParty/jquery-2.0.3.js", "work.js"], doSomethingElse);

Hoặc, được quảng cáo (và mang lại nhiều chữ ký phù hợp hơn):

function injectScript(tabId, injectDetails) {
  return new Promise((resolve, reject) => {
    chrome.tabs.executeScript(tabId, injectDetails, (data) => {
      if (chrome.runtime.lastError) {
        reject(chrome.runtime.lastError.message);
      } else {
        resolve(data);
      }
    });
  });
}

injectScript(null, {file: "thirdParty/jquery-2.0.3.js"}).then(
  () => injectScript(null, {file: "work.js"})
).then(
  () => doSomethingElse
).catch(
  (error) => console.error(error)
);

Hoặc, tại sao quái không, async/ await-ed cho cú pháp thậm chí rõ ràng hơn:

function injectScript(tabId, injectDetails) {
  return new Promise((resolve, reject) => {
    chrome.tabs.executeScript(tabId, injectDetails, (data) => {
      if (chrome.runtime.lastError) {
        reject(chrome.runtime.lastError.message);
      } else {
        resolve(data);
      }
    });
  });
}

try {
  await injectScript(null, {file: "thirdParty/jquery-2.0.3.js"});
  await injectScript(null, {file: "work.js"});
  doSomethingElse();
} catch (err) {
  console.error(err);
}

Lưu ý, trong Firefox bạn chỉ có thể sử dụng browser.tabs.executeScriptvì nó sẽ trả về một Promise.


Phương pháp đầu tiên là tuyệt vời. Là một người không biết nhiều về JavaScript, tôi chưa bao giờ xem xét một thứ như thế.
FriskySaga

11

Ngoài các giải pháp đã được đề cập, bạn cũng có thể tải xuống jquery.min.js cục bộ và sau đó sử dụng nó -

Để tải xuống -

wget "https://ajax.googleapis.com/ajax/libs/jquery/3.1.0/jquery.min.js"

manifest.json -

"content_scripts": [
   {
    "js": ["/path/to/jquery.min.js", ...]
   }
],

trong html -

<script src="/path/to/jquery.min.js"></script>

Tham khảo - https://developer.chrome.com/extensions/contentSecurityPolicy


3
Đây là cách tốt nhất ... Bạn không cần phần html.
c-an

1

Trong trường hợp của tôi, có một giải pháp hoạt động thông qua Nhắn tin tài liệu chéo (XDM) và Thực hiện tiện ích mở rộng Chrome thay vì tải trang.

manifest.json

{
  "name": "JQuery Light",
  "version": "1",
  "manifest_version": 2,

  "browser_action": {
    "default_icon": "icon.png"
  },

  "content_scripts": [
    {
      "matches": [
        "https://*.google.com/*"
      ],
      "js": [
        "jquery-3.3.1.min.js",
        "myscript.js"
      ]
    }
  ],

  "background": {
    "scripts": [
      "background.js"
    ]
  }

}

nền.js

chrome.browserAction.onClicked.addListener(function (tab) {
  chrome.tabs.query({active: true, currentWindow: true}, function (tabs) {
    var activeTab = tabs[0];
    chrome.tabs.sendMessage(activeTab.id, {"message": "clicked_browser_action"});
  });
});

myscript.js

chrome.runtime.onMessage.addListener(
    function (request, sender, sendResponse) {
        if (request.message === "clicked_browser_action") {
        console.log('Hello world!')
        }
    }
);
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.