@pymthouse/builder-sdk 0.4.4 → 0.4.6
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.
- package/README.md +120 -5
- package/dist/{client-C0HgAugK.d.cts → client-CEBVgCD7.d.cts} +28 -4
- package/dist/{client-zCskUJag.d.ts → client-D-p6v8ju.d.ts} +28 -4
- package/dist/device.d.cts +1 -1
- package/dist/device.d.ts +1 -1
- package/dist/env.cjs +64 -9
- package/dist/env.cjs.map +1 -1
- package/dist/env.d.cts +2 -2
- package/dist/env.d.ts +2 -2
- package/dist/env.js +64 -9
- package/dist/env.js.map +1 -1
- package/dist/{index-CAIAYJv7.d.cts → index-M0tsyotJ.d.cts} +1 -1
- package/dist/{index-BL1wpOki.d.ts → index-rC8smShg.d.ts} +1 -1
- package/dist/index.cjs +64 -9
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +4 -4
- package/dist/index.d.ts +4 -4
- package/dist/index.js +64 -9
- package/dist/index.js.map +1 -1
- package/dist/{proxy-KrA1vEmh.d.ts → proxy-CZLY0IfL.d.cts} +5 -2
- package/dist/{proxy-0wa8QZIU.d.cts → proxy-D36SpZ6k.d.ts} +5 -2
- package/dist/signer/gateway.cjs +542 -0
- package/dist/signer/gateway.cjs.map +1 -0
- package/dist/signer/gateway.d.cts +81 -0
- package/dist/signer/gateway.d.ts +81 -0
- package/dist/signer/gateway.js +538 -0
- package/dist/signer/gateway.js.map +1 -0
- package/dist/signer/server.cjs +225 -0
- package/dist/signer/server.cjs.map +1 -1
- package/dist/signer/server.d.cts +35 -4
- package/dist/signer/server.d.ts +35 -4
- package/dist/signer/server.js +219 -1
- package/dist/signer/server.js.map +1 -1
- package/dist/signer/webhook/adapters/oidc.d.cts +2 -2
- package/dist/signer/webhook/adapters/oidc.d.ts +2 -2
- package/dist/signer/webhook.d.cts +3 -3
- package/dist/signer/webhook.d.ts +3 -3
- package/dist/tokens.d.cts +1 -1
- package/dist/tokens.d.ts +1 -1
- package/dist/{types-BORaHW_x.d.cts → types-CcP67AZm.d.cts} +2 -0
- package/dist/{types-BORaHW_x.d.ts → types-CcP67AZm.d.ts} +2 -0
- package/dist/verify.d.cts +1 -1
- package/dist/verify.d.ts +1 -1
- package/package.json +6 -1
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { F as FetchLike } from './types-
|
|
1
|
+
import { F as FetchLike } from './types-CcP67AZm.cjs';
|
|
2
2
|
import { U as UsageIdentity, P as PaymentWebhookRequest, V as VerifiedEndUserAuth, E as EndUserAuthVerifier } from './verifier-D8z3spC0.cjs';
|
|
3
3
|
import { TrustedHeadersEndUserAuthConfig } from './signer/webhook/adapters/trusted-headers.cjs';
|
|
4
4
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { F as FetchLike } from './types-
|
|
1
|
+
import { F as FetchLike } from './types-CcP67AZm.js';
|
|
2
2
|
import { U as UsageIdentity, P as PaymentWebhookRequest, V as VerifiedEndUserAuth, E as EndUserAuthVerifier } from './verifier-D8z3spC0.js';
|
|
3
3
|
import { TrustedHeadersEndUserAuthConfig } from './signer/webhook/adapters/trusted-headers.js';
|
|
4
4
|
|
package/dist/index.cjs
CHANGED
|
@@ -338,6 +338,32 @@ var init_mint_token = __esm({
|
|
|
338
338
|
}
|
|
339
339
|
});
|
|
340
340
|
|
|
341
|
+
// src/signer/direct-signer.ts
|
|
342
|
+
function assertDirectSignerBaseUrl(signerBaseUrl) {
|
|
343
|
+
let parsed;
|
|
344
|
+
try {
|
|
345
|
+
parsed = new URL(signerBaseUrl.trim());
|
|
346
|
+
} catch {
|
|
347
|
+
throw new exports.PmtHouseError("signer URL must be an absolute http(s) URL", {
|
|
348
|
+
status: 400,
|
|
349
|
+
code: "invalid_signer_url"
|
|
350
|
+
});
|
|
351
|
+
}
|
|
352
|
+
const pathname = stripTrailingSlashes(parsed.pathname);
|
|
353
|
+
if (pathname === "/api/signer" || pathname.startsWith("/api/signer/")) {
|
|
354
|
+
throw new exports.PmtHouseError(
|
|
355
|
+
"signer URL must be the remote signer DMZ base, not a dashboard /api/signer/* proxy path. Exchange at the platform facade, then call signer endpoints directly using signerUrl from the exchange response.",
|
|
356
|
+
{ status: 400, code: "invalid_signer_url" }
|
|
357
|
+
);
|
|
358
|
+
}
|
|
359
|
+
}
|
|
360
|
+
var init_direct_signer = __esm({
|
|
361
|
+
"src/signer/direct-signer.ts"() {
|
|
362
|
+
init_string_utils();
|
|
363
|
+
init_errors();
|
|
364
|
+
}
|
|
365
|
+
});
|
|
366
|
+
|
|
341
367
|
// src/signer/device-exchange.ts
|
|
342
368
|
function extractSignerAccessTokenFromExchangeBody(body) {
|
|
343
369
|
const tokenObj = body.token;
|
|
@@ -570,6 +596,9 @@ async function exchangeApiKeyForSigner(options) {
|
|
|
570
596
|
const accessToken = extractSignerAccessTokenFromExchangeBody(parsed);
|
|
571
597
|
const signerUrlRaw = parsed.signerUrl ?? parsed.signer_url;
|
|
572
598
|
const signerUrl = typeof signerUrlRaw === "string" && signerUrlRaw.trim() ? signerUrlRaw.trim() : void 0;
|
|
599
|
+
if (signerUrl) {
|
|
600
|
+
assertDirectSignerBaseUrl(signerUrl);
|
|
601
|
+
}
|
|
573
602
|
return normalizeDeviceExchangeResponse(
|
|
574
603
|
{
|
|
575
604
|
access_token: accessToken,
|
|
@@ -632,6 +661,7 @@ var init_api_key_exchange = __esm({
|
|
|
632
661
|
init_fetch_json();
|
|
633
662
|
init_handler_errors();
|
|
634
663
|
init_device_exchange();
|
|
664
|
+
init_direct_signer();
|
|
635
665
|
EXCHANGE_RESPONSE_ERROR2 = "invalid_exchange_response";
|
|
636
666
|
}
|
|
637
667
|
});
|
|
@@ -1340,8 +1370,14 @@ var PmtHouseClient = class {
|
|
|
1340
1370
|
});
|
|
1341
1371
|
}
|
|
1342
1372
|
/**
|
|
1343
|
-
* Exchange a dashboard API key for a signer
|
|
1344
|
-
*
|
|
1373
|
+
* Exchange a dashboard API key for a short-lived signer JWT via a trusted facade.
|
|
1374
|
+
*
|
|
1375
|
+
* `facadeUrl` is used only for `POST {facadeUrl}/api/pymthouse/keys/exchange`.
|
|
1376
|
+
* After exchange, call signer RPCs directly at `signerUrl` from the response
|
|
1377
|
+
* (e.g. `{signerUrl}/sign-orchestrator-info`), not via dashboard `/api/signer/*`.
|
|
1378
|
+
*
|
|
1379
|
+
* When M2M credentials are available on this client, omit `facadeUrl` to exchange
|
|
1380
|
+
* directly against the PymtHouse issuer.
|
|
1345
1381
|
*/
|
|
1346
1382
|
async exchangeApiKeyForSignerSession(input) {
|
|
1347
1383
|
if (input.facadeUrl?.trim()) {
|
|
@@ -1358,7 +1394,8 @@ var PmtHouseClient = class {
|
|
|
1358
1394
|
token_type: exchanged.token_type,
|
|
1359
1395
|
expires_in: exchanged.expires_in,
|
|
1360
1396
|
scope: exchanged.scope,
|
|
1361
|
-
issued_token_type: "urn:ietf:params:oauth:token-type:access_token"
|
|
1397
|
+
issued_token_type: "urn:ietf:params:oauth:token-type:access_token",
|
|
1398
|
+
signerUrl: exchanged.signerUrl
|
|
1362
1399
|
};
|
|
1363
1400
|
}
|
|
1364
1401
|
const userToken = await this.exchangeApiKeyForUserAccessToken({
|
|
@@ -1432,8 +1469,13 @@ var PmtHouseClient = class {
|
|
|
1432
1469
|
params.set("subject_token", input.userJwt);
|
|
1433
1470
|
params.set("subject_token_type", SUBJECT_ACCESS_TOKEN_TYPE2);
|
|
1434
1471
|
params.set("requested_token_type", REQUESTED_ACCESS_TOKEN_TYPE);
|
|
1435
|
-
|
|
1436
|
-
|
|
1472
|
+
if (typeof input.scope === "string" && input.scope.trim() !== "") {
|
|
1473
|
+
params.set("scope", input.scope.trim());
|
|
1474
|
+
}
|
|
1475
|
+
if (!input.omitResource) {
|
|
1476
|
+
const resourceCandidate = typeof input.resource === "string" && input.resource.trim() !== "" ? input.resource.trim() : this.issuerUrl;
|
|
1477
|
+
params.set("resource", stripTrailingSlashes(resourceCandidate));
|
|
1478
|
+
}
|
|
1437
1479
|
try {
|
|
1438
1480
|
const response = await oauth4webapi.genericTokenEndpointRequest(
|
|
1439
1481
|
as,
|
|
@@ -1719,18 +1761,31 @@ var PmtHouseClient = class {
|
|
|
1719
1761
|
};
|
|
1720
1762
|
}
|
|
1721
1763
|
/**
|
|
1722
|
-
* Upsert an external user, mint a short-lived JWT, and exchange for
|
|
1764
|
+
* Upsert an external user, mint a short-lived JWT, and exchange it for a
|
|
1765
|
+
* long-lived opaque (`pmth_*`) signer session.
|
|
1766
|
+
*
|
|
1767
|
+
* Performs the *documented* remote-signer-session exchange (see
|
|
1768
|
+
* `builder-api.md` → "Remote signer session exchange"): the RFC 8693 token
|
|
1769
|
+
* exchange is sent with `scope=sign:job` and **no `resource` indicator**,
|
|
1770
|
+
* which selects the PymtHouse gateway/opaque path. A prior implementation set
|
|
1771
|
+
* `resource = issuer`, which routed to the signer-JWT path and returned a JWT
|
|
1772
|
+
* that {@link parseSignerSessionExchange} then rejected as non-opaque.
|
|
1723
1773
|
*/
|
|
1724
1774
|
async mintSignerSessionForExternalUser(input) {
|
|
1775
|
+
const scope = input.scope ?? SIGN_JOB_SCOPE;
|
|
1725
1776
|
await this.upsertAppUser({
|
|
1726
1777
|
externalUserId: input.externalUserId,
|
|
1727
1778
|
email: input.email,
|
|
1728
1779
|
status: "active"
|
|
1729
1780
|
});
|
|
1730
|
-
const
|
|
1781
|
+
const userToken = await this.mintUserAccessToken({
|
|
1731
1782
|
externalUserId: input.externalUserId,
|
|
1732
|
-
scope
|
|
1733
|
-
|
|
1783
|
+
scope
|
|
1784
|
+
});
|
|
1785
|
+
const exchange = await this.exchangeForSignerSession({
|
|
1786
|
+
userJwt: userToken.access_token,
|
|
1787
|
+
omitResource: true,
|
|
1788
|
+
scope
|
|
1734
1789
|
});
|
|
1735
1790
|
return parseSignerSessionExchange(exchange);
|
|
1736
1791
|
}
|