private function serializeHierarchy($values) {
    if ($this->isDeserializedNode($values)) {
      // the values represent a node
      $values = $this->serializeNode($values);
    }
    else {
      if (is_array($values) || ($values instanceof \Traversable)) {
        foreach ($values as $key => $value) {
          if ($value != null && !is_scalar($value)) {
            // array/object value
            $result = $this->serializeHierarchy($value);
            if (ObjectId::isValid($key)) {
              $values = $result;
            }
            else {
              $values[$key] = $result;
            }
          }
          else {
            // string value
            $values[$key] = $value;
          }
        }
      }
    }
    return $values;
  }