| Index: pkg/analysis_server/test/stress/replay/replay.dart
|
| diff --git a/pkg/analysis_server/test/stress/replay/replay.dart b/pkg/analysis_server/test/stress/replay/replay.dart
|
| index e5525e73a2ba3418299a6e9c698fb1cc5c3f3337..2ca74e49a9942c8c9f06856a30a8bd9e6bb64a44 100644
|
| --- a/pkg/analysis_server/test/stress/replay/replay.dart
|
| +++ b/pkg/analysis_server/test/stress/replay/replay.dart
|
| @@ -5,8 +5,6 @@
|
| /**
|
| * A stress test for the analysis server.
|
| */
|
| -library analysis_server.test.stress.replay.replay;
|
| -
|
| import 'dart:async';
|
| import 'dart:io';
|
| import 'dart:math' as math;
|
| @@ -23,13 +21,14 @@ import 'package:args/args.dart';
|
| import 'package:path/path.dart' as path;
|
|
|
| import '../utilities/git.dart';
|
| +import '../utilities/logger.dart';
|
| import '../utilities/server.dart';
|
| import 'operation.dart';
|
|
|
| /**
|
| * Run the simulation based on the given command-line [arguments].
|
| */
|
| -Future main(List<String> arguments) async {
|
| +Future<Null> main(List<String> arguments) async {
|
| Driver driver = new Driver();
|
| await driver.run(arguments);
|
| }
|
| @@ -74,6 +73,12 @@ class Driver {
|
| static const String TEMP_BRANCH_NAME = 'temp';
|
|
|
| /**
|
| + * The name of the command-line flag that will cause verbose output to be
|
| + * produced.
|
| + */
|
| + static String VERBOSE_FLAG_NAME = 'verbose';
|
| +
|
| + /**
|
| * The style of interaction to use for analysis.updateContent requests.
|
| */
|
| OverlayStyle overlayStyle;
|
| @@ -96,7 +101,7 @@ class Driver {
|
| /**
|
| * The connection to the analysis server.
|
| */
|
| - Server server = new Server();
|
| + Server server;
|
|
|
| /**
|
| * A list of the glob patterns used to identify the files being analyzed by
|
| @@ -110,6 +115,16 @@ class Driver {
|
| Statistics statistics;
|
|
|
| /**
|
| + * A flag indicating whether verbose output should be provided.
|
| + */
|
| + bool verbose = false;
|
| +
|
| + /**
|
| + * The logger to which verbose logging data will be written.
|
| + */
|
| + Logger logger;
|
| +
|
| + /**
|
| * Initialize a newly created driver.
|
| */
|
| Driver() {
|
| @@ -117,15 +132,27 @@ class Driver {
|
| }
|
|
|
| /**
|
| + * Allow the output from the server to be read and processed.
|
| + */
|
| + Future<Null> readServerOutput() async {
|
| + await new Future.delayed(new Duration(milliseconds: 2));
|
| + }
|
| +
|
| + /**
|
| * Run the simulation based on the given command-line arguments ([args]).
|
| */
|
| - Future run(List<String> args) async {
|
| + Future<Null> run(List<String> args) async {
|
| //
|
| // Process the command-line arguments.
|
| //
|
| if (!_processCommandLine(args)) {
|
| return null;
|
| }
|
| + if (verbose) {
|
| + stdout.writeln();
|
| + stdout.writeln('-' * 80);
|
| + stdout.writeln();
|
| + }
|
| //
|
| // Simulate interactions with the server.
|
| //
|
| @@ -133,7 +160,16 @@ class Driver {
|
| //
|
| // Print out statistics gathered while performing the simulation.
|
| //
|
| + if (verbose) {
|
| + stdout.writeln();
|
| + stdout.writeln('-' * 80);
|
| + }
|
| + stdout.writeln();
|
| statistics.print();
|
| + if (verbose) {
|
| + stdout.writeln();
|
| + server.printStatistics();
|
| + }
|
| exit(0);
|
| return null;
|
| }
|
| @@ -149,7 +185,6 @@ class Driver {
|
| help: 'Print usage information',
|
| defaultsTo: false,
|
| negatable: false);
|
| -
|
| parser.addOption(OVERLAY_STYLE_OPTION_NAME,
|
| help:
|
| 'The style of interaction to use for analysis.updateContent requests',
|
| @@ -159,6 +194,11 @@ class Driver {
|
| MULTIPLE_ADD_OVERLAY_STYLE: '<add>+ <remove>'
|
| },
|
| defaultsTo: 'change');
|
| + parser.addFlag(VERBOSE_FLAG_NAME,
|
| + abbr: 'v',
|
| + help: 'Produce verbose output for debugging',
|
| + defaultsTo: false,
|
| + negatable: false);
|
| return parser;
|
| }
|
|
|
| @@ -286,13 +326,18 @@ class Driver {
|
| overlayStyle = OverlayStyle.multipleAdd;
|
| }
|
|
|
| - List<String> arguments = results.arguments;
|
| + if (results[VERBOSE_FLAG_NAME]) {
|
| + verbose = true;
|
| + logger = new Logger(stdout);
|
| + }
|
| +
|
| + List<String> arguments = results.rest;
|
| if (arguments.length < 2) {
|
| _showUsage(parser);
|
| return false;
|
| }
|
| repositoryPath = path.normalize(arguments[0]);
|
| - repository = new GitRepository(repositoryPath);
|
| + repository = new GitRepository(repositoryPath, logger: logger);
|
|
|
| analysisRoots = arguments
|
| .sublist(1)
|
| @@ -312,66 +357,69 @@ class Driver {
|
| /**
|
| * Replay the changes in each commit.
|
| */
|
| - Future _replayChanges() async {
|
| + Future<Null> _replayChanges() async {
|
| //
|
| // Get the revision history of the repo.
|
| //
|
| LinearCommitHistory history = repository.getCommitHistory();
|
| statistics.commitCount = history.commitIds.length;
|
| LinearCommitHistoryIterator iterator = history.iterator();
|
| - //
|
| - // Iterate over the history, applying changes.
|
| - //
|
| - int dotCount = 0;
|
| - bool firstCheckout = true;
|
| - ErrorMap expectedErrors = null;
|
| - Iterable<String> changedPubspecs;
|
| - while (iterator.moveNext()) {
|
| + try {
|
| //
|
| - // Checkout the commit on which the changes are based.
|
| + // Iterate over the history, applying changes.
|
| //
|
| - String commit = iterator.srcCommit;
|
| - repository.checkout(commit);
|
| - if (expectedErrors != null) {
|
| - ErrorMap actualErrors =
|
| - await server.computeErrorMap(server.analyzedDartFiles);
|
| - String difference = expectedErrors.expectErrorMap(actualErrors);
|
| - if (difference != null) {
|
| - stdout.write('Mismatched errors after commit ');
|
| - stdout.writeln(commit);
|
| - stdout.writeln();
|
| - stdout.writeln(difference);
|
| - return;
|
| + bool firstCheckout = true;
|
| + ErrorMap expectedErrors = null;
|
| + Iterable<String> changedPubspecs;
|
| + while (iterator.moveNext()) {
|
| + //
|
| + // Checkout the commit on which the changes are based.
|
| + //
|
| + String commit = iterator.srcCommit;
|
| + repository.checkout(commit);
|
| + if (expectedErrors != null) {
|
| +// ErrorMap actualErrors =
|
| + await server.computeErrorMap(server.analyzedDartFiles);
|
| +// String difference = expectedErrors.expectErrorMap(actualErrors);
|
| +// if (difference != null) {
|
| +// stdout.write('Mismatched errors after commit ');
|
| +// stdout.writeln(commit);
|
| +// stdout.writeln();
|
| +// stdout.writeln(difference);
|
| +// return;
|
| +// }
|
| }
|
| + if (firstCheckout) {
|
| + changedPubspecs = _findPubspecsInAnalysisRoots();
|
| + server.sendAnalysisSetAnalysisRoots(analysisRoots, []);
|
| + firstCheckout = false;
|
| + } else {
|
| + server.removeAllOverlays();
|
| + }
|
| + await readServerOutput();
|
| + expectedErrors = await server.computeErrorMap(server.analyzedDartFiles);
|
| + for (String filePath in changedPubspecs) {
|
| + _runPub(filePath);
|
| + }
|
| + //
|
| + // Apply the changes.
|
| + //
|
| + CommitDelta commitDelta = iterator.next();
|
| + commitDelta.filterDiffs(analysisRoots, fileGlobs);
|
| + if (commitDelta.hasDiffs) {
|
| + statistics.commitsWithChangeInRootCount++;
|
| + await _replayDiff(commitDelta);
|
| + }
|
| + changedPubspecs = commitDelta.filesMatching(PUBSPEC_FILE_NAME);
|
| }
|
| - if (firstCheckout) {
|
| - changedPubspecs = _findPubspecsInAnalysisRoots();
|
| - server.sendAnalysisSetAnalysisRoots(analysisRoots, []);
|
| - firstCheckout = false;
|
| - } else {
|
| - server.removeAllOverlays();
|
| - }
|
| - expectedErrors = await server.computeErrorMap(server.analyzedDartFiles);
|
| - for (String filePath in changedPubspecs) {
|
| - _runPub(filePath);
|
| - }
|
| - //
|
| - // Apply the changes.
|
| - //
|
| - CommitDelta commitDelta = iterator.next();
|
| - commitDelta.filterDiffs(analysisRoots, fileGlobs);
|
| - if (commitDelta.hasDiffs) {
|
| - statistics.commitsWithChangeInRootCount++;
|
| - _replayDiff(commitDelta);
|
| - }
|
| - changedPubspecs = commitDelta.filesMatching(PUBSPEC_FILE_NAME);
|
| - stdout.write('.');
|
| - if (dotCount++ > 100) {
|
| - stdout.writeln();
|
| - dotCount = 0;
|
| + } finally {
|
| + // Ensure that the repository is left at the most recent commit.
|
| + if (history.commitIds.length > 0) {
|
| + repository.checkout(history.commitIds[0]);
|
| }
|
| }
|
| server.removeAllOverlays();
|
| + await readServerOutput();
|
| stdout.writeln();
|
| }
|
|
|
| @@ -379,7 +427,7 @@ class Driver {
|
| * Replay the changes between two commits, as represented by the given
|
| * [commitDelta].
|
| */
|
| - void _replayDiff(CommitDelta commitDelta) {
|
| + Future<Null> _replayDiff(CommitDelta commitDelta) async {
|
| List<FileEdit> editList = <FileEdit>[];
|
| for (DiffRecord record in commitDelta.diffRecords) {
|
| FileEdit edit = new FileEdit(overlayStyle, record);
|
| @@ -404,7 +452,9 @@ class Driver {
|
| AnalysisService.OVERRIDES: currentFile
|
| });
|
| for (ServerOperation operation in edit.getOperations()) {
|
| + statistics.editCount++;
|
| operation.perform(server);
|
| + await readServerOutput();
|
| }
|
| }
|
| }
|
| @@ -424,7 +474,8 @@ class Driver {
|
| /**
|
| * Run the simulation by starting up a server and sending it requests.
|
| */
|
| - Future _runSimulation() async {
|
| + Future<Null> _runSimulation() async {
|
| + server = new Server(logger: logger);
|
| Stopwatch stopwatch = new Stopwatch();
|
| statistics.stopwatch = stopwatch;
|
| stopwatch.start();
|
| @@ -443,6 +494,8 @@ class Driver {
|
| try {
|
| await _replayChanges();
|
| } finally {
|
| + // TODO(brianwilkerson) This needs to be moved into a Zone in order to
|
| + // ensure that it is always run.
|
| server.sendServerShutdown();
|
| repository.checkout('master');
|
| }
|
| @@ -450,7 +503,7 @@ class Driver {
|
| }
|
|
|
| /**
|
| - * Display usage information, preceeded by the [errorMessage] if one is given.
|
| + * Display usage information, preceded by the [errorMessage] if one is given.
|
| */
|
| void _showUsage(ArgParser parser, [String errorMessage = null]) {
|
| if (errorMessage != null) {
|
| @@ -469,7 +522,7 @@ repository.
|
|
|
| There must be at least one analysis root, and all of the analysis roots must be
|
| the absolute path of a directory contained within the repository directory. The
|
| -analysis roots represent the portion of the repository that will be analyzed by
|
| +analysis roots represent the portions of the repository that will be analyzed by
|
| the analysis server.
|
|
|
| OPTIONS:''');
|
| @@ -604,6 +657,11 @@ class Statistics {
|
| int commitsWithChangeInRootCount = 0;
|
|
|
| /**
|
| + * The total number of edits that were applied.
|
| + */
|
| + int editCount = 0;
|
| +
|
| + /**
|
| * Initialize a newly created set of statistics.
|
| */
|
| Statistics(this.driver);
|
| @@ -622,6 +680,8 @@ class Statistics {
|
| stdout.writeln(commitCount);
|
| stdout.write(' number of commits with a change in an analysis root = ');
|
| stdout.writeln(commitsWithChangeInRootCount);
|
| + stdout.write(' number of edits = ');
|
| + stdout.writeln(editCount);
|
| }
|
|
|
| /**
|
|
|