@realfavicongenerator/check-favicon 0.4.7 → 0.4.17
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/dist/desktop/desktop.d.ts +4 -4
- package/dist/desktop/desktop.js +40 -14
- package/dist/desktop/desktop.test.js +149 -64
- package/dist/desktop/ico.d.ts +2 -2
- package/dist/desktop/ico.js +30 -6
- package/dist/google.d.ts +8 -0
- package/dist/google.js +107 -0
- package/dist/google.test.js +71 -0
- package/dist/helper.d.ts +8 -1
- package/dist/helper.js +26 -7
- package/dist/helper.test.js +18 -3
- package/dist/touch-icon.js +1 -1
- package/dist/types.d.ts +29 -1
- package/dist/types.js +8 -0
- package/dist/web-app-manifest.js +1 -1
- package/package.json +6 -4
- package/src/desktop/desktop.test.ts +152 -64
- package/src/desktop/desktop.ts +46 -19
- package/src/desktop/ico.ts +35 -10
- package/src/google.test.ts +82 -0
- package/src/google.ts +103 -0
- package/src/helper.test.ts +19 -4
- package/src/helper.ts +35 -7
- package/src/touch-icon.ts +3 -3
- package/src/types.ts +33 -1
- package/src/web-app-manifest.ts +3 -3
- package/dist/web-manifest.d.ts +0 -4
- package/dist/web-manifest.js +0 -262
- package/dist/web-manifest.test.js +0 -172
- /package/dist/{web-manifest.test.d.ts → google.test.d.ts} +0 -0
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
3
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
4
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
5
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
6
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
7
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
8
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
9
|
+
});
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
const google_1 = require("./google");
|
|
13
|
+
const helper_1 = require("./helper");
|
|
14
|
+
const test_helper_1 = require("./test-helper");
|
|
15
|
+
const types_1 = require("./types");
|
|
16
|
+
test('getRobotsFileUrl', () => {
|
|
17
|
+
expect((0, google_1.getRobotsFileUrl)('https://example.com')).toEqual('https://example.com/robots.txt');
|
|
18
|
+
expect((0, google_1.getRobotsFileUrl)('https://example.com/some-path')).toEqual('https://example.com/robots.txt');
|
|
19
|
+
});
|
|
20
|
+
const runRobotsTest = (urls, robotsFile, messages) => __awaiter(void 0, void 0, void 0, function* () {
|
|
21
|
+
const report = yield (0, google_1.checkRobotsFile)('https://example.com', urls, (0, test_helper_1.testFetcher)(robotsFile ? {
|
|
22
|
+
'https://example.com/robots.txt': {
|
|
23
|
+
status: 200,
|
|
24
|
+
contentType: 'text/plain',
|
|
25
|
+
readableStream: yield (0, helper_1.stringToReadableStream)(robotsFile)
|
|
26
|
+
}
|
|
27
|
+
} : {}));
|
|
28
|
+
const filteredMessages = report.map(m => ({ status: m.status, id: m.id }));
|
|
29
|
+
expect(filteredMessages).toEqual(messages);
|
|
30
|
+
});
|
|
31
|
+
test('checkRobotsFile - No robots file', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
32
|
+
yield runRobotsTest(['https://example.com/favicon.png'], null, [
|
|
33
|
+
{
|
|
34
|
+
status: types_1.CheckerStatus.Ok,
|
|
35
|
+
id: types_1.MessageId.googleNoRobotsFile
|
|
36
|
+
}
|
|
37
|
+
]);
|
|
38
|
+
}));
|
|
39
|
+
test('checkRobotsFile - PNG favicon is accessible', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
40
|
+
yield runRobotsTest(['https://example.com/favicon.png'], `
|
|
41
|
+
User-agent: *
|
|
42
|
+
Allow: /`, [
|
|
43
|
+
{
|
|
44
|
+
status: types_1.CheckerStatus.Ok,
|
|
45
|
+
id: types_1.MessageId.googleRobotsFileFound
|
|
46
|
+
},
|
|
47
|
+
{
|
|
48
|
+
status: types_1.CheckerStatus.Ok,
|
|
49
|
+
id: types_1.MessageId.googlePngIconAllowedByRobots
|
|
50
|
+
}
|
|
51
|
+
]);
|
|
52
|
+
}));
|
|
53
|
+
test('checkRobotsFile - PNG favicon is *not* accessible', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
54
|
+
yield runRobotsTest(['https://example.com/favicon.png'], `
|
|
55
|
+
# *
|
|
56
|
+
User-agent: *
|
|
57
|
+
Allow: /
|
|
58
|
+
|
|
59
|
+
User-agent: Googlebot-Image
|
|
60
|
+
Disallow: /*.png
|
|
61
|
+
`, [
|
|
62
|
+
{
|
|
63
|
+
status: types_1.CheckerStatus.Ok,
|
|
64
|
+
id: types_1.MessageId.googleRobotsFileFound
|
|
65
|
+
},
|
|
66
|
+
{
|
|
67
|
+
status: types_1.CheckerStatus.Error,
|
|
68
|
+
id: types_1.MessageId.googlePngIconBlockedByRobots
|
|
69
|
+
}
|
|
70
|
+
]);
|
|
71
|
+
}));
|
package/dist/helper.d.ts
CHANGED
|
@@ -16,8 +16,15 @@ export type CheckIconProcessor = {
|
|
|
16
16
|
wrongSize: (widthHeight: number) => void;
|
|
17
17
|
};
|
|
18
18
|
export declare const pathToMimeType: (path: string) => string;
|
|
19
|
-
export
|
|
19
|
+
export type CheckIconOutput = {
|
|
20
|
+
content: string | null;
|
|
21
|
+
url: string | null;
|
|
22
|
+
width: number | null;
|
|
23
|
+
height: number | null;
|
|
24
|
+
};
|
|
25
|
+
export declare const checkIcon: (iconUrl: string | undefined, processor: CheckIconProcessor, fetcher: Fetcher, mimeType: string | undefined, expectedWidthHeight?: number) => Promise<CheckIconOutput | null>;
|
|
20
26
|
export declare const mergeUrlAndPath: (baseUrl: string, absoluteOrRelativePath: string) => string;
|
|
21
27
|
export declare const parseSizesAttribute: (sizes: string | undefined | null) => number | null;
|
|
22
28
|
export declare const bufferToDataUrl: (buffer: Buffer, mimeType: string) => string;
|
|
29
|
+
export declare const filePathToDataUrl: (filePath: string) => Promise<string>;
|
|
23
30
|
export declare const fetchFetcher: Fetcher;
|
package/dist/helper.js
CHANGED
|
@@ -12,7 +12,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
12
12
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
13
13
|
};
|
|
14
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
-
exports.fetchFetcher = exports.bufferToDataUrl = exports.parseSizesAttribute = exports.mergeUrlAndPath = exports.checkIcon = exports.pathToMimeType = exports.readableStreamToBuffer = exports.readableStreamToString = exports.stringToReadableStream = exports.filePathToString = exports.filePathToReadableStream = void 0;
|
|
15
|
+
exports.fetchFetcher = exports.filePathToDataUrl = exports.bufferToDataUrl = exports.parseSizesAttribute = exports.mergeUrlAndPath = exports.checkIcon = exports.pathToMimeType = exports.readableStreamToBuffer = exports.readableStreamToString = exports.stringToReadableStream = exports.filePathToString = exports.filePathToReadableStream = void 0;
|
|
16
16
|
const promises_1 = __importDefault(require("fs/promises"));
|
|
17
17
|
const sharp_1 = __importDefault(require("sharp"));
|
|
18
18
|
const filePathToReadableStream = (path) => __awaiter(void 0, void 0, void 0, function* () {
|
|
@@ -35,9 +35,11 @@ const filePathToString = (path) => __awaiter(void 0, void 0, void 0, function* (
|
|
|
35
35
|
});
|
|
36
36
|
exports.filePathToString = filePathToString;
|
|
37
37
|
const stringToReadableStream = (str) => {
|
|
38
|
+
const encoder = new TextEncoder();
|
|
39
|
+
const uint8Array = encoder.encode(str);
|
|
38
40
|
return new ReadableStream({
|
|
39
41
|
start(controller) {
|
|
40
|
-
controller.enqueue(
|
|
42
|
+
controller.enqueue(uint8Array);
|
|
41
43
|
controller.close();
|
|
42
44
|
}
|
|
43
45
|
});
|
|
@@ -114,13 +116,13 @@ const checkIcon = (iconUrl, processor, fetcher, mimeType, expectedWidthHeight) =
|
|
|
114
116
|
}
|
|
115
117
|
else if (res.readableStream) {
|
|
116
118
|
processor.downloadable();
|
|
117
|
-
const
|
|
118
|
-
const meta = yield (0, sharp_1.default)(
|
|
119
|
+
const rawContent = yield (0, exports.readableStreamToBuffer)(res.readableStream);
|
|
120
|
+
const meta = yield (0, sharp_1.default)(rawContent).metadata();
|
|
119
121
|
const contentType = res.contentType || (0, exports.pathToMimeType)(iconUrl);
|
|
122
|
+
const content = yield (0, exports.bufferToDataUrl)(rawContent, contentType);
|
|
120
123
|
if (meta.width && meta.height) {
|
|
121
124
|
if (meta.width !== meta.height) {
|
|
122
125
|
processor.notSquare(meta.width, meta.height);
|
|
123
|
-
return null;
|
|
124
126
|
}
|
|
125
127
|
else {
|
|
126
128
|
processor.square(meta.width);
|
|
@@ -134,9 +136,19 @@ const checkIcon = (iconUrl, processor, fetcher, mimeType, expectedWidthHeight) =
|
|
|
134
136
|
}
|
|
135
137
|
}
|
|
136
138
|
}
|
|
137
|
-
return
|
|
139
|
+
return {
|
|
140
|
+
content,
|
|
141
|
+
url: iconUrl,
|
|
142
|
+
width: meta.width || null,
|
|
143
|
+
height: meta.height || null
|
|
144
|
+
};
|
|
138
145
|
}
|
|
139
|
-
return
|
|
146
|
+
return {
|
|
147
|
+
content: null,
|
|
148
|
+
url: iconUrl,
|
|
149
|
+
width: null,
|
|
150
|
+
height: null
|
|
151
|
+
};
|
|
140
152
|
});
|
|
141
153
|
exports.checkIcon = checkIcon;
|
|
142
154
|
const mergeUrlAndPath = (baseUrl, absoluteOrRelativePath) => {
|
|
@@ -177,6 +189,13 @@ const bufferToDataUrl = (buffer, mimeType) => {
|
|
|
177
189
|
return `data:${mimeType};base64,${buffer.toString('base64')}`;
|
|
178
190
|
};
|
|
179
191
|
exports.bufferToDataUrl = bufferToDataUrl;
|
|
192
|
+
const filePathToDataUrl = (filePath) => __awaiter(void 0, void 0, void 0, function* () {
|
|
193
|
+
const readStream = yield (0, exports.filePathToReadableStream)(filePath);
|
|
194
|
+
const rawContent = yield (0, exports.readableStreamToBuffer)(readStream);
|
|
195
|
+
const contentType = (0, exports.pathToMimeType)(filePath);
|
|
196
|
+
return (0, exports.bufferToDataUrl)(rawContent, contentType);
|
|
197
|
+
});
|
|
198
|
+
exports.filePathToDataUrl = filePathToDataUrl;
|
|
180
199
|
const fetchFetcher = (url, contentType) => __awaiter(void 0, void 0, void 0, function* () {
|
|
181
200
|
const res = yield fetch(url, {
|
|
182
201
|
headers: {
|
package/dist/helper.test.js
CHANGED
|
@@ -34,7 +34,12 @@ test('checkIcon - noHref', () => __awaiter(void 0, void 0, void 0, function* ()
|
|
|
34
34
|
}));
|
|
35
35
|
test('checkIcon - icon404', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
36
36
|
const processor = getTestProcessor();
|
|
37
|
-
expect(yield (0, helper_1.checkIcon)('/does-not-exist.png', processor.processor, (0, test_helper_1.testFetcher)({}), 'image/png')).
|
|
37
|
+
expect(yield (0, helper_1.checkIcon)('/does-not-exist.png', processor.processor, (0, test_helper_1.testFetcher)({}), 'image/png')).toEqual({
|
|
38
|
+
content: null,
|
|
39
|
+
url: '/does-not-exist.png',
|
|
40
|
+
width: null,
|
|
41
|
+
height: null
|
|
42
|
+
});
|
|
38
43
|
expect(processor.messages).toEqual(['icon404']);
|
|
39
44
|
}));
|
|
40
45
|
test('checkIcon - icon404', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
@@ -44,7 +49,12 @@ test('checkIcon - icon404', () => __awaiter(void 0, void 0, void 0, function* ()
|
|
|
44
49
|
contentType: 'image/png',
|
|
45
50
|
status: 500
|
|
46
51
|
}
|
|
47
|
-
}), 'image/png')).
|
|
52
|
+
}), 'image/png')).toEqual({
|
|
53
|
+
content: null,
|
|
54
|
+
url: '/bad-icon.png',
|
|
55
|
+
width: null,
|
|
56
|
+
height: null
|
|
57
|
+
});
|
|
48
58
|
expect(processor.messages).toEqual(['cannotGet 500']);
|
|
49
59
|
}));
|
|
50
60
|
test('checkIcon - downloadable & square', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
@@ -99,7 +109,12 @@ test('checkIcon - downloadable & notSquare', () => __awaiter(void 0, void 0, voi
|
|
|
99
109
|
contentType: 'image/png',
|
|
100
110
|
readableStream: yield (0, helper_1.filePathToReadableStream)(nonSquareIcon)
|
|
101
111
|
}
|
|
102
|
-
}), 'image/png', 500)).
|
|
112
|
+
}), 'image/png', 500)).toEqual({
|
|
113
|
+
content: yield (0, helper_1.filePathToDataUrl)(nonSquareIcon),
|
|
114
|
+
url: '/non-square-icon.png',
|
|
115
|
+
width: 240,
|
|
116
|
+
height: 180
|
|
117
|
+
});
|
|
103
118
|
expect(processor.messages).toEqual([
|
|
104
119
|
'downloadable',
|
|
105
120
|
'notSquare 240x180'
|
package/dist/touch-icon.js
CHANGED
|
@@ -159,7 +159,7 @@ const checkTouchIconIcon = (baseUrl_2, head_2, ...args_2) => __awaiter(void 0, [
|
|
|
159
159
|
}
|
|
160
160
|
};
|
|
161
161
|
touchIcon = yield (0, helper_1.checkIcon)(touchIconUrl, processor, fetcher, undefined);
|
|
162
|
-
return { messages, touchIcon };
|
|
162
|
+
return { messages, touchIcon: touchIcon ? touchIcon.content : null };
|
|
163
163
|
});
|
|
164
164
|
exports.checkTouchIconIcon = checkTouchIconIcon;
|
|
165
165
|
const getDuplicatedSizes = (sizes) => {
|
package/dist/types.d.ts
CHANGED
|
@@ -72,7 +72,15 @@ export declare enum MessageId {
|
|
|
72
72
|
manifestIconNotSquare = 65,
|
|
73
73
|
manifestIconRightSize = 66,
|
|
74
74
|
manifestIconSquare = 67,
|
|
75
|
-
manifestIconWrongSize = 68
|
|
75
|
+
manifestIconWrongSize = 68,
|
|
76
|
+
googleNoRobotsFile = 69,
|
|
77
|
+
googleRobotsFileFound = 70,
|
|
78
|
+
googleIcoBlockedByRobots = 71,
|
|
79
|
+
googleIcoAllowedByRobots = 72,
|
|
80
|
+
googleSvgIconBlockedByRobots = 73,
|
|
81
|
+
googleSvgIconAllowedByRobots = 74,
|
|
82
|
+
googlePngIconBlockedByRobots = 75,
|
|
83
|
+
googlePngIconAllowedByRobots = 76
|
|
76
84
|
}
|
|
77
85
|
export type CheckerMessage = {
|
|
78
86
|
status: CheckerStatus;
|
|
@@ -85,9 +93,24 @@ export type FetchResponse = {
|
|
|
85
93
|
readableStream?: ReadableStream | null;
|
|
86
94
|
};
|
|
87
95
|
export type Fetcher = (url: string, contentType?: string) => Promise<FetchResponse>;
|
|
96
|
+
export type CheckedIcon = {
|
|
97
|
+
content: string | null;
|
|
98
|
+
url: string | null;
|
|
99
|
+
width: number | null;
|
|
100
|
+
height: number | null;
|
|
101
|
+
};
|
|
102
|
+
export type DesktopSingleReport = {
|
|
103
|
+
messages: CheckerMessage[];
|
|
104
|
+
icon: CheckedIcon | null;
|
|
105
|
+
};
|
|
88
106
|
export type DesktopFaviconReport = {
|
|
89
107
|
messages: CheckerMessage[];
|
|
90
108
|
icon: string | null;
|
|
109
|
+
icons: {
|
|
110
|
+
png: CheckedIcon | null;
|
|
111
|
+
ico: CheckedIcon | null;
|
|
112
|
+
svg: CheckedIcon | null;
|
|
113
|
+
};
|
|
91
114
|
};
|
|
92
115
|
export type TouchIconTitleReport = {
|
|
93
116
|
messages: CheckerMessage[];
|
|
@@ -111,3 +134,8 @@ export type FaviconReport = {
|
|
|
111
134
|
webAppManifest: WebAppManifestReport;
|
|
112
135
|
};
|
|
113
136
|
export type TouchIconReport = TouchIconIconReport & TouchIconTitleReport;
|
|
137
|
+
export type GoogleReport = {
|
|
138
|
+
messages: CheckerMessage[];
|
|
139
|
+
icon: string | null;
|
|
140
|
+
icons: CheckedIcon[];
|
|
141
|
+
};
|
package/dist/types.js
CHANGED
|
@@ -78,4 +78,12 @@ var MessageId;
|
|
|
78
78
|
MessageId[MessageId["manifestIconRightSize"] = 66] = "manifestIconRightSize";
|
|
79
79
|
MessageId[MessageId["manifestIconSquare"] = 67] = "manifestIconSquare";
|
|
80
80
|
MessageId[MessageId["manifestIconWrongSize"] = 68] = "manifestIconWrongSize";
|
|
81
|
+
MessageId[MessageId["googleNoRobotsFile"] = 69] = "googleNoRobotsFile";
|
|
82
|
+
MessageId[MessageId["googleRobotsFileFound"] = 70] = "googleRobotsFileFound";
|
|
83
|
+
MessageId[MessageId["googleIcoBlockedByRobots"] = 71] = "googleIcoBlockedByRobots";
|
|
84
|
+
MessageId[MessageId["googleIcoAllowedByRobots"] = 72] = "googleIcoAllowedByRobots";
|
|
85
|
+
MessageId[MessageId["googleSvgIconBlockedByRobots"] = 73] = "googleSvgIconBlockedByRobots";
|
|
86
|
+
MessageId[MessageId["googleSvgIconAllowedByRobots"] = 74] = "googleSvgIconAllowedByRobots";
|
|
87
|
+
MessageId[MessageId["googlePngIconBlockedByRobots"] = 75] = "googlePngIconBlockedByRobots";
|
|
88
|
+
MessageId[MessageId["googlePngIconAllowedByRobots"] = 76] = "googlePngIconAllowedByRobots";
|
|
81
89
|
})(MessageId || (exports.MessageId = MessageId = {}));
|
package/dist/web-app-manifest.js
CHANGED
|
@@ -257,6 +257,6 @@ const checkWebAppManifestFile = (manifest, baseUrl, fetcher) => __awaiter(void 0
|
|
|
257
257
|
}
|
|
258
258
|
finally { if (e_1) throw e_1.error; }
|
|
259
259
|
}
|
|
260
|
-
return { messages, name, shortName, backgroundColor, themeColor, icon };
|
|
260
|
+
return { messages, name, shortName, backgroundColor, themeColor, icon: icon ? icon.content : null };
|
|
261
261
|
});
|
|
262
262
|
exports.checkWebAppManifestFile = checkWebAppManifestFile;
|
package/package.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@realfavicongenerator/check-favicon",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.17",
|
|
4
4
|
"description": "Check the favicon of a website",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
7
7
|
"scripts": {
|
|
8
|
-
"test": "jest",
|
|
9
|
-
"test:watch": "jest --watch",
|
|
8
|
+
"test": "jest src",
|
|
9
|
+
"test:watch": "jest src --watch",
|
|
10
10
|
"build": "tsc",
|
|
11
11
|
"prepublishOnly": "npm run build"
|
|
12
12
|
},
|
|
@@ -37,6 +37,8 @@
|
|
|
37
37
|
"dependencies": {
|
|
38
38
|
"decode-ico": "^0.4.1",
|
|
39
39
|
"node-html-parser": "^6.1.13",
|
|
40
|
+
"robots-parser": "^3.0.1",
|
|
40
41
|
"sharp": "^0.32.6"
|
|
41
|
-
}
|
|
42
|
+
},
|
|
43
|
+
"gitHead": "d1b623a15751d0df89d38fc5fd4915adc2e03646"
|
|
42
44
|
}
|
|
@@ -1,10 +1,13 @@
|
|
|
1
1
|
import { parse } from 'node-html-parser'
|
|
2
2
|
import { checkPngFavicon, checkSvgFavicon } from "./desktop";
|
|
3
|
-
import { CheckerMessage, CheckerStatus, FetchResponse, MessageId } from '../types';
|
|
4
|
-
import { filePathToReadableStream, filePathToString, stringToReadableStream } from '../helper';
|
|
3
|
+
import { CheckerMessage, CheckerStatus, DesktopFaviconReport, FetchResponse, MessageId } from '../types';
|
|
4
|
+
import { filePathToDataUrl, filePathToReadableStream, filePathToString, stringToReadableStream } from '../helper';
|
|
5
5
|
import { testFetcher } from '../test-helper';
|
|
6
6
|
|
|
7
|
-
type TestOutput =
|
|
7
|
+
type TestOutput = {
|
|
8
|
+
messages: Pick<CheckerMessage, 'id' | 'status'>[];
|
|
9
|
+
icons: DesktopFaviconReport['icons'];
|
|
10
|
+
}
|
|
8
11
|
|
|
9
12
|
const runSvgTest = async (
|
|
10
13
|
headFragment: string | null,
|
|
@@ -13,62 +16,113 @@ const runSvgTest = async (
|
|
|
13
16
|
) => {
|
|
14
17
|
const root = headFragment ? parse(headFragment) : null;
|
|
15
18
|
const result = await checkSvgFavicon('https://example.com/', root, testFetcher(fetchDatabase));
|
|
16
|
-
const filteredMessages = result.map(m => ({ status: m.status, id: m.id }));
|
|
17
|
-
expect(filteredMessages).toEqual(output);
|
|
19
|
+
const filteredMessages = result.messages.map(m => ({ status: m.status, id: m.id }));
|
|
20
|
+
expect(filteredMessages).toEqual(output.messages);
|
|
18
21
|
}
|
|
19
22
|
|
|
20
23
|
test('checkSvgFavicon - noHead', async () => {
|
|
21
|
-
await runSvgTest(null,
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
24
|
+
await runSvgTest(null, {
|
|
25
|
+
messages: [{
|
|
26
|
+
status: CheckerStatus.Error,
|
|
27
|
+
id: MessageId.noHead,
|
|
28
|
+
}],
|
|
29
|
+
icons: {
|
|
30
|
+
png: null,
|
|
31
|
+
ico: null,
|
|
32
|
+
svg: null,
|
|
33
|
+
}
|
|
34
|
+
});
|
|
25
35
|
})
|
|
26
36
|
|
|
27
37
|
test('checkSvgFavicon - noSvgFavicon', async () => {
|
|
28
|
-
await runSvgTest(`<title>
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
38
|
+
await runSvgTest(`<title>Some text</title>`, {
|
|
39
|
+
messages: [{
|
|
40
|
+
status: CheckerStatus.Error,
|
|
41
|
+
id: MessageId.noSvgFavicon,
|
|
42
|
+
}],
|
|
43
|
+
icons: {
|
|
44
|
+
png: null,
|
|
45
|
+
ico: null,
|
|
46
|
+
svg: null,
|
|
47
|
+
}
|
|
48
|
+
});
|
|
32
49
|
})
|
|
33
50
|
|
|
34
51
|
test('checkSvgFavicon - multipleSvgFavicons', async () => {
|
|
35
52
|
await runSvgTest(`
|
|
36
53
|
<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />
|
|
37
54
|
<link rel="icon" type="image/svg+xml" href="/another-icon.svg" />
|
|
38
|
-
`,
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
55
|
+
`, {
|
|
56
|
+
messages: [{
|
|
57
|
+
status: CheckerStatus.Error,
|
|
58
|
+
id: MessageId.multipleSvgFavicons,
|
|
59
|
+
}], icons: {
|
|
60
|
+
png: null,
|
|
61
|
+
ico: null,
|
|
62
|
+
svg: null,
|
|
63
|
+
}
|
|
64
|
+
});
|
|
42
65
|
})
|
|
43
66
|
|
|
44
67
|
test('checkSvgFavicon - svgFaviconDeclared & noSvgFaviconHref', async () => {
|
|
45
|
-
await runSvgTest(`<link rel="icon" type="image/svg+xml" />`,
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
68
|
+
await runSvgTest(`<link rel="icon" type="image/svg+xml" />`, {
|
|
69
|
+
messages: [{
|
|
70
|
+
status: CheckerStatus.Ok,
|
|
71
|
+
id: MessageId.svgFaviconDeclared,
|
|
72
|
+
}, {
|
|
73
|
+
status: CheckerStatus.Error,
|
|
74
|
+
id: MessageId.noSvgFaviconHref,
|
|
75
|
+
}],
|
|
76
|
+
icons: {
|
|
77
|
+
png: null,
|
|
78
|
+
ico: null,
|
|
79
|
+
svg: null,
|
|
80
|
+
}
|
|
81
|
+
});
|
|
52
82
|
})
|
|
53
83
|
|
|
54
84
|
test('checkSvgFavicon - svgFaviconDeclared & svgFavicon404', async () => {
|
|
55
|
-
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />`,
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
85
|
+
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />`, {
|
|
86
|
+
messages: [{
|
|
87
|
+
status: CheckerStatus.Ok,
|
|
88
|
+
id: MessageId.svgFaviconDeclared,
|
|
89
|
+
}, {
|
|
90
|
+
status: CheckerStatus.Error,
|
|
91
|
+
id: MessageId.svgFavicon404,
|
|
92
|
+
}],
|
|
93
|
+
icons: {
|
|
94
|
+
png: null,
|
|
95
|
+
ico: null,
|
|
96
|
+
svg: {
|
|
97
|
+
content: null,
|
|
98
|
+
url: 'https://example.com/the-icon.svg',
|
|
99
|
+
width: null,
|
|
100
|
+
height: null,
|
|
101
|
+
},
|
|
102
|
+
}
|
|
103
|
+
});
|
|
62
104
|
})
|
|
63
105
|
|
|
64
106
|
test('checkSvgFavicon - svgFaviconDeclared & svgFaviconCannotGet', async () => {
|
|
65
|
-
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />`,
|
|
66
|
-
|
|
67
|
-
|
|
107
|
+
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />`, {
|
|
108
|
+
messages: [{
|
|
109
|
+
status: CheckerStatus.Ok,
|
|
110
|
+
id: MessageId.svgFaviconDeclared,
|
|
111
|
+
}, {
|
|
112
|
+
status: CheckerStatus.Error,
|
|
113
|
+
id: MessageId.svgFaviconCannotGet,
|
|
114
|
+
}],
|
|
115
|
+
icons: {
|
|
116
|
+
png: null,
|
|
117
|
+
ico: null,
|
|
118
|
+
svg: {
|
|
119
|
+
content: null,
|
|
120
|
+
url: 'https://example.com/the-icon.svg',
|
|
121
|
+
width: null,
|
|
122
|
+
height: null,
|
|
123
|
+
},
|
|
124
|
+
}
|
|
68
125
|
}, {
|
|
69
|
-
status: CheckerStatus.Error,
|
|
70
|
-
id: MessageId.svgFaviconCannotGet,
|
|
71
|
-
}], {
|
|
72
126
|
'https://example.com/the-icon.svg': {
|
|
73
127
|
status: 403,
|
|
74
128
|
contentType: 'image/svg+xml'
|
|
@@ -78,13 +132,24 @@ test('checkSvgFavicon - svgFaviconDeclared & svgFaviconCannotGet', async () => {
|
|
|
78
132
|
|
|
79
133
|
// For https://github.com/RealFaviconGenerator/core/issues/2
|
|
80
134
|
test('checkSvgFavicon - Protocol-relative URL', async () => {
|
|
81
|
-
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="//example.com/the-icon.svg" />`,
|
|
82
|
-
|
|
83
|
-
|
|
135
|
+
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="//example.com/the-icon.svg" />`, {
|
|
136
|
+
messages: [{
|
|
137
|
+
status: CheckerStatus.Ok,
|
|
138
|
+
id: MessageId.svgFaviconDeclared,
|
|
139
|
+
}, {
|
|
140
|
+
status: CheckerStatus.Error,
|
|
141
|
+
id: MessageId.svgFaviconCannotGet,
|
|
142
|
+
}], icons: {
|
|
143
|
+
png: null,
|
|
144
|
+
ico: null,
|
|
145
|
+
svg: {
|
|
146
|
+
content: null,
|
|
147
|
+
url: 'https://example.com/the-icon.svg',
|
|
148
|
+
width: null,
|
|
149
|
+
height: null,
|
|
150
|
+
},
|
|
151
|
+
}
|
|
84
152
|
}, {
|
|
85
|
-
status: CheckerStatus.Error,
|
|
86
|
-
id: MessageId.svgFaviconCannotGet,
|
|
87
|
-
}], {
|
|
88
153
|
'https://example.com/the-icon.svg': {
|
|
89
154
|
status: 403,
|
|
90
155
|
contentType: 'image/svg+xml'
|
|
@@ -97,17 +162,29 @@ test('checkSvgFavicon - svgFaviconDeclared & svgFaviconDownloadable & svgFavicon
|
|
|
97
162
|
|
|
98
163
|
const serpIcon = await filePathToString(testIconPath);
|
|
99
164
|
|
|
100
|
-
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />`,
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
165
|
+
await runSvgTest(`<link rel="icon" type="image/svg+xml" href="/the-icon.svg" />`, {
|
|
166
|
+
messages: [
|
|
167
|
+
{
|
|
168
|
+
status: CheckerStatus.Ok,
|
|
169
|
+
id: MessageId.svgFaviconDeclared,
|
|
170
|
+
}, {
|
|
171
|
+
status: CheckerStatus.Ok,
|
|
172
|
+
id: MessageId.svgFaviconDownloadable,
|
|
173
|
+
}, {
|
|
174
|
+
status: CheckerStatus.Ok,
|
|
175
|
+
id: MessageId.svgFaviconSquare,
|
|
176
|
+
}],
|
|
177
|
+
icons: {
|
|
178
|
+
png: null,
|
|
179
|
+
ico: null,
|
|
180
|
+
svg: {
|
|
181
|
+
content: await filePathToDataUrl(testIconPath),
|
|
182
|
+
url: 'https://example.com/the-icon.svg',
|
|
183
|
+
width: 36,
|
|
184
|
+
height: 36,
|
|
185
|
+
},
|
|
186
|
+
}
|
|
107
187
|
}, {
|
|
108
|
-
status: CheckerStatus.Ok,
|
|
109
|
-
id: MessageId.svgFaviconSquare,
|
|
110
|
-
}], {
|
|
111
188
|
'https://example.com/the-icon.svg': {
|
|
112
189
|
status: 200,
|
|
113
190
|
contentType: 'image/svg+xml',
|
|
@@ -124,7 +201,7 @@ const runPngTest = async (
|
|
|
124
201
|
const root = headFragment ? parse(headFragment) : null;
|
|
125
202
|
const result = await checkPngFavicon('https://example.com/', root, testFetcher(fetchDatabase));
|
|
126
203
|
const filteredMessages = result.messages.map(m => ({ status: m.status, id: m.id }));
|
|
127
|
-
expect(filteredMessages).toEqual(output);
|
|
204
|
+
expect(filteredMessages).toEqual(output.messages);
|
|
128
205
|
}
|
|
129
206
|
|
|
130
207
|
const testIcon16 = './fixtures/16x16.png';
|
|
@@ -138,16 +215,27 @@ test('checkSvgFavicon - Three PNG icons with different sizes', async () => {
|
|
|
138
215
|
<link rel="icon" type="image/png" sizes="32x32" href="/favicon/favicon-32x32.png">
|
|
139
216
|
<link rel="icon" type="image/png" sizes="48x48" href="/favicon/favicon-48x48.png">
|
|
140
217
|
<link rel="icon" type="image/png" sizes="96x96" href="/favicon/favicon-96x96.png">
|
|
141
|
-
`, [{
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
218
|
+
`, { messages: [{
|
|
219
|
+
status: CheckerStatus.Ok,
|
|
220
|
+
id: MessageId.desktopPngFaviconDeclared,
|
|
221
|
+
}, {
|
|
222
|
+
status: CheckerStatus.Ok,
|
|
223
|
+
id: MessageId.desktopPngFaviconDownloadable,
|
|
224
|
+
}, {
|
|
225
|
+
status: CheckerStatus.Ok,
|
|
226
|
+
id: MessageId.desktopPngFaviconRightSize,
|
|
227
|
+
}],
|
|
228
|
+
icons: {
|
|
229
|
+
png: {
|
|
230
|
+
content: await filePathToDataUrl(testIcon96),
|
|
231
|
+
url: 'https://example.com/favicon/favicon-96x96.png',
|
|
232
|
+
width: 96,
|
|
233
|
+
height: 96,
|
|
234
|
+
},
|
|
235
|
+
ico: null,
|
|
236
|
+
svg: null,
|
|
237
|
+
}
|
|
238
|
+
},
|
|
151
239
|
{
|
|
152
240
|
'https://example.com/favicon/favicon-16x16.png': {
|
|
153
241
|
status: 200,
|