001/*
002 *  Licensed to the Apache Software Foundation (ASF) under one
003 *  or more contributor license agreements.  See the NOTICE file
004 *  distributed with this work for additional information
005 *  regarding copyright ownership.  The ASF licenses this file
006 *  to you under the Apache License, Version 2.0 (the
007 *  "License"); you may not use this file except in compliance
008 *  with the License.  You may obtain a copy of the License at
009 *  
010 *    http://www.apache.org/licenses/LICENSE-2.0
011 *  
012 *  Unless required by applicable law or agreed to in writing,
013 *  software distributed under the License is distributed on an
014 *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015 *  KIND, either express or implied.  See the License for the
016 *  specific language governing permissions and limitations
017 *  under the License. 
018 *  
019 */
020package org.apache.directory.api.dsmlv2.request;
021
022
023import org.apache.directory.api.dsmlv2.ParserUtils;
024import org.apache.directory.api.ldap.codec.api.LdapApiService;
025import org.apache.directory.api.ldap.model.entry.Attribute;
026import org.apache.directory.api.ldap.model.entry.DefaultAttribute;
027import org.apache.directory.api.ldap.model.entry.Entry;
028import org.apache.directory.api.ldap.model.entry.Value;
029import org.apache.directory.api.ldap.model.exception.LdapException;
030import org.apache.directory.api.ldap.model.message.AddRequest;
031import org.apache.directory.api.ldap.model.message.AddRequestImpl;
032import org.apache.directory.api.ldap.model.message.AddResponse;
033import org.apache.directory.api.ldap.model.message.Control;
034import org.apache.directory.api.ldap.model.message.MessageTypeEnum;
035import org.apache.directory.api.ldap.model.name.Dn;
036import org.dom4j.Element;
037import org.dom4j.Namespace;
038import org.dom4j.QName;
039
040
041/**
042 * DSML Decorator for AddRequest
043 *
044 * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
045 */
046public class AddRequestDsml
047    extends AbstractResultResponseRequestDsml<AddRequest, AddResponse>
048    implements AddRequest
049{
050
051    /** The current attribute being decoded */
052    private Attribute currentAttribute;
053
054
055    /**
056     * Creates a new getDecoratedMessage() of AddRequestDsml.
057     */
058    public AddRequestDsml( LdapApiService codec )
059    {
060        super( codec, new AddRequestImpl() );
061    }
062
063
064    /**
065     * Creates a new getDecoratedMessage() of AddRequestDsml.
066    *
067    * @param ldapMessage
068    *      the message to decorate
069    */
070    public AddRequestDsml( LdapApiService codec, AddRequest ldapMessage )
071    {
072        super( codec, ldapMessage );
073    }
074
075
076    /**
077     * Create a new attributeValue
078     * 
079     * @param type The attribute's name (called 'type' in the grammar)
080     */
081    public void addAttributeType( String type ) throws LdapException
082    {
083        // do not create a new attribute if we have seen this attributeType before
084        if ( getDecorated().getEntry().get( type ) != null )
085        {
086            currentAttribute = getDecorated().getEntry().get( type );
087            return;
088        }
089
090        // fix this to use AttributeImpl(type.getString().toLowerCase())
091        currentAttribute = new DefaultAttribute( type );
092        getDecorated().getEntry().put( currentAttribute );
093    }
094
095
096    /**
097     * @return Returns the currentAttribute type.
098     */
099    public String getCurrentAttributeType()
100    {
101        return currentAttribute.getId();
102    }
103
104
105    /**
106     * Add a new value to the current attribute
107     * 
108     * @param value The value to add
109     */
110    public void addAttributeValue( String value ) throws LdapException
111    {
112        currentAttribute.add( value );
113    }
114
115
116    /**
117     * Add a new value to the current attribute
118     * 
119     * @param value The value to add
120     */
121    public void addAttributeValue( Value<?> value ) throws LdapException
122    {
123        currentAttribute.add( value );
124    }
125
126
127    /**
128     * Add a new value to the current attribute
129     * 
130     * @param value The value to add
131     */
132    public void addAttributeValue( byte[] value ) throws LdapException
133    {
134        currentAttribute.add( value );
135    }
136
137
138    /**
139     * {@inheritDoc}
140     */
141    public MessageTypeEnum getType()
142    {
143        return getDecorated().getType();
144    }
145
146
147    /**
148     * {@inheritDoc}
149     */
150    public Element toDsml( Element root )
151    {
152        Element element = super.toDsml( root );
153
154        // Dn
155        if ( getDecorated().getEntry() != null )
156        {
157            element.addAttribute( "dn", getDecorated().getEntry().getDn().getName() );
158        }
159
160        // Attributes
161        Entry entry = getDecorated().getEntry();
162        if ( entry != null )
163        {
164            for ( Attribute attribute : entry )
165            {
166                Element attributeElement = element.addElement( "attr" );
167                attributeElement.addAttribute( "name", attribute.getId() );
168                // Looping on Values
169                for ( Value<?> value : attribute )
170                {
171                    if ( ParserUtils.needsBase64Encoding( value.getValue() ) )
172                    {
173                        Namespace xsdNamespace = new Namespace( "xsd", ParserUtils.XML_SCHEMA_URI );
174                        Namespace xsiNamespace = new Namespace( "xsi", ParserUtils.XML_SCHEMA_INSTANCE_URI );
175                        attributeElement.getDocument().getRootElement().add( xsdNamespace );
176                        attributeElement.getDocument().getRootElement().add( xsiNamespace );
177
178                        Element valueElement = attributeElement.addElement( "value" ).addText(
179                            ParserUtils.base64Encode( value.getValue() ) );
180                        valueElement
181                            .addAttribute( new QName( "type", xsiNamespace ), "xsd:" + ParserUtils.BASE64BINARY );
182                    }
183                    else
184                    {
185                        attributeElement.addElement( "value" ).addText( value.getString() );
186                    }
187                }
188            }
189        }
190
191        return element;
192    }
193
194
195    /**
196     * Initialize the Entry.
197     */
198    public void initEntry()
199    {
200    }
201
202
203    /**
204     * Get the entry with its attributes.
205     * 
206     * @return Returns the entry.
207     */
208    public Entry getEntry()
209    {
210        return getDecorated().getEntry();
211    }
212
213
214    /**
215     * Add a new value to the current attribute
216     * 
217     * @param value The value to be added
218     */
219    public void addAttributeValue( Object value ) throws LdapException
220    {
221        if ( value instanceof Value<?> )
222        {
223            ( ( AddRequestDsml ) getDecorated() ).addAttributeValue( ( Value<?> ) value );
224        }
225        else if ( value instanceof String )
226        {
227            ( ( AddRequestDsml ) getDecorated() ).addAttributeValue( ( String ) value );
228        }
229        else if ( value instanceof byte[] )
230        {
231            ( ( AddRequestDsml ) getDecorated() ).addAttributeValue( ( byte[] ) value );
232        }
233    }
234
235
236    /**
237     * Get the added Dn
238     * 
239     * @return Returns the entry Dn.
240     */
241    public Dn getEntryDn()
242    {
243        return getDecorated().getEntryDn();
244    }
245
246
247    /**
248     * {@inheritDoc}
249     */
250    public AddRequest setEntryDn( Dn entryDn )
251    {
252        getDecorated().setEntryDn( entryDn );
253
254        return this;
255    }
256
257
258    /**
259     * {@inheritDoc}
260     */
261    public AddRequest setEntry( Entry entry )
262    {
263        getDecorated().setEntry( entry );
264
265        return this;
266    }
267
268
269    /**
270     * {@inheritDoc}
271     */
272    public AddRequest setMessageId( int messageId )
273    {
274        super.setMessageId( messageId );
275
276        return this;
277    }
278
279
280    /**
281     * {@inheritDoc}
282     */
283    public AddRequest addControl( Control control )
284    {
285        return ( AddRequest ) super.addControl( control );
286    }
287
288
289    /**
290     * {@inheritDoc}
291     */
292    public AddRequest addAllControls( Control[] controls )
293    {
294        return ( AddRequest ) super.addAllControls( controls );
295    }
296
297
298    /**
299     * {@inheritDoc}
300     */
301    public AddRequest removeControl( Control control )
302    {
303        return ( AddRequest ) super.removeControl( control );
304    }
305
306
307    /**
308     * {@inheritDoc}
309     */
310    public MessageTypeEnum getResponseType()
311    {
312        return getDecorated().getResponseType();
313    }
314}