001/* 002 * Copyright 2008-2024 Ping Identity Corporation 003 * All Rights Reserved. 004 */ 005/* 006 * Copyright 2008-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) 2008-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.matchingrules; 037 038 039 040import com.unboundid.asn1.ASN1OctetString; 041import com.unboundid.ldap.sdk.DN; 042import com.unboundid.ldap.sdk.LDAPException; 043import com.unboundid.ldap.sdk.ResultCode; 044import com.unboundid.util.Debug; 045import com.unboundid.util.NotNull; 046import com.unboundid.util.Nullable; 047import com.unboundid.util.StaticUtils; 048import com.unboundid.util.ThreadSafety; 049import com.unboundid.util.ThreadSafetyLevel; 050 051import static com.unboundid.ldap.matchingrules.MatchingRuleMessages.*; 052 053 054 055/** 056 * This class provides an implementation of a matching rule that performs 057 * equality comparisons against values that should be distinguished names. 058 * Substring and ordering matching are not supported. 059 */ 060@ThreadSafety(level=ThreadSafetyLevel.COMPLETELY_THREADSAFE) 061public final class DistinguishedNameMatchingRule 062 extends MatchingRule 063{ 064 /** 065 * The singleton instance that will be returned from the {@code getInstance} 066 * method. 067 */ 068 @NotNull private static final DistinguishedNameMatchingRule INSTANCE = 069 new DistinguishedNameMatchingRule(); 070 071 072 073 /** 074 * The name for the distinguishedNameMatch equality matching rule. 075 */ 076 @NotNull public static final String EQUALITY_RULE_NAME = 077 "distinguishedNameMatch"; 078 079 080 081 /** 082 * The name for the distinguishedNameMatch equality matching rule, formatted 083 * in all lowercase characters. 084 */ 085 @NotNull static final String LOWER_EQUALITY_RULE_NAME = 086 StaticUtils.toLowerCase(EQUALITY_RULE_NAME); 087 088 089 090 /** 091 * The OID for the distinguishedNameMatch equality matching rule. 092 */ 093 @NotNull public static final String EQUALITY_RULE_OID = "2.5.13.1"; 094 095 096 097 /** 098 * The serial version UID for this serializable class. 099 */ 100 private static final long serialVersionUID = -2617356571703597868L; 101 102 103 104 /** 105 * Creates a new instance of this distinguished name matching rule. 106 */ 107 public DistinguishedNameMatchingRule() 108 { 109 // No implementation is required. 110 } 111 112 113 114 /** 115 * Retrieves a singleton instance of this matching rule. 116 * 117 * @return A singleton instance of this matching rule. 118 */ 119 @NotNull() 120 public static DistinguishedNameMatchingRule getInstance() 121 { 122 return INSTANCE; 123 } 124 125 126 127 /** 128 * {@inheritDoc} 129 */ 130 @Override() 131 @NotNull() 132 public String getEqualityMatchingRuleName() 133 { 134 return EQUALITY_RULE_NAME; 135 } 136 137 138 139 /** 140 * {@inheritDoc} 141 */ 142 @Override() 143 @NotNull() 144 public String getEqualityMatchingRuleOID() 145 { 146 return EQUALITY_RULE_OID; 147 } 148 149 150 151 /** 152 * {@inheritDoc} 153 */ 154 @Override() 155 @Nullable() 156 public String getOrderingMatchingRuleName() 157 { 158 return null; 159 } 160 161 162 163 /** 164 * {@inheritDoc} 165 */ 166 @Override() 167 @Nullable() 168 public String getOrderingMatchingRuleOID() 169 { 170 return null; 171 } 172 173 174 175 /** 176 * {@inheritDoc} 177 */ 178 @Override() 179 @Nullable() 180 public String getSubstringMatchingRuleName() 181 { 182 return null; 183 } 184 185 186 187 /** 188 * {@inheritDoc} 189 */ 190 @Override() 191 @Nullable() 192 public String getSubstringMatchingRuleOID() 193 { 194 return null; 195 } 196 197 198 199 /** 200 * {@inheritDoc} 201 */ 202 @Override() 203 public boolean valuesMatch(@NotNull final ASN1OctetString value1, 204 @NotNull final ASN1OctetString value2) 205 throws LDAPException 206 { 207 final DN dn1; 208 try 209 { 210 dn1 = new DN(value1.stringValue()); 211 } 212 catch (final LDAPException le) 213 { 214 Debug.debugException(le); 215 throw new LDAPException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, 216 le.getMessage(), le); 217 } 218 219 final DN dn2; 220 try 221 { 222 dn2 = new DN(value2.stringValue()); 223 } 224 catch (final LDAPException le) 225 { 226 Debug.debugException(le); 227 throw new LDAPException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, 228 le.getMessage(), le); 229 } 230 231 return dn1.equals(dn2); 232 } 233 234 235 236 /** 237 * {@inheritDoc} 238 */ 239 @Override() 240 public boolean matchesAnyValue(@NotNull final ASN1OctetString assertionValue, 241 @NotNull final ASN1OctetString[] attributeValues) 242 throws LDAPException 243 { 244 if ((assertionValue == null) || (attributeValues == null) || 245 (attributeValues.length == 0)) 246 { 247 return false; 248 } 249 250 final DN assertionValueDN; 251 try 252 { 253 assertionValueDN = new DN(assertionValue.stringValue()); 254 } 255 catch (final LDAPException le) 256 { 257 Debug.debugException(le); 258 throw new LDAPException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, 259 le.getMessage(), le); 260 } 261 262 for (final ASN1OctetString attributeValue : attributeValues) 263 { 264 try 265 { 266 if (assertionValueDN.equals(new DN(attributeValue.stringValue()))) 267 { 268 return true; 269 } 270 } 271 catch (final Exception e) 272 { 273 Debug.debugException(e); 274 } 275 } 276 277 return false; 278 } 279 280 281 282 /** 283 * {@inheritDoc} 284 */ 285 @Override() 286 public boolean matchesSubstring(@NotNull final ASN1OctetString value, 287 @Nullable final ASN1OctetString subInitial, 288 @Nullable final ASN1OctetString[] subAny, 289 @Nullable final ASN1OctetString subFinal) 290 throws LDAPException 291 { 292 throw new LDAPException(ResultCode.INAPPROPRIATE_MATCHING, 293 ERR_DN_SUBSTRING_MATCHING_NOT_SUPPORTED.get()); 294 } 295 296 297 298 /** 299 * {@inheritDoc} 300 */ 301 @Override() 302 public int compareValues(@NotNull final ASN1OctetString value1, 303 @NotNull final ASN1OctetString value2) 304 throws LDAPException 305 { 306 throw new LDAPException(ResultCode.INAPPROPRIATE_MATCHING, 307 ERR_DN_ORDERING_MATCHING_NOT_SUPPORTED.get()); 308 } 309 310 311 312 /** 313 * {@inheritDoc} 314 */ 315 @Override() 316 @NotNull() 317 public ASN1OctetString normalize(@NotNull final ASN1OctetString value) 318 throws LDAPException 319 { 320 try 321 { 322 final DN dn = new DN(value.stringValue()); 323 return new ASN1OctetString(dn.toNormalizedString()); 324 } 325 catch (final LDAPException le) 326 { 327 Debug.debugException(le); 328 throw new LDAPException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, 329 le.getMessage(), le); 330 } 331 } 332 333 334 335 /** 336 * {@inheritDoc} 337 */ 338 @Override() 339 @NotNull() 340 public ASN1OctetString normalizeSubstring( 341 @NotNull final ASN1OctetString value, 342 final byte substringType) 343 throws LDAPException 344 { 345 throw new LDAPException(ResultCode.INAPPROPRIATE_MATCHING, 346 ERR_DN_SUBSTRING_MATCHING_NOT_SUPPORTED.get()); 347 } 348}