Unverified Commit a226c0f0 authored by Jonah Williams's avatar Jonah Williams Committed by GitHub

Add a flutter-attach entry point for fuchsia (#24878)

parent 5391447f
......@@ -237,19 +237,15 @@ dart_tool("fuchsia_tester") {
]
}
dart_tool("fuchsia_tools") {
package_name = "fuchsia_tools"
main_dart = "bin/fuchsia_tools.dart"
dart_tool("fuchsia_attach") {
package_name = "fuchsia_attach"
main_dart = "bin/fuchsia_attach.dart"
# Can be left empty as analysis is disabled.
sources = []
disable_analysis = true
non_dart_deps = [
"//third_party/flutter/frontend_server:frontend_server_tool",
]
deps = [
":flutter_tools",
]
......
// Copyright 2018 The Chromium Authors. 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 'package:args/args.dart';
import 'package:flutter_tools/runner.dart' as runner;
import 'package:flutter_tools/src/artifacts.dart';
import 'package:flutter_tools/src/base/common.dart';
import 'package:flutter_tools/src/base/context.dart';
import 'package:flutter_tools/src/base/file_system.dart';
import 'package:flutter_tools/src/cache.dart';
import 'package:flutter_tools/src/commands/attach.dart';
import 'package:flutter_tools/src/commands/doctor.dart';
import 'package:flutter_tools/src/fuchsia/fuchsia_sdk.dart';
import 'package:flutter_tools/src/run_hot.dart';
import 'package:flutter_tools/src/runner/flutter_command.dart';
final ArgParser parser = ArgParser()
..addOption('build-dir', help: 'The fuchsia build directory')
..addOption('dart-sdk', help: 'The prebuilt dart SDK')
..addOption('target', help: 'The GN target to attach to')
..addFlag('verbose', negatable: true);
// Track the original working directory so that the tool can find the
// flutter repo in third_party.
String originalWorkingDirectory;
Future<void> main(List<String> args) async {
final ArgResults argResults = parser.parse(args);
final bool verbose = argResults['verbose'];
final String target = argResults['target'];
final List<String> targetParts = _extractPathAndName(target);
final String path = targetParts[0];
final String name = targetParts[1];
final File dartSdk = fs.file(argResults['dart-sdk']);
final String buildDirectory = argResults['build-dir'];
final File frontendServer = fs.file('$buildDirectory/host_x64/gen/third_party/flutter/frontend_server/frontend_server_tool.snapshot');
final File sshConfig = fs.file('$buildDirectory/ssh-keys/ssh_config');
final File platformKernelDill = fs.file('$buildDirectory/flutter_runner_patched_sdk/platform_strong.dill');
final File flutterPatchedSdk = fs.file('$buildDirectory/flutter_runner_patched_sdk');
final String packages = '$buildDirectory/dartlang/gen/$path/${name}_dart_library.packages';
final String outputDill = '$buildDirectory/${name}_tmp.dill';
// TODO(jonahwilliams): running from fuchsia root hangs hot reload for some reason.
// switch to the project root directory and run from there.
originalWorkingDirectory = fs.currentDirectory.path;
fs.currentDirectory = path;
// Check for a package with a lib directory.
String targetFile = 'lib/main.dart';
if (!fs.file(targetFile).existsSync()) {
// Otherwise assume the package is flat.
targetFile = 'main.dart';
}
final List<String> command = <String>[
'attach',
'--module',
name,
'--isolate-filter',
name,
'--target',
targetFile,
'--target-model',
'flutter', // TODO(jonahwilliams): change to flutter_runner when dart SDK rolls
'--output-dill',
outputDill,
'--packages',
packages,
];
if (verbose) {
command.add('--verbose');
}
Cache.disableLocking(); // ignore: invalid_use_of_visible_for_testing_member
await runner.run(
command,
<FlutterCommand>[
_FuchsiaAttachCommand(),
_FuchsiaDoctorCommand(), // If attach fails the tool will attempt to run doctor.
],
verbose: verbose,
muteCommandLogging: false,
verboseHelp: false,
overrides: <Type, Generator>{
FuchsiaArtifacts: () => FuchsiaArtifacts(sshConfig: sshConfig),
Artifacts: () => OverrideArtifacts(
parent: CachedArtifacts(),
frontendServer: frontendServer,
engineDartBinary: dartSdk,
platformKernelDill: platformKernelDill,
flutterPatchedSdk: flutterPatchedSdk,
),
HotRunnerConfig: () => HotRunnerConfig()..computeDartDependencies = false,
}
);
}
List<String> _extractPathAndName(String gnTarget) {
// Separate strings like //path/to/target:app into [path/to/target, app]
final int lastColon = gnTarget.lastIndexOf(':');
if (lastColon < 0) {
throwToolExit('invalid path: $gnTarget');
}
final String name = gnTarget.substring(lastColon + 1);
// Skip '//' and chop off after :
if ((gnTarget.length < 3) || (gnTarget[0] != '/') || (gnTarget[1] != '/')) {
throwToolExit('invalid path: $gnTarget');
}
final String path = gnTarget.substring(2, lastColon);
return <String>[path, name];
}
class _FuchsiaDoctorCommand extends DoctorCommand {
@override
Future<FlutterCommandResult> runCommand() async {
Cache.flutterRoot = '$originalWorkingDirectory/third_party/dart-pkg/git/flutter';
return super.runCommand();
}
}
class _FuchsiaAttachCommand extends AttachCommand {
@override
Future<FlutterCommandResult> runCommand() async {
Cache.flutterRoot = '$originalWorkingDirectory/third_party/dart-pkg/git/flutter';
return super.runCommand();
}
}
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'package:flutter_tools/fuchsia_executable.dart' as executable;
void main(List<String> args) {
executable.main(args);
}
// Copyright 2018 The Chromium Authors. 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 'package:args/args.dart';
import 'runner.dart' as runner;
import 'src/artifacts.dart';
import 'src/base/common.dart';
import 'src/base/context.dart';
import 'src/base/file_system.dart';
import 'src/commands/attach.dart';
import 'src/commands/devices.dart';
import 'src/commands/shell_completion.dart';
import 'src/fuchsia/fuchsia_sdk.dart';
import 'src/run_hot.dart';
import 'src/runner/flutter_command.dart';
final ArgParser parser = ArgParser.allowAnything()
..addOption('verbose', abbr: 'v')
..addOption('help', abbr: 'h')
..addOption(
'frontend-server',
help: 'The path to the frontend server snapshot.',
)
..addOption(
'dart-sdk',
help: 'The path to the patched dart-sdk binary.',
)
..addOption(
'ssh-config',
help: 'The path to the ssh configuration file.',
);
/// Main entry point for fuchsia commands.
///
/// This function is intended to be used within the fuchsia source tree.
Future<void> main(List<String> args) async {
final ArgResults results = parser.parse(args);
final bool verbose = results['verbose'];
final bool help = results['help'];
final bool verboseHelp = help && verbose;
final File dartSdk = fs.file(results['dart-sdk']);
final File frontendServer = fs.file(results['frontend-server']);
final File sshConfig = fs.file(results['ssh-config']);
if (!dartSdk.existsSync()) {
throwToolExit('--dart-sdk is required: ${dartSdk.path} does not exist.');
}
if (!frontendServer.existsSync()) {
throwToolExit('--frontend-server is required: ${frontendServer.path} does not exist.');
}
if (!sshConfig.existsSync()) {
throwToolExit('--ssh-config is required: ${sshConfig.path} does not exist.');
}
await runner.run(args, <FlutterCommand>[
AttachCommand(verboseHelp: verboseHelp),
DevicesCommand(),
ShellCompletionCommand(),
], verbose: verbose,
muteCommandLogging: help,
verboseHelp: verboseHelp,
overrides: <Type, Generator>{
FuchsiaArtifacts: () => FuchsiaArtifacts(sshConfig: sshConfig),
Artifacts: () => OverrideArtifacts(
parent: CachedArtifacts(),
frontendServer: frontendServer,
engineDartBinary: dartSdk,
),
HotRunnerConfig: () => HotRunnerConfig()
..computeDartDependencies = false,
});
}
......@@ -311,11 +311,15 @@ class OverrideArtifacts implements Artifacts {
@required this.parent,
this.frontendServer,
this.engineDartBinary,
this.platformKernelDill,
this.flutterPatchedSdk,
}) : assert(parent != null);
final Artifacts parent;
final File frontendServer;
final File engineDartBinary;
final File platformKernelDill;
final File flutterPatchedSdk;
@override
String getArtifactPath(Artifact artifact, [TargetPlatform platform, BuildMode mode]) {
......@@ -325,6 +329,12 @@ class OverrideArtifacts implements Artifacts {
if (artifact == Artifact.engineDartBinary && engineDartBinary != null) {
return engineDartBinary.path;
}
if (artifact == Artifact.platformKernelDill && platformKernelDill != null) {
return platformKernelDill.path;
}
if (artifact == Artifact.flutterPatchedSdkPath && flutterPatchedSdk != null) {
return flutterPatchedSdk.path;
}
return parent.getArtifactPath(artifact, platform, mode);
}
......
......@@ -147,6 +147,10 @@ class AttachCommand extends FlutterCommand {
: Uri.parse('http://$ipv4Loopback:$localPort/');
status.stop();
} catch (_) {
final List<ForwardedPort> ports = device.portForwarder.forwardedPorts.toList();
for (ForwardedPort port in ports) {
await device.portForwarder.unforward(port);
}
status.cancel();
rethrow;
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment