# Copyright 2019 The Pigweed Authors
#
# 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
#
#     https://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("//build_overrides/pigweed.gni")

import("$dir_pw_build/input_group.gni")
import("$dir_pw_build/python_action.gni")

declare_args() {
  # Whether or not the current target should build docs.
  pw_docgen_BUILD_DOCS = false

  # Set to enable Google Analytics tracking of generated docs.
  pw_docgen_GOOGLE_ANALYTICS_ID = ""

  # Set to define the number of parallel threads to use during the Sphinx build.
  pw_docgen_THREADS = ""
}

# Defines a group of documentation files and assets.
#
# Args:
#   sources: Source files for the documentation (.rst or .md).
#   inputs: Additional resource files for the docs, such as images.
#   group_deps: Other pw_doc_group targets on which this group depends.
#   report_deps: Report card targets on which documentation depends.
#   other_deps: Dependencies on any other types of targets.
template("pw_doc_group") {
  assert(defined(invoker.sources) || defined(invoker.inputs),
         "pw_doc_group requires at least one of sources or inputs")

  # Create a group containing the source and input files so that docs are
  # rebuilt on file modifications.
  pw_input_group(target_name) {
    _sources = []
    if (defined(invoker.sources)) {
      _sources = invoker.sources
    }

    _inputs = []
    if (defined(invoker.inputs)) {
      _inputs = invoker.inputs
    }

    metadata = {
      pw_doc_sources = rebase_path(_sources, root_build_dir)
      pw_doc_inputs = rebase_path(_inputs, root_build_dir)
    }

    deps = []
    if (defined(invoker.group_deps)) {
      deps += invoker.group_deps
    }
    if (defined(invoker.report_deps)) {
      deps += invoker.report_deps
    }
    if (defined(invoker.other_deps)) {
      deps += invoker.other_deps
    }

    inputs = _sources + _inputs
  }
}

# Creates a target to build HTML documentation from groups of sources.
#
# Args:
#   deps: List of pw_doc_group targets.
#   python_metadata_deps: Python-related dependencies that are only used as deps
#                         for generating Python package metadata list, not the
#                         overall documentation generation. This should rarely
#                         be used by non-Pigweed code.
#   sources: Top-level documentation .rst source files.
#   conf: Configuration script (conf.py) for Sphinx.
#   output_directory: Path to directory to which HTML output is rendered.
template("pw_doc_gen") {
  assert(defined(invoker.deps),
         "pw_doc_gen requires doc groups as dependencies")
  assert(defined(invoker.sources) && invoker.sources != [],
         "pw_doc_gen requires a 'sources' list with at least one .rst source")
  assert(defined(invoker.conf),
         "pw_doc_gen requires a 'conf' argument pointing a top-level conf.py")
  assert(defined(invoker.output_directory),
         "pw_doc_gen requires an 'output_directory' argument")

  if (pw_docgen_BUILD_DOCS) {
    # Collects all dependency metadata into a single JSON file.
    _metadata_file_target = "${target_name}_metadata"
    generated_file(_metadata_file_target) {
      outputs = [ "$target_gen_dir/$target_name.json" ]
      data_keys = [
        "pw_doc_sources",
        "pw_doc_inputs",
      ]
      output_conversion = "json"
      deps = invoker.deps
    }

    pw_python_action(target_name) {
      module = "pw_docgen.docgen"
      args = [
        "--gn-root",
        rebase_path("//", root_build_dir),
        "--gn-gen-root",
        rebase_path(root_gen_dir, root_build_dir) + "/",
        "--sphinx-build-dir",
        rebase_path("$target_gen_dir/pw_docgen_tree", root_build_dir),
        "--conf",
        rebase_path(invoker.conf, root_build_dir),
        "--out-dir",
        rebase_path(invoker.output_directory, root_build_dir),
      ]

      # Enable Google Analytics if a measurement ID is provided
      if (pw_docgen_GOOGLE_ANALYTICS_ID != "") {
        args += [
          "--google-analytics-id",
          pw_docgen_GOOGLE_ANALYTICS_ID,
        ]
      }

      # Override the default number of threads for the Sphinx build.
      if (pw_docgen_THREADS != "") {
        args += [
          "-j",
          pw_docgen_THREADS,
        ]
      }

      # Metadata JSON file path.
      args += [ "--metadata" ] +
              rebase_path(get_target_outputs(":$_metadata_file_target"),
                          root_build_dir)

      args += rebase_path(invoker.sources, root_build_dir)

      python_deps = [ "$dir_pw_docgen/py" ]
      deps = [ ":$_metadata_file_target" ]

      # Required to set the PYTHONPATH for any automodule/class/function RST
      # directives.
      python_metadata_deps = [ "$dir_pw_docgen/py" ]
      if (defined(invoker.python_metadata_deps)) {
        python_metadata_deps += invoker.python_metadata_deps
      }

      inputs = [ invoker.conf ] + invoker.sources
      stamp = true
    }
  } else {
    group(target_name) {
    }
  }
}
