Index: ldap/pom.xml
===================================================================
--- ldap/pom.xml (revision 389684)
+++ ldap/pom.xml (working copy)
@@ -83,6 +83,12 @@
+ commons-io
+ commons-io
+ 1.2
+
+
+
org.apache.directory.shared
shared-asn1
${pom.version}
Index: ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifParserImpl.java
===================================================================
--- ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifParserImpl.java (revision 389684)
+++ ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifParserImpl.java (working copy)
@@ -18,9 +18,11 @@
package org.apache.directory.shared.ldap.ldif;
-import java.io.IOException;
-import java.io.StringReader;
-import java.io.BufferedReader;
+import java.io.*;
+import java.net.URL;
+import java.net.MalformedURLException;
+import java.util.regex.Pattern;
+import java.util.regex.Matcher;
import javax.naming.NamingException;
import javax.naming.directory.Attributes;
@@ -30,6 +32,7 @@
import org.apache.directory.shared.ldap.exception.LdapNamingException;
import org.apache.directory.shared.ldap.message.ResultCodeEnum;
import org.apache.directory.shared.ldap.util.Base64;
+import org.apache.commons.io.IOUtils;
/**
@@ -47,6 +50,9 @@
*/
public class LdifParserImpl implements LdifParser
{
+ public static final Pattern STRING_ENCODE_PATTERN
+ = Pattern.compile("(string_encoding=([^;]+);\\s*)?(.+)");
+
/**
* Decodes an encoded string in base64 into a byte array.
*
@@ -75,6 +81,7 @@
*/
public synchronized void parse( Attributes attributes, String ldif ) throws NamingException
{
+ boolean isImportFile = false;
boolean isBase64Encoded = false;
int lineCount = 0;
int index;
@@ -122,22 +129,24 @@
continue;
}
- // Consume next char and check if it's a colon for binary attr.
- if ( line.charAt( ++index ) == ':' )
- {
+ // Consume next char and check if it's a colon for binary attr
+ // or '<' for file inclusion
+ index++;
+ if ( line.charAt( index ) == ':' )
isBase64Encoded = true;
- }
+ else if ( line.charAt( index ) == '<' )
+ isImportFile = true;
// Advance index past whitespace to the first char of the value.
try
{
- while ( ( line.length() <= index + 1 ) && line.charAt( ++index ) == ' ' )
+ while ( ( ++index < line.length() - 1 ) && line.charAt( index ) == ' ' )
{
; // Does nothing!
}
// Capture attribute value from first char till end of line.
- attrValue = line.substring( index + 1 );
+ attrValue = line.substring( index );
}
catch ( StringIndexOutOfBoundsException e )
{
@@ -165,6 +174,72 @@
}
isBase64Encoded = false;
}
+ else if ( isImportFile && ( attrValue != null ) )
+ {
+ final URL url;
+ final Matcher matcher;
+ final String stringEncoding;
+ final String urlStr;
+ InputStream is = null;
+ StringWriter sw = null;
+ ByteArrayOutputStream bos = null;
+ final Object value;
+
+ matcher = STRING_ENCODE_PATTERN.matcher(attrValue);
+ matcher.matches();
+ stringEncoding = matcher.group(2);
+ urlStr = matcher.group(3);
+
+ try
+ {
+ url = new URL(urlStr);
+ is = url.openStream();
+ if (stringEncoding != null)
+ {
+ sw = new StringWriter(4 * 1024);
+ IOUtils.copy(is, sw, stringEncoding);
+ value = sw.toString();
+ }
+ else
+ {
+ bos = new ByteArrayOutputStream(4 * 1024);
+ IOUtils.copy(is, bos);
+ value = bos.toByteArray();
+ }
+ }
+ catch (MalformedURLException e)
+ {
+ throw new LdapNamingException( "Line " + lineCount + " [" + line
+ + "] passes malformed URL to ':<' inclusion.\n{" + ldif + "}",
+ ResultCodeEnum.OTHER );
+ }
+ catch (IOException e)
+ {
+ throw new LdapNamingException( "Line " + lineCount + " [" + line
+ + "] failed including URL passed to ':<' inclusion.\n{" + ldif + "}",
+ ResultCodeEnum.OTHER );
+ }
+ finally
+ {
+ if (is != null)
+ try { is.close(); } catch (IOException e) {}
+ if (sw != null)
+ try { sw.close(); } catch (IOException e) {}
+ if (bos != null)
+ try { bos.close(); } catch (IOException e) {}
+ }
+
+ if ( attributes.get( attrName ) == null )
+ {
+ attributes.put( attrName, value );
+ }
+ else
+ {
+ Attribute attribute = attributes.get( attrName );
+ attribute.add( value );
+ }
+ isImportFile = false;
+ }
else
{
if ( attributes.get( attrName ) == null )
Index: ldap/src/test/resources/test_inclusion.ldif
===================================================================
--- ldap/src/test/resources/test_inclusion.ldif (revision 0)
+++ ldap/src/test/resources/test_inclusion.ldif (revision 0)
@@ -0,0 +1,6 @@
+# attribute is stored as byte[]
+httpurl:< http://isis/public/hopno02/jx.txt
+# attribute is stored as byte[]
+fileurl:< file:///D:/src/ad/shared/ldap/src/test/resources/test_ldif_inclusion.txt
+# attribute is stored as UTF8 encoded String
+strfileurl:< string_encoding=UTF8;file:///D:/src/ad/shared/ldap/src/test/resources/test_ldif_inclusion.txt
Index: ldap/src/test/resources/test_ldif_inclusion.txt
===================================================================
--- ldap/src/test/resources/test_ldif_inclusion.txt (revision 0)
+++ ldap/src/test/resources/test_ldif_inclusion.txt (revision 0)
@@ -0,0 +1,4 @@
+
+multiple
+lines
+
\ No newline at end of file