mirror of
https://github.com/arnaucube/go-dvote.git
synced 2026-02-28 05:26:46 +01:00
Merge branch 'feature/new_merkletree'
Signed-off-by: p4u <p4u@dabax.net>
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
|
||||
Reference implementation of a voting census service running on the Vocdoni platform
|
||||
|
||||
#### Compile
|
||||
## Compile
|
||||
|
||||
In a GO ready environment:
|
||||
|
||||
@@ -11,35 +11,67 @@ go get -u github.com/vocdoni/dvote-census/...
|
||||
go build -o censusHttpService github.com/vocdoni/dvote-census/cmd/censushttp
|
||||
```
|
||||
|
||||
#### Usage
|
||||
## Usage
|
||||
|
||||
`./censusHttpService <port> [publicKey]`
|
||||
`./censusHttpService <port> <censusId>[:pubKey] [<censusId>[:pubKey] ...]`
|
||||
|
||||
Example:
|
||||
Example
|
||||
|
||||
```
|
||||
./censusHttpService 1500
|
||||
2018/12/17 09:54:20 Starting process HTTP service on port 1500
|
||||
2018/12/17 09:54:20 Starting server in http mode
|
||||
./censusHttpService 1500 Got_Favorite
|
||||
2019/02/12 10:20:16 Starting process HTTP service on port 1500 for namespace GoT_Favorite
|
||||
2019/02/12 10:20:16 Starting server in http mode
|
||||
```
|
||||
|
||||
## API
|
||||
|
||||
A HTTP jSON endpoint is available with the following possible fields: `censusId`, `claimData`, `rootHash` and `proofData`.
|
||||
|
||||
If `pubKey` has been configured for a specific `censusId`, then two more methods are available (`timeStamp` and `signature`) to provide authentication.
|
||||
|
||||
The next table shows the available methods and its relation with the fields.
|
||||
|
||||
| method | censusId | claimData | rootHash | proofData | protected? | description |
|
||||
|------------|-----------|-----------|----------|-----------|------------|------------|
|
||||
| `addCLaim` | mandatory | mandatory | none | none | yes | adds a new claim to the merkle tree |
|
||||
| `getRoot` | mandatory | none | none | none | no | get the current merkletree root hash
|
||||
| `genProof` | mandatory | mandatory | optional | none | no | generate the merkle proof for a given claim
|
||||
| `checkProof` | mandatory | mandatory | optional | mandatory | no | check a claim and its merkle proof
|
||||
| `getIdx` | mandatory | mandatory | optional | none | no | get the merkletree data index of a given claim
|
||||
| `dump` | mandatory | none | optional | none | yes | list the contents of the census for a given hash
|
||||
|
||||
|
||||
## Signature
|
||||
|
||||
The signature provides authentication by signing a concatenation of the following strings (even if empty) without spaces: `censusId rootHash claimData timeStamp`.
|
||||
|
||||
The `timeStamp` when received on the server side must not differ more than 10 seconds from the current UNIX time.
|
||||
|
||||
## Examples
|
||||
|
||||
#### add claims
|
||||
|
||||
Add two new claims, one for `Jon Snow` and another for `Tyrion`.
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow"}' http://localhost:1500/addClaim
|
||||
|
||||
{"error":false,"response":""}
|
||||
```
|
||||
|
||||
If public key authentication enabled, `signature` field is required using Nancl signature.
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Tyrion"}' http://localhost:1500/addClaim
|
||||
|
||||
The signed message is expected to be a concatenation of the following fields: `censusID, claimData, timeStamp`
|
||||
{"error":false,"response":""}
|
||||
```
|
||||
|
||||
In case signature is enabled:
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite",
|
||||
curl -d '{
|
||||
"censusID":"GoT_Favorite",
|
||||
"claimData":"Jon Snow",
|
||||
"timeStamp":"1547814675",
|
||||
"signature":"a117c4ce12b29090884112ffe57e664f007e7ef142a1679996e2d34fd2b852fe76966e47932f1e9d3a54610d0f361383afe2d9aab096e15d136c236abb0a0d0e"}' http://localhost:1500/addClaim
|
||||
"timeStamp":"1547814675",
|
||||
"signature":"a117c4ce12b29090884112ffe57e664f007e7ef142a1679996e2d34fd2b852fe76966e47932f1e9d3a54610d0f361383afe2d9aab096e15d136c236abb0a0d0e" }' http://localhost:1500/addClaim
|
||||
|
||||
{"error":false,"response":""}
|
||||
```
|
||||
@@ -47,88 +79,50 @@ curl -d '{"censusID":"GoT_Favorite",
|
||||
|
||||
#### generate proof
|
||||
|
||||
Generate a merkle proof for the claim `Jon Snow`
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow"}' http://localhost:1500/genProof
|
||||
|
||||
{"error":false,"response":"0x000000000000000000000000000000000000000000000000000000000000000352f3ca2aaf635ec2ae4452f6a65be7bca72678287a8bb08ad4babfcccd76c2fef1aac7675261bf6d12c746fb7907beea6d1f1635af93ba931eec0c6a747ecc37"}
|
||||
{"error":false,"response":"0x000200000000000000000000000000000000000000000000000000000000000212f8134039730791388a9bd0460f9fbd0757327212a64b3a2b0f0841ce561ee3"}
|
||||
```
|
||||
|
||||
If `rootHash` is specified, the proof will be calculated for the given root hash.
|
||||
|
||||
#### get root
|
||||
|
||||
The previous merkle proof is valid only for the current root hash. Let's get it
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite"}' http://localhost:1500/getRoot
|
||||
|
||||
{"error":false,"response":"0x2f0ddde5cb995eae23dc3b75a5c0333f1cc89b73f3a00b0fe71996fb90fef04b"}
|
||||
```
|
||||
|
||||
|
||||
#### check proof
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow", "proofData": "0x0000000000000000000000000000000000000000000000000000000000000000000123"}' http://localhost:1500/checkProof
|
||||
|
||||
{"error":false,"response":"invalid"}
|
||||
```
|
||||
Now let's check if the proof is valid
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow", "proofData": "0x000000000000000000000000000000000000000000000000000000000000000352f3ca2aaf635ec2ae4452f6a65be7bca72678287a8bb08ad4babfcccd76c2fef1aac7675261bf6d12c746fb7907beea6d1f1635af93ba931eec0c6a747ecc37"}' http://localhost:1500/checkProof
|
||||
curl -d '{
|
||||
"censusID":"GoT_Favorite","claimData":"Jon Snow",
|
||||
"rootHash":"0x2f0ddde5cb995eae23dc3b75a5c0333f1cc89b73f3a00b0fe71996fb90fef04b",
|
||||
"proofData":"0x000200000000000000000000000000000000000000000000000000000000000212f8134039730791388a9bd0460f9fbd0757327212a64b3a2b0f0841ce561ee3"}' http://localhost:1500/checkProof
|
||||
|
||||
{"error":false,"response":"valid"}
|
||||
```
|
||||
|
||||
#### make snapshot
|
||||
|
||||
Snapshots are static and unmutable copies of a specific census
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite"}' http://localhost:1500/snapshot
|
||||
|
||||
{"error":false,"response":"0x8647692e073a10980d821764c65ca3fddbc606bb936f9812a7a806bfa97df152"}
|
||||
```
|
||||
|
||||
The name for the snapshot is "0x8647692e073a10980d821764c65ca3fddbc606bb936f9812a7a806bfa97df152" which represents the Root Hash.
|
||||
|
||||
Now you can use it as censusID for checkProof, getRoot, genProof and dump. But addClaim is not longer allowed.
|
||||
If `rootHash` is not specified, the current root hash is used.
|
||||
|
||||
#### dump
|
||||
|
||||
Dump contents of a specific censusID (values)
|
||||
Dump contents of a specific censusId (values)
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite"}' http://localhost:1500/dump
|
||||
|
||||
{"error":false,"response":"[\"Tyrion\",\"Jon Snow\"]"}
|
||||
```
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
##### add claims
|
||||
|
||||
```
|
||||
curl -d '{"processID":"GoT_Favorite","claimData":"Jon Snow"}' http://localhost:1500/addClaim
|
||||
{"error":false,"response":""}
|
||||
```
|
||||
|
||||
```
|
||||
curl -d '{"processID":"GoT_Favorite","claimData":"Tyrion"}' http://localhost:1500/addClaim
|
||||
{"error":false,"response":""}
|
||||
```
|
||||
|
||||
##### generate proof
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow"}' http://localhost:1500/genProof
|
||||
{"error":false,"response":"0x000000000000000000000000000000000000000000000000000000000000000352f3ca2aaf635ec2ae4452f6a65be7bca72678287a8bb08ad4babfcccd76c2fef1aac7675261bf6d12c746fb7907beea6d1f1635af93ba931eec0c6a747ecc37"}
|
||||
```
|
||||
|
||||
##### check proof
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow", "proofData": "0x0000000000000000000000000000000000000000000000000000000000000000000123"}' http://localhost:1500/checkProof
|
||||
{"error":false,"response":"invalid"}
|
||||
```
|
||||
|
||||
```
|
||||
curl -d '{"censusID":"GoT_Favorite","claimData":"Jon Snow", "proofData": "0x000000000000000000000000000000000000000000000000000000000000000352f3ca2aaf635ec2ae4452f6a65be7bca72678287a8bb08ad4babfcccd76c2fef1aac7675261bf6d12c746fb7907beea6d1f1635af93ba931eec0c6a747ecc37"}' http://localhost:1500/checkProof
|
||||
{"error":false,"response":"valid"}
|
||||
```
|
||||
|
||||
If `rootHash` is specified, dump will return the values for the merkle tree with the given root hash.
|
||||
@@ -4,13 +4,15 @@ import (
|
||||
"log"
|
||||
"os"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
||||
censusmanager "github.com/vocdoni/dvote-census/service"
|
||||
)
|
||||
|
||||
func main() {
|
||||
if len(os.Args) < 2 {
|
||||
log.Fatal("Usage: " + os.Args[0] + " <port> [pubKey]")
|
||||
log.Fatal("Usage: " + os.Args[0] +
|
||||
" <port> <namespace>[:pubKey] [<namespace>[:pubKey]]...")
|
||||
os.Exit(2)
|
||||
}
|
||||
port, err := strconv.Atoi(os.Args[1])
|
||||
@@ -18,13 +20,18 @@ func main() {
|
||||
log.Fatal(err)
|
||||
os.Exit(2)
|
||||
}
|
||||
pubK := ""
|
||||
if len(os.Args) > 2 {
|
||||
log.Print("Public key authentication enabled")
|
||||
pubK = os.Args[2]
|
||||
for i := 2; i < len(os.Args); i++ {
|
||||
s := strings.Split(os.Args[i], ":")
|
||||
ns := s[0]
|
||||
pubK := ""
|
||||
if len(s) > 1 {
|
||||
pubK = s[1]
|
||||
log.Printf("Public Key authentication enabled on namespace %s\n", ns)
|
||||
}
|
||||
censusmanager.AddNamespace(ns, pubK)
|
||||
log.Printf("Starting process HTTP service on port %d for namespace %s\n",
|
||||
port, ns)
|
||||
}
|
||||
log.Print("Starting process HTTP service on port " + os.Args[1])
|
||||
censusmanager.T.Init()
|
||||
censusmanager.Listen(port, "http", pubK)
|
||||
censusmanager.Listen(port, "http")
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user