2023-03-10 03:41:07 +00:00
|
|
|
import { IProtoMessage } from "@waku/interfaces";
|
2022-11-23 05:59:15 +00:00
|
|
|
import { expect } from "chai";
|
|
|
|
import fc from "fast-check";
|
|
|
|
|
|
|
|
import { getPublicKey } from "./crypto/index.js";
|
2022-12-05 04:14:17 +00:00
|
|
|
import { createDecoder, createEncoder } from "./ecies.js";
|
2022-11-23 05:59:15 +00:00
|
|
|
|
|
|
|
describe("Ecies Encryption", function () {
|
|
|
|
it("Round trip binary encryption [ecies, no signature]", async function () {
|
|
|
|
await fc.assert(
|
|
|
|
fc.asyncProperty(
|
2023-03-13 03:15:57 +00:00
|
|
|
fc.string(),
|
|
|
|
fc.string(),
|
2022-11-23 05:59:15 +00:00
|
|
|
fc.uint8Array({ minLength: 1 }),
|
|
|
|
fc.uint8Array({ min: 1, minLength: 32, maxLength: 32 }),
|
2023-03-13 03:15:57 +00:00
|
|
|
async (pubSubTopic, contentTopic, payload, privateKey) => {
|
2022-11-23 05:59:15 +00:00
|
|
|
const publicKey = getPublicKey(privateKey);
|
|
|
|
|
2023-02-02 06:07:28 +00:00
|
|
|
const encoder = createEncoder({
|
2023-03-13 03:15:57 +00:00
|
|
|
contentTopic,
|
2023-02-02 06:07:28 +00:00
|
|
|
publicKey,
|
|
|
|
});
|
2022-11-23 05:59:15 +00:00
|
|
|
const bytes = await encoder.toWire({ payload });
|
|
|
|
|
2023-03-13 03:15:57 +00:00
|
|
|
const decoder = createDecoder(contentTopic, privateKey);
|
2022-11-23 05:59:15 +00:00
|
|
|
const protoResult = await decoder.fromWireToProtoObj(bytes!);
|
|
|
|
if (!protoResult) throw "Failed to proto decode";
|
2023-03-13 03:15:57 +00:00
|
|
|
const result = await decoder.fromProtoObj(pubSubTopic, protoResult);
|
2022-11-23 05:59:15 +00:00
|
|
|
if (!result) throw "Failed to decode";
|
|
|
|
|
2023-03-13 03:15:57 +00:00
|
|
|
expect(result.contentTopic).to.equal(contentTopic);
|
|
|
|
expect(result.pubSubTopic).to.equal(pubSubTopic);
|
2022-11-23 05:59:15 +00:00
|
|
|
expect(result.version).to.equal(1);
|
|
|
|
expect(result?.payload).to.deep.equal(payload);
|
|
|
|
expect(result.signature).to.be.undefined;
|
|
|
|
expect(result.signaturePublicKey).to.be.undefined;
|
|
|
|
}
|
|
|
|
)
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
|
|
|
it("R trip binary encryption [ecies, signature]", async function () {
|
|
|
|
this.timeout(4000);
|
|
|
|
|
|
|
|
await fc.assert(
|
|
|
|
fc.asyncProperty(
|
2023-03-13 03:15:57 +00:00
|
|
|
fc.string(),
|
|
|
|
fc.string(),
|
2022-11-23 05:59:15 +00:00
|
|
|
fc.uint8Array({ minLength: 1 }),
|
|
|
|
fc.uint8Array({ min: 1, minLength: 32, maxLength: 32 }),
|
|
|
|
fc.uint8Array({ min: 1, minLength: 32, maxLength: 32 }),
|
2023-03-13 03:15:57 +00:00
|
|
|
async (
|
|
|
|
pubSubTopic,
|
|
|
|
contentTopic,
|
|
|
|
payload,
|
|
|
|
alicePrivateKey,
|
|
|
|
bobPrivateKey
|
|
|
|
) => {
|
2022-11-23 05:59:15 +00:00
|
|
|
const alicePublicKey = getPublicKey(alicePrivateKey);
|
|
|
|
const bobPublicKey = getPublicKey(bobPrivateKey);
|
|
|
|
|
2023-02-02 06:07:28 +00:00
|
|
|
const encoder = createEncoder({
|
2023-03-13 03:15:57 +00:00
|
|
|
contentTopic,
|
2023-02-02 06:07:28 +00:00
|
|
|
publicKey: bobPublicKey,
|
|
|
|
sigPrivKey: alicePrivateKey,
|
|
|
|
});
|
2022-11-23 05:59:15 +00:00
|
|
|
const bytes = await encoder.toWire({ payload });
|
|
|
|
|
2023-03-13 03:15:57 +00:00
|
|
|
const decoder = createDecoder(contentTopic, bobPrivateKey);
|
2022-11-23 05:59:15 +00:00
|
|
|
const protoResult = await decoder.fromWireToProtoObj(bytes!);
|
|
|
|
if (!protoResult) throw "Failed to proto decode";
|
2023-03-13 03:15:57 +00:00
|
|
|
const result = await decoder.fromProtoObj(pubSubTopic, protoResult);
|
2022-11-23 05:59:15 +00:00
|
|
|
if (!result) throw "Failed to decode";
|
|
|
|
|
2023-03-13 03:15:57 +00:00
|
|
|
expect(result.contentTopic).to.equal(contentTopic);
|
|
|
|
expect(result.pubSubTopic).to.equal(pubSubTopic);
|
2022-11-23 05:59:15 +00:00
|
|
|
expect(result.version).to.equal(1);
|
|
|
|
expect(result?.payload).to.deep.equal(payload);
|
|
|
|
expect(result.signature).to.not.be.undefined;
|
|
|
|
expect(result.signaturePublicKey).to.deep.eq(alicePublicKey);
|
|
|
|
}
|
|
|
|
)
|
|
|
|
);
|
|
|
|
});
|
2023-03-10 03:41:07 +00:00
|
|
|
|
|
|
|
it("Check meta is set [ecies]", async function () {
|
|
|
|
await fc.assert(
|
|
|
|
fc.asyncProperty(
|
|
|
|
fc.string(),
|
|
|
|
fc.string(),
|
|
|
|
fc.uint8Array({ minLength: 1 }),
|
|
|
|
fc.uint8Array({ min: 1, minLength: 32, maxLength: 32 }),
|
|
|
|
async (pubSubTopic, contentTopic, payload, privateKey) => {
|
|
|
|
const publicKey = getPublicKey(privateKey);
|
|
|
|
const metaSetter = (
|
|
|
|
msg: IProtoMessage & { meta: undefined }
|
|
|
|
): Uint8Array => {
|
|
|
|
const buffer = new ArrayBuffer(4);
|
|
|
|
const view = new DataView(buffer);
|
|
|
|
view.setUint32(0, msg.payload.length, false);
|
|
|
|
return new Uint8Array(buffer);
|
|
|
|
};
|
|
|
|
|
|
|
|
const encoder = createEncoder({
|
|
|
|
contentTopic,
|
|
|
|
publicKey,
|
|
|
|
metaSetter,
|
|
|
|
});
|
|
|
|
const bytes = await encoder.toWire({ payload });
|
|
|
|
|
|
|
|
const decoder = createDecoder(contentTopic, privateKey);
|
|
|
|
const protoResult = await decoder.fromWireToProtoObj(bytes!);
|
|
|
|
if (!protoResult) throw "Failed to proto decode";
|
|
|
|
const result = await decoder.fromProtoObj(pubSubTopic, protoResult);
|
|
|
|
if (!result) throw "Failed to decode";
|
|
|
|
|
|
|
|
const expectedMeta = metaSetter({
|
|
|
|
payload: protoResult.payload,
|
|
|
|
timestamp: undefined,
|
|
|
|
contentTopic: "",
|
|
|
|
ephemeral: undefined,
|
|
|
|
meta: undefined,
|
|
|
|
rateLimitProof: undefined,
|
|
|
|
version: undefined,
|
|
|
|
});
|
|
|
|
|
|
|
|
expect(result.meta).to.deep.equal(expectedMeta);
|
|
|
|
}
|
|
|
|
)
|
|
|
|
);
|
|
|
|
});
|
2022-11-23 05:59:15 +00:00
|
|
|
});
|