1. 程式人生 > >Chrome外掛(Extensions)開發攻略

Chrome外掛(Extensions)開發攻略

本文將從個人經驗出發,講述為什麼需要Chrome外掛,如何開發,如何除錯,到哪裡找資料,會遇到怎樣的問題以及如何解決等,同時給出一個個人認為的比較典型的例子——獲取網頁內容,和伺服器互動,再把資訊反饋給使用者。OK,準備開始吧,我儘量把文章寫得好看點,以免讀者打瞌睡。

目錄

為什麼需要

簡單地說,瀏覽器外掛,可以大大的擴充套件你的瀏覽器的功能。包括但不僅限於這些功能:捕捉特定網頁的內容,捕捉HTTP報文,捕捉使用者瀏覽動作,改變瀏覽器位址列/起始頁/書籤/Tab等介面元素的行為,與別的站點通訊,修改網頁內容……給你增加許多想象空間,試想想看,你可以用它來識別一些網站上的廣告程式碼,並直接把這些程式碼刪掉,這樣你就不會受到廣告的困擾了,沒錯,如你所願,這樣的外掛別人已經開發好了,你可以直接用。不過,也要說瀏覽器外掛的弊端,那就是:會帶來一些安全隱患,也可能讓你的瀏覽器變得緩慢甚至不穩定。

為什麼是Chrome

因為Chrome的外掛開發起來最簡單,總體上看沒什麼新的技術,開發語言就是javascript,web前端工程師能很快上手;而Firefox的外掛開發則複雜許多,涉及到環境的搭建和一些WEB以外的技術;IE的外掛開發就更復雜了,需要熟悉C++和COM技術,當然還要裝微軟的Visual Studio。

應該說Chrome和Opera的外掛的開發都不難,但Firefox的則比較棘手,也許你要問,那為什麼Firefox的外掛是最豐富的?我想這有些歷史原因,Chrome出來畢竟比較晚,另外幾種瀏覽器提供的外掛的功能也是不盡相同的,OK,我們還是言歸正傳吧。

需要準備什麼

幾乎是零需求。Chrome瀏覽器和一個文字編輯器即可,文字編輯器最好是帶語法高亮的那種。谷歌對我們做技術的人來說真是太大度了。

如何開始

文章不長,照著文章去做,完成後,你就成功開發了第一個Chrome外掛,這個外掛會彈出一個小視窗,上面顯示些阿貓阿狗的小圖片。如圖:

這個外掛一共有4個檔案:

  • manifest.json - 所有外掛都要有這個檔案,這是外掛的配置檔案,可看作外掛的“入口”。
  • icon.png - 小圖示,推薦使用19*19的半透明png圖片,更好的做法是同時提供一張38*38的半透明的png圖片作為大圖示,在我後面提供的例子中,我就是那麼幹的。
  • popup.html - 就是你所看到的那個阿貓阿狗的彈出頁面。
  • popup.js - 阿貓阿狗頁面所引用的javascript檔案。

這裡千萬千萬注意了,我當初沒仔細看popup.html裡有一小段註釋,這一小段註釋說:出於安全考慮,javascript必須與html分開存放。而我想嘛,一個小測試程式,沒必要分開吧,直接寫一起不就行了嗎?結果javascript死活執行不了,我翻來覆去找不到原因,還以為彈出的小視窗不支援javascript,在網上搜索了半天又沒有結果,最後才發現是這個原因,浪費了許多時間,這個事情也一定程度上說明了:細節決定成敗。

manifest.json中的內容也非常顯而易見,我選擇其中幾個屬性講一下:

{
  "manifest_version": 2,

  "name": "One-click Kittens",
  "description": "This extension demonstrates a browser action with kittens.",
  "version": "1.0",

  "permissions": [
    "https://secure.flickr.com/"
  ],
  "browser_action": {
    "default_icon": "icon.png",
    "default_popup": "popup.html"
  }
}

"manifest_version":現在應該總是2。

