/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You 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 <map>
#include <string>

#include <geode/ExceptionTypes.hpp>

#include "ErrType.hpp"
#include "util/Log.hpp"

namespace apache {
namespace geode {
namespace client {

void setThreadLocalExceptionMessage(std::string exMsg);
const std::string& getThreadLocalExceptionMessage();

std::map<GfErrType,
         std::function<void(std::string, std::string&, GfErrType, std::string)>>
    error_map_;

[[noreturn]] void notConnectedException(std::string message, std::string& exMsg,
                                        GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": not connected to Geode");
  NotConnectedException ex(message);
  throw ex;
}

    [[noreturn]] void messageException(std::string message, std::string& exMsg,
                                       GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg
                                : ": message from server could not be handled");
  MessageException ex(message);
  throw ex;
}

[[noreturn]] void cacheServerException(std::string message, std::string& exMsg,
                                       GfErrType err, std::string) {
  if (err == GF_CACHESERVER_EXCEPTION) {
    message.append(!exMsg.empty() ? exMsg
                                  : ": exception happened at cache server");
  }
  if (err == GF_CACHE_REGION_NOT_FOUND) {
    message.append(!exMsg.empty() ? exMsg : ": region not found on server");
  }
  CacheServerException ex(message);
  throw ex;
}

    [[noreturn]] void notOwnerException(std::string message, std::string& exMsg,
                                        GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": not own the lock");
  NotOwnerException ex(message);
  throw ex;
}

[[noreturn]] void illegalStateException(std::string message, std::string& exMsg,
                                        GfErrType err, std::string) {
  if (err == GF_CACHE_REGION_NOT_GLOBAL) {
    message.append(!exMsg.empty() ? exMsg : ": region not global");
  }
  if (err == GF_CACHE_ILLEGAL_STATE_EXCEPTION) {
    message.append(!exMsg.empty() ? exMsg : ": illegal State");
  }
  IllegalStateException ex(message);
  throw ex;
}

    [[noreturn]] void illegalArgumentException(std::string message,
                                               std::string& exMsg,
                                               GfErrType err, std::string) {
  if (err == GF_CACHE_ILLEGAL_ARGUMENT_EXCEPTION) {
    message.append(!exMsg.empty() ? exMsg : ": illegal argument");
  }
  if (err == GF_CACHE_REGION_KEYS_NOT_STRINGS) {
    message.append(!exMsg.empty() ? exMsg
                                  : ": region entries do not support C access");
  }
  if (err == GF_CACHE_REGION_ENTRY_NOT_BYTES) {
    message.append(!exMsg.empty()
                       ? exMsg
                       : ": existing non-null values was not a byte array");
  }
  IllegalArgumentException ex(message);
  throw ex;
}

[[noreturn]] void cacheWriterException(std::string message, std::string& exMsg,
                                       GfErrType err, std::string) {
  if (err == GF_CACHE_WRITER_EXCEPTION) {
    message.append(!exMsg.empty() ? exMsg
                                  : ": exception on server during write");
  }
  if (err == GF_CACHEWRITER_ERROR) {
    message.append(!exMsg.empty() ? exMsg : ": exception in CacheWriter");
  }
  CacheWriterException ex(message);
  throw ex;
}

    [[noreturn]] void cacheLoaderException(std::string message,
                                           std::string& exMsg, GfErrType,
                                           std::string) {
  message.append(!exMsg.empty() ? exMsg : ": exception in CacheLoader");
  CacheLoaderException ex(message);
  throw ex;
}

[[noreturn]] void cacheListenerException(std::string message,
                                         std::string& exMsg, GfErrType,
                                         std::string) {
  message.append(!exMsg.empty() ? exMsg : ": exception in CacheListener");
  CacheListenerException ex(message);
  throw ex;
}

    [[noreturn]] void regionDestroyedException(std::string message,
                                               std::string& exMsg,
                                               GfErrType err, std::string) {
  if (err == GF_CACHE_REGION_INVALID) {
    message.append(!exMsg.empty() ? exMsg : ": region not valid");
  }
  if (err == GF_CACHE_REGION_DESTROYED_EXCEPTION) {
    message.append(!exMsg.empty() ? exMsg : ": Named Region Destroyed");
  }
  RegionDestroyedException ex(message);
  throw ex;
}

[[noreturn]] void cacheProxyException(std::string message, std::string& exMsg,
                                      GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": error in Cache proxy");
  CacheProxyException ex(message);
  throw ex;
}

    [[noreturn]] void geodeIOException(std::string message, std::string& exMsg,
                                       GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Input/Output error in operation");
  GeodeIOException ex(message);
  throw ex;
}

