Decode dictionary entry arrays as dictionaries.
Change-Id: If31659887dcd2d219d421f78e50cdeb1be3709a9
diff --git a/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Decoder.java b/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Decoder.java
index 8297d79..33b0480 100644
--- a/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Decoder.java
+++ b/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Decoder.java
@@ -198,6 +198,7 @@
* <li>{@link Optional} (a GVariant {@code Maybe} type)
* <li>{@link List} (a GVariant array)
* <li>{@code Object[]} (a GVariant structure)
+ * <li>{@link java.util.Map} (a dictionary)
* <li>{@link java.util.Map.Entry} (a dictionary entry)
* <li>{@link Variant} (a nested variant)
* </ul>
diff --git a/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Signature.java b/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Signature.java
index 6a4d01d..c697730 100644
--- a/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Signature.java
+++ b/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Signature.java
@@ -91,23 +91,37 @@
case 's', 'o', 'g' -> Decoder.ofString(StandardCharsets.UTF_8);
case 'v' -> Decoder.ofVariant();
case 'm' -> Decoder.ofMaybe(parseSignature(signature));
- case 'a' -> Decoder.ofArray(parseSignature(signature));
case '(' -> Decoder.ofStructure(parseTupleTypes(signature).toArray(new Decoder<?>[0]));
- case '{' -> {
- var tupleTypes = parseTupleTypes(signature);
- if (tupleTypes.size() != 2) {
- throw new ParseException(
- String.format(
- "dictionary entry type with %d components, expected 2", tupleTypes.size()),
- signature.position());
+ case 'a' -> {
+ char elementC = (char) signature.get(signature.position());
+ if (elementC == '{') {
+ signature.get();
+ List<Decoder<?>> entryTypes = parseDictionaryEntryTypes(signature);
+ yield Decoder.ofDictionary(entryTypes.get(0), entryTypes.get(1));
+ } else {
+ yield Decoder.ofArray(parseSignature(signature));
}
- yield Decoder.ofDictionaryEntry(tupleTypes.get(0), tupleTypes.get(1));
+ }
+ case '{' -> {
+ List<Decoder<?>> entryTypes = parseDictionaryEntryTypes(signature);
+ yield Decoder.ofDictionaryEntry(entryTypes.get(0), entryTypes.get(1));
}
default -> throw new ParseException(
String.format("encountered unknown signature byte '%c'", c), signature.position());
};
}
+ private static List<Decoder<?>> parseDictionaryEntryTypes(ByteBuffer signature)
+ throws ParseException {
+ var tupleTypes = parseTupleTypes(signature);
+ if (tupleTypes.size() != 2) {
+ throw new ParseException(
+ String.format("dictionary entry type with %d components, expected 2", tupleTypes.size()),
+ signature.position());
+ }
+ return tupleTypes;
+ }
+
private static List<Decoder<?>> parseTupleTypes(ByteBuffer signature) throws ParseException {
List<Decoder<?>> decoders = new ArrayList<>();
diff --git a/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Variant.java b/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Variant.java
index 34d3945..d9e13dd 100644
--- a/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Variant.java
+++ b/jgvariant-core/src/main/java/eu/mulk/jgvariant/core/Variant.java
@@ -18,6 +18,7 @@
* <li>{@link java.util.Optional} (a GVariant {@code Maybe} type)
* <li>{@link java.util.List} (a GVariant array)
* <li>{@code Object[]} (a GVariant structure)
+ * <li>{@link java.util.Map} (a dictionary)
* <li>{@link java.util.Map.Entry} (a dictionary entry)
* <li>{@link Variant} (a nested variant)
* </ul>