1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 package org.apache.directory.ldap.client.api;
22
23
24 import java.io.IOException;
25 import java.util.concurrent.TimeUnit;
26
27 import org.apache.directory.api.i18n.I18n;
28 import org.apache.directory.api.ldap.model.constants.Loggers;
29 import org.apache.directory.api.ldap.model.cursor.AbstractCursor;
30 import org.apache.directory.api.ldap.model.cursor.CursorException;
31 import org.apache.directory.api.ldap.model.cursor.InvalidCursorPositionException;
32 import org.apache.directory.api.ldap.model.cursor.SearchCursor;
33 import org.apache.directory.api.ldap.model.entry.Entry;
34 import org.apache.directory.api.ldap.model.exception.LdapException;
35 import org.apache.directory.api.ldap.model.exception.LdapReferralException;
36 import org.apache.directory.api.ldap.model.message.IntermediateResponse;
37 import org.apache.directory.api.ldap.model.message.Referral;
38 import org.apache.directory.api.ldap.model.message.Response;
39 import org.apache.directory.api.ldap.model.message.SearchResultDone;
40 import org.apache.directory.api.ldap.model.message.SearchResultEntry;
41 import org.apache.directory.api.ldap.model.message.SearchResultReference;
42 import org.apache.directory.ldap.client.api.exception.LdapConnectionTimeOutException;
43 import org.apache.directory.ldap.client.api.future.SearchFuture;
44 import org.slf4j.Logger;
45 import org.slf4j.LoggerFactory;
46
47
48
49
50
51
52
53
54
55 public class SearchCursorImpl extends AbstractCursor<Response> implements SearchCursor
56 {
57
58 private static final Logger LOG_CURSOR = LoggerFactory.getLogger( Loggers.CURSOR_LOG.getName() );
59
60
61 private SearchFuture future;
62
63
64 private long timeout;
65
66
67 private TimeUnit timeUnit;
68
69
70 private Response response;
71
72
73 private boolean done;
74
75
76 private SearchResultDone searchDoneResp;
77
78
79
80
81
82
83
84
85
86 public SearchCursorImpl( SearchFuture future, long timeout, TimeUnit timeUnit )
87 {
88 if ( LOG_CURSOR.isDebugEnabled() )
89 {
90 LOG_CURSOR.debug( I18n.msg( I18n.MSG_04170_CREATING_SEARCH_CURSOR, this ) );
91 }
92
93 this.future = future;
94 this.timeout = timeout;
95 this.timeUnit = timeUnit;
96 }
97
98
99
100
101
102 @Override
103 public boolean next() throws LdapException, CursorException
104 {
105 if ( done )
106 {
107 return false;
108 }
109
110 try
111 {
112 if ( future.isCancelled() )
113 {
114 response = null;
115 done = true;
116 return false;
117 }
118
119 response = future.get( timeout, timeUnit );
120 }
121 catch ( Exception e )
122 {
123 LdapException ldapException = new LdapException( LdapNetworkConnection.NO_RESPONSE_ERROR, e );
124
125
126 if ( !future.isCancelled() )
127 {
128 future.cancel( true );
129 }
130
131
132 try
133 {
134 close( ldapException );
135 }
136 catch ( IOException ioe )
137 {
138 throw new LdapException( ioe.getMessage(), ioe );
139 }
140
141 throw ldapException;
142 }
143
144 if ( response == null )
145 {
146 future.cancel( true );
147
148 throw new LdapConnectionTimeOutException( LdapNetworkConnection.TIME_OUT_ERROR );
149 }
150
151 done = response instanceof SearchResultDone;
152
153 if ( done )
154 {
155 searchDoneResp = ( SearchResultDone ) response;
156 response = null;
157 }
158
159 return !done;
160 }
161
162
163
164
165
166 @Override
167 public Response get() throws InvalidCursorPositionException
168 {
169 if ( !available() )
170 {
171 throw new InvalidCursorPositionException();
172 }
173
174 return response;
175 }
176
177
178
179
180
181 @Override
182 public SearchResultDone getSearchResultDone()
183 {
184 return searchDoneResp;
185 }
186
187
188
189
190
191 @Override
192 public boolean available()
193 {
194 return response != null;
195 }
196
197
198
199
200
201 @Override
202 public void close() throws IOException
203 {
204 if ( LOG_CURSOR.isDebugEnabled() )
205 {
206 LOG_CURSOR.debug( I18n.msg( I18n.MSG_04171_CLOSING_SEARCH_CURSOR, this ) );
207 }
208
209 close( null );
210 }
211
212
213
214
215
216 @Override
217 public void close( Exception cause ) throws IOException
218 {
219 if ( LOG_CURSOR.isDebugEnabled() )
220 {
221 LOG_CURSOR.debug( I18n.msg( I18n.MSG_04171_CLOSING_SEARCH_CURSOR, this ) );
222 }
223
224 if ( done )
225 {
226 super.close();
227 return;
228 }
229
230 if ( !future.isCancelled() )
231 {
232 future.cancel( true );
233 }
234
235 if ( cause != null )
236 {
237 super.close( cause );
238 }
239 else
240 {
241 super.close();
242 }
243 }
244
245
246
247
248
249
250
251
252 @Override
253 public void after( Response element ) throws LdapException, CursorException
254 {
255 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
256 .concat( "." ).concat( "after( Response element )" ) ) );
257 }
258
259
260
261
262
263
264 @Override
265 public void afterLast() throws LdapException, CursorException
266 {
267 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
268 .concat( "." ).concat( "afterLast()" ) ) );
269 }
270
271
272
273
274
275
276 @Override
277 public void before( Response element ) throws LdapException, CursorException
278 {
279 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
280 .concat( "." ).concat( "before( Response element )" ) ) );
281 }
282
283
284
285
286
287
288 @Override
289 public void beforeFirst() throws LdapException, CursorException
290 {
291 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
292 .concat( "." ).concat( "beforeFirst()" ) ) );
293 }
294
295
296
297
298
299
300 @Override
301 public boolean first() throws LdapException, CursorException
302 {
303 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
304 .concat( "." ).concat( "first()" ) ) );
305 }
306
307
308
309
310
311
312 @Override
313 public boolean last() throws LdapException, CursorException
314 {
315 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
316 .concat( "." ).concat( "last()" ) ) );
317 }
318
319
320
321
322
323
324 @Override
325 public boolean previous() throws LdapException, CursorException
326 {
327 throw new UnsupportedOperationException( I18n.err( I18n.ERR_13102_UNSUPPORTED_OPERATION, getClass().getName()
328 .concat( "." ).concat( "previous()" ) ) );
329 }
330
331
332
333
334
335 @Override
336 public boolean isDone()
337 {
338 return done;
339 }
340
341
342
343
344
345 @Override
346 public boolean isReferral()
347 {
348 return response instanceof SearchResultReference;
349 }
350
351
352
353
354
355 @Override
356 public Referral getReferral() throws LdapException
357 {
358 if ( isReferral() )
359 {
360 return ( ( SearchResultReference ) response ).getReferral();
361 }
362
363 throw new LdapException();
364 }
365
366
367
368
369
370 @Override
371 public boolean isEntry()
372 {
373 return response instanceof SearchResultEntry;
374 }
375
376
377
378
379
380 @Override
381 public Entry getEntry() throws LdapException
382 {
383 if ( isEntry() )
384 {
385 return ( ( SearchResultEntry ) response ).getEntry();
386 }
387
388 if ( isReferral() )
389 {
390 Referral referral = ( ( SearchResultReference ) response ).getReferral();
391 throw new LdapReferralException( referral.getLdapUrls() );
392 }
393
394 throw new LdapException();
395 }
396
397
398
399
400
401 @Override
402 public boolean isIntermediate()
403 {
404 return response instanceof IntermediateResponse;
405 }
406
407
408
409
410
411 @Override
412 public IntermediateResponse getIntermediate() throws LdapException
413 {
414 if ( isEntry() )
415 {
416 return ( IntermediateResponse ) response;
417 }
418
419 throw new LdapException();
420 }
421 }