| Index: pkg/analysis_server/benchmark/perf/benchmarks_impl.dart
|
| diff --git a/pkg/analysis_server/benchmark/perf/benchmarks_impl.dart b/pkg/analysis_server/benchmark/perf/benchmarks_impl.dart
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..8b2c0695abc9836a29f9b113c34afd4010bfb921
|
| --- /dev/null
|
| +++ b/pkg/analysis_server/benchmark/perf/benchmarks_impl.dart
|
| @@ -0,0 +1,183 @@
|
| +// Copyright (c) 2017, the Dart project authors. Please see the AUTHORS file
|
| +// for details. All rights reserved. Use of this source code is governed by a
|
| +// BSD-style license that can be found in the LICENSE file.
|
| +
|
| +import 'dart:async';
|
| +import 'dart:io';
|
| +
|
| +import 'package:analysis_server/src/protocol_server.dart';
|
| +import 'package:path/path.dart' as path;
|
| +
|
| +import '../../test/integration/support/integration_tests.dart';
|
| +import '../benchmarks.dart';
|
| +import 'memory_tests.dart';
|
| +
|
| +/// benchmarks:
|
| +/// - analysis-server-cold-analysis
|
| +/// - analysis-server-cold-memory
|
| +class ColdAnalysisBenchmark extends Benchmark {
|
| + ColdAnalysisBenchmark()
|
| + : super(
|
| + 'analysis-server-cold',
|
| + 'Analysis server benchmarks of a large project on start-up, no '
|
| + 'existing driver cache.',
|
| + );
|
| +
|
| + int get maxIterations => 3;
|
| +
|
| + @override
|
| + Future<BenchMarkResult> run({bool quick: false}) async {
|
| + deleteServerCache();
|
| +
|
| + Stopwatch stopwatch = new Stopwatch()..start();
|
| +
|
| + AnalysisServerMemoryUsageTest test = new AnalysisServerMemoryUsageTest();
|
| + await test.setUp();
|
| + await test.subscribeToStatusNotifications();
|
| + await test.sendAnalysisSetAnalysisRoots(getProjectRoots(quick: quick), []);
|
| + await test.analysisFinished;
|
| +
|
| + stopwatch.stop();
|
| + int usedBytes = test.getMemoryUsage();
|
| +
|
| + CompoundBenchMarkResult result = new CompoundBenchMarkResult(id);
|
| + result.add('analysis',
|
| + new BenchMarkResult('micros', stopwatch.elapsedMicroseconds));
|
| + result.add('memory', new BenchMarkResult('bytes', usedBytes));
|
| +
|
| + await test.shutdown();
|
| +
|
| + return result;
|
| + }
|
| +}
|
| +
|
| +/// benchmarks:
|
| +/// - analysis-server-warm-analysis
|
| +/// - analysis-server-warm-memory
|
| +/// - analysis-server-edit
|
| +/// - analysis-server-completion
|
| +class AnalysisBenchmark extends Benchmark {
|
| + AnalysisBenchmark()
|
| + : super(
|
| + 'analysis-server',
|
| + 'Analysis server benchmarks of a large project, with an existing '
|
| + 'driver cache.',
|
| + );
|
| +
|
| + @override
|
| + Future<BenchMarkResult> run({bool quick: false}) async {
|
| + Stopwatch stopwatch = new Stopwatch()..start();
|
| +
|
| + AnalysisServerMemoryUsageTest test = new AnalysisServerMemoryUsageTest();
|
| + await test.setUp();
|
| + await test.subscribeToStatusNotifications();
|
| + await test.sendAnalysisSetAnalysisRoots(getProjectRoots(quick: quick), []);
|
| + await test.analysisFinished;
|
| +
|
| + stopwatch.stop();
|
| + int usedBytes = test.getMemoryUsage();
|
| +
|
| + CompoundBenchMarkResult result = new CompoundBenchMarkResult(id);
|
| + result.add('warm-analysis',
|
| + new BenchMarkResult('micros', stopwatch.elapsedMicroseconds));
|
| + result.add('warm-memory', new BenchMarkResult('bytes', usedBytes));
|
| +
|
| + if (!quick) {
|
| + // change timing
|
| + final int editMicros = await _calcEditTiming(test);
|
| + result.add('edit', new BenchMarkResult('micros', editMicros));
|
| +
|
| + // code completion
|
| + final int completionMicros = await _calcCompletionTiming(test);
|
| + result.add('completion', new BenchMarkResult('micros', completionMicros));
|
| + }
|
| +
|
| + await test.shutdown();
|
| +
|
| + return result;
|
| + }
|
| +
|
| + Future<int> _calcEditTiming(
|
| + AbstractAnalysisServerIntegrationTest test) async {
|
| + const int kGroupCount = 5;
|
| +
|
| + final String filePath =
|
| + path.join(analysisServerSrcPath, 'lib/src/analysis_server.dart');
|
| + String contents = new File(filePath).readAsStringSync();
|
| +
|
| + await test
|
| + .sendAnalysisUpdateContent({filePath: new AddContentOverlay(contents)});
|
| +
|
| + final Stopwatch stopwatch = new Stopwatch()..start();
|
| +
|
| + for (int i = 0; i < kGroupCount; i++) {
|
| + int startIndex = i * (contents.length ~/ (kGroupCount + 2));
|
| + int index = contents.indexOf(';', startIndex);
|
| + contents = contents.substring(0, index + 1) +
|
| + ' ' +
|
| + contents.substring(index + 1);
|
| + test.sendAnalysisUpdateContent(
|
| + {filePath: new AddContentOverlay(contents)});
|
| + await test.analysisFinished;
|
| + }
|
| +
|
| + stopwatch.stop();
|
| +
|
| + return stopwatch.elapsedMicroseconds ~/ kGroupCount;
|
| + }
|
| +
|
| + Future<int> _calcCompletionTiming(
|
| + AbstractAnalysisServerIntegrationTest test) async {
|
| + const int kGroupCount = 10;
|
| +
|
| + final String filePath =
|
| + path.join(analysisServerSrcPath, 'lib/src/analysis_server.dart');
|
| + String contents = new File(filePath).readAsStringSync();
|
| +
|
| + await test
|
| + .sendAnalysisUpdateContent({filePath: new AddContentOverlay(contents)});
|
| +
|
| + int completionCount = 0;
|
| + final Stopwatch stopwatch = new Stopwatch()..start();
|
| +
|
| + Future _complete(int offset) async {
|
| + CompletionGetSuggestionsResult result =
|
| + await test.sendCompletionGetSuggestions(filePath, offset);
|
| +
|
| + Future<CompletionResultsParams> future = test.onCompletionResults
|
| + .where((CompletionResultsParams params) =>
|
| + params.id == result.id && params.isLast)
|
| + .first;
|
| + await future;
|
| +
|
| + completionCount++;
|
| + }
|
| +
|
| + for (int i = 0; i < kGroupCount; i++) {
|
| + int startIndex = i * (contents.length ~/ (kGroupCount + 2));
|
| + // Look for a line with a period in it that ends with a semi-colon.
|
| + int index =
|
| + contents.indexOf(new RegExp(r'\..*;$', multiLine: true), startIndex);
|
| +
|
| + await _complete(index - 10);
|
| + await _complete(index - 1);
|
| + await _complete(index);
|
| + await _complete(index + 1);
|
| + await _complete(index + 10);
|
| +
|
| + if (i + 1 < kGroupCount) {
|
| + // mutate
|
| + index = contents.indexOf(';', index);
|
| + contents = contents.substring(0, index + 1) +
|
| + ' ' +
|
| + contents.substring(index + 1);
|
| + await test.sendAnalysisUpdateContent(
|
| + {filePath: new AddContentOverlay(contents)});
|
| + }
|
| + }
|
| +
|
| + stopwatch.stop();
|
| +
|
| + return stopwatch.elapsedMicroseconds ~/ completionCount;
|
| + }
|
| +}
|
|
|