sidetree 0.1.3 → 0.1.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/main.yml +1 -1
- data/.ruby-version +1 -1
- data/README.md +239 -5
- data/lib/sidetree/model/core_proof_file.rb +5 -2
- data/lib/sidetree/version.rb +1 -1
- data/sidetree.gemspec +1 -1
- metadata +5 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1d0ba773b3e271c87bc94baf8de2cffdf3a877ab036706a1c33a856c7415a015
|
4
|
+
data.tar.gz: c33c29278762606a4be6aeaa1baab07840bb53fe247a1c579d5674134ffb0c67
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 53ff99ea81549069663f34023c53ec690f428db60b035f494ce9aaa0379b7ec54032b9963adf6ed8fbf55f3bb5ac03de2f4559b7cd615ec04a907030854238e3
|
7
|
+
data.tar.gz: 89dca27ab2ae6e1e028aecd1e3928a12e2ea0c6e517392c715de5eeb3e54fb2a3bdb027afb8a709cb9ac559e62c08e5ca66ff6af498967bc362a9ce740e115e6
|
data/.github/workflows/main.yml
CHANGED
data/.ruby-version
CHANGED
@@ -1 +1 @@
|
|
1
|
-
ruby-3.
|
1
|
+
ruby-3.2.0
|
data/README.md
CHANGED
@@ -1,8 +1,7 @@
|
|
1
|
-
#
|
1
|
+
# Sidetree for Ruby [](https://github.com/azuchi/sidetreerb/actions/workflows/main.yml) [](https://badge.fury.io/rb/sidetree) [](LICENSE)
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
TODO: Delete this and the text above, and describe your gem
|
3
|
+
This is an experimental library that implements the [Sidetree protocol](https://identity.foundation/sidetree/spec/) in Ruby.
|
4
|
+
If you use this library, please test to see if it works properly with [reference implementation](https://github.com/decentralized-identity/sidetree).
|
6
5
|
|
7
6
|
## Installation
|
8
7
|
|
@@ -22,7 +21,242 @@ Or install it yourself as:
|
|
22
21
|
|
23
22
|
## Usage
|
24
23
|
|
25
|
-
|
24
|
+
### Environment
|
25
|
+
|
26
|
+
Currently, this library support mainnet and testnet.
|
27
|
+
If you want to run with testnet, configure the network with the following code.
|
28
|
+
|
29
|
+
```ruby
|
30
|
+
Sidetree::Params.network = Sidetree::Params::Network::TESTNET
|
31
|
+
```
|
32
|
+
### Create new DID
|
33
|
+
|
34
|
+
```ruby
|
35
|
+
# Generate recovery key
|
36
|
+
recovery_key = Sidetree::Key.generate
|
37
|
+
|
38
|
+
# Generate update key
|
39
|
+
update_key = Sidetree::Key.generate
|
40
|
+
|
41
|
+
# Generate signing key
|
42
|
+
signing_key = Sidetree::Key.generate(id: "signing-key")
|
43
|
+
|
44
|
+
# Create DID Document from signing key
|
45
|
+
document = Sidetree::Model::Document.new(public_keys: [signing_key])
|
46
|
+
|
47
|
+
# Create DID
|
48
|
+
did =
|
49
|
+
Sidetree::DID.create(
|
50
|
+
document,
|
51
|
+
update_key,
|
52
|
+
recovery_key
|
53
|
+
)
|
54
|
+
=> "did:sidetree:test:EiAw8oTzWzmPyTANALvzeHkCc6-uQ7XxnohqphrwC_jhNg:eyJkZWx0YSI6eyJwYXRjaGVzIjpbeyJhY3Rpb24iOiJyZXBsYWNlIiwiZG9jdW1lbnQiOnsicHVibGljS2V5cyI6W3siaWQiOiJzaWduaW5nLWtleSIsInB1YmxpY0tleUp3ayI6eyJjcnYiOiJzZWNwMjU2azEiLCJrdHkiOiJFQyIsIngiOiJJQ3BuZXVJZ2ZqZW5UZzhhMmVCeEd1RkVjV1lwZkFTcDRXdHVmbmdGd3owIiwieSI6IlNPbUxzSzhIWlU0bmY5YWZCQmF0SlJUSjVWeGZSMlVRZ1hFVV8xTXVyTzgifSwicHVycG9zZXMiOltdLCJ0eXBlIjoiRWNkc2FTZWNwMjU2azFWZXJpZmljYXRpb25LZXkyMDE5In1dLCJzZXJ2aWNlcyI6W119fV0sInVwZGF0ZUNvbW1pdG1lbnQiOiJFaUExQ1l4NWE5NTlPRGRicThrMG1WUDJwZmVEY0RXaHd3TXhWamNDS2tZOXF3In0sInN1ZmZpeERhdGEiOnsiZGVsdGFIYXNoIjoiRWlDWklRdjlyeVVDR2dLbjMtSjNfTV9ZN0k1VTIyZlpldFRaSTFxSjZqdnVEQSIsInJlY292ZXJ5Q29tbWl0bWVudCI6IkVpQ2dPTGRPb0F5a3A4SzBrMlNwMmlzRUtNOFpmRnBVSWhVcnRLbUEydEcxcWcifX0"
|
55
|
+
```
|
56
|
+
|
57
|
+
### DID operation
|
58
|
+
|
59
|
+
#### Create Operation
|
60
|
+
|
61
|
+
```ruby
|
62
|
+
# Generate Create Operation
|
63
|
+
create_op = did.create_op
|
64
|
+
|
65
|
+
# Generate Chunk File from create operation
|
66
|
+
chunk_file = Sidetree::Model::ChunkFile.create_from_ops(create_ops: [create_op])
|
67
|
+
|
68
|
+
# Write chunk file to IPFS
|
69
|
+
# Initialize IPFS client(If the parameter is omitted, the default is to access http://localhost:5001/api/v0.)
|
70
|
+
ipfs = Sidetree::CAS::IPFS.new
|
71
|
+
|
72
|
+
chunk_file_uri = ipfs.write(chunk_file.to_compress)
|
73
|
+
|
74
|
+
# Generate Provisional Index File and write to IPFS
|
75
|
+
provisional_index_file = Sidetree::Model::ProvisionalIndexFile.new(chunks: [Sidetree::Model::Chunk.new(chunk_file_uri)])
|
76
|
+
provisional_index_file_uri = ipfs.write(provisional_index_file.to_compress)
|
77
|
+
|
78
|
+
# Generate Core Index File and write to IPFS
|
79
|
+
core_index_file = Sidetree::Model::CoreIndexFile.new(
|
80
|
+
create_ops: [create_op],
|
81
|
+
provisional_index_file_uri: provisional_index_file_uri
|
82
|
+
)
|
83
|
+
core_index_file_uri = ipfs.write(core_index_file.to_compress)
|
84
|
+
|
85
|
+
# Generate Anchor String to anchoring to Bitcoin
|
86
|
+
anchor_str = Sidetree::Util::AnchoredDataSerializer.serialize(1, core_index_file_uri)
|
87
|
+
```
|
88
|
+
|
89
|
+
#### Update Operation
|
90
|
+
|
91
|
+
```ruby
|
92
|
+
# DID suffix to be updated
|
93
|
+
did_suffix = "EiBRrmEha_Q30GieEwLB-XM8CZd_b49dQ7znhaBxfAHTsQ"
|
94
|
+
|
95
|
+
# Current update key
|
96
|
+
update_key = Sidetree::Key.new(private_key: <private key>)
|
97
|
+
|
98
|
+
# Generate new signing key
|
99
|
+
new_signing_key = Sidetree::Key.generate(id: "signing-key")
|
100
|
+
|
101
|
+
# Create replace DID Document
|
102
|
+
document = Sidetree::Model::Document.new(public_keys: [new_signing_key])
|
103
|
+
|
104
|
+
# Generate next update key
|
105
|
+
next_update_key = Sidetree::Key.generate
|
106
|
+
|
107
|
+
# Generate update delta object
|
108
|
+
delta =
|
109
|
+
Sidetree::Model::Delta.new(
|
110
|
+
[document.to_replace_patch],
|
111
|
+
next_update_key.to_commitment
|
112
|
+
)
|
113
|
+
|
114
|
+
# Generate jws and sign with update key
|
115
|
+
claim = { updateKey: update_key.to_jwk.normalize, deltaHash: delta.to_hash }
|
116
|
+
jws = Sidetree::Util::JWS.sign(claim, update_key)
|
117
|
+
|
118
|
+
# Generate Provisional Proof File and write to IPFS
|
119
|
+
provisional_proof = Sidetree::Model::ProvisionalProofFile.new([jws])
|
120
|
+
provisional_proof_uri = ipfs.write(provisional_proof.to_compress)
|
121
|
+
|
122
|
+
# Create update operation
|
123
|
+
update_op =
|
124
|
+
Sidetree::OP::Update.new(did_suffix, delta, jws, update_key.to_reveal_value)
|
125
|
+
|
126
|
+
# Generate Chunk File and write to IPFS
|
127
|
+
chunk_file =
|
128
|
+
Sidetree::Model::ChunkFile.create_from_ops(update_ops: [update_op])
|
129
|
+
chunk_file_uri = ipfs.write(chunk_file.to_compress)
|
130
|
+
|
131
|
+
# Generate Provisional Index File and write to IPFS
|
132
|
+
provisional_index_file =
|
133
|
+
Sidetree::Model::ProvisionalIndexFile.new(
|
134
|
+
proof_file_uri: provisional_proof_uri,
|
135
|
+
chunks: [Sidetree::Model::Chunk.new(chunk_file_uri)],
|
136
|
+
operations: [update_op]
|
137
|
+
)
|
138
|
+
provisional_index_file_uri = ipfs.write(provisional_index_file.to_compress)
|
139
|
+
|
140
|
+
# Generate Core Index File and write to IPFS
|
141
|
+
core_index_file =
|
142
|
+
Sidetree::Model::CoreIndexFile.new(
|
143
|
+
provisional_index_file_uri: provisional_index_file_uri
|
144
|
+
)
|
145
|
+
core_index_file_uri = ipfs.write(core_index_file.to_compress)
|
146
|
+
|
147
|
+
anchor_str =
|
148
|
+
Sidetree::Util::AnchoredDataSerializer.serialize(1, core_index_file_uri)
|
149
|
+
```
|
150
|
+
|
151
|
+
#### Recover Operation
|
152
|
+
|
153
|
+
```ruby
|
154
|
+
did_suffix = "EiBRrmEha_Q30GieEwLB-XM8CZd_b49dQ7znhaBxfAHTsQ"
|
155
|
+
|
156
|
+
# Current recovery key
|
157
|
+
recovery_key = Sidetree::Key.new(private_key: <private key>)
|
158
|
+
|
159
|
+
# Generate new recovery key
|
160
|
+
new_recovery_key = Sidetree::Key.generate
|
161
|
+
|
162
|
+
# Generate new update key
|
163
|
+
new_update_key = Sidetree::Key.generate
|
164
|
+
|
165
|
+
# Generate new signing key
|
166
|
+
new_signing_key = Sidetree::Key.generate(id: "signing-key")
|
167
|
+
|
168
|
+
# Generate replace DID Document
|
169
|
+
document = Sidetree::Model::Document.new(public_keys: [new_signing_key])
|
170
|
+
delta =
|
171
|
+
Sidetree::Model::Delta.new(
|
172
|
+
[document.to_replace_patch],
|
173
|
+
new_update_key.to_commitment
|
174
|
+
)
|
175
|
+
|
176
|
+
# Generate jws and sign with recovery key
|
177
|
+
claim = {
|
178
|
+
recoveryKey: recovery_key.to_jwk.normalize,
|
179
|
+
recoveryCommitment: new_recovery_key.to_commitment,
|
180
|
+
deltaHash: delta.to_hash
|
181
|
+
}
|
182
|
+
jws = Sidetree::Util::JWS.sign(claim, recovery_key)
|
183
|
+
|
184
|
+
# Generate Core Proof File from jws
|
185
|
+
core_proof_file = Sidetree::Model::CoreProofFile.new(recover_proofs: [jws])
|
186
|
+
core_proof_file_uri = ipfs.write(core_proof_file.to_compress)
|
187
|
+
|
188
|
+
# Create recover operation
|
189
|
+
recover_op =
|
190
|
+
Sidetree::OP::Recover.new(
|
191
|
+
did_suffix,
|
192
|
+
delta,
|
193
|
+
jws,
|
194
|
+
recovery_key.to_reveal_value
|
195
|
+
)
|
196
|
+
|
197
|
+
# Generate Chunk File and write to IPFS
|
198
|
+
chunk_file =
|
199
|
+
Sidetree::Model::ChunkFile.create_from_ops(recover_ops: [recover_op])
|
200
|
+
chunk_file_uri = ipfs.write(chunk_file.to_compress)
|
201
|
+
|
202
|
+
# Generate Provisional Index File and write to IPFS
|
203
|
+
provisional_index_file =
|
204
|
+
Sidetree::Model::ProvisionalIndexFile.new(
|
205
|
+
chunks: [Sidetree::Model::Chunk.new(chunk_file_uri)]
|
206
|
+
)
|
207
|
+
provisional_index_file_uri = ipfs.write(provisional_index_file.to_compress)
|
208
|
+
|
209
|
+
# Generate Core Index File and write to IPFS
|
210
|
+
core_index_file =
|
211
|
+
Sidetree::Model::CoreIndexFile.new(
|
212
|
+
provisional_index_file_uri: provisional_index_file_uri,
|
213
|
+
core_proof_file_uri: core_proof_file_uri,
|
214
|
+
recover_ops: [recover_op]
|
215
|
+
)
|
216
|
+
core_index_file_uri = ipfs.write(core_index_file.to_compress)
|
217
|
+
|
218
|
+
anchor_str =
|
219
|
+
Sidetree::Util::AnchoredDataSerializer.serialize(1, core_index_file_uri)
|
220
|
+
```
|
221
|
+
|
222
|
+
#### Deactivate operation
|
223
|
+
|
224
|
+
```ruby
|
225
|
+
# Current recovery key
|
226
|
+
recovery_key = Sidetree::Key.new(private_key: <private key>)
|
227
|
+
|
228
|
+
# Generate jws and sign with recovery key
|
229
|
+
claim = {
|
230
|
+
didSuffix: did_suffix,
|
231
|
+
recoveryKey: recovery_key.to_jwk.normalize
|
232
|
+
}
|
233
|
+
jws = Sidetree::Util::JWS.sign(claim, recovery_key)
|
234
|
+
|
235
|
+
# Generate Core Proof File and write to IPFS
|
236
|
+
core_proof_file = Sidetree::Model::CoreProofFile.new(deactivate_proofs: [jws])
|
237
|
+
core_proof_file_uri = ipfs.write(core_proof_file.to_compress)
|
238
|
+
|
239
|
+
# Create Deactivate Operation
|
240
|
+
deactivate_op =
|
241
|
+
Sidetree::OP::Deactivate.new(
|
242
|
+
did_suffix,
|
243
|
+
jws,
|
244
|
+
recovery_key.to_reveal_value
|
245
|
+
)
|
246
|
+
|
247
|
+
# Generate Core Index File and write to IPFS
|
248
|
+
core_index_file =
|
249
|
+
Sidetree::Model::CoreIndexFile.new(
|
250
|
+
core_proof_file_uri: core_proof_file_uri,
|
251
|
+
deactivate_ops: [deactivate_op]
|
252
|
+
)
|
253
|
+
core_index_file_uri = ipfs.write(core_index_file.to_compress)
|
254
|
+
|
255
|
+
anchor_str =
|
256
|
+
Sidetree::Util::AnchoredDataSerializer.serialize(1, core_index_file_uri)
|
257
|
+
```
|
258
|
+
|
259
|
+
The pseudocode above all anchor a single operation, but you can be combined into a batch(i.e. to single anchor string).
|
26
260
|
|
27
261
|
## Development
|
28
262
|
|
@@ -5,7 +5,7 @@ module Sidetree
|
|
5
5
|
attr_reader :recover_proofs
|
6
6
|
attr_reader :deactivate_proofs
|
7
7
|
|
8
|
-
def initialize(recover_proofs, deactivate_proofs)
|
8
|
+
def initialize(recover_proofs: [], deactivate_proofs: [])
|
9
9
|
@recover_proofs = recover_proofs
|
10
10
|
@deactivate_proofs = deactivate_proofs
|
11
11
|
end
|
@@ -78,7 +78,10 @@ module Sidetree
|
|
78
78
|
if recover_proofs.length + deactivate_proofs.length == 0
|
79
79
|
raise Sidetree::Error, "Core proof file has no proof"
|
80
80
|
end
|
81
|
-
CoreProofFile.new(
|
81
|
+
CoreProofFile.new(
|
82
|
+
recover_proofs: recover_proofs,
|
83
|
+
deactivate_proofs: deactivate_proofs
|
84
|
+
)
|
82
85
|
rescue JSON::ParserError
|
83
86
|
raise Sidetree::Error, "Core proof file is not json"
|
84
87
|
end
|
data/lib/sidetree/version.rb
CHANGED
data/sidetree.gemspec
CHANGED
@@ -32,7 +32,7 @@ Gem::Specification.new do |spec|
|
|
32
32
|
|
33
33
|
# Uncomment to register a new dependency of your gem
|
34
34
|
spec.add_dependency 'ecdsa', '~> 1.2.0'
|
35
|
-
spec.add_dependency 'json-jwt', '~> 1.
|
35
|
+
spec.add_dependency 'json-jwt', '~> 1.16.3'
|
36
36
|
spec.add_dependency 'json-canonicalization', '~> 0.3.0'
|
37
37
|
spec.add_dependency 'multihashes', '~> 0.2.0'
|
38
38
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sidetree
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- azuchi
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2023-05-26 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: ecdsa
|
@@ -30,14 +30,14 @@ dependencies:
|
|
30
30
|
requirements:
|
31
31
|
- - "~>"
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: 1.
|
33
|
+
version: 1.16.3
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
38
|
- - "~>"
|
39
39
|
- !ruby/object:Gem::Version
|
40
|
-
version: 1.
|
40
|
+
version: 1.16.3
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: json-canonicalization
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -184,7 +184,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
184
184
|
- !ruby/object:Gem::Version
|
185
185
|
version: '0'
|
186
186
|
requirements: []
|
187
|
-
rubygems_version: 3.
|
187
|
+
rubygems_version: 3.4.1
|
188
188
|
signing_key:
|
189
189
|
specification_version: 4
|
190
190
|
summary: Ruby implementation for Sidetree protocol.
|