{
"previous": "%XphMUkWQtomKjXQvFGfsGYpt69sgEY7Y4Vou9cEuJho=.sha256",
"author": "@FCX/tsDLpubCPKKfIrw4gc+SQkHcaD17s7GI6i/ziWY=.ed25519",
"sequence": 2,
"timestamp": 1514517078157,
"hash": "sha256",
"content": {
"type": "post",
"text": "Second post!"
}
}
gets signed like {
"previous": "%XphMUkWQtomKjXQvFGfsGYpt69sgEY7Y4Vou9cEuJho=.sha256",
"author": "@FCX/tsDLpubCPKKfIrw4gc+SQkHcaD17s7GI6i/ziWY=.ed25519",
"sequence": 2,
"timestamp": 1514517078157,
"hash": "sha256",
"content": {
"type": "post",
"text": "Second post!"
},
"signature": "z7W1ERg9UYZjNfE72ZwEuJF79khG+eOHWFp6iF+KLuSrw8Lqa6
IousK4cCn9T5qFa8E14GVek4cAMmMbjqDnAg==.sig.ed25519"
}
which means that you have to be careful about how you remove the signature in order to verify the original. The "main" node implementation does this by parsing the json, removing the field, and then re serializing, forcing any alternate implementation to exactly match the node serialization in order to be compatible {
"original":"json",
"goes":"here"
}
Signed: {
"original_json_contents_base64":"ewogICJvcmlnaW5hbCI6Impzb24iLAogICJnb2VzIjoiaGVyZSIKfQo=",
"hmac_sha256_of_base64":"bf1f4cb95ce8633aff46888e1717873e32bb2a770b3d4b5b74a59e5e9adefeda"
}
This way you have full control over the raw bytes you want to sign (by forcing them into Base64 where other systems can't get their dirty paws on them).I guess the problem here is if intermediate systems want to do stuff based on the payload (but without validating it), they won't like this.
But if the problem is just intermediate systems barfing on non-json, this might work!
p.s. enjoyable blog post - as they always are! ;-)
You also correctly identified why that is different from the other schemes: they don't change the structure of the outer object.
{
"data": {...}
"signature": "z7W1ER..."
}Yep, JSON has no round-trip guarantees
Everyone is on the same page that at some point bytes go into a hash function. That's not the problem.
You mention JWT, but JWT only does external signing, which doesn't trigger the problematic case several people are describing to you. Perhaps an example would be more useful. If you start with a JSON like:
{"a": 1}
how do you build a JSON like: {"a": 1, "tag": "deadbeefdeadbeefdeadbeef"}
with a signing and verification algorithm that works?> Also, you don't validate a signature by re-creating the bytes in question... that's a flawed approach, and not the approach for example JWT takes.
Can you describe an HMAC validation process that doesn't involve recreating the bytes in the HMAC tag?
{"body":"base64-json","tag":"hash"}
It seems to me that trying to do what you're saying is a flawed approach.That said, I certainly hope that it is, generally speaking.
The stringify function returns a String in UTF-16 encoded JSON format representing an ECMAScript value, or undefined.