[[noreturn]] void noSystemException(std::string message, std::string& exMsg,
                                    GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": entity does not exist");
  NoSystemException ex(message);
  throw ex;
}

    [[noreturn]] void timeoutException(std::string message, std::string& exMsg,
                                       GfErrType err, std::string) {
  if (err == GF_CLIENT_WAIT_TIMEOUT) {
    message.append(!exMsg.empty()
                       ? exMsg
                       : ": timed out, possibly bucket is not available.");
  } else {
    message.append(!exMsg.empty() ? exMsg : ": timed out");
  }
  TimeoutException ex(message);
  throw ex;
}

[[noreturn]] void outOfMemoryException(std::string message, std::string& exMsg,
                                       GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Out of memory");
  OutOfMemoryException ex(message);
  throw ex;
}

    [[noreturn]] void bufferSizeExceededException(std::string message,
                                                  std::string& exMsg, GfErrType,
                                                  std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Buffer Size Exceeded");
  BufferSizeExceededException ex(message);
  throw ex;
}

[[noreturn]] void leaseExpiredException(std::string message, std::string& exMsg,
                                        GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": lock Lease Expired On you");
  LeaseExpiredException ex(message);
  throw ex;
}

    [[noreturn]] void regionExistsException(std::string message,
                                            std::string& exMsg, GfErrType,
                                            std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Named Region Exists");
  RegionExistsException ex(message);
  throw ex;
}

[[noreturn]] void entryNotFoundException(std::string message,
                                         std::string& exMsg, GfErrType,
                                         std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Entry not found");
  EntryNotFoundException ex(message);
  throw ex;
}

    [[noreturn]] void entryExistsException(std::string message,
                                           std::string& exMsg, GfErrType,
                                           std::string) {
  message.append(!exMsg.empty() ? exMsg
                                : ": Entry already exists in the region");
  EntryExistsException ex(message);
  throw ex;
}

[[noreturn]] void entryDestroyedException(std::string message,
                                          std::string& exMsg, GfErrType,
                                          std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Entry has been destroyed");
  EntryDestroyedException ex(message);
  throw ex;
}

    [[noreturn]] void cacheClosedException(std::string message,
                                           std::string& exMsg, GfErrType,
                                           std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Cache has been closed");
  CacheClosedException ex(message);
  throw ex;
}

[[noreturn]] void statisticsDisabledException(std::string message,
                                              std::string& exMsg, GfErrType,
                                              std::string) {
  message.append(!exMsg.empty()
                     ? exMsg
                     : ": Statistics have been disabled for the region");
  StatisticsDisabledException ex(message);
  throw ex;
}

    [[noreturn]] void concurrentModificationException(std::string message,
                                                      std::string& exMsg,
                                                      GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg
                                : ": Concurrent modification in the cache");
  ConcurrentModificationException ex(message);
  throw ex;
}

[[noreturn]] void notAuthorizedException(std::string message,
                                         std::string& exMsg, GfErrType,
                                         std::string) {
  message.append(!exMsg.empty() ? exMsg : ": unauthorized operation");
  NotAuthorizedException ex(message);
  throw ex;
}

    [[noreturn]] void authenticationFailedException(std::string message,
                                                    std::string& exMsg,
                                                    GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": authentication failed");
  AuthenticationFailedException ex(message);
  throw ex;
}

[[noreturn]] void authenticationRequiredException(std::string message,
                                                  std::string& exMsg, GfErrType,
                                                  std::string) {
  message.append(!exMsg.empty() ? exMsg : ": no authentication provided");
  AuthenticationRequiredException ex(message);
  throw ex;
}

    [[noreturn]] void duplicateDurableClientException(std::string message,
                                                      std::string& exMsg,
                                                      GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Duplicate Durable Client Id");
  DuplicateDurableClientException ex(message);
  throw ex;
}

[[noreturn]] void queryException(std::string message, std::string& exMsg,
                                 GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Query failed");
  QueryException ex(message);
  throw ex;
}

    [[noreturn]] void noAvailableLocatorsException(std::string,
                                                   std::string& exMsg,
                                                   GfErrType,
                                                   std::string func) {
  NoAvailableLocatorsException cause(
      func + (!exMsg.empty() ? exMsg : ": No locators available"));
  try {
    throw cause;
  } catch (...) {
    NotConnectedException ex(
        func + (!exMsg.empty() ? exMsg : ": No locators available"));
    std::throw_with_nested(ex);
  }
}

[[noreturn]] void allConnectionsInUseException(std::string message,
                                               std::string& exMsg, GfErrType,
                                               std::string) {
  message.append(!exMsg.empty() ? exMsg : ": All connections are in use");
  AllConnectionsInUseException ex(message);
  throw ex;
}

    [[noreturn]] void functionExecutionException(std::string message,
                                                 std::string& exMsg, GfErrType,
                                                 std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Function execution failed");
  FunctionExecutionException ex(message);
  throw ex;
}

