001 /*
002 * Copyright 2008-2015 UnboundID Corp.
003 * All Rights Reserved.
004 */
005 /*
006 * Copyright (C) 2015 UnboundID Corp.
007 *
008 * This program is free software; you can redistribute it and/or modify
009 * it under the terms of the GNU General Public License (GPLv2 only)
010 * or the terms of the GNU Lesser General Public License (LGPLv2.1 only)
011 * as published by the Free Software Foundation.
012 *
013 * This program is distributed in the hope that it will be useful,
014 * but WITHOUT ANY WARRANTY; without even the implied warranty of
015 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
016 * GNU General Public License for more details.
017 *
018 * You should have received a copy of the GNU General Public License
019 * along with this program; if not, see <http://www.gnu.org/licenses>.
020 */
021 package com.unboundid.ldap.sdk.unboundidds.monitors;
022
023
024
025 import java.util.Collections;
026 import java.util.List;
027 import java.util.LinkedHashMap;
028 import java.util.Map;
029
030 import com.unboundid.ldap.sdk.Entry;
031 import com.unboundid.util.DebugType;
032 import com.unboundid.util.NotMutable;
033 import com.unboundid.util.ThreadSafety;
034 import com.unboundid.util.ThreadSafetyLevel;
035
036 import static com.unboundid.ldap.sdk.unboundidds.monitors.MonitorMessages.*;
037 import static com.unboundid.util.Debug.*;
038
039
040
041 /**
042 * <BLOCKQUOTE>
043 * <B>NOTE:</B> This class is part of the Commercial Edition of the UnboundID
044 * LDAP SDK for Java. It is not available for use in applications that
045 * include only the Standard Edition of the LDAP SDK, and is not supported for
046 * use in conjunction with non-UnboundID products.
047 * </BLOCKQUOTE>
048 * This class defines a monitor entry that provides general information about a
049 * Directory Server backend. Information that may be available in a backend
050 * monitor entry includes:
051 * <UL>
052 * <LI>The backend ID for the backend.</LI>
053 * <LI>The set of base DNs for the backend.</LI>
054 * <LI>The total number of entries in the backend.</LI>
055 * <LI>The number of entries in the backend per base DN.</LI>
056 * <LI>The writability mode for the backend, which indicates whether it will
057 * accept write operations.</LI>
058 * <LI>An indication about whether the backend is public (intended to hold
059 * user data) or private (intended to hold operational data).</LI>
060 * </UL>
061 * The set of backend monitor entries published by the directory server can be
062 * obtained using the {@link MonitorManager#getBackendMonitorEntries} method.
063 * Specific methods are available for accessing the associated monitor data
064 * (e.g., {@link BackendMonitorEntry#getBackendID} to retrieve the backend ID),
065 * and there are also methods for accessing this information in a generic manner
066 * (e.g., {@link BackendMonitorEntry#getMonitorAttributes} to retrieve all of
067 * the monitor attributes). See the {@link MonitorManager} class documentation
068 * for an example that demonstrates the use of the generic API for accessing
069 * monitor data.
070 */
071 @NotMutable()
072 @ThreadSafety(level=ThreadSafetyLevel.COMPLETELY_THREADSAFE)
073 public final class BackendMonitorEntry
074 extends MonitorEntry
075 {
076 /**
077 * The structural object class used in backend monitor entries.
078 */
079 static final String BACKEND_MONITOR_OC = "ds-backend-monitor-entry";
080
081
082
083 /**
084 * The name of the attribute that contains the backend ID.
085 */
086 private static final String ATTR_BACKEND_ID = "ds-backend-id";
087
088
089
090 /**
091 * The name of the attribute that specifies the base DN(s) for the backend.
092 */
093 private static final String ATTR_BASE_DN = "ds-backend-base-dn";
094
095
096
097 /**
098 * The name of the attribute that specifies the number of entries per base DN
099 * in the backend.
100 */
101 private static final String ATTR_ENTRIES_PER_BASE_DN =
102 "ds-base-dn-entry-count";
103
104
105
106 /**
107 * The name of the attribute that indicates whether the backend is a private
108 * backend.
109 */
110 private static final String ATTR_IS_PRIVATE = "ds-backend-is-private";
111
112
113
114 /**
115 * The name of the attribute that holds the number of soft deletes processed
116 * since the backend was initialized.
117 */
118 private static final String ATTR_SOFT_DELETE_COUNT =
119 "ds-soft-delete-operations-count";
120
121
122
123 /**
124 * The name of the attribute that specifies the total number of entries in the
125 * backend.
126 */
127 private static final String ATTR_TOTAL_ENTRIES = "ds-backend-entry-count";
128
129
130
131 /**
132 * The name of the attribute that holds the number of undeletes processed
133 * since the backend was initialized.
134 */
135 private static final String ATTR_UNDELETE_COUNT =
136 "ds-undelete-operations-count";
137
138
139
140 /**
141 * The name of the attribute that specifies the writability mode for the
142 * backend.
143 */
144 private static final String ATTR_WRITABILITY_MODE =
145 "ds-backend-writability-mode";
146
147
148
149 /**
150 * The serial version UID for this serializable class.
151 */
152 private static final long serialVersionUID = -4256944695436807547L;
153
154
155
156 // Indicates whether the backend is a private backend.
157 private final Boolean isPrivate;
158
159 // The base DNs for the backend.
160 private final List<String> baseDNs;
161
162 // The number of soft delete operations processed since the backend was
163 // started.
164 private final Long softDeleteCount;
165
166 // The total number of entries in the backend.
167 private final Long totalEntries;
168
169 // The number of undelete operations processed since the backend was started.
170 private final Long undeleteCount;
171
172 // The number of entries per base DN in the backend.
173 private final Map<String,Long> entriesPerBaseDN;
174
175 // The backend ID for the backend.
176 private final String backendID;
177
178 // The writability mode for the backend.
179 private final String writabilityMode;
180
181
182
183 /**
184 * Creates a new backend monitor entry from the provided entry.
185 *
186 * @param entry The entry to be parsed as a backend monitor entry. It must
187 * not be {@code null}.
188 */
189 public BackendMonitorEntry(final Entry entry)
190 {
191 super(entry);
192
193 backendID = getString(ATTR_BACKEND_ID);
194 baseDNs = getStrings(ATTR_BASE_DN);
195 isPrivate = getBoolean(ATTR_IS_PRIVATE);
196 softDeleteCount = getLong(ATTR_SOFT_DELETE_COUNT);
197 totalEntries = getLong(ATTR_TOTAL_ENTRIES);
198 undeleteCount = getLong(ATTR_UNDELETE_COUNT);
199 writabilityMode = getString(ATTR_WRITABILITY_MODE);
200
201 final List<String> entriesPerBase = getStrings(ATTR_ENTRIES_PER_BASE_DN);
202 final LinkedHashMap<String,Long> countMap =
203 new LinkedHashMap<String,Long>(entriesPerBase.size());
204 for (final String s : entriesPerBase)
205 {
206 try
207 {
208 final int spacePos = s.indexOf(' ');
209 final Long l = Long.parseLong(s.substring(0, spacePos));
210 final String dn = s.substring(spacePos+1).trim();
211 countMap.put(dn, l);
212 }
213 catch (Exception e)
214 {
215 debugException(e);
216
217 if (debugEnabled(DebugType.MONITOR))
218 {
219 debugMonitor(entry,
220 "Cannot parse value '" + s + "' for attribute " +
221 ATTR_ENTRIES_PER_BASE_DN);
222 }
223 }
224 }
225
226 entriesPerBaseDN = Collections.unmodifiableMap(countMap);
227 }
228
229
230
231 /**
232 * Retrieves the backend ID for the associated backend.
233 *
234 * @return The backend ID for the associated backend, or {@code null} if it
235 * was not included in the monitor entry.
236 */
237 public String getBackendID()
238 {
239 return backendID;
240 }
241
242
243
244 /**
245 * Retrieves the base DNs for the associated backend.
246 *
247 * @return The base DNs for the associated backend, or an empty list if it
248 * was not included in the monitor entry.
249 */
250 public List<String> getBaseDNs()
251 {
252 return baseDNs;
253 }
254
255
256
257 /**
258 * Indicates whether the associated backend is a private backend.
259 *
260 * @return {@code Boolean.TRUE} if the backend is a private backend,
261 * {@code Boolean.FALSE} if it is not a private backend, or
262 * {@code null} if it was not included in the monitor entry.
263 */
264 public Boolean isPrivate()
265 {
266 return isPrivate;
267 }
268
269
270
271 /**
272 * Retrieves the writability mode for the associated backend.
273 *
274 * @return The writability mode for the associated backend, or {@code null}
275 * if it was not included in the monitor entry.
276 */
277 public String getWritabilityMode()
278 {
279 return writabilityMode;
280 }
281
282
283
284 /**
285 * Retrieves the total number of entries in the associated backend.
286 *
287 * @return The total number of entries in the associated backend, or
288 * {@code null} if it was not included in the monitor entry.
289 */
290 public Long getTotalEntries()
291 {
292 return totalEntries;
293 }
294
295
296
297 /**
298 * Retrieves a count of the number of entries per base DN in the associated
299 * backend.
300 *
301 * @return A count of the number of entries per base DN in the associated
302 * backend, or an empty map if it was not included in the monitor
303 * entry.
304 */
305 public Map<String,Long> getEntriesPerBaseDN()
306 {
307 return entriesPerBaseDN;
308 }
309
310
311
312 /**
313 * Retrieves the number of soft delete operations processed in the backend
314 * since the backend was started.
315 *
316 * @return The number of soft delete operations processed in the backend
317 * since the backend was started, or {@code null} if it was not
318 * included in the monitor entry.
319 */
320 public Long getSoftDeleteCount()
321 {
322 return softDeleteCount;
323 }
324
325
326
327 /**
328 * Retrieves the number of undelete operations processed in the backend since
329 * the backend was started.
330 *
331 * @return The number of undelete operations processed in the backend since
332 * the backend was started, or {@code null} if it was not included in
333 * the monitor entry.
334 */
335 public Long getUndeleteCount()
336 {
337 return undeleteCount;
338 }
339
340
341
342 /**
343 * {@inheritDoc}
344 */
345 @Override()
346 public String getMonitorDisplayName()
347 {
348 return INFO_BACKEND_MONITOR_DISPNAME.get();
349 }
350
351
352
353 /**
354 * {@inheritDoc}
355 */
356 @Override()
357 public String getMonitorDescription()
358 {
359 return INFO_BACKEND_MONITOR_DESC.get();
360 }
361
362
363
364 /**
365 * {@inheritDoc}
366 */
367 @Override()
368 public Map<String,MonitorAttribute> getMonitorAttributes()
369 {
370 final LinkedHashMap<String,MonitorAttribute> attrs =
371 new LinkedHashMap<String,MonitorAttribute>();
372
373 if (backendID != null)
374 {
375 addMonitorAttribute(attrs,
376 ATTR_BACKEND_ID,
377 INFO_BACKEND_DISPNAME_BACKEND_ID.get(),
378 INFO_BACKEND_DESC_BACKEND_ID.get(),
379 backendID);
380 }
381
382 if (! baseDNs.isEmpty())
383 {
384 addMonitorAttribute(attrs,
385 ATTR_BASE_DN,
386 INFO_BACKEND_DISPNAME_BASE_DN.get(),
387 INFO_BACKEND_DESC_BASE_DN.get(),
388 baseDNs);
389 }
390
391 if (totalEntries != null)
392 {
393 addMonitorAttribute(attrs,
394 ATTR_TOTAL_ENTRIES,
395 INFO_BACKEND_DISPNAME_TOTAL_ENTRIES.get(),
396 INFO_BACKEND_DESC_TOTAL_ENTRIES.get(),
397 totalEntries);
398 }
399
400 for (final String baseDN : entriesPerBaseDN.keySet())
401 {
402 final Long count = entriesPerBaseDN.get(baseDN);
403 addMonitorAttribute(attrs,
404 ATTR_ENTRIES_PER_BASE_DN + '-' + baseDN,
405 INFO_BACKEND_DISPNAME_ENTRY_COUNT.get(baseDN),
406 INFO_BACKEND_DESC_ENTRY_COUNT.get(baseDN),
407 count);
408
409 }
410
411 if (softDeleteCount != null)
412 {
413 addMonitorAttribute(attrs,
414 ATTR_SOFT_DELETE_COUNT,
415 INFO_BACKEND_DISPNAME_SOFT_DELETE_COUNT.get(),
416 INFO_BACKEND_DESC_SOFT_DELETE_COUNT.get(),
417 softDeleteCount);
418 }
419
420 if (undeleteCount != null)
421 {
422 addMonitorAttribute(attrs,
423 ATTR_UNDELETE_COUNT,
424 INFO_BACKEND_DISPNAME_UNDELETE_COUNT.get(),
425 INFO_BACKEND_DESC_UNDELETE_COUNT.get(),
426 undeleteCount);
427 }
428
429 if (writabilityMode != null)
430 {
431 addMonitorAttribute(attrs,
432 ATTR_WRITABILITY_MODE,
433 INFO_BACKEND_DISPNAME_WRITABILITY_MODE.get(),
434 INFO_BACKEND_DESC_WRITABILITY_MODE.get(),
435 writabilityMode);
436 }
437
438 if (isPrivate != null)
439 {
440 addMonitorAttribute(attrs,
441 ATTR_IS_PRIVATE,
442 INFO_BACKEND_DISPNAME_IS_PRIVATE.get(),
443 INFO_BACKEND_DESC_IS_PRIVATE.get(),
444 isPrivate);
445 }
446
447 return Collections.unmodifiableMap(attrs);
448 }
449 }