Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 8 additions & 1 deletion js-user-library/jest.config.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,14 @@
module.exports = {
bail: false,
setupFiles: [
"./test-setup",
],
setupFilesAfterEnv: [
"jest-expect-message",
],
testEnvironment: "jsdom"
testEnvironment: "jsdom",
testPathIgnorePatterns: [
"/node_modules/",
"/out/",
]
};
136 changes: 136 additions & 0 deletions js-user-library/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions js-user-library/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
"@babel/core": "^7.6.0",
"@babel/preset-env": "^7.6.0",
"@babel/preset-typescript": "^7.6.0",
"@trust/webcrypto": "^0.9.2",
"@types/jest": "^24.0.18",
"babel-jest": "^24.9.0",
"borc": "^2.1.1",
Expand Down
10 changes: 7 additions & 3 deletions js-user-library/src/blob.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,14 @@
import { Buffer } from "buffer/";
import { Hex } from "./hex";

export const fromHex = (hex: Hex): Uint8Array => {
return new Uint8Array(Buffer.from(hex, "hex").buffer);
// Named `BinaryBlob` as opposed to `Blob` so not to conflict with
// https://developer.mozilla.org/en-US/docs/Web/API/Blob
export type BinaryBlob = Uint8Array & { __blob__: void };

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Interesting -- thanks Paul!

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is where I first read about this approach: microsoft/TypeScript#25709 (comment)


export const fromHex = (hex: Hex): BinaryBlob => {
return new Uint8Array(Buffer.from(hex, "hex").buffer) as BinaryBlob;
};

export const toHex = (blob: Uint8Array): string => {
export const toHex = (blob: BinaryBlob): string => {
return Buffer.from(blob).toString("hex");
};
16 changes: 16 additions & 0 deletions js-user-library/src/canisterId.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import { Hex } from "./hex";
import { Int } from "./int";
import * as int from "./int";

// FIXME
// The current implementation of the client expects canister IDs to be
// represented as u64. This `Int` type will not be sufficient for u64 but may be
// good enough for now.

// export type CanisterId = BinaryBlob & { __canisterId__: void };
export type CanisterId = Int & { __canisterId__: void };

// export const fromHex = (hex: Hex): CanisterId => {
Comment thread
paulyoung marked this conversation as resolved.
Outdated
// return blob.fromHex(hex) as CanisterId;
// };
export const fromHex = (hex: Hex): CanisterId => int.fromHex(hex) as CanisterId;
9 changes: 5 additions & 4 deletions js-user-library/src/cbor.test.ts
Original file line number Diff line number Diff line change
@@ -1,19 +1,20 @@
import { toHex } from "./blob";
import { BinaryBlob } from "./blob";
import * as blob from "./blob";
import { CborValue, decode, encode } from "./cbor";
import { Int } from "./int";

test("round trip", () => {
interface Data extends Record<string, CborValue> {
a: Int;
b: string;
c: Uint8Array;
c: BinaryBlob;
d: { four: string };
}

const input: Data = {
a: 1 as Int,
b: "two",
c: Uint8Array.from([3]),
c: Uint8Array.from([3]) as BinaryBlob,
d: { four: "four" },
};

Expand All @@ -24,5 +25,5 @@ test("round trip", () => {
const { c: inputC, ...inputRest } = input;
const { c: outputC, ...outputRest } = output;
expect(outputRest).toEqual(inputRest);
expect(toHex(outputC)).toBe(toHex(inputC));
expect(blob.toHex(outputC)).toBe(blob.toHex(inputC));
});
7 changes: 4 additions & 3 deletions js-user-library/src/cbor.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// tslint:disable-next-line: max-line-length
// https://github.com/dfinity-lab/dfinity/blob/9bca65f8edd65701ea6bdb00e0752f9186bbc893/docs/spec/public/index.adoc#cbor-encoding-of-requests-and-responses
import borc from "borc";
import { BinaryBlob } from "./blob";
import { Int } from "./int";

const SEMANTIC_TAG = 55799;
Expand All @@ -12,7 +13,7 @@ export type CborValue
= string

// Blobs: Major type 2 (“Byte string”)
| Uint8Array
| BinaryBlob

// Integer numbers: Major type 0 or 1 (“Unsigned/signed integer”) if small
// enough to fit that type, else the Bignum format is used.
Expand All @@ -21,11 +22,11 @@ export type CborValue
// Nested records: Major type 5 followed by string keys.
| CborRecord;

export const encode = (value: CborValue): Uint8Array => {
export const encode = (value: CborValue): BinaryBlob => {
const buffer = borc.encode(
new borc.Tagged(SEMANTIC_TAG, value),
);
return new Uint8Array(buffer);
return new Uint8Array(buffer) as BinaryBlob;
};

export const decode = (input: Uint8Array): CborValue => {
Expand Down
6 changes: 6 additions & 0 deletions js-user-library/src/int.ts
Original file line number Diff line number Diff line change
@@ -1 +1,7 @@
import { Hex } from "./hex";

export type Int = number & { __int__: void };

export const fromHex = (hex: Hex) => parseInt(hex, 16);

export const toHex = (int: Int): Hex => int.toString(16) as Hex;
5 changes: 5 additions & 0 deletions js-user-library/src/readRequest.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
// The types of values allowed in the `request_type` field for read requests.
export enum ReadRequestType {
Query = "query",
RequestStatus = "request-status",
}
15 changes: 15 additions & 0 deletions js-user-library/src/request.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import { BinaryBlob } from "./blob";
import { RequestType } from "./requestType";

// Common request fields.
export interface Request extends Record<string, any> {
request_type: RequestType;
// expiry?:;
Comment thread
paulyoung marked this conversation as resolved.
Outdated
// NOTE: `nonce` is optional in the spec, but we provide it so that requests
// are unique and we avoid a bug in the client when the same request is
// submitted more than once: https://dfinity.atlassian.net/browse/DFN-895
nonce?: BinaryBlob;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

// sender:;
sender_pubkey: BinaryBlob;
sender_sig: BinaryBlob;
}
Loading