@harperfast/integration-testing 0.4.0 → 0.5.1

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 (57) hide show
  1. package/README.md +20 -5
  2. package/dist/harperLifecycle.d.ts +84 -4
  3. package/dist/harperLifecycle.js +246 -34
  4. package/dist/harperLifecycle.js.map +1 -1
  5. package/dist/loopbackAddressPool.d.ts +3 -3
  6. package/dist/loopbackAddressPool.js +26 -15
  7. package/dist/loopbackAddressPool.js.map +1 -1
  8. package/dist/portUtils.d.ts +26 -0
  9. package/dist/portUtils.js +47 -0
  10. package/dist/portUtils.js.map +1 -0
  11. package/dist/run.js +0 -0
  12. package/package.json +4 -3
  13. package/dist/security/certGenUtils.d.ts +0 -52
  14. package/dist/security/certGenUtils.js +0 -170
  15. package/dist/security/certGenUtils.js.map +0 -1
  16. package/dist/security/crl/generate-test-certs.d.ts +0 -34
  17. package/dist/security/crl/generate-test-certs.js +0 -81
  18. package/dist/security/crl/generate-test-certs.js.map +0 -1
  19. package/dist/security/ocsp/generate-test-certs.d.ts +0 -55
  20. package/dist/security/ocsp/generate-test-certs.js +0 -106
  21. package/dist/security/ocsp/generate-test-certs.js.map +0 -1
  22. package/dist/security/ocspServer.d.ts +0 -18
  23. package/dist/security/ocspServer.js +0 -132
  24. package/dist/security/ocspServer.js.map +0 -1
  25. package/dist/securityServices.d.ts +0 -49
  26. package/dist/securityServices.js +0 -120
  27. package/dist/securityServices.js.map +0 -1
  28. package/dist/src/harperLifecycle.d.ts +0 -156
  29. package/dist/src/harperLifecycle.js +0 -315
  30. package/dist/src/harperLifecycle.js.map +0 -1
  31. package/dist/src/index.d.ts +0 -3
  32. package/dist/src/index.js +0 -4
  33. package/dist/src/index.js.map +0 -1
  34. package/dist/src/loopbackAddressPool.d.ts +0 -50
  35. package/dist/src/loopbackAddressPool.js +0 -337
  36. package/dist/src/loopbackAddressPool.js.map +0 -1
  37. package/dist/src/run.d.ts +0 -2
  38. package/dist/src/run.js +0 -94
  39. package/dist/src/run.js.map +0 -1
  40. package/dist/src/security/certGenUtils.d.ts +0 -52
  41. package/dist/src/security/certGenUtils.js +0 -170
  42. package/dist/src/security/certGenUtils.js.map +0 -1
  43. package/dist/src/security/crl/generate-test-certs.d.ts +0 -34
  44. package/dist/src/security/crl/generate-test-certs.js +0 -81
  45. package/dist/src/security/crl/generate-test-certs.js.map +0 -1
  46. package/dist/src/security/ocsp/generate-test-certs.d.ts +0 -55
  47. package/dist/src/security/ocsp/generate-test-certs.js +0 -106
  48. package/dist/src/security/ocsp/generate-test-certs.js.map +0 -1
  49. package/dist/src/security/ocspServer.d.ts +0 -18
  50. package/dist/src/security/ocspServer.js +0 -132
  51. package/dist/src/security/ocspServer.js.map +0 -1
  52. package/dist/src/securityServices.d.ts +0 -49
  53. package/dist/src/securityServices.js +0 -120
  54. package/dist/src/securityServices.js.map +0 -1
  55. package/dist/src/targz.d.ts +0 -6
  56. package/dist/src/targz.js +0 -20
  57. package/dist/src/targz.js.map +0 -1
@@ -4,11 +4,21 @@ import { tmpdir } from 'node:os';
4
4
  import { open, readFile, stat, unlink, writeFile } from 'node:fs/promises';
5
5
  import { createServer } from 'node:net';
6
6
  // Configuration constants
7
+ // The pool starts at 127.0.0.2 by default (rather than 127.0.0.1) to avoid conflicting
8
+ // with other servers commonly bound to localhost. Override via the
9
+ // HARPER_INTEGRATION_TEST_LOOPBACK_POOL_START environment variable.
10
+ const HARPER_LOOPBACK_POOL_START = process.env.HARPER_INTEGRATION_TEST_LOOPBACK_POOL_START
11
+ ? parseInt(process.env.HARPER_INTEGRATION_TEST_LOOPBACK_POOL_START, 10)
12
+ : 2;
13
+ if (HARPER_LOOPBACK_POOL_START < 1 || HARPER_LOOPBACK_POOL_START > 255) {
14
+ throw new Error('HARPER_INTEGRATION_TEST_LOOPBACK_POOL_START must be between 1 and 255');
15
+ }
7
16
  const HARPER_LOOPBACK_POOL_COUNT = process.env.HARPER_INTEGRATION_TEST_LOOPBACK_POOL_COUNT
8
17
  ? parseInt(process.env.HARPER_INTEGRATION_TEST_LOOPBACK_POOL_COUNT, 10)
9
18
  : 32;
