[unit-testing] 크롬 확장 프로그램을 테스트하는 방법?
이를 수행하는 좋은 방법이 있습니까? 웹 사이트와 콘텐츠 스크립트로 상호 작용하고 로컬 저장소를 사용하여 데이터를 저장하는 확장 프로그램을 작성 중입니다. 이 동작을 테스트하는 데 사용할 수있는 도구, 프레임 워크 등이 있습니까? 자바 스크립트를 테스트하기위한 일반적인 도구가 있지만 확장을 테스트하는 데 충분한 힘이 있습니까? 단위 테스트가 가장 중요하지만 다른 유형의 테스트 (예 : 통합 테스트)에도 관심이 있습니다.
답변
예, 기존 프레임 워크는 매우 유용합니다.
최근에는 모든 테스트를 응용 프로그램에 포함되었지만 실제로 입력하지 않으면 도달 할 수없는 “테스트”페이지에 배치했습니다.
예를 들어, 페이지의 모든 테스트를 아래에서 액세스 할 수 있습니다. chrome-extension://asdasdasdasdad/unittests.html
테스트는 다음에 액세스 할 수 있습니다 localStorage
. 컨텐츠 스크립트에 액세스하려면 이론적으로 테스트 페이지에 포함 된 IFRAME을 통해 테스트 할 수 있지만, 이는보다 통합 레벨 테스트이므로 단위 테스트는 실제 페이지에서 벗어나 추상화해야합니다. localStorage에 액세스 할 때와 마찬가지로 의존하지 마십시오.
페이지를 직접 테스트하려는 경우 확장 프로그램을 조정하여 새 탭 (chrome.tab.create ({ “url”: “someurl”})을 열 수 있습니다. 새 탭마다 콘텐츠 스크립트가 실행되어 사용할 수 있습니다. 테스트 프레임 워크에서 코드가 수행 한 작업을 수행했는지 확인하십시오.
프레임 워크의 경우 JsUnit 또는 최신 Jasmine 이 잘 작동합니다.
답변
여러 크롬 확장에서 작업 내가 해낸 sinon-chrome
사용하여 단위 테스트를 실행할 수 있습니다 프로젝트 mocha
, nodejs
및 phantomjs
.
기본적으로 chrome.*
사전 정의 된 json 응답을 넣을 수있는 모든 API 의 sinon mock을 만듭니다 .
다음으로, vm.runInNewContext
백그라운드 페이지 및 phantomjs
렌더 팝업 / 옵션 페이지에 노드를 사용하여 스크립트를로드합니다 .
마지막으로 크롬 API가 필요한 인수로 호출되었다고 주장합니다.
예를 들어 보겠습니다
. 버튼 배지에 열린 탭 수를 표시하는 간단한 크롬 확장 프로그램이 있다고 가정합니다.
배경 페이지 :
chrome.tabs.query({}, function(tabs) {
chrome.browserAction.setBadgeText({text: String(tabs.length)});
});
그것을 테스트하려면 다음이 필요합니다.
- 조롱
chrome.tabs.query
두 개의 탭 예, 미리 정의 된 응답을 반환 할 수 있습니다. - 조롱 된
chrome.*
API를 환경에 주입 - 이 환경에서 확장 코드를 실행하십시오.
- 버튼 배지가 ‘2’와 같다고 주장
코드 스 니펫은 다음과 같습니다.
const vm = require('vm');
const fs = require('fs');
const chrome = require('sinon-chrome');
// 1. mock `chrome.tabs.query` to return predefined response
chrome.tabs.query.yields([
{id: 1, title: 'Tab 1'},
{id: 2, title: 'Tab 2'}
]);
// 2. inject our mocked chrome.* api into some environment
const context = {
chrome: chrome
};
// 3. run our extension code in this environment
const code = fs.readFileSync('src/background.js');
vm.runInNewContext(code, context);
// 4. assert that button badge equals to '2'
sinon.assert.calledOnce(chrome.browserAction.setBadgeText);
sinon.assert.calledWithMatch(chrome.browserAction.setBadgeText, {
text: "2"
});
이제 우리는 그것을 mocha의 describe..it
함수 로 감싸서 터미널에서 실행할 수 있습니다.
$ mocha
background page
✓ should display opened tabs count in button badge
1 passing (98ms)
여기에서 전체 예제를 찾을 수 있습니다 .
또한 sinon-chrome을 사용하면 사전 정의 된 응답 (예 :
chrome.tab.onCreated.trigger({url: 'http://google.com'});
답변
sinon.js
잘 작동 하는 것처럼 보이지만 일반 Jasmine을 사용하고 필요한 Chrome 콜백을 조롱 할 수도 있습니다. 예:
chrome = {
runtime: {
onMessage : {
addListener : function() {}
}
}
}
describe("JSGuardian", function() {
describe("BlockCache", function() {
beforeEach(function() {
this.blockCache = new BlockCache();
});
it("should recognize added urls", function() {
this.blockCache.add("http://some.url");
expect(this.blockCache.allow("http://some.url")).toBe(false);
});
} // ... etc
SpecRunner.html
코드를 실행 하려면 기본값 을 수정하십시오 .
답변
Chrome의 기존 도구 정보 :
-
크롬 개발자 도구에는 로컬 저장소 관련 리소스 섹션이 있습니다.
개발자 도구> 리소스> 로컬 스토리지
로컬 저장소의 변경 사항을 참조하십시오.
-
console.profile을 사용하여 성능을 테스트하고 런타임 호출 스택을 볼 수 있습니다.
- filesystem의 경우이 URL을 사용하여 파일이 업로드되었는지 여부를 확인할 수 있습니다. filesystem : chrome-extension : /// temporary /
백그라운드 페이지 / 스크립트없이 메시지 전달없이 컨텐츠 스크립트와 로컬 스토리지를 함께 사용하는 경우 해당 사이트에서만 로컬 스토리지에 액세스 할 수 있습니다. 따라서 해당 페이지를 테스트하려면 해당 탭에 테스트 스크립트를 삽입해야합니다.
답변
Selenium은 확장 기능의 “보기”를 구동 할 수 없기 때문에 사전 설치된 확장명과 pyautogui 를 사용 하여 새 브라우저 인스턴스를 시작 하는 데 Selenium 웹 드라이버 를 사용할 수 있음을 발견했습니다 . 클릭 후 스크린 샷을 만들고 ‘예상 된’스크린 샷과 비교할 수 있으며, 유사성의 95 %를 기대합니다 (다른 브라우저에서는 몇 픽셀까지 마크 업 이동이 허용됩니다).
답변
몇 가지 이전 답변을 확인하기 위해 Jasmine은 Chrome 확장 프로그램에서 잘 작동하는 것 같습니다. 버전 3.4.0을 사용하고 있습니다.
Jasmine 스파이 를 사용 하여 다양한 API에 대한 테스트 배가를 쉽게 만들 수 있습니다. 처음부터 직접 만들 필요가 없습니다. 예를 들면 다음과 같습니다.
describe("Test suite", function() {
it("Test case", function() {
// Set up spies and fake data.
spyOn(chrome.browserAction, "setPopup");
spyOn(chrome.identity, "removeCachedAuthToken");
fakeToken = "faketoken-faketoken-faketoken";
fakeWindow = jasmine.createSpyObj("window", ["close"]);
// Call the function under test.
logout(fakeWindow, fakeToken);
// Perform assertions.
expect(chrome.browserAction.setPopup).toHaveBeenCalledWith({popup: ""});
expect(chrome.identity.removeCachedAuthToken).toHaveBeenCalledWith({token: fakeToken});
expect(fakeWindow.close.calls.count()).toEqual(1);
});
});
도움이되는 경우 자세한 내용은 다음과 같습니다.
다른 답변에서 언급했듯이 테스트를 실행하는 브라우저 확장의 일부로 HTML 페이지를 만들었습니다. HTML 페이지에는 Jasmine 라이브러리와 확장 프로그램의 JavaScript 코드 및 테스트 스위트가 포함되어 있습니다. 테스트가 자동으로 실행되고 결과 형식이 결정됩니다. 테스트 러너 또는 결과 포맷터를 구축 할 필요가 없습니다. 설치 지침을 따르고 거기에 문서화 된 HTML을 사용하여 테스트 러너 페이지를 작성하고 테스트 스위트도 페이지에 포함하십시오.
다른 호스트에서 Jasmine 프레임 워크를 동적으로 가져올 수 있다고 생각하지 않으므로 내 확장에 Jasmine 릴리스를 포함 시켰습니다. 물론 프로덕션 용 확장을 빌드 할 때는 테스트 케이스도 생략합니다.
커맨드 라인에서 테스트를 실행하는 방법을 보지 못했습니다. 자동화 된 배포 도구에 유용합니다.