@appthreat/atom-parsetools 1.1.4 → 1.1.5

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/astgen.js CHANGED
@@ -1,8 +1,6 @@
1
1
  #!/usr/bin/env node
2
2
 
3
3
  import { join, dirname } from "path";
4
- import yargs from "yargs";
5
- import { hideBin } from "yargs/helpers";
6
4
  import { parse } from "@babel/parser";
7
5
  import { parse as parseHermes } from "hermes-parser";
8
6
  import tsc from "typescript";
@@ -18,6 +16,225 @@ import { getAllFiles } from "@appthreat/atom-common";
18
16
 
19
17
  const ASTGEN_VERSION = "4.0.0";
20
18
 
19
+ const HELP_TEXT = `Options:
20
+ -i, --src Source directory [default: "."]
21
+ -o, --output Output directory for generated AST JSON files
22
+ [default: "ast_out"]
23
+ -t, --type Project type. Default auto-detect
24
+ -r, --recurse Recurse mode suitable for mono-repos [boolean] [default: true]
25
+ --tsTypes Generate type mappings using the TypeScript Compiler API
26
+ [boolean] [default: true]
27
+ --version Show version number [boolean]
28
+ -h, --help Show help [boolean]`;
29
+
30
+ const CLI_OPTIONS = {
31
+ src: { alias: "i", default: ".", type: "string" },
32
+ output: { alias: "o", default: "ast_out", type: "string" },
33
+ type: { alias: "t", type: "string" },
34
+ recurse: { alias: "r", default: true, type: "boolean" },
35
+ tsTypes: { default: true, type: "boolean" }
36
+ };
37
+
38
+ const CLI_ALIASES = Object.fromEntries(
39
+ Object.entries(CLI_OPTIONS)
40
+ .filter(([, option]) => option.alias)
41
+ .map(([name, option]) => [option.alias, name])
42
+ );
43
+
44
+ const normalizeOptionName = (name) =>
45
+ name.replace(/-([a-z])/g, (_, character) => character.toUpperCase());
46
+
47
+ const isOptionToken = (value) => value?.startsWith("-") && value !== "-";
48
+
49
+ const parseBooleanValue = (name, value) => {
50
+ if (value === undefined) {
51
+ return true;
52
+ }
53
+ if (typeof value === "boolean") {
54
+ return value;
55
+ }
56
+ const normalized = String(value).toLowerCase();
57
+ if (["true", "1", "yes", "y"].includes(normalized)) {
58
+ return true;
59
+ }
60
+ if (["false", "0", "no", "n"].includes(normalized)) {
61
+ return false;
62
+ }
63
+ throw new Error(`Invalid boolean value for --${name}: ${value}`);
64
+ };
65
+
66
+ const setParsedOption = (args, name, value) => {
67
+ const normalizedName = normalizeOptionName(name);
68
+ const option = CLI_OPTIONS[normalizedName];
69
+ if (!option) {
70
+ args[normalizedName] = value ?? true;
71
+ return;
72
+ }
73
+ args[normalizedName] =
74
+ option.type === "boolean"
75
+ ? parseBooleanValue(normalizedName, value)
76
+ : value;
77
+ };
78
+
79
+ const parseLongOption = (args, rawArgs, index) => {
80
+ const token = rawArgs[index];
81
+ const noPrefix = token.startsWith("--no-");
82
+ const optionToken = token.slice(noPrefix ? 5 : 2);
83
+ const equalsIndex = optionToken.indexOf("=");
84
+ const rawName =
85
+ equalsIndex === -1 ? optionToken : optionToken.slice(0, equalsIndex);
86
+ const name = normalizeOptionName(rawName);
87
+ const inlineValue =
88
+ equalsIndex === -1 ? undefined : optionToken.slice(equalsIndex + 1);
89
+ const option = CLI_OPTIONS[name];
90
+
91
+ if (noPrefix) {
92
+ setParsedOption(args, name, false);
93
+ return index;
94
+ }
95
+ if (!option) {
96
+ if (inlineValue !== undefined) {
97
+ setParsedOption(args, name, inlineValue);
98
+ } else if (
99
+ rawArgs[index + 1] !== undefined &&
100
+ !isOptionToken(rawArgs[index + 1])
101
+ ) {
102
+ setParsedOption(args, name, rawArgs[index + 1]);
103
+ return index + 1;
104
+ } else {
105
+ setParsedOption(args, name, true);
106
+ }
107
+ return index;
108
+ }
109
+ if (option?.type === "boolean") {
110
+ if (inlineValue !== undefined) {
111
+ setParsedOption(args, name, inlineValue);
112
+ } else if (
113
+ rawArgs[index + 1] !== undefined &&
114
+ !isOptionToken(rawArgs[index + 1])
115
+ ) {
116
+ setParsedOption(args, name, rawArgs[index + 1]);
117
+ return index + 1;
118
+ } else {
119
+ setParsedOption(args, name, true);
120
+ }
121
+ return index;
122
+ }
123
+ if (inlineValue !== undefined) {
124
+ setParsedOption(args, name, inlineValue);
125
+ return index;
126
+ }
127
+ if (rawArgs[index + 1] === undefined || isOptionToken(rawArgs[index + 1])) {
128
+ throw new Error(`Missing value for --${rawName}`);
129
+ }
130
+ setParsedOption(args, name, rawArgs[index + 1]);
131
+ return index + 1;
132
+ };
133
+
134
+ const parseShortOption = (args, rawArgs, index) => {
135
+ const token = rawArgs[index];
136
+ const equalsIndex = token.indexOf("=");
137
+ const letters = token.slice(1, equalsIndex === -1 ? undefined : equalsIndex);
138
+ const inlineValue =
139
+ equalsIndex === -1 ? undefined : token.slice(equalsIndex + 1);
140
+
141
+ for (let letterIndex = 0; letterIndex < letters.length; letterIndex++) {
142
+ const letter = letters[letterIndex];
143
+ const name = CLI_ALIASES[letter] ?? letter;
144
+ const option = CLI_OPTIONS[name];
145
+ const remainingLetters = letters.slice(letterIndex + 1);
146
+
147
+ if (letter === "h") {
148
+ args.help = true;
149
+ continue;
150
+ }
151
+ if (!option) {
152
+ if (remainingLetters) {
153
+ setParsedOption(args, name, remainingLetters);
154
+ return index;
155
+ }
156
+ if (inlineValue !== undefined) {
157
+ setParsedOption(args, name, inlineValue);
158
+ return index;
159
+ }
160
+ if (
161
+ rawArgs[index + 1] !== undefined &&
162
+ !isOptionToken(rawArgs[index + 1])
163
+ ) {
164
+ setParsedOption(args, name, rawArgs[index + 1]);
165
+ return index + 1;
166
+ }
167
+ setParsedOption(args, name, true);
168
+ continue;
169
+ }
170
+ if (option?.type === "boolean") {
171
+ if (inlineValue !== undefined) {
172
+ setParsedOption(args, name, inlineValue);
173
+ } else if (
174
+ !remainingLetters &&
175
+ rawArgs[index + 1] !== undefined &&
176
+ !isOptionToken(rawArgs[index + 1])
177
+ ) {
178
+ setParsedOption(args, name, rawArgs[index + 1]);
179
+ return index + 1;
180
+ } else {
181
+ setParsedOption(args, name, true);
182
+ }
183
+ continue;
184
+ }
185
+ if (remainingLetters) {
186
+ setParsedOption(args, name, remainingLetters);
187
+ return index;
188
+ }
189
+ if (inlineValue !== undefined) {
190
+ setParsedOption(args, name, inlineValue);
191
+ return index;
192
+ }
193
+ if (rawArgs[index + 1] === undefined || isOptionToken(rawArgs[index + 1])) {
194
+ throw new Error(`Missing value for -${letter}`);
195
+ }
196
+ setParsedOption(args, name, rawArgs[index + 1]);
197
+ return index + 1;
198
+ }
199
+ return index;
200
+ };
201
+
202
+ const parseCliArgs = (argvs) => {
203
+ const rawArgs = argvs.slice(2);
204
+ const args = Object.fromEntries(
205
+ Object.entries(CLI_OPTIONS)
206
+ .filter(([, option]) => option.default !== undefined)
207
+ .map(([name, option]) => [name, option.default])
208
+ );
209
+ args._ = [];
210
+
211
+ for (let index = 0; index < rawArgs.length; index++) {
212
+ const token = rawArgs[index];
213
+ if (token === "--") {
214
+ args._.push(...rawArgs.slice(index + 1));
215
+ break;
216
+ }
217
+ if (token === "--help") {
218
+ args.help = true;
219
+ continue;
220
+ }
221
+ if (token === "--version") {
222
+ args.version = true;
223
+ continue;
224
+ }
225
+ if (token.startsWith("--")) {
226
+ index = parseLongOption(args, rawArgs, index);
227
+ continue;
228
+ }
229
+ if (token.startsWith("-") && token !== "-") {
230
+ index = parseShortOption(args, rawArgs, index);
231
+ continue;
232
+ }
233
+ args._.push(token);
234
+ }
235
+ return args;
236
+ };
237
+
21
238
  const babelParserOptions = {
22
239
  sourceType: "unambiguous",
23
240
  allowImportExportEverywhere: true,
@@ -695,34 +912,12 @@ const start = async (options) => {
695
912
  };
696
913
 
697
914
  async function main(argvs) {
698
- const args = yargs(hideBin(argvs))
699
- .option("src", {
700
- alias: "i",
701
- default: ".",
702
- description: "Source directory"
703
- })
704
- .option("output", {
705
- alias: "o",
706
- default: "ast_out",
707
- description: "Output directory for generated AST json files"
708
- })
709
- .option("type", {
710
- alias: "t",
711
- description: "Project type. Default auto-detect"
712
- })
713
- .option("recurse", {
714
- alias: "r",
715
- default: true,
716
- type: "boolean",
717
- description: "Recurse mode suitable for mono-repos"
718
- })
719
- .option("tsTypes", {
720
- default: true,
721
- type: "boolean",
722
- description: "Generate type mappings using the Typescript Compiler API"
723
- })
724
- .version(ASTGEN_VERSION)
725
- .help("h").argv;
915
+ const args = parseCliArgs(argvs);
916
+
917
+ if (args.help) {
918
+ console.log(HELP_TEXT);
919
+ process.exit(0);
920
+ }
726
921
 
727
922
  if (args.version) {
728
923
  console.log(ASTGEN_VERSION);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@appthreat/atom-parsetools",
3
- "version": "1.1.4",
3
+ "version": "1.1.5",
4
4
  "description": "Parsing tools that complement the @appthreat/atom project.",
5
5
  "main": "./index.js",
6
6
  "type": "module",
@@ -10,10 +10,9 @@
10
10
  },
11
11
  "dependencies": {
12
12
  "@appthreat/atom-common": "^1.1.0",
13
- "@babel/parser": "^7.28.5",
14
- "typescript": "^6.0.2",
15
- "hermes-parser": "^0.34.0",
16
- "yargs": "^17.7.2"
13
+ "@babel/parser": "^7.29.3",
14
+ "hermes-parser": "^0.36.1",
15
+ "typescript": "^6.0.3"
17
16
  },
18
17
  "devDependencies": {
19
18
  "eslint": "8.57.0"
@@ -1,9 +1,9 @@
1
1
  <?php return array(
2
2
  'root' => array(
3
3
  'name' => '__root__',
4
- 'pretty_version' => 'v1.1.4',
5
- 'version' => '1.1.4.0',
6
- 'reference' => '53e7f62db85eb346578c30a7f213de43e589ed51',
4
+ 'pretty_version' => 'v1.1.5',
5
+ 'version' => '1.1.5.0',
6
+ 'reference' => 'b64151314b4cffd7976a467f82be3f24cfba0087',
7
7
  'type' => 'library',
8
8
  'install_path' => __DIR__ . '/../../',
9
9
  'aliases' => array(),
@@ -11,9 +11,9 @@
11
11
  ),
12
12
  'versions' => array(
13
13
  '__root__' => array(
14
- 'pretty_version' => 'v1.1.4',
15
- 'version' => '1.1.4.0',
16
- 'reference' => '53e7f62db85eb346578c30a7f213de43e589ed51',
14
+ 'pretty_version' => 'v1.1.5',
15
+ 'version' => '1.1.5.0',
16
+ 'reference' => 'b64151314b4cffd7976a467f82be3f24cfba0087',
17
17
  'type' => 'library',
18
18
  'install_path' => __DIR__ . '/../../',
19
19
  'aliases' => array(),
@@ -6,10 +6,10 @@ checking for whether -fvisibility=hidden is accepted as CFLAGS... yes
6
6
  creating Makefile
7
7
 
8
8
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/prism-1.7.0/ext/prism
9
- make -j5 DESTDIR\= sitearchdir\=./.gem.20260408-2400-cnvky8 sitelibdir\=./.gem.20260408-2400-cnvky8 clean
9
+ make -j5 DESTDIR\= sitearchdir\=./.gem.20260524-2504-ep411o sitelibdir\=./.gem.20260524-2504-ep411o clean
10
10
 
11
11
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/prism-1.7.0/ext/prism
12
- make -j5 DESTDIR\= sitearchdir\=./.gem.20260408-2400-cnvky8 sitelibdir\=./.gem.20260408-2400-cnvky8
12
+ make -j5 DESTDIR\= sitearchdir\=./.gem.20260524-2504-ep411o sitelibdir\=./.gem.20260524-2504-ep411o
13
13
  compiling api_node.c
14
14
  compiling api_pack.c
15
15
  compiling extension.c
@@ -37,8 +37,8 @@ compiling ./../../src/util/pm_strpbrk.c
37
37
  linking shared-object prism/prism.so
38
38
 
39
39
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/prism-1.7.0/ext/prism
40
- make -j5 DESTDIR\= sitearchdir\=./.gem.20260408-2400-cnvky8 sitelibdir\=./.gem.20260408-2400-cnvky8 install
41
- /usr/bin/install -c -m 0755 prism.so ./.gem.20260408-2400-cnvky8/prism
40
+ make -j5 DESTDIR\= sitearchdir\=./.gem.20260524-2504-ep411o sitelibdir\=./.gem.20260524-2504-ep411o install
41
+ /usr/bin/install -c -m 0755 prism.so ./.gem.20260524-2504-ep411o/prism
42
42
 
43
43
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/prism-1.7.0/ext/prism
44
- make DESTDIR\= sitearchdir\=./.gem.20260408-2400-cnvky8 sitelibdir\=./.gem.20260408-2400-cnvky8 clean
44
+ make DESTDIR\= sitearchdir\=./.gem.20260524-2504-ep411o sitelibdir\=./.gem.20260524-2504-ep411o clean
@@ -3,16 +3,16 @@ current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rub
3
3
  creating Makefile
4
4
 
5
5
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/racc-1.8.1/ext/racc/cparse
6
- make -j5 DESTDIR\= sitearchdir\=./.gem.20260408-2400-tk8n83 sitelibdir\=./.gem.20260408-2400-tk8n83 clean
6
+ make -j5 DESTDIR\= sitearchdir\=./.gem.20260524-2504-g189r0 sitelibdir\=./.gem.20260524-2504-g189r0 clean
7
7
 
8
8
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/racc-1.8.1/ext/racc/cparse
9
- make -j5 DESTDIR\= sitearchdir\=./.gem.20260408-2400-tk8n83 sitelibdir\=./.gem.20260408-2400-tk8n83
9
+ make -j5 DESTDIR\= sitearchdir\=./.gem.20260524-2504-g189r0 sitelibdir\=./.gem.20260524-2504-g189r0
10
10
  compiling cparse.c
11
11
  linking shared-object racc/cparse.so
12
12
 
13
13
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/racc-1.8.1/ext/racc/cparse
14
- make -j5 DESTDIR\= sitearchdir\=./.gem.20260408-2400-tk8n83 sitelibdir\=./.gem.20260408-2400-tk8n83 install
15
- /usr/bin/install -c -m 0755 cparse.so ./.gem.20260408-2400-tk8n83/racc
14
+ make -j5 DESTDIR\= sitearchdir\=./.gem.20260524-2504-g189r0 sitelibdir\=./.gem.20260524-2504-g189r0 install
15
+ /usr/bin/install -c -m 0755 cparse.so ./.gem.20260524-2504-g189r0/racc
16
16
 
17
17
  current directory: /home/runner/work/atom-parsetools/atom-parsetools/plugins/rubyastgen/bundle/ruby/4.0.0/gems/racc-1.8.1/ext/racc/cparse
18
- make DESTDIR\= sitearchdir\=./.gem.20260408-2400-tk8n83 sitelibdir\=./.gem.20260408-2400-tk8n83 clean
18
+ make DESTDIR\= sitearchdir\=./.gem.20260524-2504-g189r0 sitelibdir\=./.gem.20260524-2504-g189r0 clean