TODO housekeeping.

PiperOrigin-RevId: 191497587
diff --git a/src/Tulsi/BugReporter.swift b/src/Tulsi/BugReporter.swift
index 4505217..7db156e 100644
--- a/src/Tulsi/BugReporter.swift
+++ b/src/Tulsi/BugReporter.swift
@@ -18,6 +18,6 @@
 /// Provides functionality to file a bug report based on message data.
 class BugReporter {
   static func fileBugReport() {
-    // TODO(abaire): Implement.
+    // Not implemented.
   }
 }
diff --git a/src/Tulsi/ConfigEditorBuildTargetSelectorViewController.swift b/src/Tulsi/ConfigEditorBuildTargetSelectorViewController.swift
index c336f01..e5e1bcd 100644
--- a/src/Tulsi/ConfigEditorBuildTargetSelectorViewController.swift
+++ b/src/Tulsi/ConfigEditorBuildTargetSelectorViewController.swift
@@ -30,7 +30,6 @@
       "apple_ui_test",
       "cc_binary",
       "cc_library",
-      "objc_binary",  // TODO(abaire): Remove when app-related attributes are removed from Bazel.
       "objc_library",
       "ios_application",
       "ios_framework",
diff --git a/src/Tulsi/ConfigEditorSourceFilterViewController.swift b/src/Tulsi/ConfigEditorSourceFilterViewController.swift
index f392174..ed5aab4 100644
--- a/src/Tulsi/ConfigEditorSourceFilterViewController.swift
+++ b/src/Tulsi/ConfigEditorSourceFilterViewController.swift
@@ -71,7 +71,6 @@
     }
   }
 
-  // TODO(abaire): Use a custom control to override nextState: such that it's never set to mixed via user interaction.
   @objc func validateRecursive(_ ioValue: AutoreleasingUnsafeMutablePointer<AnyObject?>) throws {
     if let value = ioValue.pointee as? NSNumber {
       if value.intValue == NSControl.StateValue.mixed.rawValue {
@@ -116,8 +115,7 @@
     sourceFilterContentArray = []
     document.updateSourcePaths(populateOutlineView)
 
-    // TODO(abaire): Set when toggling selection instead.
-    document.updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+    document.updateChangeCount(.changeDone)
   }
 
   // MARK: - Private methods
diff --git a/src/Tulsi/ConfigEditorWizardViewController.swift b/src/Tulsi/ConfigEditorWizardViewController.swift
index c970059..44cf0f4 100644
--- a/src/Tulsi/ConfigEditorWizardViewController.swift
+++ b/src/Tulsi/ConfigEditorWizardViewController.swift
@@ -132,7 +132,6 @@
     _pageController(pageController, prepareViewController: viewController, withObject: object! as AnyObject)
   }
 
-  // TODO(abaire): Roll into the function body above when Swift 2.2 is dropped.
   private func _pageController(_ pageController: NSPageController,
                                prepareViewController viewController: NSViewController,
                                withObject object: AnyObject) {
diff --git a/src/Tulsi/OptionsEditorController.swift b/src/Tulsi/OptionsEditorController.swift
index ae777e6..937c3cb 100644
--- a/src/Tulsi/OptionsEditorController.swift
+++ b/src/Tulsi/OptionsEditorController.swift
@@ -364,8 +364,6 @@
         }
 
       case .bool:
-        // TODO(abaire): Track down why NSPopUpButton ignores mutation to attributedTitle and remove
-        //               the boldPopUpButtonCell here and from the storyboard.
         let identifier: String
         if explicit {
           identifier = OptionsEditorController.boldPopUpButtonCellViewIdentifier
diff --git a/src/Tulsi/OptionsEditorNode.swift b/src/Tulsi/OptionsEditorNode.swift
index 71b8d06..d16f14e 100644
--- a/src/Tulsi/OptionsEditorNode.swift
+++ b/src/Tulsi/OptionsEditorNode.swift
@@ -280,11 +280,11 @@
           return
         }
         option.targetValues![targetLabel] = value
-        model?.updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+        model?.updateChangeCount(.changeDone)
 
       case .Project:
         option.projectValue = value
-        model?.updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+        model?.updateChangeCount(.changeDone)
 
       default:
         assertionFailure("Editor node accessed via unknown subscript \(level)")
@@ -304,11 +304,11 @@
 
       case .Target:
         _ = option.targetValues?.removeValue(forKey: target!.fullLabel)
-        model?.updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+        model?.updateChangeCount(.changeDone)
 
       case .Project:
         option.projectValue = nil
-        model?.updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+        model?.updateChangeCount(.changeDone)
     }
   }
 
