// Copyright 2014 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "buffet/commands/command_instance.h"

#include <base/values.h>
#include <chromeos/errors/error.h>
#include <chromeos/errors/error_codes.h>

#include "buffet/commands/command_definition.h"
#include "buffet/commands/command_dictionary.h"
#include "buffet/commands/command_proxy_interface.h"
#include "buffet/commands/command_queue.h"
#include "buffet/commands/schema_constants.h"
#include "buffet/commands/schema_utils.h"

namespace buffet {

const char CommandInstance::kStatusQueued[] = "queued";
const char CommandInstance::kStatusInProgress[] = "inProgress";
const char CommandInstance::kStatusPaused[] = "paused";
const char CommandInstance::kStatusError[] = "error";
const char CommandInstance::kStatusDone[] = "done";
const char CommandInstance::kStatusCanceled[] = "canceled";
const char CommandInstance::kStatusAborted[] = "aborted";
const char CommandInstance::kStatusExpired[] = "expired";

CommandInstance::CommandInstance(const std::string& name,
                                 const std::string& category,
                                 const native_types::Object& parameters)
    : name_(name), category_(category), parameters_(parameters) {
}

CommandInstance::~CommandInstance() = default;

std::shared_ptr<const PropValue> CommandInstance::FindParameter(
    const std::string& name) const {
  std::shared_ptr<const PropValue> value;
  auto p = parameters_.find(name);
  if (p != parameters_.end())
    value = p->second;
  return value;
}

namespace {

// Helper method to retrieve command parameters from the command definition
// object passed in as |json| and corresponding command definition schema
// specified in |command_def|.
// On success, returns |true| and the validated parameters and values through
// |parameters|. Otherwise returns |false| and additional error information in
// |error|.
bool GetCommandParameters(const base::DictionaryValue* json,
                          const CommandDefinition* command_def,
                          native_types::Object* parameters,
                          chromeos::ErrorPtr* error) {
  // Get the command parameters from 'parameters' property.
  base::DictionaryValue no_params;  // Placeholder when no params are specified.
  const base::DictionaryValue* params = nullptr;
  const base::Value* params_value = nullptr;
  if (json->GetWithoutPathExpansion(commands::attributes::kCommand_Parameters,
                                    &params_value)) {
    // Make sure the "parameters" property is actually an object.
    if (!params_value->GetAsDictionary(&params)) {
      chromeos::Error::AddToPrintf(error, FROM_HERE,
                                   chromeos::errors::json::kDomain,
                                   chromeos::errors::json::kObjectExpected,
                                   "Property '%s' must be a JSON object",
                                   commands::attributes::kCommand_Parameters);
      return false;
    }
  } else {
    // "parameters" are not specified. Assume empty param list.
    params = &no_params;
  }

  // Now read in the parameters and validate their values against the command
  // definition schema.
  if (!TypedValueFromJson(params, command_def->GetParameters().get(),
                          parameters, error)) {
    return false;
  }
  return true;
}

}  // anonymous namespace

std::unique_ptr<CommandInstance> CommandInstance::FromJson(
    const base::Value* value,
    const CommandDictionary& dictionary,
    chromeos::ErrorPtr* error) {
  std::unique_ptr<CommandInstance> instance;
  // Get the command JSON object from the value.
  const base::DictionaryValue* json = nullptr;
  if (!value->GetAsDictionary(&json)) {
    chromeos::Error::AddTo(error, FROM_HERE, chromeos::errors::json::kDomain,
                           chromeos::errors::json::kObjectExpected,
                           "Command instance is not a JSON object");
    return instance;
  }

  // Get the command name from 'name' property.
  std::string command_name;
  if (!json->GetStringWithoutPathExpansion(commands::attributes::kCommand_Name,
                                           &command_name)) {
    chromeos::Error::AddTo(error, FROM_HERE, errors::commands::kDomain,
                           errors::commands::kPropertyMissing,
                           "Command name is missing");
    return instance;
  }
  // Make sure we know how to handle the command with this name.
  const CommandDefinition* command_def = dictionary.FindCommand(command_name);
  if (!command_def) {
    chromeos::Error::AddToPrintf(error, FROM_HERE, errors::commands::kDomain,
                                 errors::commands::kInvalidCommandName,
                                 "Unknown command received: %s",
                                 command_name.c_str());
    return instance;
  }

  native_types::Object parameters;
  if (!GetCommandParameters(json, command_def, &parameters, error)) {
    chromeos::Error::AddToPrintf(error, FROM_HERE, errors::commands::kDomain,
                                 errors::commands::kCommandFailed,
                                 "Failed to validate command '%s'",
                                 command_name.c_str());
    return instance;
  }

  instance.reset(new CommandInstance(command_name,
                                     command_def->GetCategory(),
                                     parameters));
  // TODO(antonm): Move command_id to ctor and remove setter.
  std::string command_id;
  if (json->GetStringWithoutPathExpansion(commands::attributes::kCommand_Id,
                                          &command_id)) {
    instance->SetID(command_id);
  }

  return instance;
}

void CommandInstance::AddProxy(std::unique_ptr<CommandProxyInterface> proxy) {
  proxies_.push_back(std::move(proxy));
}

bool CommandInstance::SetProgress(int progress) {
  if (progress < 0 || progress > 100)
    return false;
  if (progress != progress_) {
    progress_ = progress;
    SetStatus(kStatusInProgress);
    for (auto& proxy : proxies_) {
      proxy->OnProgressChanged(progress_);
    }
  }
  return true;
}

void CommandInstance::Abort() {
  SetStatus(kStatusAborted);
  RemoveFromQueue();
  // The command will be destroyed after that, so do not access any members.
}

void CommandInstance::Cancel() {
  SetStatus(kStatusCanceled);
  RemoveFromQueue();
  // The command will be destroyed after that, so do not access any members.
}

void CommandInstance::Done() {
  SetProgress(100);
  SetStatus(kStatusDone);
  RemoveFromQueue();
  // The command will be destroyed after that, so do not access any members.
}

void CommandInstance::SetStatus(const std::string& status) {
  if (status != status_) {
    status_ = status;
    for (auto& proxy : proxies_) {
      proxy->OnStatusChanged(status_);
    }
  }
}

void CommandInstance::RemoveFromQueue() {
  if (queue_) {
    // Store this instance in unique_ptr until the end of this method,
    // otherwise it will be destroyed as soon as CommandQueue::Remove() returns.
    std::unique_ptr<CommandInstance> this_instance = queue_->Remove(GetID());
    // The command instance will survive till the end of this scope.
  }
}


}  // namespace buffet
