001/*
002 * The contents of this file are subject to the terms of the Common Development and
003 * Distribution License (the License). You may not use this file except in compliance with the
004 * License.
005 *
006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
007 * specific language governing permission and limitations under the License.
008 *
009 * When distributing Covered Software, include this CDDL Header Notice in each file and include
010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
011 * Header, with the fields enclosed by brackets [] replaced by your own identifying
012 * information: "Portions Copyright [year] [name of copyright owner]".
013 *
014 * Portions Copyright 2011-2015 ForgeRock AS.
015 */
016package org.opends.server.types;
017
018import org.forgerock.util.Reject;
019
020
021
022/**
023 * An additional log item for an operation which may be processed in the access
024 * log.
025 * <p>
026 * Log items comprise of a source class, a key, and an optional value. If no
027 * value is present then only the key will be displayed in the log, otherwise
028 * both the key and value will usually be displayed using the format
029 * {@code key=value}. Log item values are {@code Object} instances whose string
030 * representation will be derived using the object's {@code toString()} method.
031 * <p>
032 * Log implementations may use the source class and/or key in order to filter
033 * out unwanted log items.
034 */
035public final class AdditionalLogItem
036{
037  /**
038   * Creates a new additional log item using the provided source and key, but no
039   * value.
040   *
041   * @param source
042   *          The class which generated the additional log item.
043   * @param key
044   *          The log item key.
045   * @return The new additional log item.
046   */
047  public static AdditionalLogItem keyOnly(final Class<?> source,
048      final String key)
049  {
050    Reject.ifNull(source, key);
051    return new AdditionalLogItem(source, key, null, false);
052  }
053
054
055
056  /**
057   * Creates a new additional log item using the provided source, key, and
058   * value. The value will be surrounded by quotes when serialized as a string.
059   *
060   * @param source
061   *          The class which generated the additional log item.
062   * @param key
063   *          The log item key.
064   * @param value
065   *          The log item value.
066   * @return The new additional log item.
067   */
068  public static AdditionalLogItem quotedKeyValue(final Class<?> source,
069      final String key, final Object value)
070  {
071    Reject.ifNull(source, key, value);
072    return new AdditionalLogItem(source, key, value, true);
073  }
074
075
076
077  /**
078   * Creates a new additional log item using the provided source, key, and
079   * value. The value will not be surrounded by quotes when serialized as a
080   * string.
081   *
082   * @param source
083   *          The class which generated the additional log item.
084   * @param key
085   *          The log item key.
086   * @param value
087   *          The log item value.
088   * @return The new additional log item.
089   */
090  public static AdditionalLogItem unquotedKeyValue(final Class<?> source,
091      final String key, final Object value)
092  {
093    Reject.ifNull(source, key, value);
094    return new AdditionalLogItem(source, key, value, false);
095  }
096
097
098
099  private final Class<?> source;
100
101  private final String key;
102
103  private final Object value;
104
105  private final boolean isQuoted;
106
107
108
109  /**
110   * Creates a new additional log item.
111   *
112   * @param source
113   *          The class which generated the additional log item.
114   * @param key
115   *          The log item key.
116   * @param value
117   *          The log item value.
118   * @param isQuoted
119   *          {@code true} if this item's value should be surrounded by quotes
120   *          during serialization.
121   */
122  private AdditionalLogItem(final Class<?> source, final String key,
123      final Object value, final boolean isQuoted)
124  {
125    this.source = source;
126    this.key = key;
127    this.value = value;
128    this.isQuoted = isQuoted;
129  }
130
131
132
133  /**
134   * Returns the log item key.
135   *
136   * @return The log item key.
137   */
138  public String getKey()
139  {
140    return key;
141  }
142
143
144
145  /**
146   * Returns the class which generated the additional log item.
147   *
148   * @return The class which generated the additional log item.
149   */
150  public Class<?> getSource()
151  {
152    return source;
153  }
154
155
156
157  /**
158   * Returns the log item value, or {@code null} if this log item does not have
159   * a value.
160   *
161   * @return The log item value, or {@code null} if this log item does not have
162   *         a value.
163   */
164  public Object getValue()
165  {
166    return value;
167  }
168
169
170
171  /**
172   * Returns {@code true} if this item's value should be surrounded by quotes
173   * during serialization.
174   *
175   * @return {@code true} if this item's value should be surrounded by quotes
176   *         during serialization.
177   */
178  public boolean isQuoted()
179  {
180    return isQuoted;
181  }
182
183
184
185  /** {@inheritDoc} */
186  @Override
187  public String toString()
188  {
189    if (value == null)
190    {
191      return key;
192    }
193    final StringBuilder builder = new StringBuilder(key.length() + 16);
194    toString(builder);
195    return builder.toString();
196  }
197
198
199
200  /**
201   * Appends the string representation of this additional log item to the
202   * provided string builder.
203   *
204   * @param builder
205   *          The string builder.
206   * @return A reference to the updated string builder.
207   */
208  public StringBuilder toString(final StringBuilder builder)
209  {
210    builder.append(key);
211    if (value != null)
212    {
213      builder.append('=');
214      if (isQuoted)
215      {
216        builder.append('\'');
217      }
218      builder.append(value);
219      if (isQuoted)
220      {
221        builder.append('\'');
222      }
223    }
224    return builder;
225  }
226
227}