"permissions":很重要的東西,即允許外掛做哪些事情,訪問哪些站點,假如一個外掛的"permissions"裡寫有“http://*.hacker.com/”,那麼這個外掛就被允許訪hacker.com上的所有內容,包括可能會把你的一些個人資訊提交給hacker.com,危險性不言而喻,檢視一個外掛能訪問那些站點的方法是:在chrome的位址列裡輸入“chrome://extensions/”(注意:這個頁面我們之後要頻繁用到,請收藏一下),然後點對應外掛的旁邊的那個“許可權”,如:

"default_popup":用來指定點選小圖示後彈出的小視窗中預設顯示的是哪個html,這個彈出的小視窗就叫做“popup”。

"browser_action":這是一個瀏覽器級的動作,也就是說,不管你現在在訪問哪個頁面,那個小按鈕總是顯示出來,而我們的外掛如果僅僅是針對某些頁面的話,就不適合用這個"browser_action"了。下面我們來弄一個只有訪問部落格園(www.cnblogs.com)才會出現的小按鈕。

Page Action

這個外掛只有4個檔案,其中兩個還是圖示,那就只剩下一個必須的manifest.json和一個background.js了。

mainifest.json:

{
     "manifest_version": 2,
     "name": "cnblogs.com viewer",
     "version": "0.0.1",
     "background": { "scripts": ["background.js"] },
     "permissions": ["tabs"],
     "page_action": {
          "default_icon": {
               "19": "cnblogs_19.png",
               "38": "cnblogs_38.png"
          },
          "default_title": "cnblogs.com article information"
     }
}

注意:這裡是“page_action”而不是“browser_action”屬性了。

“permissions”屬性裡的“tabs”是必須的,否則下面的js不能獲取到tab裡的url,而這個url是我們判斷是否要把小圖示show出來的依據。background是什麼概念?這是一個很重要的東西,可以把它認為是chrome外掛的主程式,理解這個很關鍵,一旦外掛被啟用(有些外掛對所有頁面都啟用,有些則只對某些頁面啟用),chrome就給外掛開闢了一個獨立的javascript執行環境(又稱作執行上下文),用來跑你指定的background script,在這個例子中,也就是background.js。

background.js

function getDomainFromUrl(url){
     var host = "null";
     if(typeof url == "undefined" || null == url)
          url = window.location.href;
     var regex = /.*\:\/\/([^\/]*).*/;
     var match = url.match(regex);
     if(typeof match != "undefined" && null != match)
          host = match[1];
     return host;
}

function checkForValidUrl(tabId, changeInfo, tab) {
     if(getDomainFromUrl(tab.url).toLowerCase()=="www.cnblogs.com"){
          chrome.pageAction.show(tabId);
     }
};

chrome.tabs.onUpdated.addListener(checkForValidUrl);

程式碼中,我們使用了一個正則表示式去匹配url,獲取出其中的domain部分,如果domain部分是“www.cnblogs.com”的話,就把小圖示show出來,效果如下:

當然了,你現在點那個小圖示的話,是沒有任何反應的,我沒有像官方提供的那個例子那樣提供了popup。OK,現在是時候描述下chrome外掛的結構了。

Chrome外掛結構

需要宣告的是,這個結構圖是我自己畫的,代表我對Chrome外掛的理解,可能並不全面,甚至還不是十分準確,但找來找去找不到現成的,只好自己動手,如有謬誤,請不吝指出。

如圖,manifest.json作為外掛的配置檔案,同時可以看作程式的“入口”,因為它指定了顯示什麼圖示,background script有哪些檔案,content script又有哪些檔案,pop up的頁面是什麼,等等。

