Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1730)

Unified Diff: pkg/analysis_server_client/lib/analysis_server_client.dart

Issue 2994723003: Add analysis_server_client without analysis_server (Closed)
Patch Set: feedback fixes Created 3 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « pkg/analysis_server_client/README.md ('k') | pkg/analysis_server_client/pubspec.yaml » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: pkg/analysis_server_client/lib/analysis_server_client.dart
diff --git a/pkg/analysis_server_client/lib/analysis_server_client.dart b/pkg/analysis_server_client/lib/analysis_server_client.dart
new file mode 100644
index 0000000000000000000000000000000000000000..96286e40dd94c92e8e016ec7b244d241db1d5c2a
--- /dev/null
+++ b/pkg/analysis_server_client/lib/analysis_server_client.dart
@@ -0,0 +1,101 @@
+// 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:convert';
+import 'dart:io';
+
+/// Type of callbacks used to process notification.
+typedef void NotificationProcessor(String event, Map<String, Object> params);
+
+/// Instances of the class [AnalysisServerClient] manage a connection to an
+/// [AnalysisServer] process, and facilitate communication to and from the
+/// client/user.
+class AnalysisServerClient {
+ /// AnalysisServer process object, or null if the server has been shut down.
+ final Process _process;
+
+ /// Commands that have been sent to the server but not yet acknowledged,
+ /// and the [Completer] objects which should be completed when
+ /// acknowledgement is received.
+ final Map<String, Completer> _pendingCommands = <String, Completer>{};
+
+ /// Number which should be used to compute the 'id' to send to the next
+ /// command sent to the server.
+ int _nextId = 0;
+
+ AnalysisServerClient(this._process);
+
+ /// Return a future that will complete when all commands that have been
+ /// sent to the server so far have been flushed to the OS buffer.
+ Future<Null> flushCommands() {
+ return _process.stdin.flush();
+ }
+
+ void listenToOutput({NotificationProcessor notificationProcessor}) {
+ _process.stdout
+ .transform((new Utf8Codec()).decoder)
+ .transform(new LineSplitter())
+ .listen((String line) {
+ String trimmedLine = line.trim();
+ if (trimmedLine.startsWith('Observatory listening on ')) {
+ return;
+ }
+ final result = JSON.decoder.convert(trimmedLine) as Map;
+ if (result.containsKey('id')) {
+ final id = result['id'] as String;
+ final completer = _pendingCommands.remove(id);
+
+ if (result.containsKey('error')) {
+ completer.completeError(new ServerErrorMessage(result['error']));
+ } else {
+ completer.complete(result['result']);
+ }
+ } else if (notificationProcessor != null && result.containsKey('event')) {
+ // Message is a notification. It should have an event and possibly
+ // params.
+ notificationProcessor(result['event'], result['params']);
+ }
+ });
+ }
+
+ /// Sends a command to the server. An 'id' will be automatically assigned.
+ /// The returned [Future] will be completed when the server acknowledges
+ /// the command with a response. If the server acknowledges the command
+ /// with a normal (non-error) response, the future will be completed
+ /// with the 'result' field from the response. If the server acknowledges
+ /// the command with an error response, the future will be completed with an
+ /// error.
+ Future send(String method, Map<String, dynamic> params) {
+ String id = '${_nextId++}';
+ Map<String, dynamic> command = <String, dynamic>{
+ 'id': id,
+ 'method': method
+ };
+ if (params != null) {
+ command['params'] = params;
+ }
+ Completer completer = new Completer();
+ _pendingCommands[id] = completer;
+ String commandAsJson = JSON.encode(command);
+ _process.stdin.add(UTF8.encoder.convert('$commandAsJson\n'));
+ return completer.future;
+ }
+
+ /// Force kill the server. Returns exit code future.
+ Future<int> kill() {
+ _process.kill();
+ return _process.exitCode;
+ }
+}
+
+class ServerErrorMessage {
+ final Map errorJson;
+
+ ServerErrorMessage(this.errorJson);
+
+ String get code => errorJson['code'].toString();
+ String get message => errorJson['message'];
+ String get stackTrace => errorJson['stackTrace'];
+}
« no previous file with comments | « pkg/analysis_server_client/README.md ('k') | pkg/analysis_server_client/pubspec.yaml » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698