diff --git a/src/Tulsi/ProjectEditorConfigManagerViewController.swift b/src/Tulsi/ProjectEditorConfigManagerViewController.swift
index b6b8704..bc105b7 100644
--- a/src/Tulsi/ProjectEditorConfigManagerViewController.swift
+++ b/src/Tulsi/ProjectEditorConfigManagerViewController.swift
@@ -96,7 +96,6 @@
   }
 
   @IBAction func doGenerate(_ sender: AnyObject?) {
-    // TODO(abaire): Make it clear to the user that only the first selection is generated.
     guard let configName = configArrayController.selectedObjects.first as? String else { return }
     guard requireValidBazel({ self.doGenerate(sender) }) else { return }
 
diff --git a/src/Tulsi/TulsiGeneratorConfigDocument.swift b/src/Tulsi/TulsiGeneratorConfigDocument.swift
index 4a017a4..6471e11 100644
--- a/src/Tulsi/TulsiGeneratorConfigDocument.swift
+++ b/src/Tulsi/TulsiGeneratorConfigDocument.swift
@@ -114,7 +114,7 @@
   /// The number of selected items in ruleEntries.
   @objc dynamic var selectedRuleInfoCount: Int = 0 {
     didSet {
-      updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+      updateChangeCount(.changeDone)
     }
   }
 
@@ -128,7 +128,7 @@
   // The display name for this config.
   var configName: String? = nil {
     didSet {
-      updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+      updateChangeCount(.changeDone)
     }
   }
 
@@ -297,7 +297,6 @@
     let storyboard = NSStoryboard(name: NSStoryboard.Name(rawValue: "Main"), bundle: nil)
     let windowController = storyboard.instantiateController(withIdentifier: NSStoryboard.SceneIdentifier(rawValue: "TulsiGeneratorConfigDocumentWindow")) as! NSWindowController
     windowController.contentViewController?.representedObject = self
-    // TODO(abaire): Consider supporting restoration of config subwindows.
     windowController.window?.isRestorable = false
     addWindowController(windowController)
   }
@@ -407,7 +406,6 @@
   }
 
   override class var autosavesInPlace: Bool {
-    // TODO(abaire): Enable autosave when undo behavior is implemented.
     return false
   }
 
diff --git a/src/Tulsi/TulsiProjectDocument.swift b/src/Tulsi/TulsiProjectDocument.swift
index 9c23c39..e7babfe 100644
--- a/src/Tulsi/TulsiProjectDocument.swift
+++ b/src/Tulsi/TulsiProjectDocument.swift
@@ -44,9 +44,6 @@
   /// Override to prevent rule entries from being extracted immediately during loading of project
   /// documents. This is only useful if the Bazel binary is expected to be set after the project
   /// document is loaded but before any other actions.
-  // TODO(abaire): Refactor project loading to make this unnecessary.
-  // Ideally the project document should be loaded in a sparse form and rules should be updated on
-  // demand later.
   static var suppressRuleEntryUpdateOnLoad = false
 
   /// The project model.
