diff --git a/test/golden-utils.js b/test/golden-utils.js
new file mode 100644
index 00000000000..55379286aa2
--- /dev/null
+++ b/test/golden-utils.js
@@ -0,0 +1,157 @@
+/**
+ * Copyright 2017 Google Inc. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+var path = require('path');
+var fs = require('fs');
+var Diff = require('text-diff');
+var mime = require('mime');
+var PNG = require('pngjs').PNG;
+var pixelmatch = require('pixelmatch');
+var rm = require('rimraf').sync;
+
+var GOLDEN_DIR = path.join(__dirname, 'golden');
+var OUTPUT_DIR = path.join(__dirname, 'output');
+
+module.exports = {
+ addMatchers: function(jasmine) {
+ jasmine.addMatchers(customMatchers);
+ },
+
+ removeOutputDir: function() {
+ if (fs.existsSync(OUTPUT_DIR))
+ rm(OUTPUT_DIR);
+ },
+};
+
+var GoldenComparators = {
+ 'image/png': compareImages,
+ 'text/plain': compareText
+};
+
+/**
+ * @param {?Object} actualBuffer
+ * @param {!Buffer} expectedBuffer
+ * @return {?{diff: (!Object:undefined), errorMessage: (string|undefined)}}
+ */
+function compareImages(actualBuffer, expectedBuffer) {
+ if (!actualBuffer || !(actualBuffer instanceof Buffer))
+ return { errorMessage: 'Actual result should be Buffer.' };
+
+ var actual = PNG.sync.read(actualBuffer);
+ var expected = PNG.sync.read(expectedBuffer);
+ if (expected.width !== actual.width || expected.height !== actual.height) {
+ return {
+ errorMessage: `Sizes differ: expected image ${expected.width}px X ${expected.height}px, but got ${actual.width}px X ${actual.height}px. `
+ };
+ }
+ var diff = new PNG({width: expected.width, height: expected.height});
+ var count = pixelmatch(expected.data, actual.data, diff.data, expected.width, expected.height, {threshold: 0.1});
+ return count > 0 ? { diff: PNG.sync.write(diff) } : null;
+}
+
+/**
+ * @param {?Object} actual
+ * @param {!Buffer} expectedBuffer
+ * @return {?{diff: (!Object:undefined), errorMessage: (string|undefined)}}
+ */
+function compareText(actual, expectedBuffer) {
+ if (typeof actual !== 'string')
+ return { errorMessage: 'Actual result should be string' };
+ var expected = expectedBuffer.toString('utf-8');
+ if (expected === actual)
+ return null;
+ var diff = new Diff();
+ var result = diff.main(expected, actual);
+ diff.cleanupSemantic(result);
+ var html = diff.prettyHtml(result);
+ var diffStylePath = path.join(__dirname, 'diffstyle.css');
+ html = `` + html;
+ return {
+ diff: html,
+ diffExtension: '.html'
+ };
+}
+
+var customMatchers = {
+ toBeGolden: function(util, customEqualityTesters) {
+ return {
+ /**
+ * @param {?Object} actual
+ * @param {string} goldenName
+ * @return {!{pass: boolean, message: (undefined|string)}}
+ */
+ compare: function(actual, goldenName) {
+ var expectedPath = path.join(GOLDEN_DIR, goldenName);
+ var actualPath = path.join(OUTPUT_DIR, goldenName);
+
+ var messageSuffix = 'Output is saved in "' + path.basename(OUTPUT_DIR + '" directory');
+
+ if (!fs.existsSync(expectedPath)) {
+ ensureOutputDir();
+ fs.writeFileSync(actualPath, actual);
+ return {
+ pass: false,
+ message: goldenName + ' is missing in golden results. ' + messageSuffix
+ };
+ }
+ var expected = fs.readFileSync(expectedPath);
+ var comparator = GoldenComparators[mime.lookup(goldenName)];
+ if (!comparator) {
+ return {
+ pass: false,
+ message: 'Failed to find comparator with type ' + mime.lookup(goldenName) + ': ' + goldenName
+ };
+ }
+ var result = comparator(actual, expected);
+ if (!result)
+ return { pass: true };
+ ensureOutputDir();
+ fs.writeFileSync(actualPath, actual);
+ // Copy expected to the output/ folder for convenience.
+ fs.writeFileSync(addSuffix(actualPath, '-expected'), expected);
+ if (result.diff) {
+ var diffPath = addSuffix(actualPath, '-diff', result.diffExtension);
+ fs.writeFileSync(diffPath, result.diff);
+ }
+
+ var message = goldenName + ' mismatch!';
+ if (result.errorMessage)
+ message += ' ' + result.errorMessage;
+ return {
+ pass: false,
+ message: message + ' ' + messageSuffix
+ };
+
+ function ensureOutputDir() {
+ if (!fs.existsSync(OUTPUT_DIR))
+ fs.mkdirSync(OUTPUT_DIR);
+ }
+ }
+ };
+ },
+};
+
+/**
+ * @param {string} filePath
+ * @param {string} suffix
+ * @param {string=} customExtension
+ * @return {string}
+ */
+function addSuffix(filePath, suffix, customExtension) {
+ var dirname = path.dirname(filePath);
+ var ext = path.extname(filePath);
+ var name = path.basename(filePath, ext);
+ return path.join(dirname, name + suffix + (customExtension || ext));
+}
diff --git a/test/test.js b/test/test.js
index 0e4ec67fece..417f2555554 100644
--- a/test/test.js
+++ b/test/test.js
@@ -14,24 +14,15 @@
* limitations under the License.
*/
-var fs = require('fs');
var path = require('path');
-var rm = require('rimraf').sync;
var Browser = require('../lib/Browser');
var StaticServer = require('./StaticServer');
-var PNG = require('pngjs').PNG;
-var mime = require('mime');
-var pixelmatch = require('pixelmatch');
-var Diff = require('text-diff');
+var GoldenUtils = require('./golden-utils');
var PORT = 8907;
var STATIC_PREFIX = 'http://localhost:' + PORT;
var EMPTY_PAGE = STATIC_PREFIX + '/empty.html';
-var GOLDEN_DIR = path.join(__dirname, 'golden');
-var OUTPUT_DIR = path.join(__dirname, 'output');
-var PROJECT_DIR = path.join(__dirname, '..');
-
jasmine.DEFAULT_TIMEOUT_INTERVAL = 10 * 1000;
describe('Puppeteer', function() {
@@ -42,8 +33,7 @@ describe('Puppeteer', function() {
beforeAll(function() {
browser = new Browser();
staticServer = new StaticServer(path.join(__dirname, 'assets'), PORT);
- if (fs.existsSync(OUTPUT_DIR))
- rm(OUTPUT_DIR);
+ GoldenUtils.removeOutputDir();
});
afterAll(function() {
@@ -53,7 +43,7 @@ describe('Puppeteer', function() {
beforeEach(SX(async function() {
page = await browser.newPage();
- jasmine.addMatchers(customMatchers);
+ GoldenUtils.addMatchers(jasmine);
}));
afterEach(function() {
@@ -336,128 +326,6 @@ describe('Puppeteer', function() {
});
});
-var GoldenComparators = {
- 'image/png': compareImages,
- 'text/plain': compareText
-};
-
-/**
- * @param {?Object} actualBuffer
- * @param {!Buffer} expectedBuffer
- * @return {?{diff: (!Object:undefined), errorMessage: (string|undefined)}}
- */
-function compareImages(actualBuffer, expectedBuffer) {
- if (!actualBuffer || !(actualBuffer instanceof Buffer))
- return { errorMessage: 'Actual result should be Buffer.' };
-
- var actual = PNG.sync.read(actualBuffer);
- var expected = PNG.sync.read(expectedBuffer);
- if (expected.width !== actual.width || expected.height !== actual.height) {
- return {
- errorMessage: `Sizes differ: expected image ${expected.width}px X ${expected.height}px, but got ${actual.width}px X ${actual.height}px. `
- };
- }
- var diff = new PNG({width: expected.width, height: expected.height});
- var count = pixelmatch(expected.data, actual.data, diff.data, expected.width, expected.height, {threshold: 0.1});
- return count > 0 ? { diff: PNG.sync.write(diff) } : null;
-}
-
-/**
- * @param {?Object} actual
- * @param {!Buffer} expectedBuffer
- * @return {?{diff: (!Object:undefined), errorMessage: (string|undefined)}}
- */
-function compareText(actual, expectedBuffer) {
- if (typeof actual !== 'string')
- return { errorMessage: 'Actual result should be string' };
- var expected = expectedBuffer.toString('utf-8');
- if (expected === actual)
- return null;
- var diff = new Diff();
- var result = diff.main(expected, actual);
- diff.cleanupSemantic(result);
- var html = diff.prettyHtml(result);
- var diffStylePath = path.join(__dirname, 'diffstyle.css');
- html = `` + html;
- return {
- diff: html,
- diffExtension: '.html'
- };
-}
-
-var customMatchers = {
- toBeGolden: function(util, customEqualityTesters) {
- return {
- /**
- * @param {?Object} actual
- * @param {string} goldenName
- * @return {!{pass: boolean, message: (undefined|string)}}
- */
- compare: function(actual, goldenName) {
- var expectedPath = path.join(GOLDEN_DIR, goldenName);
- var actualPath = path.join(OUTPUT_DIR, goldenName);
-
- var messageSuffix = 'Output is saved in ' + path.relative(PROJECT_DIR, OUTPUT_DIR);
-
- if (!fs.existsSync(expectedPath)) {
- ensureOutputDir();
- fs.writeFileSync(actualPath, actual);
- return {
- pass: false,
- message: goldenName + ' is missing in golden results. ' + messageSuffix
- };
- }
- var expected = fs.readFileSync(expectedPath);
- var comparator = GoldenComparators[mime.lookup(goldenName)];
- if (!comparator) {
- return {
- pass: false,
- message: 'Failed to find comparator with type ' + mime.lookup(goldenName) + ': ' + goldenName
- };
- }
- var result = comparator(actual, expected);
- if (!result)
- return { pass: true };
- ensureOutputDir();
- fs.writeFileSync(actualPath, actual);
- // Copy expected to the output/ folder for convenience.
- fs.writeFileSync(addSuffix(actualPath, '-expected'), expected);
- if (result.diff) {
- var diffPath = addSuffix(actualPath, '-diff', result.diffExtension);
- fs.writeFileSync(diffPath, result.diff);
- }
-
- var message = goldenName + ' mismatch!';
- if (result.errorMessage)
- message += ' ' + result.errorMessage;
- return {
- pass: false,
- message: message + ' ' + messageSuffix
- };
-
- function ensureOutputDir() {
- if (!fs.existsSync(OUTPUT_DIR))
- fs.mkdirSync(OUTPUT_DIR);
- }
- }
- };
- },
-};
-
-/**
- * @param {string} filePath
- * @param {string} suffix
- * @param {string=} customExtension
- * @return {string}
- */
-function addSuffix(filePath, suffix, customExtension) {
- var dirname = path.dirname(filePath);
- var ext = path.extname(filePath);
- var name = path.basename(filePath, ext);
- return path.join(dirname, name + suffix + (customExtension || ext));
-}
-
-
// Since Jasmine doesn't like async functions, they should be wrapped
// in a SX function.
function SX(fun) {