[[noreturn]] void diskFailureException(std::string message, std::string& exMsg,
                                       GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Disk full");
  DiskFailureException ex(message);
  throw ex;
}

    [[noreturn]] void rollbackException(std::string message, std::string& exMsg,
                                        GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Transaction rolled back");
  RollbackException ex(message);
  throw ex;
}

[[noreturn]] void commitConflictException(std::string message,
                                          std::string& exMsg, GfErrType,
                                          std::string) {
  message.append(!exMsg.empty() ? exMsg : ": Commit conflict exception");
  CommitConflictException ex(message);
  throw ex;
}

    [[noreturn]] void transactionDataRebalancedException(std::string message,
                                                         std::string& exMsg,
                                                         GfErrType,
                                                         std::string) {
  message.append(!exMsg.empty() ? exMsg
                                : ": Transaction data rebalanced exception");
  TransactionDataRebalancedException ex(message);
  throw ex;
}

[[noreturn]] void transactionDataNodeHasDepartedException(std::string message,
                                                          std::string& exMsg,
                                                          GfErrType,
                                                          std::string) {
  message.append(!exMsg.empty()
                     ? exMsg
                     : ": Transaction data node has departed exception");
  TransactionDataNodeHasDepartedException ex(message);
  throw ex;
}

    [[noreturn]] void putAllPartialResultException(std::string message,
                                                   std::string& exMsg,
                                                   GfErrType, std::string) {
  message.append(!exMsg.empty() ? exMsg : ": PutAll Partial exception");
  PutAllPartialResultException ex(message);
  throw ex;
}

[[noreturn]] void unknownException(std::string message, std::string& exMsg,
                                   GfErrType err, std::string func) {
  LOGINFO("error code: %d", err);
  message = func;
  if (exMsg.empty()) {
    message.append("Unknown error code ").append(std::to_string(err));
  } else {
    message.append(exMsg);
  }
  UnknownException ex(message);
  throw ex;
}