什麼是popup,什麼是background script,相信大家都清楚了,那什麼是content script呢?content script就是我們要注入到頁面中的指令碼,外掛允許我們往網頁中注入指令碼,這是一個多麼讓人有想象力的功能,其功能之強大無需多解釋,總的來說,就是讓我們全面干預頁面的內容!也許你馬上會想到,這可能帶來很大的安全隱患,沒錯,有些惡意外掛會竊取你的頁面資訊,而有些有漏洞的外掛則可能讓你遭受跨站指令碼注入(XSS)的攻擊;另一個可能你會想到的問題是:往頁面中注入自己的指令碼,難道不會跟頁面原本的指令碼發生衝突嗎?能想到這點說明你真的很厲害,如果我們的注入指令碼和頁面原本的指令碼處於同一個執行環境中,確實會發生衝突,所以,Chrome是另外開闢了一個獨立的執行空間,供我們的Content Script使用的,Content Script能訪問DOM的內容,但卻不能訪問頁面原本的指令碼(我是說直接訪問不行),反之,頁面原本的指令碼也不能直接訪問Content Script。在圖中,淺紅色的背景塊代表Content Script的執行環境,而淺藍色的背景塊代表頁面執行環境,另外外掛的執行環境我用淺綠色表示,注意,這是三個不同的執行環境,除錯的時候你會充分體會到它們的不同。

那麼,Content Script會在什麼時候執行呢?預設情況下,是在網頁載入完了和頁面指令碼執行完了,頁面轉入空閒的情況下(Document Idle),但這個是可以改變的,詳情可參考https://developer.chrome.com/extensions/content_scripts.html,檢視其中的“run_at”。

由於處於不同的執行環境中,Content Script和Background Script不能直接互相訪問,那它們之間如何通訊?通過Message!這個之後的程式碼中會有。

學習資料

理解了Chrome外掛結構之後,我相信你完全有能力開發一款自己的外掛了,當然了,你得自己去google一些資料,這裡我就分享下我的方法。

再則,官方提供的例子,可以看看,https://developer.chrome.com/extensions/samples.html,我發現上面的例子有些已經不能用於新版的Chrome了,但沒關係,你只要找你想要的就行了,也不用一個個嘗試,就根據你的需要,挑選幾個你感興趣的看看即可。

遇到問題,怎麼辦?當然是用google去查詢問題,但這裡我最最最強烈推薦stackoverflow.com,這簡直是解決問題的神器!不多解釋了,用過便知。

學習過程基本上就是:看個大概,寫點程式碼,除錯除錯。就可以了。哦,大前提當然是你得有javascript的基礎。(你:呵呵,你在逗我吧!)

我的例子

好,輪到我的例子登場了。它的功能是這樣的:當你瀏覽部落格園的時候,它會啟動並嘗試獲取你瀏覽的文章的資訊(標題、作者和日期),再通過往另一個伺服器傳送請求的方式,記錄和獲取你第一次訪問這篇文章的時間,把這個時間連帶文章的資訊,顯示在popup上。聽起來挺無聊的功能,但關鍵是為了演示嘛,如圖:

這個外掛一共有9個檔案,新出現的檔案有兩個(其它相信大家都很熟悉了),一個是“content_script.js”,這就是前面提到的Content Script,獲取和修改頁面的內容就靠它了;另一個是“jquery-2.0.0.min.js”,大名鼎鼎的jQuery,我很喜歡用的js庫,其理念是“write less,do more”,能幫我減少很多程式碼,這是目前最新的2.0.0版,這個版本跟以前的1.x.x的最大差別就是不再支援IE6、7和8,我個人是十分贊同這種做法的,微軟的舊版瀏覽器都成了Web技術發展的絆腳石了,而且這次我們用的是Chrome瀏覽器,果斷選擇最新版了。

另外還有一個伺服器端,為了讓問題簡化,這次我用了php程式碼,一個php檔案就是整個處理了,沒有太多繁雜的配置,簡潔,這是php最大的優勢。系統結構如圖:

抓取網頁的內容得依靠content_script.js,然後通過sendMessage/onMessage和background.js交換資料,background.js將url資訊通過ajax(XMLHttpRequest)傳送給localhost,獲取此頁面的第一次訪問的時間,最後,使用者點小圖示,popup.html出現,popup.html會讀取(程式碼在popup.js中)background.js中的articleData的資料,把它顯示出來。這就是整個過程。

