@maze014/dom-fetch 1.0.2 → 1.0.3
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/README.md +16 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.js +18 -2
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/fetch.ts +11 -0
- package/src/index.ts +3 -1
- package/src/types.ts +2 -1
- package/src/validations.ts +8 -1
package/README.md
CHANGED
|
@@ -46,6 +46,21 @@ const elements = await selectElements(
|
|
|
46
46
|
{ source: "file" }
|
|
47
47
|
);
|
|
48
48
|
```
|
|
49
|
+
---
|
|
50
|
+
|
|
51
|
+
### Fetch from runtime string
|
|
52
|
+
```ts
|
|
53
|
+
const html = "<!DOCTYPE html>" +`
|
|
54
|
+
<html>
|
|
55
|
+
<body>
|
|
56
|
+
<a class='article'>Click here<a/>
|
|
57
|
+
</body>
|
|
58
|
+
</html>`;
|
|
59
|
+
|
|
60
|
+
const elements = await selectElements(
|
|
61
|
+
html, ".article", { source: "string" }
|
|
62
|
+
);
|
|
63
|
+
```
|
|
49
64
|
|
|
50
65
|
---
|
|
51
66
|
|
|
@@ -78,7 +93,7 @@ The `output` option controls how each matched element is returned.
|
|
|
78
93
|
{
|
|
79
94
|
tag: "a",
|
|
80
95
|
text: "Click here",
|
|
81
|
-
html: "Click here",
|
|
96
|
+
html: "<a>Click here</a>",
|
|
82
97
|
attributes: {
|
|
83
98
|
href: "/about",
|
|
84
99
|
class: "link"
|
package/dist/index.d.ts
CHANGED
|
@@ -10,8 +10,9 @@ type FetchOutput = "object" | "html" | "children" | "breakdown";
|
|
|
10
10
|
* Defines the kind of sourse to fetch from or read from
|
|
11
11
|
* file : the source should be a file defined by a relative path
|
|
12
12
|
* url : the source should be the response of a fetched resource through the HTTP GET method
|
|
13
|
+
* string : the source should be from a string read at runtime
|
|
13
14
|
*/
|
|
14
|
-
type FetchSource = "file" | "url";
|
|
15
|
+
type FetchSource = "file" | "url" | "string";
|
|
15
16
|
/**
|
|
16
17
|
* Defines how the request should work to fetch the element of a given source kind
|
|
17
18
|
*/
|
package/dist/index.js
CHANGED
|
@@ -28,7 +28,7 @@ var import_jsdom = require("jsdom");
|
|
|
28
28
|
|
|
29
29
|
// src/constants.ts
|
|
30
30
|
var HTML_CONTENT_TYPE = "text/html";
|
|
31
|
-
var VERSION = "1.0.
|
|
31
|
+
var VERSION = "1.0.2";
|
|
32
32
|
|
|
33
33
|
// src/validations.ts
|
|
34
34
|
var import_node_fs = require("fs");
|
|
@@ -43,7 +43,7 @@ function validateOutputOption(options) {
|
|
|
43
43
|
}
|
|
44
44
|
function validateSourceOption(options) {
|
|
45
45
|
const source = options.source;
|
|
46
|
-
if (!/^(?:url|file)$/.test(source)) {
|
|
46
|
+
if (!/^(?:url|file|string)$/.test(source)) {
|
|
47
47
|
throw `source option not supported ["${source}"]`;
|
|
48
48
|
}
|
|
49
49
|
return source;
|
|
@@ -66,6 +66,12 @@ async function validateFileExistance(source) {
|
|
|
66
66
|
}
|
|
67
67
|
return await (0, import_promises.readFile)(source, "utf-8");
|
|
68
68
|
}
|
|
69
|
+
async function validateDefinedString(source) {
|
|
70
|
+
if (source == null || source == void 0) {
|
|
71
|
+
throw new Error(`no content read from["${source}"]`);
|
|
72
|
+
}
|
|
73
|
+
return source;
|
|
74
|
+
}
|
|
69
75
|
|
|
70
76
|
// src/fetch.ts
|
|
71
77
|
async function _fromHttp(source, selector) {
|
|
@@ -86,6 +92,14 @@ var _fromFile = async (source, selector) => {
|
|
|
86
92
|
const document = dom.window.document;
|
|
87
93
|
return Array.from(document.querySelectorAll(selector));
|
|
88
94
|
};
|
|
95
|
+
var _fromString = async (html, selector) => {
|
|
96
|
+
html = await validateDefinedString(html);
|
|
97
|
+
const dom = new import_jsdom.JSDOM(html, {
|
|
98
|
+
contentType: HTML_CONTENT_TYPE
|
|
99
|
+
});
|
|
100
|
+
const document = dom.window.document;
|
|
101
|
+
return Array.from(document.querySelectorAll(selector));
|
|
102
|
+
};
|
|
89
103
|
|
|
90
104
|
// src/index.ts
|
|
91
105
|
async function selectElements(source, selector, options) {
|
|
@@ -97,6 +111,8 @@ async function selectElements(source, selector, options) {
|
|
|
97
111
|
nodes = await _fromHttp(source, selector);
|
|
98
112
|
} else if (sourceOption == "file") {
|
|
99
113
|
nodes = await _fromFile(source, selector);
|
|
114
|
+
} else if (sourceOption == "string") {
|
|
115
|
+
nodes = await _fromString(source, selector);
|
|
100
116
|
}
|
|
101
117
|
return nodes.map((el) => {
|
|
102
118
|
return _computed(el, fixedOptions);
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/fetch.ts","../src/constants.ts","../src/validations.ts"],"sourcesContent":["import { FetchOptions } from \"./types\";\nimport { _fromFile, _fromHttp } from \"./fetch\";\nimport { validateOutputOption, validateSourceOption } from \"./validations\";\n\n/**\n *\n * @param source References the source from where to fetch the DOM. It can be an a relative file path or an URL\n * @param selector The query selector used to fetch elements from the DOM. (will run querySelectorAll)\n * @param options The FetchOptions needed for the requested elements\n * @returns\n */\nexport async function selectElements(\n\tsource: string,\n\tselector: string,\n\toptions?: FetchOptions\n) {\n\ttry {\n\t\tlet nodes: Array<Element> = [];\n\t\tconst fixedOptions = _initOptions(options);\n\t\tconst sourceOption = validateSourceOption(fixedOptions);\n\n\t\tif (sourceOption == \"url\") {\n\t\t\tnodes = await _fromHttp(source, selector);\n\t\t} else if (sourceOption == \"file\") {\n\t\t\tnodes = await _fromFile(source, selector);\n\t\t}\n\n\t\treturn nodes.map((el) => {\n\t\t\treturn _computed(el, fixedOptions);\n\t\t});\n\t} catch (error: any) {\n\t\treturn Promise.reject(error);\n\t}\n}\n\n// ============================= PRIVATE functions =============================\n\nconst _initOptions = (options: any = {}) => {\n\tconst { output = \"html\", source = \"url\" } = options;\n\treturn { output, source } as FetchOptions;\n};\n\nconst _computed = (el: Element, options: FetchOptions) => {\n\tlet result: any;\n\tconst output = validateOutputOption(options);\n\n\tswitch (output) {\n\t\tcase \"html\":\n\t\tcase \"children\":\n\t\t\tif (output == \"html\") {\n\t\t\t\tresult = el.outerHTML;\n\t\t\t} else {\n\t\t\t\tresult = el.innerHTML;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase \"breakdown\":\n\t\t\tresult = {\n\t\t\t\ttag: el.tagName.toLowerCase(),\n\t\t\t\ttext: el.textContent?.trim() ?? \"\",\n\t\t\t\thtml: el.innerHTML,\n\t\t\t\tattributes: Object.fromEntries(\n\t\t\t\t\tArray.from(el.attributes).map((a) => [a.name, a.value])\n\t\t\t\t),\n\t\t\t};\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tresult = el;\n\t}\n\treturn result;\n};\n","import { JSDOM } from \"jsdom\";\nimport { HTML_CONTENT_TYPE } from \"./constants\";\nimport {\n\tvalidateFileExistance,\n\tvalidateResource,\n} from \"./validations\";\n\nexport async function _fromHttp(\n\tsource: string,\n\tselector: string\n): Promise<Element[]> {\n\tconst res = await validateResource(source);\n\n\tconst html = await res.text();\n\n\tconst dom = new JSDOM(html, {\n\t\turl: source,\n\t\tcontentType: HTML_CONTENT_TYPE,\n\t});\n\n\tconst document = dom.window.document;\n\n\treturn Array.from(document.querySelectorAll(selector));\n}\n\nexport const _fromFile = async (source: string, selector: string) => {\n\tlet html = await validateFileExistance(source);\n\n\tconst dom = new JSDOM(html, {\n\t\tcontentType: HTML_CONTENT_TYPE,\n\t});\n\n\tconst document = dom.window.document;\n\treturn Array.from(document.querySelectorAll(selector));\n};\n","export const PACKAGE_ERROR_INTRO = \"Fetch-Dom error : \"\nexport const HTML_CONTENT_TYPE = \"text/html\";\nexport const VERSION = __VERSION__;","import { existsSync } from \"node:fs\";\nimport { VERSION } from \"./constants\";\nimport { FetchOptions } from \"./types\";\nimport { readFile } from \"node:fs/promises\";\n\nconst UA = `@maze014/dom-fetch/${VERSION}`;\n\nexport function validateOutputOption(options: FetchOptions) {\n\tconst output = options.output;\n\tif (!/^(?:object|html|children|breakdown)$/.test(output)) {\n\t\tthrow `output option not supported [\"${output}\"]`;\n\t}\n\treturn output;\n}\n\nexport function validateSourceOption(options: FetchOptions) {\n\tconst source = options.source;\n\tif (!/^(?:url|file)$/.test(source)) {\n\t\tthrow `source option not supported [\"${source}\"]`;\n\t}\n\treturn source;\n}\n\nexport function validateHTTPSource(source: string) {\n\tif (!source.startsWith(\"http\")) {\n\t\tthrow \"source given is not an URL\";\n\t}\n}\n\nexport async function validateResource(source: string) {\n\tconst res = await fetch(source, {\n\t\theaders: {\n\t\t\t\"User-Agent\": UA,\n\t\t\tAccept: \"text/html\",\n\t\t},\n\t});\n\n\tif (!res.ok) {\n\t\tthrow new Error(`Failed to fetch ${source}`);\n\t}\n\treturn res;\n}\n\nexport async function validateFileExistance(source: string) {\n\tif (!existsSync(source)) {\n\t\tthrow new Error(`no such file [\"${source}\"]`);\n\t}\n\treturn await readFile(source, \"utf-8\");\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACAA,mBAAsB;;;ACCf,IAAM,oBAAoB;AAC1B,IAAM,UAAU;;;ACFvB,qBAA2B;AAG3B,sBAAyB;AAEzB,IAAM,KAAK,sBAAsB,OAAO;AAEjC,SAAS,qBAAqB,SAAuB;AAC3D,QAAM,SAAS,QAAQ;AACvB,MAAI,CAAC,uCAAuC,KAAK,MAAM,GAAG;AACzD,UAAM,iCAAiC,MAAM;AAAA,EAC9C;AACA,SAAO;AACR;AAEO,SAAS,qBAAqB,SAAuB;AAC3D,QAAM,SAAS,QAAQ;AACvB,MAAI,CAAC,
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/fetch.ts","../src/constants.ts","../src/validations.ts"],"sourcesContent":["import { FetchOptions } from \"./types\";\nimport { _fromFile, _fromHttp, _fromString } from \"./fetch\";\nimport { validateOutputOption, validateSourceOption } from \"./validations\";\n\n/**\n *\n * @param source References the source from where to fetch the DOM. It can be an a relative file path or an URL\n * @param selector The query selector used to fetch elements from the DOM. (will run querySelectorAll)\n * @param options The FetchOptions needed for the requested elements\n * @returns\n */\nexport async function selectElements(\n\tsource: string,\n\tselector: string,\n\toptions?: FetchOptions\n) {\n\ttry {\n\t\tlet nodes: Array<Element> = [];\n\t\tconst fixedOptions = _initOptions(options);\n\t\tconst sourceOption = validateSourceOption(fixedOptions);\n\n\t\tif (sourceOption == \"url\") {\n\t\t\tnodes = await _fromHttp(source, selector);\n\t\t} else if (sourceOption == \"file\") {\n\t\t\tnodes = await _fromFile(source, selector);\n\t\t} else if (sourceOption == \"string\") {\n\t\t\tnodes = await _fromString(source, selector);\n\t\t}\n\n\t\treturn nodes.map((el) => {\n\t\t\treturn _computed(el, fixedOptions);\n\t\t});\n\t} catch (error: any) {\n\t\treturn Promise.reject(error);\n\t}\n}\n\n// ============================= PRIVATE functions =============================\n\nconst _initOptions = (options: any = {}) => {\n\tconst { output = \"html\", source = \"url\" } = options;\n\treturn { output, source } as FetchOptions;\n};\n\nconst _computed = (el: Element, options: FetchOptions) => {\n\tlet result: any;\n\tconst output = validateOutputOption(options);\n\n\tswitch (output) {\n\t\tcase \"html\":\n\t\tcase \"children\":\n\t\t\tif (output == \"html\") {\n\t\t\t\tresult = el.outerHTML;\n\t\t\t} else {\n\t\t\t\tresult = el.innerHTML;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase \"breakdown\":\n\t\t\tresult = {\n\t\t\t\ttag: el.tagName.toLowerCase(),\n\t\t\t\ttext: el.textContent?.trim() ?? \"\",\n\t\t\t\thtml: el.innerHTML,\n\t\t\t\tattributes: Object.fromEntries(\n\t\t\t\t\tArray.from(el.attributes).map((a) => [a.name, a.value])\n\t\t\t\t),\n\t\t\t};\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tresult = el;\n\t}\n\treturn result;\n};\n","import { JSDOM } from \"jsdom\";\nimport { HTML_CONTENT_TYPE } from \"./constants\";\nimport {\n\tvalidateDefinedString,\n\tvalidateFileExistance,\n\tvalidateResource,\n} from \"./validations\";\n\nexport async function _fromHttp(\n\tsource: string,\n\tselector: string\n): Promise<Element[]> {\n\tconst res = await validateResource(source);\n\n\tconst html = await res.text();\n\n\tconst dom = new JSDOM(html, {\n\t\turl: source,\n\t\tcontentType: HTML_CONTENT_TYPE,\n\t});\n\n\tconst document = dom.window.document;\n\n\treturn Array.from(document.querySelectorAll(selector));\n}\n\nexport const _fromFile = async (source: string, selector: string) => {\n\tlet html = await validateFileExistance(source);\n\n\tconst dom = new JSDOM(html, {\n\t\tcontentType: HTML_CONTENT_TYPE,\n\t});\n\n\tconst document = dom.window.document;\n\treturn Array.from(document.querySelectorAll(selector));\n};\n\nexport const _fromString = async (html: string, selector: string) => {\n\thtml = await validateDefinedString(html);\n\tconst dom = new JSDOM(html, {\n\t\tcontentType: HTML_CONTENT_TYPE,\n\t});\n\n\tconst document = dom.window.document;\n\treturn Array.from(document.querySelectorAll(selector));\n};\n","export const PACKAGE_ERROR_INTRO = \"Fetch-Dom error : \"\nexport const HTML_CONTENT_TYPE = \"text/html\";\nexport const VERSION = __VERSION__;","import { existsSync } from \"node:fs\";\nimport { VERSION } from \"./constants\";\nimport { FetchOptions } from \"./types\";\nimport { readFile } from \"node:fs/promises\";\n\nconst UA = `@maze014/dom-fetch/${VERSION}`;\n\nexport function validateOutputOption(options: FetchOptions) {\n\tconst output = options.output;\n\tif (!/^(?:object|html|children|breakdown)$/.test(output)) {\n\t\tthrow `output option not supported [\"${output}\"]`;\n\t}\n\treturn output;\n}\n\nexport function validateSourceOption(options: FetchOptions) {\n\tconst source = options.source;\n\tif (!/^(?:url|file|string)$/.test(source)) {\n\t\tthrow `source option not supported [\"${source}\"]`;\n\t}\n\treturn source;\n}\n\nexport function validateHTTPSource(source: string) {\n\tif (!source.startsWith(\"http\")) {\n\t\tthrow \"source given is not an URL\";\n\t}\n}\n\nexport async function validateResource(source: string) {\n\tconst res = await fetch(source, {\n\t\theaders: {\n\t\t\t\"User-Agent\": UA,\n\t\t\tAccept: \"text/html\",\n\t\t},\n\t});\n\n\tif (!res.ok) {\n\t\tthrow new Error(`Failed to fetch ${source}`);\n\t}\n\treturn res;\n}\n\nexport async function validateFileExistance(source: string) {\n\tif (!existsSync(source)) {\n\t\tthrow new Error(`no such file [\"${source}\"]`);\n\t}\n\treturn await readFile(source, \"utf-8\");\n}\n\nexport async function validateDefinedString(source: string) {\n\tif (source == null || source == undefined) {\n\t\tthrow new Error(`no content read from[\"${source}\"]`);\n\t}\n\treturn source;\n}\n"],"mappings":"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","names":[]}
|
package/package.json
CHANGED
package/src/fetch.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { JSDOM } from "jsdom";
|
|
2
2
|
import { HTML_CONTENT_TYPE } from "./constants";
|
|
3
3
|
import {
|
|
4
|
+
validateDefinedString,
|
|
4
5
|
validateFileExistance,
|
|
5
6
|
validateResource,
|
|
6
7
|
} from "./validations";
|
|
@@ -33,3 +34,13 @@ export const _fromFile = async (source: string, selector: string) => {
|
|
|
33
34
|
const document = dom.window.document;
|
|
34
35
|
return Array.from(document.querySelectorAll(selector));
|
|
35
36
|
};
|
|
37
|
+
|
|
38
|
+
export const _fromString = async (html: string, selector: string) => {
|
|
39
|
+
html = await validateDefinedString(html);
|
|
40
|
+
const dom = new JSDOM(html, {
|
|
41
|
+
contentType: HTML_CONTENT_TYPE,
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
const document = dom.window.document;
|
|
45
|
+
return Array.from(document.querySelectorAll(selector));
|
|
46
|
+
};
|
package/src/index.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { FetchOptions } from "./types";
|
|
2
|
-
import { _fromFile, _fromHttp } from "./fetch";
|
|
2
|
+
import { _fromFile, _fromHttp, _fromString } from "./fetch";
|
|
3
3
|
import { validateOutputOption, validateSourceOption } from "./validations";
|
|
4
4
|
|
|
5
5
|
/**
|
|
@@ -23,6 +23,8 @@ export async function selectElements(
|
|
|
23
23
|
nodes = await _fromHttp(source, selector);
|
|
24
24
|
} else if (sourceOption == "file") {
|
|
25
25
|
nodes = await _fromFile(source, selector);
|
|
26
|
+
} else if (sourceOption == "string") {
|
|
27
|
+
nodes = await _fromString(source, selector);
|
|
26
28
|
}
|
|
27
29
|
|
|
28
30
|
return nodes.map((el) => {
|
package/src/types.ts
CHANGED
|
@@ -12,8 +12,9 @@ export type FetchOutput = "object" | "html" | "children" | "breakdown";
|
|
|
12
12
|
* Defines the kind of sourse to fetch from or read from
|
|
13
13
|
* file : the source should be a file defined by a relative path
|
|
14
14
|
* url : the source should be the response of a fetched resource through the HTTP GET method
|
|
15
|
+
* string : the source should be from a string read at runtime
|
|
15
16
|
*/
|
|
16
|
-
export type FetchSource = "file" | "url";
|
|
17
|
+
export type FetchSource = "file" | "url" | "string";
|
|
17
18
|
|
|
18
19
|
/**
|
|
19
20
|
* Defines how the request should work to fetch the element of a given source kind
|
package/src/validations.ts
CHANGED
|
@@ -15,7 +15,7 @@ export function validateOutputOption(options: FetchOptions) {
|
|
|
15
15
|
|
|
16
16
|
export function validateSourceOption(options: FetchOptions) {
|
|
17
17
|
const source = options.source;
|
|
18
|
-
if (!/^(?:url|file)$/.test(source)) {
|
|
18
|
+
if (!/^(?:url|file|string)$/.test(source)) {
|
|
19
19
|
throw `source option not supported ["${source}"]`;
|
|
20
20
|
}
|
|
21
21
|
return source;
|
|
@@ -47,3 +47,10 @@ export async function validateFileExistance(source: string) {
|
|
|
47
47
|
}
|
|
48
48
|
return await readFile(source, "utf-8");
|
|
49
49
|
}
|
|
50
|
+
|
|
51
|
+
export async function validateDefinedString(source: string) {
|
|
52
|
+
if (source == null || source == undefined) {
|
|
53
|
+
throw new Error(`no content read from["${source}"]`);
|
|
54
|
+
}
|
|
55
|
+
return source;
|
|
56
|
+
}
|