001 /* 002 * Copyright 2009-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.logs; 022 023 024 025 import java.util.Collections; 026 import java.util.LinkedList; 027 import java.util.List; 028 import java.util.StringTokenizer; 029 030 import com.unboundid.ldap.sdk.ResultCode; 031 import com.unboundid.util.NotMutable; 032 import com.unboundid.util.ThreadSafety; 033 import com.unboundid.util.ThreadSafetyLevel; 034 035 036 037 /** 038 * <BLOCKQUOTE> 039 * <B>NOTE:</B> This class is part of the Commercial Edition of the UnboundID 040 * LDAP SDK for Java. It is not available for use in applications that 041 * include only the Standard Edition of the LDAP SDK, and is not supported for 042 * use in conjunction with non-UnboundID products. 043 * </BLOCKQUOTE> 044 * This class provides a data structure that holds information about a log 045 * message that may appear in the Directory Server access log about the result 046 * of an extended operation processed by the Directory Server. 047 */ 048 @NotMutable() 049 @ThreadSafety(level=ThreadSafetyLevel.COMPLETELY_THREADSAFE) 050 public final class ExtendedResultAccessLogMessage 051 extends ExtendedRequestAccessLogMessage 052 implements OperationResultAccessLogMessage 053 { 054 /** 055 * The serial version UID for this serializable class. 056 */ 057 private static final long serialVersionUID = -3980496377400403461L; 058 059 060 061 // Indicates whether the any uncached data was accessed in the course of 062 // processing this operation. 063 private final Boolean uncachedDataAccessed; 064 065 // The processing time for the operation. 066 private final Double processingTime; 067 068 // The queue time for the operation. 069 private final Double queueTime; 070 071 // The list of privileges required for processing the operation that the 072 // requester did not have. 073 private final List<String> missingPrivileges; 074 075 // The list of privileges used during the course of processing the operation 076 // before an alternate authorization identity was assigned. 077 private final List<String> preAuthZUsedPrivileges; 078 079 // The list of referral URLs for the operation. 080 private final List<String> referralURLs; 081 082 // The list of response control OIDs for the operation. 083 private final List<String> responseControlOIDs; 084 085 // The list of servers accessed while processing the operation. 086 private final List<String> serversAccessed; 087 088 // The list of privileges used during the course of processing the operation. 089 private final List<String> usedPrivileges; 090 091 // The number of intermediate response messages returned to the client. 092 private final Long intermediateResponsesReturned; 093 094 // The result code for the operation. 095 private final ResultCode resultCode; 096 097 // Additional information about the operation result. 098 private final String additionalInformation; 099 100 // The name of the client connection policy selected for the client. 101 private final String clientConnectionPolicy; 102 103 // The diagnostic message for the operation. 104 private final String diagnosticMessage; 105 106 // The intermediate client result for the operation. 107 private final String intermediateClientResult; 108 109 // The matched DN for the operation. 110 private final String matchedDN; 111 112 // The OID of the extended response. 113 private final String responseOID; 114 115 // The port of the backend server to which the request has been forwarded. 116 private final Integer targetPort; 117 118 // The address of the backend server to which the request has been forwarded. 119 private final String targetHost; 120 121 // The protocol used to forward the request to the backend server. 122 private final String targetProtocol; 123 124 125 126 /** 127 * Creates a new extended result access log message from the provided message 128 * string. 129 * 130 * @param s The string to be parsed as an extended result access log 131 * message. 132 * 133 * @throws LogException If the provided string cannot be parsed as a valid 134 * log message. 135 */ 136 public ExtendedResultAccessLogMessage(final String s) 137 throws LogException 138 { 139 this(new LogMessage(s)); 140 } 141 142 143 144 /** 145 * Creates a new extended result access log message from the provided log 146 * message. 147 * 148 * @param m The log message to be parsed as an extended result access log 149 * message. 150 */ 151 public ExtendedResultAccessLogMessage(final LogMessage m) 152 { 153 super(m); 154 155 diagnosticMessage = getNamedValue("message"); 156 additionalInformation = getNamedValue("additionalInfo"); 157 matchedDN = getNamedValue("matchedDN"); 158 processingTime = getNamedValueAsDouble("etime"); 159 queueTime = getNamedValueAsDouble("qtime"); 160 intermediateClientResult = getNamedValue("from"); 161 responseOID = getNamedValue("responseOID"); 162 targetHost = getNamedValue("targetHost"); 163 targetPort = getNamedValueAsInteger("targetPort"); 164 targetProtocol = getNamedValue("targetProtocol"); 165 clientConnectionPolicy = getNamedValue("clientConnectionPolicy"); 166 167 intermediateResponsesReturned = 168 getNamedValueAsLong("intermediateResponsesReturned"); 169 170 final Integer rcInteger = getNamedValueAsInteger("resultCode"); 171 if (rcInteger == null) 172 { 173 resultCode = null; 174 } 175 else 176 { 177 resultCode = ResultCode.valueOf(rcInteger); 178 } 179 180 final String refStr = getNamedValue("referralURLs"); 181 if ((refStr == null) || (refStr.length() == 0)) 182 { 183 referralURLs = Collections.emptyList(); 184 } 185 else 186 { 187 final LinkedList<String> refs = new LinkedList<String>(); 188 int startPos = 0; 189 while (true) 190 { 191 final int commaPos = refStr.indexOf(",ldap", startPos); 192 if (commaPos < 0) 193 { 194 refs.add(refStr.substring(startPos)); 195 break; 196 } 197 else 198 { 199 refs.add(refStr.substring(startPos, commaPos)); 200 startPos = commaPos+1; 201 } 202 } 203 referralURLs = Collections.unmodifiableList(refs); 204 } 205 206 final String controlStr = getNamedValue("responseControls"); 207 if (controlStr == null) 208 { 209 responseControlOIDs = Collections.emptyList(); 210 } 211 else 212 { 213 final LinkedList<String> controlList = new LinkedList<String>(); 214 final StringTokenizer t = new StringTokenizer(controlStr, ","); 215 while (t.hasMoreTokens()) 216 { 217 controlList.add(t.nextToken()); 218 } 219 responseControlOIDs = Collections.unmodifiableList(controlList); 220 } 221 222 final String serversAccessedStr = getNamedValue("serversAccessed"); 223 if ((serversAccessedStr == null) || (serversAccessedStr.length() == 0)) 224 { 225 serversAccessed = Collections.emptyList(); 226 } 227 else 228 { 229 final LinkedList<String> servers = new LinkedList<String>(); 230 final StringTokenizer tokenizer = 231 new StringTokenizer(serversAccessedStr, ","); 232 while (tokenizer.hasMoreTokens()) 233 { 234 servers.add(tokenizer.nextToken()); 235 } 236 serversAccessed = Collections.unmodifiableList(servers); 237 } 238 239 uncachedDataAccessed = getNamedValueAsBoolean("uncachedDataAccessed"); 240 241 final String usedPrivilegesStr = getNamedValue("usedPrivileges"); 242 if ((usedPrivilegesStr == null) || (usedPrivilegesStr.length() == 0)) 243 { 244 usedPrivileges = Collections.emptyList(); 245 } 246 else 247 { 248 final LinkedList<String> privileges = new LinkedList<String>(); 249 final StringTokenizer tokenizer = 250 new StringTokenizer(usedPrivilegesStr, ","); 251 while (tokenizer.hasMoreTokens()) 252 { 253 privileges.add(tokenizer.nextToken()); 254 } 255 usedPrivileges = Collections.unmodifiableList(privileges); 256 } 257 258 final String preAuthZUsedPrivilegesStr = 259 getNamedValue("preAuthZUsedPrivileges"); 260 if ((preAuthZUsedPrivilegesStr == null) || 261 (preAuthZUsedPrivilegesStr.length() == 0)) 262 { 263 preAuthZUsedPrivileges = Collections.emptyList(); 264 } 265 else 266 { 267 final LinkedList<String> privileges = new LinkedList<String>(); 268 final StringTokenizer tokenizer = 269 new StringTokenizer(preAuthZUsedPrivilegesStr, ","); 270 while (tokenizer.hasMoreTokens()) 271 { 272 privileges.add(tokenizer.nextToken()); 273 } 274 preAuthZUsedPrivileges = Collections.unmodifiableList(privileges); 275 } 276 277 final String missingPrivilegesStr = getNamedValue("missingPrivileges"); 278 if ((missingPrivilegesStr == null) || (missingPrivilegesStr.length() == 0)) 279 { 280 missingPrivileges = Collections.emptyList(); 281 } 282 else 283 { 284 final LinkedList<String> privileges = new LinkedList<String>(); 285 final StringTokenizer tokenizer = 286 new StringTokenizer(missingPrivilegesStr, ","); 287 while (tokenizer.hasMoreTokens()) 288 { 289 privileges.add(tokenizer.nextToken()); 290 } 291 missingPrivileges = Collections.unmodifiableList(privileges); 292 } 293 } 294 295 296 297 /** 298 * Retrieves the result code for the operation. 299 * 300 * @return The result code for the operation, or {@code null} if it is not 301 * included in the log message. 302 */ 303 public ResultCode getResultCode() 304 { 305 return resultCode; 306 } 307 308 309 310 /** 311 * Retrieves the diagnostic message for the operation. 312 * 313 * @return The diagnostic message for the operation, or {@code null} if it is 314 * not included in the log message. 315 */ 316 public String getDiagnosticMessage() 317 { 318 return diagnosticMessage; 319 } 320 321 322 323 /** 324 * Retrieves a message with additional information about the result of the 325 * operation. 326 * 327 * @return A message with additional information about the result of the 328 * operation, or {@code null} if it is not included in the log 329 * message. 330 */ 331 public String getAdditionalInformation() 332 { 333 return additionalInformation; 334 } 335 336 337 338 /** 339 * Retrieves the matched DN for the operation. 340 * 341 * @return The matched DN for the operation, or {@code null} if it is not 342 * included in the log message. 343 */ 344 public String getMatchedDN() 345 { 346 return matchedDN; 347 } 348 349 350 351 /** 352 * Retrieves the list of referral URLs for the operation. 353 * 354 * @return The list of referral URLs for the operation, or an empty list if 355 * it is not included in the log message. 356 */ 357 public List<String> getReferralURLs() 358 { 359 return referralURLs; 360 } 361 362 363 364 /** 365 * Retrieves a list of the additional servers that were accessed in the course 366 * of processing the operation. For example, if the access log message is 367 * from a Directory Proxy Server instance, then this may contain a list of the 368 * backend servers used to process the operation. 369 * 370 * @return A list of the additional servers that were accessed in the course 371 * of processing the operation, or an empty list if it is not 372 * included in the log message. 373 */ 374 public List<String> getServersAccessed() 375 { 376 return serversAccessed; 377 } 378 379 380 381 /** 382 * Indicates whether the server accessed any uncached data in the course of 383 * processing the operation. 384 * 385 * @return {@code true} if the server was known to access uncached data in 386 * the course of processing the operation, {@code false} if the 387 * server was known not to access uncached data, or {@code null} if 388 * it is not included in the log message (and the server likely did 389 * not access uncached data). 390 */ 391 public Boolean getUncachedDataAccessed() 392 { 393 return uncachedDataAccessed; 394 } 395 396 397 398 /** 399 * Retrieves the number of intermediate response messages returned in the 400 * course of processing the operation. 401 * 402 * @return The number of intermediate response messages returned to the 403 * client in the course of processing the operation, or {@code null} 404 * if it is not included in the log message. 405 */ 406 public Long getIntermediateResponsesReturned() 407 { 408 return intermediateResponsesReturned; 409 } 410 411 412 413 /** 414 * Retrieves the length of time in milliseconds required to process the 415 * operation. 416 * 417 * @return The length of time in milliseconds required to process the 418 * operation, or {@code null} if it is not included in the log 419 * message. 420 */ 421 public Double getProcessingTimeMillis() 422 { 423 return processingTime; 424 } 425 426 427 428 /** 429 * Retrieves the length of time in milliseconds the operation was required to 430 * wait on the work queue. 431 * 432 * @return The length of time in milliseconds the operation was required to 433 * wait on the work queue, or {@code null} if it is not included in 434 * the log message. 435 */ 436 public Double getQueueTimeMillis() 437 { 438 return queueTime; 439 } 440 441 442 443 /** 444 * Retrieves the OIDs of any response controls contained in the log message. 445 * 446 * @return The OIDs of any response controls contained in the log message, or 447 * an empty list if it is not included in the log message. 448 */ 449 public List<String> getResponseControlOIDs() 450 { 451 return responseControlOIDs; 452 } 453 454 455 456 /** 457 * Retrieves the content of the intermediate client result for the 458 * operation. 459 * 460 * @return The content of the intermediate client result for the operation, 461 * or {@code null} if it is not included in the log message. 462 */ 463 public String getIntermediateClientResult() 464 { 465 return intermediateClientResult; 466 } 467 468 469 470 /** 471 * Retrieves the OID for the extended response. 472 * 473 * @return The OID for the extended response, or {@code null} if it is not 474 * included in the log message. 475 */ 476 public String getResponseOID() 477 { 478 return responseOID; 479 } 480 481 482 483 /** 484 * Retrieves the address of the backend server to which the request has been 485 * forwarded. 486 * 487 * @return The address of the backend server to which the request has been 488 * forwarded, or {@code null} if it is not included in the log 489 * message. 490 */ 491 public String getTargetHost() 492 { 493 return targetHost; 494 } 495 496 497 498 /** 499 * Retrieves the port of the backend server to which the request has been 500 * forwarded. 501 * 502 * @return The port of the backend server to which the request has been 503 * forwarded, or {@code null} if it is not included in the log 504 * message. 505 */ 506 public Integer getTargetPort() 507 { 508 return targetPort; 509 } 510 511 512 513 /** 514 * Retrieves the protocol used to forward the request to the backend server. 515 * 516 * @return The protocol used to forward the request to the backend server, or 517 * {@code null} if it is not included in the log message. 518 */ 519 public String getTargetProtocol() 520 { 521 return targetProtocol; 522 } 523 524 525 526 /** 527 * Retrieves the name of the client connection policy that was selected for 528 * the client connection. 529 * 530 * @return The name of the client connection policy that was selected for the 531 * client connection, or {@code null} if it is not included in the 532 * log message. 533 */ 534 public String getClientConnectionPolicy() 535 { 536 return clientConnectionPolicy; 537 } 538 539 540 541 /** 542 * Retrieves the names of any privileges used during the course of processing 543 * the operation. 544 * 545 * @return The names of any privileges used during the course of processing 546 * the operation, or an empty list if no privileges were used or this 547 * is not included in the log message. 548 */ 549 public List<String> getUsedPrivileges() 550 { 551 return usedPrivileges; 552 } 553 554 555 556 /** 557 * Retrieves the names of any privileges used during the course of processing 558 * the operation before an alternate authorization identity was assigned. 559 * 560 * @return The names of any privileges used during the course of processing 561 * the operation before an alternate authorization identity was 562 * assigned, or an empty list if no privileges were used or this is 563 * not included in the log message. 564 */ 565 public List<String> getPreAuthorizationUsedPrivileges() 566 { 567 return preAuthZUsedPrivileges; 568 } 569 570 571 572 /** 573 * Retrieves the names of any privileges that would have been required for 574 * processing the operation but that the requester did not have. 575 * 576 * @return The names of any privileges that would have been required for 577 * processing the operation but that the requester did not have, or 578 * an empty list if there were no missing privileges or this is not 579 * included in the log message. 580 */ 581 public List<String> getMissingPrivileges() 582 { 583 return missingPrivileges; 584 } 585 586 587 588 /** 589 * {@inheritDoc} 590 */ 591 @Override() 592 public AccessLogMessageType getMessageType() 593 { 594 return AccessLogMessageType.RESULT; 595 } 596 }