mirror of
https://github.com/fluencelabs/trust-graph
synced 2025-07-04 09:01:41 +00:00
Compare commits
52 Commits
trust-grap
...
lean-keypa
Author | SHA1 | Date | |
---|---|---|---|
3a99ab285c | |||
e2d93adb1e | |||
fd145c5fe1 | |||
bfdffee69c | |||
b263ce1fb1 | |||
6389c4cec5 | |||
16bf0a0995 | |||
175e51d5db | |||
34cbc3126c | |||
b8555e666d | |||
c59451de04 | |||
106bff637e | |||
120bedfafb | |||
48351d5562 | |||
0b66f4e053 | |||
ca042d3825 | |||
d0b425c9c7 | |||
ed5bd2c0ec | |||
2f336f73cf | |||
ee63de8c71 | |||
d3d26717bd | |||
08b1879de9 | |||
9a006f1f35 | |||
35ea650928 | |||
6630e40d8a | |||
3f37ed0920 | |||
d378fe2509 | |||
80bf4aa4ff | |||
80757e6352 | |||
f2c3b2a13c | |||
4f657f9dae | |||
725d3f8f48 | |||
1fb02e4827 | |||
a37bda37a2 | |||
ee330a715a | |||
c22eab38c1 | |||
3692d6898d | |||
3a5f23741f | |||
b10991501d | |||
d80a43bcff | |||
a7ea41ed4d | |||
d04120bacf | |||
3ba3855892 | |||
f7ef0f8da0 | |||
2001f900fa | |||
412b8ba725 | |||
a7abe87c09 | |||
1a26a6809e | |||
93161afe0c | |||
11fd2de7b6 | |||
a8fdb4472e | |||
56d0ea27bd |
6
.github/release-please/config.json
vendored
6
.github/release-please/config.json
vendored
@ -14,7 +14,8 @@
|
||||
"components": [
|
||||
"trust-graph",
|
||||
"trust-graph-api",
|
||||
"trust-graph-wasm"
|
||||
"trust-graph-wasm",
|
||||
"distro"
|
||||
]
|
||||
}
|
||||
],
|
||||
@ -31,6 +32,9 @@
|
||||
},
|
||||
"keypair": {
|
||||
"component": "keypair"
|
||||
},
|
||||
"distro": {
|
||||
"component": "distro"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
9
.github/release-please/manifest.json
vendored
9
.github/release-please/manifest.json
vendored
@ -1,6 +1,7 @@
|
||||
{
|
||||
"trust-graph": "0.4.3",
|
||||
"aqua": "0.4.3",
|
||||
"service": "0.4.3",
|
||||
"keypair": "0.10.1"
|
||||
"trust-graph": "0.4.11",
|
||||
"aqua": "0.4.11",
|
||||
"service": "0.4.11",
|
||||
"keypair": "0.10.4",
|
||||
"distro": "0.4.11"
|
||||
}
|
||||
|
47
.github/workflows/release.yml
vendored
47
.github/workflows/release.yml
vendored
@ -17,6 +17,7 @@ jobs:
|
||||
trust-graph-api-release-created: ${{ steps.release.outputs['aqua--release_created'] }}
|
||||
trust-graph-release-created: ${{ steps.release.outputs['trust-graph--release_created'] }}
|
||||
trust-graph-tag-name: ${{ steps.release.outputs['trust-graph--tag_name'] }}
|
||||
trust-graph-version: ${{ steps.release.outputs['trust-graph--version'] }}
|
||||
|
||||
steps:
|
||||
- name: Run release-please
|
||||
@ -70,7 +71,6 @@ jobs:
|
||||
|
||||
- name: Build
|
||||
run: ./build.sh
|
||||
working-directory: service
|
||||
|
||||
- name: Install cargo-workspaces
|
||||
uses: baptiste0928/cargo-install@v1.3.0
|
||||
@ -97,6 +97,12 @@ jobs:
|
||||
- run: npm i
|
||||
working-directory: aqua
|
||||
|
||||
- name: Setup fcli
|
||||
uses: fluencelabs/setup-fluence@v1
|
||||
with:
|
||||
artifact: fcli
|
||||
version: unstable
|
||||
|
||||
- run: npm run build
|
||||
working-directory: aqua
|
||||
|
||||
@ -105,45 +111,6 @@ jobs:
|
||||
run: npm publish --access public
|
||||
working-directory: aqua
|
||||
|
||||
- name: Install ipfs
|
||||
uses: nahsi/setup-ipfs@v1
|
||||
|
||||
- name: Create builtin distribution package
|
||||
if: needs.release-please.outputs.trust-graph-release-created
|
||||
run: ./builtin-package/package.sh
|
||||
|
||||
- name: Calculate SHA256
|
||||
if: needs.release-please.outputs.trust-graph-release-created
|
||||
id: sha
|
||||
run: |
|
||||
# Calculate sha256
|
||||
du -hs trust-graph.tar.gz
|
||||
sha256sum trust-graph.tar.gz
|
||||
sha=($(sha256sum trust-graph.tar.gz))
|
||||
echo "sha256=${sha}" >> $GITHUB_OUTPUT
|
||||
|
||||
- name: Upload trust-graph package
|
||||
if: needs.release-please.outputs.trust-graph-release-created
|
||||
uses: softprops/action-gh-release@v1
|
||||
with:
|
||||
files: trust-graph.tar.gz
|
||||
tag_name: ${{ needs.release-please.outputs.trust-graph-tag-name }}
|
||||
|
||||
- name: Update version in node-distro repo
|
||||
if: needs.release-please.outputs.trust-graph-release-created
|
||||
uses: benc-uk/workflow-dispatch@v1
|
||||
with:
|
||||
workflow: update_service
|
||||
repo: fluencelabs/node-distro
|
||||
ref: "main"
|
||||
token: ${{ secrets.PERSONAL_TOKEN }}
|
||||
inputs: '{
|
||||
"name": "trust-graph",
|
||||
"version": "${{ needs.release-please.outputs.version }}",
|
||||
"url": "https://github.com/fluencelabs/trust-graph/releases/download/${{ needs.release-please.outputs.trust-graph-tag-name }}/trust-graph.tar.gz",
|
||||
"sha256": "${{ steps.sha.outputs.sha256 }}"
|
||||
}'
|
||||
|
||||
slack:
|
||||
if: always()
|
||||
name: "Notify"
|
||||
|
36
.github/workflows/tests.yml
vendored
36
.github/workflows/tests.yml
vendored
@ -2,6 +2,11 @@ name: Run tests with workflow_call
|
||||
|
||||
on:
|
||||
workflow_call:
|
||||
inputs:
|
||||
fcli-version:
|
||||
description: "@fluencelabs/cli version"
|
||||
type: string
|
||||
default: "main"
|
||||
|
||||
jobs:
|
||||
trust-graph:
|
||||
@ -21,9 +26,10 @@ jobs:
|
||||
|
||||
- name: Setup marine
|
||||
uses: fluencelabs/setup-marine@v1
|
||||
with:
|
||||
artifact-name: marine
|
||||
|
||||
- name: Build
|
||||
working-directory: ./service
|
||||
run: ./build.sh
|
||||
|
||||
- name: Run cargo clippy
|
||||
@ -32,17 +38,15 @@ jobs:
|
||||
command: clippy
|
||||
args: -Z unstable-options --all
|
||||
|
||||
- name: Install cargo-nextest
|
||||
uses: baptiste0928/cargo-install@v1.3.0
|
||||
with:
|
||||
crate: cargo-nextest
|
||||
version: 0.9.22
|
||||
- name: Setup nextest
|
||||
uses: taiki-e/install-action@nextest
|
||||
|
||||
- name: Run cargo nextest
|
||||
env:
|
||||
NEXTEST_RETRIES: 10
|
||||
NEXTEST_TEST_THREADS: 10
|
||||
run: cargo nextest run --release --all-features --no-fail-fast
|
||||
# exclude distro since at this point we don't have compiled wasms which are required for compilation
|
||||
run: cargo nextest run --release --all-features --no-fail-fast --workspace --exclude trust-graph-distro
|
||||
|
||||
- name: Setup node
|
||||
uses: actions/setup-node@v3
|
||||
@ -52,20 +56,14 @@ jobs:
|
||||
cache-dependency-path: "aqua/package-lock.json"
|
||||
cache: "npm"
|
||||
|
||||
- name: Setup fcli
|
||||
uses: fluencelabs/setup-fluence@v1
|
||||
with:
|
||||
artifact: fcli
|
||||
version: ${{ inputs.fcli-version }}
|
||||
|
||||
- run: npm i
|
||||
working-directory: aqua
|
||||
|
||||
- run: npm run build
|
||||
working-directory: aqua
|
||||
|
||||
- name: Install ipfs
|
||||
uses: nahsi/setup-ipfs@v1
|
||||
|
||||
- name: Create distribution package
|
||||
run: ./builtin-package/package.sh
|
||||
|
||||
- name: Upload trust-graph
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: trust-graph
|
||||
path: trust-graph.tar.gz
|
||||
|
2
.gitignore
vendored
2
.gitignore
vendored
@ -2,6 +2,8 @@ service/target
|
||||
service/artifacts
|
||||
builtin-package/*.wasm
|
||||
trust-graph.tar.gz
|
||||
distro/trust-graph-service
|
||||
distro/target
|
||||
|
||||
**/*.rs.bk
|
||||
**/.idea
|
||||
|
2100
Cargo.lock
generated
2100
Cargo.lock
generated
File diff suppressed because it is too large
Load Diff
@ -2,8 +2,9 @@
|
||||
members = [
|
||||
"trust-graph",
|
||||
"keypair",
|
||||
"service"
|
||||
"service",
|
||||
"distro"
|
||||
]
|
||||
|
||||
[workspace.dependencies]
|
||||
libp2p-identity = { version = "0.1.0", default-features = false, features = ["peerid", "rsa", "ed25519", "secp256k1", "multihash"] }
|
||||
libp2p-identity = { version = "0.2.7", default-features = false }
|
||||
|
@ -1,19 +1,25 @@
|
||||
import "@fluencelabs/trust-graph/trust-graph.aqua"
|
||||
aqua Admin
|
||||
|
||||
export timestamp_sec, get_trust_bytes, issue_trust
|
||||
export get_trust_bytes, issue_trust
|
||||
|
||||
import "@fluencelabs/trust-graph/trust-graph.aqua"
|
||||
import "@fluencelabs/aqua-lib/builtin.aqua"
|
||||
|
||||
func timestamp_sec(node: string) -> u64:
|
||||
on node:
|
||||
result <- Peer.timestamp_sec()
|
||||
|
||||
<- result
|
||||
|
||||
func get_trust_bytes(node: string, issued_for_peer_id: string, expires_at_sec: u64, issued_at_sec: u64) -> GetTrustBytesResult:
|
||||
on node:
|
||||
result <- TrustGraph.get_trust_bytes(issued_for_peer_id, expires_at_sec, issued_at_sec)
|
||||
|
||||
<- result
|
||||
|
||||
func issue_trust(node: string, issued_for_peer_id: string, expires_at_sec: u64, issued_at_sec: u64, trust_bytes: []u8) ->IssueTrustResult:
|
||||
on node:
|
||||
result <- TrustGraph.issue_trust(issued_for_peer_id, expires_at_sec, issued_at_sec, trust_bytes)
|
||||
|
||||
<- result
|
||||
|
1175
admin/package-lock.json
generated
1175
admin/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -4,7 +4,7 @@
|
||||
"description": "A simple example of how to use trust-graph in TS",
|
||||
"main": "index.js",
|
||||
"scripts": {
|
||||
"compile-aqua": "aqua -i aqua -o generated",
|
||||
"compile-aqua": "fluence aqua -i aqua -o generated",
|
||||
"prebuild": "npm run compile-aqua",
|
||||
"build": "tsc",
|
||||
"start": "node dist/index.js",
|
||||
@ -13,12 +13,11 @@
|
||||
"author": "Fluence Labs",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@fluencelabs/aqua": "^0.9.1-374",
|
||||
"@fluencelabs/aqua-lib": "^0.6.0",
|
||||
"@fluencelabs/aqua-lib": "^0.9.0",
|
||||
"@fluencelabs/fluence": "^0.27.5",
|
||||
"@fluencelabs/fluence-network-environment": "^1.0.13",
|
||||
"@fluencelabs/fluence-network-environment": "^1.1.2",
|
||||
"@fluencelabs/trust-graph": "file:../aqua",
|
||||
"bs58": "^4.0.1"
|
||||
"bs58": "^5.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"typescript": "^4.4.3"
|
||||
|
@ -1,5 +1,66 @@
|
||||
# Changelog
|
||||
|
||||
## [0.4.11](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.10...trust-graph-api-v0.4.11) (2024-01-17)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-api:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.10](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.9...trust-graph-api-v0.4.10) (2024-01-03)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **trust-graph:** Update aqua code ([#141](https://github.com/fluencelabs/trust-graph/issues/141)) ([175e51d](https://github.com/fluencelabs/trust-graph/commit/175e51d5db4d90dc6d884ce3113d68494da334a2))
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **trust-graph:** Revert release 0.4.10 ([#153](https://github.com/fluencelabs/trust-graph/issues/153)) ([b263ce1](https://github.com/fluencelabs/trust-graph/commit/b263ce1fb13b937b629608ede35b6f436023dcac))
|
||||
|
||||
## [0.4.9](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.8...trust-graph-api-v0.4.9) (2023-12-28)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-api:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.8](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.7...trust-graph-api-v0.4.8) (2023-12-20)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-api:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.7](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.6...trust-graph-api-v0.4.7) (2023-07-04)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-api:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.6](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.5...trust-graph-api-v0.4.6) (2023-06-30)
|
||||
|
||||
|
||||
### Reverts
|
||||
|
||||
* release master ([#110](https://github.com/fluencelabs/trust-graph/issues/110)) ([d80a43b](https://github.com/fluencelabs/trust-graph/commit/d80a43bcff721aff8fadf3d2d5c252804ce27a6c))
|
||||
|
||||
## [0.4.5](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.4...trust-graph-api-v0.4.5) (2023-05-09)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-api:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.4](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.3...trust-graph-api-v0.4.4) (2023-05-09)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-api:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.3](https://github.com/fluencelabs/trust-graph/compare/trust-graph-api-v0.4.1...trust-graph-api-v0.4.3) (2023-05-08)
|
||||
|
||||
|
||||
|
@ -1,3 +1,7 @@
|
||||
aqua Labelling declares *
|
||||
|
||||
export isFluencePeer
|
||||
|
||||
import "misc.aqua"
|
||||
import get_host_certs_from from "trust-graph-api.aqua"
|
||||
|
||||
@ -20,7 +24,7 @@ func isFluencePeer() -> ?bool, ?Error:
|
||||
fluence_root_peer_id = "12D3KooWNbZKaPWRZ8wgjGvrxdJFz9Fq5uVwkR6ERV1f74HhPdyB"
|
||||
label_peer_id = "12D3KooWM45u7AQxsb4MuQJNYT3NWHHMLU7JTbBV66RTfF3KSzdR"
|
||||
|
||||
result: ?bool
|
||||
result: *bool
|
||||
error: *Error
|
||||
-- get all certs issued by `label_peer_id` to current host
|
||||
certs_result <- get_host_certs_from(label_peer_id)
|
||||
@ -32,8 +36,9 @@ func isFluencePeer() -> ?bool, ?Error:
|
||||
if cert.chain!0.issued_for == fluence_root_peer_id:
|
||||
if cert.chain!1.issued_for == label_peer_id:
|
||||
result <<- true
|
||||
if result == nil:
|
||||
if result == []:
|
||||
result <<- false
|
||||
else:
|
||||
error <<- certs_result.error
|
||||
|
||||
<- result, error
|
||||
|
@ -1,3 +1,5 @@
|
||||
aqua Misc declares *
|
||||
|
||||
import "trust-graph.aqua"
|
||||
|
||||
alias Error: string
|
||||
|
14685
aqua/package-lock.json
generated
14685
aqua/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -1,16 +1,16 @@
|
||||
{
|
||||
"name": "@fluencelabs/trust-graph",
|
||||
"version": "0.4.3",
|
||||
"version": "0.4.11",
|
||||
"description": "Aqua Trust Graph API library",
|
||||
"files": [
|
||||
"*.aqua"
|
||||
],
|
||||
"dependencies": {
|
||||
"@fluencelabs/aqua-lib": "^0.7.0"
|
||||
"@fluencelabs/aqua-lib": "^0.9.0"
|
||||
},
|
||||
"scripts": {
|
||||
"generate-aqua": "../service/build.sh",
|
||||
"compile-aqua": "aqua -i . -o ./target/typescript",
|
||||
"compile-aqua": "fluence aqua -i . -o ./target/typescript",
|
||||
"build": "npm run compile-aqua"
|
||||
},
|
||||
"repository": {
|
||||
@ -29,8 +29,5 @@
|
||||
"bugs": {
|
||||
"url": "https://github.com/fluencelabs/trust-graph/issues"
|
||||
},
|
||||
"homepage": "https://github.com/fluencelabs/trust-graph#readme",
|
||||
"devDependencies": {
|
||||
"@fluencelabs/aqua": "^0.10.3"
|
||||
}
|
||||
"homepage": "https://github.com/fluencelabs/trust-graph#readme"
|
||||
}
|
||||
|
@ -1,3 +1,12 @@
|
||||
aqua TrustGraphApi declares *
|
||||
|
||||
export set_root, issue_trust, import_trust
|
||||
export add_trust, add_root_trust, verify_trust
|
||||
export get_weight, get_weight_from, issue_revocation
|
||||
export import_revocation, revoke, get_host_certs_from
|
||||
export get_all_certs, get_all_certs_from, get_host_certs
|
||||
export insert_cert
|
||||
|
||||
import Sig, Peer, PeerId from "@fluencelabs/aqua-lib/builtin.aqua"
|
||||
import "misc.aqua"
|
||||
import "trust-graph.aqua"
|
||||
@ -24,7 +33,7 @@ func issue_trust(issuer: PeerId, issued_for: PeerId, expires_at_sec: u64) -> ?Tr
|
||||
issued_at_sec <- Peer.timestamp_sec()
|
||||
bytes <- TrustGraph.get_trust_bytes(issued_for, expires_at_sec, issued_at_sec)
|
||||
|
||||
result: ?Trust
|
||||
result: *Trust
|
||||
error: *Error
|
||||
if bytes.success:
|
||||
Sig issuer
|
||||
@ -41,6 +50,7 @@ func issue_trust(issuer: PeerId, issued_for: PeerId, expires_at_sec: u64) -> ?Tr
|
||||
error <<- sig_res.error!
|
||||
else:
|
||||
error <<- bytes.error
|
||||
|
||||
<- result, error
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -51,8 +61,9 @@ func import_trust(trust: Trust, issuer: PeerId) -> ?Error:
|
||||
error: *Error
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
add_result <- TrustGraph.add_trust(trust, issuer, timestamp_sec)
|
||||
if add_result.success != true:
|
||||
if !add_result.success:
|
||||
error <<- add_result.error
|
||||
|
||||
<- error
|
||||
|
||||
-- Call context: %init_peer_id%
|
||||
@ -70,6 +81,7 @@ func add_trust(node: PeerId, issuer: PeerId, issued_for: PeerId, expires_at_sec:
|
||||
on node:
|
||||
import_error <- import_trust(trust!, issuer)
|
||||
append_error(error, import_error)
|
||||
|
||||
<- error
|
||||
|
||||
-- Call context: %init_peer_id%
|
||||
@ -99,6 +111,7 @@ func add_root_trust(node: PeerId, peer_id: PeerId, max_chain_len: u32, expires_a
|
||||
func verify_trust(trust: Trust, issuer: PeerId) -> VerifyTrustResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.verify_trust(trust, issuer, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -107,6 +120,7 @@ func verify_trust(trust: Trust, issuer: PeerId) -> VerifyTrustResult:
|
||||
func get_weight(peer_id: PeerId) -> WeightResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.get_weight(peer_id, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -114,6 +128,7 @@ func get_weight(peer_id: PeerId) -> WeightResult:
|
||||
func get_weight_from(peer_id: PeerId, issuer: PeerId) -> WeightResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.get_weight_from(peer_id, issuer, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: %init_peer_id%
|
||||
@ -127,7 +142,7 @@ func issue_revocation(revoked_by: PeerId, revoked: PeerId) -> ?Revocation, ?Erro
|
||||
issued_at_sec <- Peer.timestamp_sec()
|
||||
bytes <- TrustGraph.get_revocation_bytes(revoked, issued_at_sec)
|
||||
|
||||
result: ?Revocation
|
||||
result: *Revocation
|
||||
error: *Error
|
||||
if bytes.success:
|
||||
Sig revoked_by
|
||||
@ -145,6 +160,7 @@ func issue_revocation(revoked_by: PeerId, revoked: PeerId) -> ?Revocation, ?Erro
|
||||
error <<- sig_res.error!
|
||||
else:
|
||||
error <<- bytes.error
|
||||
|
||||
<- result, error
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -155,7 +171,7 @@ func import_revocation(revocation: Revocation) -> ?Error:
|
||||
error: *Error
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
add_result <- TrustGraph.revoke(revocation, timestamp_sec)
|
||||
if add_result.success != true:
|
||||
if !add_result.success:
|
||||
error <<- add_result.error
|
||||
|
||||
<- error
|
||||
@ -176,6 +192,7 @@ func revoke(node: PeerId, revoked_by: PeerId, revoked: PeerId) -> ?Error:
|
||||
on node:
|
||||
import_error <- import_revocation(revocation!)
|
||||
append_error(error, import_error)
|
||||
|
||||
<- error
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -183,6 +200,7 @@ func revoke(node: PeerId, revoked_by: PeerId, revoked: PeerId) -> ?Error:
|
||||
func get_host_certs_from(issuer: PeerId) -> AllCertsResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.get_host_certs_from(issuer, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -190,6 +208,7 @@ func get_host_certs_from(issuer: PeerId) -> AllCertsResult:
|
||||
func get_all_certs(issued_for: PeerId) -> AllCertsResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.get_all_certs(issued_for, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -197,6 +216,7 @@ func get_all_certs(issued_for: PeerId) -> AllCertsResult:
|
||||
func get_all_certs_from(issued_for: PeerId, issuer: PeerId) -> AllCertsResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.get_all_certs_from(issued_for, issuer, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -204,6 +224,7 @@ func get_all_certs_from(issued_for: PeerId, issuer: PeerId) -> AllCertsResult:
|
||||
func get_host_certs() -> AllCertsResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.get_host_certs(timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
||||
-- Call context: any node with registered `trust-graph` service
|
||||
@ -211,4 +232,5 @@ func get_host_certs() -> AllCertsResult:
|
||||
func insert_cert(certificate: Certificate) -> InsertResult:
|
||||
timestamp_sec <- Peer.timestamp_sec()
|
||||
result <- TrustGraph.insert_cert(certificate, timestamp_sec)
|
||||
|
||||
<- result
|
||||
|
@ -1,4 +1,4 @@
|
||||
module TrustGraph declares *
|
||||
aqua TrustGraph declares *
|
||||
|
||||
data AddTrustResult:
|
||||
success: bool
|
||||
|
15
build.sh
Executable file
15
build.sh
Executable file
@ -0,0 +1,15 @@
|
||||
#!/usr/bin/env bash
|
||||
set -o errexit -o nounset -o pipefail
|
||||
|
||||
# set current working directory to script directory to run script from everywhere
|
||||
cd "$(dirname "$0")"
|
||||
|
||||
./service/build.sh
|
||||
|
||||
TARGET="distro/trust-graph-service/"
|
||||
|
||||
mkdir -p "$TARGET"
|
||||
cp -v ./distro/init_certs.json service/artifacts/trust-graph.wasm service/artifacts/sqlite3.wasm distro/Config.toml "$TARGET"
|
||||
|
||||
cd distro
|
||||
cargo build
|
@ -3,10 +3,10 @@ set -o pipefail -o nounset -o errexit
|
||||
|
||||
# set current working directory to script directory to run script from everywhere
|
||||
cd "$(dirname "$0")"
|
||||
PACKAGE_DIR="$(pwd)/../package"
|
||||
PACKAGE_DIR="$(pwd)/../package/trust-graph"
|
||||
|
||||
(
|
||||
rm -f $PACKAGE_DIR/*
|
||||
rm -rf $PACKAGE_DIR/*
|
||||
mkdir -p $PACKAGE_DIR
|
||||
)
|
||||
|
||||
@ -34,8 +34,8 @@ echo "{}" | jq --arg trust_graph_cid "$TRUST_GRAPH_CID" --arg sqlite_cid "$SQLIT
|
||||
|
||||
(
|
||||
echo "*** create builtin distribution package ***"
|
||||
cd $PACKAGE_DIR
|
||||
(tar cf - * | gzip) > ../trust-graph.tar.gz
|
||||
cd $PACKAGE_DIR/..
|
||||
tar -f ../trust-graph.tar.gz -zcv ./trust-graph
|
||||
)
|
||||
|
||||
echo "*** done ***"
|
||||
|
48
distro/CHANGELOG.md
Normal file
48
distro/CHANGELOG.md
Normal file
@ -0,0 +1,48 @@
|
||||
# Changelog
|
||||
|
||||
## [0.4.11](https://github.com/fluencelabs/trust-graph/compare/distro-v0.4.10...distro-v0.4.11) (2024-01-17)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **distro:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.10](https://github.com/fluencelabs/trust-graph/compare/distro-v0.4.9...distro-v0.4.10) (2024-01-03)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **trust-graph:** Revert release 0.4.10 ([#153](https://github.com/fluencelabs/trust-graph/issues/153)) ([b263ce1](https://github.com/fluencelabs/trust-graph/commit/b263ce1fb13b937b629608ede35b6f436023dcac))
|
||||
|
||||
## [0.4.9](https://github.com/fluencelabs/trust-graph/compare/distro-v0.4.8...distro-v0.4.9) (2023-12-28)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** update sqlite wasm ([#135](https://github.com/fluencelabs/trust-graph/issues/135)) ([c59451d](https://github.com/fluencelabs/trust-graph/commit/c59451de04ba79152fa8d600a7b456ab24766dd0))
|
||||
|
||||
## [0.4.8](https://github.com/fluencelabs/trust-graph/compare/distro-v0.4.7...distro-v0.4.8) (2023-12-20)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* update marine sdk's, configs and sqlite connector ([#129](https://github.com/fluencelabs/trust-graph/issues/129)) ([0b66f4e](https://github.com/fluencelabs/trust-graph/commit/0b66f4e0536633879de46f69ac8391c72ece7e77))
|
||||
|
||||
## [0.4.7](https://github.com/fluencelabs/trust-graph/compare/distro-v0.4.6...distro-v0.4.7) (2023-07-04)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **distro:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.6](https://github.com/fluencelabs/trust-graph/compare/distro-v0.4.5...distro-v0.4.6) (2023-06-30)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* add distro crate [fixes NET-463] ([#93](https://github.com/fluencelabs/trust-graph/issues/93)) ([3ba3855](https://github.com/fluencelabs/trust-graph/commit/3ba3855892ae355962212a0a42099dd9f9820800))
|
||||
|
||||
|
||||
### Reverts
|
||||
|
||||
* release master ([#110](https://github.com/fluencelabs/trust-graph/issues/110)) ([d80a43b](https://github.com/fluencelabs/trust-graph/commit/d80a43bcff721aff8fadf3d2d5c252804ce27a6c))
|
18
distro/Cargo.toml
Normal file
18
distro/Cargo.toml
Normal file
@ -0,0 +1,18 @@
|
||||
[package]
|
||||
name = "trust-graph-distro"
|
||||
version = "0.4.11"
|
||||
edition = "2021"
|
||||
build = "build.rs"
|
||||
license = "Apache-2.0"
|
||||
include = [ "/src", "build.rs", "Cargo.toml", "trust-graph-service"]
|
||||
description = "Distribution package for the trust-graph service"
|
||||
|
||||
# See more keysand their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
[dependencies]
|
||||
maplit = "1.0.2"
|
||||
serde = "1.0.160"
|
||||
serde_json = "1.0.96"
|
||||
lazy_static = "1.4.0"
|
||||
|
||||
[build-dependencies]
|
||||
built = "0.6.0"
|
15
distro/Config.toml
Normal file
15
distro/Config.toml
Normal file
@ -0,0 +1,15 @@
|
||||
modules_dir = "."
|
||||
total_memory_limit = "Infinity"
|
||||
|
||||
[[module]]
|
||||
name = "sqlite3"
|
||||
logger_enabled = true
|
||||
|
||||
[module.wasi]
|
||||
mapped_dirs = { "tmp" = "data" }
|
||||
[[module]]
|
||||
name = "trust-graph"
|
||||
logger_enabled = true
|
||||
|
||||
[module.wasi]
|
||||
mapped_dirs = { "tmp" = "data" }
|
3
distro/build.rs
Normal file
3
distro/build.rs
Normal file
@ -0,0 +1,3 @@
|
||||
fn main() {
|
||||
built::write_built_file().expect("Failed to acquire build-time information")
|
||||
}
|
1
distro/init_certs.json
Normal file
1
distro/init_certs.json
Normal file
File diff suppressed because one or more lines are too long
60
distro/src/lib.rs
Normal file
60
distro/src/lib.rs
Normal file
@ -0,0 +1,60 @@
|
||||
use lazy_static::lazy_static;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[cfg(not(feature = "cargo-clippy"))]
|
||||
pub const TRUST_GRAPH_WASM: &[u8] = include_bytes!("../trust-graph-service/trust-graph.wasm");
|
||||
#[cfg(feature = "cargo-clippy")]
|
||||
pub const TRUST_GRAPH_WASM: &[u8] = &[];
|
||||
|
||||
#[cfg(not(feature = "cargo-clippy"))]
|
||||
pub const SQLITE_WASM: &[u8] = include_bytes!("../trust-graph-service/sqlite3.wasm");
|
||||
#[cfg(feature = "cargo-clippy")]
|
||||
pub const SQLITE_WASM: &[u8] = &[];
|
||||
|
||||
#[cfg(not(feature = "cargo-clippy"))]
|
||||
pub const CONFIG: &[u8] = include_bytes!("../trust-graph-service/Config.toml");
|
||||
#[cfg(feature = "cargo-clippy")]
|
||||
pub const CONFIG: &[u8] = &[];
|
||||
|
||||
#[cfg(not(feature = "cargo-clippy"))]
|
||||
pub const KRAS_CERTS_JSON: &str = include_str!("../trust-graph-service/init_certs.json");
|
||||
#[cfg(feature = "cargo-clippy")]
|
||||
pub const KRAS_CERTS_JSON: &str = "{}";
|
||||
|
||||
pub mod build_info {
|
||||
include!(concat!(env!("OUT_DIR"), "/built.rs"));
|
||||
}
|
||||
|
||||
pub use build_info::PKG_VERSION as VERSION;
|
||||
|
||||
pub fn modules() -> std::collections::HashMap<&'static str, &'static [u8]> {
|
||||
maplit::hashmap! {
|
||||
"sqlite3" => SQLITE_WASM,
|
||||
"trust-graph" => TRUST_GRAPH_WASM,
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub struct Certs {
|
||||
pub root_node: String,
|
||||
pub max_chain_length: u32,
|
||||
pub certs: Vec<Cert>,
|
||||
}
|
||||
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub struct Cert {
|
||||
pub chain: Vec<Trust>,
|
||||
}
|
||||
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub struct Trust {
|
||||
pub issued_for: String,
|
||||
pub expires_at: u64,
|
||||
pub signature: String,
|
||||
pub sig_type: String,
|
||||
pub issued_at: u64,
|
||||
}
|
||||
|
||||
lazy_static! {
|
||||
pub static ref KRAS_CERTS: Certs = serde_json::from_str(KRAS_CERTS_JSON).unwrap();
|
||||
}
|
@ -1,3 +1,4 @@
|
||||
aqua Computation
|
||||
|
||||
import "@fluencelabs/trust-graph/trust-graph-api.aqua"
|
||||
import "@fluencelabs/trust-graph/trust-graph.aqua"
|
||||
@ -12,20 +13,21 @@ service TrustedComputation("op"):
|
||||
identity(s: u64) -> u64
|
||||
|
||||
func trusted_computation(node: string) -> ?u64, ?string:
|
||||
result: ?u64
|
||||
error: ?string
|
||||
result: *u64
|
||||
error: *string
|
||||
-- on our trusted relay
|
||||
on HOST_PEER_ID:
|
||||
-- get all certificates issued for given node by our client's peer id
|
||||
certs_result <- get_all_certs_from(node, %init_peer_id%)
|
||||
certs_result <- get_all_certs_from(node, INIT_PEER_ID)
|
||||
if certs_result.success:
|
||||
len <- CertOp.array_length(certs_result.certificates)
|
||||
-- if there is any certificate node is trusted and computation is possible
|
||||
if len != 0:
|
||||
if len != 0:
|
||||
on node:
|
||||
result <- TrustedComputation.identity(5)
|
||||
else:
|
||||
error <<- "there is no certs for this peer"
|
||||
else:
|
||||
error <<- certs_result.error
|
||||
|
||||
<- result, error
|
||||
|
@ -1,11 +1,14 @@
|
||||
module Export
|
||||
aqua Export
|
||||
|
||||
import add_root_trust, add_trust, revoke from "@fluencelabs/trust-graph/trust-graph-api.aqua"
|
||||
export add_root_trust, add_trust, revoke, timestamp_sec
|
||||
import Peer from "@fluencelabs/aqua-lib/builtin.aqua"
|
||||
|
||||
export add_root_trust, add_trust, revoke, timestamp_sec
|
||||
|
||||
alias PeerId: string
|
||||
|
||||
func timestamp_sec() -> u64:
|
||||
on HOST_PEER_ID:
|
||||
result <- Peer.timestamp_sec()
|
||||
|
||||
<- result
|
||||
|
1555
example/package-lock.json
generated
1555
example/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -4,7 +4,7 @@
|
||||
"description": "A simple example of how to use trust-graph in TS",
|
||||
"main": "index.js",
|
||||
"scripts": {
|
||||
"compile-aqua": "aqua -i aqua -o generated",
|
||||
"compile-aqua": "fluence aqua -i aqua -o generated",
|
||||
"prebuild": "npm run compile-aqua",
|
||||
"build": "tsc",
|
||||
"start": "node dist/index.js",
|
||||
@ -13,14 +13,14 @@
|
||||
"author": "Fluence Labs",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@fluencelabs/aqua-lib": "^0.5.2",
|
||||
"@fluencelabs/aqua-lib": "^0.9.0",
|
||||
"@fluencelabs/fluence": "^0.23.0",
|
||||
"@fluencelabs/fluence-network-environment": "^1.0.10",
|
||||
"@fluencelabs/trust-graph": "3.0.2",
|
||||
"bs58": "^4.0.1"
|
||||
"@fluencelabs/fluence-network-environment": "^1.1.2",
|
||||
"@fluencelabs/trust-graph": "3.1.2",
|
||||
"bs58": "^5.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"typescript": "^4.5.2",
|
||||
"@fluencelabs/aqua": "^0.7.4-325"
|
||||
"@fluencelabs/aqua": "^0.10.0"
|
||||
}
|
||||
}
|
||||
|
@ -4,6 +4,38 @@ All notable changes to this project will be documented in this file.
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [0.10.4](https://github.com/fluencelabs/trust-graph/compare/keypair-v0.10.3...keypair-v0.10.4) (2023-12-20)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **fluence-keypair:** bump ed25519-dalek to 0.2.0 ([#127](https://github.com/fluencelabs/trust-graph/issues/127)) ([ed5bd2c](https://github.com/fluencelabs/trust-graph/commit/ed5bd2c0ec50bef5ac7a12deacb73da491666912))
|
||||
* update marine sdk's, configs and sqlite connector ([#129](https://github.com/fluencelabs/trust-graph/issues/129)) ([0b66f4e](https://github.com/fluencelabs/trust-graph/commit/0b66f4e0536633879de46f69ac8391c72ece7e77))
|
||||
|
||||
## [0.10.3](https://github.com/fluencelabs/trust-graph/compare/keypair-v0.10.2...keypair-v0.10.3) (2023-07-04)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **keypair:** deserialize libp2p keypair from secret key ([#116](https://github.com/fluencelabs/trust-graph/issues/116)) ([ee330a7](https://github.com/fluencelabs/trust-graph/commit/ee330a715a902e48fc9b61d662ffcd950a26379c))
|
||||
|
||||
## [0.10.2](https://github.com/fluencelabs/trust-graph/compare/keypair-v0.10.1...keypair-v0.10.2) (2023-06-30)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* update libp2p identity ([#109](https://github.com/fluencelabs/trust-graph/issues/109)) ([d04120b](https://github.com/fluencelabs/trust-graph/commit/d04120bacf802a7e1127f4955b7391b0a4353128))
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **keypair:** update description ([#105](https://github.com/fluencelabs/trust-graph/issues/105)) ([f7ef0f8](https://github.com/fluencelabs/trust-graph/commit/f7ef0f8da095fe1fef80faaa0b0c2d5ef854bd16))
|
||||
|
||||
|
||||
### Reverts
|
||||
|
||||
* release master ([#110](https://github.com/fluencelabs/trust-graph/issues/110)) ([d80a43b](https://github.com/fluencelabs/trust-graph/commit/d80a43bcff721aff8fadf3d2d5c252804ce27a6c))
|
||||
|
||||
## [0.10.1](https://github.com/fluencelabs/trust-graph/compare/keypair-v0.10.0...keypair-v0.10.1) (2023-05-02)
|
||||
|
||||
|
||||
|
@ -1,30 +1,30 @@
|
||||
[package]
|
||||
name = "fluence-keypair"
|
||||
version = "0.10.1"
|
||||
version = "0.10.4"
|
||||
authors = ["Fluence Labs"]
|
||||
edition = "2021"
|
||||
description = "identity"
|
||||
description = "unified keypair API based on libp2p-identity"
|
||||
license = "Apache-2.0"
|
||||
repository = "https://github.com/fluencelabs/trust-graph"
|
||||
|
||||
[dependencies]
|
||||
serde = { version = "1.0.118", features = ["derive"] }
|
||||
bs58 = "0.4.0"
|
||||
ed25519-dalek = { version = "1.0.1", features = ["serde", "std"] }
|
||||
rand = "0.8.5"
|
||||
bs58 = "0.5.0"
|
||||
ed25519-dalek = { version = "2.0.0", features = ["serde", "std"] }
|
||||
thiserror = "1.0.23"
|
||||
lazy_static = "1.2"
|
||||
libsecp256k1 = "0.7.1"
|
||||
asn1_der = "0.6.1"
|
||||
lazy_static = "1.4"
|
||||
sha2 = "0.10.6"
|
||||
zeroize = "1"
|
||||
serde_bytes = "0.11"
|
||||
eyre = "0.6.5"
|
||||
libp2p-identity = { workspace = true, default-features = false, features = ["peerid", "rsa", "ed25519", "secp256k1", "multihash"] }
|
||||
libp2p-identity = { workspace = true, default-features = false, features = ["peerid", "ed25519"] }
|
||||
multihash = { version = "0.18.0", features = ["identity"] }
|
||||
# rand fails to compile for restricted environments like NEAR contracts
|
||||
rand = { version = "0.8.5", optional = true }
|
||||
|
||||
[target.'cfg(not(target_arch = "wasm32"))'.dependencies]
|
||||
ring = { version = "0.16.9", features = ["alloc", "std"], default-features = false }
|
||||
[features]
|
||||
default = ["rand"]
|
||||
rand = ["dep:rand", "ed25519-dalek/rand_core", "libp2p-identity/rand"]
|
||||
|
||||
[dev-dependencies]
|
||||
quickcheck = "1.0.3"
|
||||
|
@ -1,3 +1,3 @@
|
||||
[toolchain]
|
||||
channel = "nightly-2022-08-30"
|
||||
channel = "nightly-2023-12-06"
|
||||
targets = [ "x86_64-apple-darwin", "x86_64-unknown-linux-gnu" ]
|
||||
|
@ -19,19 +19,20 @@
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
//! Ed25519 keys.
|
||||
use crate::error::{DecodingError, SigningError, VerificationError};
|
||||
use crate::error::{DecodingError, DecodingError::InvalidLength, SigningError, VerificationError};
|
||||
use core::fmt;
|
||||
use ed25519_dalek::{self as ed25519, Signer as _, Verifier as _};
|
||||
use rand::RngCore;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::convert::TryFrom;
|
||||
use zeroize::Zeroize;
|
||||
|
||||
/// An Ed25519 keypair.
|
||||
pub struct Keypair(ed25519::Keypair);
|
||||
/// An Ed25519 keypair
|
||||
#[derive(Clone)]
|
||||
pub struct Keypair(ed25519::SigningKey);
|
||||
|
||||
impl Keypair {
|
||||
/// Generate a new Ed25519 keypair.
|
||||
#[cfg(feature = "rand")]
|
||||
pub fn generate() -> Self {
|
||||
Keypair::from(SecretKey::generate())
|
||||
}
|
||||
@ -40,13 +41,15 @@ impl Keypair {
|
||||
/// of the secret scalar and the compressed public point,
|
||||
/// an informal standard for encoding Ed25519 keypairs.
|
||||
pub fn encode(&self) -> [u8; 64] {
|
||||
self.0.to_bytes()
|
||||
self.0.to_keypair_bytes()
|
||||
}
|
||||
|
||||
/// Decode a keypair from the format produced by `encode`,
|
||||
/// zeroing the input on success.
|
||||
pub fn decode(kp: &mut [u8]) -> Result<Self, DecodingError> {
|
||||
ed25519::Keypair::from_bytes(kp)
|
||||
let bytes = <[u8; 64]>::try_from(&*kp).map_err(InvalidLength)?;
|
||||
|
||||
ed25519::SigningKey::from_keypair_bytes(&bytes)
|
||||
.map(|k| {
|
||||
kp.zeroize();
|
||||
Keypair(k)
|
||||
@ -61,12 +64,12 @@ impl Keypair {
|
||||
|
||||
/// Get the public key of this keypair.
|
||||
pub fn public(&self) -> PublicKey {
|
||||
PublicKey(self.0.public)
|
||||
PublicKey(self.0.verifying_key())
|
||||
}
|
||||
|
||||
/// Get the secret key of this keypair.
|
||||
pub fn secret(&self) -> SecretKey {
|
||||
SecretKey::from_bytes(&mut self.0.secret.to_bytes())
|
||||
SecretKey::from_bytes(&mut self.0.to_bytes())
|
||||
.expect("ed25519::SecretKey::from_bytes(to_bytes(k)) != k")
|
||||
}
|
||||
}
|
||||
@ -74,26 +77,14 @@ impl Keypair {
|
||||
impl fmt::Debug for Keypair {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
f.debug_struct("Keypair")
|
||||
.field("public", &self.0.public)
|
||||
.field("public", &self.0.verifying_key())
|
||||
.finish()
|
||||
}
|
||||
}
|
||||
|
||||
impl Clone for Keypair {
|
||||
fn clone(&self) -> Self {
|
||||
let mut sk_bytes = self.0.secret.to_bytes();
|
||||
let secret = SecretKey::from_bytes(&mut sk_bytes)
|
||||
.expect("ed25519::SecretKey::from_bytes(to_bytes(k)) != k")
|
||||
.0;
|
||||
let public = ed25519::PublicKey::from_bytes(&self.0.public.to_bytes())
|
||||
.expect("ed25519::PublicKey::from_bytes(to_bytes(k)) != k");
|
||||
Keypair(ed25519::Keypair { secret, public })
|
||||
}
|
||||
}
|
||||
|
||||
/// Build keypair from existing ed25519 keypair
|
||||
impl From<ed25519::Keypair> for Keypair {
|
||||
fn from(kp: ed25519::Keypair) -> Self {
|
||||
impl From<ed25519::SigningKey> for Keypair {
|
||||
fn from(kp: ed25519::SigningKey) -> Self {
|
||||
Keypair(kp)
|
||||
}
|
||||
}
|
||||
@ -101,25 +92,21 @@ impl From<ed25519::Keypair> for Keypair {
|
||||
/// Demote an Ed25519 keypair to a secret key.
|
||||
impl From<Keypair> for SecretKey {
|
||||
fn from(kp: Keypair) -> Self {
|
||||
SecretKey(kp.0.secret)
|
||||
SecretKey(kp.0.to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
/// Promote an Ed25519 secret key into a keypair.
|
||||
impl From<SecretKey> for Keypair {
|
||||
fn from(sk: SecretKey) -> Self {
|
||||
let secret: ed25519::ExpandedSecretKey = (&sk.0).into();
|
||||
let public = ed25519::PublicKey::from(&secret);
|
||||
Keypair(ed25519::Keypair {
|
||||
secret: sk.0,
|
||||
public,
|
||||
})
|
||||
let signing = ed25519::SigningKey::from_bytes(&sk.0);
|
||||
Keypair(signing)
|
||||
}
|
||||
}
|
||||
|
||||
/// An Ed25519 public key.
|
||||
#[derive(PartialEq, Eq, Debug, Clone, Deserialize, Serialize)]
|
||||
pub struct PublicKey(ed25519::PublicKey);
|
||||
pub struct PublicKey(ed25519::VerifyingKey);
|
||||
|
||||
impl PublicKey {
|
||||
/// Verify the Ed25519 signature on a message using the public key.
|
||||
@ -143,26 +130,21 @@ impl PublicKey {
|
||||
|
||||
/// Decode a public key from a byte array as produced by `encode`.
|
||||
pub fn decode(bytes: &[u8]) -> Result<Self, DecodingError> {
|
||||
ed25519::PublicKey::from_bytes(bytes)
|
||||
let bytes = <[u8; 32]>::try_from(bytes).map_err(InvalidLength)?;
|
||||
ed25519::VerifyingKey::from_bytes(&bytes)
|
||||
.map_err(DecodingError::Ed25519)
|
||||
.map(PublicKey)
|
||||
}
|
||||
}
|
||||
|
||||
/// An Ed25519 secret key.
|
||||
#[derive(Clone)]
|
||||
pub struct SecretKey(pub ed25519::SecretKey);
|
||||
|
||||
/// View the bytes of the secret key.
|
||||
impl AsRef<[u8]> for SecretKey {
|
||||
fn as_ref(&self) -> &[u8] {
|
||||
self.0.as_bytes()
|
||||
}
|
||||
}
|
||||
|
||||
impl Clone for SecretKey {
|
||||
fn clone(&self) -> Self {
|
||||
let mut sk_bytes = self.0.to_bytes();
|
||||
Self::from_bytes(&mut sk_bytes).expect("ed25519::SecretKey::from_bytes(to_bytes(k)) != k")
|
||||
&self.0[..]
|
||||
}
|
||||
}
|
||||
|
||||
@ -174,14 +156,10 @@ impl fmt::Debug for SecretKey {
|
||||
|
||||
impl SecretKey {
|
||||
/// Generate a new Ed25519 secret key.
|
||||
#[cfg(feature = "rand")]
|
||||
pub fn generate() -> Self {
|
||||
let mut bytes = [0u8; 32];
|
||||
rand::thread_rng().fill_bytes(&mut bytes);
|
||||
SecretKey(
|
||||
ed25519::SecretKey::from_bytes(&bytes).expect(
|
||||
"this returns `Err` only if the length is wrong; the length is correct; qed",
|
||||
),
|
||||
)
|
||||
let signing = ed25519::SigningKey::generate(&mut rand::rngs::OsRng);
|
||||
SecretKey(signing.to_bytes())
|
||||
}
|
||||
|
||||
/// Create an Ed25519 secret key from a byte slice, zeroing the input on success.
|
||||
@ -189,7 +167,7 @@ impl SecretKey {
|
||||
/// returned.
|
||||
pub fn from_bytes(mut sk_bytes: impl AsMut<[u8]>) -> Result<Self, DecodingError> {
|
||||
let sk_bytes = sk_bytes.as_mut();
|
||||
let secret = ed25519::SecretKey::from_bytes(&*sk_bytes).map_err(DecodingError::Ed25519)?;
|
||||
let secret = <[u8; 32]>::try_from(&*sk_bytes).map_err(InvalidLength)?;
|
||||
sk_bytes.zeroize();
|
||||
Ok(SecretKey(secret))
|
||||
}
|
||||
@ -198,13 +176,14 @@ impl SecretKey {
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Deserialize, Serialize)]
|
||||
pub struct Signature(pub Vec<u8>);
|
||||
|
||||
#[cfg(test)]
|
||||
#[cfg(all(test, feature = "rand"))]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use crate::KeyPair;
|
||||
use quickcheck::*;
|
||||
|
||||
fn eq_keypairs(kp1: &Keypair, kp2: &Keypair) -> bool {
|
||||
kp1.public() == kp2.public() && kp1.0.secret.as_bytes() == kp2.0.secret.as_bytes()
|
||||
kp1.public() == kp2.public() && kp1.0.to_bytes() == kp2.0.to_bytes()
|
||||
}
|
||||
|
||||
#[test]
|
||||
@ -218,11 +197,22 @@ mod tests {
|
||||
QuickCheck::new().tests(10).quickcheck(prop as fn() -> _);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn ed25519_keypair_convert() {
|
||||
fn prop() -> bool {
|
||||
let kp1 = KeyPair::generate_ed25519();
|
||||
let libp2p_kp: libp2p_identity::Keypair = kp1.clone().into();
|
||||
let kp2: KeyPair = libp2p_kp.into();
|
||||
kp1.public() == kp2.public() && kp1.secret().unwrap() == kp2.secret().unwrap()
|
||||
}
|
||||
QuickCheck::new().tests(10).quickcheck(prop as fn() -> _);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn ed25519_keypair_from_secret() {
|
||||
fn prop() -> bool {
|
||||
let kp1 = Keypair::generate();
|
||||
let mut sk = kp1.0.secret.to_bytes();
|
||||
let mut sk = kp1.0.to_bytes();
|
||||
let kp2 = Keypair::from(SecretKey::from_bytes(&mut sk).unwrap());
|
||||
eq_keypairs(&kp1, &kp2) && sk == [0u8; 32]
|
||||
}
|
||||
|
@ -31,18 +31,14 @@ pub enum Error {
|
||||
/// An error during decoding of key material.
|
||||
#[derive(ThisError, Debug)]
|
||||
pub enum DecodingError {
|
||||
#[error("Failed to decode, invalid length: {0}")]
|
||||
InvalidLength(#[from] std::array::TryFromSliceError),
|
||||
#[error("Failed to decode with ed25519: {0}")]
|
||||
Ed25519(
|
||||
#[from]
|
||||
#[source]
|
||||
ed25519_dalek::ed25519::Error,
|
||||
),
|
||||
#[error("Failed to decode with RSA")]
|
||||
Rsa,
|
||||
#[error("Failed to decode with secp256k1")]
|
||||
Secp256k1,
|
||||
#[error("RSA keypair decoding is not supported yet")]
|
||||
KeypairDecodingIsNotSupported,
|
||||
#[error("Invalid type prefix")]
|
||||
InvalidTypeByte,
|
||||
#[error("Cannot decode public key from base58 :{0}")]
|
||||
@ -62,14 +58,6 @@ pub enum SigningError {
|
||||
#[source]
|
||||
ed25519_dalek::ed25519::Error,
|
||||
),
|
||||
#[error("Failed to sign with RSA")]
|
||||
Rsa,
|
||||
#[error("Failed to sign with secp256k1: {0}")]
|
||||
Secp256k1(
|
||||
#[from]
|
||||
#[source]
|
||||
libsecp256k1::Error,
|
||||
),
|
||||
}
|
||||
|
||||
/// An error during verification of a message.
|
||||
@ -77,11 +65,4 @@ pub enum SigningError {
|
||||
pub enum VerificationError {
|
||||
#[error("Failed to verify signature {1} with {2} ed25519 public key: {0}")]
|
||||
Ed25519(#[source] ed25519_dalek::ed25519::Error, String, String),
|
||||
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
#[error("Failed to verify signature {1} with {2} RSA public key: {0}")]
|
||||
Rsa(#[source] ring::error::Unspecified, String, String),
|
||||
|
||||
#[error("Failed to verify signature {1} with {2} secp256k1 public key: {0}")]
|
||||
Secp256k1(#[source] libsecp256k1::Error, String, String),
|
||||
}
|
||||
|
@ -22,11 +22,8 @@
|
||||
use crate::ed25519;
|
||||
use crate::error::{DecodingError, Error, SigningError, VerificationError};
|
||||
use crate::public_key::PublicKey;
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
use crate::rsa;
|
||||
use crate::secp256k1;
|
||||
use crate::signature::Signature;
|
||||
use libp2p_identity::PeerId;
|
||||
use libp2p_identity::{KeyType, Keypair, PeerId};
|
||||
use std::convert::TryFrom;
|
||||
use std::str::FromStr;
|
||||
|
||||
@ -47,13 +44,9 @@ use std::str::FromStr;
|
||||
/// let keypair = Keypair::rsa_from_pkcs8(&mut bytes);
|
||||
/// ```
|
||||
///
|
||||
|
||||
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
|
||||
pub enum KeyFormat {
|
||||
Ed25519,
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa,
|
||||
Secp256k1,
|
||||
}
|
||||
|
||||
impl FromStr for KeyFormat {
|
||||
@ -63,9 +56,6 @@ impl FromStr for KeyFormat {
|
||||
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
||||
match s {
|
||||
"ed25519" => Ok(KeyFormat::Ed25519),
|
||||
"secp256k1" => Ok(KeyFormat::Secp256k1),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
"rsa" => Ok(KeyFormat::Rsa),
|
||||
_ => Err(Error::InvalidKeyFormat(s.to_string())),
|
||||
}
|
||||
}
|
||||
@ -77,9 +67,6 @@ impl TryFrom<u8> for KeyFormat {
|
||||
fn try_from(value: u8) -> Result<Self, Self::Error> {
|
||||
match value {
|
||||
0 => Ok(KeyFormat::Ed25519),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
1 => Ok(KeyFormat::Rsa),
|
||||
2 => Ok(KeyFormat::Secp256k1),
|
||||
_ => Err(DecodingError::InvalidTypeByte),
|
||||
}
|
||||
}
|
||||
@ -89,9 +76,6 @@ impl From<KeyFormat> for u8 {
|
||||
fn from(kf: KeyFormat) -> Self {
|
||||
match kf {
|
||||
KeyFormat::Ed25519 => 0,
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => 1,
|
||||
KeyFormat::Secp256k1 => 2,
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -100,72 +84,36 @@ impl From<KeyFormat> for String {
|
||||
fn from(kf: KeyFormat) -> Self {
|
||||
match kf {
|
||||
KeyFormat::Ed25519 => "ed25519".to_string(),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => "rsa".to_string(),
|
||||
KeyFormat::Secp256k1 => "secp256k1".to_string(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone)]
|
||||
pub enum KeyPair {
|
||||
/// An Ed25519 keypair.
|
||||
Ed25519(ed25519::Keypair),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
/// An RSA keypair.
|
||||
Rsa(rsa::Keypair),
|
||||
/// A Secp256k1 keypair.
|
||||
Secp256k1(secp256k1::Keypair),
|
||||
}
|
||||
|
||||
impl KeyPair {
|
||||
#[cfg(feature = "rand")]
|
||||
pub fn generate(format: KeyFormat) -> KeyPair {
|
||||
match format {
|
||||
KeyFormat::Ed25519 => KeyPair::generate_ed25519(),
|
||||
KeyFormat::Secp256k1 => KeyPair::generate_secp256k1(),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => todo!("rsa generation is not supported yet!"),
|
||||
}
|
||||
}
|
||||
|
||||
/// Generate a new Ed25519 keypair.
|
||||
#[cfg(feature = "rand")]
|
||||
pub fn generate_ed25519() -> KeyPair {
|
||||
KeyPair::Ed25519(ed25519::Keypair::generate())
|
||||
}
|
||||
|
||||
/// Generate a new Secp256k1 keypair.
|
||||
pub fn generate_secp256k1() -> KeyPair {
|
||||
KeyPair::Secp256k1(secp256k1::Keypair::generate())
|
||||
}
|
||||
|
||||
/// Decode an keypair from a DER-encoded secret key in PKCS#8 PrivateKeyInfo
|
||||
/// format (i.e. unencrypted) as defined in [RFC5208].
|
||||
///
|
||||
/// [RFC5208]: https://tools.ietf.org/html/rfc5208#section-5
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
pub fn rsa_from_pkcs8(pkcs8_der: &mut [u8]) -> Result<KeyPair, DecodingError> {
|
||||
rsa::Keypair::from_pkcs8(pkcs8_der).map(KeyPair::Rsa)
|
||||
}
|
||||
|
||||
/// Decode a keypair from a DER-encoded Secp256k1 secret key in an ECPrivateKey
|
||||
/// structure as defined in [RFC5915].
|
||||
///
|
||||
/// [RFC5915]: https://tools.ietf.org/html/rfc5915
|
||||
pub fn secp256k1_from_der(der: &mut [u8]) -> Result<KeyPair, DecodingError> {
|
||||
secp256k1::SecretKey::from_der(der)
|
||||
.map(|sk| KeyPair::Secp256k1(secp256k1::Keypair::from(sk)))
|
||||
}
|
||||
|
||||
/// Sign a message using the private key of this keypair, producing
|
||||
/// a signature that can be verified using the corresponding public key.
|
||||
pub fn sign(&self, msg: &[u8]) -> Result<Signature, SigningError> {
|
||||
use KeyPair::*;
|
||||
match self {
|
||||
Ed25519(ref pair) => Ok(Signature::Ed25519(ed25519::Signature(pair.sign(msg)?))),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(ref pair) => Ok(Signature::Rsa(rsa::Signature(pair.sign(msg)?))),
|
||||
Secp256k1(ref pair) => Ok(Signature::Secp256k1(secp256k1::Signature(
|
||||
pair.secret().sign(msg)?,
|
||||
))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -175,9 +123,6 @@ impl KeyPair {
|
||||
|
||||
match self {
|
||||
Ed25519(_) => KeyFormat::Ed25519,
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => KeyFormat::Rsa,
|
||||
Secp256k1(_) => KeyFormat::Secp256k1,
|
||||
}
|
||||
}
|
||||
|
||||
@ -186,19 +131,13 @@ impl KeyPair {
|
||||
use KeyPair::*;
|
||||
match self {
|
||||
Ed25519(pair) => PublicKey::Ed25519(pair.public()),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(pair) => PublicKey::Rsa(pair.public()),
|
||||
Secp256k1(pair) => PublicKey::Secp256k1(pair.public().clone()),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn secret(&self) -> eyre::Result<Vec<u8>> {
|
||||
use KeyPair::*;
|
||||
match self {
|
||||
Ed25519(pair) => Ok(pair.secret().0.to_bytes().to_vec()),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => Err(eyre::eyre!("secret key is not available for RSA")),
|
||||
Secp256k1(pair) => Ok(pair.secret().to_bytes().to_vec()),
|
||||
Ed25519(pair) => Ok(pair.secret().0.to_vec()),
|
||||
}
|
||||
}
|
||||
|
||||
@ -215,9 +154,6 @@ impl KeyPair {
|
||||
use KeyPair::*;
|
||||
match self {
|
||||
Ed25519(kp) => kp.encode().to_vec(),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => todo!("rsa encoding is not supported yet!"),
|
||||
Secp256k1(kp) => kp.secret().to_bytes().to_vec(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -226,9 +162,6 @@ impl KeyPair {
|
||||
|
||||
match format {
|
||||
KeyFormat::Ed25519 => Ok(Ed25519(ed25519::Keypair::decode(&mut bytes)?)),
|
||||
KeyFormat::Secp256k1 => Ok(Secp256k1(secp256k1::SecretKey::from_bytes(bytes)?.into())),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => Err(DecodingError::KeypairDecodingIsNotSupported),
|
||||
}
|
||||
}
|
||||
|
||||
@ -237,9 +170,6 @@ impl KeyPair {
|
||||
|
||||
match format {
|
||||
KeyFormat::Ed25519 => Ok(Ed25519(ed25519::SecretKey::from_bytes(bytes)?.into())),
|
||||
KeyFormat::Secp256k1 => Ok(Secp256k1(secp256k1::SecretKey::from_bytes(bytes)?.into())),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => Err(DecodingError::KeypairDecodingIsNotSupported),
|
||||
}
|
||||
}
|
||||
|
||||
@ -250,42 +180,33 @@ impl KeyPair {
|
||||
|
||||
impl From<libp2p_identity::Keypair> for KeyPair {
|
||||
fn from(key: libp2p_identity::Keypair) -> Self {
|
||||
use libp2p_identity::Keypair::*;
|
||||
|
||||
#[allow(deprecated)] //TODO: fix it later
|
||||
match key {
|
||||
Ed25519(kp) => KeyPair::Ed25519(ed25519::Keypair::decode(&mut kp.encode()).unwrap()),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
// safety: these Keypair structures are identical
|
||||
Rsa(kp) => KeyPair::Rsa(unsafe {
|
||||
std::mem::transmute::<libp2p_identity::rsa::Keypair, rsa::Keypair>(kp)
|
||||
}),
|
||||
Secp256k1(kp) => KeyPair::Secp256k1(secp256k1::Keypair::from(
|
||||
secp256k1::SecretKey::from_bytes(kp.secret().to_bytes()).unwrap(),
|
||||
)),
|
||||
fn convert_keypair(key: Keypair) -> eyre::Result<KeyPair> {
|
||||
match key.key_type() {
|
||||
KeyType::Ed25519 => {
|
||||
let kp = key.try_into_ed25519()?;
|
||||
let raw_kp = ed25519::Keypair::decode(&mut kp.to_bytes())?;
|
||||
Ok(KeyPair::Ed25519(raw_kp))
|
||||
}
|
||||
_ => unimplemented!("key type not supported: {:?}", key.key_type()),
|
||||
}
|
||||
}
|
||||
|
||||
convert_keypair(key).expect("Could not convert keypair")
|
||||
}
|
||||
}
|
||||
|
||||
impl From<KeyPair> for libp2p_identity::Keypair {
|
||||
fn from(key: KeyPair) -> Self {
|
||||
use libp2p_identity::Keypair;
|
||||
use KeyPair::*;
|
||||
|
||||
#[allow(deprecated)] //TODO: fix it later
|
||||
match key {
|
||||
Ed25519(kp) => Keypair::Ed25519(
|
||||
libp2p_identity::ed25519::Keypair::decode(kp.encode().to_vec().as_mut_slice())
|
||||
.unwrap(),
|
||||
),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
// safety: these Keypair structures are identical
|
||||
Rsa(kp) => Keypair::Rsa(unsafe {
|
||||
std::mem::transmute::<rsa::Keypair, libp2p_identity::rsa::Keypair>(kp)
|
||||
}),
|
||||
Secp256k1(kp) => Keypair::Secp256k1(libp2p_identity::secp256k1::Keypair::from(
|
||||
libp2p_identity::secp256k1::SecretKey::from_bytes(kp.secret().to_bytes()).unwrap(),
|
||||
)),
|
||||
fn convert_keypair(key: KeyPair) -> eyre::Result<libp2p_identity::Keypair> {
|
||||
match key {
|
||||
KeyPair::Ed25519(kp) => {
|
||||
// for some reason, libp2p takes SecretKey's 32 bytes here instead of Keypair's 64 bytes
|
||||
let secret_bytes = kp.secret().0;
|
||||
let kp = libp2p_identity::Keypair::ed25519_from_bytes(secret_bytes)?;
|
||||
Ok(kp)
|
||||
}
|
||||
}
|
||||
}
|
||||
convert_keypair(key).expect("Could not convert key pair")
|
||||
}
|
||||
}
|
||||
|
@ -30,9 +30,6 @@ mod ed25519;
|
||||
pub mod error;
|
||||
pub mod key_pair;
|
||||
pub mod public_key;
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
mod rsa;
|
||||
mod secp256k1;
|
||||
pub mod signature;
|
||||
|
||||
pub use crate::public_key::PublicKey;
|
||||
|
@ -15,13 +15,10 @@
|
||||
*/
|
||||
use crate::ed25519;
|
||||
use crate::error::{DecodingError, VerificationError};
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
use crate::rsa;
|
||||
use crate::secp256k1;
|
||||
use crate::signature::Signature;
|
||||
|
||||
use crate::key_pair::KeyFormat;
|
||||
use libp2p_identity::PeerId;
|
||||
use libp2p_identity::{KeyType, PeerId};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::convert::TryFrom;
|
||||
|
||||
@ -30,11 +27,6 @@ use std::convert::TryFrom;
|
||||
pub enum PublicKey {
|
||||
/// A public Ed25519 key.
|
||||
Ed25519(ed25519::PublicKey),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
/// A public RSA key.
|
||||
Rsa(rsa::PublicKey),
|
||||
/// A public Secp256k1 key.
|
||||
Secp256k1(secp256k1::PublicKey),
|
||||
}
|
||||
|
||||
impl PublicKey {
|
||||
@ -47,9 +39,6 @@ impl PublicKey {
|
||||
use PublicKey::*;
|
||||
match self {
|
||||
Ed25519(pk) => pk.verify(msg, sig.to_vec()),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(pk) => pk.verify(msg, sig.to_vec()),
|
||||
Secp256k1(pk) => pk.verify(msg, sig.to_vec()),
|
||||
}
|
||||
}
|
||||
|
||||
@ -59,9 +48,6 @@ impl PublicKey {
|
||||
|
||||
match self {
|
||||
Ed25519(pk) => result.extend(pk.encode().to_vec()),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(pk) => result.extend(pk.to_pkcs1()),
|
||||
Secp256k1(pk) => result.extend(pk.encode().to_vec()),
|
||||
};
|
||||
|
||||
result
|
||||
@ -70,13 +56,6 @@ impl PublicKey {
|
||||
pub fn decode(bytes: &[u8]) -> Result<PublicKey, DecodingError> {
|
||||
match KeyFormat::try_from(bytes[0])? {
|
||||
KeyFormat::Ed25519 => Ok(PublicKey::Ed25519(ed25519::PublicKey::decode(&bytes[1..])?)),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => Ok(PublicKey::Rsa(rsa::PublicKey::from_pkcs1(
|
||||
bytes[1..].to_owned(),
|
||||
)?)),
|
||||
KeyFormat::Secp256k1 => Ok(PublicKey::Secp256k1(secp256k1::PublicKey::decode(
|
||||
&bytes[1..],
|
||||
)?)),
|
||||
}
|
||||
}
|
||||
|
||||
@ -84,9 +63,6 @@ impl PublicKey {
|
||||
use PublicKey::*;
|
||||
match self {
|
||||
Ed25519(_) => KeyFormat::Ed25519.into(),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => KeyFormat::Rsa.into(),
|
||||
Secp256k1(_) => KeyFormat::Secp256k1.into(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -102,9 +78,6 @@ impl PublicKey {
|
||||
|
||||
match self {
|
||||
Ed25519(pk) => pk.encode().to_vec(),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(pk) => pk.to_pkcs1().to_vec(),
|
||||
Secp256k1(pk) => pk.encode().to_vec(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -117,46 +90,40 @@ impl PublicKey {
|
||||
|
||||
match self {
|
||||
Ed25519(_) => KeyFormat::Ed25519,
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => KeyFormat::Rsa,
|
||||
Secp256k1(_) => KeyFormat::Secp256k1,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<libp2p_identity::PublicKey> for PublicKey {
|
||||
fn from(key: libp2p_identity::PublicKey) -> Self {
|
||||
use libp2p_identity::PublicKey::*;
|
||||
|
||||
#[allow(deprecated)] //TODO: fix it later
|
||||
match key {
|
||||
Ed25519(key) => {
|
||||
PublicKey::Ed25519(ed25519::PublicKey::decode(&key.encode()[..]).unwrap())
|
||||
}
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(key) => PublicKey::Rsa(rsa::PublicKey::from_pkcs1(key.encode_pkcs1()).unwrap()),
|
||||
Secp256k1(key) => {
|
||||
PublicKey::Secp256k1(secp256k1::PublicKey::decode(&key.encode()[..]).unwrap())
|
||||
fn convert_key(key: libp2p_identity::PublicKey) -> eyre::Result<PublicKey> {
|
||||
match key.key_type() {
|
||||
KeyType::Ed25519 => {
|
||||
let pk = key.try_into_ed25519()?;
|
||||
let raw_pk = ed25519::PublicKey::decode(&pk.to_bytes())?;
|
||||
Ok(PublicKey::Ed25519(raw_pk))
|
||||
}
|
||||
_ => unimplemented!("key not supported: {:?}", key.key_type()),
|
||||
}
|
||||
}
|
||||
|
||||
convert_key(key).expect("Could not convert public key")
|
||||
}
|
||||
}
|
||||
|
||||
impl From<PublicKey> for libp2p_identity::PublicKey {
|
||||
fn from(key: PublicKey) -> Self {
|
||||
#[allow(deprecated)] //TODO: fix it later
|
||||
match key {
|
||||
PublicKey::Ed25519(key) => libp2p_identity::PublicKey::Ed25519(
|
||||
libp2p_identity::ed25519::PublicKey::decode(&key.encode()[..]).unwrap(),
|
||||
),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
PublicKey::Rsa(key) => libp2p_identity::PublicKey::Rsa(
|
||||
libp2p_identity::rsa::PublicKey::decode_x509(&key.encode_x509()).unwrap(),
|
||||
),
|
||||
PublicKey::Secp256k1(key) => libp2p_identity::PublicKey::Secp256k1(
|
||||
libp2p_identity::secp256k1::PublicKey::decode(&key.encode()[..]).unwrap(),
|
||||
),
|
||||
fn convert_key(key: PublicKey) -> eyre::Result<libp2p_identity::PublicKey> {
|
||||
match key {
|
||||
PublicKey::Ed25519(key) => {
|
||||
let raw_pk =
|
||||
libp2p_identity::ed25519::PublicKey::try_from_bytes(&key.encode())?;
|
||||
let pk = libp2p_identity::PublicKey::from(raw_pk);
|
||||
Ok(pk)
|
||||
}
|
||||
}
|
||||
}
|
||||
convert_key(key).expect("Could not convert key")
|
||||
}
|
||||
}
|
||||
|
||||
@ -176,13 +143,13 @@ fn as_public_key(peer_id: &PeerId) -> Option<libp2p_identity::PublicKey> {
|
||||
|
||||
match multihash::Code::try_from(mhash.code()) {
|
||||
Ok(multihash::Code::Identity) => {
|
||||
libp2p_identity::PublicKey::from_protobuf_encoding(mhash.digest()).ok()
|
||||
libp2p_identity::PublicKey::try_decode_protobuf(mhash.digest()).ok()
|
||||
}
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
#[cfg(all(test, feature = "rand"))]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use crate::KeyPair;
|
||||
@ -195,17 +162,9 @@ mod tests {
|
||||
assert_eq!(pk, PublicKey::decode(&encoded_pk).unwrap());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn public_key_encode_decode_secp256k1() {
|
||||
let kp = KeyPair::generate_secp256k1();
|
||||
let pk = kp.public();
|
||||
let encoded_pk = pk.encode();
|
||||
assert_eq!(pk, PublicKey::decode(&encoded_pk).unwrap());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn public_key_peer_id_conversions() {
|
||||
let kp = KeyPair::generate_secp256k1();
|
||||
let kp = KeyPair::generate_ed25519();
|
||||
let fluence_pk = kp.public();
|
||||
let libp2p_pk: libp2p_identity::PublicKey = fluence_pk.clone().into();
|
||||
let peer_id = PeerId::from_public_key(&libp2p_pk);
|
||||
|
@ -1,286 +0,0 @@
|
||||
// Copyright 2019 Parity Technologies (UK) Ltd.
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
//! RSA keys.
|
||||
use crate::error::{DecodingError, SigningError, VerificationError};
|
||||
|
||||
use asn1_der::{Asn1Der, Asn1DerError, DerObject, DerTag, DerValue, FromDerObject, IntoDerObject};
|
||||
use lazy_static::lazy_static;
|
||||
use ring::rand::SystemRandom;
|
||||
use ring::signature::KeyPair;
|
||||
use ring::signature::{self, RsaKeyPair, RSA_PKCS1_2048_8192_SHA256, RSA_PKCS1_SHA256};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::{
|
||||
fmt::{self, Write},
|
||||
sync::Arc,
|
||||
};
|
||||
use zeroize::Zeroize;
|
||||
|
||||
/// An RSA keypair.
|
||||
#[derive(Clone)]
|
||||
pub struct Keypair(Arc<RsaKeyPair>);
|
||||
|
||||
impl Keypair {
|
||||
/// Decode an RSA keypair from a DER-encoded private key in PKCS#8 PrivateKeyInfo
|
||||
/// format (i.e. unencrypted) as defined in [RFC5208].
|
||||
///
|
||||
/// [RFC5208]: https://tools.ietf.org/html/rfc5208#section-5
|
||||
pub fn from_pkcs8(der: &mut [u8]) -> Result<Self, DecodingError> {
|
||||
let kp = RsaKeyPair::from_pkcs8(der).map_err(|_| DecodingError::Rsa)?;
|
||||
der.zeroize();
|
||||
Ok(Keypair(Arc::new(kp)))
|
||||
}
|
||||
|
||||
/// Get the public key from the keypair.
|
||||
pub fn public(&self) -> PublicKey {
|
||||
PublicKey(self.0.public_key().as_ref().to_vec())
|
||||
}
|
||||
|
||||
/// Sign a message with this keypair.
|
||||
pub fn sign(&self, data: &[u8]) -> Result<Vec<u8>, SigningError> {
|
||||
let mut signature = vec![0; self.0.public_modulus_len()];
|
||||
let rng = SystemRandom::new();
|
||||
match self.0.sign(&RSA_PKCS1_SHA256, &rng, data, &mut signature) {
|
||||
Ok(()) => Ok(signature),
|
||||
Err(_) => Err(SigningError::Rsa),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// An RSA public key.
|
||||
#[derive(Clone, PartialEq, Eq, Serialize, Deserialize)]
|
||||
pub struct PublicKey(Vec<u8>);
|
||||
|
||||
impl PublicKey {
|
||||
/// Verify an RSA signature on a message using the public key.
|
||||
pub fn verify(&self, msg: &[u8], sig: &[u8]) -> Result<(), VerificationError> {
|
||||
let key = signature::UnparsedPublicKey::new(&RSA_PKCS1_2048_8192_SHA256, &self.0);
|
||||
key.verify(msg, sig).map_err(|e| {
|
||||
VerificationError::Rsa(
|
||||
e,
|
||||
bs58::encode(sig).into_string(),
|
||||
bs58::encode(&self.0).into_string(),
|
||||
)
|
||||
})
|
||||
}
|
||||
|
||||
/// Encode the RSA public key in DER as a PKCS#1 RSAPublicKey structure,
|
||||
/// as defined in [RFC3447].
|
||||
///
|
||||
/// [RFC3447]: https://tools.ietf.org/html/rfc3447#appendix-A.1.1
|
||||
pub fn to_pkcs1(&self) -> &[u8] {
|
||||
// This is the encoding currently used in-memory, so it is trivial.
|
||||
&self.0
|
||||
}
|
||||
|
||||
pub fn from_pkcs1(pk: Vec<u8>) -> Result<Self, DecodingError> {
|
||||
Ok(PublicKey(pk))
|
||||
}
|
||||
|
||||
/// Encode the RSA public key in DER as a X.509 SubjectPublicKeyInfo structure,
|
||||
/// as defined in [RFC5280].
|
||||
///
|
||||
/// [RFC5280]: https://tools.ietf.org/html/rfc5280#section-4.1
|
||||
pub fn encode_x509(&self) -> Vec<u8> {
|
||||
let spki = Asn1SubjectPublicKeyInfo {
|
||||
algorithmIdentifier: Asn1RsaEncryption {
|
||||
algorithm: Asn1OidRsaEncryption(),
|
||||
parameters: (),
|
||||
},
|
||||
subjectPublicKey: Asn1SubjectPublicKey(self.clone()),
|
||||
};
|
||||
let mut buf = vec![0u8; spki.serialized_len()];
|
||||
spki.serialize(buf.iter_mut())
|
||||
.map(|_| buf)
|
||||
.expect("RSA X.509 public key encoding failed.")
|
||||
}
|
||||
|
||||
/// Decode an RSA public key from a DER-encoded X.509 SubjectPublicKeyInfo
|
||||
/// structure. See also `encode_x509`.
|
||||
pub fn decode_x509(pk: &[u8]) -> Result<Self, DecodingError> {
|
||||
Asn1SubjectPublicKeyInfo::deserialize(pk.iter())
|
||||
.map_err(|_| DecodingError::Rsa)
|
||||
.map(|spki| spki.subjectPublicKey.0)
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Debug for PublicKey {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
let bytes = &self.0;
|
||||
let mut hex = String::with_capacity(bytes.len() * 2);
|
||||
|
||||
for byte in bytes {
|
||||
write!(hex, "{byte:02x}").expect("Can't fail on writing to string");
|
||||
}
|
||||
|
||||
f.debug_struct("PublicKey").field("pkcs1", &hex).finish()
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
// DER encoding / decoding of public keys
|
||||
//
|
||||
// Primer: http://luca.ntop.org/Teaching/Appunti/asn1.html
|
||||
// Playground: https://lapo.it/asn1js/
|
||||
|
||||
lazy_static! {
|
||||
/// The DER encoding of the object identifier (OID) 'rsaEncryption' for
|
||||
/// RSA public keys defined for X.509 in [RFC-3279] and used in
|
||||
/// SubjectPublicKeyInfo structures defined in [RFC-5280].
|
||||
///
|
||||
/// [RFC-3279]: https://tools.ietf.org/html/rfc3279#section-2.3.1
|
||||
/// [RFC-5280]: https://tools.ietf.org/html/rfc5280#section-4.1
|
||||
static ref OID_RSA_ENCRYPTION_DER: DerObject =
|
||||
DerObject {
|
||||
tag: DerTag::x06,
|
||||
value: DerValue {
|
||||
data: vec![ 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x01 ]
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
/// The ASN.1 OID for "rsaEncryption".
|
||||
#[derive(Clone)]
|
||||
struct Asn1OidRsaEncryption();
|
||||
|
||||
impl IntoDerObject for Asn1OidRsaEncryption {
|
||||
fn into_der_object(self) -> DerObject {
|
||||
OID_RSA_ENCRYPTION_DER.clone()
|
||||
}
|
||||
fn serialized_len(&self) -> usize {
|
||||
OID_RSA_ENCRYPTION_DER.serialized_len()
|
||||
}
|
||||
}
|
||||
|
||||
impl FromDerObject for Asn1OidRsaEncryption {
|
||||
fn from_der_object(o: DerObject) -> Result<Self, Asn1DerError> {
|
||||
if o.tag != DerTag::x06 {
|
||||
return Err(Asn1DerError::InvalidTag);
|
||||
}
|
||||
if o.value != OID_RSA_ENCRYPTION_DER.value {
|
||||
return Err(Asn1DerError::InvalidEncoding);
|
||||
}
|
||||
Ok(Asn1OidRsaEncryption())
|
||||
}
|
||||
}
|
||||
|
||||
/// The ASN.1 AlgorithmIdentifier for "rsaEncryption".
|
||||
#[derive(Asn1Der)]
|
||||
struct Asn1RsaEncryption {
|
||||
algorithm: Asn1OidRsaEncryption,
|
||||
parameters: (),
|
||||
}
|
||||
|
||||
/// The ASN.1 SubjectPublicKey inside a SubjectPublicKeyInfo,
|
||||
/// i.e. encoded as a DER BIT STRING.
|
||||
struct Asn1SubjectPublicKey(PublicKey);
|
||||
|
||||
impl IntoDerObject for Asn1SubjectPublicKey {
|
||||
fn into_der_object(self) -> DerObject {
|
||||
let pk_der = (self.0).0;
|
||||
let mut bit_string = Vec::with_capacity(pk_der.len() + 1);
|
||||
// The number of bits in pk_der is trivially always a multiple of 8,
|
||||
// so there are always 0 "unused bits" signaled by the first byte.
|
||||
bit_string.push(0u8);
|
||||
bit_string.extend(pk_der);
|
||||
DerObject::new(DerTag::x03, bit_string.into())
|
||||
}
|
||||
fn serialized_len(&self) -> usize {
|
||||
DerObject::compute_serialized_len((self.0).0.len() + 1)
|
||||
}
|
||||
}
|
||||
|
||||
impl FromDerObject for Asn1SubjectPublicKey {
|
||||
fn from_der_object(o: DerObject) -> Result<Self, Asn1DerError> {
|
||||
if o.tag != DerTag::x03 {
|
||||
return Err(Asn1DerError::InvalidTag);
|
||||
}
|
||||
let pk_der: Vec<u8> = o.value.data.into_iter().skip(1).collect();
|
||||
// We don't parse pk_der further as an ASN.1 RsaPublicKey, since
|
||||
// we only need the DER encoding for `verify`.
|
||||
Ok(Asn1SubjectPublicKey(PublicKey(pk_der)))
|
||||
}
|
||||
}
|
||||
|
||||
/// ASN.1 SubjectPublicKeyInfo
|
||||
#[derive(Asn1Der)]
|
||||
#[allow(non_snake_case)]
|
||||
struct Asn1SubjectPublicKeyInfo {
|
||||
algorithmIdentifier: Asn1RsaEncryption,
|
||||
subjectPublicKey: Asn1SubjectPublicKey,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
|
||||
pub struct Signature(pub Vec<u8>);
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use quickcheck::*;
|
||||
use std::fmt;
|
||||
|
||||
const KEY1: &'static [u8] = include_bytes!("test/rsa-2048.pk8");
|
||||
const KEY2: &'static [u8] = include_bytes!("test/rsa-3072.pk8");
|
||||
const KEY3: &'static [u8] = include_bytes!("test/rsa-4096.pk8");
|
||||
|
||||
#[derive(Clone)]
|
||||
struct SomeKeypair(Keypair);
|
||||
|
||||
impl fmt::Debug for SomeKeypair {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
write!(f, "SomeKeypair")
|
||||
}
|
||||
}
|
||||
|
||||
impl Arbitrary for SomeKeypair {
|
||||
fn arbitrary(g: &mut Gen) -> SomeKeypair {
|
||||
let mut key = g.choose(&[KEY1, KEY2, KEY3]).unwrap().to_vec();
|
||||
SomeKeypair(Keypair::from_pkcs8(&mut key).unwrap())
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn rsa_from_pkcs8() {
|
||||
assert!(Keypair::from_pkcs8(&mut KEY1.to_vec()).is_ok());
|
||||
assert!(Keypair::from_pkcs8(&mut KEY2.to_vec()).is_ok());
|
||||
assert!(Keypair::from_pkcs8(&mut KEY3.to_vec()).is_ok());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn rsa_x509_encode_decode() {
|
||||
fn prop(SomeKeypair(kp): SomeKeypair) -> Result<bool, String> {
|
||||
let pk = kp.public();
|
||||
PublicKey::decode_x509(&pk.encode_x509())
|
||||
.map_err(|e| e.to_string())
|
||||
.map(|pk2| pk2 == pk)
|
||||
}
|
||||
QuickCheck::new().tests(10).quickcheck(prop as fn(_) -> _);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn rsa_sign_verify() {
|
||||
fn prop(SomeKeypair(kp): SomeKeypair, msg: Vec<u8>) -> Result<bool, SigningError> {
|
||||
kp.sign(&msg).map(|s| kp.public().verify(&msg, &s).is_ok())
|
||||
}
|
||||
QuickCheck::new()
|
||||
.tests(10)
|
||||
.quickcheck(prop as fn(_, _) -> _);
|
||||
}
|
||||
}
|
@ -1,242 +0,0 @@
|
||||
// Copyright 2019 Parity Technologies (UK) Ltd.
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the "Software"),
|
||||
// to deal in the Software without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Software, and to permit persons to whom the
|
||||
// Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
//! Secp256k1 keys.
|
||||
use crate::error::{DecodingError, SigningError, VerificationError};
|
||||
|
||||
use asn1_der::{DerObject, FromDerObject};
|
||||
use core::fmt;
|
||||
use libsecp256k1::Message;
|
||||
use rand::RngCore;
|
||||
use serde::de::Error as SerdeError;
|
||||
use serde::{Deserialize, Deserializer, Serialize, Serializer};
|
||||
use serde_bytes::{ByteBuf as SerdeByteBuf, Bytes as SerdeBytes};
|
||||
use sha2::{Digest as ShaDigestTrait, Sha256};
|
||||
use zeroize::Zeroize;
|
||||
|
||||
/// A Secp256k1 keypair.
|
||||
#[derive(Clone)]
|
||||
pub struct Keypair {
|
||||
secret: SecretKey,
|
||||
public: PublicKey,
|
||||
}
|
||||
|
||||
impl Keypair {
|
||||
/// Generate a new sec256k1 `Keypair`.
|
||||
pub fn generate() -> Self {
|
||||
Keypair::from(SecretKey::generate())
|
||||
}
|
||||
|
||||
/// Get the public key of this keypair.
|
||||
pub fn public(&self) -> &PublicKey {
|
||||
&self.public
|
||||
}
|
||||
|
||||
/// Get the secret key of this keypair.
|
||||
pub fn secret(&self) -> &SecretKey {
|
||||
&self.secret
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Debug for Keypair {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
f.debug_struct("Keypair")
|
||||
.field("public", &self.public)
|
||||
.finish()
|
||||
}
|
||||
}
|
||||
|
||||
/// Promote a Secp256k1 secret key into a keypair.
|
||||
impl From<SecretKey> for Keypair {
|
||||
fn from(secret: SecretKey) -> Self {
|
||||
let public = PublicKey(libsecp256k1::PublicKey::from_secret_key(&secret.0));
|
||||
Keypair { secret, public }
|
||||
}
|
||||
}
|
||||
|
||||
/// Demote a Secp256k1 keypair into a secret key.
|
||||
impl From<Keypair> for SecretKey {
|
||||
fn from(kp: Keypair) -> Self {
|
||||
kp.secret
|
||||
}
|
||||
}
|
||||
|
||||
/// A Secp256k1 secret key.
|
||||
#[derive(Clone)]
|
||||
pub struct SecretKey(libsecp256k1::SecretKey);
|
||||
|
||||
impl fmt::Debug for SecretKey {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
write!(f, "SecretKey")
|
||||
}
|
||||
}
|
||||
|
||||
impl SecretKey {
|
||||
/// Generate a new Secp256k1 secret key.
|
||||
pub fn generate() -> Self {
|
||||
let mut r = rand::thread_rng();
|
||||
let mut b = [0; libsecp256k1::util::SECRET_KEY_SIZE];
|
||||
// This is how it is done in `secp256k1::SecretKey::random` which
|
||||
// we do not use here because it uses `rand::Rng` from rand-0.4.
|
||||
loop {
|
||||
r.fill_bytes(&mut b);
|
||||
if let Ok(k) = libsecp256k1::SecretKey::parse(&b) {
|
||||
return SecretKey(k);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Create a secret key from a byte slice, zeroing the slice on success.
|
||||
/// If the bytes do not constitute a valid Secp256k1 secret key, an
|
||||
/// error is returned.
|
||||
pub fn from_bytes(mut sk: impl AsMut<[u8]>) -> Result<Self, DecodingError> {
|
||||
let sk_bytes = sk.as_mut();
|
||||
let secret = libsecp256k1::SecretKey::parse_slice(&*sk_bytes)
|
||||
.map_err(|_| DecodingError::Secp256k1)?;
|
||||
sk_bytes.zeroize();
|
||||
Ok(SecretKey(secret))
|
||||
}
|
||||
|
||||
/// Decode a DER-encoded Secp256k1 secret key in an ECPrivateKey
|
||||
/// structure as defined in [RFC5915].
|
||||
///
|
||||
/// [RFC5915]: https://tools.ietf.org/html/rfc5915
|
||||
pub fn from_der(mut der: impl AsMut<[u8]>) -> Result<SecretKey, DecodingError> {
|
||||
// TODO: Stricter parsing.
|
||||
let der_obj = der.as_mut();
|
||||
let obj: Vec<DerObject> =
|
||||
FromDerObject::deserialize((*der_obj).iter()).map_err(|_| DecodingError::Secp256k1)?;
|
||||
der_obj.zeroize();
|
||||
let sk_obj = obj.into_iter().nth(1).ok_or(DecodingError::Secp256k1)?;
|
||||
let mut sk_bytes: Vec<u8> =
|
||||
FromDerObject::from_der_object(sk_obj).map_err(|_| DecodingError::Secp256k1)?;
|
||||
let sk = SecretKey::from_bytes(&mut sk_bytes)?;
|
||||
sk_bytes.zeroize();
|
||||
Ok(sk)
|
||||
}
|
||||
|
||||
/// Sign a message with this secret key, producing a DER-encoded
|
||||
/// ECDSA signature, as defined in [RFC3278].
|
||||
///
|
||||
/// [RFC3278]: https://tools.ietf.org/html/rfc3278#section-8.2
|
||||
pub fn sign(&self, msg: &[u8]) -> Result<Vec<u8>, SigningError> {
|
||||
self.sign_hashed(Sha256::digest(msg).as_ref())
|
||||
}
|
||||
|
||||
/// Returns the raw bytes of the secret key.
|
||||
pub fn to_bytes(&self) -> [u8; 32] {
|
||||
self.0.serialize()
|
||||
}
|
||||
|
||||
/// Sign a raw message of length 256 bits with this secret key, produces a DER-encoded
|
||||
/// ECDSA signature.
|
||||
pub fn sign_hashed(&self, msg: &[u8]) -> Result<Vec<u8>, SigningError> {
|
||||
let m = Message::parse_slice(msg).map_err(SigningError::Secp256k1)?;
|
||||
Ok(libsecp256k1::sign(&m, &self.0)
|
||||
.0
|
||||
.serialize_der()
|
||||
.as_ref()
|
||||
.into())
|
||||
}
|
||||
}
|
||||
|
||||
/// A Secp256k1 public key.
|
||||
#[derive(PartialEq, Eq, Clone, Debug)]
|
||||
pub struct PublicKey(libsecp256k1::PublicKey);
|
||||
|
||||
impl PublicKey {
|
||||
/// Verify the Secp256k1 signature on a message using the public key.
|
||||
pub fn verify(&self, msg: &[u8], sig: &[u8]) -> Result<(), VerificationError> {
|
||||
self.verify_hashed(Sha256::digest(msg).as_ref(), sig)
|
||||
}
|
||||
|
||||
/// Verify the Secp256k1 DER-encoded signature on a raw 256-bit message using the public key.
|
||||
pub fn verify_hashed(&self, msg: &[u8], sig: &[u8]) -> Result<(), VerificationError> {
|
||||
Message::parse_slice(msg)
|
||||
.and_then(|m| {
|
||||
libsecp256k1::Signature::parse_der(sig)
|
||||
.map(|s| libsecp256k1::verify(&m, &s, &self.0))
|
||||
})
|
||||
.map_err(|e| {
|
||||
VerificationError::Secp256k1(
|
||||
e,
|
||||
bs58::encode(sig).into_string(),
|
||||
bs58::encode(self.0.serialize_compressed()).into_string(),
|
||||
)
|
||||
})
|
||||
.map(|_| ())
|
||||
}
|
||||
|
||||
/// Encode the public key in compressed form, i.e. with one coordinate
|
||||
/// represented by a single bit.
|
||||
pub fn encode(&self) -> [u8; 33] {
|
||||
self.0.serialize_compressed()
|
||||
}
|
||||
|
||||
/// Encode the public key in uncompressed form.
|
||||
pub fn encode_uncompressed(&self) -> [u8; 65] {
|
||||
self.0.serialize()
|
||||
}
|
||||
|
||||
/// Decode a public key from a byte slice in the the format produced
|
||||
/// by `encode`.
|
||||
pub fn decode(bytes: &[u8]) -> Result<Self, DecodingError> {
|
||||
libsecp256k1::PublicKey::parse_slice(bytes, Some(libsecp256k1::PublicKeyFormat::Compressed))
|
||||
.map_err(|_| DecodingError::Secp256k1)
|
||||
.map(PublicKey)
|
||||
}
|
||||
}
|
||||
|
||||
impl Serialize for PublicKey {
|
||||
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
||||
where
|
||||
S: Serializer,
|
||||
{
|
||||
SerdeBytes::new(self.encode().to_vec().as_slice()).serialize(serializer)
|
||||
}
|
||||
}
|
||||
|
||||
impl<'d> Deserialize<'d> for PublicKey {
|
||||
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
|
||||
where
|
||||
D: Deserializer<'d>,
|
||||
{
|
||||
let bytes = <SerdeByteBuf>::deserialize(deserializer)?;
|
||||
PublicKey::decode(bytes.as_slice()).map_err(SerdeError::custom)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
|
||||
pub struct Signature(pub Vec<u8>);
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn secp256k1_secret_from_bytes() {
|
||||
let sk1 = SecretKey::generate();
|
||||
let mut sk_bytes = [0; 32];
|
||||
sk_bytes.copy_from_slice(&sk1.0.serialize()[..]);
|
||||
let sk2 = SecretKey::from_bytes(&mut sk_bytes).unwrap();
|
||||
assert_eq!(sk1.0.serialize(), sk2.0.serialize());
|
||||
assert_eq!(sk_bytes, [0; 32]);
|
||||
}
|
||||
}
|
@ -16,18 +16,12 @@
|
||||
use crate::ed25519;
|
||||
use crate::error::DecodingError;
|
||||
use crate::key_pair::KeyFormat;
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
use crate::rsa;
|
||||
use crate::secp256k1;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::convert::TryFrom;
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Deserialize, Serialize)]
|
||||
pub enum Signature {
|
||||
Ed25519(ed25519::Signature),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(rsa::Signature),
|
||||
Secp256k1(secp256k1::Signature),
|
||||
}
|
||||
|
||||
pub struct RawSignature {
|
||||
@ -40,9 +34,6 @@ impl Signature {
|
||||
use Signature::*;
|
||||
match self {
|
||||
Ed25519(_) => KeyFormat::Ed25519.into(),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => KeyFormat::Rsa.into(),
|
||||
Secp256k1(_) => KeyFormat::Secp256k1.into(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -54,9 +45,6 @@ impl Signature {
|
||||
|
||||
match self {
|
||||
Ed25519(sig) => result.extend(sig.0.clone()),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(sig) => result.extend(sig.0.clone()),
|
||||
Secp256k1(sig) => result.extend(sig.0.clone()),
|
||||
}
|
||||
|
||||
result
|
||||
@ -66,11 +54,6 @@ impl Signature {
|
||||
pub fn decode(bytes: Vec<u8>) -> Result<Self, DecodingError> {
|
||||
match KeyFormat::try_from(bytes[0])? {
|
||||
KeyFormat::Ed25519 => Ok(Signature::Ed25519(ed25519::Signature(bytes[1..].to_vec()))),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => Ok(Signature::Rsa(rsa::Signature(bytes[1..].to_vec()))),
|
||||
KeyFormat::Secp256k1 => Ok(Signature::Secp256k1(secp256k1::Signature(
|
||||
bytes[1..].to_vec(),
|
||||
))),
|
||||
}
|
||||
}
|
||||
|
||||
@ -79,9 +62,6 @@ impl Signature {
|
||||
|
||||
match self {
|
||||
Ed25519(sig) => &sig.0,
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(sig) => &sig.0,
|
||||
Secp256k1(sig) => &sig.0,
|
||||
}
|
||||
}
|
||||
|
||||
@ -90,9 +70,6 @@ impl Signature {
|
||||
|
||||
match self {
|
||||
Ed25519(_) => KeyFormat::Ed25519,
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
Rsa(_) => KeyFormat::Rsa,
|
||||
Secp256k1(_) => KeyFormat::Secp256k1,
|
||||
}
|
||||
}
|
||||
|
||||
@ -106,9 +83,6 @@ impl Signature {
|
||||
pub fn from_bytes(key_format: KeyFormat, bytes: Vec<u8>) -> Self {
|
||||
match key_format {
|
||||
KeyFormat::Ed25519 => Signature::Ed25519(ed25519::Signature(bytes)),
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
KeyFormat::Rsa => Signature::Rsa(rsa::Signature(bytes)),
|
||||
KeyFormat::Secp256k1 => Signature::Secp256k1(secp256k1::Signature(bytes)),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -121,19 +95,10 @@ mod tests {
|
||||
fn signature_encode_decode() {
|
||||
let bytes: Vec<u8> = (0..10).collect();
|
||||
let ed25519_sig = Signature::Ed25519(crate::ed25519::Signature(bytes.clone()));
|
||||
let secp256k1_sig = Signature::Secp256k1(crate::secp256k1::Signature(bytes.clone()));
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
let rsa_sig = Signature::Rsa(crate::rsa::Signature(bytes.clone()));
|
||||
|
||||
assert_eq!(
|
||||
Signature::decode(ed25519_sig.encode()).unwrap(),
|
||||
ed25519_sig
|
||||
);
|
||||
assert_eq!(
|
||||
Signature::decode(secp256k1_sig.encode()).unwrap(),
|
||||
secp256k1_sig
|
||||
);
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
assert_eq!(Signature::decode(rsa_sig.encode()).unwrap(), rsa_sig);
|
||||
}
|
||||
}
|
||||
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -1,4 +1,4 @@
|
||||
[toolchain]
|
||||
channel = "nightly-2022-12-06"
|
||||
channel = "nightly-2023-12-06"
|
||||
targets = [ "x86_64-apple-darwin", "wasm32-wasi", "wasm32-unknown-unknown", "x86_64-unknown-linux-gnu" ]
|
||||
components = [ "rustfmt", "clippy" ]
|
||||
|
@ -9,6 +9,121 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
||||
* trust-graph bumped from 0.4.1 to 0.4.2
|
||||
* fluence-keypair bumped from 0.10.0 to 0.10.1
|
||||
|
||||
## [0.4.11](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.10...trust-graph-wasm-v0.4.11) (2024-01-17)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **trust-graph:** Regenerate aqua bindings from wasm ([#155](https://github.com/fluencelabs/trust-graph/issues/155)) ([fd145c5](https://github.com/fluencelabs/trust-graph/commit/fd145c5fe1a115e87539ec5c9496d8b4c8bbc468))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.10 to 0.4.11
|
||||
|
||||
## [0.4.10](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.9...trust-graph-wasm-v0.4.10) (2024-01-03)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **trust-graph:** Revert release 0.4.10 ([#153](https://github.com/fluencelabs/trust-graph/issues/153)) ([b263ce1](https://github.com/fluencelabs/trust-graph/commit/b263ce1fb13b937b629608ede35b6f436023dcac))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.9 to 0.4.10
|
||||
|
||||
## [0.4.9](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.8...trust-graph-wasm-v0.4.9) (2023-12-28)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** update sqlite wasm ([#135](https://github.com/fluencelabs/trust-graph/issues/135)) ([c59451d](https://github.com/fluencelabs/trust-graph/commit/c59451de04ba79152fa8d600a7b456ab24766dd0))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.8 to 0.4.9
|
||||
|
||||
## [0.4.8](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.7...trust-graph-wasm-v0.4.8) (2023-12-20)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* update marine sdk's, configs and sqlite connector ([#129](https://github.com/fluencelabs/trust-graph/issues/129)) ([0b66f4e](https://github.com/fluencelabs/trust-graph/commit/0b66f4e0536633879de46f69ac8391c72ece7e77))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.7 to 0.4.8
|
||||
* fluence-keypair bumped from 0.10.3 to 0.10.4
|
||||
|
||||
## [0.4.7](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.6...trust-graph-wasm-v0.4.7) (2023-07-04)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** update rust crate marine-rs-sdk-test to 0.10.0 ([#106](https://github.com/fluencelabs/trust-graph/issues/106)) ([725d3f8](https://github.com/fluencelabs/trust-graph/commit/725d3f8f48b3bf1ed8605e9ba2da5c966a145f0d))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.6 to 0.4.7
|
||||
* fluence-keypair bumped from 0.10.2 to 0.10.3
|
||||
|
||||
## [0.4.6](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.5...trust-graph-wasm-v0.4.6) (2023-06-30)
|
||||
|
||||
|
||||
### Reverts
|
||||
|
||||
* release master ([#110](https://github.com/fluencelabs/trust-graph/issues/110)) ([d80a43b](https://github.com/fluencelabs/trust-graph/commit/d80a43bcff721aff8fadf3d2d5c252804ce27a6c))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.5 to 0.4.6
|
||||
* fluence-keypair bumped from 0.10.1 to 0.10.2
|
||||
|
||||
## [0.4.5](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.4...trust-graph-wasm-v0.4.5) (2023-05-09)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-wasm:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.4 to 0.4.5
|
||||
|
||||
## [0.4.4](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.3...trust-graph-wasm-v0.4.4) (2023-05-09)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph-wasm:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* trust-graph bumped from 0.4.3 to 0.4.4
|
||||
|
||||
## [0.4.3](https://github.com/fluencelabs/trust-graph/compare/trust-graph-wasm-v0.4.2...trust-graph-wasm-v0.4.3) (2023-05-08)
|
||||
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "trust-graph-wasm"
|
||||
version = "0.4.3"
|
||||
version = "0.4.11"
|
||||
authors = ["Fluence Labs"]
|
||||
edition = "2021"
|
||||
description = "trust graph wasm"
|
||||
@ -12,16 +12,16 @@ name = "trust-graph"
|
||||
path = "src/main.rs"
|
||||
|
||||
[dependencies]
|
||||
trust-graph = { version = "0.4.3", path = "../trust-graph" }
|
||||
fluence-keypair = { version = "0.10.1", path = "../keypair" }
|
||||
marine-rs-sdk = { version = "0.7.1", features = ["logger"] }
|
||||
marine-sqlite-connector = "0.8.0"
|
||||
trust-graph = { version = "0.4.11", path = "../trust-graph" }
|
||||
fluence-keypair = { version = "0.10.4", path = "../keypair" }
|
||||
marine-rs-sdk = { version = "0.10.2", features = ["logger"] }
|
||||
marine-sqlite-connector = "0.9.2"
|
||||
|
||||
libp2p-identity = { workspace = true }
|
||||
|
||||
log = "0.4.8"
|
||||
anyhow = "1.0.31"
|
||||
once_cell = "1.4.1"
|
||||
once_cell = "1.18.0"
|
||||
serde_json = "1.0"
|
||||
bs58 = "0.4.0"
|
||||
rmp-serde = "1.1.1"
|
||||
@ -29,8 +29,9 @@ bincode = "1.3.1"
|
||||
thiserror = "1.0.23"
|
||||
|
||||
[dev-dependencies]
|
||||
marine-rs-sdk-test = "0.9.1"
|
||||
marine-rs-sdk-test = "0.12.1"
|
||||
rusqlite = "0.28.0"
|
||||
fluence-keypair = { version = "0.10.3", path = "../keypair", features = ["rand"] }
|
||||
|
||||
[build-dependencies]
|
||||
marine-rs-sdk-test = "0.9.1"
|
||||
marine-rs-sdk-test = "0.12.1"
|
||||
|
@ -1,4 +1,5 @@
|
||||
modules_dir = "artifacts/"
|
||||
total_memory_limit = "Infinity"
|
||||
|
||||
[[module]]
|
||||
name = "sqlite3"
|
||||
|
@ -1,5 +1,7 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
set -o errexit -o nounset -o pipefail
|
||||
set -x
|
||||
|
||||
# set current working directory to script directory to run script from everywhere
|
||||
cd "$(dirname "$0")"
|
||||
@ -13,7 +15,7 @@ mkdir -p artifacts
|
||||
cp ../target/wasm32-wasi/release/trust-graph.wasm artifacts/
|
||||
|
||||
# download SQLite 3 to use in tests
|
||||
curl -sS -L https://github.com/fluencelabs/sqlite/releases/download/sqlite-wasm-v0.18.1/sqlite3.wasm -o artifacts/sqlite3.wasm
|
||||
curl -sS -L https://github.com/fluencelabs/sqlite/releases/download/sqlite-wasm-v0.18.2/sqlite3.wasm -o artifacts/sqlite3.wasm
|
||||
|
||||
# generate Aqua bindings
|
||||
marine aqua artifacts/trust-graph.wasm -s TrustGraph -i trust-graph > ../aqua/trust-graph.aqua
|
||||
|
@ -1,3 +1,3 @@
|
||||
[toolchain]
|
||||
channel = "nightly-2022-12-06"
|
||||
channel = "nightly-2023-12-06"
|
||||
targets = [ "x86_64-apple-darwin", "wasm32-wasi", "wasm32-unknown-unknown", "x86_64-unknown-linux-gnu" ]
|
||||
|
@ -37,7 +37,7 @@ pub(crate) fn check_timestamp_tetraplets(
|
||||
.get(arg_number)
|
||||
.ok_or_else(|| InvalidTimestampTetraplet(format!("{:?}", call_parameters.tetraplets)))?;
|
||||
let tetraplet = tetraplets
|
||||
.get(0)
|
||||
.first()
|
||||
.ok_or_else(|| InvalidTimestampTetraplet(format!("{:?}", call_parameters.tetraplets)))?;
|
||||
(TRUSTED_TIMESTAMP.eq(&(&tetraplet.service_id, &tetraplet.function_name))
|
||||
&& tetraplet.peer_pk == call_parameters.host_id)
|
||||
|
@ -4,6 +4,89 @@
|
||||
* dependencies
|
||||
* fluence-keypair bumped from 0.10.0 to 0.10.1
|
||||
|
||||
## [0.4.11](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.10...trust-graph-v0.4.11) (2024-01-17)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.10](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.9...trust-graph-v0.4.10) (2024-01-03)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **trust-graph:** Revert release 0.4.10 ([#153](https://github.com/fluencelabs/trust-graph/issues/153)) ([b263ce1](https://github.com/fluencelabs/trust-graph/commit/b263ce1fb13b937b629608ede35b6f436023dcac))
|
||||
|
||||
## [0.4.9](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.8...trust-graph-v0.4.9) (2023-12-28)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
## [0.4.8](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.7...trust-graph-v0.4.8) (2023-12-20)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* update marine sdk's, configs and sqlite connector ([#129](https://github.com/fluencelabs/trust-graph/issues/129)) ([0b66f4e](https://github.com/fluencelabs/trust-graph/commit/0b66f4e0536633879de46f69ac8391c72ece7e77))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* fluence-keypair bumped from 0.10.3 to 0.10.4
|
||||
|
||||
## [0.4.7](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.6...trust-graph-v0.4.7) (2023-07-04)
|
||||
|
||||
|
||||
### Miscellaneous Chores
|
||||
|
||||
* **trust-graph:** Synchronize trust-graph, wasm and api versions
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* fluence-keypair bumped from 0.10.2 to 0.10.3
|
||||
|
||||
## [0.4.6](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.5...trust-graph-v0.4.6) (2023-06-30)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **deps:** update rust crate derivative to 2.2.0 ([2001f90](https://github.com/fluencelabs/trust-graph/commit/2001f900fa13a949decd513d8cbe15e3f006a7fc))
|
||||
* **deps:** update rust crate derivative to 2.2.0 ([#88](https://github.com/fluencelabs/trust-graph/issues/88)) ([2001f90](https://github.com/fluencelabs/trust-graph/commit/2001f900fa13a949decd513d8cbe15e3f006a7fc))
|
||||
|
||||
|
||||
### Reverts
|
||||
|
||||
* release master ([#110](https://github.com/fluencelabs/trust-graph/issues/110)) ([d80a43b](https://github.com/fluencelabs/trust-graph/commit/d80a43bcff721aff8fadf3d2d5c252804ce27a6c))
|
||||
|
||||
|
||||
### Dependencies
|
||||
|
||||
* The following workspace dependencies were updated
|
||||
* dependencies
|
||||
* fluence-keypair bumped from 0.10.1 to 0.10.2
|
||||
|
||||
## [0.4.5](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.4...trust-graph-v0.4.5) (2023-05-09)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* dummy to trigger release ([#101](https://github.com/fluencelabs/trust-graph/issues/101)) ([1a26a68](https://github.com/fluencelabs/trust-graph/commit/1a26a6809ea9a90ca8ff3829a76257779a8767d5))
|
||||
|
||||
## [0.4.4](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.3...trust-graph-v0.4.4) (2023-05-09)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* fix trust-graph package ([#98](https://github.com/fluencelabs/trust-graph/issues/98)) ([a8fdb44](https://github.com/fluencelabs/trust-graph/commit/a8fdb4472ef1676724e4bfab1b4419f07faae2d9))
|
||||
|
||||
## [0.4.3](https://github.com/fluencelabs/trust-graph/compare/trust-graph-v0.4.2...trust-graph-v0.4.3) (2023-05-08)
|
||||
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "trust-graph"
|
||||
version = "0.4.3"
|
||||
version = "0.4.11"
|
||||
authors = ["Fluence Labs"]
|
||||
edition = "2021"
|
||||
description = "trust graph"
|
||||
@ -10,12 +10,12 @@ repository = "https://github.com/fluencelabs/trust-graph"
|
||||
[dependencies]
|
||||
serde = { version = "1.0.118", features = ["derive"] }
|
||||
|
||||
fluence-keypair = { path = "../keypair", version = "0.10.1" }
|
||||
fluence-keypair = { path = "../keypair", version = "0.10.4" }
|
||||
bs58 = "0.4.0"
|
||||
failure = "0.1.6"
|
||||
log = "0.4.11"
|
||||
ref-cast = "1.0.2"
|
||||
derivative = "2.1.1"
|
||||
derivative = "2.2.0"
|
||||
thiserror = "1.0.23"
|
||||
sha2 = "0.10.6"
|
||||
nonempty = "0.8.1"
|
||||
|
@ -29,7 +29,7 @@ use std::{
|
||||
#[repr(transparent)]
|
||||
pub struct PublicKeyHashable(PublicKey);
|
||||
|
||||
#[allow(clippy::derive_hash_xor_eq)]
|
||||
#[allow(clippy::derived_hash_with_manual_eq)]
|
||||
impl Hash for PublicKeyHashable {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
state.write(&self.0.encode());
|
||||
|
@ -154,7 +154,7 @@ where
|
||||
C: Borrow<Certificate>,
|
||||
{
|
||||
let chain = &cert.borrow().chain;
|
||||
let mut issued_by = chain.get(0).ok_or(EmptyChain)?.issued_for.clone();
|
||||
let mut issued_by = chain.first().ok_or(EmptyChain)?.issued_for.clone();
|
||||
|
||||
// TODO: optimize to check only root weight
|
||||
for trust in chain {
|
||||
|
Reference in New Issue
Block a user