parse-domain 2.3.0 → 2.3.4

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.
@@ -0,0 +1,140 @@
1
+ "use strict";
2
+
3
+ const parse = require("../../lib/trie/parse");
4
+
5
+ describe("parse()", () => {
6
+ describe("when called with ''", () => {
7
+ test("returns a node with null as domain and no children", () => {
8
+ const root = parse("");
9
+
10
+ expect(root.domain).toBeNull();
11
+ expect(root.children.size).toBe(0);
12
+ });
13
+ });
14
+ describe("when called with 'a'", () => {
15
+ test("adds 'a' as child of root", () => {
16
+ const root = parse("a");
17
+
18
+ expect(root.children.has("a")).toBe(true);
19
+ });
20
+ test("initializes 'a' with the correct domain and parent", () => {
21
+ const root = parse("a");
22
+ const a = root.children.get("a");
23
+
24
+ expect(a.domain).toBe("a");
25
+ expect(a.parent).toBe(root);
26
+ });
27
+ });
28
+ describe("when called with 'a,b'", () => {
29
+ test("adds 'a' and 'b' as child of root", () => {
30
+ const root = parse("a,b");
31
+
32
+ expect(root.children.has("a")).toBe(true);
33
+ expect(root.children.has("b")).toBe(true);
34
+ });
35
+ test("initializes 'b' with the correct domain and parent", () => {
36
+ const root = parse("a,b");
37
+ const b = root.children.get("b");
38
+
39
+ expect(b.domain).toBe("b");
40
+ expect(b.parent).toBe(root);
41
+ });
42
+ });
43
+ describe("when called with 'a>b'", () => {
44
+ test("adds 'a' as child of root and 'b' as child of 'a'", () => {
45
+ const root = parse("a>b");
46
+
47
+ expect(root.children.has("a")).toBe(true);
48
+ expect(root.children.get("a").children.has("b")).toBe(true);
49
+ });
50
+ test("initializes 'b' with the correct domain and parent", () => {
51
+ const root = parse("a>b");
52
+ const a = root.children.get("a");
53
+ const b = a.children.get("b");
54
+
55
+ expect(b.domain).toBe("b");
56
+ expect(b.parent).toBe(a);
57
+ });
58
+ });
59
+ describe("when called with 'a>b,c'", () => {
60
+ test("adds 'b' and 'c' as child of 'a'", () => {
61
+ const root = parse("a>b,c");
62
+ const a = root.children.get("a");
63
+
64
+ expect(a.children.has("b")).toBe(true);
65
+ expect(a.children.has("c")).toBe(true);
66
+ });
67
+ test("initializes 'c' with the correct domain and parent", () => {
68
+ const root = parse("a>b,c");
69
+ const a = root.children.get("a");
70
+ const c = a.children.get("c");
71
+
72
+ expect(c.domain).toBe("c");
73
+ expect(c.parent).toBe(a);
74
+ });
75
+ });
76
+ describe("when called with 'a>b<c'", () => {
77
+ test("adds 'b' as child of 'a' and 'c' as child of root", () => {
78
+ const root = parse("a>b<c");
79
+ const a = root.children.get("a");
80
+
81
+ expect(a.children.has("b")).toBe(true);
82
+ expect(root.children.has("c")).toBe(true);
83
+ });
84
+ test("initializes 'c' with the correct domain and parent", () => {
85
+ const root = parse("a>b<c");
86
+ const c = root.children.get("c");
87
+
88
+ expect(c.domain).toBe("c");
89
+ expect(c.parent).toBe(root);
90
+ });
91
+ });
92
+ describe("when called with 'a|b'", () => {
93
+ test("adds 'a' and 'b' as child of root", () => {
94
+ const root = parse("a|b");
95
+
96
+ expect(root.children.has("a")).toBe(true);
97
+ expect(root.children.has("b")).toBe(true);
98
+ });
99
+ test("initializes 'b' with the correct domain and parent", () => {
100
+ const root = parse("a|b");
101
+ const b = root.children.get("b");
102
+
103
+ expect(b.domain).toBe("b");
104
+ expect(b.parent).toBe(root);
105
+ });
106
+ });
107
+ describe("when called with 'a>b|c'", () => {
108
+ test("adds 'b' as child of 'a' and 'c' as child of root", () => {
109
+ const root = parse("a>b|c");
110
+ const a = root.children.get("a");
111
+
112
+ expect(a.children.has("b")).toBe(true);
113
+ expect(root.children.has("c")).toBe(true);
114
+ });
115
+ });
116
+ describe("when called with 'a>b<a>d'", () => {
117
+ test("adds 'b' and 'd' as child of 'a'", () => {
118
+ const root = parse("a>b<a>c");
119
+ const a = root.children.get("a");
120
+
121
+ expect(a.children.has("b")).toBe(true);
122
+ expect(a.children.has("c")).toBe(true);
123
+ });
124
+ });
125
+ describe("when called with 'a>b>c'", () => {
126
+ test("adds 'c' as child of 'b'", () => {
127
+ const root = parse("a>b>c");
128
+ const b = root.children.get("a").children.get("b");
129
+
130
+ expect(b.children.has("c")).toBe(true);
131
+ });
132
+ });
133
+ describe("when called with 'a>b>c>d|e'", () => {
134
+ test("adds 'e' as child node of root", () => {
135
+ const node = parse("a>b>c>d|e");
136
+
137
+ expect(node.children.has("e")).toBe(true);
138
+ });
139
+ });
140
+ });
@@ -0,0 +1,130 @@
1
+ "use strict";
2
+
3
+ const fs = require("fs");
4
+ const path = require("path");
5
+ const parsePubSuffixList = require("../../lib/trie/parsePubSuffixList");
6
+
7
+ const pathToFixtures = path.resolve(__dirname, "..", "fixtures");
8
+ const icannStart = "// ===BEGIN ICANN DOMAINS===";
9
+ const icannEnd = "// ===END ICANN DOMAINS===";
10
+ const privateStart = "// ===BEGIN PRIVATE DOMAINS===";
11
+ const privateEnd = "// ===END PRIVATE DOMAINS===";
12
+
13
+ describe("parsePubSuffixList()", () => {
14
+ test("returns an object with empty lists by default", () => {
15
+ const str = [icannStart, icannEnd, privateStart, privateEnd].join("\n");
16
+
17
+ expect(parsePubSuffixList(str)).toEqual({
18
+ icann: [],
19
+ private: [],
20
+ });
21
+ });
22
+
23
+ test(
24
+ "splits the list by the line break character \\n (ignoring \\r if present)",
25
+ () => {
26
+ const str = [
27
+ icannStart,
28
+ "a.b.c\r",
29
+ "a",
30
+ "b\r",
31
+ icannEnd + "\r",
32
+ privateStart,
33
+ "a.b.c",
34
+ "a",
35
+ "b",
36
+ privateEnd,
37
+ ].join("\n");
38
+
39
+ expect(parsePubSuffixList(str)).toEqual({
40
+ icann: ["a.b.c", "a", "b"],
41
+ private: ["a.b.c", "a", "b"],
42
+ });
43
+ }
44
+ );
45
+
46
+ test("removes lines that start with a // sequence", () => {
47
+ const str = [
48
+ icannStart,
49
+ "// comment",
50
+ "a.b.c",
51
+ "a",
52
+ "b",
53
+ "//another comment",
54
+ icannEnd,
55
+ privateStart,
56
+ "a.b.c",
57
+ "//",
58
+ "a",
59
+ " // ",
60
+ "b",
61
+ privateEnd,
62
+ ].join("\n");
63
+
64
+ expect(parsePubSuffixList(str)).toEqual({
65
+ icann: ["a.b.c", "a", "b"],
66
+ private: ["a.b.c", "a", "b"],
67
+ });
68
+ });
69
+
70
+ test("removes empty lines", () => {
71
+ const str = [
72
+ icannStart,
73
+ " ",
74
+ "a.b.c",
75
+ "a",
76
+ "b",
77
+ "\r",
78
+ icannEnd,
79
+ privateStart,
80
+ "a.b.c",
81
+ "\t",
82
+ "a",
83
+ "b",
84
+ privateEnd,
85
+ ].join("\n");
86
+
87
+ expect(parsePubSuffixList(str)).toEqual({
88
+ icann: ["a.b.c", "a", "b"],
89
+ private: ["a.b.c", "a", "b"],
90
+ });
91
+ });
92
+
93
+ test("throws when the ICANN start marker is missing ", () => {
94
+ const str = [""].join("\n");
95
+
96
+ expect(() => parsePubSuffixList(str)).toThrowError("Missing start marker of icann list");
97
+ });
98
+
99
+ test("throws when the ICANN end marker is missing ", () => {
100
+ const str = [icannStart].join("\n");
101
+
102
+ expect(() => parsePubSuffixList(str)).toThrowError("Missing end marker of icann list");
103
+ });
104
+
105
+ test("throws when the PRIVATE start marker is missing ", () => {
106
+ const str = [icannStart, icannEnd].join("\n");
107
+
108
+ expect(() => parsePubSuffixList(str)).toThrowError("Missing start marker of private list");
109
+ });
110
+
111
+ test("throws when the PRIVATE end marker is missing ", () => {
112
+ const str = [icannStart, icannEnd, privateStart].join("\n");
113
+
114
+ expect(() => parsePubSuffixList(str)).toThrowError("Missing end marker of private list");
115
+ });
116
+
117
+ describe("with fixtures", () => {
118
+ const pubSuffixList = fs.readFileSync(path.resolve(pathToFixtures, "pubSuffixList.txt"), "utf8");
119
+
120
+ test("returns the expected result (based on samples)", () => {
121
+ const parsedList = parsePubSuffixList(pubSuffixList);
122
+
123
+ expect(Array.isArray(parsedList.icann)).toBe(true);
124
+ expect(Array.isArray(parsedList.private)).toBe(true);
125
+ expect(parsedList.icann).toEqual(expect.arrayContaining(["com"]));
126
+ expect(parsedList.icann).toEqual(expect.arrayContaining(["co.uk"]));
127
+ expect(parsedList.private).toEqual(expect.arrayContaining(["herokuapp.com"]));
128
+ });
129
+ });
130
+ });
@@ -1,9 +1,6 @@
1
1
  "use strict";
