001/*
002 * Copyright 2009-2024 Ping Identity Corporation
003 * All Rights Reserved.
004 */
005/*
006 * Copyright 2009-2024 Ping Identity Corporation
007 *
008 * Licensed under the Apache License, Version 2.0 (the "License");
009 * you may not use this file except in compliance with the License.
010 * You may obtain a copy of the License at
011 *
012 *    http://www.apache.org/licenses/LICENSE-2.0
013 *
014 * Unless required by applicable law or agreed to in writing, software
015 * distributed under the License is distributed on an "AS IS" BASIS,
016 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
017 * See the License for the specific language governing permissions and
018 * limitations under the License.
019 */
020/*
021 * Copyright (C) 2009-2024 Ping Identity Corporation
022 *
023 * This program is free software; you can redistribute it and/or modify
024 * it under the terms of the GNU General Public License (GPLv2 only)
025 * or the terms of the GNU Lesser General Public License (LGPLv2.1 only)
026 * as published by the Free Software Foundation.
027 *
028 * This program is distributed in the hope that it will be useful,
029 * but WITHOUT ANY WARRANTY; without even the implied warranty of
030 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
031 * GNU General Public License for more details.
032 *
033 * You should have received a copy of the GNU General Public License
034 * along with this program; if not, see <http://www.gnu.org/licenses>.
035 */
036package com.unboundid.ldap.sdk.unboundidds.monitors;
037
038
039
040import java.util.ArrayList;
041import java.util.Collections;
042import java.util.LinkedHashMap;
043import java.util.List;
044import java.util.Map;
045
046import com.unboundid.ldap.sdk.Entry;
047import com.unboundid.util.Debug;
048import com.unboundid.util.NotMutable;
049import com.unboundid.util.NotNull;
050import com.unboundid.util.Nullable;
051import com.unboundid.util.StaticUtils;
052import com.unboundid.util.ThreadSafety;
053import com.unboundid.util.ThreadSafetyLevel;
054
055import static com.unboundid.ldap.sdk.unboundidds.monitors.MonitorMessages.*;
056
057
058
059/**
060 * This class defines a monitor entry that provides information about a
061 * load-balancing algorithm used by the Directory Proxy Server.
062 * <BR>
063 * <BLOCKQUOTE>
064 *   <B>NOTE:</B>  This class, and other classes within the
065 *   {@code com.unboundid.ldap.sdk.unboundidds} package structure, are only
066 *   supported for use against Ping Identity, UnboundID, and
067 *   Nokia/Alcatel-Lucent 8661 server products.  These classes provide support
068 *   for proprietary functionality or for external specifications that are not
069 *   considered stable or mature enough to be guaranteed to work in an
070 *   interoperable way with other types of LDAP servers.
071 * </BLOCKQUOTE>
072 * <BR>
073 * Information that it may make available includes:
074 * <UL>
075 *   <LI>The aggregate health check state for servers associated with the
076 *       load-balancing algorithm.</LI>
077 *   <LI>Information about each server associated with the load-balancing
078 *       algorithm, including the address, port, and health check state for the
079 *       server.</LI>
080 *   <LI>The number of available, degraded, and unavailable servers associated
081 *       with the load-balancing algorithm.</LI>
082 * </UL>
083 * The server should present a load-balancing algorithm monitor entry for each
084 * load-balancing algorithm used by a proxying request processor.  These entries
085 * can be retrieved using the
086 * {@link MonitorManager#getLoadBalancingAlgorithmMonitorEntries} method.  These
087 * entries provide specific methods for accessing this information.
088 * Alternately, the information may be accessed using the generic API.  See the
089 * {@link MonitorManager} class documentation for an example that demonstrates
090 * the use of the generic API for accessing monitor data.
091 */
092@NotMutable()
093@ThreadSafety(level=ThreadSafetyLevel.COMPLETELY_THREADSAFE)
094public final class LoadBalancingAlgorithmMonitorEntry
095       extends MonitorEntry
096{
097  /**
098   * The structural object class used in LDAP external server monitor entries.
099   */
100  @NotNull protected static final String LOAD_BALANCING_ALGORITHM_MONITOR_OC =
101       "ds-load-balancing-algorithm-monitor-entry";
102
103
104
105  /**
106   * The name of the attribute used to provide the name of the load-balancing
107   * algorithm.
108   */
109  @NotNull private static final String ATTR_ALGORITHM_NAME = "algorithm-name";
110
111
112
113  /**
114   * The name of the attribute used to provide the DN of the configuration entry
115   * for the load-balancing algorithm.
116   */
117  @NotNull private static final String ATTR_CONFIG_ENTRY_DN = "config-entry-dn";
118
119
120
121  /**
122   * The name of the attribute used to provide the aggregate health check state
123   * for the load-balancing algorithm.
124   */
125  @NotNull private static final String ATTR_HEALTH_CHECK_STATE =
126       "health-check-state";
127
128
129
130  /**
131   * The name of the attribute used to provide information about the health
132   * check states of each of the LDAP external servers associated with the
133   * load-balancing algorithm.
134   */
135  @NotNull private static final String ATTR_LDAP_EXTERNAL_SERVER =
136       "ldap-external-server";
137
138
139
140  /**
141   * The name of the attribute used to provide the aggregate health check state
142   * for local servers for the load-balancing algorithm.
143   */
144  @NotNull private static final String ATTR_LOCAL_SERVERS_HEALTH_CHECK_STATE =
145       "local-servers-health-check-state";
146
147
148
149  /**
150   * The name of the attribute used to provide the aggregate health check state
151   * for non-local servers for the load-balancing algorithm.
152   */
153  @NotNull private static final String
154       ATTR_NON_LOCAL_SERVERS_HEALTH_CHECK_STATE =
155            "non-local-servers-health-check-state";
156
157
158
159  /**
160   * The name of the attribute used to provide the number of servers associated
161   * with the load-balancing algorithm with a health check state of AVAILABLE.
162   */
163  @NotNull private static final String ATTR_NUM_AVAILABLE =
164       "num-available-servers";
165
166
167
168  /**
169   * The name of the attribute used to provide the number of servers associated
170   * with the load-balancing algorithm with a health check state of DEGRADED.
171   */
172  @NotNull private static final String ATTR_NUM_DEGRADED =
173       "num-degraded-servers";
174
175
176
177  /**
178   * The name of the attribute used to provide the number of servers associated
179   * with the load-balancing algorithm with a health check state of UNAVAILABLE.
180   */
181  @NotNull private static final String ATTR_NUM_UNAVAILABLE =
182       "num-unavailable-servers";
183
184
185
186  /**
187   * The serial version UID for this serializable class.
188   */
189  private static final long serialVersionUID = -5251924301718025205L;
190
191
192
193  // The aggregate health check state for the load-balancing algorithm.
194  @Nullable private final HealthCheckState healthCheckState;
195
196  // The aggregate health check state for local servers for the load-balancing
197  // algorithm.
198  @Nullable private final HealthCheckState localServersHealthCheckState;
199
200  // The aggregate health check state for non-local servers for the
201  // load-balancing algorithm.
202  @Nullable private final HealthCheckState nonLocalServersHealthCheckState;
203
204  // The list of server availability objects.
205  @NotNull private final List<LoadBalancingAlgorithmServerAvailabilityData>
206       serverAvailabilityData;
207
208  // The number of servers with a health check state of AVAILABLE.
209  @Nullable private final Long numAvailableServers;
210
211  // The number of servers with a health check state of DEGRADED.
212  @Nullable private final Long numDegradedServers;
213
214  // The number of servers with a health check state of UNAVAILABLE.
215  @Nullable private final Long numUnavailableServers;
216
217  // The name of the load-balancing algorithm.
218  @Nullable private final String algorithmName;
219
220  // The DN of the configuration entry for the load-balancing algorithm.
221  @Nullable private final String configEntryDN;
222
223
224
225  /**
226   * Creates a new load-balancing algorithm monitor entry from the provided
227   * entry.
228   *
229   * @param  entry  The entry to be parsed as a load-balancing algorithm monitor
230   *                entry.  It must not be {@code null}.
231   */
232  public LoadBalancingAlgorithmMonitorEntry(@NotNull final Entry entry)
233  {
234    super(entry);
235
236    algorithmName = getString(ATTR_ALGORITHM_NAME);
237    configEntryDN = getString(ATTR_CONFIG_ENTRY_DN);
238    numAvailableServers = getLong(ATTR_NUM_AVAILABLE);
239    numDegradedServers = getLong(ATTR_NUM_DEGRADED);
240    numUnavailableServers = getLong(ATTR_NUM_UNAVAILABLE);
241
242    final String hcStateStr = getString(ATTR_HEALTH_CHECK_STATE);
243    if (hcStateStr == null)
244    {
245      healthCheckState = null;
246    }
247    else
248    {
249      healthCheckState = HealthCheckState.forName(hcStateStr);
250    }
251
252    final String localHCStateStr =
253         getString(ATTR_LOCAL_SERVERS_HEALTH_CHECK_STATE);
254    if (localHCStateStr == null)
255    {
256      localServersHealthCheckState = null;
257    }
258    else
259    {
260      localServersHealthCheckState = HealthCheckState.forName(localHCStateStr);
261    }
262
263    final String nonLocalHCStateStr =
264         getString(ATTR_NON_LOCAL_SERVERS_HEALTH_CHECK_STATE);
265    if (nonLocalHCStateStr == null)
266    {
267      nonLocalServersHealthCheckState = null;
268    }
269    else
270    {
271      nonLocalServersHealthCheckState =
272           HealthCheckState.forName(nonLocalHCStateStr);
273    }
274
275    final List<String> externalServerStrings =
276         getStrings(ATTR_LDAP_EXTERNAL_SERVER);
277    final ArrayList<LoadBalancingAlgorithmServerAvailabilityData> serverData =
278         new ArrayList<>(externalServerStrings.size());
279    for (final String s : externalServerStrings)
280    {
281      try
282      {
283        serverData.add(new LoadBalancingAlgorithmServerAvailabilityData(s));
284      }
285      catch (final Exception e)
286      {
287        Debug.debugException(e);
288      }
289    }
290    serverAvailabilityData = Collections.unmodifiableList(serverData);
291  }
292
293
294
295  /**
296   * Retrieves the name of the load-balancing algorithm.
297   *
298   * @return  The name of the load-balancing algorithm, or {@code null} if it
299   *          was not included in the monitor entry.
300   */
301  @Nullable()
302  public String getAlgorithmName()
303  {
304    return algorithmName;
305  }
306
307
308
309  /**
310   * Retrieves the DN of the configuration entry for the load-balancing
311   * algorithm.
312   *
313   * @return  The DN of the configuration entry for the load-balancing
314   *          algorithm, or {@code null} if it was not included in the monitor
315   *          entry.
316   */
317  @Nullable()
318  public String getConfigEntryDN()
319  {
320    return configEntryDN;
321  }
322
323
324
325  /**
326   * Retrieves the aggregate health check state for the load-balancing
327   * algorithm.
328   *
329   * @return  The aggregate health check state for the load-balancing algorithm,
330   *          or {@code null} if it was not included in the monitor
331   *          entry.
332   */
333  @Nullable()
334  public HealthCheckState getHealthCheckState()
335  {
336    return healthCheckState;
337  }
338
339
340
341  /**
342   * Retrieves the aggregate health check state for local servers for the
343   * load-balancing algorithm.
344   *
345   * @return  The aggregate health check state for local servers for the
346   *          load-balancing algorithm, or {@code null} if it was not included
347   *          in the monitor entry.
348   */
349  @Nullable()
350  public HealthCheckState getLocalServersHealthCheckState()
351  {
352    return localServersHealthCheckState;
353  }
354
355
356
357  /**
358   * Retrieves the aggregate health check state for non-local servers for the
359   * load-balancing algorithm.
360   *
361   * @return  The aggregate health check state for non-local servers for the
362   *          load-balancing algorithm, or {@code null} if it was not included
363   *          in the monitor entry.
364   */
365  @Nullable()
366  public HealthCheckState getNonLocalServersHealthCheckState()
367  {
368    return nonLocalServersHealthCheckState;
369  }
370
371
372
373  /**
374   * Retrieves a list with information about the healths of the individual LDAP
375   * external servers associated with the load-balancing algorithm.
376   *
377   * @return  A list with information about the healths of the individual LDAP
378   *          external servers associated with the load-balancing algorithm, or
379   *          an empty list if it was not included in the monitor entry.
380   */
381  @NotNull()
382  public List<LoadBalancingAlgorithmServerAvailabilityData>
383              getServerAvailabilityData()
384  {
385    return serverAvailabilityData;
386  }
387
388
389
390  /**
391   * Retrieves the number of servers associated with the load-balancing
392   * algorithm that have a health check state of AVAILABLE.
393   *
394   * @return  The number of servers associated with the load-balancing algorithm
395   *          that have a health check state of AVAILABLE, or {@code null} if it
396   *          was not included in the monitor entry.
397   */
398  @Nullable()
399  public Long getNumAvailableServers()
400  {
401    return numAvailableServers;
402  }
403
404
405
406  /**
407   * Retrieves the number of servers associated with the load-balancing
408   * algorithm that have a health check state of DEGRADED.
409   *
410   * @return  The number of servers associated with the load-balancing algorithm
411   *          that have a health check state of DEGRADED, or {@code null} if it
412   *          was not included in the monitor entry.
413   */
414  @Nullable()
415  public Long getNumDegradedServers()
416  {
417    return numDegradedServers;
418  }
419
420
421
422  /**
423   * Retrieves the number of servers associated with the load-balancing
424   * algorithm that have a health check state of UNAVAILABLE.
425   *
426   * @return  The number of servers associated with the load-balancing algorithm
427   *          that have a health check state of UNAVAILABLE, or {@code null} if
428   *          it was not included in the monitor entry.
429   */
430  @Nullable()
431  public Long getNumUnavailableServers()
432  {
433    return numUnavailableServers;
434  }
435
436
437
438  /**
439   * {@inheritDoc}
440   */
441  @Override()
442  @NotNull()
443  public String getMonitorDisplayName()
444  {
445    return INFO_LOAD_BALANCING_ALGORITHM_MONITOR_DISPNAME.get();
446  }
447
448
449
450  /**
451   * {@inheritDoc}
452   */
453  @Override()
454  @NotNull()
455  public String getMonitorDescription()
456  {
457    return INFO_LOAD_BALANCING_ALGORITHM_MONITOR_DESC.get();
458  }
459
460
461
462  /**
463   * {@inheritDoc}
464   */
465  @Override()
466  @NotNull()
467  public Map<String,MonitorAttribute> getMonitorAttributes()
468  {
469    final LinkedHashMap<String,MonitorAttribute> attrs =
470         new LinkedHashMap<>(StaticUtils.computeMapCapacity(9));
471
472    if (algorithmName != null)
473    {
474      addMonitorAttribute(attrs,
475           ATTR_ALGORITHM_NAME,
476           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_ALGORITHM_NAME.get(),
477           INFO_LOAD_BALANCING_ALGORITHM_DESC_ALGORITHM_NAME.get(),
478           algorithmName);
479    }
480
481    if (configEntryDN != null)
482    {
483      addMonitorAttribute(attrs,
484           ATTR_CONFIG_ENTRY_DN,
485           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_CONFIG_ENTRY_DN.get(),
486           INFO_LOAD_BALANCING_ALGORITHM_DESC_CONFIG_ENTRY_DN.get(),
487           configEntryDN);
488    }
489
490    if (healthCheckState != null)
491    {
492      addMonitorAttribute(attrs,
493           ATTR_HEALTH_CHECK_STATE,
494           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_HEALTH_CHECK_STATE.get(),
495           INFO_LOAD_BALANCING_ALGORITHM_DESC_HEALTH_CHECK_STATE.get(),
496           healthCheckState.name());
497    }
498
499    if (localServersHealthCheckState != null)
500    {
501      addMonitorAttribute(attrs,
502           ATTR_LOCAL_SERVERS_HEALTH_CHECK_STATE,
503           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_L_HEALTH_CHECK_STATE.get(),
504           INFO_LOAD_BALANCING_ALGORITHM_DESC_L_HEALTH_CHECK_STATE.get(),
505           localServersHealthCheckState.name());
506    }
507
508    if (nonLocalServersHealthCheckState != null)
509    {
510      addMonitorAttribute(attrs,
511           ATTR_NON_LOCAL_SERVERS_HEALTH_CHECK_STATE,
512           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_NL_HEALTH_CHECK_STATE.get(),
513           INFO_LOAD_BALANCING_ALGORITHM_DESC_NL_HEALTH_CHECK_STATE.get(),
514           nonLocalServersHealthCheckState.name());
515    }
516
517    if ((serverAvailabilityData != null) &&
518        (! serverAvailabilityData.isEmpty()))
519    {
520      final ArrayList<String> availabilityStrings =
521           new ArrayList<>(serverAvailabilityData.size());
522      for (final LoadBalancingAlgorithmServerAvailabilityData d :
523           serverAvailabilityData)
524      {
525        availabilityStrings.add(d.toCompactString());
526      }
527      addMonitorAttribute(attrs,
528           ATTR_LDAP_EXTERNAL_SERVER,
529           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_SERVER_DATA.get(),
530           INFO_LOAD_BALANCING_ALGORITHM_DESC_SERVER_DATA.get(),
531           availabilityStrings);
532    }
533
534    if (numAvailableServers != null)
535    {
536      addMonitorAttribute(attrs,
537           ATTR_NUM_AVAILABLE,
538           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_NUM_AVAILABLE.get(),
539           INFO_LOAD_BALANCING_ALGORITHM_DESC_NUM_AVAILABLE.get(),
540           numAvailableServers);
541    }
542
543    if (numDegradedServers != null)
544    {
545      addMonitorAttribute(attrs,
546           ATTR_NUM_DEGRADED,
547           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_NUM_DEGRADED.get(),
548           INFO_LOAD_BALANCING_ALGORITHM_DESC_NUM_DEGRADED.get(),
549           numDegradedServers);
550    }
551
552    if (numUnavailableServers != null)
553    {
554      addMonitorAttribute(attrs,
555           ATTR_NUM_UNAVAILABLE,
556           INFO_LOAD_BALANCING_ALGORITHM_DISPNAME_NUM_UNAVAILABLE.get(),
557           INFO_LOAD_BALANCING_ALGORITHM_DESC_NUM_UNAVAILABLE.get(),
558           numUnavailableServers);
559    }
560
561    return Collections.unmodifiableMap(attrs);
562  }
563}