// Copyright 2016 The Tulsi Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

import XCTest
@testable import TulsiGenerator


class XcodeProjectGeneratorTests: XCTestCase {
  static let outputFolderPath = "/dev/null/project"
  static let projectName = "ProjectName"

  let outputFolderURL = URL(fileURLWithPath: XcodeProjectGeneratorTests.outputFolderPath)
  let xcodeProjectPath = "\(XcodeProjectGeneratorTests.outputFolderPath)/\(XcodeProjectGeneratorTests.projectName).xcodeproj"

  let workspaceRoot = URL(fileURLWithPath: "/workspace")
  let testTulsiVersion = "9.99.999.9999"

  let buildTargetLabels = ["//test:MainTarget", "//test/path/to/target:target"].map({ BuildLabel($0) })
  let pathFilters = Set<String>(["test", "additional"])

  let additionalFilePaths = ["additional/File1", "additional/File2"]

  let bazelURL = URL(fileURLWithPath: "/test/dir/testBazel")

  let resourceURLs = XcodeProjectGenerator.ResourceSourcePathURLs(
      buildScript: URL(fileURLWithPath: "/scripts/Build"),
      cleanScript: URL(fileURLWithPath: "/scripts/Clean"),
      postProcessor: URL(fileURLWithPath: "/utils/covmap_patcher"),
      uiRunnerEntitlements: URL(fileURLWithPath: "/generatedProjectResources/XCTRunner.entitlements"),
      stubInfoPlist: URL(fileURLWithPath: "/generatedProjectResources/StubInfoPlist.plist"),
      stubIOSAppExInfoPlist: URL(fileURLWithPath: "/generatedProjectResources/stubIOSAppExInfoPlist.plist"),
      stubWatchOS2InfoPlist: URL(fileURLWithPath: "/generatedProjectResources/StubWatchOS2InfoPlist.plist"),
      stubWatchOS2AppExInfoPlist: URL(fileURLWithPath: "/generatedProjectResources/StubWatchOS2AppExInfoPlist.plist"),
      bazelWorkspaceFile: URL(fileURLWithPath: "/WORKSPACE"),
      tulsiPackageFiles: [URL(fileURLWithPath: "/tulsi/tulsi_aspects.bzl")])

  var config: TulsiGeneratorConfig! = nil
  var mockLocalizedMessageLogger: MockLocalizedMessageLogger! = nil
  var mockFileManager: MockFileManager! = nil
  var mockExtractor: MockWorkspaceInfoExtractor! = nil
  var generator: XcodeProjectGenerator! = nil

  var writtenFiles = Set<String>()

  override func setUp() {
    super.setUp()
    mockLocalizedMessageLogger = MockLocalizedMessageLogger()
    mockFileManager = MockFileManager()
    mockExtractor = MockWorkspaceInfoExtractor()
    writtenFiles.removeAll()
  }