我抓取網頁資料的方式並不能確保所有的部落格園的文章都能被正常獲取,這跟使用者使用的部落格模板有關係,但我嘗試下來大多數文章還是可以抓取的,我不去適應所有的模板了,畢竟這只是個演示的demo。

另外還需說明的一點是我使用了jQuery做XMLHttpRequest,post的內容不是傳統的html表單形式,而是json資料,所以在伺服器端這邊,就不能直接用$_REQUEST獲取,而是通過讀取“php://input”的內容獲取。順便談談個人對web api的一個看法:“統一”大於“靈活”,這是我的觀點,我確定我的介面的格式是json,使用utf-8編碼,於是就一直用下去,呼叫者不用考慮用XML還是html表單還是別的,開發者也不必多考慮,讓這成為一種統一的約定,在團隊協助和以後的開發中會很省事。

除錯

程式開發,必定要涉及到除錯,記得我剛開始做WEB開發前,問一些做了好久WEB開發的朋友,你們是怎樣做javascript除錯的,我發覺大多數人竟然回答:用alert一點點試吧——不是不行,是太原始,太低效了,對吧?其實Chrome直接支援javascript的除錯,擁有了Chrome,就相當於擁有了一個強大的javascript偵錯程式了。

Chrome開啟開發者工具的方法是<Ctrl>+<Shift>+<I>(Windows版),大致如下:

我們這次需要關心的有“Elements”、“Sources”和“Console”這三個標籤。Elements是用來做DOM分析的,功能有點類似Firebug,幫助我們分析頁面的內容;而Sources,是我們用來除錯javascript的;Console則是我們的Log的輸出視窗,也是一個除錯利器。

除錯Content Script

如我提供的這個例子,可在Sources的“Copntent Scripts”下看到“content_script.js”然後設斷點,執行到斷點處時,Chrome會挺住,你可以觀察到上面的值,如圖:

太cool了,請問你還要一點點alert嗎?

除錯Background

由於background和content script並不在同一個執行環境中,因此上面的方法是看不到Background的javascript的。要除錯Background,還需要開啟外掛頁,也就是“chrome://extensions”。點對應的外掛的“generated background page.html”,就出現了除錯視窗,接下來的操作就跟前面的類似了。如圖:

至於你看到ID,“aajnhhjiia……”這一長串東西,這是chrome自動安排的一個ID。

除錯Popup

雖然Popup和Background是處於同一執行環境中,但在剛才的Background的除錯視窗中是看不到Popup的程式碼的。除錯Popup還需要這樣:

然後……就跟前面差不多了。

一些問題

也許有時候你會發覺偵錯程式不是很靈,至少我用下來感覺如此,比如你可能發現斷點設不了,或者斷點不起作用,或者看不到你自己的javascript檔案。我的方法是在外掛頁中,把對應的外掛的“已啟用”這個複選框去掉,再重新勾上,然後再點一下“重新載入(Ctrl+R)”,通常能解決問題。當然了,還有些很古怪的問題,還不好重現,總體的解決思路就是重新載入一下,實在不行的話重啟瀏覽器,或者清除瀏覽器快取什麼的,再試試看。

在做外掛除錯的時候我還遇到一個十分鬱悶的問題,那就是我的Chrome使用了“Go Agent”,關於Go Agent是用來幹嘛的,這個嘛,可以去google一下,我相信絕大多數程式設計師都會喜歡上它……可由於使用了這個東西,很可能會導致外掛的XMLHttpRequest工作不正常,而且可能你會思索半天也找不到原因,好吧,暫時把Go Agent停用掉,甚至可能你需要重啟下Chrome——我的經驗。

總結

我還是想說,我覺得Google對我們程式設計師來說是個很大度的公司,在Chrome這個產品上面就可見一斑。利用Chrome外掛技術,我們可以做許多有用的東西,通過本文,相信你已經知道如何去開發一款Chrome外掛了,當然了,Chrome外掛的功能是很強大的,我用到的僅是冰山一小角。要深入,當然還需要更加充分地利用google和stackoverflow.com了。

