001/* 002 * CDDL HEADER START 003 * 004 * The contents of this file are subject to the terms of the 005 * Common Development and Distribution License, Version 1.0 only 006 * (the "License"). You may not use this file except in compliance 007 * with the License. 008 * 009 * You can obtain a copy of the license at legal-notices/CDDLv1_0.txt 010 * or http://forgerock.org/license/CDDLv1.0.html. 011 * See the License for the specific language governing permissions 012 * and limitations under the License. 013 * 014 * When distributing Covered Code, include this CDDL HEADER in each 015 * file and include the License file at legal-notices/CDDLv1_0.txt. 016 * If applicable, add the following below this CDDL HEADER, with the 017 * fields enclosed by brackets "[]" replaced with your own identifying 018 * information: 019 * Portions Copyright [yyyy] [name of copyright owner] 020 * 021 * CDDL HEADER END 022 * 023 * 024 * Copyright 2008 Sun Microsystems, Inc. 025 */ 026package org.forgerock.opendj.server.config.meta; 027 028 029 030import java.util.Collection; 031import java.util.SortedSet; 032import org.forgerock.opendj.config.AdministratorAction; 033import org.forgerock.opendj.config.AliasDefaultBehaviorProvider; 034import org.forgerock.opendj.config.AttributeTypePropertyDefinition; 035import org.forgerock.opendj.config.client.ConcurrentModificationException; 036import org.forgerock.opendj.config.client.ManagedObject; 037import org.forgerock.opendj.config.client.MissingMandatoryPropertiesException; 038import org.forgerock.opendj.config.client.OperationRejectedException; 039import org.forgerock.opendj.config.DefaultBehaviorProvider; 040import org.forgerock.opendj.config.DefinedDefaultBehaviorProvider; 041import org.forgerock.opendj.config.EnumPropertyDefinition; 042import org.forgerock.opendj.config.IntegerPropertyDefinition; 043import org.forgerock.opendj.config.ManagedObjectAlreadyExistsException; 044import org.forgerock.opendj.config.ManagedObjectDefinition; 045import org.forgerock.opendj.config.PropertyException; 046import org.forgerock.opendj.config.PropertyOption; 047import org.forgerock.opendj.config.PropertyProvider; 048import org.forgerock.opendj.config.RelativeInheritedDefaultBehaviorProvider; 049import org.forgerock.opendj.config.server.ConfigurationChangeListener; 050import org.forgerock.opendj.config.server.ServerManagedObject; 051import org.forgerock.opendj.config.StringPropertyDefinition; 052import org.forgerock.opendj.config.Tag; 053import org.forgerock.opendj.config.TopCfgDefn; 054import org.forgerock.opendj.config.UndefinedDefaultBehaviorProvider; 055import org.forgerock.opendj.ldap.DN; 056import org.forgerock.opendj.ldap.LdapException; 057import org.forgerock.opendj.ldap.schema.AttributeType; 058import org.forgerock.opendj.server.config.client.BackendIndexCfgClient; 059import org.forgerock.opendj.server.config.server.BackendIndexCfg; 060 061 062 063/** 064 * An interface for querying the Backend Index managed object 065 * definition meta information. 066 * <p> 067 * Backend Indexes are used to store information that makes it 068 * possible to locate entries very quickly when processing search 069 * operations. 070 */ 071public final class BackendIndexCfgDefn extends ManagedObjectDefinition<BackendIndexCfgClient, BackendIndexCfg> { 072 073 /** The singleton configuration definition instance. */ 074 private static final BackendIndexCfgDefn INSTANCE = new BackendIndexCfgDefn(); 075 076 077 078 /** 079 * Defines the set of permissable values for the "index-type" property. 080 * <p> 081 * Specifies the type(s) of indexing that should be performed for 082 * the associated attribute. 083 * <p> 084 * For equality, presence, and substring index types, the associated 085 * attribute type must have a corresponding matching rule. 086 */ 087 public static enum IndexType { 088 089 /** 090 * This index type is used to improve the efficiency of searches 091 * using approximate matching search filters. 092 */ 093 APPROXIMATE("approximate"), 094 095 096 097 /** 098 * This index type is used to improve the efficiency of searches 099 * using equality search filters. 100 */ 101 EQUALITY("equality"), 102 103 104 105 /** 106 * This index type is used to improve the efficiency of searches 107 * using extensible matching search filters. 108 */ 109 EXTENSIBLE("extensible"), 110 111 112 113 /** 114 * This index type is used to improve the efficiency of searches 115 * using "greater than or equal to" or "less then or equal to" 116 * search filters. 117 */ 118 ORDERING("ordering"), 119 120 121 122 /** 123 * This index type is used to improve the efficiency of searches 124 * using the presence search filters. 125 */ 126 PRESENCE("presence"), 127 128 129 130 /** 131 * This index type is used to improve the efficiency of searches 132 * using substring search filters. 133 */ 134 SUBSTRING("substring"); 135 136 137 138 /** String representation of the value. */ 139 private final String name; 140 141 142 143 /** Private constructor. */ 144 private IndexType(String name) { this.name = name; } 145 146 147 148 /** {@inheritDoc} */ 149 public String toString() { return name; } 150 151 } 152 153 154 155 /** The "attribute" property definition. */ 156 private static final AttributeTypePropertyDefinition PD_ATTRIBUTE; 157 158 159 160 /** The "index-entry-limit" property definition. */ 161 private static final IntegerPropertyDefinition PD_INDEX_ENTRY_LIMIT; 162 163 164 165 /** The "index-extensible-matching-rule" property definition. */ 166 private static final StringPropertyDefinition PD_INDEX_EXTENSIBLE_MATCHING_RULE; 167 168 169 170 /** The "index-type" property definition. */ 171 private static final EnumPropertyDefinition<IndexType> PD_INDEX_TYPE; 172 173 174 175 /** The "substring-length" property definition. */ 176 private static final IntegerPropertyDefinition PD_SUBSTRING_LENGTH; 177 178 179 180 /** Build the "attribute" property definition. */ 181 static { 182 AttributeTypePropertyDefinition.Builder builder = AttributeTypePropertyDefinition.createBuilder(INSTANCE, "attribute"); 183 builder.setOption(PropertyOption.READ_ONLY); 184 builder.setOption(PropertyOption.MANDATORY); 185 builder.setAdministratorAction(new AdministratorAction(AdministratorAction.Type.NONE, INSTANCE, "attribute")); 186 builder.setDefaultBehaviorProvider(new UndefinedDefaultBehaviorProvider<AttributeType>()); 187 PD_ATTRIBUTE = builder.getInstance(); 188 INSTANCE.registerPropertyDefinition(PD_ATTRIBUTE); 189 } 190 191 192 193 /** Build the "index-entry-limit" property definition. */ 194 static { 195 IntegerPropertyDefinition.Builder builder = IntegerPropertyDefinition.createBuilder(INSTANCE, "index-entry-limit"); 196 builder.setAdministratorAction(new AdministratorAction(AdministratorAction.Type.OTHER, INSTANCE, "index-entry-limit")); 197 DefaultBehaviorProvider<Integer> provider = new RelativeInheritedDefaultBehaviorProvider<Integer>(PluggableBackendCfgDefn.getInstance(), "index-entry-limit", 1); 198 builder.setDefaultBehaviorProvider(provider); 199 builder.setUpperLimit(2147483647); 200 builder.setLowerLimit(0); 201 PD_INDEX_ENTRY_LIMIT = builder.getInstance(); 202 INSTANCE.registerPropertyDefinition(PD_INDEX_ENTRY_LIMIT); 203 } 204 205 206 207 /** Build the "index-extensible-matching-rule" property definition. */ 208 static { 209 StringPropertyDefinition.Builder builder = StringPropertyDefinition.createBuilder(INSTANCE, "index-extensible-matching-rule"); 210 builder.setOption(PropertyOption.MULTI_VALUED); 211 builder.setAdministratorAction(new AdministratorAction(AdministratorAction.Type.OTHER, INSTANCE, "index-extensible-matching-rule")); 212 builder.setDefaultBehaviorProvider(new AliasDefaultBehaviorProvider<String>(INSTANCE, "index-extensible-matching-rule")); 213 builder.setPattern("([a-z][a-z](-[A-Z][A-Z]){0,2}(.(([a-z]{2,3})|\\d))?)|(^\\d.((\\d)+.)+\\d$)", "LOCALE | OID"); 214 PD_INDEX_EXTENSIBLE_MATCHING_RULE = builder.getInstance(); 215 INSTANCE.registerPropertyDefinition(PD_INDEX_EXTENSIBLE_MATCHING_RULE); 216 } 217 218 219 220 /** Build the "index-type" property definition. */ 221 static { 222 EnumPropertyDefinition.Builder<IndexType> builder = EnumPropertyDefinition.createBuilder(INSTANCE, "index-type"); 223 builder.setOption(PropertyOption.MULTI_VALUED); 224 builder.setOption(PropertyOption.MANDATORY); 225 builder.setAdministratorAction(new AdministratorAction(AdministratorAction.Type.OTHER, INSTANCE, "index-type")); 226 builder.setDefaultBehaviorProvider(new UndefinedDefaultBehaviorProvider<IndexType>()); 227 builder.setEnumClass(IndexType.class); 228 PD_INDEX_TYPE = builder.getInstance(); 229 INSTANCE.registerPropertyDefinition(PD_INDEX_TYPE); 230 } 231 232 233 234 /** Build the "substring-length" property definition. */ 235 static { 236 IntegerPropertyDefinition.Builder builder = IntegerPropertyDefinition.createBuilder(INSTANCE, "substring-length"); 237 builder.setOption(PropertyOption.ADVANCED); 238 builder.setAdministratorAction(new AdministratorAction(AdministratorAction.Type.OTHER, INSTANCE, "substring-length")); 239 DefaultBehaviorProvider<Integer> provider = new DefinedDefaultBehaviorProvider<Integer>("6"); 240 builder.setDefaultBehaviorProvider(provider); 241 builder.setLowerLimit(3); 242 PD_SUBSTRING_LENGTH = builder.getInstance(); 243 INSTANCE.registerPropertyDefinition(PD_SUBSTRING_LENGTH); 244 } 245 246 247 248 // Register the tags associated with this managed object definition. 249 static { 250 INSTANCE.registerTag(Tag.valueOf("database")); 251 } 252 253 254 255 /** 256 * Get the Backend Index configuration definition singleton. 257 * 258 * @return Returns the Backend Index configuration definition 259 * singleton. 260 */ 261 public static BackendIndexCfgDefn getInstance() { 262 return INSTANCE; 263 } 264 265 266 267 /** 268 * Private constructor. 269 */ 270 private BackendIndexCfgDefn() { 271 super("backend-index", TopCfgDefn.getInstance()); 272 } 273 274 275 276 /** {@inheritDoc} */ 277 public BackendIndexCfgClient createClientConfiguration( 278 ManagedObject<? extends BackendIndexCfgClient> impl) { 279 return new BackendIndexCfgClientImpl(impl); 280 } 281 282 283 284 /** {@inheritDoc} */ 285 public BackendIndexCfg createServerConfiguration( 286 ServerManagedObject<? extends BackendIndexCfg> impl) { 287 return new BackendIndexCfgServerImpl(impl); 288 } 289 290 291 292 /** {@inheritDoc} */ 293 public Class<BackendIndexCfg> getServerConfigurationClass() { 294 return BackendIndexCfg.class; 295 } 296 297 298 299 /** 300 * Get the "attribute" property definition. 301 * <p> 302 * Specifies the name of the attribute for which the index is to be 303 * maintained. 304 * 305 * @return Returns the "attribute" property definition. 306 */ 307 public AttributeTypePropertyDefinition getAttributePropertyDefinition() { 308 return PD_ATTRIBUTE; 309 } 310 311 312 313 /** 314 * Get the "index-entry-limit" property definition. 315 * <p> 316 * Specifies the maximum number of entries that are allowed to match 317 * a given index key before that particular index key is no longer 318 * maintained. 319 * <p> 320 * This is analogous to the ALL IDs threshold in the Sun Java System 321 * Directory Server. If this is specified, its value overrides the JE 322 * backend-wide configuration. For no limit, use 0 for the value. 323 * 324 * @return Returns the "index-entry-limit" property definition. 325 */ 326 public IntegerPropertyDefinition getIndexEntryLimitPropertyDefinition() { 327 return PD_INDEX_ENTRY_LIMIT; 328 } 329 330 331 332 /** 333 * Get the "index-extensible-matching-rule" property definition. 334 * <p> 335 * The extensible matching rule in an extensible index. 336 * <p> 337 * An extensible matching rule must be specified using either LOCALE 338 * or OID of the matching rule. 339 * 340 * @return Returns the "index-extensible-matching-rule" property definition. 341 */ 342 public StringPropertyDefinition getIndexExtensibleMatchingRulePropertyDefinition() { 343 return PD_INDEX_EXTENSIBLE_MATCHING_RULE; 344 } 345 346 347 348 /** 349 * Get the "index-type" property definition. 350 * <p> 351 * Specifies the type(s) of indexing that should be performed for 352 * the associated attribute. 353 * <p> 354 * For equality, presence, and substring index types, the associated 355 * attribute type must have a corresponding matching rule. 356 * 357 * @return Returns the "index-type" property definition. 358 */ 359 public EnumPropertyDefinition<IndexType> getIndexTypePropertyDefinition() { 360 return PD_INDEX_TYPE; 361 } 362 363 364 365 /** 366 * Get the "substring-length" property definition. 367 * <p> 368 * The length of substrings in a substring index. 369 * 370 * @return Returns the "substring-length" property definition. 371 */ 372 public IntegerPropertyDefinition getSubstringLengthPropertyDefinition() { 373 return PD_SUBSTRING_LENGTH; 374 } 375 376 377 378 /** 379 * Managed object client implementation. 380 */ 381 private static class BackendIndexCfgClientImpl implements 382 BackendIndexCfgClient { 383 384 /** Private implementation. */ 385 private ManagedObject<? extends BackendIndexCfgClient> impl; 386 387 388 389 /** Private constructor. */ 390 private BackendIndexCfgClientImpl( 391 ManagedObject<? extends BackendIndexCfgClient> impl) { 392 this.impl = impl; 393 } 394 395 396 397 /** {@inheritDoc} */ 398 public AttributeType getAttribute() { 399 return impl.getPropertyValue(INSTANCE.getAttributePropertyDefinition()); 400 } 401 402 403 404 /** {@inheritDoc} */ 405 public void setAttribute(AttributeType value) throws PropertyException { 406 impl.setPropertyValue(INSTANCE.getAttributePropertyDefinition(), value); 407 } 408 409 410 411 /** {@inheritDoc} */ 412 public Integer getIndexEntryLimit() { 413 return impl.getPropertyValue(INSTANCE.getIndexEntryLimitPropertyDefinition()); 414 } 415 416 417 418 /** {@inheritDoc} */ 419 public void setIndexEntryLimit(Integer value) { 420 impl.setPropertyValue(INSTANCE.getIndexEntryLimitPropertyDefinition(), value); 421 } 422 423 424 425 /** {@inheritDoc} */ 426 public SortedSet<String> getIndexExtensibleMatchingRule() { 427 return impl.getPropertyValues(INSTANCE.getIndexExtensibleMatchingRulePropertyDefinition()); 428 } 429 430 431 432 /** {@inheritDoc} */ 433 public void setIndexExtensibleMatchingRule(Collection<String> values) { 434 impl.setPropertyValues(INSTANCE.getIndexExtensibleMatchingRulePropertyDefinition(), values); 435 } 436 437 438 439 /** {@inheritDoc} */ 440 public SortedSet<IndexType> getIndexType() { 441 return impl.getPropertyValues(INSTANCE.getIndexTypePropertyDefinition()); 442 } 443 444 445 446 /** {@inheritDoc} */ 447 public void setIndexType(Collection<IndexType> values) { 448 impl.setPropertyValues(INSTANCE.getIndexTypePropertyDefinition(), values); 449 } 450 451 452 453 /** {@inheritDoc} */ 454 public int getSubstringLength() { 455 return impl.getPropertyValue(INSTANCE.getSubstringLengthPropertyDefinition()); 456 } 457 458 459 460 /** {@inheritDoc} */ 461 public void setSubstringLength(Integer value) { 462 impl.setPropertyValue(INSTANCE.getSubstringLengthPropertyDefinition(), value); 463 } 464 465 466 467 /** {@inheritDoc} */ 468 public ManagedObjectDefinition<? extends BackendIndexCfgClient, ? extends BackendIndexCfg> definition() { 469 return INSTANCE; 470 } 471 472 473 474 /** {@inheritDoc} */ 475 public PropertyProvider properties() { 476 return impl; 477 } 478 479 480 481 /** {@inheritDoc} */ 482 public void commit() throws ManagedObjectAlreadyExistsException, 483 MissingMandatoryPropertiesException, ConcurrentModificationException, 484 OperationRejectedException, LdapException { 485 impl.commit(); 486 } 487 488 489 490 /** {@inheritDoc} */ 491 public String toString() { 492 return impl.toString(); 493 } 494 } 495 496 497 498 /** 499 * Managed object server implementation. 500 */ 501 private static class BackendIndexCfgServerImpl implements 502 BackendIndexCfg { 503 504 /** Private implementation. */ 505 private ServerManagedObject<? extends BackendIndexCfg> impl; 506 507 /** The value of the "attribute" property. */ 508 private final AttributeType pAttribute; 509 510 /** The value of the "index-entry-limit" property. */ 511 private final Integer pIndexEntryLimit; 512 513 /** The value of the "index-extensible-matching-rule" property. */ 514 private final SortedSet<String> pIndexExtensibleMatchingRule; 515 516 /** The value of the "index-type" property. */ 517 private final SortedSet<IndexType> pIndexType; 518 519 /** The value of the "substring-length" property. */ 520 private final int pSubstringLength; 521 522 523 524 /** Private constructor. */ 525 private BackendIndexCfgServerImpl(ServerManagedObject<? extends BackendIndexCfg> impl) { 526 this.impl = impl; 527 this.pAttribute = impl.getPropertyValue(INSTANCE.getAttributePropertyDefinition()); 528 this.pIndexEntryLimit = impl.getPropertyValue(INSTANCE.getIndexEntryLimitPropertyDefinition()); 529 this.pIndexExtensibleMatchingRule = impl.getPropertyValues(INSTANCE.getIndexExtensibleMatchingRulePropertyDefinition()); 530 this.pIndexType = impl.getPropertyValues(INSTANCE.getIndexTypePropertyDefinition()); 531 this.pSubstringLength = impl.getPropertyValue(INSTANCE.getSubstringLengthPropertyDefinition()); 532 } 533 534 535 536 /** {@inheritDoc} */ 537 public void addChangeListener( 538 ConfigurationChangeListener<BackendIndexCfg> listener) { 539 impl.registerChangeListener(listener); 540 } 541 542 543 544 /** {@inheritDoc} */ 545 public void removeChangeListener( 546 ConfigurationChangeListener<BackendIndexCfg> listener) { 547 impl.deregisterChangeListener(listener); 548 } 549 550 551 552 /** {@inheritDoc} */ 553 public AttributeType getAttribute() { 554 return pAttribute; 555 } 556 557 558 559 /** {@inheritDoc} */ 560 public Integer getIndexEntryLimit() { 561 return pIndexEntryLimit; 562 } 563 564 565 566 /** {@inheritDoc} */ 567 public SortedSet<String> getIndexExtensibleMatchingRule() { 568 return pIndexExtensibleMatchingRule; 569 } 570 571 572 573 /** {@inheritDoc} */ 574 public SortedSet<IndexType> getIndexType() { 575 return pIndexType; 576 } 577 578 579 580 /** {@inheritDoc} */ 581 public int getSubstringLength() { 582 return pSubstringLength; 583 } 584 585 586 587 /** {@inheritDoc} */ 588 public Class<? extends BackendIndexCfg> configurationClass() { 589 return BackendIndexCfg.class; 590 } 591 592 593 594 /** {@inheritDoc} */ 595 public DN dn() { 596 return impl.getDN(); 597 } 598 599 600 601 /** {@inheritDoc} */ 602 public String toString() { 603 return impl.toString(); 604 } 605 } 606}