View Javadoc

1   /*
2    *  Licensed to the Apache Software Foundation (ASF) under one
3    *  or more contributor license agreements.  See the NOTICE file
4    *  distributed with this work for additional information
5    *  regarding copyright ownership.  The ASF licenses this file
6    *  to you under the Apache License, Version 2.0 (the
7    *  "License"); you may not use this file except in compliance
8    *  with the License.  You may obtain a copy of the License at
9    *
10   *    http://www.apache.org/licenses/LICENSE-2.0
11   *
12   *  Unless required by applicable law or agreed to in writing,
13   *  software distributed under the License is distributed on an
14   *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   *  KIND, either express or implied.  See the License for the
16   *  specific language governing permissions and limitations
17   *  under the License.
18   *
19   */
20  package org.apache.directory.mavibot.btree;
21  
22  
23  import java.io.IOException;
24  import java.nio.ByteBuffer;
25  
26  import org.apache.directory.mavibot.btree.serializer.AbstractElementSerializer;
27  import org.apache.directory.mavibot.btree.serializer.BufferHandler;
28  import org.apache.directory.mavibot.btree.serializer.ByteArraySerializer;
29  import org.apache.directory.mavibot.btree.serializer.IntSerializer;
30  import org.apache.directory.mavibot.btree.serializer.LongSerializer;
31  import org.apache.directory.mavibot.btree.serializer.StringSerializer;
32  import org.apache.directory.mavibot.btree.util.Strings;
33  
34  
35  /**
36   * A serializer for the RevisionName object. The RevisionName will be serialized 
37   * as a long (the revision), followed by the String.
38   * 
39   * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
40   */
41  public class RevisionNameSerializer extends AbstractElementSerializer<RevisionName>
42  {
43      /**
44       * Create a new instance of a RevisionNameSerializer
45       */
46      public RevisionNameSerializer()
47      {
48          super( new RevisionNameComparator() );
49      }
50  
51  
52      /**
53       * A static method used to deserialize a RevisionName from a byte array.
54       * 
55       * @param in The byte array containing the RevisionName
56       * @return A RevisionName instance
57       */
58      public static RevisionName deserialize( byte[] in )
59      {
60          return deserialize( in, 0 );
61      }
62  
63  
64      /**
65       * A static method used to deserialize a RevisionName from a byte array.
66       * 
67       * @param in The byte array containing the RevisionName
68       * @param start the position in the byte[] we will deserialize the RevisionName from
69       * @return A RevisionName instance
70       */
71      public static RevisionName deserialize( byte[] in, int start )
72      {
73          // The buffer must be 8 bytes plus 4 bytes long (the revision is a long, and the name is a String
74          if ( ( in == null ) || ( in.length < 12 + start ) )
75          {
76              throw new RuntimeException( "Cannot extract a RevisionName from a buffer with not enough bytes" );
77          }
78  
79          long revision = LongSerializer.deserialize( in, start );
80          String name = StringSerializer.deserialize( in, 8 + start );
81  
82          RevisionName revisionName = new RevisionName( revision, name );
83  
84          return revisionName;
85      }
86  
87  
88      /**
89       * A static method used to deserialize a RevisionName from a byte array.
90       * 
91       * @param in The byte array containing the RevisionName
92       * @return A RevisionName instance
93       */
94      public RevisionName fromBytes( byte[] in )
95      {
96          return deserialize( in, 0 );
97      }
98  
99  
100     /**
101      * A static method used to deserialize a RevisionName from a byte array.
102      * 
103      * @param in The byte array containing the RevisionName
104      * @param start the position in the byte[] we will deserialize the RevisionName from
105      * @return A RevisionName instance
106      */
107     public RevisionName fromBytes( byte[] in, int start )
108     {
109         // The buffer must be 8 bytes plus 4 bytes long (the revision is a long, and the name is a String
110         if ( ( in == null ) || ( in.length < 12 + start ) )
111         {
112             throw new RuntimeException( "Cannot extract a RevisionName from a buffer with not enough bytes" );
113         }
114 
115         long revision = LongSerializer.deserialize( in, start );
116         String name = StringSerializer.deserialize( in, 8 + start );
117 
118         RevisionName revisionName = new RevisionName( revision, name );
119 
120         return revisionName;
121     }
122 
123 
124     /**
125      * {@inheritDoc}
126      */
127     @Override
128     public byte[] serialize( RevisionName revisionName )
129     {
130         if ( revisionName == null )
131         {
132             throw new RuntimeException( "The revisionName instance should not be null " );
133         }
134 
135         byte[] result = null;
136 
137         if ( revisionName.getName() != null )
138         {
139             byte[] stringBytes = Strings.getBytesUtf8( revisionName.getName() );
140             int stringLen = stringBytes.length;
141             result = new byte[8 + 4 + stringBytes.length];
142             LongSerializer.serialize( result, 0, revisionName.getRevision() );
143 
144             if ( stringLen > 0 )
145             {
146                 ByteArraySerializer.serialize( result, 8, stringBytes );
147             }
148         }
149         else
150         {
151             result = new byte[8 + 4];
152             LongSerializer.serialize( result, 0, revisionName.getRevision() );
153             StringSerializer.serialize( result, 8, null );
154         }
155 
156         return result;
157     }
158 
159 
160     /**
161      * Serialize a RevisionName
162      * 
163      * @param buffer the Buffer that will contain the serialized value
164      * @param start the position in the buffer we will store the serialized RevisionName
165      * @param value the value to serialize
166      * @return The byte[] containing the serialized RevisionName
167      */
168     public static byte[] serialize( byte[] buffer, int start, RevisionName revisionName )
169     {
170         if ( revisionName.getName() != null )
171         {
172             byte[] stringBytes = Strings.getBytesUtf8( revisionName.getName() );
173             int stringLen = stringBytes.length;
174             LongSerializer.serialize( buffer, start, revisionName.getRevision() );
175             IntSerializer.serialize( buffer, 8 + start, stringLen );
176             ByteArraySerializer.serialize( buffer, 12 + start, stringBytes );
177         }
178         else
179         {
180             LongSerializer.serialize( buffer, start, revisionName.getRevision() );
181             StringSerializer.serialize( buffer, 8, null );
182         }
183 
184         return buffer;
185     }
186 
187 
188     /**
189      * {@inheritDoc}
190      */
191     @Override
192     public RevisionName deserialize( BufferHandler bufferHandler ) throws IOException
193     {
194         byte[] revisionBytes = bufferHandler.read( 8 );
195         long revision = LongSerializer.deserialize( revisionBytes );
196 
197         byte[] lengthBytes = bufferHandler.read( 4 );
198 
199         int len = IntSerializer.deserialize( lengthBytes );
200 
201         switch ( len )
202         {
203             case 0:
204                 return new RevisionName( revision, "" );
205 
206             case -1:
207                 return new RevisionName( revision, null );
208 
209             default:
210                 byte[] nameBytes = bufferHandler.read( len );
211 
212                 return new RevisionName( revision, Strings.utf8ToString( nameBytes ) );
213         }
214     }
215 
216 
217     /**
218      * {@inheritDoc}
219      */
220     @Override
221     public RevisionName deserialize( ByteBuffer buffer ) throws IOException
222     {
223         // The revision
224         long revision = buffer.getLong();
225 
226         // The name's length
227         int len = buffer.getInt();
228 
229         switch ( len )
230         {
231             case 0:
232                 return new RevisionName( revision, "" );
233 
234             case -1:
235                 return new RevisionName( revision, null );
236 
237             default:
238                 byte[] nameBytes = new byte[len];
239                 buffer.get( nameBytes );
240 
241                 return new RevisionName( revision, Strings.utf8ToString( nameBytes ) );
242         }
243     }
244 }