/*
 * Copyright (C) 2009 Google Inc.
 *
 * 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.
 */

package com.googlecode.android_scripting.jsonrpc;

import com.googlecode.android_scripting.Log;
import com.googlecode.android_scripting.SimpleServer;
import com.googlecode.android_scripting.rpc.MethodDescriptor;
import com.googlecode.android_scripting.rpc.RpcError;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.io.BufferedReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Map;

/**
 * A JSON RPC server that forwards RPC calls to a specified receiver object.
 *
 * @author Damon Kohler (damonkohler@gmail.com)
 */
public class JsonRpcServer extends SimpleServer {

  private final RpcReceiverManagerFactory mRpcReceiverManagerFactory;
  private final String mHandshake;

  /**
   * Construct a {@link JsonRpcServer} connected to the provided {@link RpcReceiverManager}.
   *
   * @param managerFactory
   *          the {@link RpcReceiverManager} to register with the server
   * @param handshake
   *          the secret handshake required for authorization to use this server
   */
  public JsonRpcServer(RpcReceiverManagerFactory managerFactory, String handshake) {
    mHandshake = handshake;
    mRpcReceiverManagerFactory = managerFactory;
  }

  @Override
  public void shutdown() {
    super.shutdown();
    // Notify all RPC receiving objects. They may have to clean up some of their state.
    for (RpcReceiverManager manager : mRpcReceiverManagerFactory.getRpcReceiverManagers().values()) {
      manager.shutdown();
    }
  }


  @Override
  protected void handleRPCConnection(Socket sock, Integer UID, BufferedReader reader, PrintWriter writer) throws Exception {
    RpcReceiverManager receiverManager = null;
    Map<Integer, RpcReceiverManager> mgrs = mRpcReceiverManagerFactory.getRpcReceiverManagers();
    synchronized (mgrs) {
      Log.d("UID "+UID);
      Log.d("manager map size: "+mRpcReceiverManagerFactory.getRpcReceiverManagers().size());
      Log.d("manager map keys: "+mRpcReceiverManagerFactory.getRpcReceiverManagers().keySet());
      if(mgrs.containsKey(UID)) {
        Log.d("Look up existing session");
        receiverManager = mgrs.get(UID);
      }else{
        Log.d("Create a new session");
        receiverManager = mRpcReceiverManagerFactory.create(UID);
      }
    }

    /*RpcReceiverManager receiverManager = mRpcReceiverManagerFactory.create();
    BufferedReader reader =
        new BufferedReader(new InputStreamReader(socket.getInputStream()), 8192);
    PrintWriter writer = new PrintWriter(socket.getOutputStream(), true);*/
    //boolean passedAuthentication = false;
    String data;
    while ((data = reader.readLine()) != null) {
      Log.v("Session " + UID + " Received: " + data);
      JSONObject request = new JSONObject(data);
      int id = request.getInt("id");
      String method = request.getString("method");
      JSONArray params = request.getJSONArray("params");

      // First RPC must be _authenticate if a handshake was specified.
//      if (!passedAuthentication && mHandshake != null) {
//        if (!checkHandshake(method, params)) {
//          SecurityException exception = new SecurityException("Authentication failed!");
//          send(writer, JsonRpcResult.error(id, exception));
//          shutdown();
//          throw exception;
//        }
//        passedAuthentication = true;
//        send(writer, JsonRpcResult.result(id, true));
//        continue;
//      }

      MethodDescriptor rpc = receiverManager.getMethodDescriptor(method);
      if (rpc == null) {
        send(writer, JsonRpcResult.error(id, new RpcError("Unknown RPC.")), UID);
        continue;
      }
      try {
        send(writer, JsonRpcResult.result(id, rpc.invoke(receiverManager, params)), UID);
      } catch (Throwable t) {
        Log.e("Invocation error.", t);
        send(writer, JsonRpcResult.error(id, t), UID);
      }
    }
  }

  private boolean checkHandshake(String method, JSONArray params) throws JSONException {
    if (!method.equals("_authenticate") || !mHandshake.equals(params.getString(0))) {
      return false;
    }
    return true;
  }

  private void send(PrintWriter writer, JSONObject result, int UID) {
    writer.write(result + "\n");
    writer.flush();
    Log.v("Session " + UID + " Sent: " + result);
  }

  @Override
  protected void handleConnection(Socket socket) throws Exception {
  }
}