  func testSuccessfulGeneration() {
    let ruleEntries = XcodeProjectGeneratorTests.labelToRuleEntryMapForLabels(buildTargetLabels)
    prepareGenerator(ruleEntries)
    do {
      _ = try generator.generateXcodeProjectInFolder(outputFolderURL)
      mockLocalizedMessageLogger.assertNoErrors()
      mockLocalizedMessageLogger.assertNoWarnings()

      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/project.pbxproj"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/project.xcworkspace/xcuserdata/USER.xcuserdatad/WorkspaceSettings.xcsettings"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/test-path-to-target-target.xcscheme"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/test-MainTarget.xcscheme"))
    } catch let e {
      XCTFail("Unexpected exception \(e)")
    }
  }

  func testUnresolvedLabelsThrows() {
    let ruleEntries = XcodeProjectGeneratorTests.labelToRuleEntryMapForLabels(buildTargetLabels)
    prepareGenerator(ruleEntries)
    mockExtractor.labelToRuleEntry = [:]
    do {
      _ = try generator.generateXcodeProjectInFolder(outputFolderURL)
      XCTFail("Generation succeeded unexpectedly")
    } catch XcodeProjectGenerator.ProjectGeneratorError.labelResolutionFailed(let missingLabels) {
      for label in buildTargetLabels {
        XCTAssert(missingLabels.contains(label), "Expected missing label \(label) not found")
      }
    } catch let e {
      XCTFail("Unexpected exception \(e)")
    }
  }

  func testTestSuiteSchemeGeneration() {
    checkTestSuiteSchemeGeneration("ios_test", testHostAttributeName: "xctest_app")
  }

  func testTestSuiteSchemeGenerationWithSkylarkUnitTest() {
    checkTestSuiteSchemeGeneration("apple_unit_test", testHostAttributeName: "test_host")
  }

  func testTestSuiteSchemeGenerationWithSkylarkUITest() {
    checkTestSuiteSchemeGeneration("apple_ui_test", testHostAttributeName: "test_host")
  }

  func checkTestSuiteSchemeGeneration(_ testRuleType: String, testHostAttributeName: String) {
    @discardableResult
    func addRule(_ labelName: String,
                 type: String,
                 attributes: [String: AnyObject] = [:],
                 weakDependencies: Set<BuildLabel>? = nil) -> BuildLabel {
      let label = BuildLabel(labelName)
      mockExtractor.labelToRuleEntry[label] = type(of: self).makeRuleEntry(label,
                                                                             type: type,
                                                                             attributes: attributes,
                                                                             weakDependencies: weakDependencies)
      return label
    }

    let app = addRule("//test:Application", type: "ios_application")
    let test1 = addRule("//test:TestOne", type: testRuleType, attributes: [testHostAttributeName: app.value as AnyObject])
    let test2 = addRule("//test:TestTwo", type: testRuleType, attributes: [testHostAttributeName: app.value as AnyObject])
    addRule("//test:UnusedTest", type: testRuleType)
    addRule("//test:TestSuite", type: "test_suite", weakDependencies: Set([test1, test2]))
    prepareGenerator(mockExtractor.labelToRuleEntry)

    do {
      _ = try generator.generateXcodeProjectInFolder(outputFolderURL)
      mockLocalizedMessageLogger.assertNoErrors()
      mockLocalizedMessageLogger.assertNoWarnings()

      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/project.pbxproj"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/project.xcworkspace/xcuserdata/USER.xcuserdatad/WorkspaceSettings.xcsettings"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/test-Application.xcscheme"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/test-TestOne.xcscheme"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/test-TestTwo.xcscheme"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/test-UnusedTest.xcscheme"))
      XCTAssert(writtenFiles.contains("\(xcodeProjectPath)/xcshareddata/xcschemes/TestSuite_Suite.xcscheme"))
    } catch let e {
      XCTFail("Unexpected exception \(e)")
    }
  }

  func testProjectSDKROOT() {
    func validate(_ types: [String], _ expectedSDKROOT: String?, line: UInt = #line) {
      let rules = types.map() {
        XcodeProjectGeneratorTests.makeRuleEntry(BuildLabel($0), type: $0)
      }
      let sdkroot = XcodeProjectGenerator.projectSDKROOT(rules)
      XCTAssertEqual(sdkroot, expectedSDKROOT, line: line)
    }

    validate(["ios_application"], "iphoneos")
    validate(["ios_application", "ios_application"], "iphoneos")
    validate(["ios_application", "apple_watch2_extension"], "iphoneos")
    validate(["apple_watch2_extension"], "watchos")
    validate(["apple_watch2_extension", "apple_watch2_extension"], "watchos")
    validate(["apple_watch2_extension", "_tvos_extension"], nil)
    validate(["ios_application", "apple_watch2_extension", "_tvos_extension"], nil)
    validate(["ios_application", "_tvos_extension"], nil)
    validate(["_tvos_extension"], "appletvos")
  }

  // MARK: - Private methods

  private static func labelToRuleEntryMapForLabels(_ labels: [BuildLabel]) -> [BuildLabel: RuleEntry] {
    var ret = [BuildLabel: RuleEntry]()
    for label in labels {
      ret[label] = makeRuleEntry(label, type: "ios_application")
    }
    return ret
  }

  private static func makeRuleEntry(_ label: BuildLabel,
                                    type: String,
                                    attributes: [String: AnyObject] = [:],
                                    artifacts: [BazelFileInfo] = [],
                                    sourceFiles: [BazelFileInfo] = [],
                                    nonARCSourceFiles: [BazelFileInfo] = [],
                                    dependencies: Set<String> = Set(),
                                    secondaryArtifacts: [BazelFileInfo] = [],
                                    weakDependencies: Set<BuildLabel>? = nil,
                                    buildFilePath: String? = nil,
                                    generatedIncludePaths: [RuleEntry.IncludePath]? = nil,
                                    implicitIPATarget: BuildLabel? = nil) -> RuleEntry {
    return RuleEntry(label: label,
                     type: type,
                     attributes: attributes,
                     artifacts: artifacts,
                     sourceFiles: sourceFiles,
                     nonARCSourceFiles: nonARCSourceFiles,
                     dependencies: dependencies,
                     secondaryArtifacts: secondaryArtifacts,
                     weakDependencies: weakDependencies,
                     buildFilePath: buildFilePath,
                     generatedIncludePaths: generatedIncludePaths,
                     implicitIPATarget: implicitIPATarget)
  }

  private func prepareGenerator(_ ruleEntries: [BuildLabel: RuleEntry]) {
    config = TulsiGeneratorConfig(projectName: XcodeProjectGeneratorTests.projectName,
                                  buildTargetLabels: Array(ruleEntries.keys),
                                  pathFilters: pathFilters,
                                  additionalFilePaths: additionalFilePaths,
                                  options: TulsiOptionSet(),
                                  bazelURL: bazelURL)
    let projectURL = URL(fileURLWithPath: xcodeProjectPath, isDirectory: true)
    mockFileManager.allowedDirectoryCreates.insert(projectURL.path)

    let xcshareddata = projectURL.appendingPathComponent("project.xcworkspace/xcshareddata")
    mockFileManager.allowedDirectoryCreates.insert(xcshareddata.path)

    let xcuserdata = projectURL.appendingPathComponent("project.xcworkspace/xcuserdata/USER.xcuserdatad")
    mockFileManager.allowedDirectoryCreates.insert(xcuserdata.path)

    let xcschemes = projectURL.appendingPathComponent("xcshareddata/xcschemes")
    mockFileManager.allowedDirectoryCreates.insert(xcschemes.path)

    let scripts = projectURL.appendingPathComponent(".tulsi/Scripts")
    mockFileManager.allowedDirectoryCreates.insert(scripts.path)

    let utils = projectURL.appendingPathComponent(".tulsi/Utils")
    mockFileManager.allowedDirectoryCreates.insert(utils.path)

    let resources = projectURL.appendingPathComponent(".tulsi/Resources")
    mockFileManager.allowedDirectoryCreates.insert(resources.path)

    let tulsiBazelRoot = projectURL.appendingPathComponent(".tulsi/Bazel")
    mockFileManager.allowedDirectoryCreates.insert(tulsiBazelRoot.path)

    let tulsiBazelPackage = projectURL.appendingPathComponent(".tulsi/Bazel/tulsi")
    mockFileManager.allowedDirectoryCreates.insert(tulsiBazelPackage.path)

    mockExtractor.labelToRuleEntry = ruleEntries

    generator = XcodeProjectGenerator(workspaceRootURL: workspaceRoot,
                                      config: config,
                                      localizedMessageLogger: mockLocalizedMessageLogger,
                                      workspaceInfoExtractor: mockExtractor,
                                      resourceURLs: resourceURLs,
                                      tulsiVersion: testTulsiVersion,
                                      fileManager: mockFileManager,
                                      pbxTargetGeneratorType: MockPBXTargetGenerator.self)
    generator.writeDataHandler = { (url, _) in
      self.writtenFiles.insert(url.path)
    }
    generator.usernameFetcher = { "USER" }
  }
}


