src/com/netscape/admin/dirserv/DSUtil.java | 281 ++++++++++----
src/com/netscape/admin/dirserv/propedit/DSEntryPanel.java | 12
2 files changed, 222 insertions(+), 71 deletions(-)
New commits:
commit b2e8292736c270424f2e60a4e0e3bb243dacde74
Author: Rich Megginson <rmeggins(a)redhat.com>
Date: Mon May 3 11:33:34 2010 -0600
Bug 586571 - DS Console shows escaped DNs
https://bugzilla.redhat.com/show_bug.cgi?id=586571
Resolves: bug 586571
Bug Description: DS Console shows escaped DNs
Reviewed by: nkinder (Thanks!)
Branch: HEAD
Fix Description: Was not working correctly in the property and advanced
editor for editing some DNs that contained other DNs as RDN values.
I also moved a lot of the DN handling code into the main console package
into the LDAPUtil class. This will allow the main console to handle DN
escapes as well. Unfortunately, if managing a new DS on a machine which
only has the old console framework, these methods will be missing.
So, use the new methods if available, otherwise, fallback on the DSUtil
implementation.
Platforms tested: RHEL5 x86_64
Flag Day: no
Doc impact: no
diff --git a/src/com/netscape/admin/dirserv/DSUtil.java
b/src/com/netscape/admin/dirserv/DSUtil.java
index 6f0b3d1..316d62c 100644
--- a/src/com/netscape/admin/dirserv/DSUtil.java
+++ b/src/com/netscape/admin/dirserv/DSUtil.java
@@ -19,6 +19,7 @@
package com.netscape.admin.dirserv;
+import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.awt.*;
import java.awt.image.*;
@@ -1809,57 +1810,6 @@ public class DSUtil {
return state ? IServerObject.STATUS_STARTED : IServerObject.STATUS_STOPPED;
}
- /**
- * Check if the string is a valid dn
- *
- */
- static public boolean isValidDN (String dn){
- if (dn.equals (""))
- return true;
-
- if (!netscape.ldap.util.DN.isDN(dn))
- return false;
-
- int eq = dn.indexOf('=');
-
- return (eq > 0 && eq < dn.length () -1 );
- }
-
- static public boolean equalDNs(DN dn1, DN dn2) {
- boolean status = (dn1 == null || dn2 == null);
- if (status) { // if at least one of the arguments is null
- status = (dn1 == dn2); // true if both are null, false otherwise
- return status; // short circuit
- }
-
- Vector thisRDNs = dn1.getRDNs();
- Vector thatRDNs = dn2.getRDNs();
- if (thisRDNs != null && thatRDNs != null &&
- thisRDNs.size() == thatRDNs.size()) {
- int ii;
- for (ii = 0; ii < thisRDNs.size(); ++ii) {
- RDN thisRDN = (RDN)thisRDNs.elementAt(ii);
- RDN thatRDN = (RDN)thatRDNs.elementAt(ii);
- if (!thisRDN.equals(thatRDN))
- break;
- }
-
- // all RDNs were equal
- if (ii == thisRDNs.size())
- status = true;
- }
-
- return status;
- }
-
- static public boolean equalDNs(String dn1, String dn2) {
- boolean retVal = false;
- if (isValidDN(dn1) && isValidDN(dn2)) {
- retVal = equalDNs(new DN(dn1), new DN(dn2));
- }
- return retVal;
- }
-
// returns true if dn1 completely contains dn2 or false otherwise
// contains is defined as dn2 is a parent of or is equal to dn1
// NOTE that this method is required until the ldapjdk
@@ -2021,6 +1971,125 @@ public class DSUtil {
}
}
+ private static Method isValidDN_meth = null;
+ private static Method equalDNs_str_meth = null;
+ private static Method equalDNs_dn_meth = null;
+ private static Method unEscapeRDNVal_meth = null;
+ private static Method unEscapeRDN_meth = null;
+ private static Method unEscapeDN_meth = null;
+ private static Method escapeDNVal_meth = null;
+ private static Method DNUsesLDAPv2Quoting_meth = null;
+ static {
+ try {
+ isValidDN_meth = LDAPUtil.class.getMethod("isValidDN", String.class);
+ equalDNs_str_meth = LDAPUtil.class.getMethod("equalDNs", String.class,
String.class);
+ equalDNs_dn_meth = LDAPUtil.class.getMethod("equalDNs", DN.class,
DN.class);
+ unEscapeRDNVal_meth = LDAPUtil.class.getMethod("unEscapeRDNVal",
String.class);
+ unEscapeRDN_meth = LDAPUtil.class.getMethod("unEscapeRDN", String.class);
+ unEscapeDN_meth = LDAPUtil.class.getMethod("unEscapeDN", String.class);
+ escapeDNVal_meth = LDAPUtil.class.getMethod("escapeDNVal", String.class);
+ DNUsesLDAPv2Quoting_meth = LDAPUtil.class.getMethod("DNUsesLDAPv2Quoting",
String.class);
+ } catch (SecurityException e) {
+ e.printStackTrace();
+ throw e;
+ } catch (NoSuchMethodException e) {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * Check if the string is a valid dn
+ *
+ */
+ static public boolean isValidDN (String dn){
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (isValidDN_meth != null) {
+ try {
+ return ((Boolean)isValidDN_meth.invoke(null, dn)).booleanValue();
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
+ if (dn.equals (""))
+ return true;
+
+ if (!netscape.ldap.util.DN.isDN(dn))
+ return false;
+
+ int eq = dn.indexOf('=');
+
+ return (eq > 0 && eq < dn.length () -1 );
+ }
+
+ static public boolean equalDNs(DN dn1, DN dn2) {
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (equalDNs_dn_meth != null) {
+ try {
+ return ((Boolean)equalDNs_dn_meth.invoke(null, dn1, dn2)).booleanValue();
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
+ boolean status = (dn1 == null || dn2 == null);
+ if (status) { // if at least one of the arguments is null
+ status = (dn1 == dn2); // true if both are null, false otherwise
+ return status; // short circuit
+ }
+
+ Vector thisRDNs = dn1.getRDNs();
+ Vector thatRDNs = dn2.getRDNs();
+ if (thisRDNs != null && thatRDNs != null &&
+ thisRDNs.size() == thatRDNs.size()) {
+ int ii;
+ for (ii = 0; ii < thisRDNs.size(); ++ii) {
+ RDN thisRDN = (RDN)thisRDNs.elementAt(ii);
+ RDN thatRDN = (RDN)thatRDNs.elementAt(ii);
+ if (!thisRDN.equals(thatRDN))
+ break;
+ }
+
+ // all RDNs were equal
+ if (ii == thisRDNs.size())
+ status = true;
+ }
+
+ return status;
+ }
+
+ static public boolean equalDNs(String dn1, String dn2) {
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (equalDNs_str_meth != null) {
+ try {
+ return ((Boolean)equalDNs_str_meth.invoke(null, dn1, dn2)).booleanValue();
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
+ boolean retVal = false;
+ if (isValidDN(dn1) && isValidDN(dn2)) {
+ retVal = equalDNs(new DN(dn1), new DN(dn2));
+ }
+ return retVal;
+ }
+
/**
* Returns the RDN value after unescaping any escaped characters.
* Can be a simple escape - a \ followed by any character -
@@ -2040,6 +2109,20 @@ public class DSUtil {
* @see netscape.ldap.LDAPDN#escapeRDN(java.lang.String)
*/
public static String unEscapeRDNVal(String rdnval) {
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (unEscapeRDNVal_meth != null) {
+ try {
+ return (String)unEscapeRDNVal_meth.invoke(null, rdnval);
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
StringBuffer copy = new StringBuffer();
CharacterIterator it = new StringCharacterIterator(rdnval);
for (char ch = it.first(); ch != CharacterIterator.DONE; ch = it.next()) {
@@ -2089,6 +2172,20 @@ public class DSUtil {
* @see netscape.ldap.LDAPDN#escapeRDN(java.lang.String)
*/
public static String unEscapeRDN(String rdn) {
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (unEscapeRDN_meth != null) {
+ try {
+ return (String)unEscapeRDN_meth.invoke(null, rdn);
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
RDN name = new RDN(rdn);
String[] vals = name.getValues();
if ( (vals == null) || (vals.length < 1) ) {
@@ -2123,6 +2220,20 @@ public class DSUtil {
* @return the unescaped DN or the original DN if there were errors
*/
public static String unEscapeDN(String dn) {
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (unEscapeDN_meth != null) {
+ try {
+ return (String)unEscapeDN_meth.invoke(null, dn);
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
if ((dn == null) || (dn.equals(""))) {
return dn;
}
@@ -2175,6 +2286,20 @@ public class DSUtil {
* @return the escaped string
*/
public static String escapeDNVal(String dnval) {
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (escapeDNVal_meth != null) {
+ try {
+ return (String)escapeDNVal_meth.invoke(null, dnval);
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
StringBuffer copy = new StringBuffer();
CharacterIterator it = new StringCharacterIterator(dnval);
for (char ch = it.first(); ch != CharacterIterator.DONE; ch = it.next()) {
@@ -2196,26 +2321,40 @@ public class DSUtil {
* @return true if the given string contains LDAPv2 style quoting
*/
static public boolean DNUsesLDAPv2Quoting(String dn) {
- char ESC = '\\';
- char Q = '"';
- boolean ret = false;
-
- // check dn for a even number (incl. 0) of ESC followed by Q
- if (dn == null)
- return ret;
-
- int p = dn.indexOf(Q);
- if (p >= 0)
- {
- int nESC = 0;
- for (--p; (p >= 0) && (dn.charAt(p) == ESC); --p)
- ++nESC;
- // the quote is unescaped if it is preceeded by an even
- // number of escape characters, including 0
- ret = ((nESC % 2) == 0);
- }
-
- return ret;
+ // attempt to invoke the method defined in LDAPUtil
+ // if not found, or some problem occurred, just fall through
+ // and use the default implementation of this method
+ if (DNUsesLDAPv2Quoting_meth != null) {
+ try {
+ return ((Boolean)DNUsesLDAPv2Quoting_meth.invoke(null, dn)).booleanValue();
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ }
+ }
+ char ESC = '\\';
+ char Q = '"';
+ boolean ret = false;
+
+ // check dn for a even number (incl. 0) of ESC followed by Q
+ if (dn == null)
+ return ret;
+
+ int p = dn.indexOf(Q);
+ if (p >= 0)
+ {
+ int nESC = 0;
+ for (--p; (p >= 0) && (dn.charAt(p) == ESC); --p)
+ ++nESC;
+ // the quote is unescaped if it is preceeded by an even
+ // number of escape characters, including 0
+ ret = ((nESC % 2) == 0);
+ }
+
+ return ret;
}
static public void checkForLDAPv2Quoting(String dn, JFrame frame,
diff --git a/src/com/netscape/admin/dirserv/propedit/DSEntryPanel.java
b/src/com/netscape/admin/dirserv/propedit/DSEntryPanel.java
index aff65a8..1d0193a 100644
--- a/src/com/netscape/admin/dirserv/propedit/DSEntryPanel.java
+++ b/src/com/netscape/admin/dirserv/propedit/DSEntryPanel.java
@@ -1492,6 +1492,18 @@ public class DSEntryPanel extends JPanel implements
ActionListener,
typeWithValue = true;
break;
}
+ // note: current versions of the directory
server
+ // use dn values as values of RDNs e.g.
+ // cn=dc\3Dexample\2Cdc\3Dcom,cn=mapping
tree, cn=config
+ // where dc\3Dexample\2Cdc\3Dcom is
dc=example,dc=com
+ String unescval =
DSUtil.unEscapeRDNVal(value);
+ if (DSUtil.isValidDN(unescval)) {
+ // compare as DNs
+ if (DSUtil.equalDNs(unescval,
currentValue)) {
+ typeWithValue = true;
+ break;
+ }
+ }
}
if (typeWithValue) {
continue;