OLD | NEW |
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 library analyzer_cli.src.options; | 5 library analyzer_cli.src.options; |
6 | 6 |
7 import 'dart:io'; | 7 import 'dart:io'; |
8 | 8 |
9 import 'package:args/args.dart'; | 9 import 'package:args/args.dart'; |
10 import 'package:cli_util/cli_util.dart' show getSdkDir; | 10 import 'package:cli_util/cli_util.dart' show getSdkDir; |
11 | 11 |
12 const _binaryName = 'dartanalyzer'; | 12 const _binaryName = 'dartanalyzer'; |
13 | 13 |
14 /// Print the given message and exit with the given [exitCode] | 14 /// Print the given message and exit with the given [exitCode] |
15 void printAndFail(String message, {int exitCode: 15}) { | 15 void printAndFail(String message, {int exitCode: 15}) { |
16 print(message); | 16 print(message); |
17 exit(exitCode); | 17 exit(exitCode); |
18 } | 18 } |
19 | 19 |
20 /// Analyzer commandline configuration options. | 20 /// Analyzer commandline configuration options. |
21 class CommandLineOptions { | 21 class CommandLineOptions { |
22 | |
23 /// The path to an analysis options file | 22 /// The path to an analysis options file |
24 final String analysisOptionsFile; | 23 final String analysisOptionsFile; |
25 | 24 |
26 /// The path to the dart SDK | 25 /// The path to the dart SDK |
27 String dartSdkPath; | 26 String dartSdkPath; |
28 | 27 |
29 /// A table mapping the names of defined variables to their values. | 28 /// A table mapping the names of defined variables to their values. |
30 final Map<String, String> definedVariables; | 29 final Map<String, String> definedVariables; |
31 | 30 |
32 /// Whether to report hints | 31 /// Whether to report hints |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
75 | 74 |
76 /// Whether to show SDK warnings | 75 /// Whether to show SDK warnings |
77 final bool showSdkWarnings; | 76 final bool showSdkWarnings; |
78 | 77 |
79 /// The source files to analyze | 78 /// The source files to analyze |
80 final List<String> sourceFiles; | 79 final List<String> sourceFiles; |
81 | 80 |
82 /// Whether to treat warnings as fatal | 81 /// Whether to treat warnings as fatal |
83 final bool warningsAreFatal; | 82 final bool warningsAreFatal; |
84 | 83 |
85 /// A table mapping library URIs to the file system path where the library | |
86 /// source is located. | |
87 final Map<String, String> customUrlMappings; | |
88 | |
89 /// Whether to use package:dev_compiler for strong static checking. | 84 /// Whether to use package:dev_compiler for strong static checking. |
90 final bool strongMode; | 85 final bool strongMode; |
91 | 86 |
92 /// Whether to emit hints from [strongMode] analysis. | 87 /// Whether to emit hints from [strongMode] analysis. |
93 final bool strongHints; | 88 final bool strongHints; |
94 | 89 |
95 /// Initialize options from the given parsed [args]. | 90 /// Initialize options from the given parsed [args]. |
96 CommandLineOptions._fromArgs(ArgResults args, | 91 CommandLineOptions._fromArgs( |
97 Map<String, String> definedVariables, | 92 ArgResults args, Map<String, String> definedVariables) |
98 Map<String, String> customUrlMappings) | |
99 : dartSdkPath = args['dart-sdk'], | 93 : dartSdkPath = args['dart-sdk'], |
100 this.definedVariables = definedVariables, | 94 this.definedVariables = definedVariables, |
101 analysisOptionsFile = args['options'], | 95 analysisOptionsFile = args['options'], |
102 disableHints = args['no-hints'], | 96 disableHints = args['no-hints'], |
103 displayVersion = args['version'], | 97 displayVersion = args['version'], |
104 enableNullAwareOperators = args['enable-null-aware-operators'], | 98 enableNullAwareOperators = args['enable-null-aware-operators'], |
105 enableStrictCallChecks = args['enable-strict-call-checks'], | 99 enableStrictCallChecks = args['enable-strict-call-checks'], |
106 enableSuperMixins = args['supermixin'], | 100 enableSuperMixins = args['supermixin'], |
107 enableTypeChecks = args['enable_type_checks'], | 101 enableTypeChecks = args['enable_type_checks'], |
108 ignoreUnrecognizedFlags = args['ignore-unrecognized-flags'], | 102 ignoreUnrecognizedFlags = args['ignore-unrecognized-flags'], |
109 lints = args['lints'], | 103 lints = args['lints'], |
110 log = args['log'], | 104 log = args['log'], |
111 machineFormat = args['machine'] || args['format'] == 'machine', | 105 machineFormat = args['machine'] || args['format'] == 'machine', |
112 packageConfigPath = args['packages'], | 106 packageConfigPath = args['packages'], |
113 packageRootPath = args['package-root'], | 107 packageRootPath = args['package-root'], |
114 shouldBatch = args['batch'], | 108 shouldBatch = args['batch'], |
115 showPackageWarnings = args['show-package-warnings'] || | 109 showPackageWarnings = |
116 args['package-warnings'], | 110 args['show-package-warnings'] || args['package-warnings'], |
117 showSdkWarnings = args['show-sdk-warnings'] || args['warnings'], | 111 showSdkWarnings = args['show-sdk-warnings'] || args['warnings'], |
118 sourceFiles = args.rest, | 112 sourceFiles = args.rest, |
119 warningsAreFatal = args['fatal-warnings'], | 113 warningsAreFatal = args['fatal-warnings'], |
120 this.customUrlMappings = customUrlMappings, | |
121 strongMode = args['strong'], | 114 strongMode = args['strong'], |
122 strongHints = args['strong-hints']; | 115 strongHints = args['strong-hints']; |
123 | 116 |
124 /// Parse [args] into [CommandLineOptions] describing the specified | 117 /// Parse [args] into [CommandLineOptions] describing the specified |
125 /// analyzer options. In case of a format error, calls [printAndFail], which | 118 /// analyzer options. In case of a format error, calls [printAndFail], which |
126 /// by default prints an error message and exits. | 119 /// by default prints an error message and exits. |
127 static CommandLineOptions parse(List<String> args, | 120 static CommandLineOptions parse(List<String> args, |
128 [printAndFail = printAndFail]) { | 121 [printAndFail = printAndFail]) { |
129 CommandLineOptions options = _parse(args); | 122 CommandLineOptions options = _parse(args); |
130 // Check SDK. | 123 // Check SDK. |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
182 static CommandLineOptions _parse(List<String> args) { | 175 static CommandLineOptions _parse(List<String> args) { |
183 args = args.expand((String arg) => arg.split('=')).toList(); | 176 args = args.expand((String arg) => arg.split('=')).toList(); |
184 var parser = new CommandLineParser() | 177 var parser = new CommandLineParser() |
185 ..addFlag('batch', | 178 ..addFlag('batch', |
186 abbr: 'b', | 179 abbr: 'b', |
187 help: 'Run in batch mode.', | 180 help: 'Run in batch mode.', |
188 defaultsTo: false, | 181 defaultsTo: false, |
189 negatable: false) | 182 negatable: false) |
190 ..addOption('dart-sdk', help: 'The path to the Dart SDK.') | 183 ..addOption('dart-sdk', help: 'The path to the Dart SDK.') |
191 ..addOption('packages', | 184 ..addOption('packages', |
192 help: 'Path to the package resolution configuration file, which suppli
es a mapping of package names to paths. This option cannot be used with --packa
ge-root.') | 185 help: |
| 186 'Path to the package resolution configuration file, which supplies
a mapping of package names to paths. This option cannot be used with --package
-root.') |
193 ..addOption('package-root', | 187 ..addOption('package-root', |
194 abbr: 'p', | 188 abbr: 'p', |
195 help: 'Path to a package root directory (deprecated). This option cann
ot be used with --packages.') | 189 help: |
| 190 'Path to a package root directory (deprecated). This option cannot
be used with --packages.') |
196 ..addOption('options', help: 'Path to an analysis options file.') | 191 ..addOption('options', help: 'Path to an analysis options file.') |
197 ..addOption('format', | 192 ..addOption('format', |
198 help: 'Specifies the format in which errors are displayed.') | 193 help: 'Specifies the format in which errors are displayed.') |
199 ..addFlag('machine', | 194 ..addFlag('machine', |
200 help: 'Print errors in a format suitable for parsing (deprecated).', | 195 help: 'Print errors in a format suitable for parsing (deprecated).', |
201 defaultsTo: false, | 196 defaultsTo: false, |
202 negatable: false) | 197 negatable: false) |
203 ..addFlag('version', | 198 ..addFlag('version', |
204 help: 'Print the analyzer version.', | 199 help: 'Print the analyzer version.', |
205 defaultsTo: false, | 200 defaultsTo: false, |
(...skipping 28 matching lines...) Expand all Loading... |
234 help: 'Show warnings from SDK imports (deprecated).', | 229 help: 'Show warnings from SDK imports (deprecated).', |
235 defaultsTo: false, | 230 defaultsTo: false, |
236 negatable: false) | 231 negatable: false) |
237 ..addFlag('help', | 232 ..addFlag('help', |
238 abbr: 'h', | 233 abbr: 'h', |
239 help: 'Display this help message.', | 234 help: 'Display this help message.', |
240 defaultsTo: false, | 235 defaultsTo: false, |
241 negatable: false) | 236 negatable: false) |
242 ..addOption('url-mapping', | 237 ..addOption('url-mapping', |
243 help: '--url-mapping=libraryUri,/path/to/library.dart directs the ' | 238 help: '--url-mapping=libraryUri,/path/to/library.dart directs the ' |
244 'analyzer to use "library.dart" as the source for an import ' 'of "lib
raryUri".', | 239 'analyzer to use "library.dart" as the source for an import ' |
| 240 'of "libraryUri".', |
245 allowMultiple: true, | 241 allowMultiple: true, |
246 splitCommas: false) | 242 splitCommas: false) |
247 // | 243 // |
248 // Hidden flags. | 244 // Hidden flags. |
249 // | 245 // |
250 ..addFlag('enable-async', | 246 ..addFlag('enable-async', |
251 help: 'Enable support for the proposed async feature.', | 247 help: 'Enable support for the proposed async feature.', |
252 defaultsTo: false, | 248 defaultsTo: false, |
253 negatable: false, | 249 negatable: false, |
254 hide: true) | 250 hide: true) |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
307 } | 303 } |
308 } else if (results['version']) { | 304 } else if (results['version']) { |
309 print('$_binaryName version ${_getVersion()}'); | 305 print('$_binaryName version ${_getVersion()}'); |
310 exit(0); | 306 exit(0); |
311 } else { | 307 } else { |
312 if (results.rest.isEmpty) { | 308 if (results.rest.isEmpty) { |
313 _showUsage(parser); | 309 _showUsage(parser); |
314 exit(15); | 310 exit(15); |
315 } | 311 } |
316 } | 312 } |
317 Map<String, String> customUrlMappings = <String, String>{}; | 313 return new CommandLineOptions._fromArgs(results, definedVariables); |
318 for (String mapping in results['url-mapping']) { | |
319 List<String> splitMapping = mapping.split(','); | |
320 if (splitMapping.length != 2) { | |
321 _showUsage(parser); | |
322 exit(15); | |
323 } | |
324 customUrlMappings[splitMapping[0]] = splitMapping[1]; | |
325 } | |
326 return new CommandLineOptions._fromArgs( | |
327 results, definedVariables, customUrlMappings); | |
328 } on FormatException catch (e) { | 314 } on FormatException catch (e) { |
329 print(e.message); | 315 print(e.message); |
330 _showUsage(parser); | 316 _showUsage(parser); |
331 exit(15); | 317 exit(15); |
332 } | 318 } |
333 } | 319 } |
334 | 320 |
335 static _showUsage(parser) { | 321 static _showUsage(parser) { |
336 print('Usage: $_binaryName [options...] <libraries to analyze...>'); | 322 print('Usage: $_binaryName [options...] <libraries to analyze...>'); |
337 print(parser.getUsage()); | 323 print(parser.getUsage()); |
(...skipping 15 matching lines...) Expand all Loading... |
353 /// Creates a new command line parser. | 339 /// Creates a new command line parser. |
354 CommandLineParser({bool alwaysIgnoreUnrecognized: false}) | 340 CommandLineParser({bool alwaysIgnoreUnrecognized: false}) |
355 : _knownFlags = <String>[], | 341 : _knownFlags = <String>[], |
356 _alwaysIgnoreUnrecognized = alwaysIgnoreUnrecognized, | 342 _alwaysIgnoreUnrecognized = alwaysIgnoreUnrecognized, |
357 _parser = new ArgParser(allowTrailingOptions: true); | 343 _parser = new ArgParser(allowTrailingOptions: true); |
358 | 344 |
359 ArgParser get parser => _parser; | 345 ArgParser get parser => _parser; |
360 | 346 |
361 /// Defines a flag. | 347 /// Defines a flag. |
362 /// See [ArgParser.addFlag()]. | 348 /// See [ArgParser.addFlag()]. |
363 void addFlag(String name, {String abbr, String help, bool defaultsTo: false, | 349 void addFlag(String name, |
364 bool negatable: true, void callback(bool value), bool hide: false}) { | 350 {String abbr, |
| 351 String help, |
| 352 bool defaultsTo: false, |
| 353 bool negatable: true, |
| 354 void callback(bool value), |
| 355 bool hide: false}) { |
365 _knownFlags.add(name); | 356 _knownFlags.add(name); |
366 _parser.addFlag(name, | 357 _parser.addFlag(name, |
367 abbr: abbr, | 358 abbr: abbr, |
368 help: help, | 359 help: help, |
369 defaultsTo: defaultsTo, | 360 defaultsTo: defaultsTo, |
370 negatable: negatable, | 361 negatable: negatable, |
371 callback: callback, | 362 callback: callback, |
372 hide: hide); | 363 hide: hide); |
373 } | 364 } |
374 | 365 |
375 /// Defines a value-taking option. | 366 /// Defines a value-taking option. |
376 /// See [ArgParser.addOption()]. | 367 /// See [ArgParser.addOption()]. |
377 void addOption(String name, {String abbr, String help, List<String> allowed, | 368 void addOption(String name, |
378 Map<String, String> allowedHelp, String defaultsTo, void callback(value), | 369 {String abbr, |
379 bool allowMultiple: false, bool splitCommas}) { | 370 String help, |
| 371 List<String> allowed, |
| 372 Map<String, String> allowedHelp, |
| 373 String defaultsTo, |
| 374 void callback(value), |
| 375 bool allowMultiple: false, |
| 376 bool splitCommas}) { |
380 _knownFlags.add(name); | 377 _knownFlags.add(name); |
381 _parser.addOption(name, | 378 _parser.addOption(name, |
382 abbr: abbr, | 379 abbr: abbr, |
383 help: help, | 380 help: help, |
384 allowed: allowed, | 381 allowed: allowed, |
385 allowedHelp: allowedHelp, | 382 allowedHelp: allowedHelp, |
386 defaultsTo: defaultsTo, | 383 defaultsTo: defaultsTo, |
387 callback: callback, | 384 callback: callback, |
388 allowMultiple: allowMultiple, | 385 allowMultiple: allowMultiple, |
389 splitCommas: splitCommas); | 386 splitCommas: splitCommas); |
390 } | 387 } |
391 | 388 |
392 /// Generates a string displaying usage information for the defined options. | 389 /// Generates a string displaying usage information for the defined options. |
393 /// See [ArgParser.usage]. | 390 /// See [ArgParser.usage]. |
394 String getUsage() => _parser.usage; | 391 String getUsage() => _parser.usage; |
395 | 392 |
396 /// Parses [args], a list of command-line arguments, matches them against the | 393 /// Parses [args], a list of command-line arguments, matches them against the |
397 /// flags and options defined by this parser, and returns the result. The | 394 /// flags and options defined by this parser, and returns the result. The |
398 /// values of any defined variables are captured in the given map. | 395 /// values of any defined variables are captured in the given map. |
399 /// See [ArgParser]. | 396 /// See [ArgParser]. |
400 ArgResults parse( | 397 ArgResults parse(List<String> args, Map<String, String> definedVariables) => |
401 List<String> args, Map<String, String> definedVariables) => _parser | 398 _parser.parse( |
402 .parse(_filterUnknowns(parseDefinedVariables(args, definedVariables))); | 399 _filterUnknowns(parseDefinedVariables(args, definedVariables))); |
403 | 400 |
404 List<String> parseDefinedVariables( | 401 List<String> parseDefinedVariables( |
405 List<String> args, Map<String, String> definedVariables) { | 402 List<String> args, Map<String, String> definedVariables) { |
406 int count = args.length; | 403 int count = args.length; |
407 List<String> remainingArgs = <String>[]; | 404 List<String> remainingArgs = <String>[]; |
408 for (int i = 0; i < count; i++) { | 405 for (int i = 0; i < count; i++) { |
409 String arg = args[i]; | 406 String arg = args[i]; |
410 if (arg == '--') { | 407 if (arg == '--') { |
411 while (i < count) { | 408 while (i < count) { |
412 remainingArgs.add(args[i++]); | 409 remainingArgs.add(args[i++]); |
413 } | 410 } |
414 } else if (arg.startsWith("-D")) { | 411 } else if (arg.startsWith("-D")) { |
415 definedVariables[arg.substring(2)] = args[++i]; | 412 definedVariables[arg.substring(2)] = args[++i]; |
416 } else { | 413 } else { |
417 remainingArgs.add(arg); | 414 remainingArgs.add(arg); |
418 } | 415 } |
419 } | 416 } |
420 return remainingArgs; | 417 return remainingArgs; |
421 } | 418 } |
422 | 419 |
423 List<String> _filterUnknowns(List<String> args) { | 420 List<String> _filterUnknowns(List<String> args) { |
424 | |
425 // Only filter args if the ignore flag is specified, or if | 421 // Only filter args if the ignore flag is specified, or if |
426 // _alwaysIgnoreUnrecognized was set to true. | 422 // _alwaysIgnoreUnrecognized was set to true. |
427 if (_alwaysIgnoreUnrecognized || | 423 if (_alwaysIgnoreUnrecognized || |
428 args.contains('--ignore-unrecognized-flags')) { | 424 args.contains('--ignore-unrecognized-flags')) { |
429 | |
430 //TODO(pquitslund): replace w/ the following once library skew issues are | 425 //TODO(pquitslund): replace w/ the following once library skew issues are |
431 // sorted out | 426 // sorted out |
432 //return args.where((arg) => !arg.startsWith('--') || | 427 //return args.where((arg) => !arg.startsWith('--') || |
433 // _knownFlags.contains(arg.substring(2))); | 428 // _knownFlags.contains(arg.substring(2))); |
434 | 429 |
435 // Filter all unrecognized flags and options. | 430 // Filter all unrecognized flags and options. |
436 List<String> filtered = <String>[]; | 431 List<String> filtered = <String>[]; |
437 for (int i = 0; i < args.length; ++i) { | 432 for (int i = 0; i < args.length; ++i) { |
438 String arg = args[i]; | 433 String arg = args[i]; |
439 if (arg.startsWith('--') && arg.length > 2) { | 434 if (arg.startsWith('--') && arg.length > 2) { |
(...skipping 23 matching lines...) Expand all Loading... |
463 | 458 |
464 int _getNextFlagIndex(args, i) { | 459 int _getNextFlagIndex(args, i) { |
465 for (; i < args.length; ++i) { | 460 for (; i < args.length; ++i) { |
466 if (args[i].startsWith('--')) { | 461 if (args[i].startsWith('--')) { |
467 return i; | 462 return i; |
468 } | 463 } |
469 } | 464 } |
470 return i; | 465 return i; |
471 } | 466 } |
472 } | 467 } |
OLD | NEW |