// Copyright 2014 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// @dart = 2.8

import 'dart:async';
import 'dart:convert';

import 'package:args/command_runner.dart';
import 'package:file/memory.dart';
import 'package:flutter_tools/src/base/common.dart';
import 'package:flutter_tools/src/base/file_system.dart';
import 'package:flutter_tools/src/base/logger.dart';
import 'package:flutter_tools/src/build_info.dart';
import 'package:flutter_tools/src/cache.dart';
import 'package:flutter_tools/src/commands/test.dart';
import 'package:flutter_tools/src/device.dart';
import 'package:flutter_tools/src/project.dart';
import 'package:flutter_tools/src/runner/flutter_command.dart';
import 'package:flutter_tools/src/test/runner.dart';
import 'package:flutter_tools/src/test/test_time_recorder.dart';
import 'package:flutter_tools/src/test/test_wrapper.dart';
import 'package:flutter_tools/src/test/watcher.dart';
import 'package:meta/meta.dart';

import '../../src/common.dart';
import '../../src/context.dart';
import '../../src/fake_devices.dart';
import '../../src/logging_logger.dart';
import '../../src/test_flutter_command_runner.dart';

const String _pubspecContents = '''
dev_dependencies:
  flutter_test:
    sdk: flutter
  integration_test:
    sdk: flutter''';
final String _packageConfigContents = json.encode(<String, Object>{
  'configVersion': 2,
  'packages': <Map<String, Object>>[
    <String, String>{
      'name': 'test_api',
      'rootUri': 'file:///path/to/pubcache/.pub-cache/hosted/pub.dartlang.org/test_api-0.2.19',
      'packageUri': 'lib/',
      'languageVersion': '2.12',
    },
    <String, String>{
      'name': 'integration_test',
      'rootUri': 'file:///path/to/flutter/packages/integration_test',
      'packageUri': 'lib/',
      'languageVersion': '2.12',
    },
  ],
  'generated': '2021-02-24T07:55:20.084834Z',
  'generator': 'pub',
  'generatorVersion': '2.13.0-68.0.dev',
});