class MockFileManager: FileManager {
  var filesThatExist = Set<String>()
  var allowedDirectoryCreates = Set<String>()
  var copyOperations = [String: String]()

  override func fileExists(atPath path: String) -> Bool {
    return filesThatExist.contains(path)
  }

  override func createDirectory(at url: URL,
                                     withIntermediateDirectories createIntermediates: Bool,
                                     attributes: [String:Any]?) throws {
    if allowedDirectoryCreates.contains(url.path) { return }
    throw NSError(domain: "MockFileManager: Directory creation disallowed",
                  code: 0,
                  userInfo: nil)
  }

  override func createDirectory(atPath path: String,
                                      withIntermediateDirectories createIntermediates: Bool,
                                      attributes: [String:Any]?) throws {
    if allowedDirectoryCreates.contains(path) { return }
    throw NSError(domain: "MockFileManager: Directory creation disallowed",
                  code: 0,
                  userInfo: nil)
  }

  override func removeItem(at URL: URL) throws {
    throw NSError(domain: "MockFileManager: removeItem disallowed", code: 0, userInfo: nil)
  }

  override func removeItem(atPath path: String) throws {
    throw NSError(domain: "MockFileManager: removeItem disallowed", code: 0, userInfo: nil)
  }

  override func copyItem(at srcURL: URL, to dstURL: URL) throws {
    copyOperations[dstURL.path] = srcURL.path
  }

