ehbp 0.0.1 → 0.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (41) hide show
  1. package/package.json +17 -7
  2. package/src/client.ts +13 -2
  3. package/src/test/client.test.ts +5 -3
  4. package/tsconfig.cjs.json +8 -0
  5. package/tsconfig.esm.json +7 -0
  6. package/dist/client.d.ts +0 -47
  7. package/dist/client.d.ts.map +0 -1
  8. package/dist/client.js +0 -145
  9. package/dist/client.js.map +0 -1
  10. package/dist/example.d.ts +0 -6
  11. package/dist/example.d.ts.map +0 -1
  12. package/dist/example.js +0 -115
  13. package/dist/example.js.map +0 -1
  14. package/dist/identity.d.ts +0 -52
  15. package/dist/identity.d.ts.map +0 -1
  16. package/dist/identity.js +0 -270
  17. package/dist/identity.js.map +0 -1
  18. package/dist/index.d.ts +0 -12
  19. package/dist/index.d.ts.map +0 -1
  20. package/dist/index.js +0 -11
  21. package/dist/index.js.map +0 -1
  22. package/dist/protocol.d.ts +0 -19
  23. package/dist/protocol.d.ts.map +0 -1
  24. package/dist/protocol.js +0 -19
  25. package/dist/protocol.js.map +0 -1
  26. package/dist/streaming-test.d.ts +0 -3
  27. package/dist/streaming-test.d.ts.map +0 -1
  28. package/dist/streaming-test.js +0 -102
  29. package/dist/streaming-test.js.map +0 -1
  30. package/dist/test/client.test.d.ts +0 -2
  31. package/dist/test/client.test.d.ts.map +0 -1
  32. package/dist/test/client.test.js +0 -70
  33. package/dist/test/client.test.js.map +0 -1
  34. package/dist/test/identity.test.d.ts +0 -2
  35. package/dist/test/identity.test.d.ts.map +0 -1
  36. package/dist/test/identity.test.js +0 -39
  37. package/dist/test/identity.test.js.map +0 -1
  38. package/dist/test/streaming.test.d.ts +0 -2
  39. package/dist/test/streaming.test.d.ts.map +0 -1
  40. package/dist/test/streaming.test.js +0 -71
  41. package/dist/test/streaming.test.js.map +0 -1
