code: public void notifyTaskAction(String action, Integer previousStatus, Integer previousState)
      throws ServiceException, DataAccessException {
          CodeTimer timer = new CodeTimer("TaskManager.notifyStatusChange()", true);
  
          try {
              // new-style notifiers
              String outcome = TaskStatuses.getTaskStatuses().get(taskInstance.getStatusCode());
              //if (!action.equals(TaskAction.CLAIM) && !action.equals(TaskAction.RELEASE))  // avoid nuisance notice to claimer and releaser
              sendNotification(action, outcome);
  
              // new-style auto-assign
              if (TaskStatus.STATUS_OPEN.intValue() == taskInstance.getStatusCode().intValue()
                      && !action.equals(TaskAction.RELEASE)) {
                  AutoAssignStrategy strategy = getAutoAssignStrategy();
                  if (strategy != null) {
                      User assignee = strategy.selectAssignee(taskInstance);
                      if (assignee == null)
                          logger.severe("No users found for auto-assignment of task instance ID: " + taskInstance.getTaskInstanceId());
                      else
                      {
                        taskInstance.setAssigneeId(assignee.getId());
                        taskInstance.setAssigneeCuid(assignee.getCuid());
                        performAction(TaskAction.ASSIGN, assignee.getId(), assignee.getId(), "Auto-assigned", null, false, false);
                      }
                  }
              }
          }
          catch (ObserverException ex) {
              // do not rethrow; observer problems should not prevent task actions
              logger.severeException(ex.getMessage(), ex);
          }
          catch (StrategyException ex) {
              logger.severeException(ex.getMessage(), ex);
          }
          timer.stopAndLogTiming("");
      }
docs: TODO: handle non-standard status changes