จัดการกิจกรรมด้วยสคริปต์เบื้องหลัง

ส่วนขยายคือโปรแกรมที่อิงตามเหตุการณ์ซึ่งใช้ในการแก้ไขหรือปรับปรุงประสบการณ์การท่องเว็บของ Chrome กิจกรรม เป็นทริกเกอร์ของเบราว์เซอร์ เช่น การไปยังหน้าใหม่ การนำบุ๊กมาร์กออก หรือการปิดแท็บ ส่วนขยายจะตรวจสอบเหตุการณ์เหล่านี้ในสคริปต์พื้นหลัง แล้วโต้ตอบกับคำสั่งที่ระบุ

หน้าเว็บพื้นหลังจะโหลดเมื่อจําเป็น และยกเลิกการโหลดเมื่อไม่มีการใช้งาน ตัวอย่างบางส่วนของ เหตุการณ์ต่างๆ ได้แก่

  • ส่วนขยายจะได้รับการติดตั้งหรืออัปเดตเป็นเวอร์ชันใหม่ก่อน
  • หน้าพื้นหลังกําลังรอข้อมูลกิจกรรมอยู่ แล้วมีการส่งกิจกรรมนั้นไป
  • สคริปต์เนื้อหาหรือส่วนขยายอื่นๆ ส่งข้อความ
  • มุมมองอื่นในส่วนขยาย เช่น ป๊อปอัป การโทร runtime.getBackgroundPage

เมื่อโหลดแล้ว หน้าพื้นหลังจะยังคงทำงานอยู่ตราบใดที่ยังมีการทำงานอยู่ เช่น การเรียก Chrome API หรือการออกคำขอเครือข่าย นอกจากนี้ หน้าพื้นหลังจะ ไม่ยกเลิกการโหลดจนกว่ามุมมองที่มองเห็นได้และพอร์ตข้อความทั้งหมดจะปิดไป โปรดทราบว่าการเปิดมุมมอง ไม่ทำให้หน้ากิจกรรมโหลดขึ้น แต่ป้องกันไม่ให้ปิดหน้ากิจกรรมเมื่อโหลดแล้วเท่านั้น

สคริปต์พื้นหลังที่มีประสิทธิภาพจะไม่มีความเคลื่อนไหวจนกว่าจะถึงเหตุการณ์ไฟป่า แล้วแสดงความรู้สึกด้วย คำแนะนำที่ระบุ จากนั้นยกเลิกการโหลด

ลงทะเบียนสคริปต์พื้นหลัง

สคริปต์พื้นหลังจะมีการลงทะเบียนในไฟล์ Manifest ใต้ช่อง "background" นั่นคือ แสดงในอาร์เรย์หลังคีย์ "scripts" และควรระบุ "persistent" เป็น "เท็จ"

{
  "name": "Awesome Test Extension",
  ...
  "background": {
    "scripts": ["background.js"],
    "persistent": false
  },
  ...
}

สามารถลงทะเบียนสคริปต์พื้นหลังได้หลายรายการสำหรับโค้ดแบบแยกส่วน

{
    "name": "Awesome Test Extension",
    ...
    "background": {
      "scripts": [
        "backgroundContextMenus.js",
        "backgroundOmniBox.js",
        "backgroundOauth.js"
      ],
      "persistent": false
    },
    ...
  }

หากส่วนขยายใช้หน้าเว็บพื้นหลังแบบถาวรอยู่ โปรดดูการย้ายข้อมูลในเบื้องหลัง คำแนะนำสำหรับวิธีการเปลี่ยนไปใช้โมเดลที่ไม่ถาวร

เริ่มต้นส่วนขยาย

ฟังเหตุการณ์ runtime.onInstalled เพื่อเริ่มต้นส่วนขยายเมื่อมีการติดตั้ง ใช้ร่างคำตอบนี้ เหตุการณ์เพื่อตั้งค่าสถานะหรือสำหรับการเริ่มต้นครั้งเดียว เช่น เมนูตามบริบท

chrome.runtime.onInstalled.addListener(function() {
  chrome.contextMenus.create({
    "id": "sampleContextMenu",
    "title": "Sample Context Menu",
    "contexts": ["selection"]
  });
});

ตั้งค่า Listener

จัดโครงสร้างสคริปต์พื้นหลังตามเหตุการณ์ที่ส่วนขยายอ้างอิง การกำหนดฟังก์ชันที่เกี่ยวข้อง เหตุการณ์ต่างๆ ทำให้สคริปต์พื้นหลังไม่มีความเคลื่อนไหว จนกว่าเหตุการณ์เหล่านั้นจะเริ่มทำงาน และป้องกันเหตุการณ์ ขาดทริกเกอร์ที่สำคัญ

ผู้ฟังจะต้องได้รับการลงทะเบียนแบบพร้อมกันตั้งแต่จุดเริ่มต้นของหน้าเว็บ

chrome.runtime.onInstalled.addListener(function() {
  chrome.contextMenus.create({
    "id": "sampleContextMenu",
    "title": "Sample Context Menu",
    "contexts": ["selection"]
  });
});

