// Copyright (c) 2019, 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 'package:args/args.dart';
import 'package:args/command_runner.dart';
import 'package:logging/logging.dart';

import '../logging.dart';
import '../pubspec.dart';
import '../serve/dev_workflow.dart';
import 'configuration.dart';
import 'shared.dart';

/// Command to run a server for local web development with the build daemon.
class ServeCommand extends Command<int> {
  @override
  final name = 'serve';

  @override
  final description = 'Run a local web development server and a file system'
      ' watcher that rebuilds on changes.';

  @override
  final argParser = ArgParser(usageLineLength: lineLength)
    ..addOption(autoOption, help: '''
Automatically performs an action after each build:

restart: Reload modules and re-invoke main (loses current state)
refresh: Performs a full page refresh.
''', allowed: ['restart', 'refresh'])
    ..addFlag(debugFlag,
        help: 'Enable the launching of DevTools (Alt + D / Option + D). '
            'This also enables --$launchInChromeFlag.')
    ..addFlag(debugExtensionFlag,
        help: 'Enable the backend for the Dart Debug Extension. '
            'Learn more at dart.dev/to/web-debug-extension.')
    ..addFlag(enableInjectedClientFlag,
        help: 'Whether or not to inject the client.js script in web apps. This '
            'is required for all debugging related features, but may interact '
            'poorly with proxy servers or other environments.',
        defaultsTo: true)
    ..addSeparator('Advanced:')
    ..addOption(chromeDebugPortFlag,
        help: 'Specify which port the Chrome debugger is listening on. '
            'If used with $launchInChromeFlag Chrome will be started with the'
            ' debugger listening on this port.')
    ..addOption(hostnameFlag,
        help: 'Specify the hostname to serve on.', defaultsTo: 'localhost')
    ..addFlag(hotRestartFlag,
        negatable: false,
        help: 'Automatically reloads changed modules after each build '
            'and restarts your application.\n'
            "Can't be used with $liveReloadFlag.",
        hide: true)
    ..addFlag(hotReloadFlag, negatable: false, hide: true)
    ..addFlag(launchInChromeFlag,
        help: 'Automatically launches your application in Chrome with the '
            'debug port open. Use $chromeDebugPortFlag to specify a specific '
            'port to attach to an already running chrome instance instead.')
    ..addOption(userDataDirFlag,
        defaultsTo: null,
        help: 'Use with $launchInChromeFlag to specify user data directory '
            'to pass to chrome. Will start chrome window logged into default '
            'profile with enabled extensions. Use `auto` as a value to infer '
            'the default directory for the current OS. '
            'Note: only supported for Mac OS X and linux platforms.')
    ..addFlag(liveReloadFlag,
        negatable: false,
        help: 'Automatically refreshes the page after each successful build.\n'
            "Can't be used with $hotRestartFlag.",
        hide: true)
    ..addFlag(logRequestsFlag,
        negatable: false,
        help: 'Enables logging for each request to the server.')
    ..addOption(tlsCertChainFlag,
        help:
            'The file location to a TLS Certificate to create an HTTPs server.\n'
            'Must be used with $tlsCertKeyFlag.')
    ..addOption(tlsCertKeyFlag,
        help: 'The file location to a TLS Key to create an HTTPs server.\n'
            'Must be used with $tlsCertChainFlag.')
    ..addSeparator('Common:');

  ServeCommand() {
    addSharedArgs(argParser, releaseDefault: false);
  }

  @override
  String get invocation => '${super.invocation} [<directory>[:<port>]]...';

  @override
  Future<int> run() async {
    Configuration configuration;
    configuration = Configuration.fromArgs(argResults);
    configureLogWriter(configuration.verbose);
    try {
      await validatePubspecLock(configuration);
    } on PackageException catch (e) {
      logWriter(Level.SEVERE, 'Pubspec errors: ', error: '${e.details}');
      rethrow;
    }
    // Forward remaining arguments as Build Options to the Daemon.
    // This isn't documented. Should it be advertised?
    final buildOptions = buildRunnerArgs(configuration)
      ..addAll(argResults!.rest.where((arg) => arg.startsWith('-')).toList());
    final extraArgs = argResults?.rest ?? [];
    final directoryArgs =
        extraArgs.where((arg) => !arg.startsWith('-')).toList();
    final targetPorts = parseDirectoryArgs(directoryArgs);
    validateLaunchApps(configuration.launchApps, targetPorts.keys);

    final workflow =
        await DevWorkflow.start(configuration, buildOptions, targetPorts);
    await workflow.done;
    return 0;
  }
}