2
2
 
3
- const chai = require("chai");
4
- const serializeTrie = require("../../lib/tries/serializeTrie");
5
-
6
- const expect = chai.expect;
3
+ const serializeTrie = require("../../lib/trie/serializeTrie");
7
4
 
8
5
  describe("serializeTrie()", () => {
9
6
  [
@@ -36,9 +33,12 @@ describe("serializeTrie()", () => {
36
33
  const parsedList = args[0];
37
34
  const expectedString = args[1];
38
35
 
39
- it(`maps ${JSON.stringify(parsedList)} on ${JSON.stringify(expectedString)}`, () => {
40
- expect(serializeTrie(parsedList)).to.equal(expectedString);
41
- });
36
+ test(
37
+ `maps ${JSON.stringify(parsedList)} on ${JSON.stringify(expectedString)}`,
38
+ () => {
39
+ expect(serializeTrie(parsedList)).toBe(expectedString);
40
+ }
41
+ );
42
42
  });
43
43
 
44
44
  describe(`type ${serializeTrie.TYPE_LIGHT}`, () => {
@@ -57,9 +57,12 @@ describe("serializeTrie()", () => {
57
57
  const parsedList = args[0];
58
58
  const expectedString = args[1];
59
59
 
60
- it(`maps ${JSON.stringify(parsedList)} on ${JSON.stringify(expectedString)}`, () => {
61
- expect(serializeTrie(parsedList, type)).to.equal(expectedString);
62
- });
60
+ test(
61
+ `maps ${JSON.stringify(parsedList)} on ${JSON.stringify(expectedString)}`,
62
+ () => {
63
+ expect(serializeTrie(parsedList, type)).toBe(expectedString);
64
+ }
65
+ );
63
66
  });
64
67
  });
65
68
 
@@ -84,16 +87,19 @@ describe("serializeTrie()", () => {
84
87
  const parsedList = args[0];
85
88
  const expectedString = args[1];
86
89
 
87
- it(`maps ${JSON.stringify(parsedList)} on ${JSON.stringify(expectedString)}`, () => {
88
- expect(serializeTrie(parsedList, type)).to.equal(expectedString);
89
- });
90
+ test(
91
+ `maps ${JSON.stringify(parsedList)} on ${JSON.stringify(expectedString)}`,
92
+ () => {
93
+ expect(serializeTrie(parsedList, type)).toBe(expectedString);
94
+ }
95
+ );
90
96
  });
91
97
  });
92
98
 
93
99
  describe("wrong usage", () => {
94
100
  expect(() => {
95
101
  serializeTrie([], "unsupported type");
96
- }).to.throw(
102
+ }).toThrowError(
97
103
  'Cannot serialize trie: Unknown trie type "unsupported type". Expected type to be one of complete, light'
98
104
  );
99
105
  });
@@ -1,40 +0,0 @@
1
- "use strict";
2
-
3
- var WILDCARD = "*";
4
- var EXCEPTION = "!";
5
-
6
- function lookUp(trie, hostname) {
7
- var domains = hostname.split(".").reverse();
8
- var tlds = [];
9
- var currentTrie = trie;
10
-
11
- for (var i = 0; i < domains.length; i++) {
12
- var domain = domains[i];
13
- var isWildcardRule = currentTrie.has(WILDCARD);
14
-
15
- if (isWildcardRule) {
16
- if (currentTrie.has(EXCEPTION + domain) === false) {
17
- tlds.push(domain);
18
- }
19
-
20
- break;
21
- }
22
-
23
- if (currentTrie.has(domain) === false) {
24
- break;
25
- }
26
-
27
- tlds.push(domain);
28
- var value = currentTrie.get(domain);
29
-
30
- if (value === true) {
31
- break;
32
- }
33
-
34
- currentTrie = value;
35
- }
36
-
37
- return tlds.length === 0 ? null : tlds.reverse().join(".");
38
- }
39
-
40
- module.exports = lookUp;
@@ -1,62 +0,0 @@
1
- "use strict";
2
-
3
- var SEPARATORS = require("./separators");
4
-
5
- function parseTrie(input) {
6
- var map = new Map();
7
- var parentMaps = [map];
8
- var domain = "";
9
-
10
- function setDomain(value) {
11
- if (domain === "") {
12
- return;
13
- }
14
-
15
- map.set(domain, value);
16
- domain = "";
17
- }
18
-
19
- for (var i = 0; i < input.length; i++) {
20
- var _char = input.charAt(i);
21
-
22
- switch (_char) {
23
- case SEPARATORS.SAME:
24
- {
25
- setDomain(true);
26
- continue;
27
- }
28
-
29
- case SEPARATORS.DOWN:
30
- {
31
- var childMap = new Map();
32
- setDomain(childMap);
33
- parentMaps.push(map);
34
- map = childMap;
35
- continue;
36
- }
37
-
38
- case SEPARATORS.RESET:
39
- {
40
- setDomain(true); // Remove all parent maps but the top most
41
-
42
- parentMaps.length = 1;
43
- map = parentMaps[0];
44
- continue;
45
- }
46
-
47
- case SEPARATORS.UP:
48
- {
49
- setDomain(true);
50
- map = parentMaps.pop();
51
- continue;
52
- }
53
- }
54
-
55
- domain += _char;
56
- }
57
-
58
- setDomain(true);
59
- return parentMaps[0];
60
- }
61
-
62
- module.exports = parseTrie;
@@ -1,12 +0,0 @@
1
- "use strict";
2
-
3
- module.exports = {
4
- UP: "<",
5
- // one level up
6
- SAME: ",",
7
- // same level
8
- DOWN: ">",
9
- // one level down
10
- RESET: "|" // reset level index and start new
11
-
12
- };
package/test/mocha.opts DELETED
@@ -1 +0,0 @@
1
- --recursive
@@ -1,116 +0,0 @@
1
- "use strict";
2
-
3
- const chai = require("chai");
4
- const lookUp = require("../../lib/tries/lookUp");
5
-
6
- const expect = chai.expect;
7
-
8
- describe("lookUp()", () => {
9
- it("returns null if the trie is empty", () => {
10
- const trie = new Map();
11
- const hostname = "a.b.c";
12
-
13
- expect(lookUp(trie, hostname)).to.eql(null);
14
- });
15
- it("returns null if the trie contains no matching top-level domain", () => {
16
- const trie = new Map();
17
- const hostname = "a.b.c";
18
-
19
- trie.set("cc", true);
20
-
21
- expect(lookUp(trie, hostname)).to.eql(null);
22
- });
23
- it("returns the hostname if the hostname is a top-level domain", () => {
24
- const trie = new Map();
25
- const hostname = "a";
26
-
27
- trie.set("a", true);
28
- trie.set("b", true);
29
-
30
- expect(lookUp(trie, hostname)).to.eql("a");
31
- });
32
- it("returns the top-level domain from the hostname (2 domains)", () => {
33
- const trie = new Map();
34
- const hostname = "b.a";
35
-
36
- trie.set("a", true);
37
- trie.set("b", true);
38
-
39
- expect(lookUp(trie, hostname)).to.eql("a");
40
- });
41
- it("returns the top-level domain from the hostname (3 domains)", () => {
42
- const trie = new Map();
43
- const hostname = "c.b.a";
44
-
45
- trie.set("a", true);
46
- trie.set("b", true);
47
-
48
- expect(lookUp(trie, hostname)).to.eql("a");
49
- });
50
- it("returns the top-level domain (2 tlds) from the hostname (3 domains)", () => {
51
- const trie = new Map();
52
- const trieA = new Map();
53
- const hostname = "c.b.a";
54
-
55
- trieA.set("b", true);
56
- trie.set("a", trieA);
57
- trie.set("b", new Map());
58
-
59
- expect(lookUp(trie, hostname)).to.eql("b.a");
60
- });
61
- it("returns the top-level domain (3 tlds) from the hostname (4 domains)", () => {
62
- const trie = new Map();
63
- const trieA = new Map();
64
- const trieAB = new Map();
65
- const hostname = "d.c.b.a";
66
-
67
- trieAB.set("c", true);
68
- trieA.set("b", trieAB);
69
- trieA.set("a", true);
70
- trie.set("a", trieA);
71
- trie.set("b", new Map());
72
-
73
- expect(lookUp(trie, hostname)).to.eql("c.b.a");
74
- });
75
- it("interprets wildcards in the trie correctly (simple)", () => {
76
- const trie = new Map();
77
- const hostname = "a.b.c";
78
-
79
- trie.set("*", true);
80
-
81
- expect(lookUp(trie, hostname)).to.eql("c");
82
- });
83
- it("interprets wildcards in the trie correctly (nested)", () => {
84
- const trie = new Map();
85
- const trieA = new Map();
86
- const hostname = "c.b.a";
87
-
88
- trieA.set("*", true);
89
- trie.set("a", trieA);
90
-
91
- expect(lookUp(trie, hostname)).to.eql("b.a");
92
- });
93
- it("interprets exceptions of wildcards in the trie correctly (simple)", () => {
94
- const trie = new Map();
95
- const trieA = new Map();
96
- const hostname = "c.b.a";
97
-
98
- trieA.set("*", true);
99
- trieA.set("!b", true);
100
- trie.set("a", trieA);
101
-
102
- expect(lookUp(trie, hostname)).to.eql("a");
103
- });
104
- it("still handles wildcards correctly if there are non-matching exceptions", () => {
105
- const trie = new Map();
106
- const trieA = new Map();
107
- const hostname = "c.b.a";
108
-
109
- trieA.set("*", true);
110
- trieA.set("!a", true);
111
- trieA.set("!c", true);
112
- trie.set("a", trieA);
113
-
114
- expect(lookUp(trie, hostname)).to.eql("b.a");
115
- });
116
- });