1package eu.siacs.conversations.crypto.sasl;
2
3import java.util.ArrayList;
4import java.util.Arrays;
5import java.util.Iterator;
6import java.util.List;
7import java.util.NoSuchElementException;
8
9/** A tokenizer for GS2 header strings */
10public final class Tokenizer implements Iterator<String>, Iterable<String> {
11 private final List<String> parts;
12 private int index;
13
14 public Tokenizer(final byte[] challenge) {
15 final String challengeString = new String(challenge);
16 parts = new ArrayList<>(Arrays.asList(challengeString.split(",")));
17 // Trim parts.
18 for (int i = 0; i < parts.size(); i++) {
19 parts.set(i, parts.get(i).trim());
20 }
21 index = 0;
22 }
23
24 /**
25 * Returns true if there is at least one more element, false otherwise.
26 *
27 * @see #next
28 */
29 @Override
30 public boolean hasNext() {
31 return parts.size() != index + 1;
32 }
33
34 /**
35 * Returns the next object and advances the iterator.
36 *
37 * @return the next object.
38 * @throws java.util.NoSuchElementException if there are no more elements.
39 * @see #hasNext
40 */
41 @Override
42 public String next() {
43 if (hasNext()) {
44 return parts.get(index++);
45 } else {
46 throw new NoSuchElementException("No such element. Size is: " + parts.size());
47 }
48 }
49
50 /**
51 * Removes the last object returned by {@code next} from the collection. This method can only be
52 * called once between each call to {@code next}.
53 *
54 * @throws UnsupportedOperationException if removing is not supported by the collection being
55 * iterated.
56 * @throws IllegalStateException if {@code next} has not been called, or {@code remove} has
57 * already been called after the last call to {@code next}.
58 */
59 @Override
60 public void remove() {
61 if (index <= 0) {
62 throw new IllegalStateException(
63 "You can't delete an element before first next() method call");
64 }
65 parts.remove(--index);
66 }
67
68 /**
69 * Returns an {@link java.util.Iterator} for the elements in this object.
70 *
71 * @return An {@code Iterator} instance.
72 */
73 @Override
74 public Iterator<String> iterator() {
75 return parts.iterator();
76 }
77}