guess-js-deps-bash 0.1.62 → 0.1.64
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/autoguess_config.txt +1 -0
- package/guess-js-deps.sh +96 -23
- package/manif_script_cmd2pkg.sed +1 -0
- package/package.json +10 -4
- package/scan_webpack_config.js +53 -0
package/autoguess_config.txt
CHANGED
package/guess-js-deps.sh
CHANGED
|
@@ -21,18 +21,16 @@ function guess_js_deps () {
|
|
|
21
21
|
devDep
|
|
22
22
|
peerDep
|
|
23
23
|
)
|
|
24
|
+
local -A CFG=(
|
|
25
|
+
[runmode]='cmp'
|
|
26
|
+
)
|
|
27
|
+
local POS_ARGN=( runmode )
|
|
28
|
+
local POS_ARGS=()
|
|
29
|
+
parse_cli_opts "$@" || return $?
|
|
24
30
|
|
|
25
|
-
local RUNMODE="$1"; shift
|
|
26
|
-
case "$RUNMODE" in
|
|
27
|
-
'..' | '../'* )
|
|
28
|
-
cd -- "$RUNMODE" # probably to where your package.json is.
|
|
29
|
-
RUNMODE="$1"
|
|
30
|
-
shift;;
|
|
31
|
-
esac
|
|
32
31
|
local OUTPUT_MODE=( fail 'Unsupported output mode. This is a bug.' )
|
|
33
|
-
case "$
|
|
32
|
+
case "${CFG[runmode]}" in
|
|
34
33
|
as-json ) OUTPUT_MODE=( dump_deps_as_json );;
|
|
35
|
-
'' | \
|
|
36
34
|
cmp ) OUTPUT_MODE=( maybe_colorize_diff compare_deps_as_json );;
|
|
37
35
|
upd ) OUTPUT_MODE=( update_manifest );;
|
|
38
36
|
sym ) OUTPUT_MODE=( symlink_nonlocal_node_modules );;
|
|
@@ -56,13 +54,46 @@ function guess_js_deps () {
|
|
|
56
54
|
tabulate-found ) OUTPUT_MODE=( 'fmt://tsv' );;
|
|
57
55
|
tabulate-known ) tabulate_manifest_deps; return $?;;
|
|
58
56
|
--func ) "$@"; return $?;;
|
|
59
|
-
* ) fail "unsupported runmode: $
|
|
57
|
+
* ) fail "unsupported runmode: ${CFG[runmode]}"; return 2;;
|
|
60
58
|
esac
|
|
61
59
|
|
|
62
60
|
find_imports_in_project "${OUTPUT_MODE[@]}"
|
|
63
61
|
}
|
|
64
62
|
|
|
65
63
|
|
|
64
|
+
function parse_cli_opts () {
|
|
65
|
+
local OPT=
|
|
66
|
+
while [ "$#" -gt 0 ]; do
|
|
67
|
+
OPT="$1"; shift
|
|
68
|
+
# [ -n "$OPT" ] || continue
|
|
69
|
+
#case "${CFG[no-more-opts]}$OPT" in
|
|
70
|
+
case "$OPT" in
|
|
71
|
+
'' ) continue;;
|
|
72
|
+
'..' | '../'* ) cd -- "$OPT";; # probably to where your package.json is.
|
|
73
|
+
-- ) POS_ARGS+=( "$@" ); break;;
|
|
74
|
+
#-- ) CFG[no-more-opts]='%%--'; continue;;
|
|
75
|
+
--expect-no-changes | \
|
|
76
|
+
--maybe-no-imports | \
|
|
77
|
+
'' ) CFG["${OPT#--}"]=+;;
|
|
78
|
+
--*=* )
|
|
79
|
+
OPT="${OPT#--}"
|
|
80
|
+
CFG["${OPT%%=*}"]="${OPT#*=}";;
|
|
81
|
+
--help | \
|
|
82
|
+
-* )
|
|
83
|
+
local -fp "${FUNCNAME[0]}" | guess_bash_script_config_opts-pmb
|
|
84
|
+
[ "${OPT//-/}" == help ] && return 1
|
|
85
|
+
echo "E: $0, CLI: unsupported option: $OPT" >&2; return 1;;
|
|
86
|
+
* )
|
|
87
|
+
case "${POS_ARGN[0]}" in
|
|
88
|
+
'' ) echo "E: $0: unexpected positional argument" >&2; return 1;;
|
|
89
|
+
'+' ) POS_ARGS+=( "$OPT" );;
|
|
90
|
+
* ) CFG["${POS_ARGN[0]}"]="$OPT"; POS_ARGN=( "${POS_ARGN[@]:1}" );;
|
|
91
|
+
esac;;
|
|
92
|
+
esac
|
|
93
|
+
done
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
|
|
66
97
|
function warn_no_args () {
|
|
67
98
|
[ "$#" -ge 2 ] || echo "W: Calling $1 with no arguments!" >&2
|
|
68
99
|
"$@"; return $?
|
|
@@ -70,8 +101,18 @@ function warn_no_args () {
|
|
|
70
101
|
|
|
71
102
|
|
|
72
103
|
function maybe_colorize_diff () {
|
|
73
|
-
[ -
|
|
74
|
-
"$
|
|
104
|
+
[ -n "$*" ] || return 0
|
|
105
|
+
if [ -n "$COLORIZE_DIFF" ]; then
|
|
106
|
+
exec > >("$COLORIZE_DIFF")
|
|
107
|
+
fi
|
|
108
|
+
local RV=
|
|
109
|
+
"$@"; RV=$?
|
|
110
|
+
|
|
111
|
+
# Wait for output to go through the coloring process before returning
|
|
112
|
+
# control to parent process. (Which might want to print something
|
|
113
|
+
# immediately, which might overlap.)
|
|
114
|
+
[ -z "$COLORIZE_DIFF" ] || sleep 0.2s
|
|
115
|
+
return "$RV"
|
|
75
116
|
}
|
|
76
117
|
|
|
77
118
|
|
|
@@ -106,7 +147,7 @@ function init_resolve_cache () {
|
|
|
106
147
|
|
|
107
148
|
|
|
108
149
|
function init_resolve_cache__prep () {
|
|
109
|
-
init_resolve_cache__webpack_cfg || return $?
|
|
150
|
+
init_resolve_cache__webpack_cfg eval || return $?
|
|
110
151
|
init_resolve_cache__forced_custom || return $?
|
|
111
152
|
}
|
|
112
153
|
|
|
@@ -114,9 +155,17 @@ function init_resolve_cache__prep () {
|
|
|
114
155
|
function init_resolve_cache__webpack_cfg () {
|
|
115
156
|
local WPCFG='./webpack.config.js'
|
|
116
157
|
[ -f "$WPCFG" ] || return 0
|
|
117
|
-
local
|
|
118
|
-
|
|
119
|
-
|
|
158
|
+
local SCAN="$SELFPATH"/scan_webpack_config.js
|
|
159
|
+
local LEARN='
|
|
160
|
+
const scan = require(process.env.SCAN);
|
|
161
|
+
const wpcfg = require(process.env.WPCFG);
|
|
162
|
+
JSON.stringify(scan(wpcfg), null, 2)
|
|
163
|
+
'
|
|
164
|
+
LEARN="$(WPCFG="$WPCFG" SCAN="$SCAN" nodejs -e "$LEARN")" || return $?$(
|
|
165
|
+
echo "E: $FUNCNAME: Failed to scan $WPCFG" >&2)
|
|
166
|
+
local NEXT="${1:-echo}"; shift
|
|
167
|
+
"$NEXT" "$@" "$LEARN" || return $?$(
|
|
168
|
+
echo "E: $FUNCNAME: Failed to '$NEXT' the scan report" >&2)
|
|
120
169
|
}
|
|
121
170
|
|
|
122
171
|
|
|
@@ -165,6 +214,8 @@ function scan_all_scannable_files_in_project () {
|
|
|
165
214
|
progress "found ${#IMPORTS[@]}"
|
|
166
215
|
|
|
167
216
|
progress 'I: Searching for require()s/imports: '
|
|
217
|
+
eval "$(init_resolve_cache)"
|
|
218
|
+
find_webpack_config_cached_deps
|
|
168
219
|
find_imports_in_files "${IMPORTS[@]}"
|
|
169
220
|
find_manif_script_deps
|
|
170
221
|
find_manif_eslint_deps
|
|
@@ -172,6 +223,12 @@ function scan_all_scannable_files_in_project () {
|
|
|
172
223
|
}
|
|
173
224
|
|
|
174
225
|
|
|
226
|
+
function find_webpack_config_cached_deps () {
|
|
227
|
+
local KEY='bundler://webpack/config/needs'
|
|
228
|
+
<<<"${RESOLVE_CACHE["?$KEY"]}" grep -oPe '\S+' | sed -re 's~$~\t'"$KEY~"
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
|
|
175
232
|
function find_imports_in_project () {
|
|
176
233
|
local THEN=( "$@" )
|
|
177
234
|
local CWD_PKG_NAME="$(guess_cwd_pkg_name)"
|
|
@@ -184,8 +241,16 @@ function find_imports_in_project () {
|
|
|
184
241
|
| guess_unique_stdin_dep_types 1-3)
|
|
185
242
|
progress 'done.'
|
|
186
243
|
|
|
187
|
-
|
|
188
|
-
|
|
244
|
+
local ERR=
|
|
245
|
+
if [ -z "${IMPORTS[0]}" ]; then
|
|
246
|
+
ERR="Unable to find any import()s/imports in package: $CWD_PKG_NAME"
|
|
247
|
+
if [ -n "${CFG[maybe-no-imports]}" ]; then
|
|
248
|
+
echo "D: $ERR"
|
|
249
|
+
return 0
|
|
250
|
+
fi
|
|
251
|
+
fail "$ERR"
|
|
252
|
+
return 3
|
|
253
|
+
fi
|
|
189
254
|
|
|
190
255
|
if [ "${OUTPUT_MODE[0]}" == 'fmt://tsv' ]; then
|
|
191
256
|
printf '%s\n' "${IMPORTS[@]}"
|
|
@@ -238,6 +303,7 @@ function find_manif_eslint_deps () {
|
|
|
238
303
|
|
|
239
304
|
local ECNP='eslint-config-nodejs-pmb'
|
|
240
305
|
case "$BUF" in
|
|
306
|
+
*"¶ eslint-config-jslint-compat-pmb "* | \
|
|
241
307
|
*"¶ $ECNP "* )
|
|
242
308
|
local PEER_DEPS="$ECNP/test/expectedPeerDependencies.js"
|
|
243
309
|
PEER_DEPS="require('$PEER_DEPS').join('\n')"
|
|
@@ -345,9 +411,15 @@ function compare_deps_as_json () {
|
|
|
345
411
|
eval local -A DEP_OFFSETS="( $(find_dep_keys_line_numbers) )"
|
|
346
412
|
|
|
347
413
|
local DEP_TYPE=
|
|
414
|
+
local CHANGES_IN_DEP_TYPES=
|
|
415
|
+
|
|
348
416
|
for DEP_TYPE in "${KNOWN_DEP_TYPES[@]}"; do
|
|
349
417
|
compare_deps_as_json__one_dep_type || return $?
|
|
350
418
|
done
|
|
419
|
+
|
|
420
|
+
[ -z "$CHANGES_IN_DEP_TYPES" ] \
|
|
421
|
+
|| [ -z "${CFG[expect-no-changes]}" ] || return 4$(
|
|
422
|
+
fail "Found unexpected changes! in:$CHANGES_IN_DEP_TYPES")
|
|
351
423
|
}
|
|
352
424
|
|
|
353
425
|
|
|
@@ -359,6 +431,7 @@ function compare_deps_as_json__one_dep_type () {
|
|
|
359
431
|
echo "D: no changes in ${DEP_TYPE}s"
|
|
360
432
|
return 0
|
|
361
433
|
fi
|
|
434
|
+
CHANGES_IN_DEP_TYPES+=" $DEP_TYPE"
|
|
362
435
|
|
|
363
436
|
local EMPTY="${DEP_OFFSETS[$DEP_TYPE:empty]}"
|
|
364
437
|
if [ -n "$VERBATIM_EMPTY_ORIG" -a -n "$EMPTY" ]; then
|
|
@@ -567,7 +640,6 @@ function find_imports_in_files () {
|
|
|
567
640
|
[ "$#" == 0 ] && return 0
|
|
568
641
|
eval "$(init_resolve_cache)"
|
|
569
642
|
local SBC_RGX='($bogus^'"$(printf '|%s' "${AUTOGUESS_SHEBANG_CMDS[@]}"))"
|
|
570
|
-
|
|
571
643
|
LANG=C grep -PHone '#!.*$|^(\xEF\xBB\xBF|)\s*'$(
|
|
572
644
|
)'(import|\W*from)\s.*$|require\([^()]+\)' -- "$@" \
|
|
573
645
|
| tr "'" '"' | LANG=C sed -rf <(echo '
|
|
@@ -692,9 +764,9 @@ function guess_one_dep_type () {
|
|
|
692
764
|
esac
|
|
693
765
|
|
|
694
766
|
if [ -z "$DEP_VER" ]; then
|
|
695
|
-
case
|
|
696
|
-
|
|
697
|
-
DEP_TYPE='
|
|
767
|
+
case " ${RESOLVE_CACHE['?bundler://alias_pkgnames']} " in
|
|
768
|
+
*" ${REQ_MOD%%/*} "* )
|
|
769
|
+
DEP_TYPE='bundler-alias'
|
|
698
770
|
DEP_VER='*';;
|
|
699
771
|
esac
|
|
700
772
|
fi
|
|
@@ -751,9 +823,10 @@ function guess_one_dep_type () {
|
|
|
751
823
|
esac
|
|
752
824
|
|
|
753
825
|
case "$REQ_NORM_FEXT" in
|
|
826
|
+
bundler://* | \
|
|
827
|
+
manif://lint | \
|
|
754
828
|
manif://scripts/*lint* | \
|
|
755
829
|
manif://scripts/*test* | \
|
|
756
|
-
manif://lint | \
|
|
757
830
|
. ) DEP_TYPE=devDep;;
|
|
758
831
|
*/* ) ;; # files in subdirs are handled above
|
|
759
832
|
# below: top-level files
|
package/manif_script_cmd2pkg.sed
CHANGED
package/package.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{ "name": "guess-js-deps-bash",
|
|
2
|
-
"version": "0.1.
|
|
2
|
+
"version": "0.1.64",
|
|
3
3
|
"description": "A bash attempt at npm-forgot: Guess JavaScript require() dependencies, detect their versions, compare with package.json.",
|
|
4
4
|
|
|
5
5
|
"keywords": [
|
|
@@ -26,12 +26,18 @@
|
|
|
26
26
|
|
|
27
27
|
"main": "capture-bash.js",
|
|
28
28
|
"bin": { "guess-js-deps": "guess-js-deps.sh" },
|
|
29
|
-
"scripts": { "test": "
|
|
29
|
+
"scripts": { "test": "elp && guess-js-deps cmp --expect-no-changes" },
|
|
30
30
|
"directories": { "test": "test" },
|
|
31
|
+
"eslintConfig": { "extends": "nodejs-pmb" },
|
|
31
32
|
|
|
32
33
|
"dependencies": {},
|
|
33
|
-
"devDependencies": {
|
|
34
|
+
"devDependencies": {
|
|
35
|
+
"eslint-config-nodejs-pmb": "^0.3.5",
|
|
36
|
+
"eslint-plugin-json-light-pmb": "^1.0.7",
|
|
37
|
+
"eslint-plugin-n": "^15.2.4",
|
|
38
|
+
"eslint-pretty-pmb": "^1.0.5"
|
|
39
|
+
},
|
|
34
40
|
|
|
35
41
|
|
|
36
|
-
"
|
|
42
|
+
"engines": { "npm": ">=7.0.0", "node": ">=16.0.0" }
|
|
37
43
|
}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
// const same = require('assert').deepStrictEqual;
|
|
4
|
+
|
|
5
|
+
function orf(x) { return x || false; }
|
|
6
|
+
function shellQuoteNoApos(s) { return "'" + s.replace(/'/g, '') + "'"; }
|
|
7
|
+
|
|
8
|
+
function setSlotNoApos(k, v, op) {
|
|
9
|
+
console.log("RESOLVE_CACHE['" + k + "']" + (op || '') + '='
|
|
10
|
+
+ shellQuoteNoApos(v));
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
const EX = function scanWebpackConfig(wpCfg) {
|
|
15
|
+
const scan = {
|
|
16
|
+
wpCfg,
|
|
17
|
+
needPkgs: new Set(EX.alwaysNeededPkgs),
|
|
18
|
+
};
|
|
19
|
+
EX.aliases(scan);
|
|
20
|
+
EX.resourceLoaders(scan);
|
|
21
|
+
|
|
22
|
+
setSlotNoApos('?bundler://webpack/config/needs',
|
|
23
|
+
Array.from(scan.needPkgs.values()).sort().join(' '));
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
Object.assign(EX, {
|
|
28
|
+
|
|
29
|
+
alwaysNeededPkgs: [
|
|
30
|
+
'browserslist',
|
|
31
|
+
],
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
aliases(scan) {
|
|
35
|
+
const alNames = Object.keys(orf(orf(scan.wpCfg.resolve).alias)).join(' ');
|
|
36
|
+
if (!alNames) { return; }
|
|
37
|
+
setSlotNoApos('?bundler://alias_pkgnames', (' ' + alNames + ' '), '+');
|
|
38
|
+
},
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
resourceLoaders(scan) {
|
|
42
|
+
[].concat(orf(scan.wpCfg.module).rules).forEach(function foundRule(rule) {
|
|
43
|
+
if (!rule) { return; }
|
|
44
|
+
const ldr = (rule.loader || orf(rule.use).loader);
|
|
45
|
+
if (!ldr) { return; }
|
|
46
|
+
scan.needPkgs.add(ldr);
|
|
47
|
+
});
|
|
48
|
+
},
|
|
49
|
+
|
|
50
|
+
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
module.exports = EX;
|