Skip to content

Commit c9d3396

Browse files
authored
Merge pull request #140 from filip26/feat/v1-decoder
V1.0 decoder + URIs
2 parents d057425 + d415a71 commit c9d3396

File tree

6 files changed

+131
-33
lines changed

6 files changed

+131
-33
lines changed

README.md

Lines changed: 61 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,6 @@
66

77
Iridium CBOR-LD is a Java implementation of [CBOR-LD 1.0](https://json-ld.github.io/cbor-ld-spec/), a compact binary format for Linked Data.
88

9-
---
10-
119
## ✨ Features
1210

1311
- 🔄 Semantic compression and decompression
@@ -35,19 +33,14 @@ Iridium CBOR-LD is a Java implementation of [CBOR-LD 1.0](https://json-ld.github
3533
```javascript
3634
// create an encoder builder initialized with default values
3735
var encoder = CborLd.createEncoder()
36+
// terms dictionary (optional)
37+
.dictionary(dictionary)
3838
// use bundled static contexts (true by default)
3939
.useBundledContexts(true)
4040
// loader (optional)
4141
.loader(...)
42-
// custom terms dictionary (optional)
43-
.dictionary(customDictionary)
4442
// create a new encoder instance
4543
.build();
46-
47-
// create barcodes encoder builder
48-
var encoder = CborLd.createEncoder(BarcodesConfig.INSTANCE)
49-
// ... customize
50-
.build()
5144

5245
// encode a document
5346
byte[] encoded = encoder.encode(document);
@@ -58,37 +51,82 @@ byte[] encoded = encoder.encode(document);
5851
```javascript
5952
// create a decoder builder initialized with default values
6053
var decoder = CborLd.createDecoder()
54+
// terms dictionaries (optional)
55+
.dictionary(dictionary1);
56+
.dictionary(dictionary2);
57+
// ...
6158
// use bundled static contexts (true by default)
6259
.useBundledContexts(true)
6360
// loader (optional)
6461
.loader(...)
65-
// add custom terms dictionary (optional)
66-
.dictionary(customDictionary);
6762
// create a new decoder instance
6863
.build();
69-
70-
// create barcodes decoder builder
71-
var decoder = CborLd.createDecoder(BarcodesConfig.INSTANCE)
72-
// ... customize
73-
.build()
74-
64+
7565
// decode
7666
document = decoder.decode(encoded);
7767
```
7868

69+
### Dictionary
70+
71+
It’s highly recommended to use dictionaries to maximize the compression ratio. A dictionary consists of terms and the codes they are encoded to. The dictionary code is preserved in the encoded CBOR-LD, but the decoder must have the same dictionary enabled. See the [W3C CBOR-LD Registry for examples](https://json-ld.github.io/cbor-ld-spec/#registry).
72+
73+
A dictionary should contain terms that are not present in contexts, such as the context URIs themselves, custom common values bound to types, and custom common URIs.
74+
75+
```javascript
76+
// build a new dictionary
77+
var dictionary = DocumentDictionaryBuilder
78+
.create(DICTIONARY_CODE)
79+
.context("https://www.w3.org/ns/credentials/v2", 1)
80+
.context("https://w3id.org/vc-barcodes/v1", 2)
81+
.type("https://w3id.org/security#cryptosuiteString",
82+
DictionaryBuilder.create()
83+
.set("ecdsa-rdfc-2019", 1)
84+
.set("ecdsa-sd-2023", 2)
85+
.set("eddsa-rdfc-2022", 3)
86+
.set("ecdsa-xi-2023", 4))
87+
.uri("did:key:zDnaeWjKfs1ob9QcgasjYSPEMkwq31hmvSAWPVAgnrt1e9GKj", 1)
88+
.uri("did:key:zDnaeWjKfs1ob9QcgasjYSPEMkwq31hmvSAWPVAgnrt1e9GKj#zDnaeWjKfs1ob9QcgasjYSPEMkwq31hmvSAWPVAgnrt1e9GKj", 2)
89+
.uri("https://sandbox.platform.veres.dev/statuses/z19rJ4oGrbFCqf3cNTVDHSbNd/status-lists", 3)
90+
.uri("did:key:zDnaeZSD9XcuULaS8qmgDUa6TMg2QjF9xABnZK42awDH3BEzj", 4)
91+
.build();
92+
93+
// use with encoder
94+
var encoder = CborLd.createEncoder()
95+
.dictionary(dictionary)
96+
.loader(...)
97+
// customize
98+
.build();
99+
100+
// use with decoder, please note you can register multiple dictionaries
101+
var decoder = CborLd.createDecoder()
102+
.dictionary(dictionary)
103+
.loader(...)
104+
// customize
105+
.build();
106+
107+
```
108+
79109
### Backward Compatibility
80110

81111
```javascript
82-
// Iridium < v0.2.0
83-
CborLd.create[Encoder|Decoder](V05Config.INSTANCE)
112+
// CBOR-LD v0.5
113+
CborLd.createEncoder(CborLdVersion.V05)
84114
// ... customize
85115
.build();
86-
87-
// Iridium < v0.2.0, @digitalbazaar/cborld compatibility
88-
CborLd.create[Encoder|Decoder](V05Config.INSTANCE)
89-
.compactArrays(false)
116+
117+
// CBOR-LD v0.6
118+
CborLd.createEncoder(CborLdVersion.V06)
90119
// ... customize
91120
.build();
121+
122+
// Multi-Decoder
123+
CborLd.createDecoder(CborLdVersion.V1, CborLdVersion.V06, CborLdVersion.V05)
124+
// sets dictionary for v1
125+
.dictionary(dictionary)
126+
// sets dictionary for v0.6
127+
.dictionary(CborLdVersion.V06, dictionary)
128+
// ... customize
129+
.build();
92130
```
93131

94132

src/main/java/com/apicatalog/cborld/config/ConfigV1.java

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,6 @@
2323
import com.apicatalog.cborld.encoder.EncoderConfig;
2424
import com.apicatalog.cborld.encoder.value.ContextValueEncoder;
2525
import com.apicatalog.cborld.encoder.value.CustomTypeValueEncoder;
26-
import com.apicatalog.cborld.encoder.value.CustomUriValueEncoder;
2726
import com.apicatalog.cborld.encoder.value.DidKeyValueEncoder;
2827
import com.apicatalog.cborld.encoder.value.IdValueEncoder;
2928
import com.apicatalog.cborld.encoder.value.MultibaseValueEncoder;
@@ -63,7 +62,6 @@ public class ConfigV1 extends BaseConfig implements EncoderConfig, DecoderConfig
6362
valueEncoders.add(new CustomTypeValueEncoder());
6463

6564
// value driven
66-
valueEncoders.add(new CustomUriValueEncoder());
6765
valueEncoders.add(new UuidValueEncoder());
6866
valueEncoders.add(new DidKeyValueEncoder());
6967

src/main/java/com/apicatalog/cborld/decoder/DecoderV1.java

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313

1414
import co.nstant.in.cbor.CborDecoder;
1515
import co.nstant.in.cbor.CborException;
16+
import co.nstant.in.cbor.model.Array;
1617
import co.nstant.in.cbor.model.DataItem;
1718
import co.nstant.in.cbor.model.MajorType;
1819
import co.nstant.in.cbor.model.UnsignedInteger;
@@ -30,11 +31,21 @@ public JsonValue decode(CborLdVersion version, byte[] encoded) throws ContextErr
3031
final ByteArrayInputStream bais = new ByteArrayInputStream(encoded);
3132
final List<DataItem> dataItems = new CborDecoder(bais).decode();
3233

33-
if (dataItems.size() != 2) {
34+
if (dataItems.size() != 1) {
35+
throw new DecoderError(Code.InvalidDocument, "The document is not CBOR-LD v1.0 document.");
36+
}
37+
38+
final DataItem dataItem = dataItems.iterator().next();
39+
40+
if (dataItem == null || dataItem.getMajorType() != MajorType.ARRAY) {
41+
throw new DecoderError(Code.InvalidDocument, "The document is not CBOR-LD v1.0 document. Must start with array of two items, but is " + dataItem + ".");
42+
}
43+
44+
if (((Array)dataItem).getDataItems().size() != 2) {
3445
throw new DecoderError(Code.InvalidDocument, "The document is not CBOR-LD v1.0 document. Must start with array of two items but size = " + dataItems.size() + ".");
3546
}
3647

37-
final Iterator<DataItem> it = dataItems.iterator();
48+
final Iterator<DataItem> it = ((Array)dataItem).getDataItems().iterator();
3849

3950
final DataItem registryId = it.next();
4051

src/main/java/com/apicatalog/cborld/decoder/value/IdValueDecoder.java

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,10 +18,16 @@ public class IdValueDecoder implements ValueDecoder {
1818
public JsonValue decode(Mapping mapping, DataItem value, String term, Collection<String> types) throws DecoderError {
1919
if (mapping != null && mapping.terms() != null && types != null && types.contains(Keywords.ID)
2020
&& MajorType.UNSIGNED_INTEGER.equals(value.getMajorType())) {
21-
final String type = mapping.terms().getValue(((UnsignedInteger) value).getValue().intValueExact());
22-
23-
if (type != null) {
24-
return Json.createValue(type);
21+
22+
int code = ((UnsignedInteger) value).getValue().intValueExact();
23+
24+
String id = mapping.uris().getValue(code);
25+
if (id == null) {
26+
id = mapping.terms().getValue(code);
27+
}
28+
29+
if (id != null) {
30+
return Json.createValue(id);
2531
}
2632
}
2733
return null;

src/main/java/com/apicatalog/cborld/encoder/value/IdValueEncoder.java

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,10 +14,15 @@ public class IdValueEncoder implements ValueEncoder {
1414

1515
@Override
1616
public DataItem encode(Mapping mapping, JsonValue jsonValue, String term, Collection<String> types) {
17-
1817
if (types != null && types.contains(Keywords.ID)) {
1918

20-
final Integer code = mapping.terms().getCode(((JsonString) jsonValue).getString());
19+
final String id = ((JsonString) jsonValue).getString();
20+
21+
Integer code = mapping.uris().getCode(id);
22+
23+
if (code == null) {
24+
code = mapping.terms().getCode(id);
25+
}
2126

2227
if (code != null) {
2328
return new UnsignedInteger(code);

src/test/resources/com/apicatalog/cborld/decoder-manifest.jsonld

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -332,6 +332,46 @@
332332
"name": "0.6: Utopia EAD VCB",
333333
"input": "0.6/barcode-ex-14.cborld",
334334
"expect": "0.6/barcode-ex-14.jsonld"
335+
},
336+
{
337+
"@id": "#t0200",
338+
"@type": [
339+
"PositiveEvaluationTest",
340+
"DecoderTest"
341+
],
342+
"name": "1.0: Utopia Driver's License VCB",
343+
"input": "1.0/utopia-12.cborld",
344+
"expect": "1.0/utopia-12.jsonld"
345+
},
346+
{
347+
"@id": "#t0201",
348+
"@type": [
349+
"PositiveEvaluationTest",
350+
"DecoderTest"
351+
],
352+
"name": "1.0: Utopia EAD VCB",
353+
"input": "1.0/utopia-19.cborld",
354+
"expect": "1.0/utopia-19.jsonld"
355+
},
356+
{
357+
"@id": "#t0202",
358+
"@type": [
359+
"PositiveEvaluationTest",
360+
"DecoderTest"
361+
],
362+
"name": "1.0: URIs: Utopia Driver's License VCB",
363+
"input": "1.0/utopia-ext-12.cborld",
364+
"expect": "1.0/utopia-ext-12.jsonld"
365+
},
366+
{
367+
"@id": "#t0201",
368+
"@type": [
369+
"PositiveEvaluationTest",
370+
"DecoderTest"
371+
],
372+
"name": "1.0: URIs: Utopia EAD VCB",
373+
"input": "1.0/utopia-ext-19.cborld",
374+
"expect": "1.0/utopia-ext-19.jsonld"
335375
}
336376
]
337377
}

0 commit comments

Comments
 (0)