1 16 package scriptella.driver.ldap; 17 18 import scriptella.core.EtlCancelledException; 19 import scriptella.driver.ldap.ldif.Entry; 20 import scriptella.driver.ldap.ldif.LdifParseException; 21 import scriptella.driver.ldap.ldif.LdifReader; 22 import scriptella.driver.ldap.ldif.SubstitutingLineReader; 23 import scriptella.spi.AbstractConnection; 24 import scriptella.spi.ParametersCallback; 25 26 import javax.naming.CompoundName ; 27 import javax.naming.Name ; 28 import javax.naming.NamingException ; 29 import javax.naming.directory.Attributes ; 30 import javax.naming.directory.DirContext ; 31 import javax.naming.directory.ModificationItem ; 32 import java.io.IOException ; 33 import java.io.InputStream ; 34 import java.io.Reader ; 35 import java.util.List ; 36 import java.util.Properties ; 37 import java.util.logging.Level ; 38 import java.util.logging.Logger ; 39 40 46 public class LdifScript { 47 private static final Logger LOG = Logger.getLogger(LdifScript.class.getName()); 48 static final Properties DN_SYNTAX = new Properties (); 50 51 static { 52 DN_SYNTAX.setProperty("jndi.syntax.direction", "right_to_left"); 53 DN_SYNTAX.setProperty("jndi.syntax.separator", ","); 54 DN_SYNTAX.setProperty("jndi.syntax.ignorecase", "true"); 55 DN_SYNTAX.setProperty("jndi.syntax.trimblanks", "true"); 56 } 57 58 private final LdapConnection connection; 59 60 public LdifScript(LdapConnection connection) { 61 if (connection == null) { 62 throw new IllegalArgumentException ("Connection cannot be null"); 63 } 64 this.connection = connection; 65 } 66 67 68 74 public void execute(Reader reader, DirContext ctx, ParametersCallback parameters) throws LdapProviderException { 75 if (reader == null) { 76 throw new IllegalArgumentException ("Reader cannot be null"); 77 } 78 if (ctx == null) { 79 throw new IllegalArgumentException ("DirContext cannot be null"); 80 } 81 if (parameters == null) { 82 throw new IllegalArgumentException ("Parameters cannot be null"); 83 } 84 SubstitutingLineReader in = new SubstitutingLineReader(reader, parameters); 85 AbstractConnection.StatementCounter counter = connection.getStatementCounter(); 86 try { 87 in.trackLines(); 88 for (LdifIterator it = new LdifIterator(in); it.hasNext(); in.trackLines()) { 89 EtlCancelledException.checkEtlCancelled(); 90 Entry e = it.next(); 91 if (isReadonly()) { 92 LOG.info("Readonly Mode - "+e+" has been skipped."); 93 } else { 94 modify(ctx, e); 95 } 96 counter.statements++; 97 } 98 } catch (LdifParseException e) { 99 if (e.getErrorStatement() == null) { 100 e.setErrorStatement(in.getTrackedLines()); 101 } 102 throw e; 103 } catch (NamingException e) { 104 LdapProviderException ex = new LdapProviderException("Failed to execute LDIF entry", e); 105 ex.setErrorStatement(in.getTrackedLines()); 106 throw ex; 107 } 108 } 109 110 117 static void modify(DirContext ctx, final Entry e) throws NamingException { 118 if (LOG.isLoggable(Level.FINE)) { 119 LOG.fine("Processing " + e); 120 } 121 Attributes atts = e.getAttributes(); 122 final String rootDn = ctx.getNameInNamespace(); 123 if (atts != null) { ctx.createSubcontext(getRelativeDN(rootDn, e.getDn()), e.getAttributes()); 125 } else if (e.isChangeDelete()) { 126 ctx.destroySubcontext(getRelativeDN(rootDn, e.getDn())); 127 } else if (e.isChangeModDn() || e.isChangeModRdn()) { 128 Name newRdn; 129 if (e.getNewSuperior() != null) { newRdn = getRelativeDN(rootDn, e.getNewSuperior()); 131 } else { newRdn = getRelativeDN(rootDn, e.getDn()); 133 newRdn.remove(newRdn.size() - 1); 134 } 135 newRdn.add(e.getNewRdn()); 136 ctx.addToEnvironment("java.naming.ldap.deleteRDN", String.valueOf(e.isDeleteOldRdn())); 137 ctx.rename(getRelativeDN(rootDn, e.getDn()), newRdn); 138 ctx.removeFromEnvironment("java.naming.ldap.deleteRDN"); 140 } else { 141 List <ModificationItem > items = e.getModificationItems(); 142 ctx.modifyAttributes(getRelativeDN(rootDn, e.getDn()), 143 items.toArray(new ModificationItem [items.size()])); 144 } 145 } 146 147 148 153 static Name getRelativeDN(final String rootDn, final String dn) throws NamingException { 154 CompoundName root = new CompoundName (rootDn, DN_SYNTAX); 155 CompoundName entry = new CompoundName (dn, DN_SYNTAX); 156 if (!entry.startsWith(root)) { 157 throw new NamingException ("Dn " + dn + " is not from root DN " + rootDn); 158 } 159 return entry.getSuffix(root.size()); 160 } 161 162 165 protected Long getMaxFileLength() { 166 return connection == null ? null : connection.getMaxFileLength(); 167 } 168 169 protected boolean isReadonly() { 170 return connection != null && connection.isReadonly(); 171 } 172 173 private class LdifIterator extends LdifReader { 174 175 public LdifIterator(Reader in) { 176 super(in); 177 final Long maxFileLength = getMaxFileLength(); 178 if (maxFileLength != null) { 179 setSizeLimit(maxFileLength * 1024); 180 } 181 } 182 183 protected InputStream getUriStream(String uri) throws IOException { 184 return connection.getDriversContext().resolve(uri).openStream(); 185 } 186 } 187 188 } 189 | Popular Tags |