@aglyn/aglyn 1.0.0-beta.220 → 1.0.0-beta.222
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/package.json +15 -11
- package/src/lib/app-utils/agent-openapi.js +1 -1
- package/src/lib/app-utils/agent-openapi.js.map +1 -1
- package/src/lib/app-utils/analytics-events.d.ts +3 -2
- package/src/lib/app-utils/analytics-events.js +3 -2
- package/src/lib/app-utils/analytics-events.js.map +1 -1
- package/src/lib/app-utils/api-plugins.d.ts +30 -0
- package/src/lib/app-utils/api-plugins.js +24 -1
- package/src/lib/app-utils/api-plugins.js.map +1 -1
- package/src/lib/app-utils/author-html.d.ts +1 -1
- package/src/lib/app-utils/author-html.js.map +1 -1
- package/src/lib/app-utils/bandwidth-cap.d.ts +12 -1
- package/src/lib/app-utils/bandwidth-cap.js +17 -1
- package/src/lib/app-utils/bandwidth-cap.js.map +1 -1
- package/src/lib/app-utils/compose-reusable-components.d.ts +19 -0
- package/src/lib/app-utils/compose-reusable-components.js +116 -26
- package/src/lib/app-utils/compose-reusable-components.js.map +1 -1
- package/src/lib/app-utils/console-routes.d.ts +4 -0
- package/src/lib/app-utils/console-routes.js +3 -0
- package/src/lib/app-utils/console-routes.js.map +1 -1
- package/src/lib/app-utils/contacts.d.ts +71 -0
- package/src/lib/app-utils/contacts.js +55 -0
- package/src/lib/app-utils/contacts.js.map +1 -1
- package/src/lib/app-utils/contexts.d.ts +1 -0
- package/src/lib/app-utils/contexts.js +1 -0
- package/src/lib/app-utils/contexts.js.map +1 -1
- package/src/lib/app-utils/crm-email-templates.js +21 -4
- package/src/lib/app-utils/crm-email-templates.js.map +1 -1
- package/src/lib/app-utils/crm-kinds.d.ts +2 -0
- package/src/lib/app-utils/crm-kinds.js +1 -0
- package/src/lib/app-utils/crm-kinds.js.map +1 -1
- package/src/lib/app-utils/crm.d.ts +1199 -67
- package/src/lib/app-utils/crm.js +1951 -310
- package/src/lib/app-utils/crm.js.map +1 -1
- package/src/lib/app-utils/csv-import.d.ts +10 -38
- package/src/lib/app-utils/csv-import.js +17 -42
- package/src/lib/app-utils/csv-import.js.map +1 -1
- package/src/lib/app-utils/csv.d.ts +32 -11
- package/src/lib/app-utils/csv.js +43 -5
- package/src/lib/app-utils/csv.js.map +1 -1
- package/src/lib/app-utils/default-site.d.ts +116 -0
- package/src/lib/app-utils/default-site.js +1024 -0
- package/src/lib/app-utils/default-site.js.map +1 -0
- package/src/lib/app-utils/docs-help.generated.d.ts +23 -23
- package/src/lib/app-utils/docs-help.generated.js +47 -10
- package/src/lib/app-utils/docs-help.generated.js.map +1 -1
- package/src/lib/app-utils/docs-index.generated.js +746 -151
- package/src/lib/app-utils/docs-index.generated.js.map +1 -1
- package/src/lib/app-utils/draft-placeholders.d.ts +76 -0
- package/src/lib/app-utils/draft-placeholders.js +115 -0
- package/src/lib/app-utils/draft-placeholders.js.map +1 -0
- package/src/lib/app-utils/entity-picker-context.d.ts +19 -15
- package/src/lib/app-utils/entity-picker-context.js +4 -4
- package/src/lib/app-utils/entity-picker-context.js.map +1 -1
- package/src/lib/app-utils/expand-repeatables.d.ts +66 -10
- package/src/lib/app-utils/expand-repeatables.js +88 -14
- package/src/lib/app-utils/expand-repeatables.js.map +1 -1
- package/src/lib/app-utils/forms.d.ts +33 -22
- package/src/lib/app-utils/forms.js +47 -28
- package/src/lib/app-utils/forms.js.map +1 -1
- package/src/lib/app-utils/full-use-cost.d.ts +277 -0
- package/src/lib/app-utils/full-use-cost.js +421 -0
- package/src/lib/app-utils/full-use-cost.js.map +1 -0
- package/src/lib/app-utils/health-report.js +33 -0
- package/src/lib/app-utils/health-report.js.map +1 -1
- package/src/lib/app-utils/leaving-notice.d.ts +96 -0
- package/src/lib/app-utils/leaving-notice.js +157 -0
- package/src/lib/app-utils/leaving-notice.js.map +1 -0
- package/src/lib/app-utils/llms-txt.d.ts +20 -0
- package/src/lib/app-utils/llms-txt.js +7 -1
- package/src/lib/app-utils/llms-txt.js.map +1 -1
- package/src/lib/app-utils/media-asset-facts.d.ts +16 -1
- package/src/lib/app-utils/media-asset-facts.js +40 -13
- package/src/lib/app-utils/media-asset-facts.js.map +1 -1
- package/src/lib/app-utils/media-bandwidth.d.ts +52 -0
- package/src/lib/app-utils/media-bandwidth.js +94 -0
- package/src/lib/app-utils/media-bandwidth.js.map +1 -0
- package/src/lib/app-utils/media-ref.d.ts +241 -33
- package/src/lib/app-utils/media-ref.js +324 -43
- package/src/lib/app-utils/media-ref.js.map +1 -1
- package/src/lib/app-utils/media-src.d.ts +8 -8
- package/src/lib/app-utils/media-src.js +27 -11
- package/src/lib/app-utils/media-src.js.map +1 -1
- package/src/lib/app-utils/media-takedown-reach.d.ts +4 -1
- package/src/lib/app-utils/media-takedown-reach.js +6 -3
- package/src/lib/app-utils/media-takedown-reach.js.map +1 -1
- package/src/lib/app-utils/notifications.d.ts +1 -1
- package/src/lib/app-utils/notifications.js +2 -0
- package/src/lib/app-utils/notifications.js.map +1 -1
- package/src/lib/app-utils/operator-alerts.js +17 -0
- package/src/lib/app-utils/operator-alerts.js.map +1 -1
- package/src/lib/app-utils/organizations.d.ts +51 -2
- package/src/lib/app-utils/organizations.js +56 -3
- package/src/lib/app-utils/organizations.js.map +1 -1
- package/src/lib/app-utils/page-record-sources.d.ts +87 -0
- package/src/lib/app-utils/page-record-sources.js +53 -0
- package/src/lib/app-utils/page-record-sources.js.map +1 -0
- package/src/lib/app-utils/paid-media-source.d.ts +3 -7
- package/src/lib/app-utils/paid-media-source.js +5 -19
- package/src/lib/app-utils/paid-media-source.js.map +1 -1
- package/src/lib/app-utils/person-erasure.d.ts +5 -2
- package/src/lib/app-utils/person-erasure.js.map +1 -1
- package/src/lib/app-utils/picklists.d.ts +187 -0
- package/src/lib/app-utils/picklists.js +320 -0
- package/src/lib/app-utils/picklists.js.map +1 -0
- package/src/lib/app-utils/plan-entitlements.d.ts +220 -50
- package/src/lib/app-utils/plan-entitlements.js +309 -115
- package/src/lib/app-utils/plan-entitlements.js.map +1 -1
- package/src/lib/app-utils/realm-host-surface.generated.js +2 -0
- package/src/lib/app-utils/realm-host-surface.generated.js.map +1 -1
- package/src/lib/app-utils/release-flags.d.ts +1 -1
- package/src/lib/app-utils/release-flags.js +11 -0
- package/src/lib/app-utils/release-flags.js.map +1 -1
- package/src/lib/app-utils/rendered-widths.d.ts +121 -0
- package/src/lib/app-utils/rendered-widths.js +211 -0
- package/src/lib/app-utils/rendered-widths.js.map +1 -0
- package/src/lib/app-utils/repeat-sources.d.ts +2 -1
- package/src/lib/app-utils/repeat-sources.js.map +1 -1
- package/src/lib/app-utils/screen-link-context-value.d.ts +7 -0
- package/src/lib/app-utils/screen-link-context-value.js.map +1 -1
- package/src/lib/app-utils/screen-link-context.js +14 -2
- package/src/lib/app-utils/screen-link-context.js.map +1 -1
- package/src/lib/app-utils/screen-route.d.ts +157 -36
- package/src/lib/app-utils/screen-route.js +191 -41
- package/src/lib/app-utils/screen-route.js.map +1 -1
- package/src/lib/app-utils/seo-audit.d.ts +11 -1
- package/src/lib/app-utils/seo-audit.js +33 -13
- package/src/lib/app-utils/seo-audit.js.map +1 -1
- package/src/lib/app-utils/seo-keywords.d.ts +11 -0
- package/src/lib/app-utils/seo-keywords.js +19 -5
- package/src/lib/app-utils/seo-keywords.js.map +1 -1
- package/src/lib/app-utils/seo-page-facts.d.ts +47 -4
- package/src/lib/app-utils/seo-page-facts.js +136 -31
- package/src/lib/app-utils/seo-page-facts.js.map +1 -1
- package/src/lib/app-utils/seo-site-scan.d.ts +42 -4
- package/src/lib/app-utils/seo-site-scan.js +113 -12
- package/src/lib/app-utils/seo-site-scan.js.map +1 -1
- package/src/lib/app-utils/server.d.ts +5 -4
- package/src/lib/app-utils/server.js +14 -5
- package/src/lib/app-utils/server.js.map +1 -1
- package/src/lib/app-utils/site-icon-set.d.ts +195 -0
- package/src/lib/app-utils/site-icon-set.js +351 -0
- package/src/lib/app-utils/site-icon-set.js.map +1 -0
- package/src/lib/app-utils/site-interactions.d.ts +101 -4
- package/src/lib/app-utils/site-interactions.js +120 -4
- package/src/lib/app-utils/site-interactions.js.map +1 -1
- package/src/lib/app-utils/starter-template-nodes.d.ts +7 -0
- package/src/lib/app-utils/starter-template-nodes.js +3 -0
- package/src/lib/app-utils/starter-template-nodes.js.map +1 -1
- package/src/lib/app-utils/starter-templates.d.ts +5 -19
- package/src/lib/app-utils/starter-templates.js +5 -49
- package/src/lib/app-utils/starter-templates.js.map +1 -1
- package/src/lib/app-utils/transfer-launcher-context.d.ts +136 -0
- package/src/lib/app-utils/transfer-launcher-context.js +23 -0
- package/src/lib/app-utils/transfer-launcher-context.js.map +1 -0
- package/src/lib/app-utils/transfer-resume-import.d.ts +39 -0
- package/src/lib/app-utils/transfer-resume-import.js +128 -0
- package/src/lib/app-utils/transfer-resume-import.js.map +1 -0
- package/src/lib/app-utils/upgrade-proposal.d.ts +66 -0
- package/src/lib/app-utils/upgrade-proposal.js +95 -0
- package/src/lib/app-utils/upgrade-proposal.js.map +1 -0
- package/src/lib/app-utils/utc-month.d.ts +33 -0
- package/src/lib/app-utils/utc-month.js +35 -0
- package/src/lib/app-utils/utc-month.js.map +1 -0
- package/src/lib/app-utils/visitor-record-ceiling.d.ts +4 -4
- package/src/lib/app-utils/visitor-record-ceiling.js +4 -4
- package/src/lib/app-utils/visitor-record-ceiling.js.map +1 -1
- package/src/lib/app-utils/wire-nodes.d.ts +39 -19
- package/src/lib/app-utils/wire-nodes.js +120 -34
- package/src/lib/app-utils/wire-nodes.js.map +1 -1
- package/src/lib/data-transfer/access.d.ts +74 -0
- package/src/lib/data-transfer/access.js +93 -0
- package/src/lib/data-transfer/access.js.map +1 -0
- package/src/lib/data-transfer/derive.d.ts +246 -0
- package/src/lib/data-transfer/derive.js +1007 -0
- package/src/lib/data-transfer/derive.js.map +1 -0
- package/src/lib/data-transfer/export-file.d.ts +46 -0
- package/src/lib/data-transfer/export-file.js +146 -0
- package/src/lib/data-transfer/export-file.js.map +1 -0
- package/src/lib/data-transfer/field-catalog.d.ts +134 -0
- package/src/lib/data-transfer/field-catalog.js +278 -0
- package/src/lib/data-transfer/field-catalog.js.map +1 -0
- package/src/lib/data-transfer/header-match.d.ts +129 -0
- package/src/lib/data-transfer/header-match.js +367 -0
- package/src/lib/data-transfer/header-match.js.map +1 -0
- package/src/lib/data-transfer/index.d.ts +34 -0
- package/src/lib/data-transfer/index.js +40 -0
- package/src/lib/data-transfer/index.js.map +1 -0
- package/src/lib/data-transfer/job.d.ts +190 -0
- package/src/lib/data-transfer/job.js +229 -0
- package/src/lib/data-transfer/job.js.map +1 -0
- package/src/lib/data-transfer/lookup.d.ts +45 -0
- package/src/lib/data-transfer/lookup.js +71 -0
- package/src/lib/data-transfer/lookup.js.map +1 -0
- package/src/lib/data-transfer/match.d.ts +99 -0
- package/src/lib/data-transfer/match.js +244 -0
- package/src/lib/data-transfer/match.js.map +1 -0
- package/src/lib/data-transfer/package-plan.d.ts +205 -0
- package/src/lib/data-transfer/package-plan.js +475 -0
- package/src/lib/data-transfer/package-plan.js.map +1 -0
- package/src/lib/data-transfer/package.d.ts +181 -0
- package/src/lib/data-transfer/package.js +426 -0
- package/src/lib/data-transfer/package.js.map +1 -0
- package/src/lib/data-transfer/picklist-map.d.ts +139 -0
- package/src/lib/data-transfer/picklist-map.js +271 -0
- package/src/lib/data-transfer/picklist-map.js.map +1 -0
- package/src/lib/data-transfer/plan.d.ts +176 -0
- package/src/lib/data-transfer/plan.js +451 -0
- package/src/lib/data-transfer/plan.js.map +1 -0
- package/src/lib/data-transfer/policy.d.ts +170 -0
- package/src/lib/data-transfer/policy.js +378 -0
- package/src/lib/data-transfer/policy.js.map +1 -0
- package/src/lib/data-transfer/resource.d.ts +211 -0
- package/src/lib/data-transfer/resource.js +241 -0
- package/src/lib/data-transfer/resource.js.map +1 -0
- package/src/lib/data-transfer/review.d.ts +70 -0
- package/src/lib/data-transfer/review.js +233 -0
- package/src/lib/data-transfer/review.js.map +1 -0
- package/src/lib/data-transfer/similarity.d.ts +40 -0
- package/src/lib/data-transfer/similarity.js +106 -0
- package/src/lib/data-transfer/similarity.js.map +1 -0
- package/src/lib/data-transfer/site-package.d.ts +365 -0
- package/src/lib/data-transfer/site-package.js +1077 -0
- package/src/lib/data-transfer/site-package.js.map +1 -0
- package/src/lib/data-transfer/source.d.ts +74 -0
- package/src/lib/data-transfer/source.js +293 -0
- package/src/lib/data-transfer/source.js.map +1 -0
- package/src/lib/data-transfer/transfer-api.d.ts +898 -0
- package/src/lib/data-transfer/transfer-api.js +107 -0
- package/src/lib/data-transfer/transfer-api.js.map +1 -0
- package/src/lib/foundation/definitions/org-billing.types.d.ts +31 -0
- package/src/lib/foundation/definitions/org-billing.types.js.map +1 -1
- package/src/lib/foundation/definitions/organization.types.d.ts +42 -1
- package/src/lib/foundation/definitions/organization.types.js.map +1 -1
- package/src/lib/foundation/definitions/platform.types.d.ts +6 -4
- package/src/lib/foundation/definitions/platform.types.js.map +1 -1
- package/src/lib/foundation/index.d.ts +1 -1
- package/src/lib/foundation/index.js.map +1 -1
- package/src/lib/plugin-manager/feature-plugins.d.ts +91 -2
- package/src/lib/plugin-manager/feature-plugins.js +48 -3
- package/src/lib/plugin-manager/feature-plugins.js.map +1 -1
- package/src/lib/plugin-manager/first-party-plugins.generated.d.ts +56 -0
- package/src/lib/plugin-manager/first-party-plugins.generated.js +1132 -27
- package/src/lib/plugin-manager/first-party-plugins.generated.js.map +1 -1
- package/src/lib/plugin-manager/index.d.ts +0 -1
- package/src/lib/plugin-manager/index.js +0 -1
- package/src/lib/plugin-manager/index.js.map +1 -1
- package/src/lib/plugin-manager/interaction-recipes.d.ts +142 -0
- package/src/lib/plugin-manager/interaction-recipes.js +104 -0
- package/src/lib/plugin-manager/interaction-recipes.js.map +1 -0
- package/src/lib/plugin-manager/interaction-step-checks.d.ts +66 -0
- package/src/lib/plugin-manager/interaction-step-checks.js +86 -0
- package/src/lib/plugin-manager/interaction-step-checks.js.map +1 -0
- package/src/lib/plugin-manager/plugin-artifact-types.d.ts +235 -0
- package/src/lib/plugin-manager/plugin-artifact-types.js +99 -0
- package/src/lib/plugin-manager/plugin-artifact-types.js.map +1 -0
- package/src/lib/plugin-manager/plugin-contact-capture.d.ts +8 -0
- package/src/lib/plugin-manager/plugin-contact-capture.js.map +1 -1
- package/src/lib/plugin-manager/plugin-conversion-credit.d.ts +216 -0
- package/src/lib/plugin-manager/plugin-conversion-credit.js +91 -0
- package/src/lib/plugin-manager/plugin-conversion-credit.js.map +1 -0
- package/src/lib/plugin-manager/plugin-entity-pickers.d.ts +83 -0
- package/src/lib/plugin-manager/plugin-entity-pickers.js +87 -0
- package/src/lib/plugin-manager/plugin-entity-pickers.js.map +1 -0
- package/src/lib/plugin-manager/plugin-host-resources.d.ts +6 -0
- package/src/lib/plugin-manager/plugin-host-resources.js +6 -1
- package/src/lib/plugin-manager/plugin-host-resources.js.map +1 -1
- package/src/lib/plugin-manager/plugin-intake-gates.d.ts +75 -0
- package/src/lib/plugin-manager/plugin-intake-gates.js +49 -0
- package/src/lib/plugin-manager/plugin-intake-gates.js.map +1 -0
- package/src/lib/plugin-manager/plugin-jobs.d.ts +5 -5
- package/src/lib/plugin-manager/plugin-jobs.js +7 -7
- package/src/lib/plugin-manager/plugin-jobs.js.map +1 -1
- package/src/lib/plugin-manager/plugin-live-paths.d.ts +70 -0
- package/src/lib/plugin-manager/plugin-live-paths.js +66 -0
- package/src/lib/plugin-manager/plugin-live-paths.js.map +1 -0
- package/src/lib/plugin-manager/plugin-org-erasure.d.ts +3 -2
- package/src/lib/plugin-manager/plugin-org-erasure.js +30 -5
- package/src/lib/plugin-manager/plugin-org-erasure.js.map +1 -1
- package/src/lib/plugin-manager/plugin-person-erasure.d.ts +68 -9
- package/src/lib/plugin-manager/plugin-person-erasure.js +196 -51
- package/src/lib/plugin-manager/plugin-person-erasure.js.map +1 -1
- package/src/lib/plugin-manager/plugin-person-records.d.ts +275 -0
- package/src/lib/plugin-manager/plugin-person-records.js +107 -0
- package/src/lib/plugin-manager/plugin-person-records.js.map +1 -0
- package/src/lib/plugin-manager/plugin-record-counts.d.ts +76 -0
- package/src/lib/plugin-manager/plugin-record-counts.js +49 -0
- package/src/lib/plugin-manager/plugin-record-counts.js.map +1 -0
- package/src/lib/plugin-manager/plugin-record-email-state.d.ts +26 -0
- package/src/lib/plugin-manager/plugin-record-email-state.js +16 -0
- package/src/lib/plugin-manager/plugin-record-email-state.js.map +1 -1
- package/src/lib/plugin-manager/plugin-record-index.d.ts +10 -0
- package/src/lib/plugin-manager/plugin-record-index.js.map +1 -1
- package/src/lib/plugin-manager/plugin-record-lists.d.ts +86 -6
- package/src/lib/plugin-manager/plugin-record-lists.js +42 -5
- package/src/lib/plugin-manager/plugin-record-lists.js.map +1 -1
- package/src/lib/plugin-manager/plugin-record-origin.d.ts +79 -0
- package/src/lib/plugin-manager/plugin-record-origin.js +46 -0
- package/src/lib/plugin-manager/plugin-record-origin.js.map +1 -0
- package/src/lib/plugin-manager/plugin-record-pages.d.ts +37 -0
- package/src/lib/plugin-manager/plugin-record-pages.js +52 -0
- package/src/lib/plugin-manager/plugin-record-pages.js.map +1 -0
- package/src/lib/plugin-manager/plugin-record-timeline.d.ts +60 -0
- package/src/lib/plugin-manager/plugin-record-timeline.js +16 -0
- package/src/lib/plugin-manager/plugin-record-timeline.js.map +1 -1
- package/src/lib/plugin-manager/plugin-resource-drafts.d.ts +5 -5
- package/src/lib/plugin-manager/plugin-resource-drafts.js.map +1 -1
- package/src/lib/plugin-manager/plugin-revocations.d.ts +64 -0
- package/src/lib/plugin-manager/plugin-revocations.js +47 -0
- package/src/lib/plugin-manager/plugin-revocations.js.map +1 -0
- package/src/lib/plugin-manager/plugin-send-tallies.d.ts +69 -0
- package/src/lib/plugin-manager/plugin-send-tallies.js +45 -0
- package/src/lib/plugin-manager/plugin-send-tallies.js.map +1 -0
- package/src/lib/plugin-manager/plugin-server-steps.d.ts +170 -0
- package/src/lib/plugin-manager/plugin-server-steps.js +116 -0
- package/src/lib/plugin-manager/plugin-server-steps.js.map +1 -0
- package/src/lib/plugin-manager/plugin-site-bundle.d.ts +40 -0
- package/src/lib/plugin-manager/plugin-site-bundle.js +4 -0
- package/src/lib/plugin-manager/plugin-site-bundle.js.map +1 -1
- package/src/lib/plugin-manager/plugin-site-export.d.ts +57 -1
- package/src/lib/plugin-manager/plugin-site-export.js +23 -10
- package/src/lib/plugin-manager/plugin-site-export.js.map +1 -1
- package/src/lib/plugin-manager/plugin-sitemap-readers.d.ts +146 -0
- package/src/lib/plugin-manager/plugin-sitemap-readers.js +110 -0
- package/src/lib/plugin-manager/plugin-sitemap-readers.js.map +1 -0
- package/src/lib/plugin-manager/plugin-transfer-resources.d.ts +714 -0
- package/src/lib/plugin-manager/plugin-transfer-resources.js +443 -0
- package/src/lib/plugin-manager/plugin-transfer-resources.js.map +1 -0
- package/src/lib/plugin-manager/plugin-usage-axes.d.ts +54 -5
- package/src/lib/plugin-manager/plugin-usage-axes.js +11 -3
- package/src/lib/plugin-manager/plugin-usage-axes.js.map +1 -1
- package/src/lib/plugin-manager/plugin-user-erasure.js +9 -1
- package/src/lib/plugin-manager/plugin-user-erasure.js.map +1 -1
- package/src/lib/plugin-manager/plugin-visitor-doors.d.ts +104 -0
- package/src/lib/plugin-manager/plugin-visitor-doors.js +108 -0
- package/src/lib/plugin-manager/plugin-visitor-doors.js.map +1 -0
- package/src/lib/plugin-manager/realm-host-aglyn.generated.js +2 -0
- package/src/lib/plugin-manager/realm-host-aglyn.generated.js.map +1 -1
- package/src/lib/plugin-manager/repeat-rows.d.ts +5 -6
- package/src/lib/plugin-manager/repeat-rows.js.map +1 -1
- package/src/lib/app-utils/actions.d.ts +0 -310
- package/src/lib/app-utils/actions.js +0 -506
- package/src/lib/app-utils/actions.js.map +0 -1
- package/src/lib/app-utils/automation-placeholders.d.ts +0 -72
- package/src/lib/app-utils/automation-placeholders.js +0 -207
- package/src/lib/app-utils/automation-placeholders.js.map +0 -1
- package/src/lib/app-utils/dataset-models.d.ts +0 -339
- package/src/lib/app-utils/dataset-models.js +0 -722
- package/src/lib/app-utils/dataset-models.js.map +0 -1
- package/src/lib/app-utils/datasets.d.ts +0 -171
- package/src/lib/app-utils/datasets.js +0 -227
- package/src/lib/app-utils/datasets.js.map +0 -1
- package/src/lib/app-utils/form-abuse-ceiling.d.ts +0 -146
- package/src/lib/app-utils/form-abuse-ceiling.js +0 -158
- package/src/lib/app-utils/form-abuse-ceiling.js.map +0 -1
- package/src/lib/plugin-manager/order-fulfilment.d.ts +0 -142
- package/src/lib/plugin-manager/order-fulfilment.js +0 -104
- package/src/lib/plugin-manager/order-fulfilment.js.map +0 -1
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Aglyn LLC
|
|
4
|
+
*
|
|
5
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
6
|
+
* you may not use this file except in compliance with the License.
|
|
7
|
+
* You may obtain a copy of the License at
|
|
8
|
+
*
|
|
9
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
*
|
|
11
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
12
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
13
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
14
|
+
* See the License for the specific language governing permissions and
|
|
15
|
+
* limitations under the License.
|
|
16
|
+
*/
|
|
17
|
+
/**
|
|
18
|
+
* Every icon a published site serves, derived from the one file its author
|
|
19
|
+
* uploaded (AGL-3484).
|
|
20
|
+
*
|
|
21
|
+
* A site's Favicon and App icon are a single media reference each. A browser
|
|
22
|
+
* tab draws 16px, iOS a 180px touch icon, an installer anything from 48px to
|
|
23
|
+
* 512px plus a maskable tile — and every one of them used to download the
|
|
24
|
+
* original upload, a 512×512 PNG to paint a 16px tab. This module is the
|
|
25
|
+
* grammar of the derived set: which sizes exist, how each is addressed on the
|
|
26
|
+
* media CDN, and which `<link>` and manifest entries describe them. The pixels
|
|
27
|
+
* are drawn by `site-icon-render.ts` in `@aglyn/tenant-data-admin`, behind the
|
|
28
|
+
* `?icon=` representation of `serveMediaCdn`; the tenant layout, manifest and
|
|
29
|
+
* `/favicon.ico` route build their URLs here, so the three can never name a
|
|
30
|
+
* size the renderer does not draw.
|
|
31
|
+
*
|
|
32
|
+
* ## Addressing
|
|
33
|
+
*
|
|
34
|
+
* A derived icon is the asset's own stable CDN URL plus three parameters:
|
|
35
|
+
*
|
|
36
|
+
* - `icon` — the {@link SiteIconSpec}, e.g. `png-32`, `flat-180`,
|
|
37
|
+
* `maskable-512` or `ico`. Only the sizes listed below parse, so the cache
|
|
38
|
+
* key space is bounded and nobody can ask the renderer for a 20000px tile.
|
|
39
|
+
* - `bg` — the plate color, six hex digits, for the two plates that have one.
|
|
40
|
+
* - `v` — the asset's `contentHash`. With it the response is cached for a
|
|
41
|
+
* year; a DAM Replace changes the hash, so the next render names a new URL
|
|
42
|
+
* and the old one is never asked for again. A stale `v` that does arrive
|
|
43
|
+
* redirects to the current one.
|
|
44
|
+
*/
|
|
45
|
+
/** The CDN query parameter that selects a derived icon. */
|
|
46
|
+
export declare const SITE_ICON_PARAM = "icon";
|
|
47
|
+
/** The plate color of a flattened or maskable icon, six hex digits. */
|
|
48
|
+
export declare const SITE_ICON_BACKGROUND_PARAM = "bg";
|
|
49
|
+
/** The asset's `contentHash`, which keys the year-long cache. */
|
|
50
|
+
export declare const SITE_ICON_VERSION_PARAM = "v";
|
|
51
|
+
/** Tab, bookmark and taskbar sizes, as `<link rel="icon" type="image/png">`. */
|
|
52
|
+
export declare const FAVICON_PNG_SIZES: readonly [16, 32, 48];
|
|
53
|
+
/** The images packed into the site's `/favicon.ico`. */
|
|
54
|
+
export declare const FAVICON_ICO_SIZES: readonly [16, 32, 48];
|
|
55
|
+
/** iPhone (180), iPad Pro (167) and iPad (152) home-screen icons. */
|
|
56
|
+
export declare const APPLE_TOUCH_ICON_SIZES: readonly [180, 167, 152];
|
|
57
|
+
/** The manifest's `purpose: "any"` set. */
|
|
58
|
+
export declare const MANIFEST_ICON_SIZES: readonly [48, 72, 96, 128, 144, 152, 192, 256, 384, 512];
|
|
59
|
+
/** The manifest's `purpose: "maskable"` set. */
|
|
60
|
+
export declare const MANIFEST_MASKABLE_ICON_SIZES: readonly [192, 512];
|
|
61
|
+
/**
|
|
62
|
+
* The diameter of the maskable safe zone, as a fraction of the icon.
|
|
63
|
+
*
|
|
64
|
+
* The Web App Manifest spec promises only a centered circle of 40% radius
|
|
65
|
+
* survives every launcher mask. A mark's box is therefore fitted inside the
|
|
66
|
+
* square INSCRIBED in that circle — {@link maskableMarkSize} — so even its
|
|
67
|
+
* corners stay uncropped on a circle mask.
|
|
68
|
+
*/
|
|
69
|
+
export declare const MASKABLE_SAFE_ZONE = 0.8;
|
|
70
|
+
/** The plate of a site with no theme background: white, like the manifest's. */
|
|
71
|
+
export declare const DEFAULT_SITE_ICON_BACKGROUND = "ffffff";
|
|
72
|
+
/**
|
|
73
|
+
* One derived icon.
|
|
74
|
+
*
|
|
75
|
+
* - `transparent` — the mark center-fit on a transparent square. Favicons
|
|
76
|
+
* and the manifest's `any` set.
|
|
77
|
+
* - `flat` — the same, flattened onto the theme background. iOS renders
|
|
78
|
+
* transparency black, so every apple-touch-icon is one of these.
|
|
79
|
+
* - `maskable` — the mark inside the safe zone on the theme background.
|
|
80
|
+
* - `ico` — the {@link FAVICON_ICO_SIZES} transparent PNGs in one ICO.
|
|
81
|
+
*/
|
|
82
|
+
export type SiteIconSpec = {
|
|
83
|
+
plate: 'transparent' | 'flat' | 'maskable';
|
|
84
|
+
size: number;
|
|
85
|
+
} | {
|
|
86
|
+
plate: 'ico';
|
|
87
|
+
};
|
|
88
|
+
/** The spec's spelling in the `icon` parameter. */
|
|
89
|
+
export declare function formatSiteIconSpec(spec: SiteIconSpec): string;
|
|
90
|
+
/**
|
|
91
|
+
* Reads the `icon` parameter back; `null` for anything this module would not
|
|
92
|
+
* have written — an unknown plate, or a size outside that plate's list.
|
|
93
|
+
*/
|
|
94
|
+
export declare function parseSiteIconSpec(value: unknown): SiteIconSpec | null;
|
|
95
|
+
/** Whether a spec is drawn on the theme background rather than transparency. */
|
|
96
|
+
export declare function siteIconUsesBackground(spec: SiteIconSpec): boolean;
|
|
97
|
+
/** The served type of a derived icon. */
|
|
98
|
+
export declare function siteIconContentType(spec: SiteIconSpec): string;
|
|
99
|
+
/**
|
|
100
|
+
* The side of the box a maskable icon's mark is fitted into: the square
|
|
101
|
+
* inscribed in the {@link MASKABLE_SAFE_ZONE} circle, so no launcher mask can
|
|
102
|
+
* reach any part of it.
|
|
103
|
+
*/
|
|
104
|
+
export declare function maskableMarkSize(size: number): number;
|
|
105
|
+
/**
|
|
106
|
+
* A theme color as the `bg` parameter carries it: six lowercase hex digits,
|
|
107
|
+
* or `undefined` for anything that is not a plain color.
|
|
108
|
+
*
|
|
109
|
+
* A theme's `background.default` is free CSS text. `#rgb`, `#rrggbb`,
|
|
110
|
+
* `#rrggbbaa` (alpha dropped — a plate is opaque by definition) and `rgb()` /
|
|
111
|
+
* `rgba()` are read; a gradient, a `var()` or a named color is not a color
|
|
112
|
+
* this module can put in a URL, and the caller's default stands in.
|
|
113
|
+
*/
|
|
114
|
+
export declare function normalizeSiteIconBackground(value: unknown): string | undefined;
|
|
115
|
+
/**
|
|
116
|
+
* What one read of the source asset's media document says, or `null` when it
|
|
117
|
+
* was not read (a raw URL, or a failed read).
|
|
118
|
+
*/
|
|
119
|
+
export interface SiteIconSourceFacts {
|
|
120
|
+
/** The upload's MIME type. */
|
|
121
|
+
contentType?: string;
|
|
122
|
+
/** The upload's content hash — the cache key a DAM Replace changes. */
|
|
123
|
+
contentHash?: string;
|
|
124
|
+
}
|
|
125
|
+
/**
|
|
126
|
+
* Whether the derived set can be drawn from this source.
|
|
127
|
+
*
|
|
128
|
+
* Only an asset our CDN serves has a renderer behind it; a hotlinked or raw
|
|
129
|
+
* storage URL is linked as it is, exactly as before. A known non-image or an
|
|
130
|
+
* ICO (which `sharp` cannot decode) passes through too. Unknown facts derive
|
|
131
|
+
* anyway: the renderer redirects to the original for anything it cannot draw,
|
|
132
|
+
* so a failed read costs a hop, never a broken icon.
|
|
133
|
+
*/
|
|
134
|
+
export declare function siteIconDerivable(src: string | undefined | null, facts?: SiteIconSourceFacts | null): boolean;
|
|
135
|
+
/**
|
|
136
|
+
* Whether the renderer can draw from an upload of this MIME type: any image
|
|
137
|
+
* `sharp` decodes, SVG included (it is rasterized at each size).
|
|
138
|
+
*/
|
|
139
|
+
export declare function siteIconSourceTypeDerivable(type: unknown): boolean;
|
|
140
|
+
/** Whether the source is an SVG, which also passes through as `sizes="any"`. */
|
|
141
|
+
export declare function siteIconIsSvg(src: string | undefined | null, facts?: SiteIconSourceFacts | null): boolean;
|
|
142
|
+
/**
|
|
143
|
+
* The URL of one derived icon of `src`, or `undefined` when `src` is not a
|
|
144
|
+
* CDN URL and so has no renderer behind it.
|
|
145
|
+
*
|
|
146
|
+
* The parameters merge into a query `src` already carries — a signed private
|
|
147
|
+
* asset's `exp`/`sig` — and their order is fixed, so one icon has one URL and
|
|
148
|
+
* one cache entry.
|
|
149
|
+
*/
|
|
150
|
+
export declare function siteIconSrc(src: string | undefined | null, spec: SiteIconSpec, options?: {
|
|
151
|
+
background?: string | null;
|
|
152
|
+
version?: string | null;
|
|
153
|
+
}): string | undefined;
|
|
154
|
+
/** One `<link>` the layout emits. */
|
|
155
|
+
export interface SiteIconLink {
|
|
156
|
+
rel: 'icon' | 'apple-touch-icon';
|
|
157
|
+
href: string;
|
|
158
|
+
type?: string;
|
|
159
|
+
sizes?: string;
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* The `<link rel="icon">` set for a favicon source.
|
|
163
|
+
*
|
|
164
|
+
* Derivable: a PNG per {@link FAVICON_PNG_SIZES}, each with its real `type`
|
|
165
|
+
* and `sizes`, then the SVG itself as `sizes="any"` when the source is one —
|
|
166
|
+
* last, so a browser that draws SVG favicons prefers it and one that does not
|
|
167
|
+
* already has its PNG. Anything else is the single link it always was.
|
|
168
|
+
*/
|
|
169
|
+
export declare function siteFaviconLinks(src: string | undefined | null, facts?: SiteIconSourceFacts | null): SiteIconLink[];
|
|
170
|
+
/**
|
|
171
|
+
* The `<link rel="apple-touch-icon">` set: each of
|
|
172
|
+
* {@link APPLE_TOUCH_ICON_SIZES}, flattened onto `background`, or the single
|
|
173
|
+
* pass-through link for a source with no renderer behind it.
|
|
174
|
+
*/
|
|
175
|
+
export declare function siteAppleTouchIconLinks(src: string | undefined | null, facts?: SiteIconSourceFacts | null, background?: string | null): SiteIconLink[];
|
|
176
|
+
/** One entry of the manifest's `icons`. */
|
|
177
|
+
export interface SiteManifestIcon {
|
|
178
|
+
src: string;
|
|
179
|
+
sizes: string;
|
|
180
|
+
type?: string;
|
|
181
|
+
purpose: 'any' | 'maskable';
|
|
182
|
+
}
|
|
183
|
+
/**
|
|
184
|
+
* The manifest's whole `icons` array for one source, which the caller has
|
|
185
|
+
* already made ABSOLUTE (an installer fetches icons with no page to resolve
|
|
186
|
+
* against).
|
|
187
|
+
*
|
|
188
|
+
* Derivable: every {@link MANIFEST_ICON_SIZES} size as `purpose: "any"`, then
|
|
189
|
+
* {@link MANIFEST_MASKABLE_ICON_SIZES} as `purpose: "maskable"` on
|
|
190
|
+
* `background`, then the SVG as `sizes: "any"` when the source is one. Each
|
|
191
|
+
* `sizes` is a measurement, because the renderer draws exactly that square.
|
|
192
|
+
* Anything else is the single `sizes: "any"` entry it always was: nothing
|
|
193
|
+
* measured it, so nothing may claim a pixel size for it (AGL-2204).
|
|
194
|
+
*/
|
|
195
|
+
export declare function siteManifestIcons(src: string | undefined | null, facts?: SiteIconSourceFacts | null, background?: string | null): SiteManifestIcon[];
|
|
@@ -0,0 +1,351 @@
|
|
|
1
|
+
import { _ as _extends } from "@swc/helpers/_/_extends";
|
|
2
|
+
/**
|
|
3
|
+
* @license
|
|
4
|
+
* Copyright 2026 Aglyn LLC
|
|
5
|
+
*
|
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
7
|
+
* you may not use this file except in compliance with the License.
|
|
8
|
+
* You may obtain a copy of the License at
|
|
9
|
+
*
|
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
11
|
+
*
|
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
15
|
+
* See the License for the specific language governing permissions and
|
|
16
|
+
* limitations under the License.
|
|
17
|
+
*/ import { MEDIA_CDN_SEGMENT } from "./media-cdn-scope.js";
|
|
18
|
+
import { isMediaCdnUrl } from "./media-ref.js";
|
|
19
|
+
/**
|
|
20
|
+
* Every icon a published site serves, derived from the one file its author
|
|
21
|
+
* uploaded (AGL-3484).
|
|
22
|
+
*
|
|
23
|
+
* A site's Favicon and App icon are a single media reference each. A browser
|
|
24
|
+
* tab draws 16px, iOS a 180px touch icon, an installer anything from 48px to
|
|
25
|
+
* 512px plus a maskable tile — and every one of them used to download the
|
|
26
|
+
* original upload, a 512×512 PNG to paint a 16px tab. This module is the
|
|
27
|
+
* grammar of the derived set: which sizes exist, how each is addressed on the
|
|
28
|
+
* media CDN, and which `<link>` and manifest entries describe them. The pixels
|
|
29
|
+
* are drawn by `site-icon-render.ts` in `@aglyn/tenant-data-admin`, behind the
|
|
30
|
+
* `?icon=` representation of `serveMediaCdn`; the tenant layout, manifest and
|
|
31
|
+
* `/favicon.ico` route build their URLs here, so the three can never name a
|
|
32
|
+
* size the renderer does not draw.
|
|
33
|
+
*
|
|
34
|
+
* ## Addressing
|
|
35
|
+
*
|
|
36
|
+
* A derived icon is the asset's own stable CDN URL plus three parameters:
|
|
37
|
+
*
|
|
38
|
+
* - `icon` — the {@link SiteIconSpec}, e.g. `png-32`, `flat-180`,
|
|
39
|
+
* `maskable-512` or `ico`. Only the sizes listed below parse, so the cache
|
|
40
|
+
* key space is bounded and nobody can ask the renderer for a 20000px tile.
|
|
41
|
+
* - `bg` — the plate color, six hex digits, for the two plates that have one.
|
|
42
|
+
* - `v` — the asset's `contentHash`. With it the response is cached for a
|
|
43
|
+
* year; a DAM Replace changes the hash, so the next render names a new URL
|
|
44
|
+
* and the old one is never asked for again. A stale `v` that does arrive
|
|
45
|
+
* redirects to the current one.
|
|
46
|
+
*/ /** The CDN query parameter that selects a derived icon. */ export const SITE_ICON_PARAM = 'icon';
|
|
47
|
+
/** The plate color of a flattened or maskable icon, six hex digits. */ export const SITE_ICON_BACKGROUND_PARAM = 'bg';
|
|
48
|
+
/** The asset's `contentHash`, which keys the year-long cache. */ export const SITE_ICON_VERSION_PARAM = 'v';
|
|
49
|
+
/** Tab, bookmark and taskbar sizes, as `<link rel="icon" type="image/png">`. */ export const FAVICON_PNG_SIZES = [
|
|
50
|
+
16,
|
|
51
|
+
32,
|
|
52
|
+
48
|
|
53
|
+
];
|
|
54
|
+
/** The images packed into the site's `/favicon.ico`. */ export const FAVICON_ICO_SIZES = [
|
|
55
|
+
16,
|
|
56
|
+
32,
|
|
57
|
+
48
|
|
58
|
+
];
|
|
59
|
+
/** iPhone (180), iPad Pro (167) and iPad (152) home-screen icons. */ export const APPLE_TOUCH_ICON_SIZES = [
|
|
60
|
+
180,
|
|
61
|
+
167,
|
|
62
|
+
152
|
|
63
|
+
];
|
|
64
|
+
/** The manifest's `purpose: "any"` set. */ export const MANIFEST_ICON_SIZES = [
|
|
65
|
+
48,
|
|
66
|
+
72,
|
|
67
|
+
96,
|
|
68
|
+
128,
|
|
69
|
+
144,
|
|
70
|
+
152,
|
|
71
|
+
192,
|
|
72
|
+
256,
|
|
73
|
+
384,
|
|
74
|
+
512
|
|
75
|
+
];
|
|
76
|
+
/** The manifest's `purpose: "maskable"` set. */ export const MANIFEST_MASKABLE_ICON_SIZES = [
|
|
77
|
+
192,
|
|
78
|
+
512
|
|
79
|
+
];
|
|
80
|
+
/**
|
|
81
|
+
* The diameter of the maskable safe zone, as a fraction of the icon.
|
|
82
|
+
*
|
|
83
|
+
* The Web App Manifest spec promises only a centered circle of 40% radius
|
|
84
|
+
* survives every launcher mask. A mark's box is therefore fitted inside the
|
|
85
|
+
* square INSCRIBED in that circle — {@link maskableMarkSize} — so even its
|
|
86
|
+
* corners stay uncropped on a circle mask.
|
|
87
|
+
*/ export const MASKABLE_SAFE_ZONE = 0.8;
|
|
88
|
+
/** The plate of a site with no theme background: white, like the manifest's. */ export const DEFAULT_SITE_ICON_BACKGROUND = 'ffffff';
|
|
89
|
+
const PLATE_SIZES = {
|
|
90
|
+
transparent: [
|
|
91
|
+
...new Set([
|
|
92
|
+
...FAVICON_PNG_SIZES,
|
|
93
|
+
...MANIFEST_ICON_SIZES
|
|
94
|
+
])
|
|
95
|
+
],
|
|
96
|
+
flat: APPLE_TOUCH_ICON_SIZES,
|
|
97
|
+
maskable: MANIFEST_MASKABLE_ICON_SIZES
|
|
98
|
+
};
|
|
99
|
+
const PLATE_PREFIX = {
|
|
100
|
+
transparent: 'png',
|
|
101
|
+
flat: 'flat',
|
|
102
|
+
maskable: 'maskable'
|
|
103
|
+
};
|
|
104
|
+
/** The spec's spelling in the `icon` parameter. */ export function formatSiteIconSpec(spec) {
|
|
105
|
+
return spec.plate === 'ico' ? 'ico' : `${PLATE_PREFIX[spec.plate]}-${spec.size}`;
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Reads the `icon` parameter back; `null` for anything this module would not
|
|
109
|
+
* have written — an unknown plate, or a size outside that plate's list.
|
|
110
|
+
*/ export function parseSiteIconSpec(value) {
|
|
111
|
+
const raw = Array.isArray(value) ? value[0] : value;
|
|
112
|
+
if (typeof raw !== 'string') return null;
|
|
113
|
+
if (raw === 'ico') return {
|
|
114
|
+
plate: 'ico'
|
|
115
|
+
};
|
|
116
|
+
const match = /^(png|flat|maskable)-(\d{1,4})$/.exec(raw);
|
|
117
|
+
if (!match) return null;
|
|
118
|
+
const plate = Object.keys(PLATE_PREFIX).find((key)=>PLATE_PREFIX[key] === match[1]);
|
|
119
|
+
const size = Number(match[2]);
|
|
120
|
+
if (!plate || !PLATE_SIZES[plate].includes(size)) return null;
|
|
121
|
+
return {
|
|
122
|
+
plate,
|
|
123
|
+
size
|
|
124
|
+
};
|
|
125
|
+
}
|
|
126
|
+
/** Whether a spec is drawn on the theme background rather than transparency. */ export function siteIconUsesBackground(spec) {
|
|
127
|
+
return spec.plate === 'flat' || spec.plate === 'maskable';
|
|
128
|
+
}
|
|
129
|
+
/** The served type of a derived icon. */ export function siteIconContentType(spec) {
|
|
130
|
+
return spec.plate === 'ico' ? 'image/x-icon' : 'image/png';
|
|
131
|
+
}
|
|
132
|
+
/**
|
|
133
|
+
* The side of the box a maskable icon's mark is fitted into: the square
|
|
134
|
+
* inscribed in the {@link MASKABLE_SAFE_ZONE} circle, so no launcher mask can
|
|
135
|
+
* reach any part of it.
|
|
136
|
+
*/ export function maskableMarkSize(size) {
|
|
137
|
+
return Math.floor(size * MASKABLE_SAFE_ZONE / Math.SQRT2);
|
|
138
|
+
}
|
|
139
|
+
const HEX = /^#?([0-9a-f]{3}|[0-9a-f]{6}|[0-9a-f]{8})$/i;
|
|
140
|
+
const RGB = /^rgba?\(\s*(\d{1,3})\s*[, ]\s*(\d{1,3})\s*[, ]\s*(\d{1,3})/i;
|
|
141
|
+
/**
|
|
142
|
+
* A theme color as the `bg` parameter carries it: six lowercase hex digits,
|
|
143
|
+
* or `undefined` for anything that is not a plain color.
|
|
144
|
+
*
|
|
145
|
+
* A theme's `background.default` is free CSS text. `#rgb`, `#rrggbb`,
|
|
146
|
+
* `#rrggbbaa` (alpha dropped — a plate is opaque by definition) and `rgb()` /
|
|
147
|
+
* `rgba()` are read; a gradient, a `var()` or a named color is not a color
|
|
148
|
+
* this module can put in a URL, and the caller's default stands in.
|
|
149
|
+
*/ export function normalizeSiteIconBackground(value) {
|
|
150
|
+
if (typeof value !== 'string') return undefined;
|
|
151
|
+
const trimmed = value.trim();
|
|
152
|
+
const hex = HEX.exec(trimmed);
|
|
153
|
+
if (hex) {
|
|
154
|
+
const digits = hex[1].toLowerCase();
|
|
155
|
+
if (digits.length === 3) {
|
|
156
|
+
return digits.split('').map((digit)=>digit + digit).join('');
|
|
157
|
+
}
|
|
158
|
+
return digits.slice(0, 6);
|
|
159
|
+
}
|
|
160
|
+
const rgb = RGB.exec(trimmed);
|
|
161
|
+
if (rgb) {
|
|
162
|
+
const channels = rgb.slice(1, 4).map(Number);
|
|
163
|
+
if (channels.some((channel)=>channel > 255)) return undefined;
|
|
164
|
+
return channels.map((channel)=>channel.toString(16).padStart(2, '0')).join('');
|
|
165
|
+
}
|
|
166
|
+
return undefined;
|
|
167
|
+
}
|
|
168
|
+
/** Types `sharp` cannot decode, which therefore pass through as uploaded. */ const UNDERIVABLE_TYPES = new Set([
|
|
169
|
+
'image/x-icon',
|
|
170
|
+
'image/vnd.microsoft.icon'
|
|
171
|
+
]);
|
|
172
|
+
/**
|
|
173
|
+
* Whether the derived set can be drawn from this source.
|
|
174
|
+
*
|
|
175
|
+
* Only an asset our CDN serves has a renderer behind it; a hotlinked or raw
|
|
176
|
+
* storage URL is linked as it is, exactly as before. A known non-image or an
|
|
177
|
+
* ICO (which `sharp` cannot decode) passes through too. Unknown facts derive
|
|
178
|
+
* anyway: the renderer redirects to the original for anything it cannot draw,
|
|
179
|
+
* so a failed read costs a hop, never a broken icon.
|
|
180
|
+
*/ export function siteIconDerivable(src, facts) {
|
|
181
|
+
if (!src || !isMediaCdnUrl(src)) return false;
|
|
182
|
+
const type = facts == null ? void 0 : facts.contentType;
|
|
183
|
+
return !type || siteIconSourceTypeDerivable(type);
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Whether the renderer can draw from an upload of this MIME type: any image
|
|
187
|
+
* `sharp` decodes, SVG included (it is rasterized at each size).
|
|
188
|
+
*/ export function siteIconSourceTypeDerivable(type) {
|
|
189
|
+
return typeof type === 'string' && type.startsWith('image/') && !UNDERIVABLE_TYPES.has(type);
|
|
190
|
+
}
|
|
191
|
+
/** Whether the source is an SVG, which also passes through as `sizes="any"`. */ export function siteIconIsSvg(src, facts) {
|
|
192
|
+
var _src_split_;
|
|
193
|
+
if (!src) return false;
|
|
194
|
+
if (facts == null ? void 0 : facts.contentType) return facts.contentType === 'image/svg+xml';
|
|
195
|
+
if (isMediaCdnUrl(src)) return false;
|
|
196
|
+
return /\.svg$/i.test((_src_split_ = src.split(/[?#]/)[0]) != null ? _src_split_ : '');
|
|
197
|
+
}
|
|
198
|
+
/**
|
|
199
|
+
* The URL of one derived icon of `src`, or `undefined` when `src` is not a
|
|
200
|
+
* CDN URL and so has no renderer behind it.
|
|
201
|
+
*
|
|
202
|
+
* The parameters merge into a query `src` already carries — a signed private
|
|
203
|
+
* asset's `exp`/`sig` — and their order is fixed, so one icon has one URL and
|
|
204
|
+
* one cache entry.
|
|
205
|
+
*/ export function siteIconSrc(src, spec, options = {}) {
|
|
206
|
+
if (!src || !isMediaCdnUrl(src)) return undefined;
|
|
207
|
+
const params = [
|
|
208
|
+
[
|
|
209
|
+
SITE_ICON_PARAM,
|
|
210
|
+
formatSiteIconSpec(spec)
|
|
211
|
+
]
|
|
212
|
+
];
|
|
213
|
+
if (siteIconUsesBackground(spec)) {
|
|
214
|
+
var _normalizeSiteIconBackground;
|
|
215
|
+
params.push([
|
|
216
|
+
SITE_ICON_BACKGROUND_PARAM,
|
|
217
|
+
(_normalizeSiteIconBackground = normalizeSiteIconBackground(options.background)) != null ? _normalizeSiteIconBackground : DEFAULT_SITE_ICON_BACKGROUND
|
|
218
|
+
]);
|
|
219
|
+
}
|
|
220
|
+
if (options.version && MEDIA_CDN_SEGMENT.test(options.version)) {
|
|
221
|
+
params.push([
|
|
222
|
+
SITE_ICON_VERSION_PARAM,
|
|
223
|
+
options.version
|
|
224
|
+
]);
|
|
225
|
+
}
|
|
226
|
+
const query = params.map(([key, value])=>`${key}=${value}`).join('&');
|
|
227
|
+
return `${src}${src.includes('?') ? '&' : '?'}${query}`;
|
|
228
|
+
}
|
|
229
|
+
const square = (size)=>`${size}x${size}`;
|
|
230
|
+
/**
|
|
231
|
+
* The `<link rel="icon">` set for a favicon source.
|
|
232
|
+
*
|
|
233
|
+
* Derivable: a PNG per {@link FAVICON_PNG_SIZES}, each with its real `type`
|
|
234
|
+
* and `sizes`, then the SVG itself as `sizes="any"` when the source is one —
|
|
235
|
+
* last, so a browser that draws SVG favicons prefers it and one that does not
|
|
236
|
+
* already has its PNG. Anything else is the single link it always was.
|
|
237
|
+
*/ export function siteFaviconLinks(src, facts) {
|
|
238
|
+
if (!src) return [];
|
|
239
|
+
const svg = siteIconIsSvg(src, facts);
|
|
240
|
+
const passThrough = _extends({
|
|
241
|
+
rel: 'icon',
|
|
242
|
+
href: src
|
|
243
|
+
}, svg ? {
|
|
244
|
+
type: 'image/svg+xml',
|
|
245
|
+
sizes: 'any'
|
|
246
|
+
} : {});
|
|
247
|
+
if (!siteIconDerivable(src, facts)) return [
|
|
248
|
+
passThrough
|
|
249
|
+
];
|
|
250
|
+
const version = facts == null ? void 0 : facts.contentHash;
|
|
251
|
+
return [
|
|
252
|
+
...FAVICON_PNG_SIZES.map((size)=>{
|
|
253
|
+
var _siteIconSrc;
|
|
254
|
+
return {
|
|
255
|
+
rel: 'icon',
|
|
256
|
+
href: (_siteIconSrc = siteIconSrc(src, {
|
|
257
|
+
plate: 'transparent',
|
|
258
|
+
size
|
|
259
|
+
}, {
|
|
260
|
+
version
|
|
261
|
+
})) != null ? _siteIconSrc : src,
|
|
262
|
+
type: 'image/png',
|
|
263
|
+
sizes: square(size)
|
|
264
|
+
};
|
|
265
|
+
}),
|
|
266
|
+
...svg ? [
|
|
267
|
+
passThrough
|
|
268
|
+
] : []
|
|
269
|
+
];
|
|
270
|
+
}
|
|
271
|
+
/**
|
|
272
|
+
* The `<link rel="apple-touch-icon">` set: each of
|
|
273
|
+
* {@link APPLE_TOUCH_ICON_SIZES}, flattened onto `background`, or the single
|
|
274
|
+
* pass-through link for a source with no renderer behind it.
|
|
275
|
+
*/ export function siteAppleTouchIconLinks(src, facts, background) {
|
|
276
|
+
if (!src) return [];
|
|
277
|
+
if (!siteIconDerivable(src, facts)) {
|
|
278
|
+
return [
|
|
279
|
+
{
|
|
280
|
+
rel: 'apple-touch-icon',
|
|
281
|
+
href: src
|
|
282
|
+
}
|
|
283
|
+
];
|
|
284
|
+
}
|
|
285
|
+
const version = facts == null ? void 0 : facts.contentHash;
|
|
286
|
+
return APPLE_TOUCH_ICON_SIZES.map((size)=>{
|
|
287
|
+
var _siteIconSrc;
|
|
288
|
+
return {
|
|
289
|
+
rel: 'apple-touch-icon',
|
|
290
|
+
href: (_siteIconSrc = siteIconSrc(src, {
|
|
291
|
+
plate: 'flat',
|
|
292
|
+
size
|
|
293
|
+
}, {
|
|
294
|
+
background,
|
|
295
|
+
version
|
|
296
|
+
})) != null ? _siteIconSrc : src,
|
|
297
|
+
sizes: square(size)
|
|
298
|
+
};
|
|
299
|
+
});
|
|
300
|
+
}
|
|
301
|
+
/**
|
|
302
|
+
* The manifest's whole `icons` array for one source, which the caller has
|
|
303
|
+
* already made ABSOLUTE (an installer fetches icons with no page to resolve
|
|
304
|
+
* against).
|
|
305
|
+
*
|
|
306
|
+
* Derivable: every {@link MANIFEST_ICON_SIZES} size as `purpose: "any"`, then
|
|
307
|
+
* {@link MANIFEST_MASKABLE_ICON_SIZES} as `purpose: "maskable"` on
|
|
308
|
+
* `background`, then the SVG as `sizes: "any"` when the source is one. Each
|
|
309
|
+
* `sizes` is a measurement, because the renderer draws exactly that square.
|
|
310
|
+
* Anything else is the single `sizes: "any"` entry it always was: nothing
|
|
311
|
+
* measured it, so nothing may claim a pixel size for it (AGL-2204).
|
|
312
|
+
*/ export function siteManifestIcons(src, facts, background) {
|
|
313
|
+
if (!src) return [];
|
|
314
|
+
const svg = siteIconIsSvg(src, facts);
|
|
315
|
+
const passThrough = _extends({
|
|
316
|
+
src,
|
|
317
|
+
sizes: 'any'
|
|
318
|
+
}, svg ? {
|
|
319
|
+
type: 'image/svg+xml'
|
|
320
|
+
} : {}, {
|
|
321
|
+
purpose: 'any'
|
|
322
|
+
});
|
|
323
|
+
if (!siteIconDerivable(src, facts)) return [
|
|
324
|
+
passThrough
|
|
325
|
+
];
|
|
326
|
+
const version = facts == null ? void 0 : facts.contentHash;
|
|
327
|
+
const entry = (plate, size)=>{
|
|
328
|
+
var _siteIconSrc;
|
|
329
|
+
return {
|
|
330
|
+
src: (_siteIconSrc = siteIconSrc(src, {
|
|
331
|
+
plate,
|
|
332
|
+
size
|
|
333
|
+
}, {
|
|
334
|
+
background,
|
|
335
|
+
version
|
|
336
|
+
})) != null ? _siteIconSrc : src,
|
|
337
|
+
sizes: square(size),
|
|
338
|
+
type: 'image/png',
|
|
339
|
+
purpose: plate === 'maskable' ? 'maskable' : 'any'
|
|
340
|
+
};
|
|
341
|
+
};
|
|
342
|
+
return [
|
|
343
|
+
...MANIFEST_ICON_SIZES.map((size)=>entry('transparent', size)),
|
|
344
|
+
...MANIFEST_MASKABLE_ICON_SIZES.map((size)=>entry('maskable', size)),
|
|
345
|
+
...svg ? [
|
|
346
|
+
passThrough
|
|
347
|
+
] : []
|
|
348
|
+
];
|
|
349
|
+
}
|
|
350
|
+
|
|
351
|
+
//# sourceMappingURL=site-icon-set.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../../../../libs/aglyn/src/lib/app-utils/site-icon-set.ts"],"sourcesContent":["/**\n * @license\n * Copyright 2026 Aglyn LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { MEDIA_CDN_SEGMENT } from './media-cdn-scope'\nimport { isMediaCdnUrl } from './media-ref'\n\n/**\n * Every icon a published site serves, derived from the one file its author\n * uploaded (AGL-3484).\n *\n * A site's Favicon and App icon are a single media reference each. A browser\n * tab draws 16px, iOS a 180px touch icon, an installer anything from 48px to\n * 512px plus a maskable tile — and every one of them used to download the\n * original upload, a 512×512 PNG to paint a 16px tab. This module is the\n * grammar of the derived set: which sizes exist, how each is addressed on the\n * media CDN, and which `<link>` and manifest entries describe them. The pixels\n * are drawn by `site-icon-render.ts` in `@aglyn/tenant-data-admin`, behind the\n * `?icon=` representation of `serveMediaCdn`; the tenant layout, manifest and\n * `/favicon.ico` route build their URLs here, so the three can never name a\n * size the renderer does not draw.\n *\n * ## Addressing\n *\n * A derived icon is the asset's own stable CDN URL plus three parameters:\n *\n * - `icon` — the {@link SiteIconSpec}, e.g. `png-32`, `flat-180`,\n * `maskable-512` or `ico`. Only the sizes listed below parse, so the cache\n * key space is bounded and nobody can ask the renderer for a 20000px tile.\n * - `bg` — the plate color, six hex digits, for the two plates that have one.\n * - `v` — the asset's `contentHash`. With it the response is cached for a\n * year; a DAM Replace changes the hash, so the next render names a new URL\n * and the old one is never asked for again. A stale `v` that does arrive\n * redirects to the current one.\n */\n\n/** The CDN query parameter that selects a derived icon. */\nexport const SITE_ICON_PARAM = 'icon'\n/** The plate color of a flattened or maskable icon, six hex digits. */\nexport const SITE_ICON_BACKGROUND_PARAM = 'bg'\n/** The asset's `contentHash`, which keys the year-long cache. */\nexport const SITE_ICON_VERSION_PARAM = 'v'\n\n/** Tab, bookmark and taskbar sizes, as `<link rel=\"icon\" type=\"image/png\">`. */\nexport const FAVICON_PNG_SIZES = [16, 32, 48] as const\n/** The images packed into the site's `/favicon.ico`. */\nexport const FAVICON_ICO_SIZES = [16, 32, 48] as const\n/** iPhone (180), iPad Pro (167) and iPad (152) home-screen icons. */\nexport const APPLE_TOUCH_ICON_SIZES = [180, 167, 152] as const\n/** The manifest's `purpose: \"any\"` set. */\nexport const MANIFEST_ICON_SIZES = [\n 48, 72, 96, 128, 144, 152, 192, 256, 384, 512,\n] as const\n/** The manifest's `purpose: \"maskable\"` set. */\nexport const MANIFEST_MASKABLE_ICON_SIZES = [192, 512] as const\n\n/**\n * The diameter of the maskable safe zone, as a fraction of the icon.\n *\n * The Web App Manifest spec promises only a centered circle of 40% radius\n * survives every launcher mask. A mark's box is therefore fitted inside the\n * square INSCRIBED in that circle — {@link maskableMarkSize} — so even its\n * corners stay uncropped on a circle mask.\n */\nexport const MASKABLE_SAFE_ZONE = 0.8\n\n/** The plate of a site with no theme background: white, like the manifest's. */\nexport const DEFAULT_SITE_ICON_BACKGROUND = 'ffffff'\n\n/**\n * One derived icon.\n *\n * - `transparent` — the mark center-fit on a transparent square. Favicons\n * and the manifest's `any` set.\n * - `flat` — the same, flattened onto the theme background. iOS renders\n * transparency black, so every apple-touch-icon is one of these.\n * - `maskable` — the mark inside the safe zone on the theme background.\n * - `ico` — the {@link FAVICON_ICO_SIZES} transparent PNGs in one ICO.\n */\nexport type SiteIconSpec =\n | { plate: 'transparent' | 'flat' | 'maskable'; size: number }\n | { plate: 'ico' }\n\nconst PLATE_SIZES: Record<\n Exclude<SiteIconSpec['plate'], 'ico'>,\n readonly number[]\n> = {\n transparent: [...new Set([...FAVICON_PNG_SIZES, ...MANIFEST_ICON_SIZES])],\n flat: APPLE_TOUCH_ICON_SIZES,\n maskable: MANIFEST_MASKABLE_ICON_SIZES,\n}\n\nconst PLATE_PREFIX = {\n transparent: 'png',\n flat: 'flat',\n maskable: 'maskable',\n} as const\n\n/** The spec's spelling in the `icon` parameter. */\nexport function formatSiteIconSpec(spec: SiteIconSpec): string {\n return spec.plate === 'ico' ? 'ico' : `${PLATE_PREFIX[spec.plate]}-${spec.size}`\n}\n\n/**\n * Reads the `icon` parameter back; `null` for anything this module would not\n * have written — an unknown plate, or a size outside that plate's list.\n */\nexport function parseSiteIconSpec(value: unknown): SiteIconSpec | null {\n const raw = Array.isArray(value) ? value[0] : value\n if (typeof raw !== 'string') return null\n if (raw === 'ico') return { plate: 'ico' }\n const match = /^(png|flat|maskable)-(\\d{1,4})$/.exec(raw)\n if (!match) return null\n const plate = (Object.keys(PLATE_PREFIX) as Array<keyof typeof PLATE_PREFIX>)\n .find((key) => PLATE_PREFIX[key] === match[1])\n const size = Number(match[2])\n if (!plate || !PLATE_SIZES[plate].includes(size)) return null\n return { plate, size }\n}\n\n/** Whether a spec is drawn on the theme background rather than transparency. */\nexport function siteIconUsesBackground(spec: SiteIconSpec): boolean {\n return spec.plate === 'flat' || spec.plate === 'maskable'\n}\n\n/** The served type of a derived icon. */\nexport function siteIconContentType(spec: SiteIconSpec): string {\n return spec.plate === 'ico' ? 'image/x-icon' : 'image/png'\n}\n\n/**\n * The side of the box a maskable icon's mark is fitted into: the square\n * inscribed in the {@link MASKABLE_SAFE_ZONE} circle, so no launcher mask can\n * reach any part of it.\n */\nexport function maskableMarkSize(size: number): number {\n return Math.floor((size * MASKABLE_SAFE_ZONE) / Math.SQRT2)\n}\n\nconst HEX = /^#?([0-9a-f]{3}|[0-9a-f]{6}|[0-9a-f]{8})$/i\nconst RGB = /^rgba?\\(\\s*(\\d{1,3})\\s*[, ]\\s*(\\d{1,3})\\s*[, ]\\s*(\\d{1,3})/i\n\n/**\n * A theme color as the `bg` parameter carries it: six lowercase hex digits,\n * or `undefined` for anything that is not a plain color.\n *\n * A theme's `background.default` is free CSS text. `#rgb`, `#rrggbb`,\n * `#rrggbbaa` (alpha dropped — a plate is opaque by definition) and `rgb()` /\n * `rgba()` are read; a gradient, a `var()` or a named color is not a color\n * this module can put in a URL, and the caller's default stands in.\n */\nexport function normalizeSiteIconBackground(value: unknown): string | undefined {\n if (typeof value !== 'string') return undefined\n const trimmed = value.trim()\n const hex = HEX.exec(trimmed)\n if (hex) {\n const digits = hex[1].toLowerCase()\n if (digits.length === 3) {\n return digits\n .split('')\n .map((digit) => digit + digit)\n .join('')\n }\n return digits.slice(0, 6)\n }\n const rgb = RGB.exec(trimmed)\n if (rgb) {\n const channels = rgb.slice(1, 4).map(Number)\n if (channels.some((channel) => channel > 255)) return undefined\n return channels\n .map((channel) => channel.toString(16).padStart(2, '0'))\n .join('')\n }\n return undefined\n}\n\n/**\n * What one read of the source asset's media document says, or `null` when it\n * was not read (a raw URL, or a failed read).\n */\nexport interface SiteIconSourceFacts {\n /** The upload's MIME type. */\n contentType?: string\n /** The upload's content hash — the cache key a DAM Replace changes. */\n contentHash?: string\n}\n\n/** Types `sharp` cannot decode, which therefore pass through as uploaded. */\nconst UNDERIVABLE_TYPES: ReadonlySet<string> = new Set([\n 'image/x-icon',\n 'image/vnd.microsoft.icon',\n])\n\n/**\n * Whether the derived set can be drawn from this source.\n *\n * Only an asset our CDN serves has a renderer behind it; a hotlinked or raw\n * storage URL is linked as it is, exactly as before. A known non-image or an\n * ICO (which `sharp` cannot decode) passes through too. Unknown facts derive\n * anyway: the renderer redirects to the original for anything it cannot draw,\n * so a failed read costs a hop, never a broken icon.\n */\nexport function siteIconDerivable(\n src: string | undefined | null,\n facts?: SiteIconSourceFacts | null,\n): boolean {\n if (!src || !isMediaCdnUrl(src)) return false\n const type = facts?.contentType\n return !type || siteIconSourceTypeDerivable(type)\n}\n\n/**\n * Whether the renderer can draw from an upload of this MIME type: any image\n * `sharp` decodes, SVG included (it is rasterized at each size).\n */\nexport function siteIconSourceTypeDerivable(type: unknown): boolean {\n return (\n typeof type === 'string' &&\n type.startsWith('image/') &&\n !UNDERIVABLE_TYPES.has(type)\n )\n}\n\n/** Whether the source is an SVG, which also passes through as `sizes=\"any\"`. */\nexport function siteIconIsSvg(\n src: string | undefined | null,\n facts?: SiteIconSourceFacts | null,\n): boolean {\n if (!src) return false\n if (facts?.contentType) return facts.contentType === 'image/svg+xml'\n if (isMediaCdnUrl(src)) return false\n return /\\.svg$/i.test(src.split(/[?#]/)[0] ?? '')\n}\n\n/**\n * The URL of one derived icon of `src`, or `undefined` when `src` is not a\n * CDN URL and so has no renderer behind it.\n *\n * The parameters merge into a query `src` already carries — a signed private\n * asset's `exp`/`sig` — and their order is fixed, so one icon has one URL and\n * one cache entry.\n */\nexport function siteIconSrc(\n src: string | undefined | null,\n spec: SiteIconSpec,\n options: { background?: string | null; version?: string | null } = {},\n): string | undefined {\n if (!src || !isMediaCdnUrl(src)) return undefined\n const params: Array<[string, string]> = [\n [SITE_ICON_PARAM, formatSiteIconSpec(spec)],\n ]\n if (siteIconUsesBackground(spec)) {\n params.push([\n SITE_ICON_BACKGROUND_PARAM,\n normalizeSiteIconBackground(options.background) ??\n DEFAULT_SITE_ICON_BACKGROUND,\n ])\n }\n if (options.version && MEDIA_CDN_SEGMENT.test(options.version)) {\n params.push([SITE_ICON_VERSION_PARAM, options.version])\n }\n const query = params.map(([key, value]) => `${key}=${value}`).join('&')\n return `${src}${src.includes('?') ? '&' : '?'}${query}`\n}\n\n/** One `<link>` the layout emits. */\nexport interface SiteIconLink {\n rel: 'icon' | 'apple-touch-icon'\n href: string\n type?: string\n sizes?: string\n}\n\nconst square = (size: number) => `${size}x${size}`\n\n/**\n * The `<link rel=\"icon\">` set for a favicon source.\n *\n * Derivable: a PNG per {@link FAVICON_PNG_SIZES}, each with its real `type`\n * and `sizes`, then the SVG itself as `sizes=\"any\"` when the source is one —\n * last, so a browser that draws SVG favicons prefers it and one that does not\n * already has its PNG. Anything else is the single link it always was.\n */\nexport function siteFaviconLinks(\n src: string | undefined | null,\n facts?: SiteIconSourceFacts | null,\n): SiteIconLink[] {\n if (!src) return []\n const svg = siteIconIsSvg(src, facts)\n const passThrough: SiteIconLink = {\n rel: 'icon',\n href: src,\n ...(svg ? { type: 'image/svg+xml', sizes: 'any' } : {}),\n }\n if (!siteIconDerivable(src, facts)) return [passThrough]\n const version = facts?.contentHash\n return [\n ...FAVICON_PNG_SIZES.map((size) => ({\n rel: 'icon' as const,\n href: siteIconSrc(src, { plate: 'transparent', size }, { version }) ?? src,\n type: 'image/png',\n sizes: square(size),\n })),\n ...(svg ? [passThrough] : []),\n ]\n}\n\n/**\n * The `<link rel=\"apple-touch-icon\">` set: each of\n * {@link APPLE_TOUCH_ICON_SIZES}, flattened onto `background`, or the single\n * pass-through link for a source with no renderer behind it.\n */\nexport function siteAppleTouchIconLinks(\n src: string | undefined | null,\n facts?: SiteIconSourceFacts | null,\n background?: string | null,\n): SiteIconLink[] {\n if (!src) return []\n if (!siteIconDerivable(src, facts)) {\n return [{ rel: 'apple-touch-icon', href: src }]\n }\n const version = facts?.contentHash\n return APPLE_TOUCH_ICON_SIZES.map((size) => ({\n rel: 'apple-touch-icon' as const,\n href:\n siteIconSrc(src, { plate: 'flat', size }, { background, version }) ?? src,\n sizes: square(size),\n }))\n}\n\n/** One entry of the manifest's `icons`. */\nexport interface SiteManifestIcon {\n src: string\n sizes: string\n type?: string\n purpose: 'any' | 'maskable'\n}\n\n/**\n * The manifest's whole `icons` array for one source, which the caller has\n * already made ABSOLUTE (an installer fetches icons with no page to resolve\n * against).\n *\n * Derivable: every {@link MANIFEST_ICON_SIZES} size as `purpose: \"any\"`, then\n * {@link MANIFEST_MASKABLE_ICON_SIZES} as `purpose: \"maskable\"` on\n * `background`, then the SVG as `sizes: \"any\"` when the source is one. Each\n * `sizes` is a measurement, because the renderer draws exactly that square.\n * Anything else is the single `sizes: \"any\"` entry it always was: nothing\n * measured it, so nothing may claim a pixel size for it (AGL-2204).\n */\nexport function siteManifestIcons(\n src: string | undefined | null,\n facts?: SiteIconSourceFacts | null,\n background?: string | null,\n): SiteManifestIcon[] {\n if (!src) return []\n const svg = siteIconIsSvg(src, facts)\n const passThrough: SiteManifestIcon = {\n src,\n sizes: 'any',\n ...(svg ? { type: 'image/svg+xml' } : {}),\n purpose: 'any',\n }\n if (!siteIconDerivable(src, facts)) return [passThrough]\n const version = facts?.contentHash\n const entry = (\n plate: 'transparent' | 'maskable',\n size: number,\n ): SiteManifestIcon => ({\n src: siteIconSrc(src, { plate, size }, { background, version }) ?? src,\n sizes: square(size),\n type: 'image/png',\n purpose: plate === 'maskable' ? 'maskable' : 'any',\n })\n return [\n ...MANIFEST_ICON_SIZES.map((size) => entry('transparent', size)),\n ...MANIFEST_MASKABLE_ICON_SIZES.map((size) => entry('maskable', size)),\n ...(svg ? [passThrough] : []),\n ]\n}\n"],"names":["MEDIA_CDN_SEGMENT","isMediaCdnUrl","SITE_ICON_PARAM","SITE_ICON_BACKGROUND_PARAM","SITE_ICON_VERSION_PARAM","FAVICON_PNG_SIZES","FAVICON_ICO_SIZES","APPLE_TOUCH_ICON_SIZES","MANIFEST_ICON_SIZES","MANIFEST_MASKABLE_ICON_SIZES","MASKABLE_SAFE_ZONE","DEFAULT_SITE_ICON_BACKGROUND","PLATE_SIZES","transparent","Set","flat","maskable","PLATE_PREFIX","formatSiteIconSpec","spec","plate","size","parseSiteIconSpec","value","raw","Array","isArray","match","exec","Object","keys","find","key","Number","includes","siteIconUsesBackground","siteIconContentType","maskableMarkSize","Math","floor","SQRT2","HEX","RGB","normalizeSiteIconBackground","undefined","trimmed","trim","hex","digits","toLowerCase","length","split","map","digit","join","slice","rgb","channels","some","channel","toString","padStart","UNDERIVABLE_TYPES","siteIconDerivable","src","facts","type","contentType","siteIconSourceTypeDerivable","startsWith","has","siteIconIsSvg","test","siteIconSrc","options","params","push","background","version","query","square","siteFaviconLinks","svg","passThrough","rel","href","sizes","contentHash","siteAppleTouchIconLinks","siteManifestIcons","purpose","entry"],"mappings":"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"}
|