// This will run when a bookmark is created.
chrome.bookmarks.onCreated.addListener(function() {
  // do something
});

อย่าลงทะเบียน Listener แบบไม่พร้อมกันเนื่องจากจะทำให้ทริกเกอร์ไม่ถูกต้อง

chrome.runtime.onInstalled.addListener(function() {
  // ERROR! Events must be registered synchronously from the start of
  // the page.
  chrome.bookmarks.onCreated.addListener(function() {
    // do something
  });
});

ส่วนขยายจะนำผู้ฟังออกจากสคริปต์เบื้องหลังได้โดยโทรหา removeListener หากทั้งหมด Listener เหตุการณ์ถูกนำออกแล้ว Chrome จะไม่โหลดสคริปต์พื้นหลังของส่วนขยายสำหรับ เหตุการณ์นั้น

chrome.runtime.onMessage.addListener(function(message, sender, reply) {
    chrome.runtime.onMessage.removeListener(event);
});

กรองเหตุการณ์

ใช้ API ที่รองรับตัวกรองเหตุการณ์เพื่อจำกัด Listener เฉพาะกรณีที่ส่วนขยายให้ความสำคัญ ประมาณ หากส่วนขยายกําลังรอฟังเหตุการณ์ tabs.onUpdated ให้ลองใช้ เหตุการณ์ webNavigation.onCompleted ที่มีตัวกรองแทน เนื่องจาก API ของแท็บไม่รองรับ ตัวกรอง

chrome.webNavigation.onCompleted.addListener(function() {
    alert("This is my favorite website!");
}, {url: [{urlMatches : 'https://www.google.com/'}]});

โต้ตอบกับผู้ฟัง

มี Listener ที่จะทริกเกอร์ฟังก์ชันการทำงานเมื่อเหตุการณ์เริ่มทำงานแล้ว เพื่อตอบสนองต่อเหตุการณ์ โครงสร้าง รีแอ็กชันที่ต้องการภายในเหตุการณ์ Listener นั้นๆ

chrome.runtime.onMessage.addListener(function(message, callback) {
  if (message.data == "setAlarm") {
    chrome.alarms.create({delayInMinutes: 5})
  } else if (message.data == "runLogic") {
    chrome.tabs.executeScript({file: 'logic.js'});
  } else if (message.data == "changeColor") {
    chrome.tabs.executeScript(
        {code: 'document.body.style.backgroundColor="orange"'});
  };
});

ยกเลิกการโหลดสคริปต์พื้นหลัง

ควรเก็บข้อมูลไว้เป็นระยะๆ เพื่อที่ข้อมูลสำคัญจะไม่สูญหายไปในกรณีที่ส่วนขยาย ขัดข้องที่ไม่ได้รับ onSuspend ให้ใช้ API ของ storage เพื่อช่วยในเรื่องนี้

chrome.storage.local.set({variable: variableInformation});

หากส่วนขยายใช้การส่งข้อความ โปรดตรวจสอบว่าพอร์ตทั้งหมดปิดอยู่ สคริปต์ที่ทำงานอยู่เบื้องหลังจะ ไม่ยกเลิกการโหลดจนกว่าพอร์ตข้อความทั้งหมดจะปิดลง กำลังฟังเหตุการณ์ runtime.Port.onDisconnect ให้ข้อมูลเชิงลึกเมื่อพอร์ตที่เปิดอยู่ปิดลง ปิดด้วยตนเองโดยใช้ runtime.Port.disconnect

chrome.runtime.onMessage.addListener(function(message, callback) {
  if (message == 'hello') {
    sendResponse({greeting: 'welcome!'})
  } else if (message == 'goodbye') {
    chrome.runtime.Port.disconnect();
  }
});

อายุการใช้งานของสคริปต์ที่ทำงานอยู่เบื้องหลังจะสังเกตได้โดยการตรวจสอบเมื่อมีรายการสำหรับส่วนขยาย ปรากฏขึ้นและหายไปจากตัวจัดการงานของ Chrome

ALT_TEXT_HERE

เปิดตัวจัดการงานโดยคลิกเมนู Chrome จากนั้นวางเมาส์เหนือเครื่องมือเพิ่มเติม แล้วเลือก "งาน Manager"

สคริปต์พื้นหลังจะยกเลิกการโหลดเองหลังจากไม่มีการใช้งาน 2-3 วินาที หากมีการล้างข้อมูลในนาทีสุดท้าย ต้องระบุเหตุการณ์ runtime.onSuspend

chrome.runtime.onSuspend.addListener(function() {
  console.log("Unloading.");
  chrome.browserAction.setBadgeText({text: ""});
});

อย่างไรก็ตาม คุณควรใช้ข้อมูลถาวรแทนการใช้ runtime.onSuspend ไม่ได้ผล ทำให้สามารถทำความสะอาดได้เท่าที่จำเป็น และจะไม่ช่วยแก้ปัญหาในกรณีที่เกิดเหตุขัดข้อง