  override func copyItem(atPath srcPath: String, toPath dstPath: String) throws {
    copyOperations[dstPath] = srcPath
  }
}


final class MockPBXTargetGenerator: PBXTargetGeneratorProtocol {
  var project: PBXProject

  static func getRunTestTargetBuildConfigPrefix() -> String {
    return "TestRunner__"
  }

  static func workingDirectoryForPBXGroup(_ group: PBXGroup) -> String {
    return ""
  }

  static func mainGroupForOutputFolder(_ outputFolderURL: URL, workspaceRootURL: URL) -> PBXGroup {
    return PBXGroup(name: "mainGroup",
                    path: "/A/Test/Path",
                    sourceTree: .Absolute,
                    parent: nil)
  }

  required init(bazelURL: URL,
                bazelBinPath: String,
                project: PBXProject,
                buildScriptPath: String,
                stubInfoPlistPaths: StubInfoPlistPaths,
                tulsiVersion: String,
                options: TulsiOptionSet,
                localizedMessageLogger: LocalizedMessageLogger,
                workspaceRootURL: URL,
                suppressCompilerDefines: Bool,
                redactWorkspaceSymlink: Bool) {
    self.project = project
  }

  func generateFileReferencesForFilePaths(_ paths: [String], pathFilters: Set<String>?) {
  }

  func registerRuleEntryForIndexer(_ ruleEntry: RuleEntry,
                                   ruleEntryMap: [BuildLabel:RuleEntry],
                                   pathFilters: Set<String>) {
  }

  func generateIndexerTargets() -> [String: PBXTarget] {
    return [:]
  }

  func generateBazelCleanTarget(_ scriptPath: String, workingDirectory: String) {
  }

  func generateTopLevelBuildConfigurations(_ buildSettingOverrides: [String: String]) {
  }

  func generateBuildTargetsForRuleEntries(_ ruleEntries: Set<RuleEntry>,
                                          ruleEntryMap: [BuildLabel: RuleEntry]) throws -> [String: [String]] {
    let namedRuleEntries = ruleEntries.map() { (e: RuleEntry) -> (String, RuleEntry) in
      return (e.label.asFullPBXTargetName!, e)
    }

    var testTargetLinkages = [(PBXTarget, BuildLabel)]()
    for (name, entry) in namedRuleEntries {
      let target = project.createNativeTarget(name, targetType: entry.pbxTargetType!)

      for attribute in [.xctest_app, .test_host] as [RuleEntry.Attribute] {
        if let hostLabelString = entry.attributes[attribute] as? String {
          let hostLabel = BuildLabel(hostLabelString)
          testTargetLinkages.append((target, hostLabel))
        }
      }
    }

    for (testTarget, testHostLabel) in testTargetLinkages {
      let hostTarget = project.targetByName(testHostLabel.asFullPBXTargetName!) as! PBXNativeTarget
      project.linkTestTarget(testTarget, toHostTarget: hostTarget)
    }

    return [:]
  }
}
