# Copyright 2015 The Bazel 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.

"""Build definitions for JavaScript binaries compiled with the Closure Compiler.

A single file is produced with the _compiled.js suffix.

By default, the name of the entry point is assumed to be the same as that of the
build target. This behaviour may be overridden with the "main" attribute.

The optimization level may be set with the "compilation_level" attribute.
Supported values are: unobfuscated, simple, and advanced.

Example:

  closure_js_binary(
      name = "hello",
      compilation_level = "simple",
      language_in = "ecmascript6",
      language_out = "ecmascript3",
      externs = ["//third_party/javascript/google_cast/cast.js"],
      deps = [
          "@closure_library//:closure_library",
          ":hello_lib",
      ],
  )

This rule will produce hello_combined.js.
"""

_COMPILATION_LEVELS = {
  "whitespace_only": [
      "--compilation_level=WHITESPACE_ONLY",
      "--formatting=PRETTY_PRINT"
  ],
  "simple": ["--compilation_level=SIMPLE"],
  "advanced": ["--compilation_level=ADVANCED"]
}

_SUPPORTED_LANGUAGES = {
  "es3": ["ES3"],
  "ecmascript3": ["ECMASCRIPT3"],
  "es5": ["ES5"],
  "ecmascript5": ["ECMASCRIPT5"],
  "es5_strict": ["ES5_STRICT"],
  "ecmascript5_strict": ["ECMASCRIPT5_STRICT"],
  "es6": ["ES6"],
  "ecmascript6": ["ECMASCRIPT6"],
  "es6_strict": ["ES6_STRICT"],
  "ecmascript6_strict": ["ECMASCRIPT6_STRICT"],
  "es6_typed": ["ES6_TYPED"],
  "ecmascript6_typed": ["ECMASCRIPT6_TYPED"],
}

def _impl(ctx):
  externs = set(order="compile")
  srcs = set(order="compile")
  for dep in ctx.attr.deps:
    externs += dep.transitive_js_externs
    srcs += dep.transitive_js_srcs

  args = [
      "--entry_point=goog:%s" % ctx.attr.main,
      "--js_output_file=%s" % ctx.outputs.out.path,
      "--dependency_mode=LOOSE",
      "--warning_level=VERBOSE",
  ] + (["--js=%s" % src.path for src in srcs] +
       ["--externs=%s" % extern.path for extern in externs])

  # Set the compilation level.
  if ctx.attr.compilation_level in _COMPILATION_LEVELS:
    args += _COMPILATION_LEVELS[ctx.attr.compilation_level]
  else:
    fail("Invalid compilation_level '%s', expected one of %s" %
         (ctx.attr.compilation_level, _COMPILATION_LEVELS.keys()))

  # Set the language in.
  if ctx.attr.language_in in _SUPPORTED_LANGUAGES:
    args += "--language_in=" + _SUPPORTED_LANGUAGES[ctx.attr.language_in]
  else:
    fail("Invalid language_in '%s', expected one of %s" %
         (ctx.attr.language_in, _SUPPORTED_LANGUAGES.keys()))

  # Set the language out.
  if ctx.attr.language_out in _SUPPORTED_LANGUAGES:
    args += "--language_out=" + _SUPPORTED_LANGUAGES[ctx.attr.language_out]
  else:
    fail("Invalid language_out '%s', expected one of %s" %
         (ctx.attr.language_out, _SUPPORTED_LANGUAGES.keys()))

  ctx.action(
      inputs=list(srcs) + list(externs),
      outputs=[ctx.outputs.out],
      arguments=args,
      executable=ctx.executable._closure_compiler)

  return struct(files=set([ctx.outputs.out]))

closure_js_binary = rule(
    implementation=_impl,
    attrs={
        "deps": attr.label_list(
            allow_files=False,
            providers=["transitive_js_externs", "transitive_js_srcs"]),
        "main": attr.string(default="%{name}"),
        "compilation_level": attr.string(default="advanced"),
        "language_in": attr.string(default="ecmascript6"),
        "language_out": attr.string(default="ecmascript3"),
        "_closure_compiler": attr.label(
            default=Label("//external:closure_compiler_"),
            executable=True),
    },
    outputs={"out": "%{name}_combined.js"})
