// Copyright 2013 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.

import 'dart:io' as io;

import 'package:args/command_runner.dart';
import 'package:path/path.dart' as path;

import 'environment.dart';

class LicensesCommand extends Command<bool> {
  @override
  final String name = 'check-licenses';

  @override
  final String description = 'Check license headers.';

  @override
  bool run() {
    _checkLicenseHeaders();
    return true;
  }

  void _checkLicenseHeaders() {
    final List<io.File> allSourceFiles =
        _flatListSourceFiles(environment.webUiRootDir);
    _expect(allSourceFiles.isNotEmpty,
        'Dart source listing of ${environment.webUiRootDir.path} must not be empty.');

    final List<String> allDartPaths =
        allSourceFiles.map((io.File f) => f.path).toList();

    for (final String expectedDirectory in const <String>[
      'lib',
      'test',
      'dev',
      'tool'
    ]) {
      final String expectedAbsoluteDirectory =
          path.join(environment.webUiRootDir.path, expectedDirectory);
      _expect(
        allDartPaths
            .where((String p) => p.startsWith(expectedAbsoluteDirectory))
            .isNotEmpty,
        'Must include the $expectedDirectory/ directory',
      );
    }

    allSourceFiles.forEach(_expectLicenseHeader);
    print('License headers OK!');
  }

  final RegExp _copyRegex =
      RegExp(r'// Copyright 2013 The Flutter Authors\. All rights reserved\.');

  void _expectLicenseHeader(io.File file) {
    final List<String> head = file.readAsStringSync().split('\n').take(3).toList();

    _expect(head.length >= 3, 'File too short: ${file.path}');
    _expect(
      _copyRegex.firstMatch(head[0]) != null,
      'Invalid first line of license header in file ${file.path}',
    );
    _expect(
      head[1] ==
          '// Use of this source code is governed by a BSD-style license that can be',
      'Invalid second line of license header in file ${file.path}',
    );
    _expect(
      head[2] == '// found in the LICENSE file.',
      'Invalid third line of license header in file ${file.path}',
    );
  }

  void _expect(bool value, String requirement) {
    if (!value) {
      throw Exception('Test failed: $requirement');
    }
  }

  List<io.File> _flatListSourceFiles(io.Directory directory) {
    return directory.listSync(recursive: true).whereType<io.File>().where((io.File f) {
      if (!f.path.endsWith('.dart') && !f.path.endsWith('.js')) {
        // Not a source file we're checking.
        return false;
      }
      if (path.isWithin(environment.webUiBuildDir.path, f.path) ||
          path.isWithin(environment.webUiDartToolDir.path, f.path)) {
        // Generated files.
        return false;
      }
      return true;
    }).toList();
  }
}
