hadoop BoundedAppender 源码

  • 2022-10-20
  • 浏览 (205)

haddop BoundedAppender 代码

文件路径:/hadoop-yarn-project/hadoop-yarn/hadoop-yarn-common/src/main/java/org/apache/hadoop/yarn/util/BoundedAppender.java

/**
 * 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.
 */

package org.apache.hadoop.yarn.util;

import org.apache.hadoop.classification.VisibleForTesting;
import org.apache.hadoop.util.Preconditions;
import org.apache.hadoop.classification.InterfaceAudience;
import org.apache.hadoop.classification.InterfaceStability;

/**
 * A {@link CharSequence} appender that considers its {@link #limit} as upper
 * bound.
 * <p>
 * When {@link #limit} would be reached on append, past messages will be
 * truncated from head, and a header telling the user about truncation will be
 * prepended, with ellipses in between header and messages.
 * <p>
 * Note that header and ellipses are not counted against {@link #limit}.
 * <p>
 * An example:
 *
 * <pre>
 * {@code
 *   // At the beginning it's an empty string
 *   final Appendable shortAppender = new BoundedAppender(80);
 *   // The whole message fits into limit
 *   shortAppender.append(
 *       "message1 this is a very long message but fitting into limit\n");
 *   // The first message is truncated, the second not
 *   shortAppender.append("message2 this is shorter than the previous one\n");
 *   // The first message is deleted, the second truncated, the third
 *   // preserved
 *   shortAppender.append("message3 this is even shorter message, maybe.\n");
 *   // The first two are deleted, the third one truncated, the last preserved
 *   shortAppender.append("message4 the shortest one, yet the greatest :)");
 *   // Current contents are like this:
 *   // Diagnostic messages truncated, showing last 80 chars out of 199:
 *   // ...s is even shorter message, maybe.
 *   // message4 the shortest one, yet the greatest :)
 * }
 * </pre>
 * <p>
 * Note that <tt>null</tt> values are {@link #append(CharSequence) append}ed
 * just like in {@link StringBuilder#append(CharSequence) original
 * implementation}.
 * <p>
 * Note that this class is not thread safe.
 */

@InterfaceAudience.Public
@InterfaceStability.Unstable
@VisibleForTesting
public class BoundedAppender {
  @VisibleForTesting
  public static final String TRUNCATED_MESSAGES_TEMPLATE =
      "Diagnostic messages truncated, showing last "
          + "%d chars out of %d:%n...%s";

  private final int limit;
  private final StringBuilder messages = new StringBuilder();
  private int totalCharacterCount = 0;

  public BoundedAppender(final int limit) {
    Preconditions.checkArgument(limit > 0, "limit should be positive");

    this.limit = limit;
  }

  /**
   * Append a {@link CharSequence} considering {@link #limit}, truncating
   * from the head of {@code csq} or {@link #messages} when necessary.
   *
   * @param csq the {@link CharSequence} to append
   * @return this
   */
  public BoundedAppender append(final CharSequence csq) {
    appendAndCount(csq);
    checkAndCut();

    return this;
  }

  private void appendAndCount(final CharSequence csq) {
    final int before = messages.length();
    messages.append(csq);
    final int after = messages.length();
    totalCharacterCount += after - before;
  }

  private void checkAndCut() {
    if (messages.length() > limit) {
      final int newStart = messages.length() - limit;
      messages.delete(0, newStart);
    }
  }

  /**
   * Get current length of messages considering truncates
   * without header and ellipses.
   *
   * @return current length
   */
  public int length() {
    return messages.length();
  }

  public int getLimit() {
    return limit;
  }

  /**
   * Get a string representation of the actual contents, displaying also a
   * header and ellipses when there was a truncate.
   *
   * @return String representation of the {@link #messages}
   */
  @Override
  public String toString() {
    if (messages.length() < totalCharacterCount) {
      return String.format(TRUNCATED_MESSAGES_TEMPLATE, messages.length(),
          totalCharacterCount, messages.toString());
    }

    return messages.toString();
  }
}

相关信息

hadoop 源码目录

相关文章

hadoop AbstractLivelinessMonitor 源码

hadoop AdHocLogDumper 源码

hadoop ApplicationClassLoader 源码

hadoop Apps 源码

hadoop AsyncCallback 源码

hadoop AuxiliaryServiceHelper 源码

hadoop Clock 源码

hadoop ConverterUtils 源码

hadoop DockerClientConfigHandler 源码

hadoop FSDownload 源码

0  赞