@@ -94,7 +91,7 @@
   @objc dynamic var bazelPackages: [String]? {
     set {
       project!.bazelPackages = newValue ?? [String]()
-      updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+      updateChangeCount(.changeDone)
       updateRuleEntries()
     }
     get {
@@ -109,7 +106,7 @@
       if newValue != nil && infoExtractor != nil {
         infoExtractor.bazelURL = newValue!
       }
-      updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+      updateChangeCount(.changeDone)
       updateRuleEntries()
     }
     get {
@@ -194,7 +191,7 @@
     project = TulsiProject(projectName: projectName,
                            projectBundleURL: tempProjectBundleURL,
                            workspaceRootURL: workspaceRootURL)
-    updateChangeCount(.changeDone)  // TODO(abaire): Implement undo functionality.
+    updateChangeCount(.changeDone)
 
     LogMessage.postSyslog("Create project: \(projectName)")
 
@@ -431,7 +428,6 @@
 
       // Unsupported actions.
       case .some(#selector(TulsiProjectDocument.duplicate(_:))):
-        // TODO(abaire): Consider implementing and allowing project duplication.
         return false
 
       default:
@@ -493,7 +489,6 @@
       case .Error:
         messages.append(UIMessage(text: fullMessage, type: .error))
         if TulsiProjectDocument.showAlertsOnErrors {
-          // TODO(abaire): Implement better error handling, allowing recovery of a good state.
           ErrorAlertView.displayModalError(item.message, details: item.details)
         }
 
@@ -547,7 +542,6 @@
       return
     }
 
-    // TODO(abaire): Cancel any outstanding update operations.
     processingTaskStarted()
     infoExtractor = TulsiProjectInfoExtractor(bazelURL: concreteBazelURL, project: project)
 
diff --git a/src/Tulsi/UISelectableOutlineViewNode.swift b/src/Tulsi/UISelectableOutlineViewNode.swift
index 73640bc..601b244 100644
--- a/src/Tulsi/UISelectableOutlineViewNode.swift
+++ b/src/Tulsi/UISelectableOutlineViewNode.swift
@@ -102,7 +102,6 @@
     child.parent = self
   }
 
-  // TODO(abaire): Use a custom control to override nextState: such that it's never set to mixed via user interaction.
   @objc func validateState(_ ioValue: AutoreleasingUnsafeMutablePointer<AnyObject?>) throws {
     if let value = ioValue.pointee as? NSNumber {
       if value.intValue == NSControl.StateValue.mixed.rawValue {
diff --git a/src/TulsiGenerator/Bazel/tulsi/tulsi_aspects.bzl b/src/TulsiGenerator/Bazel/tulsi/tulsi_aspects.bzl
index 1bdf432..5dfccf3 100644
--- a/src/TulsiGenerator/Bazel/tulsi/tulsi_aspects.bzl
+++ b/src/TulsiGenerator/Bazel/tulsi/tulsi_aspects.bzl
@@ -201,7 +201,6 @@
   else:
     root_execution_path_fragment = None
 
-  # TODO(abaire): Remove once Skylark File objects can reference directories.
   # At the moment (Oct. 2016), Bazel disallows most files without extensions.
   # As a temporary hack, Tulsi treats File instances pointing at extension-less
   # paths as directories. This is extremely fragile and must be replaced with
diff --git a/src/TulsiGenerator/BazelLocator.swift b/src/TulsiGenerator/BazelLocator.swift
index 754ab41..d93fd8b 100644
--- a/src/TulsiGenerator/BazelLocator.swift
+++ b/src/TulsiGenerator/BazelLocator.swift
@@ -23,7 +23,6 @@
   public static let DefaultBazelURLKey = "defaultBazelURL"
 
   static var bazelURL: URL? {
-    // TODO(abaire): Fall back to searching the user's path if no default exists.
     return UserDefaults.standard.url(forKey: BazelLocator.DefaultBazelURLKey)
   }
 
diff --git a/src/TulsiGenerator/BazelWorkspaceInfoExtractor.swift b/src/TulsiGenerator/BazelWorkspaceInfoExtractor.swift
index c47a9c6..83fed20 100644
--- a/src/TulsiGenerator/BazelWorkspaceInfoExtractor.swift
+++ b/src/TulsiGenerator/BazelWorkspaceInfoExtractor.swift
@@ -17,7 +17,6 @@
 
 // Concrete extractor that utilizes Bazel query (http://bazel.build/docs/query.html) and aspects to
 // extract information from a workspace.
-// TODO(abaire): Add link to aspect documentation when it becomes available.
 final class BazelWorkspaceInfoExtractor: BazelWorkspaceInfoExtractorProtocol {
   var bazelURL: URL {
     get { return queryExtractor.bazelURL as URL }
@@ -83,7 +82,6 @@
       return commandLineSplitter.splitCommandLine(options) ?? []
     }
 
-    // TODO(abaire): Support per-target and per-config options during aspect lookups.
     let startupOptions = splitOptionString(startupOptions.commonValue)
     let buildOptions = splitOptionString(buildOptions.commonValue)
     let useAspectForTestSuites = useAspectForTestSuitesOption.commonValueAsBool ?? true
diff --git a/src/TulsiGenerator/PBXObjects.swift b/src/TulsiGenerator/PBXObjects.swift
index 1d7f357..eb2cb10 100644
--- a/src/TulsiGenerator/PBXObjects.swift
+++ b/src/TulsiGenerator/PBXObjects.swift
@@ -235,7 +235,6 @@
       try serializer.addField("lastKnownFileType", uti)
     } else if let uti = explicitFileType {
       try serializer.addField("explicitFileType", uti)
-      // TODO(abaire): set includeInIndex to 0 for output files?
     }
   }
 }
@@ -922,7 +921,6 @@
 }
 
 func == (lhs: PBXTarget, rhs: PBXTarget) -> Bool {
-  // TODO(abaire): check that PBXProjects match- name is only unique with project scope.
   return lhs.name == rhs.name
 }
 
@@ -1317,8 +1315,7 @@
       // Check to see if this component is actually a bundle that should be treated as a file
       // reference by Xcode (e.g., .xcassets bundles) instead of as a PBXGroup.
       let currentComponent = components[i]
-      // TODO(abaire): Look into proper support for localization bundles. This will naively create
-      //               a bundle grouping rather than including the per-locale strings.
+      // This will naively create a bundle grouping rather than including the per-locale strings.
       if let ext = currentComponent.pbPathExtension, let uti = DirExtensionToUTI[ext] {
         let partialPath = components[0...i].joined(separator: "/")
         let fileRef = group.getOrCreateFileReferenceBySourceTree(.Group, path: partialPath)
diff --git a/src/TulsiGenerator/PBXTargetGenerator.swift b/src/TulsiGenerator/PBXTargetGenerator.swift
index d40fdb0..3e320ae 100644
--- a/src/TulsiGenerator/PBXTargetGenerator.swift
+++ b/src/TulsiGenerator/PBXTargetGenerator.swift
@@ -141,7 +141,6 @@
   /// Release builds.
   // NOTE: This value needs to be kept in sync with the bazel_build script.
   static let runTestTargetBuildConfigPrefix = "__TulsiTestRunner_"
-  // TODO(abaire): Remove when Swift supports static stored properties in protocols.
   static func getRunTestTargetBuildConfigPrefix() -> String {
     return runTestTargetBuildConfigPrefix
   }
@@ -589,7 +588,6 @@
                                                      withPerFileSettings: nonARCSettings)
 
       if !buildPhase.files.isEmpty {
-        // TODO(abaire): Extract STL path via the aspect once it is exposed to Skylark.
         // Bazel appends a built-in tools/cpp/gcc3 path in CppHelper.java but that path is not
         // exposed to Skylark. For now Tulsi hardcodes it here to allow proper indexer behavior.
         // NOTE: this requires tools/cpp/gcc3 to be available from the workspace root, which may
@@ -1227,8 +1225,6 @@
       return
     }
     for opt in copts {
-      // TODO(abaire): Add support for shell tokenization as advertised in the Bazel build
-      //     encyclopedia.
       if opt.hasPrefix("-D") {
         let index = opt.index(opt.startIndex, offsetBy: 2)
         localDefines.insert(String(opt[index...]))
@@ -1369,8 +1365,6 @@
       config.buildSettings = buildSettings
 
       // Insert any defines that are injected by Bazel's ObjcConfiguration.
-      // TODO(abaire): Grab these in the aspect instead of hardcoding them here.
-      //               Note that doing this would also require per-config aspect passes.
       if configName == "Debug" {
         addPreprocessorDefine("DEBUG=1", toConfig: config)
       } else if configName == "Release" {
diff --git a/src/TulsiGenerator/RuleEntry.swift b/src/TulsiGenerator/RuleEntry.swift
index edb88b3..885b311 100644
--- a/src/TulsiGenerator/RuleEntry.swift
+++ b/src/TulsiGenerator/RuleEntry.swift
@@ -206,7 +206,6 @@
   public let swiftLanguageVersion: String?
 
   /// The swift toolchain argument used by this target.
-  // TODO(abaire): It is hoped that this may be removed when support for Swift 2.3 is dropped.
   public let swiftToolchain: String?
 
   /// List containing the transitive swiftmodules on which this rule depends.
diff --git a/src/TulsiGenerator/Scripts/bazel_build.py b/src/TulsiGenerator/Scripts/bazel_build.py
index 8323e3e..29c514e 100755
--- a/src/TulsiGenerator/Scripts/bazel_build.py
+++ b/src/TulsiGenerator/Scripts/bazel_build.py
@@ -1209,7 +1209,6 @@
                            level=1)
 
         if not filename.startswith(bundle_subpath):
-          # TODO(abaire): Make an error if Bazel modifies this behavior.
           _PrintXcodeWarning('Mismatched extraction path. Bundle content '
                              'at "%s" expected to have subpath of "%s"' %
                              (filename, bundle_subpath))
diff --git a/src/TulsiGenerator/TulsiOptionSet.swift b/src/TulsiGenerator/TulsiOptionSet.swift
index 103b4fa..5a0bba3 100644
--- a/src/TulsiGenerator/TulsiOptionSet.swift
+++ b/src/TulsiGenerator/TulsiOptionSet.swift
@@ -200,7 +200,6 @@
   func commonBuildSettings() -> [String: String] {
     // These values come from AppleToolchain.java in Bazel
     // https://github.com/bazelbuild/bazel/blob/master/src/main/java/com/google/devtools/build/lib/rules/apple/AppleToolchain.java
-    // TODO(abaire): Expose for user modification.
     var buildSettings = [
         "GCC_WARN_64_TO_32_BIT_CONVERSION": "YES",
         "CLANG_WARN_BOOL_CONVERSION": "YES",
diff --git a/src/TulsiGenerator/XcodeProjectGenerator.swift b/src/TulsiGenerator/XcodeProjectGenerator.swift
index eaa496c..93d2b58 100644
--- a/src/TulsiGenerator/XcodeProjectGenerator.swift
+++ b/src/TulsiGenerator/XcodeProjectGenerator.swift
@@ -96,7 +96,6 @@
   private let pbxTargetGeneratorType: PBXTargetGeneratorProtocol.Type
 
   /// Exposed for testing. Simply writes the given NSData to the given NSURL.
-  /// TODO(dmishe): Use fileManager instance to perform writes, and remove this block.
   var writeDataHandler: (URL, Data) throws -> Void = { (outputFileURL: URL, data: Data) in
     try data.write(to: outputFileURL, options: NSData.WritingOptions.atomic)
   }
@@ -390,9 +389,7 @@
     let ruleEntryMap = try loadRuleEntryMap()
     var expandedTargetLabels = Set<BuildLabel>()
     var testSuiteRules = [BuildLabel: RuleEntry]()
-    // Ideally this should use a generic SequenceType, but Swift 2.2 sometimes crashes in this case.
-    // TODO(abaire): Go back to using a generic here when support for Swift 2.2 is removed.
-    func expandTargetLabels(_ labels: Set<BuildLabel>) {
+    func expandTargetLabels<T: Sequence>(_ labels: T) where T.Iterator.Element == BuildLabel {
       for label in labels {
         // Effectively we will only be using the last RuleEntry in the case of duplicates.
         // We could log about duplicates here, but this would only lead to duplicate logging.
@@ -413,8 +410,7 @@
         }
       }
     }
-    let buildTargetLabels = Set(config.buildTargetLabels)
-    expandTargetLabels(buildTargetLabels)
+    expandTargetLabels(config.buildTargetLabels)
 
     var targetRules = Set<RuleEntry>()
     var hostTargetLabels = [BuildLabel: BuildLabel]()
@@ -1418,7 +1414,6 @@
       var ret = [URL]()
       for n in root.children.values {
         for path in n.leafPaths() {
-          // TODO(dmishe): Swicth to an appropriate URL method.
           guard let url = NSURL.fileURL(withPathComponents: path) else {
             continue
           }
diff --git a/src/TulsiGeneratorIntegrationTests/PlatformDependentEndToEndGenerationTests.swift b/src/TulsiGeneratorIntegrationTests/PlatformDependentEndToEndGenerationTests.swift
index a9f7312..186a8a1 100644
--- a/src/TulsiGeneratorIntegrationTests/PlatformDependentEndToEndGenerationTests.swift
+++ b/src/TulsiGeneratorIntegrationTests/PlatformDependentEndToEndGenerationTests.swift
@@ -20,6 +20,6 @@
 // contains some platform-dependent components (e.g., dependency paths).
 class PlatformDependentEndToEndGenerationTests: EndToEndIntegrationTestCase {
   func test_PlatformDependentProject() {
-    // TODO(abaire): Implement.
+    // Not implemented.
   }
 }
diff --git a/src/TulsiGeneratorTests/PBXTargetGeneratorTests.swift b/src/TulsiGeneratorTests/PBXTargetGeneratorTests.swift
index c8f094d..c9ecde5 100644
--- a/src/TulsiGeneratorTests/PBXTargetGeneratorTests.swift
+++ b/src/TulsiGeneratorTests/PBXTargetGeneratorTests.swift
@@ -2853,7 +2853,6 @@
 
       let script = scriptBuildPhase.shellScript
 
-      // TODO(abaire): Consider doing deeper validation of the script.
       XCTAssert(script.contains(bazelURL.path),
                 "Build script does not contain \(bazelURL.path)",
                 line: line)