OLD | NEW |
| (Empty) |
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | |
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. | |
4 | |
5 import 'dart:async'; | |
6 import 'dart:io'; | |
7 | |
8 import 'package:args/args.dart'; | |
9 import 'package:matcher/matcher.dart'; | |
10 import 'package:path/path.dart' as path; | |
11 | |
12 import 'fuzz/server_manager.dart'; | |
13 | |
14 /** | |
15 * Start analysis server as a separate process and use the stdio to communicate | |
16 * with the server. | |
17 */ | |
18 void main(List<String> args) { | |
19 new _FuzzTest().run(args); | |
20 } | |
21 | |
22 /** | |
23 * Instances of [_FuzzTest] launch and test an analysis server. | |
24 * You must specify the location of the Dart SDK and the directory | |
25 * containing sources to be analyzed. | |
26 */ | |
27 class _FuzzTest { | |
28 /** | |
29 * The name of the application that is used to start the fuzz tester. | |
30 */ | |
31 static const BINARY_NAME = 'fuzz'; | |
32 | |
33 //TODO (danrubel) extract common behavior for use in multiple test scenarios | |
34 //TODO (danrubel) cleanup test to use async/await for better readability | |
35 // VM flag --enable_async | |
36 | |
37 static const String DART_SDK_OPTION = 'dart-sdk'; | |
38 static const String HELP_OPTION = 'help'; | |
39 | |
40 File serverSnapshot; | |
41 Directory appDir; | |
42 | |
43 /// Parse the arguments and initialize the receiver | |
44 /// Return `true` if proper arguments were provided | |
45 bool parseArgs(List<String> args) { | |
46 ArgParser parser = new ArgParser(); | |
47 | |
48 void error(String errMsg) { | |
49 stderr.writeln(errMsg); | |
50 print(''); | |
51 _printUsage(parser); | |
52 exitCode = 11; | |
53 } | |
54 | |
55 parser.addOption(DART_SDK_OPTION, help: '[sdkPath] path to Dart SDK'); | |
56 parser.addFlag( | |
57 HELP_OPTION, | |
58 help: 'print this help message without starting analysis', | |
59 defaultsTo: false, | |
60 negatable: false); | |
61 | |
62 ArgResults results; | |
63 try { | |
64 results = parser.parse(args); | |
65 } on FormatException catch (e) { | |
66 error(e.message); | |
67 return false; | |
68 } | |
69 if (results[HELP_OPTION]) { | |
70 _printUsage(parser); | |
71 return false; | |
72 } | |
73 String sdkPath = results[DART_SDK_OPTION]; | |
74 if (sdkPath is! String) { | |
75 error('Missing path to Dart SDK'); | |
76 return false; | |
77 } | |
78 Directory sdkDir = new Directory(sdkPath); | |
79 if (!sdkDir.existsSync()) { | |
80 error('Specified Dart SDK does not exist: $sdkPath'); | |
81 return false; | |
82 } | |
83 if (results.rest.length == 0) { | |
84 error('Expected directory to analyze'); | |
85 return false; | |
86 } | |
87 appDir = new Directory(results.rest[0]); | |
88 if (!appDir.existsSync()) { | |
89 error('Specified application directory does not exist: $appDir'); | |
90 return false; | |
91 } | |
92 if (results.rest.length > 1) { | |
93 error('Unexpected arguments after $appDir'); | |
94 return false; | |
95 } | |
96 serverSnapshot = new File( | |
97 path.join(sdkDir.path, 'bin', 'snapshots', 'analysis_server.dart.snapsho
t')); | |
98 if (!serverSnapshot.existsSync()) { | |
99 error('Analysis Server snapshot not found: $serverSnapshot'); | |
100 return false; | |
101 } | |
102 return true; | |
103 } | |
104 | |
105 /// Main entry point for launching, testing, and shutting down the server | |
106 void run(List<String> args) { | |
107 if (!parseArgs(args)) return; | |
108 ServerManager.start(serverSnapshot.path).then((ServerManager manager) { | |
109 runZoned(() { | |
110 test(manager).then(manager.stop).then((_) { | |
111 expect(manager.errorOccurred, isFalse); | |
112 print('Test completed successfully'); | |
113 }); | |
114 }, onError: (error, stack) { | |
115 stderr.writeln(error); | |
116 print(stack); | |
117 exitCode = 12; | |
118 manager.stop(); | |
119 }); | |
120 }); | |
121 } | |
122 | |
123 /// Use manager to exercise the analysis server | |
124 Future test(ServerManager manager) { | |
125 | |
126 // perform initial analysis | |
127 return manager.analyze(appDir).then((AnalysisResults analysisResults) { | |
128 print( | |
129 'Found ${analysisResults.errorCount} errors,' | |
130 ' ${analysisResults.warningCount} warnings,' | |
131 ' and ${analysisResults.hintCount} hints in ${analysisResults.elap
sed}'); | |
132 | |
133 // edit a method body | |
134 return manager.openFileNamed( | |
135 'domain_completion.dart').then((Editor editor) { | |
136 return editor.moveAfter('Response processRequest(Request request) {'); | |
137 }).then((Editor editor) { | |
138 return editor.replace(0, '\nOb'); | |
139 }).then((Editor editor) { | |
140 | |
141 // request code completion and assert results | |
142 return editor.getSuggestions().then((List<CompletionResults> list) { | |
143 expect(list, isNotNull); | |
144 expect(list.length, equals(0)); | |
145 list.forEach((CompletionResults results) { | |
146 print( | |
147 '${results.elapsed} received ${results.suggestionCount} suggesti
ons'); | |
148 }); | |
149 return editor; | |
150 }); | |
151 | |
152 }).then((Editor editor) { | |
153 print('tests complete'); | |
154 }); | |
155 }); | |
156 } | |
157 | |
158 // void _printAnalysisSummary(AnalysisResults results) { | |
159 // print( | |
160 // 'Found ${results.errorCount} errors, ${results.warningCount} warnings,
' | |
161 // ' and ${results.hintCount} hints in $results.elapsed'); | |
162 // } | |
163 | |
164 /// Print information about how to use the server. | |
165 void _printUsage(ArgParser parser) { | |
166 print('Usage: $BINARY_NAME [flags] <application_directory>'); | |
167 print(''); | |
168 print('Supported flags are:'); | |
169 print(parser.usage); | |
170 } | |
171 } | |
OLD | NEW |