void main() {
  Cache.disableLocking();
  MemoryFileSystem fs;
  LoggingLogger logger;

  setUp(() {
    fs = MemoryFileSystem.test();
    fs.file('/package/pubspec.yaml').createSync(recursive: true);
    fs.file('/package/pubspec.yaml').writeAsStringSync(_pubspecContents);
    (fs.directory('/package/.dart_tool')
        .childFile('package_config.json')
      ..createSync(recursive: true))
        .writeAsString(_packageConfigContents);
    fs.directory('/package/test').childFile('some_test.dart').createSync(recursive: true);
    fs.directory('/package/integration_test').childFile('some_integration_test.dart').createSync(recursive: true);

    fs.currentDirectory = '/package';

    logger = LoggingLogger();
  });

  testUsingContext('Missing dependencies in pubspec',
      () async {
    // Clear the dependencies already added in [setUp].
    fs.file('pubspec.yaml').writeAsStringSync('');
    fs.directory('.dart_tool').childFile('package_config.json').writeAsStringSync('');

    final FakePackageTest fakePackageTest = FakePackageTest();
    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner =
    createTestCommandRunner(testCommand);

    expect(() => commandRunner.run(const <String>[
      'test',
      '--no-pub',
    ]), throwsToolExit());
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Logger: () => logger,
  });

  testUsingContext('Missing dependencies in pubspec for integration tests',
      () async {
    // Only use the flutter_test dependency, integration_test is deliberately
    // absent.
    fs.file('pubspec.yaml').writeAsStringSync('''
dev_dependencies:
  flutter_test:
    sdk: flutter
    ''');
    fs.directory('.dart_tool').childFile('package_config.json').writeAsStringSync(json.encode(<String, Object>{
      'configVersion': 2,
      'packages': <Map<String, Object>>[
        <String, String>{
          'name': 'test_api',
          'rootUri': 'file:///path/to/pubcache/.pub-cache/hosted/pub.dartlang.org/test_api-0.2.19',
          'packageUri': 'lib/',
          'languageVersion': '2.12',
        },
      ],
      'generated': '2021-02-24T07:55:20.084834Z',
      'generator': 'pub',
      'generatorVersion': '2.13.0-68.0.dev',
    }));
    final FakePackageTest fakePackageTest = FakePackageTest();
    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    expect(() => commandRunner.run(const <String>[
      'test',
      '--no-pub',
      'integration_test',
    ]), throwsToolExit());
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
  });

  testUsingContext('Pipes test-randomize-ordering-seed to package:test',
      () async {
    final FakePackageTest fakePackageTest = FakePackageTest();

    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--test-randomize-ordering-seed=random',
      '--no-pub',
    ]);
    expect(
      fakePackageTest.lastArgs,
      contains('--test-randomize-ordering-seed=random'),
    );
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
  });

  group('shard-index and total-shards', () {
    testUsingContext('with the params they are Piped to package:test',
        () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner =
          createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--total-shards=1',
        '--shard-index=2',
        '--no-pub',
      ]);

      expect(fakePackageTest.lastArgs, contains('--total-shards=1'));
      expect(fakePackageTest.lastArgs, contains('--shard-index=2'));
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      Cache: () => Cache.test(processManager: FakeProcessManager.any()),
    });

    testUsingContext('without the params they not Piped to package:test',
        () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner =
          createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
      ]);

      expect(fakePackageTest.lastArgs, isNot(contains('--total-shards')));
      expect(fakePackageTest.lastArgs, isNot(contains('--shard-index')));
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      Cache: () => Cache.test(processManager: FakeProcessManager.any()),
    });
  });

  testUsingContext('Supports coverage and machine', () async {
    final FakePackageTest fakePackageTest = FakePackageTest();

    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    expect(() => commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--machine',
      '--coverage',
      '--',
      'test/fake_test.dart',
    ]), throwsA(isA<ToolExit>().having((ToolExit toolExit) => toolExit.message, 'message', isNull)));
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
  });

  testUsingContext('Pipes start-paused to package:test',
      () async {
    final FakePackageTest fakePackageTest = FakePackageTest();

    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--start-paused',
      '--',
      'test/fake_test.dart',
    ]);
    expect(
      fakePackageTest.lastArgs,
      contains('--pause-after-load'),
    );
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
  });

  testUsingContext('Pipes run-skipped to package:test',
      () async {
    final FakePackageTest fakePackageTest = FakePackageTest();

    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--run-skipped',
      '--',
      'test/fake_test.dart',
    ]);
    expect(
      fakePackageTest.lastArgs,
      contains('--run-skipped'),
    );
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
  });

  testUsingContext('Pipes enable-observatory', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--enable-vmservice',
      '--',
      'test/fake_test.dart',
    ]);
    expect(
      testRunner.lastEnableObservatoryValue,
      true,
    );

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--start-paused',
      '--no-enable-vmservice',
      '--',
      'test/fake_test.dart',
    ]);
    expect(
      testRunner.lastEnableObservatoryValue,
      true,
    );

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--',
      'test/fake_test.dart',
    ]);
    expect(
      testRunner.lastEnableObservatoryValue,
      false,
    );
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
  });

  testUsingContext('Verbose prints phase timings', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0, const Duration(milliseconds: 1));

    final TestCommand testCommand = TestCommand(testRunner: testRunner, verbose: true);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--',
      'test/fake_test.dart',
    ]);

    // Expect one message for each phase.
    final List<String> logPhaseMessages = logger.messages.where((String m) => m.startsWith('Runtime for phase ')).toList();
    expect(logPhaseMessages, hasLength(TestTimePhases.values.length));

    // As we force the `runTests` command to take at least 1 ms expect at least
    // one phase to take a non-zero amount of time.
    final List<String> logPhaseMessagesNonZero = logPhaseMessages.where((String m) => !m.contains(Duration.zero.toString())).toList();
    expect(logPhaseMessagesNonZero, isNotEmpty);
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
    Logger: () => logger,
  });

  testUsingContext('Non-verbose does not prints phase timings', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0, const Duration(milliseconds: 1));

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner =
        createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--',
      'test/fake_test.dart',
    ]);

    final List<String> logPhaseMessages = logger.messages.where((String m) => m.startsWith('Runtime for phase ')).toList();
    expect(logPhaseMessages, isEmpty);
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    Cache: () => Cache.test(processManager: FakeProcessManager.any()),
    Logger: () => logger,
  });

  testUsingContext('Pipes different args when running Integration Tests', () async {
    final FakePackageTest fakePackageTest = FakePackageTest();

    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      'integration_test',
    ]);

    expect(fakePackageTest.lastArgs, contains('--concurrency=1'));
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[
      FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
    ]),
  });

  testUsingContext('Overrides concurrency when running Integration Tests', () async {
    final FakePackageTest fakePackageTest = FakePackageTest();

    final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--concurrency=100',
      'integration_test',
    ]);

    expect(fakePackageTest.lastArgs, contains('--concurrency=1'));
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[
      FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
    ]),
  });

  group('Detecting Integration Tests', () {
    testUsingContext('when integration_test is not passed', () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
      ]);

      expect(testCommand.isIntegrationTest, false);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      DeviceManager: () => _FakeDeviceManager(<Device>[
        FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
      ]),
    });

    testUsingContext('when integration_test is passed', () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
        'integration_test',
      ]);

      expect(testCommand.isIntegrationTest, true);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      DeviceManager: () => _FakeDeviceManager(<Device>[
        FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
      ]),
    });

    testUsingContext('when relative path to integration test is passed', () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
        'integration_test/some_integration_test.dart',
      ]);

      expect(testCommand.isIntegrationTest, true);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      DeviceManager: () => _FakeDeviceManager(<Device>[
        FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
      ]),
    });

    testUsingContext('when absolute path to integration test is passed', () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
        '/package/integration_test/some_integration_test.dart',
      ]);

      expect(testCommand.isIntegrationTest, true);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      DeviceManager: () => _FakeDeviceManager(<Device>[
        FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
      ]),
    });

    testUsingContext('when absolute unnormalized path to integration test is passed', () async {
      final FakePackageTest fakePackageTest = FakePackageTest();

      final TestCommand testCommand = TestCommand(testWrapper: fakePackageTest);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
        '/package/../package/integration_test/some_integration_test.dart',
      ]);

      expect(testCommand.isIntegrationTest, true);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      DeviceManager: () => _FakeDeviceManager(<Device>[
        FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
      ]),
    });

    testUsingContext('when both test and integration test are passed', () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      expect(() => commandRunner.run(const <String>[
        'test',
        '--no-pub',
        'test/some_test.dart',
        'integration_test/some_integration_test.dart',
      ]), throwsToolExit());
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
    });
  });

  group('Required artifacts', () {
    testUsingContext('for default invocation', () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
      ]);

      expect(await testCommand.requiredArtifacts, isEmpty);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
    });

    testUsingContext('when platform is chrome', () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
        '--platform=chrome',
      ]);

      expect(await testCommand.requiredArtifacts, <DevelopmentArtifact>[DevelopmentArtifact.web]);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
    });

    testUsingContext('when running integration tests', () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      await commandRunner.run(const <String>[
        'test',
        '--no-pub',
        'integration_test',
      ]);

      expect(await testCommand.requiredArtifacts, <DevelopmentArtifact>[
        DevelopmentArtifact.universal,
        DevelopmentArtifact.androidGenSnapshot,
      ]);
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
      DeviceManager: () => _FakeDeviceManager(<Device>[
        FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
      ]),
    });
  });

  testUsingContext('Integration tests when no devices are connected', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    expect(() => commandRunner.run(const <String>[
      'test',
      '--no-pub',
      'integration_test',
    ]), throwsToolExit());
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[]),
  });

  // TODO(jiahaog): Remove this when web is supported. https://github.com/flutter/flutter/issues/66264
  testUsingContext('Integration tests when only web devices are connected', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    expect(() => commandRunner.run(const <String>[
      'test',
      '--no-pub',
      'integration_test',
    ]), throwsToolExit());
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[
      FakeDevice('ephemeral', 'ephemeral'),
    ]),
  });

  testUsingContext('Integration tests set the correct dart-defines', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      'integration_test',
    ]);

    expect(
      testRunner.lastDebuggingOptionsValue.buildInfo.dartDefines,
      contains('INTEGRATION_TEST_SHOULD_REPORT_RESULTS_TO_NATIVE=false'),
    );
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[
      FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
    ]),
  });

  testUsingContext('Integration tests given flavor', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--flavor',
      'dev',
      'integration_test',
    ]);

    expect(
      testRunner.lastDebuggingOptionsValue.buildInfo.flavor,
      contains('dev'),
    );
  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[
      FakeDevice('ephemeral', 'ephemeral', type: PlatformType.android),
    ]),
  });

  testUsingContext('Builds the asset manifest by default', () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
    ]);

    final bool fileExists = await fs.isFile('build/unit_test_assets/AssetManifest.json');
    expect(fileExists, true);

  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[]),
  });

  testUsingContext("Don't build the asset manifest if --no-test-assets if informed", () async {
    final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

    final TestCommand testCommand = TestCommand(testRunner: testRunner);
    final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

    await commandRunner.run(const <String>[
      'test',
      '--no-pub',
      '--no-test-assets',
    ]);

    final bool fileExists = await fs.isFile('build/unit_test_assets/AssetManifest.json');
    expect(fileExists, false);

  }, overrides: <Type, Generator>{
    FileSystem: () => fs,
    ProcessManager: () => FakeProcessManager.any(),
    DeviceManager: () => _FakeDeviceManager(<Device>[]),
  });

  group('Fatal Logs', () {
    testUsingContext("doesn't fail when --fatal-warnings is set and no warning output", () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      try {
        await commandRunner.run(const <String>[
          'test',
          '--no-pub',
          '--${FlutterOptions.kFatalWarnings}',
        ]);
      } on Exception {
        fail('Unexpected exception thrown');
      }
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
    });
    testUsingContext('fails if --fatal-warnings specified and warnings emitted', () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      testLogger.printWarning('Warning: Mild annoyance, Will Robinson!');
      expect(commandRunner.run(const <String>[
        'test',
        '--no-pub',
        '--${FlutterOptions.kFatalWarnings}',
      ]), throwsToolExit(message: 'Logger received warning output during the run, and "--${FlutterOptions.kFatalWarnings}" is enabled.'));
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
    });
    testUsingContext('fails when --fatal-warnings is set and only errors emitted', () async {
      final FakeFlutterTestRunner testRunner = FakeFlutterTestRunner(0);

      final TestCommand testCommand = TestCommand(testRunner: testRunner);
      final CommandRunner<void> commandRunner = createTestCommandRunner(testCommand);

      testLogger.printError('Error: Danger Will Robinson!');
      expect(commandRunner.run(const <String>[
        'test',
        '--no-pub',
        '--${FlutterOptions.kFatalWarnings}',
      ]), throwsToolExit(message: 'Logger received error output during the run, and "--${FlutterOptions.kFatalWarnings}" is enabled.'));
    }, overrides: <Type, Generator>{
      FileSystem: () => fs,
      ProcessManager: () => FakeProcessManager.any(),
    });
  });
}