相關推薦

Chrome外掛Extensions開發

本文將從個人經驗出發,講述為什麼需要Chrome外掛,如何開發,如何除錯,到哪裡找資料,會遇到怎樣的問題以及如何解決等,同時給出一個個人認為的比較典型的例子——獲取網頁內容,和伺服器互動,再把資訊反饋給使用者。OK,準備開始吧,我儘量把文章寫得好看點,以免讀者打瞌睡。 目錄 為什麼需要 簡單地說,瀏

從頭開發一個Flutter外掛開發流程

文章由來 在上一篇分享的文章Flutter 天氣應用裡我介紹了一個用flutter編寫的天氣預報app,裡面有一個需要完善的功能就是根據當前定位所在城市顯示天氣資訊。由於沒有辦法使用gms(google mobile service)的緣故,flutter官方提供的基於Google map的定位packag

搜尋引擎快捷導航:一個簡單的chrome外掛教程

搜尋引擎快捷導航 使用方法 :下載crx副檔名檔案,拖入chrome應用管理介面即可 編寫一個簡單的chrome外掛(教程) 實現效果: 簡單理解:chrome擴充套件程式就是一個web應用

推薦幾款我一直在用的chrome外掛

6. Pocket 可以很方便的儲存文章、視訊等供以後檢視,即實現了“Read it later”功能。有了 Pocket,您可以將所有想下次讀的內容匯聚到一個地方,然後在任何裝置上隨時檢視。Pocket還提供了另外一個功能,即可以通過傳送郵件的方式來儲存內容(不需要點選這個外掛),傳送連結URL到

推薦幾款我一直在用的chrome外掛

我用的chrome外掛挺多的,所謂工欲善其事必先利其器,我熱衷於搜尋好用的工具來讓我平時的工作事半功倍。下面介紹幾款我正在用的感覺還不錯的外掛,如果大家還有其它好用的(肯定有,chrome外掛庫太龐大了),一定要互相分享!! 1. LastPass 用的最爽的一款,強烈推薦。LastPass是一款Free

VSCode外掛開發開發除錯技巧

更多文章請戳VSCode外掛開發全攻略系列目錄導航。 前言 在介紹完一些比較簡單的內容點之後,我覺得有必要先和大家介紹一些開發中遇到的一些細節問題以及技巧,特別是後面一章節將要介紹WebView的知識,這個坑會比較多,避免大家走彎路。 開發方式 最理想的方式是準備雙顯示器,一個寫程式

Windows 系統 Unicode 文件名操作新建、重命名、枚舉、復制

for overflow date col left 文件的 函數 參數 splay 常見的那些文件操作函數都不支持,於是為了達到目的,需要各種方法配合,應該是不如其他語言方便。我只是想看看Perl到底是否適合做這件事,於是折騰了一回。文件的建立: 模塊:Win32

從頭開發一個Flutter外掛高德地圖定位外掛

在上一篇文章從頭開發一個Flutter外掛(一)開發流程裡具體介紹了flutter外掛的具體開發流程,從建立專案到釋出。接下來將會為Flutter天氣專案開發一個基於高德定位sdk的flutter定位外掛。 完整程式碼在git倉庫裡 github.com/KinsomyJS/l… 申請key 首先先進入

中國最適合窮遊玩雪地,沒錢也能玩的開心漠河旅遊省錢

旅遊,就意味著花錢?曾有朋友和我說,我們應該多多旅行,而不是旅遊,多多體驗不同地域不同的文化、不同的生活方式,欣賞不同的風景,品嚐當地特色的美食。也許有許多人認為旅遊就是一件花錢的事情,沒錢哪都去了,玩不了。其實錢的多少隻能影響你旅遊的舒適度,但不能影響你旅遊的

Android Studio 提高開發效率的非常有用的外掛

