@arslankhan/doc-forge 0.0.0-stage → 0.1.0
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/CHANGELOG.md +11 -0
- package/LICENSE +13 -0
- package/LICENSING.md +80 -0
- package/README.md +547 -2
- package/RELEASE.md +50 -0
- package/dist/binding-path.d.ts +15 -0
- package/dist/binding-path.d.ts.map +1 -0
- package/dist/binding-path.js +37 -0
- package/dist/binding-path.js.map +1 -0
- package/dist/binding.d.ts +91 -0
- package/dist/binding.d.ts.map +1 -0
- package/dist/binding.js +229 -0
- package/dist/binding.js.map +1 -0
- package/dist/designer/Canvas.d.ts +51 -0
- package/dist/designer/Canvas.d.ts.map +1 -0
- package/dist/designer/Canvas.js +188 -0
- package/dist/designer/Canvas.js.map +1 -0
- package/dist/designer/DocumentDesigner.d.ts +14 -0
- package/dist/designer/DocumentDesigner.d.ts.map +1 -0
- package/dist/designer/DocumentDesigner.js +351 -0
- package/dist/designer/DocumentDesigner.js.map +1 -0
- package/dist/designer/HtmlPreview.d.ts +9 -0
- package/dist/designer/HtmlPreview.d.ts.map +1 -0
- package/dist/designer/HtmlPreview.js +20 -0
- package/dist/designer/HtmlPreview.js.map +1 -0
- package/dist/designer/ImageBindingFields.d.ts +11 -0
- package/dist/designer/ImageBindingFields.d.ts.map +1 -0
- package/dist/designer/ImageBindingFields.js +106 -0
- package/dist/designer/ImageBindingFields.js.map +1 -0
- package/dist/designer/InvoiceFields.d.ts +13 -0
- package/dist/designer/InvoiceFields.d.ts.map +1 -0
- package/dist/designer/InvoiceFields.js +85 -0
- package/dist/designer/InvoiceFields.js.map +1 -0
- package/dist/designer/PreviewDataDialog.d.ts +13 -0
- package/dist/designer/PreviewDataDialog.d.ts.map +1 -0
- package/dist/designer/PreviewDataDialog.js +16 -0
- package/dist/designer/PreviewDataDialog.js.map +1 -0
- package/dist/designer/PropertiesPanel.d.ts +15 -0
- package/dist/designer/PropertiesPanel.d.ts.map +1 -0
- package/dist/designer/PropertiesPanel.js +63 -0
- package/dist/designer/PropertiesPanel.js.map +1 -0
- package/dist/designer/ReportFields.d.ts +14 -0
- package/dist/designer/ReportFields.d.ts.map +1 -0
- package/dist/designer/ReportFields.js +257 -0
- package/dist/designer/ReportFields.js.map +1 -0
- package/dist/designer/StyleFields.d.ts +16 -0
- package/dist/designer/StyleFields.d.ts.map +1 -0
- package/dist/designer/StyleFields.js +138 -0
- package/dist/designer/StyleFields.js.map +1 -0
- package/dist/designer/TextBindingFields.d.ts +11 -0
- package/dist/designer/TextBindingFields.d.ts.map +1 -0
- package/dist/designer/TextBindingFields.js +105 -0
- package/dist/designer/TextBindingFields.js.map +1 -0
- package/dist/designer/Toolbar.d.ts +52 -0
- package/dist/designer/Toolbar.d.ts.map +1 -0
- package/dist/designer/Toolbar.js +62 -0
- package/dist/designer/Toolbar.js.map +1 -0
- package/dist/designer/Toolbox.d.ts +8 -0
- package/dist/designer/Toolbox.d.ts.map +1 -0
- package/dist/designer/Toolbox.js +43 -0
- package/dist/designer/Toolbox.js.map +1 -0
- package/dist/designer/border-preview.d.ts +15 -0
- package/dist/designer/border-preview.d.ts.map +1 -0
- package/dist/designer/border-preview.js +34 -0
- package/dist/designer/border-preview.js.map +1 -0
- package/dist/designer/history.d.ts +13 -0
- package/dist/designer/history.d.ts.map +1 -0
- package/dist/designer/history.js +51 -0
- package/dist/designer/history.js.map +1 -0
- package/dist/designer/index.d.ts +5 -0
- package/dist/designer/index.d.ts.map +1 -0
- package/dist/designer/index.js +3 -0
- package/dist/designer/index.js.map +1 -0
- package/dist/designer/page-geometry.d.ts +35 -0
- package/dist/designer/page-geometry.d.ts.map +1 -0
- package/dist/designer/page-geometry.js +123 -0
- package/dist/designer/page-geometry.js.map +1 -0
- package/dist/designer/styles.d.ts +3 -0
- package/dist/designer/styles.d.ts.map +1 -0
- package/dist/designer/styles.js +594 -0
- package/dist/designer/styles.js.map +1 -0
- package/dist/designer/template-edits.d.ts +26 -0
- package/dist/designer/template-edits.d.ts.map +1 -0
- package/dist/designer/template-edits.js +323 -0
- package/dist/designer/template-edits.js.map +1 -0
- package/dist/designer/theme.d.ts +31 -0
- package/dist/designer/theme.d.ts.map +1 -0
- package/dist/designer/theme.js +92 -0
- package/dist/designer/theme.js.map +1 -0
- package/dist/examples/bound-invoice.d.ts +143 -0
- package/dist/examples/bound-invoice.d.ts.map +1 -0
- package/dist/examples/bound-invoice.js +99 -0
- package/dist/examples/bound-invoice.js.map +1 -0
- package/dist/examples/full-invoice-data.d.ts +81 -0
- package/dist/examples/full-invoice-data.d.ts.map +1 -0
- package/dist/examples/full-invoice-data.js +86 -0
- package/dist/examples/full-invoice-data.js.map +1 -0
- package/dist/examples/full-invoice.d.ts +402 -0
- package/dist/examples/full-invoice.d.ts.map +1 -0
- package/dist/examples/full-invoice.js +199 -0
- package/dist/examples/full-invoice.js.map +1 -0
- package/dist/examples/invoice-data.d.ts +51 -0
- package/dist/examples/invoice-data.d.ts.map +1 -0
- package/dist/examples/invoice-data.js +51 -0
- package/dist/examples/invoice-data.js.map +1 -0
- package/dist/examples/invoice.d.ts +90 -0
- package/dist/examples/invoice.d.ts.map +1 -0
- package/dist/examples/invoice.js +62 -0
- package/dist/examples/invoice.js.map +1 -0
- package/dist/examples/jobs-report-data.d.ts +84 -0
- package/dist/examples/jobs-report-data.d.ts.map +1 -0
- package/dist/examples/jobs-report-data.js +79 -0
- package/dist/examples/jobs-report-data.js.map +1 -0
- package/dist/examples/jobs-report.d.ts +182 -0
- package/dist/examples/jobs-report.d.ts.map +1 -0
- package/dist/examples/jobs-report.js +96 -0
- package/dist/examples/jobs-report.js.map +1 -0
- package/dist/index.d.ts +31 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +21 -0
- package/dist/index.js.map +1 -0
- package/dist/invoice/calculate.d.ts +59 -0
- package/dist/invoice/calculate.d.ts.map +1 -0
- package/dist/invoice/calculate.js +270 -0
- package/dist/invoice/calculate.js.map +1 -0
- package/dist/invoice/context.d.ts +15 -0
- package/dist/invoice/context.d.ts.map +1 -0
- package/dist/invoice/context.js +79 -0
- package/dist/invoice/context.js.map +1 -0
- package/dist/invoice/format.d.ts +10 -0
- package/dist/invoice/format.d.ts.map +1 -0
- package/dist/invoice/format.js +95 -0
- package/dist/invoice/format.js.map +1 -0
- package/dist/license/capabilities.d.ts +17 -0
- package/dist/license/capabilities.d.ts.map +1 -0
- package/dist/license/capabilities.js +46 -0
- package/dist/license/capabilities.js.map +1 -0
- package/dist/license/client.d.ts +109 -0
- package/dist/license/client.d.ts.map +1 -0
- package/dist/license/client.js +346 -0
- package/dist/license/client.js.map +1 -0
- package/dist/license/codec.d.ts +5 -0
- package/dist/license/codec.d.ts.map +1 -0
- package/dist/license/codec.js +26 -0
- package/dist/license/codec.js.map +1 -0
- package/dist/license/errors.d.ts +11 -0
- package/dist/license/errors.d.ts.map +1 -0
- package/dist/license/errors.js +19 -0
- package/dist/license/errors.js.map +1 -0
- package/dist/license/features.d.ts +20 -0
- package/dist/license/features.d.ts.map +1 -0
- package/dist/license/features.js +28 -0
- package/dist/license/features.js.map +1 -0
- package/dist/license/index.d.ts +16 -0
- package/dist/license/index.d.ts.map +1 -0
- package/dist/license/index.js +9 -0
- package/dist/license/index.js.map +1 -0
- package/dist/license/provider.d.ts +59 -0
- package/dist/license/provider.d.ts.map +1 -0
- package/dist/license/provider.js +150 -0
- package/dist/license/provider.js.map +1 -0
- package/dist/license/redact.d.ts +4 -0
- package/dist/license/redact.d.ts.map +1 -0
- package/dist/license/redact.js +15 -0
- package/dist/license/redact.js.map +1 -0
- package/dist/license/store.d.ts +26 -0
- package/dist/license/store.d.ts.map +1 -0
- package/dist/license/store.js +90 -0
- package/dist/license/store.js.map +1 -0
- package/dist/license/token.d.ts +45 -0
- package/dist/license/token.d.ts.map +1 -0
- package/dist/license/token.js +195 -0
- package/dist/license/token.js.map +1 -0
- package/dist/pdf/browser-blocked.d.ts +12 -0
- package/dist/pdf/browser-blocked.d.ts.map +1 -0
- package/dist/pdf/browser-blocked.js +25 -0
- package/dist/pdf/browser-blocked.js.map +1 -0
- package/dist/pdf/browser.d.ts +12 -0
- package/dist/pdf/browser.d.ts.map +1 -0
- package/dist/pdf/browser.js +69 -0
- package/dist/pdf/browser.js.map +1 -0
- package/dist/pdf/errors.d.ts +6 -0
- package/dist/pdf/errors.d.ts.map +1 -0
- package/dist/pdf/errors.js +11 -0
- package/dist/pdf/errors.js.map +1 -0
- package/dist/pdf/index.d.ts +10 -0
- package/dist/pdf/index.d.ts.map +1 -0
- package/dist/pdf/index.js +9 -0
- package/dist/pdf/index.js.map +1 -0
- package/dist/pdf/options.d.ts +143 -0
- package/dist/pdf/options.d.ts.map +1 -0
- package/dist/pdf/options.js +322 -0
- package/dist/pdf/options.js.map +1 -0
- package/dist/pdf/render-pdf.d.ts +13 -0
- package/dist/pdf/render-pdf.d.ts.map +1 -0
- package/dist/pdf/render-pdf.js +195 -0
- package/dist/pdf/render-pdf.js.map +1 -0
- package/dist/render/appearance.d.ts +25 -0
- package/dist/render/appearance.d.ts.map +1 -0
- package/dist/render/appearance.js +149 -0
- package/dist/render/appearance.js.map +1 -0
- package/dist/render/css.d.ts +17 -0
- package/dist/render/css.d.ts.map +1 -0
- package/dist/render/css.js +170 -0
- package/dist/render/css.js.map +1 -0
- package/dist/render/errors.d.ts +6 -0
- package/dist/render/errors.d.ts.map +1 -0
- package/dist/render/errors.js +11 -0
- package/dist/render/errors.js.map +1 -0
- package/dist/render/escape.d.ts +7 -0
- package/dist/render/escape.d.ts.map +1 -0
- package/dist/render/escape.js +27 -0
- package/dist/render/escape.js.map +1 -0
- package/dist/render/image-policy.d.ts +21 -0
- package/dist/render/image-policy.d.ts.map +1 -0
- package/dist/render/image-policy.js +62 -0
- package/dist/render/image-policy.js.map +1 -0
- package/dist/render/render-html.d.ts +28 -0
- package/dist/render/render-html.d.ts.map +1 -0
- package/dist/render/render-html.js +364 -0
- package/dist/render/render-html.js.map +1 -0
- package/dist/render/render-report.d.ts +23 -0
- package/dist/render/render-report.d.ts.map +1 -0
- package/dist/render/render-report.js +313 -0
- package/dist/render/render-report.js.map +1 -0
- package/dist/report/process.d.ts +48 -0
- package/dist/report/process.d.ts.map +1 -0
- package/dist/report/process.js +347 -0
- package/dist/report/process.js.map +1 -0
- package/dist/schema.d.ts +30 -0
- package/dist/schema.d.ts.map +1 -0
- package/dist/schema.js +8 -0
- package/dist/schema.js.map +1 -0
- package/dist/serialize.d.ts +13 -0
- package/dist/serialize.d.ts.map +1 -0
- package/dist/serialize.js +42 -0
- package/dist/serialize.js.map +1 -0
- package/dist/types.d.ts +335 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +40 -0
- package/dist/types.js.map +1 -0
- package/dist/validate.d.ts +15 -0
- package/dist/validate.d.ts.map +1 -0
- package/dist/validate.js +977 -0
- package/dist/validate.js.map +1 -0
- package/package.json +97 -4
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export { inspectDocumentCapabilities } from "./capabilities.js";
|
|
2
|
+
export { activateLicense, configureLicense, createLicenseClient, deactivateLicense, getEntitlements, getLicenseStatus, hasFeature, LicenseClient, LICENSE_STATUSES, resetLicenseConfiguration, } from "./client.js";
|
|
3
|
+
export { LicenseError, LicenseNetworkError } from "./errors.js";
|
|
4
|
+
export { entitlementsForPlan, isLicenseFeature, LICENSE_FEATURES } from "./features.js";
|
|
5
|
+
export { createHttpLicenseProvider, createMockLicenseProvider } from "./provider.js";
|
|
6
|
+
export { redactSecret } from "./redact.js";
|
|
7
|
+
export { createBrowserLicenseStore, createMemoryLicenseStore, LICENSE_STORAGE_KEY } from "./store.js";
|
|
8
|
+
export { verifyLicenseToken } from "./token.js";
|
|
9
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/license/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,2BAA2B,EAAE,MAAM,mBAAmB,CAAC;AAEhE,OAAO,EACL,eAAe,EACf,gBAAgB,EAChB,mBAAmB,EACnB,iBAAiB,EACjB,eAAe,EACf,gBAAgB,EAChB,UAAU,EACV,aAAa,EACb,gBAAgB,EAChB,yBAAyB,GAC1B,MAAM,aAAa,CAAC;AASrB,OAAO,EAAE,YAAY,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AAEhE,OAAO,EAAE,mBAAmB,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAExF,OAAO,EAAE,yBAAyB,EAAE,yBAAyB,EAAE,MAAM,eAAe,CAAC;AASrF,OAAO,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAC3C,OAAO,EAAE,yBAAyB,EAAE,wBAAwB,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAEtG,OAAO,EAAE,kBAAkB,EAAE,MAAM,YAAY,CAAC"}
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
export declare const LICENSE_SERVICE_STATUSES: readonly ["unconfigured", "valid", "expired", "invalid", "revoked", "network_unavailable"];
|
|
2
|
+
export type LicenseServiceStatus = (typeof LICENSE_SERVICE_STATUSES)[number];
|
|
3
|
+
/**
|
|
4
|
+
* Response from a license service.
|
|
5
|
+
* `valid` is accepted only after this package verifies the signed token.
|
|
6
|
+
* A redirect to a payment success page is not a license result.
|
|
7
|
+
*/
|
|
8
|
+
export interface LicenseServiceResult {
|
|
9
|
+
status: LicenseServiceStatus;
|
|
10
|
+
token?: string;
|
|
11
|
+
message?: string;
|
|
12
|
+
}
|
|
13
|
+
export interface LicenseProviderContext {
|
|
14
|
+
productId: string;
|
|
15
|
+
signal?: AbortSignal;
|
|
16
|
+
}
|
|
17
|
+
export interface LicenseActivateRequest {
|
|
18
|
+
key: string;
|
|
19
|
+
productId: string;
|
|
20
|
+
}
|
|
21
|
+
export interface LicenseRefreshRequest {
|
|
22
|
+
token: string;
|
|
23
|
+
productId: string;
|
|
24
|
+
}
|
|
25
|
+
export interface LicenseDeactivateRequest {
|
|
26
|
+
token?: string;
|
|
27
|
+
productId: string;
|
|
28
|
+
}
|
|
29
|
+
/** Host-supplied license API. This package does not include a license-server admin client. */
|
|
30
|
+
export interface LicenseProvider {
|
|
31
|
+
readonly name: string;
|
|
32
|
+
activate(request: LicenseActivateRequest, context: LicenseProviderContext): Promise<LicenseServiceResult>;
|
|
33
|
+
refresh?(request: LicenseRefreshRequest, context: LicenseProviderContext): Promise<LicenseServiceResult>;
|
|
34
|
+
deactivate?(request: LicenseDeactivateRequest, context: LicenseProviderContext): Promise<void>;
|
|
35
|
+
}
|
|
36
|
+
export interface MockLicenseHandlers {
|
|
37
|
+
activate?: (key: string) => Promise<LicenseServiceResult> | LicenseServiceResult;
|
|
38
|
+
refresh?: (token: string) => Promise<LicenseServiceResult> | LicenseServiceResult;
|
|
39
|
+
deactivate?: () => Promise<void> | void;
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Test double. It does not contact a license service and cannot mint a trusted token.
|
|
43
|
+
* A `valid` result still has to carry a signature this package can verify.
|
|
44
|
+
*/
|
|
45
|
+
export declare function createMockLicenseProvider(handlers?: MockLicenseHandlers): LicenseProvider;
|
|
46
|
+
export interface HttpLicenseProviderOptions {
|
|
47
|
+
/** Absolute HTTPS URL of the activation endpoint. There is no default. */
|
|
48
|
+
activateUrl: string;
|
|
49
|
+
refreshUrl?: string;
|
|
50
|
+
deactivateUrl?: string;
|
|
51
|
+
headers?: Readonly<Record<string, string>>;
|
|
52
|
+
fetchImpl?: typeof fetch;
|
|
53
|
+
}
|
|
54
|
+
/**
|
|
55
|
+
* Posts the license key to a host-configured HTTPS endpoint.
|
|
56
|
+
* The endpoint must return a signed token. This client does not grant entitlements from the HTTP status.
|
|
57
|
+
*/
|
|
58
|
+
export declare function createHttpLicenseProvider(options: HttpLicenseProviderOptions): LicenseProvider;
|
|
59
|
+
//# sourceMappingURL=provider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"provider.d.ts","sourceRoot":"","sources":["../../src/license/provider.ts"],"names":[],"mappings":"AAGA,eAAO,MAAM,wBAAwB,4FAO3B,CAAC;AAEX,MAAM,MAAM,oBAAoB,GAAG,CAAC,OAAO,wBAAwB,CAAC,CAAC,MAAM,CAAC,CAAC;AAE7E;;;;GAIG;AACH,MAAM,WAAW,oBAAoB;IACnC,MAAM,EAAE,oBAAoB,CAAC;IAC7B,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,sBAAsB;IACrC,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,WAAW,CAAC;CACtB;AAED,MAAM,WAAW,sBAAsB;IACrC,GAAG,EAAE,MAAM,CAAC;IACZ,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,qBAAqB;IACpC,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,wBAAwB;IACvC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,8FAA8F;AAC9F,MAAM,WAAW,eAAe;IAC9B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,OAAO,EAAE,sBAAsB,EAAE,OAAO,EAAE,sBAAsB,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAAC;IAC1G,OAAO,CAAC,CAAC,OAAO,EAAE,qBAAqB,EAAE,OAAO,EAAE,sBAAsB,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAAC;IACzG,UAAU,CAAC,CAAC,OAAO,EAAE,wBAAwB,EAAE,OAAO,EAAE,sBAAsB,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CAChG;AAED,MAAM,WAAW,mBAAmB;IAClC,QAAQ,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,OAAO,CAAC,oBAAoB,CAAC,GAAG,oBAAoB,CAAC;IACjF,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,OAAO,CAAC,oBAAoB,CAAC,GAAG,oBAAoB,CAAC;IAClF,UAAU,CAAC,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC;CACzC;AAED;;;GAGG;AACH,wBAAgB,yBAAyB,CAAC,QAAQ,GAAE,mBAAwB,GAAG,eAAe,CAyB7F;AAED,MAAM,WAAW,0BAA0B;IACzC,0EAA0E;IAC1E,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,OAAO,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAC3C,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;CAC1B;AAED;;;GAGG;AACH,wBAAgB,yBAAyB,CAAC,OAAO,EAAE,0BAA0B,GAAG,eAAe,CA+B9F"}
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
import { LicenseError } from "./errors.js";
|
|
2
|
+
import { messageWithoutSecret } from "./redact.js";
|
|
3
|
+
export const LICENSE_SERVICE_STATUSES = [
|
|
4
|
+
"unconfigured",
|
|
5
|
+
"valid",
|
|
6
|
+
"expired",
|
|
7
|
+
"invalid",
|
|
8
|
+
"revoked",
|
|
9
|
+
"network_unavailable",
|
|
10
|
+
];
|
|
11
|
+
/**
|
|
12
|
+
* Test double. It does not contact a license service and cannot mint a trusted token.
|
|
13
|
+
* A `valid` result still has to carry a signature this package can verify.
|
|
14
|
+
*/
|
|
15
|
+
export function createMockLicenseProvider(handlers = {}) {
|
|
16
|
+
return {
|
|
17
|
+
name: "mock",
|
|
18
|
+
async activate(request) {
|
|
19
|
+
if (!handlers.activate) {
|
|
20
|
+
return {
|
|
21
|
+
status: "unconfigured",
|
|
22
|
+
message: "The mock license provider is not a license server. Activation is unconfigured.",
|
|
23
|
+
};
|
|
24
|
+
}
|
|
25
|
+
return handlers.activate(request.key);
|
|
26
|
+
},
|
|
27
|
+
async refresh(request) {
|
|
28
|
+
if (!handlers.refresh) {
|
|
29
|
+
return {
|
|
30
|
+
status: "network_unavailable",
|
|
31
|
+
message: "The mock license provider has no refresh handler.",
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
return handlers.refresh(request.token);
|
|
35
|
+
},
|
|
36
|
+
async deactivate() {
|
|
37
|
+
await handlers.deactivate?.();
|
|
38
|
+
},
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Posts the license key to a host-configured HTTPS endpoint.
|
|
43
|
+
* The endpoint must return a signed token. This client does not grant entitlements from the HTTP status.
|
|
44
|
+
*/
|
|
45
|
+
export function createHttpLicenseProvider(options) {
|
|
46
|
+
const activateUrl = assertLicenseUrl(options.activateUrl, "activateUrl");
|
|
47
|
+
const refreshUrl = options.refreshUrl === undefined ? undefined : assertLicenseUrl(options.refreshUrl, "refreshUrl");
|
|
48
|
+
const deactivateUrl = options.deactivateUrl === undefined ? undefined : assertLicenseUrl(options.deactivateUrl, "deactivateUrl");
|
|
49
|
+
const fetchImpl = options.fetchImpl ?? globalThis.fetch;
|
|
50
|
+
const headers = options.headers;
|
|
51
|
+
return {
|
|
52
|
+
name: "http",
|
|
53
|
+
async activate(request, context) {
|
|
54
|
+
return postJson(fetchImpl, activateUrl, { key: request.key, productId: request.productId }, request.key, headers, context);
|
|
55
|
+
},
|
|
56
|
+
refresh: refreshUrl
|
|
57
|
+
? async (request, context) => postJson(fetchImpl, refreshUrl, { token: request.token, productId: request.productId }, request.token, headers, context)
|
|
58
|
+
: undefined,
|
|
59
|
+
deactivate: deactivateUrl
|
|
60
|
+
? async (request, context) => {
|
|
61
|
+
const result = await postJson(fetchImpl, deactivateUrl, { token: request.token, productId: request.productId }, request.token ?? "", headers, context);
|
|
62
|
+
if (result.status === "network_unavailable") {
|
|
63
|
+
throw new LicenseError("unavailable_runtime", result.message ?? "The license service could not be reached.");
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
: undefined,
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
function assertLicenseUrl(value, label) {
|
|
70
|
+
let url;
|
|
71
|
+
try {
|
|
72
|
+
url = new URL(value);
|
|
73
|
+
}
|
|
74
|
+
catch {
|
|
75
|
+
throw new LicenseError("invalid_input", `${label} must be an absolute URL.`);
|
|
76
|
+
}
|
|
77
|
+
if (url.protocol !== "https:") {
|
|
78
|
+
throw new LicenseError("invalid_input", `${label} must use HTTPS.`);
|
|
79
|
+
}
|
|
80
|
+
if (url.username.length > 0 || url.password.length > 0) {
|
|
81
|
+
throw new LicenseError("invalid_input", `${label} must not include credentials.`);
|
|
82
|
+
}
|
|
83
|
+
return url.toString();
|
|
84
|
+
}
|
|
85
|
+
async function postJson(fetchImpl, url, body, secret, headers, context) {
|
|
86
|
+
if (typeof fetchImpl !== "function") {
|
|
87
|
+
return { status: "network_unavailable", message: "This runtime cannot reach a license service." };
|
|
88
|
+
}
|
|
89
|
+
let response;
|
|
90
|
+
try {
|
|
91
|
+
response = await fetchImpl(url, {
|
|
92
|
+
method: "POST",
|
|
93
|
+
headers: {
|
|
94
|
+
accept: "application/json",
|
|
95
|
+
"content-type": "application/json",
|
|
96
|
+
...headers,
|
|
97
|
+
},
|
|
98
|
+
body: JSON.stringify(body),
|
|
99
|
+
signal: context.signal,
|
|
100
|
+
});
|
|
101
|
+
}
|
|
102
|
+
catch {
|
|
103
|
+
return { status: "network_unavailable", message: "The license service could not be reached." };
|
|
104
|
+
}
|
|
105
|
+
if (response.status === 404) {
|
|
106
|
+
return { status: "unconfigured", message: "The license service endpoint was not found." };
|
|
107
|
+
}
|
|
108
|
+
if (response.status >= 500) {
|
|
109
|
+
return { status: "network_unavailable", message: "The license service could not be reached." };
|
|
110
|
+
}
|
|
111
|
+
let payload;
|
|
112
|
+
try {
|
|
113
|
+
payload = await response.json();
|
|
114
|
+
}
|
|
115
|
+
catch {
|
|
116
|
+
return { status: "invalid", message: "The license service returned an unreadable response." };
|
|
117
|
+
}
|
|
118
|
+
return parseServiceResult(payload, secret);
|
|
119
|
+
}
|
|
120
|
+
function parseServiceResult(payload, secret) {
|
|
121
|
+
const record = asRecord(payload);
|
|
122
|
+
if (!record) {
|
|
123
|
+
return { status: "invalid", message: "The license service returned an unreadable response." };
|
|
124
|
+
}
|
|
125
|
+
const status = record.status;
|
|
126
|
+
if (typeof status !== "string" || !isServiceStatus(status)) {
|
|
127
|
+
return { status: "invalid", message: "The license service returned an unknown status." };
|
|
128
|
+
}
|
|
129
|
+
const token = record.token;
|
|
130
|
+
if (token !== undefined && (typeof token !== "string" || token.length === 0 || token.length > 8192)) {
|
|
131
|
+
return { status: "invalid", message: "The license service returned an unreadable token." };
|
|
132
|
+
}
|
|
133
|
+
const message = record.message;
|
|
134
|
+
const safeMessage = typeof message === "string" ? messageWithoutSecret(message.slice(0, 300), secret) : undefined;
|
|
135
|
+
return {
|
|
136
|
+
status,
|
|
137
|
+
token: typeof token === "string" ? token : undefined,
|
|
138
|
+
message: safeMessage,
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
function asRecord(value) {
|
|
142
|
+
if (!value || typeof value !== "object" || Array.isArray(value)) {
|
|
143
|
+
return undefined;
|
|
144
|
+
}
|
|
145
|
+
return value;
|
|
146
|
+
}
|
|
147
|
+
function isServiceStatus(value) {
|
|
148
|
+
return LICENSE_SERVICE_STATUSES.includes(value);
|
|
149
|
+
}
|
|
150
|
+
//# sourceMappingURL=provider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"provider.js","sourceRoot":"","sources":["../../src/license/provider.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"redact.d.ts","sourceRoot":"","sources":["../../src/license/redact.ts"],"names":[],"mappings":"AAAA,kEAAkE;AAClE,wBAAgB,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAMlD;AAED,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CAK5E"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/** Returns a log-safe hint. The full secret is never included. */
|
|
2
|
+
export function redactSecret(value) {
|
|
3
|
+
const trimmed = value.trim();
|
|
4
|
+
if (trimmed.length <= 8) {
|
|
5
|
+
return "****";
|
|
6
|
+
}
|
|
7
|
+
return `****${trimmed.slice(-4)}`;
|
|
8
|
+
}
|
|
9
|
+
export function messageWithoutSecret(message, secret) {
|
|
10
|
+
if (secret.length === 0) {
|
|
11
|
+
return message;
|
|
12
|
+
}
|
|
13
|
+
return message.split(secret).join(redactSecret(secret));
|
|
14
|
+
}
|
|
15
|
+
//# sourceMappingURL=redact.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"redact.js","sourceRoot":"","sources":["../../src/license/redact.ts"],"names":[],"mappings":"AAAA,kEAAkE;AAClE,MAAM,UAAU,YAAY,CAAC,KAAa;IACxC,MAAM,OAAO,GAAG,KAAK,CAAC,IAAI,EAAE,CAAC;IAC7B,IAAI,OAAO,CAAC,MAAM,IAAI,CAAC,EAAE,CAAC;QACxB,OAAO,MAAM,CAAC;IAChB,CAAC;IACD,OAAO,OAAO,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;AACpC,CAAC;AAED,MAAM,UAAU,oBAAoB,CAAC,OAAe,EAAE,MAAc;IAClE,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACxB,OAAO,OAAO,CAAC;IACjB,CAAC;IACD,OAAO,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC;AAC1D,CAAC"}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/** Local activation record. The license key itself is not stored. */
|
|
2
|
+
export interface StoredLicense {
|
|
3
|
+
token: string;
|
|
4
|
+
/** ISO time of the last successful online verification. */
|
|
5
|
+
lastVerifiedAt?: string;
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* Persistence for one installation.
|
|
9
|
+
* Document templates are not a license store. Do not write this record into invoice or report JSON.
|
|
10
|
+
*/
|
|
11
|
+
export interface LicenseStore {
|
|
12
|
+
read(): Promise<StoredLicense | null>;
|
|
13
|
+
write(record: StoredLicense): Promise<void>;
|
|
14
|
+
clear(): Promise<void>;
|
|
15
|
+
}
|
|
16
|
+
export declare function createMemoryLicenseStore(initial?: StoredLicense | null): LicenseStore;
|
|
17
|
+
/** Browser persistence key. It is separate from `doc-forge-theme` and from saved templates. */
|
|
18
|
+
export declare const LICENSE_STORAGE_KEY = "doc-forge-license";
|
|
19
|
+
type KeyValueStorage = Pick<Storage, "getItem" | "setItem" | "removeItem">;
|
|
20
|
+
/**
|
|
21
|
+
* Stores the signed token in the supplied storage, or in `localStorage` when a browser is present.
|
|
22
|
+
* Calling this during server rendering does not touch `window`. A later write with no storage throws.
|
|
23
|
+
*/
|
|
24
|
+
export declare function createBrowserLicenseStore(storage?: KeyValueStorage | null): LicenseStore;
|
|
25
|
+
export {};
|
|
26
|
+
//# sourceMappingURL=store.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../../src/license/store.ts"],"names":[],"mappings":"AAEA,qEAAqE;AACrE,MAAM,WAAW,aAAa;IAC5B,KAAK,EAAE,MAAM,CAAC;IACd,2DAA2D;IAC3D,cAAc,CAAC,EAAE,MAAM,CAAC;CACzB;AAED;;;GAGG;AACH,MAAM,WAAW,YAAY;IAC3B,IAAI,IAAI,OAAO,CAAC,aAAa,GAAG,IAAI,CAAC,CAAC;IACtC,KAAK,CAAC,MAAM,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5C,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;CACxB;AAED,wBAAgB,wBAAwB,CAAC,OAAO,CAAC,EAAE,aAAa,GAAG,IAAI,GAAG,YAAY,CAarF;AAED,+FAA+F;AAC/F,eAAO,MAAM,mBAAmB,sBAAsB,CAAC;AAEvD,KAAK,eAAe,GAAG,IAAI,CAAC,OAAO,EAAE,SAAS,GAAG,SAAS,GAAG,YAAY,CAAC,CAAC;AAE3E;;;GAGG;AACH,wBAAgB,yBAAyB,CAAC,OAAO,CAAC,EAAE,eAAe,GAAG,IAAI,GAAG,YAAY,CAmCxF"}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { LicenseError } from "./errors.js";
|
|
2
|
+
export function createMemoryLicenseStore(initial) {
|
|
3
|
+
let current = initial ?? null;
|
|
4
|
+
return {
|
|
5
|
+
async read() {
|
|
6
|
+
return current ? { ...current } : null;
|
|
7
|
+
},
|
|
8
|
+
async write(record) {
|
|
9
|
+
current = { token: record.token, lastVerifiedAt: record.lastVerifiedAt };
|
|
10
|
+
},
|
|
11
|
+
async clear() {
|
|
12
|
+
current = null;
|
|
13
|
+
},
|
|
14
|
+
};
|
|
15
|
+
}
|
|
16
|
+
/** Browser persistence key. It is separate from `doc-forge-theme` and from saved templates. */
|
|
17
|
+
export const LICENSE_STORAGE_KEY = "doc-forge-license";
|
|
18
|
+
/**
|
|
19
|
+
* Stores the signed token in the supplied storage, or in `localStorage` when a browser is present.
|
|
20
|
+
* Calling this during server rendering does not touch `window`. A later write with no storage throws.
|
|
21
|
+
*/
|
|
22
|
+
export function createBrowserLicenseStore(storage) {
|
|
23
|
+
const explicit = storage === undefined ? undefined : storage;
|
|
24
|
+
return {
|
|
25
|
+
async read() {
|
|
26
|
+
const target = resolveStorage(explicit);
|
|
27
|
+
if (!target) {
|
|
28
|
+
return null;
|
|
29
|
+
}
|
|
30
|
+
const raw = target.getItem(LICENSE_STORAGE_KEY);
|
|
31
|
+
if (!raw) {
|
|
32
|
+
return null;
|
|
33
|
+
}
|
|
34
|
+
return parseStoredLicense(raw);
|
|
35
|
+
},
|
|
36
|
+
async write(record) {
|
|
37
|
+
const target = resolveStorage(explicit);
|
|
38
|
+
if (!target) {
|
|
39
|
+
throw new LicenseError("persistence", "License storage is unavailable in this runtime. Provide a store that does not read browser APIs during server rendering.");
|
|
40
|
+
}
|
|
41
|
+
target.setItem(LICENSE_STORAGE_KEY, JSON.stringify({ token: record.token, lastVerifiedAt: record.lastVerifiedAt }));
|
|
42
|
+
},
|
|
43
|
+
async clear() {
|
|
44
|
+
const target = resolveStorage(explicit);
|
|
45
|
+
if (!target) {
|
|
46
|
+
throw new LicenseError("persistence", "License storage is unavailable in this runtime. Provide a store that does not read browser APIs during server rendering.");
|
|
47
|
+
}
|
|
48
|
+
target.removeItem(LICENSE_STORAGE_KEY);
|
|
49
|
+
},
|
|
50
|
+
};
|
|
51
|
+
}
|
|
52
|
+
function resolveStorage(explicit) {
|
|
53
|
+
if (explicit) {
|
|
54
|
+
return explicit;
|
|
55
|
+
}
|
|
56
|
+
if (explicit === null) {
|
|
57
|
+
return null;
|
|
58
|
+
}
|
|
59
|
+
if (typeof window === "undefined") {
|
|
60
|
+
return null;
|
|
61
|
+
}
|
|
62
|
+
try {
|
|
63
|
+
return window.localStorage;
|
|
64
|
+
}
|
|
65
|
+
catch {
|
|
66
|
+
return null;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
function parseStoredLicense(raw) {
|
|
70
|
+
try {
|
|
71
|
+
const parsed = JSON.parse(raw);
|
|
72
|
+
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
73
|
+
return null;
|
|
74
|
+
}
|
|
75
|
+
const record = parsed;
|
|
76
|
+
const token = record.token;
|
|
77
|
+
if (typeof token !== "string" || token.length === 0 || token.length > 8192) {
|
|
78
|
+
return null;
|
|
79
|
+
}
|
|
80
|
+
const verified = record.lastVerifiedAt;
|
|
81
|
+
if (verified !== undefined && typeof verified !== "string") {
|
|
82
|
+
return null;
|
|
83
|
+
}
|
|
84
|
+
return { token, lastVerifiedAt: verified };
|
|
85
|
+
}
|
|
86
|
+
catch {
|
|
87
|
+
return null;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=store.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"store.js","sourceRoot":"","sources":["../../src/license/store.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { type LicenseFeature } from "./features.js";
|
|
2
|
+
export interface LicensePublicKey {
|
|
3
|
+
/** Key id carried in the token header. Required when more than one key is configured. */
|
|
4
|
+
kid: string;
|
|
5
|
+
/** SubjectPublicKeyInfo for a P-256 public key, base64 or base64url. */
|
|
6
|
+
spki: string;
|
|
7
|
+
}
|
|
8
|
+
export interface LicenseClaims {
|
|
9
|
+
issuer: string;
|
|
10
|
+
audience: readonly string[];
|
|
11
|
+
/** Unix seconds. */
|
|
12
|
+
expiresAt: number;
|
|
13
|
+
notBefore?: number;
|
|
14
|
+
product: string;
|
|
15
|
+
entitlements: readonly LicenseFeature[];
|
|
16
|
+
unrecognizedEntitlements: readonly string[];
|
|
17
|
+
plan?: string;
|
|
18
|
+
tokenId?: string;
|
|
19
|
+
subject?: string;
|
|
20
|
+
}
|
|
21
|
+
export interface LicenseVerifyOptions {
|
|
22
|
+
productId: string;
|
|
23
|
+
issuer: string;
|
|
24
|
+
audience: string;
|
|
25
|
+
keys: readonly LicensePublicKey[];
|
|
26
|
+
now: Date;
|
|
27
|
+
clockSkewSeconds: number;
|
|
28
|
+
revokedTokenIds: readonly string[];
|
|
29
|
+
}
|
|
30
|
+
export type TokenVerification = {
|
|
31
|
+
ok: true;
|
|
32
|
+
claims: LicenseClaims;
|
|
33
|
+
} | {
|
|
34
|
+
ok: false;
|
|
35
|
+
reason: "malformed" | "signature" | "claims" | "expired" | "revoked";
|
|
36
|
+
message: string;
|
|
37
|
+
claims?: LicenseClaims;
|
|
38
|
+
};
|
|
39
|
+
/**
|
|
40
|
+
* Verifies a compact JWS signed with ES256.
|
|
41
|
+
* The private key is not present in this package. A token that fails this check
|
|
42
|
+
* cannot grant entitlements, including a token that only says `isPremium: true`.
|
|
43
|
+
*/
|
|
44
|
+
export declare function verifyLicenseToken(token: string, options: LicenseVerifyOptions): Promise<TokenVerification>;
|
|
45
|
+
//# sourceMappingURL=token.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"token.d.ts","sourceRoot":"","sources":["../../src/license/token.ts"],"names":[],"mappings":"AAEA,OAAO,EAAoB,KAAK,cAAc,EAAE,MAAM,eAAe,CAAC;AAEtE,MAAM,WAAW,gBAAgB;IAC/B,yFAAyF;IACzF,GAAG,EAAE,MAAM,CAAC;IACZ,wEAAwE;IACxE,IAAI,EAAE,MAAM,CAAC;CACd;AAED,MAAM,WAAW,aAAa;IAC5B,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,SAAS,MAAM,EAAE,CAAC;IAC5B,oBAAoB;IACpB,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,EAAE,SAAS,cAAc,EAAE,CAAC;IACxC,wBAAwB,EAAE,SAAS,MAAM,EAAE,CAAC;IAC5C,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,oBAAoB;IACnC,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,SAAS,gBAAgB,EAAE,CAAC;IAClC,GAAG,EAAE,IAAI,CAAC;IACV,gBAAgB,EAAE,MAAM,CAAC;IACzB,eAAe,EAAE,SAAS,MAAM,EAAE,CAAC;CACpC;AAED,MAAM,MAAM,iBAAiB,GACzB;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,MAAM,EAAE,aAAa,CAAA;CAAE,GACnC;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,MAAM,EAAE,WAAW,GAAG,WAAW,GAAG,QAAQ,GAAG,SAAS,GAAG,SAAS,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,aAAa,CAAA;CAAE,CAAC;AAIjI;;;;GAIG;AACH,wBAAsB,kBAAkB,CAAC,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,oBAAoB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAoCjH"}
|
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
import { decodeBase64Url, utf8Bytes, utf8String } from "./codec.js";
|
|
2
|
+
import { LicenseError } from "./errors.js";
|
|
3
|
+
import { isLicenseFeature } from "./features.js";
|
|
4
|
+
const keyCache = new Map();
|
|
5
|
+
/**
|
|
6
|
+
* Verifies a compact JWS signed with ES256.
|
|
7
|
+
* The private key is not present in this package. A token that fails this check
|
|
8
|
+
* cannot grant entitlements, including a token that only says `isPremium: true`.
|
|
9
|
+
*/
|
|
10
|
+
export async function verifyLicenseToken(token, options) {
|
|
11
|
+
const parts = token.split(".");
|
|
12
|
+
if (parts.length !== 3 || parts.some((part) => part.length === 0)) {
|
|
13
|
+
return rejected("malformed", "The license token is not a signed token.");
|
|
14
|
+
}
|
|
15
|
+
const [encodedHeader, encodedPayload, encodedSignature] = parts;
|
|
16
|
+
let header;
|
|
17
|
+
let payload;
|
|
18
|
+
try {
|
|
19
|
+
header = JSON.parse(utf8String(decodeBase64Url(encodedHeader)));
|
|
20
|
+
payload = JSON.parse(utf8String(decodeBase64Url(encodedPayload)));
|
|
21
|
+
}
|
|
22
|
+
catch {
|
|
23
|
+
return rejected("malformed", "The license token is not a signed token.");
|
|
24
|
+
}
|
|
25
|
+
if (!isRecord(header) || !isRecord(payload)) {
|
|
26
|
+
return rejected("malformed", "The license token is not a signed token.");
|
|
27
|
+
}
|
|
28
|
+
if (header.alg !== "ES256" || Object.hasOwn(header, "crit")) {
|
|
29
|
+
return rejected("signature", "The license token algorithm is not accepted.");
|
|
30
|
+
}
|
|
31
|
+
const kid = typeof header.kid === "string" ? header.kid : undefined;
|
|
32
|
+
const key = selectKey(options.keys, kid);
|
|
33
|
+
if (!key) {
|
|
34
|
+
return rejected("signature", "The license token was not signed by a configured key.");
|
|
35
|
+
}
|
|
36
|
+
let signature;
|
|
37
|
+
try {
|
|
38
|
+
signature = decodeBase64Url(encodedSignature);
|
|
39
|
+
}
|
|
40
|
+
catch {
|
|
41
|
+
return rejected("malformed", "The license token is not a signed token.");
|
|
42
|
+
}
|
|
43
|
+
const verified = await signatureMatches(key.spki, utf8Bytes(`${encodedHeader}.${encodedPayload}`), signature);
|
|
44
|
+
if (!verified) {
|
|
45
|
+
return rejected("signature", "The license token signature is not valid.");
|
|
46
|
+
}
|
|
47
|
+
return readClaims(payload, options);
|
|
48
|
+
}
|
|
49
|
+
async function signatureMatches(spki, data, signature) {
|
|
50
|
+
const subtle = globalThis.crypto?.subtle;
|
|
51
|
+
if (!subtle) {
|
|
52
|
+
throw new LicenseError("unavailable_runtime", "This runtime cannot verify license signatures.");
|
|
53
|
+
}
|
|
54
|
+
let key;
|
|
55
|
+
try {
|
|
56
|
+
key = await importPublicKey(subtle, spki);
|
|
57
|
+
}
|
|
58
|
+
catch (error) {
|
|
59
|
+
if (error instanceof LicenseError) {
|
|
60
|
+
throw error;
|
|
61
|
+
}
|
|
62
|
+
return false;
|
|
63
|
+
}
|
|
64
|
+
try {
|
|
65
|
+
return await subtle.verify({ name: "ECDSA", hash: "SHA-256" }, key, arrayBuffer(signature), arrayBuffer(data));
|
|
66
|
+
}
|
|
67
|
+
catch {
|
|
68
|
+
return false;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
async function importPublicKey(subtle, spki) {
|
|
72
|
+
const cached = keyCache.get(spki);
|
|
73
|
+
if (cached) {
|
|
74
|
+
return cached;
|
|
75
|
+
}
|
|
76
|
+
const bytes = decodeKeyBytes(spki);
|
|
77
|
+
const key = await subtle.importKey("spki", arrayBuffer(bytes), { name: "ECDSA", namedCurve: "P-256" }, false, ["verify"]);
|
|
78
|
+
keyCache.set(spki, key);
|
|
79
|
+
return key;
|
|
80
|
+
}
|
|
81
|
+
function arrayBuffer(bytes) {
|
|
82
|
+
const copy = new ArrayBuffer(bytes.byteLength);
|
|
83
|
+
new Uint8Array(copy).set(bytes);
|
|
84
|
+
return copy;
|
|
85
|
+
}
|
|
86
|
+
function decodeKeyBytes(value) {
|
|
87
|
+
const compact = value.replace(/\s+/gu, "").replace(/=+$/u, "").replaceAll("+", "-").replaceAll("/", "_");
|
|
88
|
+
return decodeBase64Url(compact);
|
|
89
|
+
}
|
|
90
|
+
function selectKey(keys, kid) {
|
|
91
|
+
if (kid) {
|
|
92
|
+
return keys.find((key) => key.kid === kid);
|
|
93
|
+
}
|
|
94
|
+
return keys.length === 1 ? keys[0] : undefined;
|
|
95
|
+
}
|
|
96
|
+
function readClaims(payload, options) {
|
|
97
|
+
const issuer = readString(payload, "iss");
|
|
98
|
+
const product = readString(payload, "product");
|
|
99
|
+
const expiresAt = readNumber(payload, "exp");
|
|
100
|
+
const audience = readAudience(payload);
|
|
101
|
+
if (!issuer || !product || expiresAt === undefined || audience.length === 0) {
|
|
102
|
+
return rejected("claims", "The license token is missing required claims.");
|
|
103
|
+
}
|
|
104
|
+
if (issuer !== options.issuer || product !== options.productId || !audience.includes(options.audience)) {
|
|
105
|
+
return rejected("claims", "The license token does not match this product.");
|
|
106
|
+
}
|
|
107
|
+
const entitlementResult = readEntitlements(payload);
|
|
108
|
+
if (!entitlementResult) {
|
|
109
|
+
return rejected("claims", "The license token entitlements are not a list of features.");
|
|
110
|
+
}
|
|
111
|
+
const notBefore = readOptionalNumber(payload, "nbf");
|
|
112
|
+
const claims = {
|
|
113
|
+
issuer,
|
|
114
|
+
audience,
|
|
115
|
+
expiresAt,
|
|
116
|
+
notBefore,
|
|
117
|
+
product,
|
|
118
|
+
entitlements: entitlementResult.features,
|
|
119
|
+
unrecognizedEntitlements: entitlementResult.unrecognized,
|
|
120
|
+
plan: readOptionalString(payload, "plan"),
|
|
121
|
+
tokenId: readOptionalString(payload, "jti"),
|
|
122
|
+
subject: readOptionalString(payload, "sub"),
|
|
123
|
+
};
|
|
124
|
+
const now = Math.floor(options.now.getTime() / 1000);
|
|
125
|
+
if (notBefore !== undefined && notBefore > now + options.clockSkewSeconds) {
|
|
126
|
+
return rejected("claims", "The license token is not valid yet.", claims);
|
|
127
|
+
}
|
|
128
|
+
if (expiresAt <= now - options.clockSkewSeconds) {
|
|
129
|
+
return rejected("expired", "The license token has expired.", claims);
|
|
130
|
+
}
|
|
131
|
+
if (claims.tokenId !== undefined && options.revokedTokenIds.includes(claims.tokenId)) {
|
|
132
|
+
return rejected("revoked", "The license token has been revoked.", claims);
|
|
133
|
+
}
|
|
134
|
+
return { ok: true, claims };
|
|
135
|
+
}
|
|
136
|
+
function readEntitlements(payload) {
|
|
137
|
+
if (!Object.hasOwn(payload, "entitlements")) {
|
|
138
|
+
return { features: [], unrecognized: [] };
|
|
139
|
+
}
|
|
140
|
+
const value = payload.entitlements;
|
|
141
|
+
if (!Array.isArray(value)) {
|
|
142
|
+
return undefined;
|
|
143
|
+
}
|
|
144
|
+
const features = [];
|
|
145
|
+
const unrecognized = [];
|
|
146
|
+
for (const entry of value) {
|
|
147
|
+
if (typeof entry !== "string") {
|
|
148
|
+
return undefined;
|
|
149
|
+
}
|
|
150
|
+
if (isLicenseFeature(entry)) {
|
|
151
|
+
features.push(entry);
|
|
152
|
+
}
|
|
153
|
+
else {
|
|
154
|
+
unrecognized.push(entry);
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
return { features, unrecognized };
|
|
158
|
+
}
|
|
159
|
+
function readAudience(payload) {
|
|
160
|
+
const value = payload.aud;
|
|
161
|
+
if (typeof value === "string" && value.length > 0) {
|
|
162
|
+
return [value];
|
|
163
|
+
}
|
|
164
|
+
if (!Array.isArray(value) || value.length === 0 || value.some((entry) => typeof entry !== "string" || entry.length === 0)) {
|
|
165
|
+
return [];
|
|
166
|
+
}
|
|
167
|
+
return value;
|
|
168
|
+
}
|
|
169
|
+
function readString(record, key) {
|
|
170
|
+
const value = record[key];
|
|
171
|
+
return typeof value === "string" && value.length > 0 ? value : undefined;
|
|
172
|
+
}
|
|
173
|
+
function readOptionalString(record, key) {
|
|
174
|
+
if (!Object.hasOwn(record, key)) {
|
|
175
|
+
return undefined;
|
|
176
|
+
}
|
|
177
|
+
return readString(record, key);
|
|
178
|
+
}
|
|
179
|
+
function readNumber(record, key) {
|
|
180
|
+
const value = record[key];
|
|
181
|
+
return typeof value === "number" && Number.isFinite(value) ? value : undefined;
|
|
182
|
+
}
|
|
183
|
+
function readOptionalNumber(record, key) {
|
|
184
|
+
if (!Object.hasOwn(record, key)) {
|
|
185
|
+
return undefined;
|
|
186
|
+
}
|
|
187
|
+
return readNumber(record, key);
|
|
188
|
+
}
|
|
189
|
+
function rejected(reason, message, claims) {
|
|
190
|
+
return claims ? { ok: false, reason, message, claims } : { ok: false, reason, message };
|
|
191
|
+
}
|
|
192
|
+
function isRecord(value) {
|
|
193
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
194
|
+
}
|
|
195
|
+
//# sourceMappingURL=token.js.map
|