class FakeFlutterTestRunner implements FlutterTestRunner {
  FakeFlutterTestRunner(this.exitCode, [this.leastRunTime]);

  int exitCode;
  Duration leastRunTime;
  bool lastEnableObservatoryValue;
  DebuggingOptions lastDebuggingOptionsValue;

  @override
  Future<int> runTests(
    TestWrapper testWrapper,
    List<String> testFiles, {
    @required DebuggingOptions debuggingOptions,
    Directory workDir,
    List<String> names = const <String>[],
    List<String> plainNames = const <String>[],
    String tags,
    String excludeTags,
    bool enableObservatory = false,
    bool ipv6 = false,
    bool machine = false,
    String precompiledDillPath,
    Map<String, String> precompiledDillFiles,
    BuildMode buildMode,
    bool trackWidgetCreation = false,
    bool updateGoldens = false,
    TestWatcher watcher,
    int concurrency,
    String testAssetDirectory,
    FlutterProject flutterProject,
    String icudtlPath,
    Directory coverageDirectory,
    bool web = false,
    String randomSeed,
    @override List<String> extraFrontEndOptions,
    String reporter,
    String timeout,
    bool runSkipped = false,
    int shardIndex,
    int totalShards,
    Device integrationTestDevice,
    String integrationTestUserIdentifier,
    TestTimeRecorder testTimeRecorder,
  }) async {
    lastEnableObservatoryValue = enableObservatory;
    lastDebuggingOptionsValue = debuggingOptions;

    if (leastRunTime != null) {
      await Future<void>.delayed(leastRunTime);
    }

    return exitCode;
  }
}

class FakePackageTest implements TestWrapper {
  List<String> lastArgs;

  @override
  Future<void> main(List<String> args) async {
    lastArgs = args;
  }

  @override
  void registerPlatformPlugin(
    Iterable<Runtime> runtimes,
    FutureOr<PlatformPlugin> Function() platforms,
  ) {}
}

class _FakeDeviceManager extends DeviceManager {
  _FakeDeviceManager(this._connectedDevices);

  final List<Device> _connectedDevices;

  @override
  Future<List<Device>> getAllConnectedDevices() async => _connectedDevices;

  @override
  List<DeviceDiscovery> get deviceDiscoverers => <DeviceDiscovery>[];
}
