public BinarySearchTreeNode<T> getSuccessorNode() {
    /**
     * Case 1: Node has right child
     * If a node X has a right child, then node X's successor node is the
     * minimum value of the right child node (i.e., you perform the minimum
     * operation on that right child). The result of performing the minimum
     * operation on the right child could either be the right child itself
     * (if the right child has no left child) or you trace all the way down
     * the left until you reach the leaf node (which would be the minimum).
     */
    if (rightChild != null) {
      return rightChild.getMinimumNode();
    }

    /**
     * If a node X has no right child, then node X's successor is found by
     * tracing back up the tree until you find a node that is a left child.
     * X's successor is the parent of that left child's. In other words,
     * if node X has no right child, you trace back up the tree until you
     * have the first opportunity to turn right and X's successor is the
     * first node after turning right as you traverse back up the graph. 
     */
    // Seed the operation by starting with the current node as a parent.
    BinarySearchTreeNode<T> parentNode = this;
    while (parentNode != null) {
      if (parentNode.parent != null &&
          parentNode.parent.leftChild == parentNode) {
        return parentNode.parent;
      }

      // Walk up the tree.
      parentNode = parentNode.parent;
    }
    return null; 
  }