10
- if (HARPER_LOOPBACK_POOL_COUNT < 1 || HARPER_LOOPBACK_POOL_COUNT > 255) {
11
- throw new Error('HARPER_INTEGRATION_TEST_LOOPBACK_POOL_COUNT must be between 1 and 255');
19
+ const HARPER_LOOPBACK_POOL_MAX = 256 - HARPER_LOOPBACK_POOL_START;
20
+ if (HARPER_LOOPBACK_POOL_COUNT < 1 || HARPER_LOOPBACK_POOL_COUNT > HARPER_LOOPBACK_POOL_MAX) {
21
+ throw new Error(`HARPER_INTEGRATION_TEST_LOOPBACK_POOL_COUNT must be between 1 and ${HARPER_LOOPBACK_POOL_MAX}`);
12
22
  }
13
23
  const HARPER_LOOPBACK_POOL_PATH = join(tmpdir(), 'harper-integration-test-loopback-pool.json');
14
24
  const HARPER_LOOPBACK_POOL_LOCK_PATH = join(tmpdir(), 'harper-integration-test-loopback-pool.lock');
@@ -27,7 +37,7 @@ class LoopbackAddressValidationError extends Error {
27
37
  }
28
38
  class InvalidLoopbackAddressError extends Error {
29
39
  constructor(address) {
30
- super(`Invalid loopback address format: ${address}. Expected format: 127.0.0.X where X is between 1 and ${HARPER_LOOPBACK_POOL_COUNT}`);
40
+ super(`Invalid loopback address format: ${address}. Expected format: 127.0.0.X where X is between ${HARPER_LOOPBACK_POOL_START} and ${HARPER_LOOPBACK_POOL_START + HARPER_LOOPBACK_POOL_COUNT - 1}`);
31
41
  this.name = 'InvalidLoopbackAddressError';
32
42
  }
33
43
  }
@@ -101,7 +111,7 @@ async function withLock(callback) {
101
111
  }
102
112
  /**
103
113
  * Reads the loopback pool from the pool file. The pool is a JSON array where each
104
- * index represents a loopback address (127.0.0.1, 127.0.0.2, etc.) and the value
114
+ * index represents a loopback address (127.0.0.2, 127.0.0.3, etc.) and the value
105
115
  * is either null (available) or a process PID (in use).
106
116
  *
107
117
  * If the file doesn't exist, creates and returns a new empty pool with all addresses
@@ -148,8 +158,9 @@ function findAvailableIndex(pool) {
148
158
  /**
149
159
  * Validates the format of a loopback address and extracts the pool index.
150
160
  *
151
- * Expects addresses in the format "127.0.0.X" where X is between 1 and the pool count.
152
- * The returned index is 0-based (e.g., "127.0.0.1" returns index 0).
161
+ * Expects addresses in the format "127.0.0.X" where X is between the pool start
162
+ * (127.0.0.2) and the pool start + pool count - 1. The returned index is 0-based
163
+ * (e.g., "127.0.0.2" returns index 0).
153
164
  *
154
165
  * @param address The loopback address to parse (e.g., "127.0.0.2")
155
166
  * @returns The 0-based pool index for this address
@@ -160,7 +171,7 @@ function parseLoopbackAddress(address) {
160
171
  if (parts.length !== 4 || parts[0] !== '127' || parts[1] !== '0' || parts[2] !== '0') {
161
172
  throw new InvalidLoopbackAddressError(address);
162
173
  }
163
- const index = parseInt(parts[3], 10) - 1;
174
+ const index = parseInt(parts[3], 10) - HARPER_LOOPBACK_POOL_START;
164
175
  if (isNaN(index) || index < 0 || index >= HARPER_LOOPBACK_POOL_COUNT) {
165
176
  throw new InvalidLoopbackAddressError(address);
166
177
  }
@@ -198,13 +209,13 @@ function validateLoopbackAddress(loopbackAddress) {
198
209
  * bind to each one. It returns an object containing arrays of successfully bound
199
210
  * loopback addresses and those that failed along with their errors.
200
211
  *
201
- * It will check all loopback addresses from 127.0.0.1 to 127.0.0.32 (by default).
212
+ * It will check all loopback addresses from 127.0.0.2 to 127.0.0.33 (by default).
202
213
  *
203
214
  * Use the HARPER_INTEGRATION_TEST_LOOPBACK_POOL_COUNT environment variable to
204
- * adjust the number of loopback addresses to validate (up to 255).
215
+ * adjust the number of loopback addresses to validate (up to 254).
205
216
  */
206
217
  export async function validateLoopbackAddressPool() {
207
- return Promise.allSettled(Array.from({ length: HARPER_LOOPBACK_POOL_COUNT }, (_, i) => validateLoopbackAddress(`127.0.0.${i + 1}`))).then((results) => results.reduce((acc, result) => {
218
+ return Promise.allSettled(Array.from({ length: HARPER_LOOPBACK_POOL_COUNT }, (_, i) => validateLoopbackAddress(`127.0.0.${i + HARPER_LOOPBACK_POOL_START}`))).then((results) => results.reduce((acc, result) => {
208
219
  if (result.status === 'fulfilled') {
209
220
  acc.successful.push(result.value);
210
221
  }
@@ -236,10 +247,10 @@ export async function validateLoopbackAddressPool() {
236
247
  * @throws {LoopbackAddressValidationError} If the allocated address cannot be bound to
237
248
  */
238
249
  export async function getNextAvailableLoopbackAddress() {
239
- // Each index+1 is a different loopback address that a test process will be assigned to
240
- // So if the first test process number is 42, it would be assigned to index 0 associated with address 127.0.0.1
250
+ // Each index maps to a different loopback address (index 0 -> 127.0.0.2, index 1 -> 127.0.0.3, etc.)
251
+ // So if the first test process number is 42, it would be assigned to index 0 associated with address 127.0.0.2
241
252
  // [42, null, null, ...];
242
- // Then the next process (call is 43) gets the next available, so index 1 -> 127.0.0.2
253
+ // Then the next process (call is 43) gets the next available, so index 1 -> 127.0.0.3
243
254
  // [42, 43, null, ...];
244
255
  // And so on...
245
256
  // As processes exit and release their loopback addresses, those addresses become available for new processes to use
@@ -268,7 +279,7 @@ export async function getNextAvailableLoopbackAddress() {
268
279
  });
269
280
  // If we got an index, validate and return the address
270
281
  if (assignedIndex !== null) {
271
- const loopbackAddress = `127.0.0.${assignedIndex + 1}`;
282
+ const loopbackAddress = `127.0.0.${assignedIndex + HARPER_LOOPBACK_POOL_START}`;
272
283
  try {
273
284
  await validateLoopbackAddress(loopbackAddress);
274
285
  return loopbackAddress;
@@ -301,7 +312,7 @@ function removeDeadProcessesFromPool(loopbackPool) {
301
312
  /**
302
313
  * Releases a loopback address back to the pool, making it available for other processes.
303
314
  *
304
- * @param address The loopback address to release (e.g., "127.0.0.1")
315
+ * @param address The loopback address to release (e.g., "127.0.0.2")
305
316
  * @throws InvalidLoopbackAddressError if the address format is invalid
306
317
  */
307
318
  export async function releaseLoopbackAddress(address) {
@@ -1 +1 @@
1
- {"version":3,"file":"loopbackAddressPool.js","sourceRoot":"","sources":["../src/loopbackAddressPool.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"loopbackAddressPool.js","sourceRoot":"","sources":["../src/loopbackAddressPool.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,26 @@
1
+ /**
2
+ * Checks whether a TCP port can be bound on a given host (i.e. the port is free).
3
+ *
4
+ * Attempts to bind a throwaway server to `host:port`; resolves `true` if the bind
5
+ * succeeds (the server is closed immediately) and `false` if it fails (e.g. the port
6
+ * is still held by another process or socket).
7
+ *
8
+ * @param host The host/address to bind on (e.g. "127.0.0.2")
9
+ * @param port The port to test
10
+ * @returns A promise resolving to `true` if the port is free, `false` otherwise
11
+ */
12
+ export declare function isPortFree(host: string, port: number): Promise<boolean>;
13
+ /**
14
+ * Polls until every `host:port` in `ports` is free, or `timeoutMs` elapses.
15
+ *
16
+ * Unlike binding to an ephemeral port (which only proves the *address* is usable), this
17
+ * verifies the specific fixed ports a Harper instance binds are actually released, which
18
+ * is what the next test suite needs before it can reuse the address.
19
+ *
20
+ * @param host The host/address the ports are bound on (e.g. "127.0.0.2")
21
+ * @param ports The fixed ports to wait on
22
+ * @param timeoutMs Maximum time to wait for all ports to become free
23
+ * @param pollIntervalMs Delay between polls (default 100ms)
24
+ * @returns `true` if all ports became free within the timeout, `false` if it gave up
25
+ */
26
+ export declare function waitForPortsFree(host: string, ports: number[], timeoutMs: number, pollIntervalMs?: number): Promise<boolean>;
@@ -0,0 +1,47 @@
1
+ import { createServer } from 'node:net';
2
+ import { setTimeout as sleep } from 'node:timers/promises';
3
+ /**
4
+ * Checks whether a TCP port can be bound on a given host (i.e. the port is free).
5
+ *
6
+ * Attempts to bind a throwaway server to `host:port`; resolves `true` if the bind
7
+ * succeeds (the server is closed immediately) and `false` if it fails (e.g. the port
8
+ * is still held by another process or socket).
9
+ *
10
+ * @param host The host/address to bind on (e.g. "127.0.0.2")
11
+ * @param port The port to test
12
+ * @returns A promise resolving to `true` if the port is free, `false` otherwise
13
+ */
14
+ export function isPortFree(host, port) {
15
+ return new Promise((resolve) => {
16
+ const server = createServer();
17
+ server.once('error', () => resolve(false));
18
+ server.listen(port, host, () => {
19
+ server.close(() => resolve(true));
20
+ });
21
+ });
22
+ }
23
+ /**
24
+ * Polls until every `host:port` in `ports` is free, or `timeoutMs` elapses.
25
+ *
26
+ * Unlike binding to an ephemeral port (which only proves the *address* is usable), this
27
+ * verifies the specific fixed ports a Harper instance binds are actually released, which
28
+ * is what the next test suite needs before it can reuse the address.
29
+ *
30
+ * @param host The host/address the ports are bound on (e.g. "127.0.0.2")
31
+ * @param ports The fixed ports to wait on
32
+ * @param timeoutMs Maximum time to wait for all ports to become free
33
+ * @param pollIntervalMs Delay between polls (default 100ms)
34
+ * @returns `true` if all ports became free within the timeout, `false` if it gave up
35
+ */
36
+ export async function waitForPortsFree(host, ports, timeoutMs, pollIntervalMs = 100) {
37
+ const deadline = Date.now() + timeoutMs;
38
+ while (true) {
39
+ const results = await Promise.all(ports.map((port) => isPortFree(host, port)));
40
+ if (results.every(Boolean))
41
+ return true;
42
+ if (Date.now() >= deadline)
43
+ return false;
44
+ await sleep(pollIntervalMs);
45
+ }
46
+ }
47
+ //# sourceMappingURL=portUtils.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"portUtils.js","sourceRoot":"","sources":["../src/portUtils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AACxC,OAAO,EAAE,UAAU,IAAI,KAAK,EAAE,MAAM,sBAAsB,CAAC;AAE3D;;;;;;;;;;GAUG;AACH,MAAM,UAAU,UAAU,CAAC,IAAY,EAAE,IAAY;IACpD,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE;QAC9B,MAAM,MAAM,GAAG,YAAY,EAAE,CAAC;QAC9B,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC;QAC3C,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE;YAC9B,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC;QACnC,CAAC,CAAC,CAAC;IACJ,CAAC,CAAC,CAAC;AACJ,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACrC,IAAY,EACZ,KAAe,EACf,SAAiB,EACjB,cAAc,GAAG,GAAG;IAEpB,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,SAAS,CAAC;IACxC,OAAO,IAAI,EAAE,CAAC;QACb,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,UAAU,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC,CAAC,CAAC;QAC/E,IAAI,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC;YAAE,OAAO,IAAI,CAAC;QACxC,IAAI,IAAI,CAAC,GAAG,EAAE,IAAI,QAAQ;YAAE,OAAO,KAAK,CAAC;QACzC,MAAM,KAAK,CAAC,cAAc,CAAC,CAAC;IAC7B,CAAC;AACF,CAAC"}
package/dist/run.js CHANGED
File without changes
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@harperfast/integration-testing",
3
- "version": "0.4.0",
3
+ "version": "0.5.1",
4
4
  "type": "module",
5
5
  "description": "Integration testing utilities for Harper-based projects. Provides Harper instance lifecycle management, loopback address pooling, and a test runner script.",
6
6
  "license": "Apache-2.0",
@@ -22,7 +22,8 @@
22
22
  ],
23
23
  "scripts": {
24
24
  "check": "tsc",
25
- "build": "tsc -p tsconfig.build.json"
25
+ "build": "tsc -p tsconfig.build.json",
26
+ "test": "node --test \"test/**/*.test.ts\""
26
27
  },
27
28
  "engines": {
28
29
  "node": ">=20"
@@ -30,7 +31,7 @@
30
31
  "devEngines": {
31
32
  "runtime": {
32
33
  "name": "node",
33
- "version": ">=22",
34
+ "version": ">=22.18.0",
34
35
  "onFail": "error"
35
36
  },
36
37
  "packageManager": {
@@ -1,52 +0,0 @@
1
- /**
2
- * Pure Node.js X.509 certificate and CRL generation utilities
3
- *
4
- * Uses Node.js built-in webcrypto (Ed25519) + pkijs for ASN.1 encoding.
5
- * No openssl CLI dependency — fully portable across macOS and Linux.
6
- */
7
- import * as pkijs from 'pkijs';
8
- declare const OCSP_SIGNING_OID = "1.3.6.1.5.5.7.3.9";
9
- declare const CLIENT_AUTH_OID = "1.3.6.1.5.5.7.3.2";
10
- export interface Ed25519KeyPair {
11
- privateKey: CryptoKey;
12
- publicKey: CryptoKey;
13
- /** PKCS8 PEM string */
14
- privateKeyPem: string;
15
- }
16
- export declare function generateEd25519KeyPair(): Promise<Ed25519KeyPair>;
17
- /** Convert a pkijs Certificate to PEM string */
18
- export declare function certToPem(cert: pkijs.Certificate): string;
19
- /** Convert a pkijs CertificateRevocationList to PEM string */
20
- export declare function crlToPem(crl: pkijs.CertificateRevocationList): string;
21
- interface CertOptions {
22
- serialNumber: number;
23
- subject: {
24
- CN: string;
25
- O?: string;
26
- };
27
- issuer: {
28
- CN: string;
29
- O?: string;
30
- };
31
- validDays: number;
32
- issuerKey: CryptoKey;
33
- subjectPublicKey: CryptoKey;
34
- isCA?: boolean;
35
- extensions?: pkijs.Extension[];
36
- }
37
- /** Create a signed Ed25519 X.509 v3 certificate */
38
- export declare function createCertificate(opts: CertOptions): Promise<pkijs.Certificate>;
39
- /** Create a CRL Distribution Points extension */
40
- export declare function makeCRLDistributionPointsExt(url: string): pkijs.Extension;
41
- /** Create an Authority Info Access extension with an OCSP URL */
42
- export declare function makeOCSPAIAExt(url: string): pkijs.Extension;
43
- /** Create an Extended Key Usage extension */
44
- export declare function makeExtKeyUsageExt(oids: string[]): pkijs.Extension;
45
- export { OCSP_SIGNING_OID, CLIENT_AUTH_OID };
46
- /** Create a signed X.509v2 CRL */
47
- export declare function createCRL(issuerCert: pkijs.Certificate, issuerKey: CryptoKey, revokedSerials: number[]): Promise<pkijs.CertificateRevocationList>;
48
- /**
49
- * Sign a pkijs BasicOCSPResponse with an Ed25519 key.
50
- * Must be called after tbsResponseData.responses is populated.
51
- */
52
- export declare function signBasicOCSPResponse(basicResponse: pkijs.BasicOCSPResponse, privateKey: CryptoKey): Promise<void>;
@@ -1,170 +0,0 @@
1
- /**
2
- * Pure Node.js X.509 certificate and CRL generation utilities
3
- *
4
- * Uses Node.js built-in webcrypto (Ed25519) + pkijs for ASN.1 encoding.
5
- * No openssl CLI dependency — fully portable across macOS and Linux.
6
- */
7
- import { webcrypto } from 'node:crypto';
8
- import * as pkijs from 'pkijs';
9
- import * as asn1js from 'asn1js';
10
- // Ed25519 OID (RFC 8410)
11
- const ED25519_OID = '1.3.101.112';
12
- // Standard extension OIDs
13
- const BASIC_CONSTRAINTS_OID = '2.5.29.19';
14
- const CRL_DISTRIBUTION_POINTS_OID = '2.5.29.31';
15
- const AUTHORITY_INFO_ACCESS_OID = '1.3.6.1.5.5.7.1.1';
16
- const EXT_KEY_USAGE_OID = '2.5.29.37';
17
- const OCSP_SIGNING_OID = '1.3.6.1.5.5.7.3.9';
18
- const CLIENT_AUTH_OID = '1.3.6.1.5.5.7.3.2';
19
- const OCSP_ACCESS_METHOD_OID = '1.3.6.1.5.5.7.48.1';
20
- // Configure pkijs to use Node.js webcrypto
21
- pkijs.setEngine('node', new pkijs.CryptoEngine({ name: 'node', crypto: webcrypto }));
22
- export async function generateEd25519KeyPair() {
23
- // Ed25519 is supported at runtime (Node 20+) but @types/node lacks dedicated types for it
24
- const keyPair = (await webcrypto.subtle.generateKey({ name: 'Ed25519' }, true, [
25
- 'sign',
26
- 'verify',
27
- ]));
28
- const pkcs8 = await webcrypto.subtle.exportKey('pkcs8', keyPair.privateKey);
29
- const b64 = Buffer.from(pkcs8).toString('base64');
30
- const lines = b64.match(/.{1,64}/g).join('\n');
31
- const privateKeyPem = `-----BEGIN PRIVATE KEY-----\n${lines}\n-----END PRIVATE KEY-----\n`;
32
- return { privateKey: keyPair.privateKey, publicKey: keyPair.publicKey, privateKeyPem };
33
- }
34
- /**
35
- * Sign a pkijs Certificate or CertificateRevocationList with an Ed25519 key.
36
- * Bypasses pkijs's sign() method which does not support Ed25519.
37
- */
38
- async function signWithEd25519(obj, privateKey) {
39
- const algId = new pkijs.AlgorithmIdentifier({ algorithmId: ED25519_OID });
40
- obj.signature = algId;
41
- obj.signatureAlgorithm = algId;
42
- const tbsBer = obj.encodeTBS().toBER();
43
- obj.tbsView = new Uint8Array(tbsBer);
44
- const sig = await webcrypto.subtle.sign('Ed25519', privateKey, tbsBer);
45
- obj.signatureValue = new asn1js.BitString({ valueHex: sig });
46
- }
47
- /** Convert a pkijs Certificate to PEM string */
48
- export function certToPem(cert) {
49
- const der = cert.toSchema(false).toBER();
50
- const b64 = Buffer.from(der).toString('base64');
51
- return `-----BEGIN CERTIFICATE-----\n${b64.match(/.{1,64}/g).join('\n')}\n-----END CERTIFICATE-----\n`;
52
- }
53
- /** Convert a pkijs CertificateRevocationList to PEM string */
54
- export function crlToPem(crl) {
55
- const der = crl.toSchema(false).toBER();
56
- const b64 = Buffer.from(der).toString('base64');
57
- return `-----BEGIN X509 CRL-----\n${b64.match(/.{1,64}/g).join('\n')}\n-----END X509 CRL-----\n`;
58
- }
59
- /** Create a signed Ed25519 X.509 v3 certificate */
60
- export async function createCertificate(opts) {
61
- const cert = new pkijs.Certificate();
62
- cert.version = 2; // v3
63
- cert.serialNumber = new asn1js.Integer({ value: opts.serialNumber });
64
- const now = new Date();
65
- cert.notBefore.value = now;
66
- cert.notAfter.value = new Date(now.getTime() + opts.validDays * 24 * 60 * 60 * 1000);
67
- // Build subject RDN
68
- const buildRDN = (dn, target) => {
69
- target.typesAndValues.push(new pkijs.AttributeTypeAndValue({
70
- type: '2.5.4.3',
71
- value: new asn1js.Utf8String({ value: dn.CN }),
72
- }));
73
- if (dn.O) {
74
- target.typesAndValues.push(new pkijs.AttributeTypeAndValue({
75
- type: '2.5.4.10',
76
- value: new asn1js.Utf8String({ value: dn.O }),
77
- }));
78
- }
79
- };
80
- buildRDN(opts.subject, cert.subject);
81
- buildRDN(opts.issuer, cert.issuer);
82
- // Import public key into SubjectPublicKeyInfo
83
- const spki = await webcrypto.subtle.exportKey('spki', opts.subjectPublicKey);
84
- const spkiAsn1 = asn1js.fromBER(spki);
85
- cert.subjectPublicKeyInfo.fromSchema(spkiAsn1.result);
86
- // Add basic constraints extension (always present)
87
- cert.extensions = [];
88
- const bc = new pkijs.BasicConstraints({ cA: opts.isCA === true });
89
- cert.extensions.push(new pkijs.Extension({
90
- extnID: BASIC_CONSTRAINTS_OID,
91
- critical: true,
92
- extnValue: bc.toSchema().toBER(),
93
- }));
94
- // Add caller-supplied extensions
95
- if (opts.extensions) {
96
- cert.extensions.push(...opts.extensions);
97
- }
98
- await signWithEd25519(cert, opts.issuerKey);
99
- return cert;
100
- }
101
- /** Create a CRL Distribution Points extension */
102
- export function makeCRLDistributionPointsExt(url) {
103
- const dp = new pkijs.DistributionPoint({
104
- distributionPoint: [new pkijs.GeneralName({ type: 6, value: url })],
105
- });
106
- const cdp = new pkijs.CRLDistributionPoints({ distributionPoints: [dp] });
107
- return new pkijs.Extension({
108
- extnID: CRL_DISTRIBUTION_POINTS_OID,
109
- critical: false,
110
- extnValue: cdp.toSchema().toBER(),
111
- });
112
- }
113
- /** Create an Authority Info Access extension with an OCSP URL */
114
- export function makeOCSPAIAExt(url) {
115
- const desc = new pkijs.AccessDescription({
116
- accessMethod: OCSP_ACCESS_METHOD_OID,
117
- accessLocation: new pkijs.GeneralName({ type: 6, value: url }),
118
- });
119
- const aia = new pkijs.InfoAccess({ accessDescriptions: [desc] });
120
- return new pkijs.Extension({
121
- extnID: AUTHORITY_INFO_ACCESS_OID,
122
- critical: false,
123
- extnValue: aia.toSchema().toBER(),
124
- });
125
- }
126
- /** Create an Extended Key Usage extension */
127
- export function makeExtKeyUsageExt(oids) {
128
- const seq = new asn1js.Sequence({
129
- value: oids.map((oid) => new asn1js.ObjectIdentifier({ value: oid })),
130
- });
131
- return new pkijs.Extension({
132
- extnID: EXT_KEY_USAGE_OID,
133
- critical: false,
134
- extnValue: seq.toBER(),
135
- });
136
- }
137
- export { OCSP_SIGNING_OID, CLIENT_AUTH_OID };
138
- /** Create a signed X.509v2 CRL */
139
- export async function createCRL(issuerCert, issuerKey, revokedSerials) {
140
- const crl = new pkijs.CertificateRevocationList();
141
- crl.version = 1; // CRLv2 = version field value 1
142
- // Copy issuer from CA cert subject
143
- crl.issuer = issuerCert.subject;
144
- const now = new Date();
145
- const next = new Date(now.getTime() + 30 * 24 * 60 * 60 * 1000);
146
- crl.thisUpdate = new pkijs.Time({ type: 0, value: now });
147
- crl.nextUpdate = new pkijs.Time({ type: 0, value: next });
148
- if (revokedSerials.length > 0) {
149
- crl.revokedCertificates = revokedSerials.map((serial) => new pkijs.RevokedCertificate({
150
- userCertificate: new asn1js.Integer({ value: serial }),
151
- revocationDate: new pkijs.Time({ type: 0, value: now }),
152
- }));
153
- }
154
- await signWithEd25519(crl, issuerKey);
155
- return crl;
156
- }
157
- /**
158
- * Sign a pkijs BasicOCSPResponse with an Ed25519 key.
159
- * Must be called after tbsResponseData.responses is populated.
160
- */
161
- export async function signBasicOCSPResponse(basicResponse, privateKey) {
162
- const algId = new pkijs.AlgorithmIdentifier({ algorithmId: ED25519_OID });
163
- basicResponse.signatureAlgorithm = algId;
164
- // Encode the TBS response data
165
- const tbsDer = basicResponse.tbsResponseData.toSchema(true).toBER();
166
- basicResponse.tbsResponseData.tbsView = new Uint8Array(tbsDer);
167
- const sig = await webcrypto.subtle.sign('Ed25519', privateKey, tbsDer);
168
- basicResponse.signature = new asn1js.BitString({ valueHex: sig });
169
- }
170
- //# sourceMappingURL=certGenUtils.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"certGenUtils.js","sourceRoot":"","sources":["../../src/security/certGenUtils.ts"],"names":[],"mappings":"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"}
@@ -1,34 +0,0 @@
1
- /**
2
- * Generate test certificates for CRL integration testing
3
- *
4
- * Uses pure Node.js (webcrypto + pkijs) — no openssl CLI dependency.
5
- */
6
- export interface CrlCertificates {
7
- /** Path to CA certificate */
8
- ca: string;
9
- /** Valid client certificate paths */
10
- valid: {
11
- /** Path to valid client certificate chain (cert + CA) */
12
- cert: string;
13
- /** Path to valid client private key */
14
- key: string;
15
- };
16
- /** Revoked client certificate paths */
17
- revoked: {
18
- /** Path to revoked client certificate chain (cert + CA) */
19
- cert: string;
20
- /** Path to revoked client private key */
21
- key: string;
22
- };
23
- /** Path to Certificate Revocation List */
24
- crl: string;
25
- }
26
- /**
27
- * Generate CRL test certificates using pure Node.js (no openssl CLI).
28
- *
29
- * Serial numbers:
30
- * 1 = CA
31
- * 2 = valid client
32
- * 3 = revoked client
33
- */
34
- export declare function generateCrlCertificates(outputDir: string, crlHost: string, crlPort: number): Promise<CrlCertificates>;
@@ -1,81 +0,0 @@
1
- /**
2
- * Generate test certificates for CRL integration testing
3
- *
4
- * Uses pure Node.js (webcrypto + pkijs) — no openssl CLI dependency.
5
- */
6
- import fs from 'node:fs';
7
- import path from 'node:path';
8
- import { generateEd25519KeyPair, createCertificate, createCRL, makeCRLDistributionPointsExt, certToPem, crlToPem, CLIENT_AUTH_OID, makeExtKeyUsageExt, } from "../certGenUtils.js";
9
- /**
10
- * Generate CRL test certificates using pure Node.js (no openssl CLI).
11
- *
12
- * Serial numbers:
13
- * 1 = CA
14
- * 2 = valid client
15
- * 3 = revoked client
16
- */
17
- export async function generateCrlCertificates(outputDir, crlHost, crlPort) {
18
- const crlUrl = `http://${crlHost}:${crlPort}/test.crl`;
19
- // --- CA ---
20
- const caKey = await generateEd25519KeyPair();
21
- const caKeyPath = path.join(outputDir, 'harper-ca.key');
22
- fs.writeFileSync(caKeyPath, caKey.privateKeyPem);
23
- const caCert = await createCertificate({
24
- serialNumber: 1,
25
- subject: { CN: 'Harper Test CA', O: 'Harper CRL Test' },
26
- issuer: { CN: 'Harper Test CA', O: 'Harper CRL Test' },
27
- validDays: 365,
28
- issuerKey: caKey.privateKey,
29
- subjectPublicKey: caKey.publicKey,
30
- isCA: true,
31
- });
32
- const caCertPath = path.join(outputDir, 'harper-ca.crt');
33
- fs.writeFileSync(caCertPath, certToPem(caCert));
34
- // --- Valid client cert ---
35
- const validKey = await generateEd25519KeyPair();
36
- const validKeyPath = path.join(outputDir, 'client-valid.key');
37
- fs.writeFileSync(validKeyPath, validKey.privateKeyPem);
38
- const validCert = await createCertificate({
39
- serialNumber: 2,
40
- subject: { CN: 'Valid CRL Client', O: 'Harper CRL Test' },
41
- issuer: { CN: 'Harper Test CA', O: 'Harper CRL Test' },
42
- validDays: 30,
43
- issuerKey: caKey.privateKey,
44
- subjectPublicKey: validKey.publicKey,
45
- extensions: [makeCRLDistributionPointsExt(crlUrl), makeExtKeyUsageExt([CLIENT_AUTH_OID])],
46
- });
47
- const validCertPath = path.join(outputDir, 'client-valid.crt');
48
- fs.writeFileSync(validCertPath, certToPem(validCert));
49
- // Build chain: client cert + CA cert
50
- const validChainPath = path.join(outputDir, 'client-valid-chain.crt');
51
- fs.writeFileSync(validChainPath, certToPem(validCert) + certToPem(caCert));
52
- // --- Revoked client cert ---
53
- const revokedKey = await generateEd25519KeyPair();
54
- const revokedKeyPath = path.join(outputDir, 'client-revoked.key');
55
- fs.writeFileSync(revokedKeyPath, revokedKey.privateKeyPem);
56
- const revokedCert = await createCertificate({
57
- serialNumber: 3,
58
- subject: { CN: 'Revoked CRL Client', O: 'Harper CRL Test' },
59
- issuer: { CN: 'Harper Test CA', O: 'Harper CRL Test' },
60
- validDays: 30,
61
- issuerKey: caKey.privateKey,
62
- subjectPublicKey: revokedKey.publicKey,
63
- extensions: [makeCRLDistributionPointsExt(crlUrl), makeExtKeyUsageExt([CLIENT_AUTH_OID])],
64
- });
65
- const revokedCertPath = path.join(outputDir, 'client-revoked.crt');
66
- fs.writeFileSync(revokedCertPath, certToPem(revokedCert));
67
- // Build chain: client cert + CA cert
68
- const revokedChainPath = path.join(outputDir, 'client-revoked-chain.crt');
69
- fs.writeFileSync(revokedChainPath, certToPem(revokedCert) + certToPem(caCert));
70
- // --- CRL (serial 3 = revoked) ---
71
- const crl = await createCRL(caCert, caKey.privateKey, [3]);
72
- const crlPath = path.join(outputDir, 'test.crl');
73
- fs.writeFileSync(crlPath, crlToPem(crl));
74
- return {
75
- ca: caCertPath,
76
- valid: { cert: validChainPath, key: validKeyPath },
77
- revoked: { cert: revokedChainPath, key: revokedKeyPath },
78
- crl: crlPath,
79
- };
80
- }
81
- //# sourceMappingURL=generate-test-certs.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"generate-test-certs.js","sourceRoot":"","sources":["../../../src/security/crl/generate-test-certs.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EACN,sBAAsB,EACtB,iBAAiB,EACjB,SAAS,EACT,4BAA4B,EAC5B,SAAS,EACT,QAAQ,EACR,eAAe,EACf,kBAAkB,GAClB,MAAM,oBAAoB,CAAC;AAuB5B;;;;;;;GAOG;AACH,MAAM,CAAC,KAAK,UAAU,uBAAuB,CAC5C,SAAiB,EACjB,OAAe,EACf,OAAe;IAEf,MAAM,MAAM,GAAG,UAAU,OAAO,IAAI,OAAO,WAAW,CAAC;IAEvD,aAAa;IACb,MAAM,KAAK,GAAG,MAAM,sBAAsB,EAAE,CAAC;IAC7C,MAAM,SAAS,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,eAAe,CAAC,CAAC;IACxD,EAAE,CAAC,aAAa,CAAC,SAAS,EAAE,KAAK,CAAC,aAAa,CAAC,CAAC;IAEjD,MAAM,MAAM,GAAG,MAAM,iBAAiB,CAAC;QACtC,YAAY,EAAE,CAAC;QACf,OAAO,EAAE,EAAE,EAAE,EAAE,gBAAgB,EAAE,CAAC,EAAE,iBAAiB,EAAE;QACvD,MAAM,EAAE,EAAE,EAAE,EAAE,gBAAgB,EAAE,CAAC,EAAE,iBAAiB,EAAE;QACtD,SAAS,EAAE,GAAG;QACd,SAAS,EAAE,KAAK,CAAC,UAAU;QAC3B,gBAAgB,EAAE,KAAK,CAAC,SAAS;QACjC,IAAI,EAAE,IAAI;KACV,CAAC,CAAC;IACH,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,eAAe,CAAC,CAAC;IACzD,EAAE,CAAC,aAAa,CAAC,UAAU,EAAE,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;IAEhD,4BAA4B;IAC5B,MAAM,QAAQ,GAAG,MAAM,sBAAsB,EAAE,CAAC;IAChD,MAAM,YAAY,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,kBAAkB,CAAC,CAAC;IAC9D,EAAE,CAAC,aAAa,CAAC,YAAY,EAAE,QAAQ,CAAC,aAAa,CAAC,CAAC;IAEvD,MAAM,SAAS,GAAG,MAAM,iBAAiB,CAAC;QACzC,YAAY,EAAE,CAAC;QACf,OAAO,EAAE,EAAE,EAAE,EAAE,kBAAkB,EAAE,CAAC,EAAE,iBAAiB,EAAE;QACzD,MAAM,EAAE,EAAE,EAAE,EAAE,gBAAgB,EAAE,CAAC,EAAE,iBAAiB,EAAE;QACtD,SAAS,EAAE,EAAE;QACb,SAAS,EAAE,KAAK,CAAC,UAAU;QAC3B,gBAAgB,EAAE,QAAQ,CAAC,SAAS;QACpC,UAAU,EAAE,CAAC,4BAA4B,CAAC,MAAM,CAAC,EAAE,kBAAkB,CAAC,CAAC,eAAe,CAAC,CAAC,CAAC;KACzF,CAAC,CAAC;IACH,MAAM,aAAa,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,kBAAkB,CAAC,CAAC;IAC/D,EAAE,CAAC,aAAa,CAAC,aAAa,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC,CAAC;IAEtD,qCAAqC;IACrC,MAAM,cAAc,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,wBAAwB,CAAC,CAAC;IACtE,EAAE,CAAC,aAAa,CAAC,cAAc,EAAE,SAAS,CAAC,SAAS,CAAC,GAAG,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;IAE3E,8BAA8B;IAC9B,MAAM,UAAU,GAAG,MAAM,sBAAsB,EAAE,CAAC;IAClD,MAAM,cAAc,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,oBAAoB,CAAC,CAAC;IAClE,EAAE,CAAC,aAAa,CAAC,cAAc,EAAE,UAAU,CAAC,aAAa,CAAC,CAAC;IAE3D,MAAM,WAAW,GAAG,MAAM,iBAAiB,CAAC;QAC3C,YAAY,EAAE,CAAC;QACf,OAAO,EAAE,EAAE,EAAE,EAAE,oBAAoB,EAAE,CAAC,EAAE,iBAAiB,EAAE;QAC3D,MAAM,EAAE,EAAE,EAAE,EAAE,gBAAgB,EAAE,CAAC,EAAE,iBAAiB,EAAE;QACtD,SAAS,EAAE,EAAE;QACb,SAAS,EAAE,KAAK,CAAC,UAAU;QAC3B,gBAAgB,EAAE,UAAU,CAAC,SAAS;QACtC,UAAU,EAAE,CAAC,4BAA4B,CAAC,MAAM,CAAC,EAAE,kBAAkB,CAAC,CAAC,eAAe,CAAC,CAAC,CAAC;KACzF,CAAC,CAAC;IACH,MAAM,eAAe,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,oBAAoB,CAAC,CAAC;IACnE,EAAE,CAAC,aAAa,CAAC,eAAe,EAAE,SAAS,CAAC,WAAW,CAAC,CAAC,CAAC;IAE1D,qCAAqC;IACrC,MAAM,gBAAgB,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,0BAA0B,CAAC,CAAC;IAC1E,EAAE,CAAC,aAAa,CAAC,gBAAgB,EAAE,SAAS,CAAC,WAAW,CAAC,GAAG,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;IAE/E,mCAAmC;IACnC,MAAM,GAAG,GAAG,MAAM,SAAS,CAAC,MAAM,EAAE,KAAK,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3D,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,UAAU,CAAC,CAAC;IACjD,EAAE,CAAC,aAAa,CAAC,OAAO,EAAE,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC;IAEzC,OAAO;QACN,EAAE,EAAE,UAAU;QACd,KAAK,EAAE,EAAE,IAAI,EAAE,cAAc,EAAE,GAAG,EAAE,YAAY,EAAE;QAClD,OAAO,EAAE,EAAE,IAAI,EAAE,gBAAgB,EAAE,GAAG,EAAE,cAAc,EAAE;QACxD,GAAG,EAAE,OAAO;KACZ,CAAC;AACH,CAAC"}