stack-analyze 1.1.9 → 1.2.0
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/CHANGELOG.md +9 -0
- package/cli.js +17 -16
- package/functions/animeInfo.js +9 -9
- package/functions/gitUser.js +13 -13
- package/functions/password.js +25 -0
- package/index.cjs +85 -74
- package/index.mjs +81 -64
- package/package.json +10 -10
- package/readme.md +27 -4
- package/demo.js +0 -20
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,15 @@
|
|
|
2
2
|
|
|
3
3
|
stack-analyze all version and notable changes, fixed, remove and new additions in code.
|
|
4
4
|
|
|
5
|
+
## version 1.2.0
|
|
6
|
+
### Added
|
|
7
|
+
- new tool password generator
|
|
8
|
+
### fixed
|
|
9
|
+
- update anime search tool
|
|
10
|
+
- the files modules now using callbacks and remove no using vars
|
|
11
|
+
### change
|
|
12
|
+
- the web scraping tool decided to use the question returns to the main menu instead of going to the main menu
|
|
13
|
+
|
|
5
14
|
## version 1.1.9
|
|
6
15
|
### Added
|
|
7
16
|
- new module cheerio
|
package/cli.js
CHANGED
|
@@ -20,6 +20,7 @@ import bitlyInfo from "./functions/bitly.js";
|
|
|
20
20
|
import movieDB from "./functions/moviesInfo.js";
|
|
21
21
|
import twitchInfo from "./functions/twitch.js";
|
|
22
22
|
import scrape from "./functions/scraping.js";
|
|
23
|
+
import genPassword from "./functions/password.js";
|
|
23
24
|
|
|
24
25
|
/**
|
|
25
26
|
* @description web scraping menu
|
|
@@ -56,48 +57,42 @@ async function scrapingOpts (url) {
|
|
|
56
57
|
table_data,
|
|
57
58
|
table_heading
|
|
58
59
|
} = scrape(url);
|
|
60
|
+
|
|
61
|
+
const timeScrape = 2000;
|
|
59
62
|
|
|
60
63
|
/** @type {Object.<string, function(): void>} */
|
|
61
64
|
const scrapeOpt = {
|
|
62
65
|
pageTitle() {
|
|
63
66
|
title();
|
|
64
|
-
|
|
65
|
-
setTimeout(question, timeScrape);
|
|
67
|
+
setTimeout(returnQuestion, timeScrape);
|
|
66
68
|
},
|
|
67
69
|
pageImages() {
|
|
68
70
|
images();
|
|
69
|
-
|
|
70
|
-
setTimeout(question, timeScrape);
|
|
71
|
+
setTimeout(returnQuestion, timeScrape);
|
|
71
72
|
},
|
|
72
73
|
pageMetadata() {
|
|
73
74
|
metadata();
|
|
74
|
-
|
|
75
|
-
setTimeout(question, timeScrape);
|
|
75
|
+
setTimeout(returnQuestion, timeScrape);
|
|
76
76
|
},
|
|
77
77
|
pageHeadings() {
|
|
78
78
|
headings();
|
|
79
|
-
|
|
80
|
-
setTimeout(question, timeScrape);
|
|
79
|
+
setTimeout(returnQuestion, timeScrape);
|
|
81
80
|
},
|
|
82
81
|
pageTableHead() {
|
|
83
82
|
table_heading();
|
|
84
|
-
|
|
85
|
-
setTimeout(question, timeScrape);
|
|
83
|
+
setTimeout(returnQuestion, timeScrape);
|
|
86
84
|
},
|
|
87
85
|
pageTableData() {
|
|
88
86
|
table_data();
|
|
89
|
-
|
|
90
|
-
setTimeout(question, timeScrape);
|
|
87
|
+
setTimeout(returnQuestion, timeScrape);
|
|
91
88
|
},
|
|
92
89
|
pageLinks() {
|
|
93
90
|
links();
|
|
94
|
-
|
|
95
|
-
setTimeout(question, timeScrape);
|
|
91
|
+
setTimeout(returnQuestion, timeScrape);
|
|
96
92
|
},
|
|
97
93
|
pageCites() {
|
|
98
94
|
cites();
|
|
99
|
-
|
|
100
|
-
setTimeout(question, timeScrape);
|
|
95
|
+
setTimeout(returnQuestion, timeScrape);
|
|
101
96
|
},
|
|
102
97
|
};
|
|
103
98
|
|
|
@@ -277,6 +272,11 @@ const toolsOpts = {
|
|
|
277
272
|
cryptoMarket();
|
|
278
273
|
setTimeout(returnQuestion, 5000);
|
|
279
274
|
},
|
|
275
|
+
password() {
|
|
276
|
+
console.clear();
|
|
277
|
+
genPassword();
|
|
278
|
+
setTimeout(returnQuestion, 3000);
|
|
279
|
+
},
|
|
280
280
|
bitly_info() {
|
|
281
281
|
console.clear();
|
|
282
282
|
inquirer.prompt([
|
|
@@ -402,6 +402,7 @@ async function question() {
|
|
|
402
402
|
"twitch_info",
|
|
403
403
|
"hardware tools",
|
|
404
404
|
"scraping",
|
|
405
|
+
"password",
|
|
405
406
|
"about",
|
|
406
407
|
"exit"
|
|
407
408
|
]
|
package/functions/animeInfo.js
CHANGED
|
@@ -15,26 +15,26 @@ const animeSearch = async (query) => {
|
|
|
15
15
|
/* error manager */
|
|
16
16
|
try {
|
|
17
17
|
// call api
|
|
18
|
-
const { data } = await axios.get("https://api.jikan.moe/
|
|
18
|
+
const { data } = await axios.get("https://api.jikan.moe/v4/anime", {
|
|
19
19
|
params: {
|
|
20
20
|
q: query,
|
|
21
21
|
limit: 10
|
|
22
22
|
}
|
|
23
23
|
});
|
|
24
24
|
|
|
25
|
-
const animeData = data.
|
|
25
|
+
const animeData = data.data.map(({
|
|
26
26
|
title,
|
|
27
27
|
episodes,
|
|
28
|
-
|
|
29
|
-
|
|
28
|
+
aired,
|
|
29
|
+
status,
|
|
30
30
|
type }) => ({
|
|
31
31
|
title,
|
|
32
32
|
type,
|
|
33
|
-
episodes,
|
|
34
|
-
debutDate: format(
|
|
35
|
-
finalDate:
|
|
36
|
-
? format(
|
|
37
|
-
:
|
|
33
|
+
totalEpisodes: episodes ?? 1,
|
|
34
|
+
debutDate: format(aired.from),
|
|
35
|
+
finalDate: aired.to !== null
|
|
36
|
+
? format(aired.to)
|
|
37
|
+
: status
|
|
38
38
|
}));
|
|
39
39
|
|
|
40
40
|
|
package/functions/gitUser.js
CHANGED
|
@@ -12,25 +12,25 @@ import colors from "colors";
|
|
|
12
12
|
*/
|
|
13
13
|
export default async function githubInfo(user) {
|
|
14
14
|
try {
|
|
15
|
-
const
|
|
15
|
+
const { data, status } = await axios.get(`https://api.github.com/users/${user}`);
|
|
16
16
|
|
|
17
|
-
if (
|
|
17
|
+
if (status !== 404){
|
|
18
18
|
const info = {
|
|
19
|
-
username:
|
|
20
|
-
fullName:
|
|
21
|
-
Email:
|
|
22
|
-
userFollowers:
|
|
23
|
-
userFollowing:
|
|
24
|
-
accountAge: format(
|
|
25
|
-
updated_info: format(
|
|
26
|
-
twitter:
|
|
27
|
-
repos:
|
|
28
|
-
gists:
|
|
19
|
+
username: data.login,
|
|
20
|
+
fullName: data.name === null ? "no info": data.name,
|
|
21
|
+
Email: data.email === null ? "no info": data.email,
|
|
22
|
+
userFollowers: data.followers,
|
|
23
|
+
userFollowing: data.following,
|
|
24
|
+
accountAge: format(data.created_at),
|
|
25
|
+
updated_info: format(data.updated_at),
|
|
26
|
+
twitter: data.twitter_username === null ? "no info": data.twitter_username,
|
|
27
|
+
repos: data.public_repos,
|
|
28
|
+
gists: data.public_gists
|
|
29
29
|
};
|
|
30
30
|
|
|
31
31
|
console.table(info);
|
|
32
32
|
} else {
|
|
33
|
-
console.info(colors.yellow(
|
|
33
|
+
console.info(colors.yellow(""+status));
|
|
34
34
|
}
|
|
35
35
|
} catch(err) {
|
|
36
36
|
console.error(colors.red(err.message));
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import colors from "colors";
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
*
|
|
5
|
+
* @description generate a new password
|
|
6
|
+
* @returns { void }
|
|
7
|
+
*/
|
|
8
|
+
const genPassword = () => {
|
|
9
|
+
const chars = "0123456789abcdefghijklmnopqrstuvwxyz!@#$%^&*()ABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
|
10
|
+
|
|
11
|
+
// blank password var
|
|
12
|
+
let password = "";
|
|
13
|
+
|
|
14
|
+
// loop generate chars
|
|
15
|
+
for(let i = 0; i < 12; i++) {
|
|
16
|
+
const randomNumber = Math.floor(Math.random() * chars.length);
|
|
17
|
+
|
|
18
|
+
password += chars.substring(randomNumber, randomNumber + 1);
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
// print new passwors
|
|
22
|
+
console.info(colors.yellow("new password:"), password);
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
export default genPassword;
|
package/index.cjs
CHANGED
|
@@ -9,13 +9,13 @@ const {
|
|
|
9
9
|
bios
|
|
10
10
|
} = require("systeminformation");
|
|
11
11
|
const Wappalyzer = require("wappalyzer");
|
|
12
|
-
const
|
|
12
|
+
const cheerio = require("cheerio");
|
|
13
13
|
|
|
14
|
-
const animeSearch = async ({ query, results }) => {
|
|
14
|
+
const animeSearch = async ({ query, results, failed }) => {
|
|
15
15
|
/* error manager */
|
|
16
16
|
try {
|
|
17
17
|
// call api
|
|
18
|
-
const { data } = await axios.get("https://api.jikan.moe/
|
|
18
|
+
const { data } = await axios.get("https://api.jikan.moe/v/anime", {
|
|
19
19
|
params: {
|
|
20
20
|
q: query,
|
|
21
21
|
limit: 10
|
|
@@ -24,10 +24,10 @@ const animeSearch = async ({ query, results }) => {
|
|
|
24
24
|
|
|
25
25
|
results(data.results);
|
|
26
26
|
|
|
27
|
-
} catch (err) {
|
|
27
|
+
} catch (err) { failed(err); }
|
|
28
28
|
};
|
|
29
29
|
|
|
30
|
-
const bitlyInfo = async ({ link, token, results }) => {
|
|
30
|
+
const bitlyInfo = async ({ link, token, results, failed }) => {
|
|
31
31
|
try {
|
|
32
32
|
const { data } = await axios.post(
|
|
33
33
|
"https://api-ssl.bitly.com/v4/expand",
|
|
@@ -43,38 +43,32 @@ const bitlyInfo = async ({ link, token, results }) => {
|
|
|
43
43
|
);
|
|
44
44
|
|
|
45
45
|
results(data);
|
|
46
|
-
} catch (err) {
|
|
46
|
+
} catch (err) { failed(err); }
|
|
47
47
|
};
|
|
48
48
|
|
|
49
|
-
|
|
50
|
-
*
|
|
51
|
-
* @descripiton call the crypto market list
|
|
52
|
-
* @param {function(any): void} callback
|
|
53
|
-
* @returns { Promise<void> } - return results search
|
|
54
|
-
*/
|
|
55
|
-
const cryptoMarket = async (callback) => {
|
|
49
|
+
const cryptoMarket = async ({results, failed}) => {
|
|
56
50
|
try {
|
|
57
51
|
// start crypto
|
|
58
52
|
const { data } = await axios.get(
|
|
59
53
|
"https://api.coingecko.com/api/v3/coins/markets", {
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
54
|
+
params: {
|
|
55
|
+
vs_currency: "usd",
|
|
56
|
+
per_page: 10
|
|
57
|
+
}
|
|
63
58
|
}
|
|
64
|
-
}
|
|
65
59
|
);
|
|
66
60
|
|
|
67
61
|
// map coinData
|
|
68
|
-
|
|
69
|
-
} catch (err) {
|
|
62
|
+
results(data);
|
|
63
|
+
} catch (err) { failed(err); }
|
|
70
64
|
};
|
|
71
65
|
|
|
72
|
-
async function githubInfo({ user, results }) {
|
|
66
|
+
async function githubInfo({ user, results, failed }) {
|
|
73
67
|
try {
|
|
74
68
|
const { data } = await axios.get(`https://api.github.com/users/${user}`);
|
|
75
69
|
|
|
76
70
|
results(data);
|
|
77
|
-
} catch (err) {
|
|
71
|
+
} catch (err) { failed(err); }
|
|
78
72
|
}
|
|
79
73
|
|
|
80
74
|
async function cpuInfo(callback) {
|
|
@@ -232,7 +226,7 @@ async function biosInfo(callback) {
|
|
|
232
226
|
} catch (err) { callback(err); }
|
|
233
227
|
}
|
|
234
228
|
|
|
235
|
-
const movieDB = async ({ api_key, query, results }) => {
|
|
229
|
+
const movieDB = async ({ api_key, query, results, failed }) => {
|
|
236
230
|
try {
|
|
237
231
|
const { data } = await axios.get("https://api.themoviedb.org/3/search/movie", {
|
|
238
232
|
params: {
|
|
@@ -266,10 +260,10 @@ const movieDB = async ({ api_key, query, results }) => {
|
|
|
266
260
|
.filter(({ release_date }) => release_date !== undefined && release_date !== "");
|
|
267
261
|
|
|
268
262
|
results(movieData);
|
|
269
|
-
} catch (err) {
|
|
263
|
+
} catch (err) { failed(err); }
|
|
270
264
|
};
|
|
271
265
|
|
|
272
|
-
async function multipleStack({ urls, results }) {
|
|
266
|
+
async function multipleStack({ urls, results, failed }) {
|
|
273
267
|
let result;
|
|
274
268
|
const wappalyzer = new Wappalyzer();
|
|
275
269
|
try {
|
|
@@ -283,12 +277,12 @@ async function multipleStack({ urls, results }) {
|
|
|
283
277
|
};
|
|
284
278
|
})
|
|
285
279
|
);
|
|
286
|
-
|
|
280
|
+
results(result);
|
|
281
|
+
} catch (err) { failed(err); }
|
|
287
282
|
await wappalyzer.destroy();
|
|
288
|
-
results(result);
|
|
289
283
|
}
|
|
290
284
|
|
|
291
|
-
const pageSpeed = async ({ url, results }) => {
|
|
285
|
+
const pageSpeed = async ({ url, results, failed }) => {
|
|
292
286
|
try {
|
|
293
287
|
const resMobile = await axios.get("https://www.googleapis.com/pagespeedonline/v5/runPagespeed", {
|
|
294
288
|
params: {
|
|
@@ -311,10 +305,10 @@ const pageSpeed = async ({ url, results }) => {
|
|
|
311
305
|
const desktop = Math.round(resDesktop.data.lighthouseResult.categories.performance.score * 100);
|
|
312
306
|
|
|
313
307
|
results({ mobile, desktop });
|
|
314
|
-
} catch (err) {
|
|
308
|
+
} catch (err) { failed(err); }
|
|
315
309
|
};
|
|
316
310
|
|
|
317
|
-
async function singleStack({ url, results }) {
|
|
311
|
+
async function singleStack({ url, results, failed }) {
|
|
318
312
|
const wappalyzer = await new Wappalyzer;
|
|
319
313
|
|
|
320
314
|
let result;
|
|
@@ -332,13 +326,13 @@ async function singleStack({ url, results }) {
|
|
|
332
326
|
techWebsite: website,
|
|
333
327
|
techCategories: categories.map(({ name }) => name).join(", ")
|
|
334
328
|
}));
|
|
335
|
-
|
|
329
|
+
results(result);
|
|
330
|
+
} catch (err) { failed(err); }
|
|
336
331
|
|
|
337
332
|
await wappalyzer.destroy();
|
|
338
|
-
results(result);
|
|
339
333
|
}
|
|
340
334
|
|
|
341
|
-
async function twitchInfo({ query, token, clientID, results }) {
|
|
335
|
+
async function twitchInfo({ query, token, clientID, results, failed }) {
|
|
342
336
|
try {
|
|
343
337
|
const { data: twitchData } = await axios.get(`https://api.twitch.tv/helix/users?login=${query}`,
|
|
344
338
|
{
|
|
@@ -349,7 +343,7 @@ async function twitchInfo({ query, token, clientID, results }) {
|
|
|
349
343
|
});
|
|
350
344
|
|
|
351
345
|
results(twitchData.data);
|
|
352
|
-
} catch (err) {
|
|
346
|
+
} catch (err) { failed(err); }
|
|
353
347
|
}
|
|
354
348
|
|
|
355
349
|
function scrape(url) {
|
|
@@ -359,33 +353,33 @@ function scrape(url) {
|
|
|
359
353
|
baseURL: url
|
|
360
354
|
});
|
|
361
355
|
|
|
362
|
-
const title = async (
|
|
356
|
+
const title = async ({results, failed}) => {
|
|
363
357
|
try {
|
|
364
|
-
const { data } = await scraping.get(
|
|
365
|
-
$ = load(data);
|
|
358
|
+
const { data } = await scraping.get(url);
|
|
359
|
+
$ = cheerio.load(data);
|
|
366
360
|
|
|
367
|
-
|
|
368
|
-
} catch (err) {
|
|
361
|
+
results($("title").text());
|
|
362
|
+
} catch (err) { failed(err); }
|
|
369
363
|
};
|
|
370
364
|
|
|
371
|
-
const images = async (
|
|
365
|
+
const images = async ({results, failed}) => {
|
|
372
366
|
try {
|
|
373
|
-
const { data } = await scraping.get(
|
|
374
|
-
$ = load(data);
|
|
367
|
+
const { data } = await scraping.get(url);
|
|
368
|
+
$ = cheerio.load(data);
|
|
375
369
|
|
|
376
370
|
const imgs = $("img").map((i, el) => ({
|
|
377
371
|
imagePath: $(el).attr("src"),
|
|
378
372
|
imageTitle: $(el).attr("alt")
|
|
379
373
|
})).toArray();
|
|
380
374
|
|
|
381
|
-
|
|
382
|
-
} catch (err) {
|
|
375
|
+
results(imgs);
|
|
376
|
+
} catch (err) { failed(err); }
|
|
383
377
|
};
|
|
384
378
|
|
|
385
|
-
const metadata = async (
|
|
379
|
+
const metadata = async ({results, failed}) => {
|
|
386
380
|
try {
|
|
387
|
-
const { data } = await scraping.get(
|
|
388
|
-
$ = load(data);
|
|
381
|
+
const { data } = await scraping.get(url);
|
|
382
|
+
$ = cheerio.load(data);
|
|
389
383
|
|
|
390
384
|
const metadataList = $("meta").map((i, el) => ({
|
|
391
385
|
metaInfo: $(el).attr("name"),
|
|
@@ -393,54 +387,54 @@ function scrape(url) {
|
|
|
393
387
|
})).toArray()
|
|
394
388
|
.filter(({ metaInfo }) => metaInfo !== undefined);
|
|
395
389
|
|
|
396
|
-
|
|
397
|
-
} catch (err) {
|
|
390
|
+
results(metadataList);
|
|
391
|
+
} catch (err) { failed(err); }
|
|
398
392
|
};
|
|
399
393
|
|
|
400
|
-
const headings = async (
|
|
394
|
+
const headings = async ({results, failed}) => {
|
|
401
395
|
try {
|
|
402
|
-
const { data } = await scraping.get(
|
|
403
|
-
$ = load(data);
|
|
396
|
+
const { data } = await scraping.get(url);
|
|
397
|
+
$ = cheerio.load(data);
|
|
404
398
|
|
|
405
399
|
const headingList = $("h1, h2, h3, h4, h5, h6").map((i, el) => ({
|
|
406
400
|
headingTag: $(el).prop("tagName"),
|
|
407
401
|
headingText: $(el).text()
|
|
408
402
|
})).toArray();
|
|
409
403
|
|
|
410
|
-
|
|
411
|
-
} catch (err) {
|
|
404
|
+
results(headingList);
|
|
405
|
+
} catch (err) { failed(err); }
|
|
412
406
|
};
|
|
413
407
|
|
|
414
|
-
const table_heading = async (
|
|
408
|
+
const table_heading = async ({results, failed}) => {
|
|
415
409
|
try {
|
|
416
|
-
const { data } = await scraping.get(
|
|
417
|
-
$ = load(data);
|
|
410
|
+
const { data } = await scraping.get(url);
|
|
411
|
+
$ = cheerio.load(data);
|
|
418
412
|
|
|
419
413
|
const tableHeadList = $("th").map((i, el) => ({
|
|
420
414
|
headingRow: i,
|
|
421
415
|
text: $(el).text()
|
|
422
416
|
})).toArray();
|
|
423
417
|
|
|
424
|
-
|
|
425
|
-
} catch (err) {
|
|
418
|
+
results(tableHeadList);
|
|
419
|
+
} catch (err) { failed(err); }
|
|
426
420
|
};
|
|
427
421
|
|
|
428
|
-
const table_data = async (
|
|
422
|
+
const table_data = async ({results, failed}) => {
|
|
429
423
|
try {
|
|
430
|
-
const { data } = await scraping.get(
|
|
431
|
-
$ = load(data);
|
|
424
|
+
const { data } = await scraping.get(url);
|
|
425
|
+
$ = cheerio.load(data);
|
|
432
426
|
|
|
433
427
|
const tableColumnList = $("td").map((i, el) => $(el).text()).toArray();
|
|
434
428
|
|
|
435
|
-
|
|
436
|
-
} catch (err) {
|
|
429
|
+
results(tableColumnList);
|
|
430
|
+
} catch (err) { failed(err); }
|
|
437
431
|
};
|
|
438
432
|
|
|
439
433
|
|
|
440
|
-
const links = async (
|
|
434
|
+
const links = async ({results, failed}) => {
|
|
441
435
|
try {
|
|
442
|
-
const { data } = await scraping.get(
|
|
443
|
-
$ = load(data);
|
|
436
|
+
const { data } = await scraping.get(url);
|
|
437
|
+
$ = cheerio.load(data);
|
|
444
438
|
|
|
445
439
|
const linkList = $("a").map((i, el) => ({
|
|
446
440
|
url: $(el).attr("href"),
|
|
@@ -448,14 +442,14 @@ function scrape(url) {
|
|
|
448
442
|
})).toArray()
|
|
449
443
|
.filter(({ url }) => url.indexOf("#") !== 0);
|
|
450
444
|
|
|
451
|
-
|
|
452
|
-
} catch (err) {
|
|
445
|
+
results(linkList);
|
|
446
|
+
} catch (err) { failed(err); }
|
|
453
447
|
};
|
|
454
448
|
|
|
455
|
-
const cites = async (
|
|
449
|
+
const cites = async ({results, failed}) => {
|
|
456
450
|
try {
|
|
457
|
-
const { data } = await scraping.get(
|
|
458
|
-
$ = load(data);
|
|
451
|
+
const { data } = await scraping.get(url);
|
|
452
|
+
$ = cheerio.load(data);
|
|
459
453
|
|
|
460
454
|
const citeList = $("q, blockquote").map((i, el) => ({
|
|
461
455
|
citeTag: $(el).prop("tagName"),
|
|
@@ -463,8 +457,8 @@ function scrape(url) {
|
|
|
463
457
|
citeText: $(el).text()
|
|
464
458
|
})).toArray();
|
|
465
459
|
|
|
466
|
-
|
|
467
|
-
} catch (err) {
|
|
460
|
+
results(citeList);
|
|
461
|
+
} catch (err) { failed(err); }
|
|
468
462
|
};
|
|
469
463
|
|
|
470
464
|
return {
|
|
@@ -479,6 +473,22 @@ function scrape(url) {
|
|
|
479
473
|
};
|
|
480
474
|
}
|
|
481
475
|
|
|
476
|
+
const password = () => {
|
|
477
|
+
const chars = "0123456789abcdefghijklmnopqrstuvwxyz!@#$%^&*()ABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
|
478
|
+
|
|
479
|
+
// blank password var
|
|
480
|
+
let password = "";
|
|
481
|
+
|
|
482
|
+
// loop generate chars
|
|
483
|
+
for(let i = 0; i < 12; i++) {
|
|
484
|
+
const randomNumber = Math.floor(Math.random() * chars.length);
|
|
485
|
+
|
|
486
|
+
password += chars.substring(randomNumber, randomNumber + 1);
|
|
487
|
+
}
|
|
488
|
+
|
|
489
|
+
return password;
|
|
490
|
+
};
|
|
491
|
+
|
|
482
492
|
// exports
|
|
483
493
|
module.exports = {
|
|
484
494
|
animeSearch,
|
|
@@ -497,5 +507,6 @@ module.exports = {
|
|
|
497
507
|
pageSpeed,
|
|
498
508
|
singleStack,
|
|
499
509
|
twitchInfo,
|
|
500
|
-
scrape
|
|
510
|
+
scrape,
|
|
511
|
+
password
|
|
501
512
|
};
|
package/index.mjs
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
// modules
|
|
2
2
|
import {default as axios} from "axios";
|
|
3
|
-
import CoinGecko from "coingecko-api";
|
|
4
3
|
import {
|
|
5
4
|
cpu,
|
|
6
5
|
mem,
|
|
@@ -10,12 +9,13 @@ import {
|
|
|
10
9
|
bios
|
|
11
10
|
} from "systeminformation";
|
|
12
11
|
import Wappalyzer from "wappalyzer";
|
|
12
|
+
import cheerio from "cheerio";
|
|
13
13
|
|
|
14
|
-
const animeSearch = async ({ query, results }) => {
|
|
14
|
+
const animeSearch = async ({ query, results, failed }) => {
|
|
15
15
|
/* error manager */
|
|
16
16
|
try {
|
|
17
17
|
// call api
|
|
18
|
-
const { data } = await axios.get("https://api.jikan.moe/
|
|
18
|
+
const { data } = await axios.get("https://api.jikan.moe/v/anime", {
|
|
19
19
|
params: {
|
|
20
20
|
q: query,
|
|
21
21
|
limit: 10
|
|
@@ -24,10 +24,10 @@ const animeSearch = async ({ query, results }) => {
|
|
|
24
24
|
|
|
25
25
|
results(data.results);
|
|
26
26
|
|
|
27
|
-
} catch (err) {
|
|
27
|
+
} catch (err) { failed(err); }
|
|
28
28
|
};
|
|
29
29
|
|
|
30
|
-
const bitlyInfo = async ({ link, token, results }) => {
|
|
30
|
+
const bitlyInfo = async ({ link, token, results, failed }) => {
|
|
31
31
|
try {
|
|
32
32
|
const { data } = await axios.post(
|
|
33
33
|
"https://api-ssl.bitly.com/v4/expand",
|
|
@@ -43,10 +43,10 @@ const bitlyInfo = async ({ link, token, results }) => {
|
|
|
43
43
|
);
|
|
44
44
|
|
|
45
45
|
results(data);
|
|
46
|
-
} catch (err) {
|
|
46
|
+
} catch (err) { failed(err); }
|
|
47
47
|
};
|
|
48
48
|
|
|
49
|
-
const cryptoMarket = async (
|
|
49
|
+
const cryptoMarket = async ({results, failed}) => {
|
|
50
50
|
try {
|
|
51
51
|
// start crypto
|
|
52
52
|
const { data } = await axios.get(
|
|
@@ -59,16 +59,16 @@ const cryptoMarket = async (callback) => {
|
|
|
59
59
|
);
|
|
60
60
|
|
|
61
61
|
// map coinData
|
|
62
|
-
|
|
63
|
-
} catch (err) {
|
|
62
|
+
results(data);
|
|
63
|
+
} catch (err) { failed(err); }
|
|
64
64
|
};
|
|
65
65
|
|
|
66
|
-
async function githubInfo({ user, results }) {
|
|
66
|
+
async function githubInfo({ user, results, failed }) {
|
|
67
67
|
try {
|
|
68
68
|
const { data } = await axios.get(`https://api.github.com/users/${user}`);
|
|
69
69
|
|
|
70
70
|
results(data);
|
|
71
|
-
} catch (err) {
|
|
71
|
+
} catch (err) { failed(err); }
|
|
72
72
|
}
|
|
73
73
|
|
|
74
74
|
async function cpuInfo(callback) {
|
|
@@ -226,7 +226,7 @@ async function biosInfo(callback) {
|
|
|
226
226
|
} catch (err) { callback(err); }
|
|
227
227
|
}
|
|
228
228
|
|
|
229
|
-
const movieDB = async ({ api_key, query, results }) => {
|
|
229
|
+
const movieDB = async ({ api_key, query, results, failed }) => {
|
|
230
230
|
try {
|
|
231
231
|
const { data } = await axios.get("https://api.themoviedb.org/3/search/movie", {
|
|
232
232
|
params: {
|
|
@@ -260,10 +260,10 @@ const movieDB = async ({ api_key, query, results }) => {
|
|
|
260
260
|
.filter(({ release_date }) => release_date !== undefined && release_date !== "");
|
|
261
261
|
|
|
262
262
|
results(movieData);
|
|
263
|
-
} catch (err) {
|
|
263
|
+
} catch (err) { failed(err); }
|
|
264
264
|
};
|
|
265
265
|
|
|
266
|
-
async function multipleStack({ urls, results }) {
|
|
266
|
+
async function multipleStack({ urls, results, failed }) {
|
|
267
267
|
let result;
|
|
268
268
|
const wappalyzer = new Wappalyzer();
|
|
269
269
|
try {
|
|
@@ -277,12 +277,12 @@ async function multipleStack({ urls, results }) {
|
|
|
277
277
|
};
|
|
278
278
|
})
|
|
279
279
|
);
|
|
280
|
-
|
|
280
|
+
results(result);
|
|
281
|
+
} catch (err) { failed(err); }
|
|
281
282
|
await wappalyzer.destroy();
|
|
282
|
-
results(result);
|
|
283
283
|
}
|
|
284
284
|
|
|
285
|
-
const pageSpeed = async ({ url, results }) => {
|
|
285
|
+
const pageSpeed = async ({ url, results, failed }) => {
|
|
286
286
|
try {
|
|
287
287
|
const resMobile = await axios.get("https://www.googleapis.com/pagespeedonline/v5/runPagespeed", {
|
|
288
288
|
params: {
|
|
@@ -305,10 +305,10 @@ const pageSpeed = async ({ url, results }) => {
|
|
|
305
305
|
const desktop = Math.round(resDesktop.data.lighthouseResult.categories.performance.score * 100);
|
|
306
306
|
|
|
307
307
|
results({ mobile, desktop });
|
|
308
|
-
} catch (err) {
|
|
308
|
+
} catch (err) { failed(err); }
|
|
309
309
|
};
|
|
310
310
|
|
|
311
|
-
async function singleStack({ url, results }) {
|
|
311
|
+
async function singleStack({ url, results, failed }) {
|
|
312
312
|
const wappalyzer = await new Wappalyzer;
|
|
313
313
|
|
|
314
314
|
let result;
|
|
@@ -326,13 +326,13 @@ async function singleStack({ url, results }) {
|
|
|
326
326
|
techWebsite: website,
|
|
327
327
|
techCategories: categories.map(({ name }) => name).join(", ")
|
|
328
328
|
}));
|
|
329
|
-
|
|
329
|
+
results(result);
|
|
330
|
+
} catch (err) { failed(err); }
|
|
330
331
|
|
|
331
332
|
await wappalyzer.destroy();
|
|
332
|
-
results(result);
|
|
333
333
|
}
|
|
334
334
|
|
|
335
|
-
async function twitchInfo({ query, token, clientID, results }) {
|
|
335
|
+
async function twitchInfo({ query, token, clientID, results, failed }) {
|
|
336
336
|
try {
|
|
337
337
|
const { data: twitchData } = await axios.get(`https://api.twitch.tv/helix/users?login=${query}`,
|
|
338
338
|
{
|
|
@@ -343,7 +343,7 @@ async function twitchInfo({ query, token, clientID, results }) {
|
|
|
343
343
|
});
|
|
344
344
|
|
|
345
345
|
results(twitchData.data);
|
|
346
|
-
} catch (err) {
|
|
346
|
+
} catch (err) { failed(err); }
|
|
347
347
|
}
|
|
348
348
|
|
|
349
349
|
function scrape(url) {
|
|
@@ -353,33 +353,33 @@ function scrape(url) {
|
|
|
353
353
|
baseURL: url
|
|
354
354
|
});
|
|
355
355
|
|
|
356
|
-
const title = async (
|
|
356
|
+
const title = async ({results, failed}) => {
|
|
357
357
|
try {
|
|
358
|
-
const { data } = await scraping.get(
|
|
359
|
-
$ = load(data);
|
|
358
|
+
const { data } = await scraping.get(url);
|
|
359
|
+
$ = cheerio.load(data);
|
|
360
360
|
|
|
361
|
-
|
|
362
|
-
} catch (err) {
|
|
361
|
+
results($("title").text());
|
|
362
|
+
} catch (err) { failed(err); }
|
|
363
363
|
};
|
|
364
364
|
|
|
365
|
-
const images = async (
|
|
365
|
+
const images = async ({results, failed}) => {
|
|
366
366
|
try {
|
|
367
|
-
const { data } = await scraping.get(
|
|
368
|
-
$ = load(data);
|
|
367
|
+
const { data } = await scraping.get(url);
|
|
368
|
+
$ = cheerio.load(data);
|
|
369
369
|
|
|
370
370
|
const imgs = $("img").map((i, el) => ({
|
|
371
371
|
imagePath: $(el).attr("src"),
|
|
372
372
|
imageTitle: $(el).attr("alt")
|
|
373
373
|
})).toArray();
|
|
374
374
|
|
|
375
|
-
|
|
376
|
-
} catch (err) {
|
|
375
|
+
results(imgs);
|
|
376
|
+
} catch (err) { failed(err); }
|
|
377
377
|
};
|
|
378
378
|
|
|
379
|
-
const metadata = async (
|
|
379
|
+
const metadata = async ({results, failed}) => {
|
|
380
380
|
try {
|
|
381
|
-
const { data } = await scraping.get(
|
|
382
|
-
$ = load(data);
|
|
381
|
+
const { data } = await scraping.get(url);
|
|
382
|
+
$ = cheerio.load(data);
|
|
383
383
|
|
|
384
384
|
const metadataList = $("meta").map((i, el) => ({
|
|
385
385
|
metaInfo: $(el).attr("name"),
|
|
@@ -387,54 +387,54 @@ function scrape(url) {
|
|
|
387
387
|
})).toArray()
|
|
388
388
|
.filter(({ metaInfo }) => metaInfo !== undefined);
|
|
389
389
|
|
|
390
|
-
|
|
391
|
-
} catch (err) {
|
|
390
|
+
results(metadataList);
|
|
391
|
+
} catch (err) { failed(err); }
|
|
392
392
|
};
|
|
393
393
|
|
|
394
|
-
const headings = async (
|
|
394
|
+
const headings = async ({results, failed}) => {
|
|
395
395
|
try {
|
|
396
|
-
const { data } = await scraping.get(
|
|
397
|
-
$ = load(data);
|
|
396
|
+
const { data } = await scraping.get(url);
|
|
397
|
+
$ = cheerio.load(data);
|
|
398
398
|
|
|
399
399
|
const headingList = $("h1, h2, h3, h4, h5, h6").map((i, el) => ({
|
|
400
400
|
headingTag: $(el).prop("tagName"),
|
|
401
401
|
headingText: $(el).text()
|
|
402
402
|
})).toArray();
|
|
403
403
|
|
|
404
|
-
|
|
405
|
-
} catch (err) {
|
|
404
|
+
results(headingList);
|
|
405
|
+
} catch (err) { failed(err); }
|
|
406
406
|
};
|
|
407
407
|
|
|
408
|
-
const table_heading = async (
|
|
408
|
+
const table_heading = async ({results, failed}) => {
|
|
409
409
|
try {
|
|
410
|
-
const { data } = await scraping.get(
|
|
411
|
-
$ = load(data);
|
|
410
|
+
const { data } = await scraping.get(url);
|
|
411
|
+
$ = cheerio.load(data);
|
|
412
412
|
|
|
413
413
|
const tableHeadList = $("th").map((i, el) => ({
|
|
414
414
|
headingRow: i,
|
|
415
415
|
text: $(el).text()
|
|
416
416
|
})).toArray();
|
|
417
417
|
|
|
418
|
-
|
|
419
|
-
} catch (err) {
|
|
418
|
+
results(tableHeadList);
|
|
419
|
+
} catch (err) { failed(err); }
|
|
420
420
|
};
|
|
421
421
|
|
|
422
|
-
const table_data = async (
|
|
422
|
+
const table_data = async ({results, failed}) => {
|
|
423
423
|
try {
|
|
424
|
-
const { data } = await scraping.get(
|
|
425
|
-
$ = load(data);
|
|
424
|
+
const { data } = await scraping.get(url);
|
|
425
|
+
$ = cheerio.load(data);
|
|
426
426
|
|
|
427
427
|
const tableColumnList = $("td").map((i, el) => $(el).text()).toArray();
|
|
428
428
|
|
|
429
|
-
|
|
430
|
-
} catch (err) {
|
|
429
|
+
results(tableColumnList);
|
|
430
|
+
} catch (err) { failed(err); }
|
|
431
431
|
};
|
|
432
432
|
|
|
433
433
|
|
|
434
|
-
const links = async (
|
|
434
|
+
const links = async ({results, failed}) => {
|
|
435
435
|
try {
|
|
436
|
-
const { data } = await scraping.get(
|
|
437
|
-
$ = load(data);
|
|
436
|
+
const { data } = await scraping.get(url);
|
|
437
|
+
$ = cheerio.load(data);
|
|
438
438
|
|
|
439
439
|
const linkList = $("a").map((i, el) => ({
|
|
440
440
|
url: $(el).attr("href"),
|
|
@@ -442,14 +442,14 @@ function scrape(url) {
|
|
|
442
442
|
})).toArray()
|
|
443
443
|
.filter(({ url }) => url.indexOf("#") !== 0);
|
|
444
444
|
|
|
445
|
-
|
|
446
|
-
} catch (err) {
|
|
445
|
+
results(linkList);
|
|
446
|
+
} catch (err) { failed(err); }
|
|
447
447
|
};
|
|
448
448
|
|
|
449
|
-
const cites = async (
|
|
449
|
+
const cites = async ({results, failed}) => {
|
|
450
450
|
try {
|
|
451
|
-
const { data } = await scraping.get(
|
|
452
|
-
$ = load(data);
|
|
451
|
+
const { data } = await scraping.get(url);
|
|
452
|
+
$ = cheerio.load(data);
|
|
453
453
|
|
|
454
454
|
const citeList = $("q, blockquote").map((i, el) => ({
|
|
455
455
|
citeTag: $(el).prop("tagName"),
|
|
@@ -457,8 +457,8 @@ function scrape(url) {
|
|
|
457
457
|
citeText: $(el).text()
|
|
458
458
|
})).toArray();
|
|
459
459
|
|
|
460
|
-
|
|
461
|
-
} catch (err) {
|
|
460
|
+
results(citeList);
|
|
461
|
+
} catch (err) { failed(err); }
|
|
462
462
|
};
|
|
463
463
|
|
|
464
464
|
return {
|
|
@@ -473,6 +473,22 @@ function scrape(url) {
|
|
|
473
473
|
};
|
|
474
474
|
}
|
|
475
475
|
|
|
476
|
+
const password = () => {
|
|
477
|
+
const chars = "0123456789abcdefghijklmnopqrstuvwxyz!@#$%^&*()ABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
|
478
|
+
|
|
479
|
+
// blank password var
|
|
480
|
+
let password = "";
|
|
481
|
+
|
|
482
|
+
// loop generate chars
|
|
483
|
+
for(let i = 0; i < 12; i++) {
|
|
484
|
+
const randomNumber = Math.floor(Math.random() * chars.length);
|
|
485
|
+
|
|
486
|
+
password += chars.substring(randomNumber, randomNumber + 1);
|
|
487
|
+
}
|
|
488
|
+
|
|
489
|
+
// print new passwors
|
|
490
|
+
return password;
|
|
491
|
+
};
|
|
476
492
|
|
|
477
493
|
// exports
|
|
478
494
|
export {
|
|
@@ -492,5 +508,6 @@ export {
|
|
|
492
508
|
pageSpeed,
|
|
493
509
|
singleStack,
|
|
494
510
|
twitchInfo,
|
|
495
|
-
scrape
|
|
511
|
+
scrape,
|
|
512
|
+
password
|
|
496
513
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "stack-analyze",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.2.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "cli tech stack analyze and pagespeed with node.js using the wappalyzer module. with google pagespeed api, hardware and crypto market",
|
|
6
6
|
"main": "index.mjs",
|
|
@@ -18,25 +18,25 @@
|
|
|
18
18
|
"cheerio": "^1.0.0-rc.12",
|
|
19
19
|
"cli-progress": "^3.11.2",
|
|
20
20
|
"colors": "^1.4.0",
|
|
21
|
-
"console-table-printer": "^2.11.
|
|
21
|
+
"console-table-printer": "^2.11.1",
|
|
22
22
|
"figlet": "^1.5.2",
|
|
23
|
-
"inquirer": "^9.
|
|
24
|
-
"systeminformation": "^5.
|
|
23
|
+
"inquirer": "^9.1.1",
|
|
24
|
+
"systeminformation": "^5.12.6",
|
|
25
25
|
"timeago.js": "^4.0.2",
|
|
26
|
-
"wappalyzer": "^6.10.
|
|
26
|
+
"wappalyzer": "^6.10.39"
|
|
27
27
|
},
|
|
28
28
|
"devDependencies": {
|
|
29
|
-
"eslint": "^8.
|
|
29
|
+
"eslint": "^8.23.0",
|
|
30
30
|
"gh-pages": "^4.0.0",
|
|
31
|
-
"jest": "^
|
|
32
|
-
"jsdoc": "^3.6.
|
|
31
|
+
"jest": "^29.0.1",
|
|
32
|
+
"jsdoc": "^3.6.11",
|
|
33
33
|
"minami": "^1.2.3"
|
|
34
34
|
},
|
|
35
35
|
"scripts": {
|
|
36
36
|
"start": "node cli.js",
|
|
37
37
|
"test": "jest",
|
|
38
|
-
"lint:test": "eslint . --ext .js",
|
|
39
|
-
"lint:fix": "eslint . --ext .js --fix",
|
|
38
|
+
"lint:test": "eslint . --ext .js,.cjs,.mjs",
|
|
39
|
+
"lint:fix": "eslint . --ext .js,.cjs,.mjs --fix",
|
|
40
40
|
"docs": "jsdoc -c jsdoc.json",
|
|
41
41
|
"docs:deploy": "npm run docs && gh-pages -d docs"
|
|
42
42
|
},
|
package/readme.md
CHANGED
|
@@ -12,19 +12,42 @@
|
|
|
12
12
|
|
|
13
13
|
cli tech stack analyze with **node.js** using the wappalyzer and google pagespeed api the module this node external module or install.
|
|
14
14
|
|
|
15
|
-
use the cli program install
|
|
15
|
+
## use the cli program install
|
|
16
16
|
|
|
17
|
-
##
|
|
17
|
+
## cli module
|
|
18
18
|
``` sh
|
|
19
|
-
#
|
|
19
|
+
# old npm mode
|
|
20
20
|
npm i -g stack-analyze
|
|
21
21
|
|
|
22
|
-
#
|
|
22
|
+
# new npm mode
|
|
23
23
|
npm i --location=global
|
|
24
24
|
|
|
25
|
+
# if using global install
|
|
26
|
+
stack-analyze
|
|
27
|
+
|
|
25
28
|
# portable
|
|
26
29
|
npx stack-analyze
|
|
27
30
|
```
|
|
31
|
+
|
|
32
|
+
## module
|
|
33
|
+
|
|
34
|
+
``` sh
|
|
35
|
+
npm i stack-analyze
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
``` js
|
|
39
|
+
// cjs
|
|
40
|
+
const stackAnalyze = require('stack-analyze') // full
|
|
41
|
+
const { password } = require('stack-analyze') // destructuring
|
|
42
|
+
|
|
43
|
+
// esm
|
|
44
|
+
import stackAnalyze from 'stack-analyze' // full
|
|
45
|
+
import { password } from 'stack-analyze' // destructuring
|
|
46
|
+
|
|
47
|
+
// examples
|
|
48
|
+
password()
|
|
49
|
+
```
|
|
50
|
+
|
|
28
51
|
>note: if global install fail using npx
|
|
29
52
|
|
|
30
53
|
[github repo](https://github.com/stack-analyze/stack-analyze.git)
|
package/demo.js
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
import inquirer from 'inquirer';
|
|
2
|
-
|
|
3
|
-
inquirer
|
|
4
|
-
.prompt([
|
|
5
|
-
{
|
|
6
|
-
type: "input",
|
|
7
|
-
name: "username",
|
|
8
|
-
message: "What's your name?"
|
|
9
|
-
}
|
|
10
|
-
])
|
|
11
|
-
.then((answers) => {
|
|
12
|
-
console.log(`Hello ${answers.username}!`)
|
|
13
|
-
})
|
|
14
|
-
.catch((error) => {
|
|
15
|
-
if (error.isTtyError) {
|
|
16
|
-
console.log("Your console environment is not supported!")
|
|
17
|
-
} else {
|
|
18
|
-
console.log(error)
|
|
19
|
-
}
|
|
20
|
-
})
|