// Copyright 2017 The Cobalt 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.

#include <iostream>

#include "base/command_line.h"
#include "base/files/file_path.h"
#include "base/strings/string_util.h"
#include "cobalt/base/wrap_main.h"
#include "cobalt/script/source_code.h"
#include "cobalt/script/standalone_javascript_runner.h"
#include "cobalt/script/v8c/v8c_global_environment.h"
#include "v8/include/libplatform/libplatform.h"
#include "v8/include/v8.h"

namespace cobalt {
namespace script {
namespace v8c {
namespace {

void Print(const v8::FunctionCallbackInfo<v8::Value>& args) {
  v8::Isolate* isolate = args.GetIsolate();
  v8::HandleScope scope(isolate);

  std::vector<std::string> string_args;
  for (int i = 0; i < args.Length(); i++) {
    v8::TryCatch try_catch(args.GetIsolate());
    v8::Local<v8::Value> arg = args[i];
    v8::Local<v8::String> string;

    if (arg->IsSymbol()) {
      arg = v8::Local<v8::Symbol>::Cast(arg)->Name();
    }
    if (!arg->ToString(args.GetIsolate()->GetCurrentContext())
             .ToLocal(&string)) {
      try_catch.ReThrow();
      return;
    }

    v8::String::Utf8Value utf8_value(args.GetIsolate(), string);
    string_args.push_back(*utf8_value);
  }

  std::string joined = base::JoinString(string_args, " ");
  std::cout << joined << std::endl;
}

void SetupBindings(GlobalEnvironment* global_environment) {
  V8cGlobalEnvironment* v8c_global_environment =
      static_cast<V8cGlobalEnvironment*>(global_environment);
  v8::Isolate* isolate = v8c_global_environment->isolate();
  v8::Isolate::Scope isolate_scope(isolate);
  v8::HandleScope handle_scope(isolate);
  v8::Local<v8::Context> context = v8c_global_environment->context();
  v8::Context::Scope context_scope(context);
  v8::Maybe<bool> set_result = context->Global()->Set(
      context,
      v8::String::NewFromUtf8(isolate, "print", v8::NewStringType::kNormal)
          .ToLocalChecked(),
      v8::Function::New(context, Print).ToLocalChecked());
  DCHECK(set_result.FromJust());
}

cobalt::script::StandaloneJavascriptRunner* g_javascript_runner = NULL;

void StartApplication(int argc, char** argv, const char* /*link */,
                      const base::Closure& quit_closure) {
  DCHECK(!g_javascript_runner);
  g_javascript_runner = new cobalt::script::StandaloneJavascriptRunner(
      base::MessageLoop::current()->task_runner());
  DCHECK(g_javascript_runner);

  GlobalEnvironment* global_environment =
      g_javascript_runner->global_environment().get();
  SetupBindings(global_environment);
  if (argc > 1) {
    // Command line arguments will be flag-value pairs of the form
    // -f filename
    // and
    // -e "inline script"
    // and will be evaluated in order.
    for (int i = 1; (i + 1) < argc; ++i) {
      if (std::string(argv[i]) == "-f") {
        std::string filename = std::string(argv[i + 1]);
        // Execute source file.
        base::FilePath source_file(filename);
        g_javascript_runner->ExecuteFile(source_file);
        ++i;
      } else if (std::string(argv[i]) == "-e") {
        // Execute inline script.
        scoped_refptr<SourceCode> source = SourceCode::CreateSourceCode(
            argv[i + 1], base::SourceLocation("[stdin]", 1, 1));

        // Execute the script and get the results of execution.
        std::string result;
        bool success = global_environment->EvaluateScript(source, &result);
        // Echo the results to stdout.
        if (!success) {
          std::cout << "Exception: ";
        }
        std::cout << result << std::endl;
        ++i;
      }
    }
    g_javascript_runner->Quit(quit_closure);
  } else {
    g_javascript_runner->RunUntilDone(quit_closure);
  }
}

void StopApplication() {
  DCHECK(g_javascript_runner);
  delete g_javascript_runner;
  g_javascript_runner = NULL;
}

}  // namespace
}  // namespace v8c
}  // namespace script
}  // namespace cobalt

COBALT_WRAP_BASE_MAIN(cobalt::script::v8c::StartApplication,
                      cobalt::script::v8c::StopApplication);