package/package.json CHANGED
@@ -1,17 +1,27 @@
1
1
  {
2
2
  "name": "ehbp",
3
- "version": "0.0.1",
3
+ "version": "0.0.3",
4
4
  "description": "JavaScript client for Encrypted HTTP Body Protocol (EHBP)",
5
- "main": "dist/index.js",
6
- "type": "module",
5
+ "main": "./dist/cjs/index.js",
6
+ "module": "./dist/esm/index.js",
7
+ "types": "./dist/esm/index.d.ts",
8
+ "exports": {
9
+ ".": {
10
+ "import": "./dist/esm/index.js",
11
+ "require": "./dist/cjs/index.js",
12
+ "types": "./dist/esm/index.d.ts"
13
+ }
14
+ },
7
15
  "scripts": {
8
- "build": "tsc",
16
+ "build": "npm run build:esm && npm run build:cjs",
17
+ "build:esm": "tsc -p tsconfig.esm.json && echo '{\"type\":\"module\"}' > dist/esm/package.json",
18
+ "build:cjs": "tsc -p tsconfig.cjs.json && echo '{\"type\":\"commonjs\"}' > dist/cjs/package.json",
9
19
  "build:browser": "node build-browser.js",
10
20
  "build:all": "npm run build && npm run build:browser",
11
21
  "dev": "tsc --watch",
12
- "test": "node --test dist/test/*.test.js",
13
- "example": "node dist/example.js",
14
- "streaming": "node dist/streaming-test.js",
22
+ "test": "node --test dist/esm/test/*.test.js",
23
+ "example": "node dist/esm/example.js",
24
+ "streaming": "node dist/esm/streaming-test.js",
15
25
  "serve": "node serve.js"
16
26
  },
17
27
  "keywords": [
package/src/client.ts CHANGED
@@ -45,14 +45,25 @@ export class Transport {
45
45
  /**
46
46
  * Get the server public key
47
47
  */
48
- async getServerPublicKey(): Promise<CryptoKey> {
48
+ getServerPublicKey(): CryptoKey {
49
49
  return this.serverPublicKey;
50
50
  }
51
51
 
52
+ /**
53
+ * Get the server public key as hex string
54
+ */
55
+ async getServerPublicKeyHex(): Promise<string> {
56
+ const exported = await crypto.subtle.exportKey('raw', this.serverPublicKey);
57
+ const keyBytes = new Uint8Array(exported);
58
+ return Array.from(keyBytes)
59
+ .map(b => b.toString(16).padStart(2, '0'))
60
+ .join('');
61
+ }
62
+
52
63
  /**
53
64
  * Get the client public key
54
65
  */
55
- async getClientPublicKey(): Promise<CryptoKey> {
66
+ getClientPublicKey(): CryptoKey {
56
67
  return this.clientIdentity.getPublicKey();
57
68
  }
58
69
 
@@ -1,6 +1,6 @@
1
1
  import { describe, it, before, after } from 'node:test';
2
2
  import assert from 'node:assert';
3
- import { Identity, Transport } from '../index.js';
3
+ import { Identity, Transport, createTransport } from '../index.js';
4
4
  import { PROTOCOL } from '../protocol.js';
5
5
 
6
6
  describe('Transport', () => {
@@ -70,11 +70,13 @@ describe('Transport', () => {
70
70
  }
71
71
 
72
72
  // Create transport that will connect to the real server
73
- const { createTransport } = await import('../index.js');
74
73
  const transport = await createTransport(serverURL, clientIdentity);
75
74
 
76
75
  const testName = 'Integration Test User';
77
-
76
+
77
+ const serverPubKeyHex = await transport.getServerPublicKeyHex();
78
+ assert.strictEqual(serverPubKeyHex.length, 64, 'Server public key should be 64 bytes');
79
+
78
80
  // Make actual POST request to /secure endpoint
79
81
  const response = await transport.post(`${serverURL}/secure`, testName, {
80
82
  headers: { 'Content-Type': 'text/plain' }
@@ -0,0 +1,8 @@
1
+ {
2
+ "extends": "./tsconfig.json",
3
+ "compilerOptions": {
4
+ "module": "CommonJS",
5
+ "outDir": "./dist/cjs"
6
+ },
7
+ "exclude": ["node_modules", "dist", "src/example.ts", "src/streaming-test.ts", "src/test"]
8
+ }
@@ -0,0 +1,7 @@
1
+ {
2
+ "extends": "./tsconfig.json",
3
+ "compilerOptions": {
4
+ "module": "ESNext",
5
+ "outDir": "./dist/esm"
6
+ }
7
+ }
package/dist/client.d.ts DELETED
@@ -1,47 +0,0 @@
1
- import { Identity } from './identity.js';
2
- /**
3
- * HTTP transport for EHBP
4
- */
5
- export declare class Transport {
6
- private clientIdentity;
7
- private serverHost;
8
- private serverPublicKey;
9
- constructor(clientIdentity: Identity, serverHost: string, serverPublicKey: CryptoKey);
10
- /**
11
- * Create a new transport by fetching server public key
12
- */
13
- static create(serverURL: string, clientIdentity: Identity): Promise<Transport>;
14
- /**
15
- * Get the server public key
16
- */
17
- getServerPublicKey(): Promise<CryptoKey>;
18
- /**
19
- * Get the client public key
20
- */
21
- getClientPublicKey(): Promise<CryptoKey>;
22
- /**
23
- * Make an encrypted HTTP request
24
- */
25
- request(input: RequestInfo | URL, init?: RequestInit): Promise<Response>;
26
- /**
27
- * Convenience method for GET requests
28
- */
29
- get(url: string | URL, init?: RequestInit): Promise<Response>;
30
- /**
31
- * Convenience method for POST requests
32
- */
33
- post(url: string | URL, body?: BodyInit, init?: RequestInit): Promise<Response>;
34
- /**
35
- * Convenience method for PUT requests
36
- */
37
- put(url: string | URL, body?: BodyInit, init?: RequestInit): Promise<Response>;
38
- /**
39
- * Convenience method for DELETE requests
40
- */
41
- delete(url: string | URL, init?: RequestInit): Promise<Response>;
42
- }
43
- /**
44
- * Create a new transport instance
45
- */
46
- export declare function createTransport(serverURL: string, clientIdentity: Identity): Promise<Transport>;
47
- //# sourceMappingURL=client.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAGzC;;GAEG;AACH,qBAAa,SAAS;IACpB,OAAO,CAAC,cAAc,CAAW;IACjC,OAAO,CAAC,UAAU,CAAS;IAC3B,OAAO,CAAC,eAAe,CAAY;gBAEvB,cAAc,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,EAAE,eAAe,EAAE,SAAS;IAMpF;;OAEG;WACU,MAAM,CAAC,SAAS,EAAE,MAAM,EAAE,cAAc,EAAE,QAAQ,GAAG,OAAO,CAAC,SAAS,CAAC;IAwBpF;;OAEG;IACG,kBAAkB,IAAI,OAAO,CAAC,SAAS,CAAC;IAI9C;;OAEG;IACG,kBAAkB,IAAI,OAAO,CAAC,SAAS,CAAC;IAI9C;;OAEG;IACG,OAAO,CAAC,KAAK,EAAE,WAAW,GAAG,GAAG,EAAE,IAAI,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,QAAQ,CAAC;IA0E9E;;OAEG;IACG,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,EAAE,IAAI,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,QAAQ,CAAC;IAInE;;OAEG;IACG,IAAI,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,EAAE,IAAI,CAAC,EAAE,QAAQ,EAAE,IAAI,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,QAAQ,CAAC;IAIrF;;OAEG;IACG,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,EAAE,IAAI,CAAC,EAAE,QAAQ,EAAE,IAAI,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,QAAQ,CAAC;IAIpF;;OAEG;IACG,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,EAAE,IAAI,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,QAAQ,CAAC;CAGvE;AAED;;GAEG;AACH,wBAAsB,eAAe,CAAC,SAAS,EAAE,MAAM,EAAE,cAAc,EAAE,QAAQ,GAAG,OAAO,CAAC,SAAS,CAAC,CAErG"}
package/dist/client.js DELETED
@@ -1,145 +0,0 @@
1
- import { Identity } from './identity.js';
2
- import { PROTOCOL } from './protocol.js';
3
- /**
4
- * HTTP transport for EHBP
5
- */
6
- export class Transport {
7
- clientIdentity;
8
- serverHost;
9
- serverPublicKey;
10
- constructor(clientIdentity, serverHost, serverPublicKey) {
11
- this.clientIdentity = clientIdentity;
12
- this.serverHost = serverHost;
13
- this.serverPublicKey = serverPublicKey;
14
- }
15
- /**
16
- * Create a new transport by fetching server public key
17
- */
18
- static async create(serverURL, clientIdentity) {
19
- const url = new URL(serverURL);
20
- const serverHost = url.host;
21
- // Fetch server public key
22
- const keysURL = new URL(PROTOCOL.KEYS_PATH, serverURL);
23
- const response = await fetch(keysURL.toString());
24
- if (!response.ok) {
25
- throw new Error(`Failed to get server public key: ${response.status}`);
26
- }
27
- const contentType = response.headers.get('content-type');
28
- if (contentType !== PROTOCOL.KEYS_MEDIA_TYPE) {
29
- throw new Error(`Invalid content type: ${contentType}`);
30
- }
31
- const keysData = new Uint8Array(await response.arrayBuffer());
32
- const serverIdentity = await Identity.unmarshalPublicConfig(keysData);
33
- const serverPublicKey = serverIdentity.getPublicKey();
34
- return new Transport(clientIdentity, serverHost, serverPublicKey);
35
- }
36
- /**
37
- * Get the server public key
38
- */
39
- async getServerPublicKey() {
40
- return this.serverPublicKey;
41
- }
42
- /**
43
- * Get the client public key
44
- */
45
- async getClientPublicKey() {
46
- return this.clientIdentity.getPublicKey();
47
- }
48
- /**
49
- * Make an encrypted HTTP request
50
- */
51
- async request(input, init) {
52
- // Extract body from init or original request before creating Request object
53
- let requestBody = null;
54
- if (input instanceof Request) {
55
- // If input is a Request, extract its body
56
- if (input.body) {
57
- requestBody = await input.arrayBuffer();
58
- }
59
- }
60
- else {
61
- // If input is URL/string, get body from init
62
- requestBody = init?.body || null;
63
- }
64
- // Create the URL with correct host
65
- let url;
66
- let method;
67
- let headers;
68
- if (input instanceof Request) {
69
- url = new URL(input.url);
70
- method = input.method;
71
- headers = input.headers;
72
- }
73
- else {
74
- url = new URL(input);
75
- method = init?.method || 'GET';
76
- headers = init?.headers || {};
77
- }
78
- url.host = this.serverHost;
79
- let request = new Request(url.toString(), {
80
- method,
81
- headers,
82
- body: requestBody,
83
- duplex: 'half'
84
- });
85
- // Encrypt request body if present (check the original requestBody, not request.body)
86
- if (requestBody !== null && requestBody !== undefined) {
87
- request = await this.clientIdentity.encryptRequest(request, this.serverPublicKey);
88
- }
89
- else {
90
- // No body, just set client public key header
91
- const headers = new Headers(request.headers);
92
- headers.set(PROTOCOL.CLIENT_PUBLIC_KEY_HEADER, await this.clientIdentity.getPublicKeyHex());
93
- request = new Request(request.url, {
94
- method: request.method,
95
- headers,
96
- body: null
97
- });
98
- }
99
- // Make the request
100
- const response = await fetch(request);
101
- if (!response.ok) {
102
- console.warn(`Server returned non-OK status: ${response.status}`);
103
- }
104
- // Check for encapsulated key header
105
- const encapKeyHeader = response.headers.get(PROTOCOL.ENCAPSULATED_KEY_HEADER);
106
- if (!encapKeyHeader) {
107
- throw new Error(`Missing ${PROTOCOL.ENCAPSULATED_KEY_HEADER} encapsulated key header`);
108
- }
109
- // Decode encapsulated key
110
- const serverEncapKey = new Uint8Array(encapKeyHeader.match(/.{2}/g).map(byte => parseInt(byte, 16)));
111
- // Decrypt response
112
- return await this.clientIdentity.decryptResponse(response, serverEncapKey);
113
- }
114
- /**
115
- * Convenience method for GET requests
116
- */
117
- async get(url, init) {
118
- return this.request(url, { ...init, method: 'GET' });
119
- }
120
- /**
121
- * Convenience method for POST requests
122
- */
123
- async post(url, body, init) {
124
- return this.request(url, { ...init, method: 'POST', body });
125
- }
126
- /**
127
- * Convenience method for PUT requests
128
- */
129
- async put(url, body, init) {
130
- return this.request(url, { ...init, method: 'PUT', body });
131
- }
132
- /**
133
- * Convenience method for DELETE requests
134
- */
135
- async delete(url, init) {
136
- return this.request(url, { ...init, method: 'DELETE' });
137
- }
138
- }
139
- /**
140
- * Create a new transport instance
141
- */
142
- export async function createTransport(serverURL, clientIdentity) {
143
- return Transport.create(serverURL, clientIdentity);
144
- }
145
- //# sourceMappingURL=client.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAEzC;;GAEG;AACH,MAAM,OAAO,SAAS;IACZ,cAAc,CAAW;IACzB,UAAU,CAAS;IACnB,eAAe,CAAY;IAEnC,YAAY,cAAwB,EAAE,UAAkB,EAAE,eAA0B;QAClF,IAAI,CAAC,cAAc,GAAG,cAAc,CAAC;QACrC,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;QAC7B,IAAI,CAAC,eAAe,GAAG,eAAe,CAAC;IACzC,CAAC;IAED;;OAEG;IACH,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,SAAiB,EAAE,cAAwB;QAC7D,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,SAAS,CAAC,CAAC;QAC/B,MAAM,UAAU,GAAG,GAAG,CAAC,IAAI,CAAC;QAE5B,0BAA0B;QAC1B,MAAM,OAAO,GAAG,IAAI,GAAG,CAAC,QAAQ,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC;QACvD,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,OAAO,CAAC,QAAQ,EAAE,CAAC,CAAC;QAEjD,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;YACjB,MAAM,IAAI,KAAK,CAAC,oCAAoC,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAC;QACzE,CAAC;QAED,MAAM,WAAW,GAAG,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC,CAAC;QACzD,IAAI,WAAW,KAAK,QAAQ,CAAC,eAAe,EAAE,CAAC;YAC7C,MAAM,IAAI,KAAK,CAAC,yBAAyB,WAAW,EAAE,CAAC,CAAC;QAC1D,CAAC;QAED,MAAM,QAAQ,GAAG,IAAI,UAAU,CAAC,MAAM,QAAQ,CAAC,WAAW,EAAE,CAAC,CAAC;QAC9D,MAAM,cAAc,GAAG,MAAM,QAAQ,CAAC,qBAAqB,CAAC,QAAQ,CAAC,CAAC;QACtE,MAAM,eAAe,GAAG,cAAc,CAAC,YAAY,EAAE,CAAC;QAEtD,OAAO,IAAI,SAAS,CAAC,cAAc,EAAE,UAAU,EAAE,eAAe,CAAC,CAAC;IACpE,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,kBAAkB;QACtB,OAAO,IAAI,CAAC,eAAe,CAAC;IAC9B,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,kBAAkB;QACtB,OAAO,IAAI,CAAC,cAAc,CAAC,YAAY,EAAE,CAAC;IAC5C,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,OAAO,CAAC,KAAwB,EAAE,IAAkB;QACxD,4EAA4E;QAC5E,IAAI,WAAW,GAAoB,IAAI,CAAC;QAExC,IAAI,KAAK,YAAY,OAAO,EAAE,CAAC;YAC7B,0CAA0C;YAC1C,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC;gBACf,WAAW,GAAG,MAAM,KAAK,CAAC,WAAW,EAAE,CAAC;YAC1C,CAAC;QACH,CAAC;aAAM,CAAC;YACN,6CAA6C;YAC7C,WAAW,GAAG,IAAI,EAAE,IAAI,IAAI,IAAI,CAAC;QACnC,CAAC;QAED,mCAAmC;QACnC,IAAI,GAAQ,CAAC;QACb,IAAI,MAAc,CAAC;QACnB,IAAI,OAAoB,CAAC;QAEzB,IAAI,KAAK,YAAY,OAAO,EAAE,CAAC;YAC7B,GAAG,GAAG,IAAI,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;YACzB,MAAM,GAAG,KAAK,CAAC,MAAM,CAAC;YACtB,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC;QAC1B,CAAC;aAAM,CAAC;YACN,GAAG,GAAG,IAAI,GAAG,CAAC,KAAK,CAAC,CAAC;YACrB,MAAM,GAAG,IAAI,EAAE,MAAM,IAAI,KAAK,CAAC;YAC/B,OAAO,GAAG,IAAI,EAAE,OAAO,IAAI,EAAE,CAAC;QAChC,CAAC;QAED,GAAG,CAAC,IAAI,GAAG,IAAI,CAAC,UAAU,CAAC;QAE3B,IAAI,OAAO,GAAG,IAAI,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,EAAE;YACxC,MAAM;YACN,OAAO;YACP,IAAI,EAAE,WAAW;YACjB,MAAM,EAAE,MAAM;SACA,CAAC,CAAC;QAElB,qFAAqF;QACrF,IAAI,WAAW,KAAK,IAAI,IAAI,WAAW,KAAK,SAAS,EAAE,CAAC;YACtD,OAAO,GAAG,MAAM,IAAI,CAAC,cAAc,CAAC,cAAc,CAAC,OAAO,EAAE,IAAI,CAAC,eAAe,CAAC,CAAC;QACpF,CAAC;aAAM,CAAC;YACN,6CAA6C;YAC7C,MAAM,OAAO,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;YAC7C,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,wBAAwB,EAAE,MAAM,IAAI,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC;YAC5F,OAAO,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC,GAAG,EAAE;gBACjC,MAAM,EAAE,OAAO,CAAC,MAAM;gBACtB,OAAO;gBACP,IAAI,EAAE,IAAI;aACX,CAAC,CAAC;QACL,CAAC;QAED,mBAAmB;QACnB,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,OAAO,CAAC,CAAC;QAEtC,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;YACjB,OAAO,CAAC,IAAI,CAAC,kCAAkC,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAC;QACpE,CAAC;QAED,oCAAoC;QACpC,MAAM,cAAc,GAAG,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,uBAAuB,CAAC,CAAC;QAC9E,IAAI,CAAC,cAAc,EAAE,CAAC;YACpB,MAAM,IAAI,KAAK,CAAC,WAAW,QAAQ,CAAC,uBAAuB,0BAA0B,CAAC,CAAC;QACzF,CAAC;QAED,0BAA0B;QAC1B,MAAM,cAAc,GAAG,IAAI,UAAU,CACnC,cAAc,CAAC,KAAK,CAAC,OAAO,CAAE,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,QAAQ,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,CAC/D,CAAC;QAEF,mBAAmB;QACnB,OAAO,MAAM,IAAI,CAAC,cAAc,CAAC,eAAe,CAAC,QAAQ,EAAE,cAAc,CAAC,CAAC;IAC7E,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,GAAG,CAAC,GAAiB,EAAE,IAAkB;QAC7C,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,GAAG,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;IACvD,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,IAAI,CAAC,GAAiB,EAAE,IAAe,EAAE,IAAkB;QAC/D,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,GAAG,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;IAC9D,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,GAAG,CAAC,GAAiB,EAAE,IAAe,EAAE,IAAkB;QAC9D,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,GAAG,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC;IAC7D,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,MAAM,CAAC,GAAiB,EAAE,IAAkB;QAChD,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,GAAG,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,CAAC,CAAC;IAC1D,CAAC;CACF;AAED;;GAEG;AACH,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,SAAiB,EAAE,cAAwB;IAC/E,OAAO,SAAS,CAAC,MAAM,CAAC,SAAS,EAAE,cAAc,CAAC,CAAC;AACrD,CAAC"}
package/dist/example.d.ts DELETED
@@ -1,6 +0,0 @@
1
- #!/usr/bin/env node
2
- /**
3
- * Example usage of the EHBP JavaScript client
4
- */
5
- export {};
6
- //# sourceMappingURL=example.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"example.d.ts","sourceRoot":"","sources":["../src/example.ts"],"names":[],"mappings":";AAEA;;GAEG"}
package/dist/example.js DELETED
@@ -1,115 +0,0 @@
1
- #!/usr/bin/env node
2
- /**
3
- * Example usage of the EHBP JavaScript client
4
- */
5
- import { Identity, createTransport } from './index.js';
6
- async function main() {
7
- console.log('EHBP JavaScript Client Example');
8
- console.log('==============================');
9
- try {
10
- // Create client identity
11
- console.log('Creating client identity...');
12
- const clientIdentity = await Identity.generate();
13
- console.log('Client public key:', await clientIdentity.getPublicKeyHex());
14
- // Create transport (this will fetch server public key)
15
- console.log('Creating transport...');
16
- const serverURL = 'http://localhost:8080'; // Adjust as needed
17
- const transport = await createTransport(serverURL, clientIdentity);
18
- console.log('Transport created successfully');
19
- // Example 1: GET request to secure endpoint
20
- console.log('\n--- GET Request ---');
21
- try {
22
- const getResponse = await transport.get(`${serverURL}/secure`);
23
- console.log('GET Response status:', getResponse.status);
24
- if (getResponse.ok) {
25
- const getData = await getResponse.text();
26
- console.log('GET Response:', getData);
27
- }
28
- else {
29
- console.log('GET Request failed with status:', getResponse.status);
30
- }
31
- }
32
- catch (error) {
33
- console.log('GET Request failed:', error instanceof Error ? error.message : String(error));
34
- }
35
- // Example 2: POST request with JSON data
36
- console.log('\n--- POST Request ---');
37
- try {
38
- const postData = { message: 'Hello from JavaScript client!', timestamp: new Date().toISOString() };
39
- const postResponse = await transport.post(`${serverURL}/secure`, JSON.stringify(postData), { headers: { 'Content-Type': 'application/json' } });
40
- console.log('POST Response status:', postResponse.status);
41
- if (postResponse.ok) {
42
- const responseData = await postResponse.text();
43
- console.log('POST Response:', responseData);
44
- }
45
- else {
46
- console.log('POST Request failed with status:', postResponse.status);
47
- }
48
- }
49
- catch (error) {
50
- console.log('POST Request failed:', error instanceof Error ? error.message : String(error));
51
- }
52
- // Example 3: PUT request
53
- console.log('\n--- PUT Request ---');
54
- try {
55
- const putData = { id: 1, name: 'Updated Item' };
56
- const putResponse = await transport.put(`${serverURL}/secure`, JSON.stringify(putData), { headers: { 'Content-Type': 'application/json' } });
57
- console.log('PUT Response status:', putResponse.status);
58
- if (putResponse.ok) {
59
- const putResponseData = await putResponse.text();
60
- console.log('PUT Response:', putResponseData);
61
- }
62
- else {
63
- console.log('PUT Request failed with status:', putResponse.status);
64
- }
65
- }
66
- catch (error) {
67
- console.log('PUT Request failed:', error instanceof Error ? error.message : String(error));
68
- }
69
- // Example 4: Streaming request
70
- console.log('\n--- Streaming Request ---');
71
- try {
72
- const streamResponse = await transport.get(`${serverURL}/stream`);
73
- console.log('Stream Response status:', streamResponse.status);
74
- if (streamResponse.ok) {
75
- console.log('Streaming response (should show numbers 1-20):');
76
- const reader = streamResponse.body?.getReader();
77
- if (reader) {
78
- const decoder = new TextDecoder();
79
- let chunkCount = 0;
80
- while (true) {
81
- const { done, value } = await reader.read();
82
- if (done)
83
- break;
84
- const text = decoder.decode(value, { stream: true });
85
- process.stdout.write(text);
86
- chunkCount++;
87
- }
88
- console.log(`\nStream completed with ${chunkCount} chunks`);
89
- }
90
- else {
91
- console.log('No readable stream available');
92
- }
93
- }
94
- else {
95
- console.log('Stream Request failed with status:', streamResponse.status);
96
- }
97
- }
98
- catch (error) {
99
- console.log('Stream Request failed:', error instanceof Error ? error.message : String(error));
100
- }
101
- console.log('\nExample completed successfully!');
102
- console.log('\nTo test with a real server:');
103
- console.log('1. Start the Go server: go run pkg/server/main.go');
104
- console.log('2. Run this example: npm run example');
105
- }
106
- catch (error) {
107
- console.error('Error:', error);
108
- process.exit(1);
109
- }
110
- }
111
- // Run the example
112
- if (import.meta.url === `file://${process.argv[1]}`) {
113
- main().catch(console.error);
114
- }
115
- //# sourceMappingURL=example.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"example.js","sourceRoot":"","sources":["../src/example.ts"],"names":[],"mappings":"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"}
@@ -1,52 +0,0 @@
1
- import { CipherSuite } from '@hpke/core';
2
- /**
3
- * Identity class for managing HPKE key pairs and encryption/decryption
4
- */
5
- export declare class Identity {
6
- private suite;
7
- private publicKey;
8
- private privateKey;
9
- constructor(suite: CipherSuite, publicKey: CryptoKey, privateKey: CryptoKey);
10
- /**
11
- * Generate a new identity with X25519 key pair
12
- */
13
- static generate(): Promise<Identity>;
14
- /**
15
- * Create identity from JSON string
16
- */
17
- static fromJSON(json: string): Promise<Identity>;
18
- /**
19
- * Convert identity to JSON string
20
- */
21
- toJSON(): Promise<string>;
22
- /**
23
- * Get public key as CryptoKey
24
- */
25
- getPublicKey(): CryptoKey;
26
- /**
27
- * Get public key as hex string
28
- */
29
- getPublicKeyHex(): Promise<string>;
30
- /**
31
- * Get private key as CryptoKey
32
- */
33
- getPrivateKey(): CryptoKey;
34
- /**
35
- * Marshal public key configuration for server key distribution
36
- * Implements RFC 9458 format
37
- */
38
- marshalConfig(): Promise<Uint8Array>;
39
- /**
40
- * Unmarshal public configuration from server
41
- */
42
- static unmarshalPublicConfig(data: Uint8Array): Promise<Identity>;
43
- /**
44
- * Encrypt request body and set appropriate headers
45
- */
46
- encryptRequest(request: Request, serverPublicKey: CryptoKey): Promise<Request>;
47
- /**
48
- * Decrypt response body
49
- */
50
- decryptResponse(response: Response, serverEncapKey: Uint8Array): Promise<Response>;
51
- }
52
- //# sourceMappingURL=identity.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"identity.d.ts","sourceRoot":"","sources":["../src/identity.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAgD,MAAM,YAAY,CAAC;AAGvF;;GAEG;AACH,qBAAa,QAAQ;IACnB,OAAO,CAAC,KAAK,CAAc;IAC3B,OAAO,CAAC,SAAS,CAAY;IAC7B,OAAO,CAAC,UAAU,CAAY;gBAElB,KAAK,EAAE,WAAW,EAAE,SAAS,EAAE,SAAS,EAAE,UAAU,EAAE,SAAS;IAM3E;;OAEG;WACU,QAAQ,IAAI,OAAO,CAAC,QAAQ,CAAC;IAsB1C;;OAEG;WACU,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC;IAwBtD;;OAEG;IACG,MAAM,IAAI,OAAO,CAAC,MAAM,CAAC;IAY/B;;OAEG;IACH,YAAY,IAAI,SAAS;IAIzB;;OAEG;IACG,eAAe,IAAI,OAAO,CAAC,MAAM,CAAC;IAOxC;;OAEG;IACH,aAAa,IAAI,SAAS;IAI1B;;;OAGG;IACG,aAAa,IAAI,OAAO,CAAC,UAAU,CAAC;IA0C1C;;OAEG;WACU,qBAAqB,CAAC,IAAI,EAAE,UAAU,GAAG,OAAO,CAAC,QAAQ,CAAC;IAwCvE;;OAEG;IACG,cAAc,CAAC,OAAO,EAAE,OAAO,EAAE,eAAe,EAAE,SAAS,GAAG,OAAO,CAAC,OAAO,CAAC;IAgDpF;;OAEG;IACG,eAAe,CAAC,QAAQ,EAAE,QAAQ,EAAE,cAAc,EAAE,UAAU,GAAG,OAAO,CAAC,QAAQ,CAAC;CAuFzF"}
package/dist/identity.js DELETED
@@ -1,270 +0,0 @@
1
- import { CipherSuite, DhkemX25519HkdfSha256, HkdfSha256, Aes256Gcm } from '@hpke/core';
2
- import { PROTOCOL, HPKE_CONFIG } from './protocol.js';
3
- /**
4
- * Identity class for managing HPKE key pairs and encryption/decryption
5
- */
6
- export class Identity {
7
- suite;
8
- publicKey;
9
- privateKey;
10
- constructor(suite, publicKey, privateKey) {
11
- this.suite = suite;
12
- this.publicKey = publicKey;
13
- this.privateKey = privateKey;
14
- }
15
- /**
16
- * Generate a new identity with X25519 key pair
17
- */
18
- static async generate() {
19
- const suite = new CipherSuite({
20
- kem: new DhkemX25519HkdfSha256(),
21
- kdf: new HkdfSha256(),
22
- aead: new Aes256Gcm()
23
- });
24
- const { publicKey, privateKey } = await suite.kem.generateKeyPair();
25
- // Make sure the public key is extractable for serialization
26
- const extractablePublicKey = await crypto.subtle.importKey('raw', await crypto.subtle.exportKey('raw', publicKey), { name: 'X25519' }, true, // extractable
27
- []);
28
- return new Identity(suite, extractablePublicKey, privateKey);
29
- }
30
- /**
31
- * Create identity from JSON string
32
- */
33
- static async fromJSON(json) {
34
- const data = JSON.parse(json);
35
- const suite = new CipherSuite({
36
- kem: new DhkemX25519HkdfSha256(),
37
- kdf: new HkdfSha256(),
38
- aead: new Aes256Gcm()
39
- });
40
- // Import public key
41
- const publicKey = await crypto.subtle.importKey('raw', new Uint8Array(data.publicKey), { name: 'X25519' }, true, // extractable
42
- []);
43
- // Deserialize private key using HPKE library
44
- const privateKey = await suite.kem.deserializePrivateKey(new Uint8Array(data.privateKey).buffer);
45
- return new Identity(suite, publicKey, privateKey);
46
- }
47
- /**
48
- * Convert identity to JSON string
49
- */
50
- async toJSON() {
51
- const publicKeyBytes = new Uint8Array(await crypto.subtle.exportKey('raw', this.publicKey));
52
- // For X25519, we need to use the HPKE library's serialization for private keys
53
- const privateKeyBytes = await this.suite.kem.serializePrivateKey(this.privateKey);
54
- return JSON.stringify({
55
- publicKey: Array.from(publicKeyBytes),
56
- privateKey: Array.from(new Uint8Array(privateKeyBytes))
57
- });
58
- }
59
- /**
60
- * Get public key as CryptoKey
61
- */
62
- getPublicKey() {
63
- return this.publicKey;
64
- }
65
- /**
66
- * Get public key as hex string
67
- */
68
- async getPublicKeyHex() {
69
- const exported = await crypto.subtle.exportKey('raw', this.publicKey);
70
- return Array.from(new Uint8Array(exported))
71
- .map(b => b.toString(16).padStart(2, '0'))
72
- .join('');
73
- }
74
- /**
75
- * Get private key as CryptoKey
76
- */
77
- getPrivateKey() {
78
- return this.privateKey;
79
- }
80
- /**
81
- * Marshal public key configuration for server key distribution
82
- * Implements RFC 9458 format
83
- */
84
- async marshalConfig() {
85
- const kemId = HPKE_CONFIG.KEM;
86
- const kdfId = HPKE_CONFIG.KDF;
87
- const aeadId = HPKE_CONFIG.AEAD;
88
- // Export public key as raw bytes
89
- const publicKeyBytes = new Uint8Array(await crypto.subtle.exportKey('raw', this.publicKey));
90
- // Key ID (1 byte) + KEM ID (2 bytes) + Public Key + Cipher Suites
91
- const keyId = 0;
92
- const publicKeySize = publicKeyBytes.length;
93
- const cipherSuitesSize = 2 + 2; // KDF ID + AEAD ID
94
- const buffer = new Uint8Array(1 + 2 + publicKeySize + 2 + cipherSuitesSize);
95
- let offset = 0;
96
- // Key ID
97
- buffer[offset++] = keyId;
98
- // KEM ID
99
- buffer[offset++] = (kemId >> 8) & 0xFF;
100
- buffer[offset++] = kemId & 0xFF;
101
- // Public Key
102
- buffer.set(publicKeyBytes, offset);
103
- offset += publicKeySize;
104
- // Cipher Suites Length (2 bytes)
105
- buffer[offset++] = (cipherSuitesSize >> 8) & 0xFF;
106
- buffer[offset++] = cipherSuitesSize & 0xFF;
107
- // KDF ID
108
- buffer[offset++] = (kdfId >> 8) & 0xFF;
109
- buffer[offset++] = kdfId & 0xFF;
110
- // AEAD ID
111
- buffer[offset++] = (aeadId >> 8) & 0xFF;
112
- buffer[offset++] = aeadId & 0xFF;
113
- return buffer;
114
- }
115
- /**
116
- * Unmarshal public configuration from server
117
- */
118
- static async unmarshalPublicConfig(data) {
119
- let offset = 0;
120
- // Read Key ID
121
- const keyId = data[offset++];
122
- // Read KEM ID
123
- const kemId = (data[offset++] << 8) | data[offset++];
124
- // Read Public Key (32 bytes for X25519)
125
- const publicKeySize = 32;
126
- const publicKeyBytes = data.slice(offset, offset + publicKeySize);
127
- offset += publicKeySize;
128
- // Read Cipher Suites Length
129
- const cipherSuitesLength = (data[offset++] << 8) | data[offset++];
130
- // Read KDF ID
131
- const kdfId = (data[offset++] << 8) | data[offset++];
132
- // Read AEAD ID
133
- const aeadId = (data[offset++] << 8) | data[offset++];
134
- // Create suite (assuming X25519 for now)
135
- const suite = new CipherSuite({
136
- kem: new DhkemX25519HkdfSha256(),
137
- kdf: new HkdfSha256(),
138
- aead: new Aes256Gcm()
139
- });
140
- // Import public key using HPKE library
141
- const publicKey = await suite.kem.deserializePublicKey(publicKeyBytes.buffer);
142
- // For server config, we only have the public key, no private key
143
- // We'll create a dummy private key that won't be used
144
- const dummyPrivateKey = await suite.kem.deserializePrivateKey(new Uint8Array(32).buffer);
145
- return new Identity(suite, publicKey, dummyPrivateKey);
146
- }
147
- /**
148
- * Encrypt request body and set appropriate headers
149
- */
150
- async encryptRequest(request, serverPublicKey) {
151
- const body = await request.arrayBuffer();
152
- if (body.byteLength === 0) {
153
- // No body to encrypt, just set client public key header
154
- const headers = new Headers(request.headers);
155
- headers.set(PROTOCOL.CLIENT_PUBLIC_KEY_HEADER, await this.getPublicKeyHex());
156
- return new Request(request.url, {
157
- method: request.method,
158
- headers,
159
- body: null
160
- });
161
- }
162
- // Create sender for encryption
163
- const sender = await this.suite.createSenderContext({
164
- recipientPublicKey: serverPublicKey
165
- });
166
- // Encrypt the body
167
- const encrypted = await sender.seal(body);
168
- // Get encapsulated key
169
- const encapKey = sender.enc;
170
- // Create chunked format: 4-byte length header + encrypted data
171
- const chunkLength = new Uint8Array(4);
172
- const view = new DataView(chunkLength.buffer);
173
- view.setUint32(0, encrypted.byteLength, false); // Big-endian
174
- const chunkedData = new Uint8Array(4 + encrypted.byteLength);
175
- chunkedData.set(chunkLength, 0);
176
- chunkedData.set(new Uint8Array(encrypted), 4);
177
- // Create new request with encrypted body and headers
178
- const headers = new Headers(request.headers);
179
- headers.set(PROTOCOL.CLIENT_PUBLIC_KEY_HEADER, await this.getPublicKeyHex());
180
- headers.set(PROTOCOL.ENCAPSULATED_KEY_HEADER, Array.from(new Uint8Array(encapKey))
181
- .map(b => b.toString(16).padStart(2, '0'))
182
- .join(''));
183
- return new Request(request.url, {
184
- method: request.method,
185
- headers,
186
- body: chunkedData,
187
- duplex: 'half'
188
- });
189
- }
190
- /**
191
- * Decrypt response body
192
- */
193
- async decryptResponse(response, serverEncapKey) {
194
- if (!response.body) {
195
- return response;
196
- }
197
- // Create receiver for decryption
198
- const receiver = await this.suite.createRecipientContext({
199
- recipientKey: this.privateKey,
200
- enc: serverEncapKey.buffer
201
- });
202
- // Create a readable stream that decrypts chunks as they arrive
203
- const decryptedStream = new ReadableStream({
204
- start(controller) {
205
- const reader = response.body.getReader();
206
- let buffer = new Uint8Array(0);
207
- let offset = 0;
208
- async function pump() {
209
- try {
210
- while (true) {
211
- const { done, value } = await reader.read();
212
- if (done)
213
- break;
214
- // Append new data to buffer
215
- const newBuffer = new Uint8Array(buffer.length + value.length);
216
- newBuffer.set(buffer);
217
- newBuffer.set(value, buffer.length);
218
- buffer = newBuffer;
219
- // Process complete chunks
220
- while (offset + 4 <= buffer.length) {
221
- // Read chunk length (4 bytes big-endian)
222
- const chunkLength = (buffer[offset] << 24) |
223
- (buffer[offset + 1] << 16) |
224
- (buffer[offset + 2] << 8) |
225
- buffer[offset + 3];
226
- offset += 4;
227
- if (chunkLength === 0) {
228
- continue; // Empty chunk
229
- }
230
- // Check if we have the complete chunk
231
- if (offset + chunkLength > buffer.length) {
232
- // Not enough data yet, wait for more
233
- break;
234
- }
235
- // Extract and decrypt the chunk
236
- const encryptedChunk = buffer.slice(offset, offset + chunkLength);
237
- offset += chunkLength;
238
- try {
239
- const decryptedChunk = await receiver.open(encryptedChunk.buffer);
240
- controller.enqueue(new Uint8Array(decryptedChunk));
241
- }
242
- catch (error) {
243
- controller.error(new Error(`Failed to decrypt chunk: ${error}`));
244
- return;
245
- }
246
- }
247
- // Remove processed data from buffer
248
- if (offset > 0) {
249
- buffer = buffer.slice(offset);
250
- offset = 0;
251
- }
252
- }
253
- controller.close();
254
- }
255
- catch (error) {
256
- controller.error(error);
257
- }
258
- }
259
- pump();
260
- }
261
- });
262
- // Create new response with decrypted stream
263
- return new Response(decryptedStream, {
264
- status: response.status,
265
- statusText: response.statusText,
266
- headers: response.headers
267
- });
268
- }
269
- }
270
- //# sourceMappingURL=identity.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"identity.js","sourceRoot":"","sources":["../src/identity.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts DELETED
@@ -1,12 +0,0 @@
1
- /**
2
- * JavaScript client for Encrypted HTTP Body Protocol (EHBP) using HPKE
3
- *
4
- * This library provides secure HTTP communication using Hybrid Public Key Encryption (HPKE)
5
- * as specified in RFC 9180. It automatically encrypts request bodies and decrypts response
6
- * bodies while preserving HTTP headers for routing.
7
- */
8
- export { Identity } from './identity.js';
9
- export { Transport, createTransport } from './client.js';
10
- export { PROTOCOL, HPKE_CONFIG } from './protocol.js';
11
- export type { CipherSuite } from '@hpke/core';
12
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,EAAE,SAAS,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AACzD,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAGtD,YAAY,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC"}
package/dist/index.js DELETED
@@ -1,11 +0,0 @@
1
- /**
2
- * JavaScript client for Encrypted HTTP Body Protocol (EHBP) using HPKE
3
- *
4
- * This library provides secure HTTP communication using Hybrid Public Key Encryption (HPKE)
5
- * as specified in RFC 9180. It automatically encrypts request bodies and decrypts response
6
- * bodies while preserving HTTP headers for routing.
7
- */
8
- export { Identity } from './identity.js';
9
- export { Transport, createTransport } from './client.js';
10
- export { PROTOCOL, HPKE_CONFIG } from './protocol.js';
11
- //# sourceMappingURL=index.js.map
package/dist/index.js.map DELETED
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,EAAE,SAAS,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AACzD,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC"}
@@ -1,19 +0,0 @@
1
- /**
2
- * Protocol constants for EHBP (Encrypted HTTP Body Protocol)
3
- */
4
- export declare const PROTOCOL: {
5
- readonly ENCAPSULATED_KEY_HEADER: "Ehbp-Encapsulated-Key";
6
- readonly CLIENT_PUBLIC_KEY_HEADER: "Ehbp-Client-Public-Key";
7
- readonly KEYS_MEDIA_TYPE: "application/ohttp-keys";
8
- readonly KEYS_PATH: "/.well-known/hpke-keys";
9
- readonly FALLBACK_HEADER: "Ehbp-Fallback";
10
- };
11
- /**
12
- * HPKE suite configuration matching the Go implementation
13
- */
14
- export declare const HPKE_CONFIG: {
15
- readonly KEM: 32;
16
- readonly KDF: 1;
17
- readonly AEAD: 2;
18
- };
19
- //# sourceMappingURL=protocol.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"protocol.d.ts","sourceRoot":"","sources":["../src/protocol.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,eAAO,MAAM,QAAQ;;;;;;CAMX,CAAC;AAEX;;GAEG;AACH,eAAO,MAAM,WAAW;;;;CAId,CAAC"}
package/dist/protocol.js DELETED
@@ -1,19 +0,0 @@
1
- /**
2
- * Protocol constants for EHBP (Encrypted HTTP Body Protocol)
3
- */
4
- export const PROTOCOL = {
5
- ENCAPSULATED_KEY_HEADER: 'Ehbp-Encapsulated-Key',
6
- CLIENT_PUBLIC_KEY_HEADER: 'Ehbp-Client-Public-Key',
7
- KEYS_MEDIA_TYPE: 'application/ohttp-keys',
8
- KEYS_PATH: '/.well-known/hpke-keys',
9
- FALLBACK_HEADER: 'Ehbp-Fallback'
10
- };
11
- /**
12
- * HPKE suite configuration matching the Go implementation
13
- */
14
- export const HPKE_CONFIG = {
15
- KEM: 0x0020, // X25519 HKDF SHA256
16
- KDF: 0x0001, // HKDF SHA256
17
- AEAD: 0x0002 // AES-256-GCM
18
- };
19
- //# sourceMappingURL=protocol.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"protocol.js","sourceRoot":"","sources":["../src/protocol.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,CAAC,MAAM,QAAQ,GAAG;IACtB,uBAAuB,EAAE,uBAAuB;IAChD,wBAAwB,EAAE,wBAAwB;IAClD,eAAe,EAAE,wBAAwB;IACzC,SAAS,EAAE,wBAAwB;IACnC,eAAe,EAAE,eAAe;CACxB,CAAC;AAEX;;GAEG;AACH,MAAM,CAAC,MAAM,WAAW,GAAG;IACzB,GAAG,EAAE,MAAM,EAAE,qBAAqB;IAClC,GAAG,EAAE,MAAM,EAAE,cAAc;IAC3B,IAAI,EAAE,MAAM,CAAC,cAAc;CACnB,CAAC"}
@@ -1,3 +0,0 @@
1
- #!/usr/bin/env node
2
- export {};
3
- //# sourceMappingURL=streaming-test.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"streaming-test.d.ts","sourceRoot":"","sources":["../src/streaming-test.ts"],"names":[],"mappings":""}
@@ -1,102 +0,0 @@
1
- #!/usr/bin/env node
2
- import { Identity, createTransport } from './index.js';
3
- async function streamingTest() {
4
- console.log('EHBP Streaming Test');
5
- console.log('===================');
6
- try {
7
- // Create client identity
8
- console.log('Creating client identity...');
9
- const clientIdentity = await Identity.generate();
10
- console.log('Client identity created');
11
- // Create transport
12
- console.log('Creating transport...');
13
- const serverURL = 'http://localhost:8080';
14
- const transport = await createTransport(serverURL, clientIdentity);
15
- console.log('Transport created');
16
- // Test 1: Basic streaming request
17
- console.log('\n--- Test 1: Basic Streaming ---');
18
- const streamResponse = await transport.get(`${serverURL}/stream`);
19
- console.log('Stream request sent, status:', streamResponse.status);
20
- if (streamResponse.ok) {
21
- console.log('Reading stream data...');
22
- const reader = streamResponse.body?.getReader();
23
- if (reader) {
24
- const decoder = new TextDecoder();
25
- while (true) {
26
- const { done, value } = await reader.read();
27
- if (done)
28
- break;
29
- const text = decoder.decode(value, { stream: true });
30
- process.stdout.write(text);
31
- }
32
- console.log('\nStream completed');
33
- }
34
- else {
35
- console.log('No readable stream available');
36
- }
37
- }
38
- else {
39
- console.log('Stream request failed with status:', streamResponse.status);
40
- }
41
- // Test 2: Multiple concurrent streams
42
- console.log('\n--- Test 2: Concurrent Streams ---');
43
- const concurrentStreams = 3;
44
- const streamPromises = [];
45
- for (let i = 0; i < concurrentStreams; i++) {
46
- streamPromises.push((async (streamId) => {
47
- const response = await transport.get(`${serverURL}/stream`);
48
- if (response.ok && response.body) {
49
- const reader = response.body.getReader();
50
- const decoder = new TextDecoder();
51
- while (true) {
52
- const { done, value } = await reader.read();
53
- if (done)
54
- break;
55
- const text = decoder.decode(value, { stream: true });
56
- // Prefix with stream ID to show concurrency
57
- process.stdout.write(`[Stream ${streamId}] ${text}`);
58
- }
59
- return { streamId };
60
- }
61
- return { streamId };
62
- })(i + 1));
63
- }
64
- const results = await Promise.all(streamPromises);
65
- console.log('\nConcurrent streams completed:');
66
- results.forEach(result => {
67
- console.log(` - Stream ${result.streamId}: completed`);
68
- });
69
- // Test 3: Large data streaming (if server supports it)
70
- console.log('\n--- Test 3: Large Data Stream ---');
71
- try {
72
- const largeStreamResponse = await transport.get(`${serverURL}/stream`);
73
- if (largeStreamResponse.ok) {
74
- console.log('Reading large data stream...');
75
- const reader = largeStreamResponse.body?.getReader();
76
- if (reader) {
77
- const decoder = new TextDecoder();
78
- while (true) {
79
- const { done, value } = await reader.read();
80
- if (done)
81
- break;
82
- const text = decoder.decode(value, { stream: true });
83
- process.stdout.write(text);
84
- }
85
- }
86
- }
87
- }
88
- catch (error) {
89
- console.log('Large data stream test failed:', error instanceof Error ? error.message : String(error));
90
- }
91
- console.log('\nAll streaming tests completed successfully!');
92
- }
93
- catch (error) {
94
- console.error('Streaming test failed:', error);
95
- process.exit(1);
96
- }
97
- }
98
- // Run the streaming test
99
- if (import.meta.url === `file://${process.argv[1]}`) {
100
- streamingTest().catch(console.error);
101
- }
102
- //# sourceMappingURL=streaming-test.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"streaming-test.js","sourceRoot":"","sources":["../src/streaming-test.ts"],"names":[],"mappings":";AAEA,OAAO,EAAE,QAAQ,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAEvD,KAAK,UAAU,aAAa;IAC1B,OAAO,CAAC,GAAG,CAAC,qBAAqB,CAAC,CAAC;IACnC,OAAO,CAAC,GAAG,CAAC,qBAAqB,CAAC,CAAC;IAEnC,IAAI,CAAC;QACH,yBAAyB;QACzB,OAAO,CAAC,GAAG,CAAC,6BAA6B,CAAC,CAAC;QAC3C,MAAM,cAAc,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,CAAC;QACjD,OAAO,CAAC,GAAG,CAAC,yBAAyB,CAAC,CAAC;QAEvC,mBAAmB;QACnB,OAAO,CAAC,GAAG,CAAC,uBAAuB,CAAC,CAAC;QACrC,MAAM,SAAS,GAAG,uBAAuB,CAAC;QAC1C,MAAM,SAAS,GAAG,MAAM,eAAe,CAAC,SAAS,EAAE,cAAc,CAAC,CAAC;QACnE,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAC,CAAC;QAEjC,kCAAkC;QAClC,OAAO,CAAC,GAAG,CAAC,mCAAmC,CAAC,CAAC;QACjD,MAAM,cAAc,GAAG,MAAM,SAAS,CAAC,GAAG,CAAC,GAAG,SAAS,SAAS,CAAC,CAAC;QAClE,OAAO,CAAC,GAAG,CAAC,8BAA8B,EAAE,cAAc,CAAC,MAAM,CAAC,CAAC;QAEnE,IAAI,cAAc,CAAC,EAAE,EAAE,CAAC;YACtB,OAAO,CAAC,GAAG,CAAC,wBAAwB,CAAC,CAAC;YACtC,MAAM,MAAM,GAAG,cAAc,CAAC,IAAI,EAAE,SAAS,EAAE,CAAC;YAChD,IAAI,MAAM,EAAE,CAAC;gBACX,MAAM,OAAO,GAAG,IAAI,WAAW,EAAE,CAAC;gBAElC,OAAO,IAAI,EAAE,CAAC;oBACZ,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;oBAC5C,IAAI,IAAI;wBAAE,MAAM;oBAEhB,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;oBACrD,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;gBAC7B,CAAC;gBAED,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC,CAAC;YACpC,CAAC;iBAAM,CAAC;gBACN,OAAO,CAAC,GAAG,CAAC,8BAA8B,CAAC,CAAC;YAC9C,CAAC;QACH,CAAC;aAAM,CAAC;YACN,OAAO,CAAC,GAAG,CAAC,oCAAoC,EAAE,cAAc,CAAC,MAAM,CAAC,CAAC;QAC3E,CAAC;QAED,sCAAsC;QACtC,OAAO,CAAC,GAAG,CAAC,sCAAsC,CAAC,CAAC;QACpD,MAAM,iBAAiB,GAAG,CAAC,CAAC;QAC5B,MAAM,cAAc,GAAG,EAAE,CAAC;QAE1B,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,iBAAiB,EAAE,CAAC,EAAE,EAAE,CAAC;YAC3C,cAAc,CAAC,IAAI,CACjB,CAAC,KAAK,EAAE,QAAgB,EAAE,EAAE;gBAC1B,MAAM,QAAQ,GAAG,MAAM,SAAS,CAAC,GAAG,CAAC,GAAG,SAAS,SAAS,CAAC,CAAC;gBAC5D,IAAI,QAAQ,CAAC,EAAE,IAAI,QAAQ,CAAC,IAAI,EAAE,CAAC;oBACjC,MAAM,MAAM,GAAG,QAAQ,CAAC,IAAI,CAAC,SAAS,EAAE,CAAC;oBACzC,MAAM,OAAO,GAAG,IAAI,WAAW,EAAE,CAAC;oBAElC,OAAO,IAAI,EAAE,CAAC;wBACZ,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;wBAC5C,IAAI,IAAI;4BAAE,MAAM;wBAEhB,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;wBAErD,4CAA4C;wBAC5C,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,WAAW,QAAQ,KAAK,IAAI,EAAE,CAAC,CAAC;oBACvD,CAAC;oBAED,OAAO,EAAE,QAAQ,EAAE,CAAC;gBACtB,CAAC;gBACD,OAAO,EAAE,QAAQ,EAAE,CAAC;YACtB,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CACV,CAAC;QACJ,CAAC;QAED,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC,CAAC;QAClD,OAAO,CAAC,GAAG,CAAC,iCAAiC,CAAC,CAAC;QAC/C,OAAO,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE;YACvB,OAAO,CAAC,GAAG,CAAC,cAAc,MAAM,CAAC,QAAQ,aAAa,CAAC,CAAC;QAC1D,CAAC,CAAC,CAAC;QAEH,uDAAuD;QACvD,OAAO,CAAC,GAAG,CAAC,qCAAqC,CAAC,CAAC;QACnD,IAAI,CAAC;YACH,MAAM,mBAAmB,GAAG,MAAM,SAAS,CAAC,GAAG,CAAC,GAAG,SAAS,SAAS,CAAC,CAAC;YACvE,IAAI,mBAAmB,CAAC,EAAE,EAAE,CAAC;gBAC3B,OAAO,CAAC,GAAG,CAAC,8BAA8B,CAAC,CAAC;gBAC5C,MAAM,MAAM,GAAG,mBAAmB,CAAC,IAAI,EAAE,SAAS,EAAE,CAAC;gBACrD,IAAI,MAAM,EAAE,CAAC;oBACX,MAAM,OAAO,GAAG,IAAI,WAAW,EAAE,CAAC;oBAElC,OAAO,IAAI,EAAE,CAAC;wBACZ,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;wBAC5C,IAAI,IAAI;4BAAE,MAAM;wBAEhB,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;wBACrD,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;oBAC7B,CAAC;gBACH,CAAC;YACH,CAAC;QACH,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,GAAG,CAAC,gCAAgC,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;QACxG,CAAC;QAED,OAAO,CAAC,GAAG,CAAC,+CAA+C,CAAC,CAAC;IAE/D,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,wBAAwB,EAAE,KAAK,CAAC,CAAC;QAC/C,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;AACH,CAAC;AAED,yBAAyB;AACzB,IAAI,MAAM,CAAC,IAAI,CAAC,GAAG,KAAK,UAAU,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IACpD,aAAa,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;AACvC,CAAC"}
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=client.test.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"client.test.d.ts","sourceRoot":"","sources":["../../src/test/client.test.ts"],"names":[],"mappings":""}
@@ -1,70 +0,0 @@
1
- import { describe, it, before } from 'node:test';
2
- import assert from 'node:assert';
3
- import { Identity, Transport } from '../index.js';
4
- import { PROTOCOL } from '../protocol.js';
5
- describe('Transport', () => {
6
- let clientIdentity;
7
- let serverIdentity;
8
- before(async () => {
9
- clientIdentity = await Identity.generate();
10
- serverIdentity = await Identity.generate();
11
- });
12
- it('should create transport with server public key', () => {
13
- const transport = new Transport(clientIdentity, 'localhost:8080', serverIdentity.getPublicKey());
14
- assert(transport instanceof Transport, 'Should create transport instance');
15
- });
16
- it('should encrypt and decrypt request', async () => {
17
- const serverPublicKey = serverIdentity.getPublicKey();
18
- const originalBody = new TextEncoder().encode('Hello, World!');
19
- const request = new Request('http://localhost:8080/test', {
20
- method: 'POST',
21
- body: originalBody
22
- });
23
- const encryptedRequest = await clientIdentity.encryptRequest(request, serverPublicKey);
24
- // Check that headers are set
25
- assert(encryptedRequest.headers.get(PROTOCOL.CLIENT_PUBLIC_KEY_HEADER), 'Client public key header should be set');
26
- assert(encryptedRequest.headers.get(PROTOCOL.ENCAPSULATED_KEY_HEADER), 'Encapsulated key header should be set');
27
- // Check that body is encrypted (different from original)
28
- const encryptedBody = await encryptedRequest.arrayBuffer();
29
- assert(encryptedBody.byteLength > 0, 'Encrypted body should not be empty');
30
- assert(encryptedBody.byteLength !== originalBody.length, 'Encrypted body should have different length');
31
- });
32
- it('should handle request without body', async () => {
33
- const serverPublicKey = serverIdentity.getPublicKey();
34
- const request = new Request('http://localhost:8080/test', {
35
- method: 'GET'
36
- });
37
- const encryptedRequest = await clientIdentity.encryptRequest(request, serverPublicKey);
38
- // Check that only client public key header is set
39
- assert(encryptedRequest.headers.get(PROTOCOL.CLIENT_PUBLIC_KEY_HEADER), 'Client public key header should be set');
40
- assert(!encryptedRequest.headers.get(PROTOCOL.ENCAPSULATED_KEY_HEADER), 'Encapsulated key header should not be set for empty body');
41
- });
42
- it('should connect to actual server and POST to /secure endpoint', async (t) => {
43
- const serverURL = 'http://localhost:8080';
44
- try {
45
- const keysResponse = await fetch(`${serverURL}${PROTOCOL.KEYS_PATH}`);
46
- if (!keysResponse.ok) {
47
- t.skip('Server not running at localhost:8080');
48
- return;
49
- }
50
- }
51
- catch (error) {
52
- t.skip('Server not running at localhost:8080');
53
- return;
54
- }
55
- // Create transport that will connect to the real server
56
- const { createTransport } = await import('../index.js');
57
- const transport = await createTransport(serverURL, clientIdentity);
58
- const testName = 'Integration Test User';
59
- // Make actual POST request to /secure endpoint
60
- const response = await transport.post(`${serverURL}/secure`, testName, {
61
- headers: { 'Content-Type': 'text/plain' }
62
- });
63
- // Verify response
64
- assert(response.ok, `Response should be ok, got status: ${response.status}`);
65
- const responseText = await response.text();
66
- assert.strictEqual(responseText, `Hello, ${testName}`, 'Server should respond with Hello, {name}');
67
- console.log(`✓ Integration test passed: ${responseText}`);
68
- });
69
- });
70
- //# sourceMappingURL=client.test.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"client.test.js","sourceRoot":"","sources":["../../src/test/client.test.ts"],"names":[],"mappings":"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"}
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=identity.test.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"identity.test.d.ts","sourceRoot":"","sources":["../../src/test/identity.test.ts"],"names":[],"mappings":""}
@@ -1,39 +0,0 @@
1
- import { describe, it } from 'node:test';
2
- import assert from 'node:assert';
3
- import { Identity } from '../identity.js';
4
- describe('Identity', () => {
5
- it('should generate a new identity', async () => {
6
- const identity = await Identity.generate();
7
- assert(identity.getPublicKey() instanceof CryptoKey, 'Public key should be a CryptoKey');
8
- assert(identity.getPrivateKey() instanceof CryptoKey, 'Private key should be a CryptoKey');
9
- const publicKeyHex = await identity.getPublicKeyHex();
10
- assert(publicKeyHex.length > 0, 'Public key hex should not be empty');
11
- });
12
- it('should serialize and deserialize identity', async () => {
13
- const original = await Identity.generate();
14
- const json = await original.toJSON();
15
- const restored = await Identity.fromJSON(json);
16
- const originalHex = await original.getPublicKeyHex();
17
- const restoredHex = await restored.getPublicKeyHex();
18
- assert(originalHex === restoredHex, 'Public keys should match');
19
- assert(original.getPrivateKey() instanceof CryptoKey, 'Private key should be a CryptoKey');
20
- assert(restored.getPrivateKey() instanceof CryptoKey, 'Private key should be a CryptoKey');
21
- });
22
- it('should marshal configuration', async () => {
23
- const identity = await Identity.generate();
24
- const config = await identity.marshalConfig();
25
- assert(config.length > 0, 'Config should not be empty');
26
- assert(config[0] === 0, 'Key ID should be 0');
27
- assert(config[1] === 0x00, 'KEM ID high byte should be 0x00');
28
- assert(config[2] === 0x20, 'KEM ID low byte should be 0x20');
29
- });
30
- it('should unmarshal public configuration', async () => {
31
- const identity = await Identity.generate();
32
- const config = await identity.marshalConfig();
33
- const restored = await Identity.unmarshalPublicConfig(config);
34
- const originalHex = await identity.getPublicKeyHex();
35
- const restoredHex = await restored.getPublicKeyHex();
36
- assert(restoredHex === originalHex, 'Public keys should match');
37
- });
38
- });
39
- //# sourceMappingURL=identity.test.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"identity.test.js","sourceRoot":"","sources":["../../src/test/identity.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,MAAM,MAAM,aAAa,CAAC;AACjC,OAAO,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAE1C,QAAQ,CAAC,UAAU,EAAE,GAAG,EAAE;IACxB,EAAE,CAAC,gCAAgC,EAAE,KAAK,IAAI,EAAE;QAC9C,MAAM,QAAQ,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,CAAC;QAE3C,MAAM,CAAC,QAAQ,CAAC,YAAY,EAAE,YAAY,SAAS,EAAE,kCAAkC,CAAC,CAAC;QACzF,MAAM,CAAC,QAAQ,CAAC,aAAa,EAAE,YAAY,SAAS,EAAE,mCAAmC,CAAC,CAAC;QAC3F,MAAM,YAAY,GAAG,MAAM,QAAQ,CAAC,eAAe,EAAE,CAAC;QACtD,MAAM,CAAC,YAAY,CAAC,MAAM,GAAG,CAAC,EAAE,oCAAoC,CAAC,CAAC;IACxE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,2CAA2C,EAAE,KAAK,IAAI,EAAE;QACzD,MAAM,QAAQ,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,CAAC;QAC3C,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,MAAM,EAAE,CAAC;QACrC,MAAM,QAAQ,GAAG,MAAM,QAAQ,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QAE/C,MAAM,WAAW,GAAG,MAAM,QAAQ,CAAC,eAAe,EAAE,CAAC;QACrD,MAAM,WAAW,GAAG,MAAM,QAAQ,CAAC,eAAe,EAAE,CAAC;QACrD,MAAM,CAAC,WAAW,KAAK,WAAW,EAAE,0BAA0B,CAAC,CAAC;QAChE,MAAM,CAAC,QAAQ,CAAC,aAAa,EAAE,YAAY,SAAS,EAAE,mCAAmC,CAAC,CAAC;QAC3F,MAAM,CAAC,QAAQ,CAAC,aAAa,EAAE,YAAY,SAAS,EAAE,mCAAmC,CAAC,CAAC;IAC7F,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,8BAA8B,EAAE,KAAK,IAAI,EAAE;QAC5C,MAAM,QAAQ,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,CAAC;QAC3C,MAAM,MAAM,GAAG,MAAM,QAAQ,CAAC,aAAa,EAAE,CAAC;QAE9C,MAAM,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,EAAE,4BAA4B,CAAC,CAAC;QACxD,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,oBAAoB,CAAC,CAAC;QAC9C,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,IAAI,EAAE,iCAAiC,CAAC,CAAC;QAC9D,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,IAAI,EAAE,gCAAgC,CAAC,CAAC;IAC/D,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,uCAAuC,EAAE,KAAK,IAAI,EAAE;QACrD,MAAM,QAAQ,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,CAAC;QAC3C,MAAM,MAAM,GAAG,MAAM,QAAQ,CAAC,aAAa,EAAE,CAAC;QAC9C,MAAM,QAAQ,GAAG,MAAM,QAAQ,CAAC,qBAAqB,CAAC,MAAM,CAAC,CAAC;QAE9D,MAAM,WAAW,GAAG,MAAM,QAAQ,CAAC,eAAe,EAAE,CAAC;QACrD,MAAM,WAAW,GAAG,MAAM,QAAQ,CAAC,eAAe,EAAE,CAAC;QACrD,MAAM,CAAC,WAAW,KAAK,WAAW,EAAE,0BAA0B,CAAC,CAAC;IAClE,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=streaming.test.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"streaming.test.d.ts","sourceRoot":"","sources":["../../src/test/streaming.test.ts"],"names":[],"mappings":""}
@@ -1,71 +0,0 @@
1
- import { describe, it } from 'node:test';
2
- import assert from 'node:assert';
3
- describe('Streaming', () => {
4
- it('should handle streaming responses', async () => {
5
- // Create a mock streaming response
6
- const mockStreamData = 'Number: 1\nNumber: 2\nNumber: 3\n';
7
- const mockResponse = new Response(mockStreamData, {
8
- status: 200,
9
- headers: {
10
- 'Content-Type': 'text/plain',
11
- 'Ehbp-Encapsulated-Key': 'abcd1234' // Mock encapsulated key
12
- }
13
- });
14
- // Test that we can read from a stream
15
- const reader = mockResponse.body?.getReader();
16
- assert(reader, 'Response should have a readable stream');
17
- const decoder = new TextDecoder();
18
- let receivedData = '';
19
- while (true) {
20
- const { done, value } = await reader.read();
21
- if (done)
22
- break;
23
- const text = decoder.decode(value, { stream: true });
24
- receivedData += text;
25
- }
26
- assert(receivedData === mockStreamData, 'Should receive all stream data');
27
- });
28
- it('should handle empty streams', async () => {
29
- const emptyResponse = new Response('', {
30
- status: 200,
31
- headers: {
32
- 'Ehbp-Encapsulated-Key': 'abcd1234'
33
- }
34
- });
35
- const reader = emptyResponse.body?.getReader();
36
- assert(reader, 'Response should have a readable stream');
37
- const { done } = await reader.read();
38
- assert(done, 'Empty stream should be done immediately');
39
- });
40
- it('should handle chunked data correctly', async () => {
41
- // Simulate chunked data
42
- const chunks = ['Hello', ' ', 'World', '!'];
43
- const stream = new ReadableStream({
44
- start(controller) {
45
- chunks.forEach(chunk => {
46
- controller.enqueue(new TextEncoder().encode(chunk));
47
- });
48
- controller.close();
49
- }
50
- });
51
- const response = new Response(stream, {
52
- status: 200,
53
- headers: {
54
- 'Ehbp-Encapsulated-Key': 'abcd1234'
55
- }
56
- });
57
- const reader = response.body?.getReader();
58
- assert(reader, 'Response should have a readable stream');
59
- const decoder = new TextDecoder();
60
- let receivedData = '';
61
- while (true) {
62
- const { done, value } = await reader.read();
63
- if (done)
64
- break;
65
- const text = decoder.decode(value, { stream: true });
66
- receivedData += text;
67
- }
68
- assert(receivedData === 'Hello World!', 'Should receive all chunks correctly');
69
- });
70
- });
71
- //# sourceMappingURL=streaming.test.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"streaming.test.js","sourceRoot":"","sources":["../../src/test/streaming.test.ts"],"names":[],"mappings":"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"}