void setErrorMap() {
  error_map_.emplace(std::make_pair(GF_NOTCON, notConnectedException));
  error_map_.emplace(std::make_pair(GF_MSG, messageException));
  error_map_.emplace(
      std::make_pair(GF_CACHESERVER_EXCEPTION, cacheServerException));
  error_map_.emplace(std::make_pair(GF_NOTOWN, notOwnerException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_REGION_NOT_FOUND, cacheServerException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_REGION_NOT_GLOBAL, illegalStateException));
  error_map_.emplace(std::make_pair(GF_CACHE_ILLEGAL_ARGUMENT_EXCEPTION,
                                    illegalArgumentException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_ILLEGAL_STATE_EXCEPTION, illegalStateException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_WRITER_EXCEPTION, cacheWriterException));
  error_map_.emplace(
      std::make_pair(GF_CACHEWRITER_ERROR, cacheWriterException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_LOADER_EXCEPTION, cacheLoaderException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_LISTENER_EXCEPTION, cacheListenerException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_REGION_INVALID, regionDestroyedException));
  error_map_.emplace(std::make_pair(GF_CACHE_PROXY, cacheProxyException));
  error_map_.emplace(std::make_pair(GF_IOERR, geodeIOException));
  error_map_.emplace(std::make_pair(GF_ENOENT, noSystemException));
  error_map_.emplace(std::make_pair(GF_CACHE_REGION_KEYS_NOT_STRINGS,
                                    illegalArgumentException));
  error_map_.emplace(std::make_pair(GF_CACHE_REGION_ENTRY_NOT_BYTES,
                                    illegalArgumentException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_TIMEOUT_EXCEPTION, timeoutException));
  error_map_.emplace(std::make_pair(GF_TIMEOUT, timeoutException));
  error_map_.emplace(std::make_pair(GF_CLIENT_WAIT_TIMEOUT, timeoutException));
  error_map_.emplace(std::make_pair(GF_ENOMEM, outOfMemoryException));
  error_map_.emplace(std::make_pair(GF_ERANGE, bufferSizeExceededException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_LEASE_EXPIRED_EXCEPTION, leaseExpiredException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_REGION_EXISTS_EXCEPTION, regionExistsException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_ENTRY_NOT_FOUND, entryNotFoundException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_ENTRY_EXISTS, entryExistsException));
  error_map_.emplace(std::make_pair(GF_CACHE_ENTRY_DESTROYED_EXCEPTION,
                                    entryDestroyedException));
  error_map_.emplace(std::make_pair(GF_CACHE_REGION_DESTROYED_EXCEPTION,
                                    regionDestroyedException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_CLOSED_EXCEPTION, cacheClosedException));
  error_map_.emplace(std::make_pair(GF_CACHE_STATISTICS_DISABLED_EXCEPTION,
                                    statisticsDisabledException));
  error_map_.emplace(std::make_pair(GF_CACHE_CONCURRENT_MODIFICATION_EXCEPTION,
                                    concurrentModificationException));
  error_map_.emplace(
      std::make_pair(GF_NOT_AUTHORIZED_EXCEPTION, notAuthorizedException));
  error_map_.emplace(std::make_pair(GF_AUTHENTICATION_FAILED_EXCEPTION,
                                    authenticationFailedException));
  error_map_.emplace(std::make_pair(GF_AUTHENTICATION_REQUIRED_EXCEPTION,
                                    authenticationRequiredException));
  error_map_.emplace(std::make_pair(GF_DUPLICATE_DURABLE_CLIENT,
                                    duplicateDurableClientException));
  error_map_.emplace(std::make_pair(GF_REMOTE_QUERY_EXCEPTION, queryException));
  error_map_.emplace(
      std::make_pair(GF_CACHE_LOCATOR_EXCEPTION, noAvailableLocatorsException));
  error_map_.emplace(std::make_pair(GF_ALL_CONNECTIONS_IN_USE_EXCEPTION,
                                    allConnectionsInUseException));
  error_map_.emplace(
      std::make_pair(GF_FUNCTION_EXCEPTION, functionExecutionException));
  error_map_.emplace(std::make_pair(GF_DISKFULL, diskFailureException));
  error_map_.emplace(std::make_pair(GF_ROLLBACK_EXCEPTION, rollbackException));
  error_map_.emplace(
      std::make_pair(GF_COMMIT_CONFLICT_EXCEPTION, commitConflictException));
  error_map_.emplace(std::make_pair(GF_TRANSACTION_DATA_REBALANCED_EXCEPTION,
                                    transactionDataRebalancedException));
  error_map_.emplace(
      std::make_pair(GF_TRANSACTION_DATA_NODE_HAS_DEPARTED_EXCEPTION,
                     transactionDataNodeHasDepartedException));
  error_map_.emplace(std::make_pair(GF_PUTALL_PARTIAL_RESULT_EXCEPTION,
                                    putAllPartialResultException));
  error_map_.emplace(std::make_pair(GF_NOERR, unknownException));
  error_map_.emplace(std::make_pair(GF_DEADLK, unknownException));
  error_map_.emplace(std::make_pair(GF_EACCES, unknownException));
  error_map_.emplace(std::make_pair(GF_ECONFL, unknownException));
  error_map_.emplace(std::make_pair(GF_EINVAL, unknownException));
  error_map_.emplace(std::make_pair(GF_ETYPE, unknownException));
  error_map_.emplace(std::make_pair(GF_NOTOBJ, unknownException));
  error_map_.emplace(std::make_pair(GF_NOTSUP, unknownException));
  error_map_.emplace(std::make_pair(GF_SCPGBL, unknownException));
  error_map_.emplace(std::make_pair(GF_SCPEXC, unknownException));
  error_map_.emplace(std::make_pair(GF_OVRFLW, unknownException));
  error_map_.emplace(std::make_pair(GF_EINTR, unknownException));
  error_map_.emplace(std::make_pair(GF_NOSERVER_FOUND, unknownException));
  error_map_.emplace(std::make_pair(GF_SERVER_FAILED, unknownException));
  error_map_.emplace(std::make_pair(GF_CLIENT_WAIT_TIMEOUT_REFRESH_PRMETADATA,
                                    unknownException));
  error_map_.emplace(
      std::make_pair(GF_CANNOT_PROCESS_GII_REQUEST, unknownException));
  error_map_.emplace(std::make_pair(GF_CACHE_ENTRY_UPDATED, unknownException));
  error_map_.emplace(std::make_pair(GF_INVALID_DELTA, unknownException));
  error_map_.emplace(std::make_pair(GF_EUNDEF, unknownException));
}

[[noreturn]] void GfErrTypeThrowException(const char* str, GfErrType err) {
  std::string func;
  std::string message;
  auto exMsg = getThreadLocalExceptionMessage();
  setThreadLocalExceptionMessage("");
  if (!exMsg.empty()) {
    func.append(str);
    func.append(": ");
  }

  setErrorMap();
  auto iter = error_map_.find(err);
  if (iter != std::end(error_map_)) {
    iter->second(message, exMsg, err, func);
  }
  unknownException(message, exMsg, err, func);
}
}  // namespace client
}  // namespace geode
}  // namespace apache