在使用as開發安卓的過程中,我們都會使用到各種各樣的外掛,自己使用的一些外掛進行記錄一下,為新的android 開放工程師提供一些微薄的幫助。 1. Android Studio Prettify 可以將程式碼中的字串寫在string.xml檔案中

如何為Apache JMeter開發外掛

為什麼選擇使用JMeter 當被問到這個問題的時候,也許你會在腦海裡產生很多的理由,比如: Apache基金會下的開源專案,沒有版權問題; 為數不多的還在持續更新的開源效能自動化測試工具; 支援協議豐富,是商用測試工具最佳替代品; 有專門的外掛專案做支撐,

如何為Apache JMeter開發外掛——監聽器之Vizualizer監視器

如何對Apache Tomcat的效能計數進行監視 上一章節我們對JMeter的監聽器元件進行了一個概況介紹,並通過實現開發一個Report(報告)元件為大家展示了監聽器元件的內部工作邏輯,本篇將為大家簡單介紹一下Vizualizer(監視器)元件的開發流程和

開發IDEA定位到.class檔案的外掛外掛環境搭建的坑@gradle

昨天折騰了好幾個小時,覺得還是把一些細節也一起記錄下來。 1、gradle的環境配置,設定使用本地的gradle 我使用的是本地的gradle,沒有用gradle wrapper 是以前裝的,版本是4.3 IDEA設定為本地版本,勾選use local gradle dis

開發IDEA定位到.class檔案的外掛專案配置及原理詳細記錄

專案配置及原理詳細記錄 專案結構  HelloAction.java import com.intellij.openapi.actionSystem.AnAction; import com.intellij.openapi.actionSystem.AnActio

開發IDEA定位到.class檔案的外掛

開發IDEA定位到.class檔案的外掛   原始需求: 釋出補丁的時候,需要找到.class檔案放到jar包裡。 想開發一個IDEA外掛,直接右鍵.java檔案,定位到對應的.class檔案,可以是複製.class檔案路徑,最好的是,直接右鍵開啟.class所在目錄

USTCOJ程式碼檢視功能的實現我的第一個Chrome外掛,UstcOjSourceView

因工作需要,會不時的在USTCOJ上產看程式原始碼。檢視原始碼的流程通常是這樣的: 1,根據指定題號、賬號,或許相關的RunID。 3,在如下所示的輸入框中輸入RunID號,點選View按鈕檢視程式碼。 (圖片一) 採用這種方式檢視原始碼是相當痛苦的,因為judge.p

教你開發jQuery外掛

要說jQuery 最成功的地方,我認為是它的可擴充套件性吸引了眾多開發者為其開發外掛,從而建立起了一個生態系統。這好比大公司們爭相做平臺一樣,得平臺者得天下。蘋果,微軟,谷歌等巨頭,都有各自的平臺及生態圈。 學會使用jQuery並不難,因為它簡單易學,並且相信你接觸jQuery後肯定也使用或熟悉了不少其

如何為Apache JMeter開發外掛——第一個JMeter外掛

本篇將開啟為JMeter開發外掛之旅,我們選擇以Function(函式)元件作為外掛開發的入手物件,在前面的章節我們將其劃分為非GUI元件,選擇它的理由不僅僅是因為Function外掛在開發方面是極簡的,而且在實際運用JMeter執行測試時,對於Function

Qt5的外掛機制6--開發Qt外掛時幾個重要的巨集

如何開發Qt外掛,可以在Qt Assistant 中搜索"Qt Plugins"或"How to Create Qt Plugins",看看那篇manual中的介紹。 其中涉及到了幾個巨集Q_DECLARE_INTERFACE( ClassName, Identifier

github程式碼閱讀的chrome外掛insightio-for-github

在github上找個專案之後,有時候需要先看看其中幾個類才決定收藏與否或者想直接線上找答案; 但是其實一般的專案層級會很深,看程式碼需要一級一級進去,換個層級需要回退回退。。。。。。。 下面介紹一個chrome的一個小外掛:insight.io for githab 安裝之