<import src="/mojo/public/sky/connection.sky" as="connection" />
<import src="/mojo/public/sky/core.sky" as="core" />
<import src="/mojo/public/sky/support.sky" as="support" />
<import src="/sky/services/inspector/inspector.mojom.sky" as="inspector" />
<import src="console-agent.sky" as="ConsoleAgent" />
<import src="dom-agent.sky" as="DOMAgent" />
<import src="page-agent.sky" as="PageAgent" />
<import src="worker-agent.sky" as="WorkerAgent" />
<import src="runtime-agent.sky" as="RuntimeAgent" />
<import src="indexeddb-agent.sky" as="IndexedDBAgent" />
<import src="css-agent.sky" as="CSSAgent" />
<script>
function InspectorBackend(frontend) {
  this.frontend = frontend;
  var domAgent = new DOMAgent(this);
  this.agents = {
    Console: new ConsoleAgent(),
    DOM: domAgent,
    Page: new PageAgent(this),
    Worker: new WorkerAgent(),
    Runtime: new RuntimeAgent(this),
    CSS: new CSSAgent(domAgent),
    IndexedDB: new IndexedDBAgent(),
  };
  this.missingNames_ = {};
  this.unansweredMessages_ = [];
}

InspectorBackend.prototype = Object.create(
    inspector.InspectorBackend.stubClass.prototype);

InspectorBackend.prototype.IMPLEMENTED_IN_CPP = "IMPLEMENTED_IN_CPP";
InspectorBackend.prototype.ASYNC_RESPONSE = "ASYNC_RESPONSE";
InspectorBackend.prototype.MESSAGE_TIMEOUT_MS = 30000;

InspectorBackend.prototype.onConnect = function() {
};

InspectorBackend.prototype.onDisconnect = function() {
};

InspectorBackend.prototype.logMissing_ = function(name) {
  if (name in this.missingNames_)
    return;
  this.missingNames_[name] = true;
  console.log("InspectorBackend missing " + name);
}

InspectorBackend.prototype.dispatch_ = function(descriptor, params, message_id) {
  var parsed = descriptor.split('.');

  var agentName = parsed[0];
  var methodName = parsed[1];

  // Debugger is implemented in c++.
  if (agentName == "Debugger")
    return this.IMPLEMENTED_IN_CPP;

  if (!(agentName in this.agents)) {
    this.logMissing_(agentName);
    return {};
  }

  var agent = this.agents[agentName];

  if (!(methodName in agent)) {
    this.logMissing_(descriptor);
    return {};
  }

  try {
    return agent[methodName](params, message_id);
  } catch(ex) {
    console.log(descriptor + ": " + ex);
  }
};

InspectorBackend.prototype.onMessage = function(data) {
  var message = JSON.parse(data);
  var result = this.dispatch_(message.method, message.params, message.id);
  if (result === this.IMPLEMENTED_IN_CPP)
      return;
  this.unansweredMessages_.push(message.id);
  // FIXME: This magic return value is kinda hacky.
  if (result !== this.ASYNC_RESPONSE)
    this.sendResponse(message.id, result);
  else {
    window.setTimeout(function() {
      if (this.unansweredMessages_.indexOf(message.id) == -1)
        return;
      console.log("Error, failed to reply to message id " + message.id);
    }.bind(this), this.MESSAGE_TIMEOUT_MS);
  }
};

InspectorBackend.prototype.sendResponse = function(message_id, result) {
  var messageIndex = this.unansweredMessages_.indexOf(message_id);
  if (messageIndex != -1)
    this.unansweredMessages_.splice(messageIndex, 1);
  else
    console.log("Error, responding to unknown message id " + message_id);
  var response = {
    id: message_id,
  };
  if (typeof result !== "undefined")
    response.result = result;
  this.frontend.sendMessage(JSON.stringify(response));
}

InspectorBackend.prototype.sendMessage = function(method, params) {
  var message = JSON.stringify({
    method: method,
    params: params,
  });
  this.frontend.sendMessage(message);
};

var frontendHandle = internals.connectToService(
    "mojo:sky_inspector_server", inspector.InspectorFrontend.name);
window.frontendConnection = new connection.Connection(
    frontendHandle,
    InspectorBackend,
    inspector.InspectorFrontend.proxyClass);

window.frontend = frontendConnection.remote;
</script>
