public static void process(
      ActionRequest actionRequest,
      ActionResponse actionResponse,
      Map<String, BaseAlloyControllerImpl> alloyControllers)
      throws Exception {

    String jsonString = null;

    String controller = ParamUtil.getString(actionRequest, "controller");

    BaseAlloyControllerImpl baseAlloyControllerImpl = alloyControllers.get(controller);

    if (baseAlloyControllerImpl == null) {
      throw new Exception("Unable to find controller " + controller);
    }

    String action = ParamUtil.getString(actionRequest, "action");

    try {
      if (action.equals("custom")) {
        Class<?> clazz = BaseAlloyControllerImpl.class;

        Method method =
            clazz.getDeclaredMethod("processDataRequest", new Class<?>[] {ActionRequest.class});

        jsonString =
            (String)
                ServiceBeanMethodInvocationFactoryUtil.proceed(
                    baseAlloyControllerImpl,
                    clazz,
                    method,
                    new Object[] {actionRequest},
                    new String[] {"transactionAdvice"});
      } else if (action.equals("dynamicQuery")) {
        jsonString = executeDynamicQuery(baseAlloyControllerImpl, actionRequest);
      } else if (action.equals("search")) {
        jsonString = executeSearch(baseAlloyControllerImpl, actionRequest);
      }
    } catch (Exception e) {
      JSONObject jsonObject = JSONFactoryUtil.createJSONObject();

      String message = e.getMessage();

      if (Validator.isNull(message)) {
        message = baseAlloyControllerImpl.translate("an-unexpected-error-occurred");
      }

      jsonObject.put("message", message);

      jsonObject.put("stacktrace", StackTraceUtil.getStackTrace(e));
      jsonObject.put("success", false);

      jsonString = jsonObject.toString();
    }

    if (jsonString != null) {
      writeJSON(actionRequest, actionResponse, jsonString);
    }
  }
  @Test
  public void testAddFileEntryWithInvalidMimeType() throws Exception {
    long folderId = parentFolder.getFolderId();
    String description = StringPool.BLANK;
    String changeLog = StringPool.BLANK;

    ServiceContext serviceContext = new ServiceContext();

    serviceContext.setAddGroupPermissions(true);
    serviceContext.setAddGuestPermissions(true);
    serviceContext.setScopeGroupId(group.getGroupId());

    try {
      String name = "InvalidMime.txt";
      byte[] bytes = CONTENT.getBytes();

      FileEntry fileEntry =
          DLAppServiceUtil.addFileEntry(
              group.getGroupId(),
              folderId,
              name,
              ContentTypes.APPLICATION_OCTET_STREAM,
              name,
              description,
              changeLog,
              bytes,
              serviceContext);

      Assert.assertEquals(ContentTypes.TEXT_PLAIN, fileEntry.getMimeType());

      name = "InvalidMime";

      fileEntry =
          DLAppServiceUtil.updateFileEntry(
              fileEntry.getFileEntryId(),
              name,
              null,
              name,
              description,
              changeLog,
              true,
              bytes,
              serviceContext);

      Assert.assertEquals(ContentTypes.TEXT_PLAIN, fileEntry.getMimeType());
    } catch (Exception e) {
      Assert.fail("Unable to add file with invalid mime type " + StackTraceUtil.getStackTrace(e));
    }
  }
  @Test
  public void testAddNullFileEntry() throws Exception {
    long folderId = parentFolder.getFolderId();
    String description = StringPool.BLANK;
    String changeLog = StringPool.BLANK;

    ServiceContext serviceContext = new ServiceContext();

    serviceContext.setAddGroupPermissions(true);
    serviceContext.setAddGuestPermissions(true);
    serviceContext.setScopeGroupId(group.getGroupId());

    try {
      String name = "Bytes-null.txt";
      byte[] bytes = null;

      FileEntry fileEntry =
          DLAppServiceUtil.addFileEntry(
              group.getGroupId(),
              folderId,
              name,
              ContentTypes.TEXT_PLAIN,
              name,
              description,
              changeLog,
              bytes,
              serviceContext);

      DLAppServiceUtil.updateFileEntry(
          fileEntry.getFileEntryId(),
          name,
          ContentTypes.TEXT_PLAIN,
          name,
          description,
          changeLog,
          true,
          bytes,
          serviceContext);

      String newName = "Bytes-changed.txt";

      bytes = CONTENT.getBytes();

      DLAppServiceUtil.updateFileEntry(
          fileEntry.getFileEntryId(),
          newName,
          ContentTypes.TEXT_PLAIN,
          newName,
          description,
          changeLog,
          true,
          bytes,
          serviceContext);
    } catch (Exception e) {
      Assert.fail("Unable to pass null byte[] " + StackTraceUtil.getStackTrace(e));
    }

    try {
      String name = "File-null.txt";
      File file = null;

      FileEntry fileEntry =
          DLAppServiceUtil.addFileEntry(
              group.getGroupId(),
              folderId,
              name,
              ContentTypes.TEXT_PLAIN,
              name,
              description,
              changeLog,
              file,
              serviceContext);

      DLAppServiceUtil.updateFileEntry(
          fileEntry.getFileEntryId(),
          name,
          ContentTypes.TEXT_PLAIN,
          name,
          description,
          changeLog,
          true,
          file,
          serviceContext);

      try {
        String newName = "File-changed.txt";

        file = FileUtil.createTempFile(CONTENT.getBytes());

        DLAppServiceUtil.updateFileEntry(
            fileEntry.getFileEntryId(),
            newName,
            ContentTypes.TEXT_PLAIN,
            newName,
            description,
            changeLog,
            true,
            file,
            serviceContext);
      } finally {
        FileUtil.delete(file);
      }
    } catch (Exception e) {
      Assert.fail("Unable to pass null File " + StackTraceUtil.getStackTrace(e));
    }

    try {
      String name = "IS-null.txt";
      InputStream is = null;

      FileEntry fileEntry =
          DLAppServiceUtil.addFileEntry(
              group.getGroupId(),
              folderId,
              name,
              ContentTypes.TEXT_PLAIN,
              name,
              description,
              changeLog,
              is,
              0,
              serviceContext);

      DLAppServiceUtil.updateFileEntry(
          fileEntry.getFileEntryId(),
          name,
          ContentTypes.TEXT_PLAIN,
          name,
          description,
          changeLog,
          true,
          is,
          0,
          serviceContext);

      try {
        String newName = "IS-changed.txt";

        is = new ByteArrayInputStream(CONTENT.getBytes());

        DLAppServiceUtil.updateFileEntry(
            fileEntry.getFileEntryId(),
            newName,
            ContentTypes.TEXT_PLAIN,
            newName,
            description,
            changeLog,
            true,
            is,
            0,
            serviceContext);
      } finally {
        if (is != null) {
          is.close();
        }
      }
    } catch (Exception e) {
      Assert.fail("Unable to pass null InputStream " + StackTraceUtil.getStackTrace(e));
    }
  }
  @Override
  protected void doReceive(Message message) throws Exception {
    long backgroundTaskId = (Long) message.get(BackgroundTaskConstants.BACKGROUND_TASK_ID);

    BackgroundTaskThreadLocal.setBackgroundTaskId(backgroundTaskId);

    ServiceContext serviceContext = new ServiceContext();

    BackgroundTask backgroundTask =
        _backgroundTaskManager.amendBackgroundTask(
            backgroundTaskId, null, BackgroundTaskConstants.STATUS_IN_PROGRESS, serviceContext);

    if (backgroundTask == null) {
      if (_log.isDebugEnabled()) {
        _log.debug("Unable to find background task " + backgroundTaskId);
      }

      return;
    }

    BackgroundTaskExecutor backgroundTaskExecutor = null;
    BackgroundTaskStatusMessageListener backgroundTaskStatusMessageListener = null;

    int status = backgroundTask.getStatus();
    String statusMessage = null;

    try {
      ClassLoader classLoader = getBackgroundTaskExecutorClassLoader(backgroundTask);

      backgroundTaskExecutor = wrapBackgroundTaskExecutor(backgroundTask, classLoader);

      _backgroundTaskStatusRegistry.registerBackgroundTaskStatus(backgroundTaskId);

      BackgroundTaskStatusMessageTranslator backgroundTaskStatusMessageTranslator =
          backgroundTaskExecutor.getBackgroundTaskStatusMessageTranslator();

      if (backgroundTaskStatusMessageTranslator != null) {
        backgroundTaskStatusMessageListener =
            new BackgroundTaskStatusMessageListener(
                backgroundTaskId,
                backgroundTaskStatusMessageTranslator,
                _backgroundTaskStatusRegistry);

        _messageBus.registerMessageListener(
            DestinationNames.BACKGROUND_TASK_STATUS, backgroundTaskStatusMessageListener);
      }

      backgroundTask =
          _backgroundTaskManager.fetchBackgroundTask(backgroundTask.getBackgroundTaskId());

      BackgroundTaskResult backgroundTaskResult = backgroundTaskExecutor.execute(backgroundTask);

      status = backgroundTaskResult.getStatus();
      statusMessage = backgroundTaskResult.getStatusMessage();
    } catch (DuplicateLockException dle) {
      status = BackgroundTaskConstants.STATUS_QUEUED;

      if (_log.isDebugEnabled()) {
        _log.debug("Unable to acquire lock, queuing background task " + backgroundTaskId);
      }
    } catch (Exception e) {
      status = BackgroundTaskConstants.STATUS_FAILED;

      if (e instanceof SystemException) {
        Throwable cause = e.getCause();

        if (cause instanceof Exception) {
          e = (Exception) cause;
        }
      }

      if (backgroundTaskExecutor != null) {
        statusMessage = backgroundTaskExecutor.handleException(backgroundTask, e);
      }

      if (_log.isInfoEnabled()) {
        if (statusMessage != null) {
          statusMessage = statusMessage.concat(StackTraceUtil.getStackTrace(e));
        } else {
          statusMessage = StackTraceUtil.getStackTrace(e);
        }
      }

      _log.error("Unable to execute background task", e);
    } finally {
      if (_log.isDebugEnabled()) {
        _log.debug("Completing background task " + backgroundTaskId + " with status: " + status);
      }

      _backgroundTaskManager.amendBackgroundTask(
          backgroundTaskId, null, status, statusMessage, serviceContext);

      _backgroundTaskStatusRegistry.unregisterBackgroundTaskStatus(backgroundTaskId);

      if (backgroundTaskStatusMessageListener != null) {
        _messageBus.unregisterMessageListener(
            DestinationNames.BACKGROUND_TASK_STATUS, backgroundTaskStatusMessageListener);
      }

      Message responseMessage = new Message();

      responseMessage.put(
          BackgroundTaskConstants.BACKGROUND_TASK_ID, backgroundTask.getBackgroundTaskId());
      responseMessage.put("name", backgroundTask.getName());
      responseMessage.put("status", status);
      responseMessage.put("taskExecutorClassName", backgroundTask.getTaskExecutorClassName());

      _messageBus.sendMessage(DestinationNames.BACKGROUND_TASK_STATUS, responseMessage);
    }
  }