@aglyn/plugins-ai 1.0.0-beta.143
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/LICENSE +201 -0
- package/README.md +25 -0
- package/package.json +60 -0
- package/src/index.d.ts +21 -0
- package/src/index.js +22 -0
- package/src/index.js.map +1 -0
- package/src/lib/activity/ai-activity-actions.d.ts +106 -0
- package/src/lib/activity/ai-activity-actions.js +209 -0
- package/src/lib/activity/ai-activity-actions.js.map +1 -0
- package/src/lib/activity/ai-activity.d.ts +219 -0
- package/src/lib/activity/ai-activity.js +251 -0
- package/src/lib/activity/ai-activity.js.map +1 -0
- package/src/lib/billing/ai-overage-charge.d.ts +102 -0
- package/src/lib/billing/ai-overage-charge.js +258 -0
- package/src/lib/billing/ai-overage-charge.js.map +1 -0
- package/src/lib/billing/ai-overage-close.d.ts +62 -0
- package/src/lib/billing/ai-overage-close.js +129 -0
- package/src/lib/billing/ai-overage-close.js.map +1 -0
- package/src/lib/billing/ai-overage-cutover.d.ts +63 -0
- package/src/lib/billing/ai-overage-cutover.js +114 -0
- package/src/lib/billing/ai-overage-cutover.js.map +1 -0
- package/src/lib/billing/ai-overage-events.d.ts +77 -0
- package/src/lib/billing/ai-overage-events.js +174 -0
- package/src/lib/billing/ai-overage-events.js.map +1 -0
- package/src/lib/billing/ai-overage-gate.d.ts +147 -0
- package/src/lib/billing/ai-overage-gate.js +177 -0
- package/src/lib/billing/ai-overage-gate.js.map +1 -0
- package/src/lib/billing/ai-overage-ledger.d.ts +135 -0
- package/src/lib/billing/ai-overage-ledger.js +278 -0
- package/src/lib/billing/ai-overage-ledger.js.map +1 -0
- package/src/lib/billing/ai-overage-standing-writes.d.ts +110 -0
- package/src/lib/billing/ai-overage-standing-writes.js +205 -0
- package/src/lib/billing/ai-overage-standing-writes.js.map +1 -0
- package/src/lib/billing/ai-overage-standing.d.ts +168 -0
- package/src/lib/billing/ai-overage-standing.js +215 -0
- package/src/lib/billing/ai-overage-standing.js.map +1 -0
- package/src/lib/billing/ai-overage-trigger.d.ts +30 -0
- package/src/lib/billing/ai-overage-trigger.js +76 -0
- package/src/lib/billing/ai-overage-trigger.js.map +1 -0
- package/src/lib/components/ai-allotment-editor.component.d.ts +40 -0
- package/src/lib/components/ai-allotment-editor.component.js +213 -0
- package/src/lib/components/ai-allotment-editor.component.js.map +1 -0
- package/src/lib/components/ai-assist-actions-context.d.ts +13 -0
- package/src/lib/components/ai-assist-actions-context.js +21 -0
- package/src/lib/components/ai-assist-actions-context.js.map +1 -0
- package/src/lib/components/ai-assist-provider.component.d.ts +51 -0
- package/src/lib/components/ai-assist-provider.component.js +519 -0
- package/src/lib/components/ai-assist-provider.component.js.map +1 -0
- package/src/lib/components/ai-brief-dialog.component.d.ts +56 -0
- package/src/lib/components/ai-brief-dialog.component.js +319 -0
- package/src/lib/components/ai-brief-dialog.component.js.map +1 -0
- package/src/lib/components/ai-collaborator-permissions-column.component.d.ts +32 -0
- package/src/lib/components/ai-collaborator-permissions-column.component.js +132 -0
- package/src/lib/components/ai-collaborator-permissions-column.component.js.map +1 -0
- package/src/lib/components/ai-credits-card.component.d.ts +34 -0
- package/src/lib/components/ai-credits-card.component.js +131 -0
- package/src/lib/components/ai-credits-card.component.js.map +1 -0
- package/src/lib/components/ai-credits-columns.component.d.ts +56 -0
- package/src/lib/components/ai-credits-columns.component.js +118 -0
- package/src/lib/components/ai-credits-columns.component.js.map +1 -0
- package/src/lib/components/ai-crm-email-draft.component.d.ts +17 -0
- package/src/lib/components/ai-crm-email-draft.component.js +159 -0
- package/src/lib/components/ai-crm-email-draft.component.js.map +1 -0
- package/src/lib/components/ai-crm-import-mapping.component.d.ts +20 -0
- package/src/lib/components/ai-crm-import-mapping.component.js +167 -0
- package/src/lib/components/ai-crm-import-mapping.component.js.map +1 -0
- package/src/lib/components/ai-crm-record-card.component.d.ts +27 -0
- package/src/lib/components/ai-crm-record-card.component.js +263 -0
- package/src/lib/components/ai-crm-record-card.component.js.map +1 -0
- package/src/lib/components/ai-describe-automation.component.d.ts +31 -0
- package/src/lib/components/ai-describe-automation.component.js +226 -0
- package/src/lib/components/ai-describe-automation.component.js.map +1 -0
- package/src/lib/components/ai-describe-button.component.d.ts +39 -0
- package/src/lib/components/ai-describe-button.component.js +87 -0
- package/src/lib/components/ai-describe-button.component.js.map +1 -0
- package/src/lib/components/ai-describe-page.component.d.ts +26 -0
- package/src/lib/components/ai-describe-page.component.js +18 -0
- package/src/lib/components/ai-describe-page.component.js.map +1 -0
- package/src/lib/components/ai-experiment-cards.component.d.ts +75 -0
- package/src/lib/components/ai-experiment-cards.component.js +573 -0
- package/src/lib/components/ai-experiment-cards.component.js.map +1 -0
- package/src/lib/components/ai-explain-automation.component.d.ts +31 -0
- package/src/lib/components/ai-explain-automation.component.js +265 -0
- package/src/lib/components/ai-explain-automation.component.js.map +1 -0
- package/src/lib/components/ai-insight-dialog.component.d.ts +37 -0
- package/src/lib/components/ai-insight-dialog.component.js +441 -0
- package/src/lib/components/ai-insight-dialog.component.js.map +1 -0
- package/src/lib/components/ai-job-plan.component.d.ts +46 -0
- package/src/lib/components/ai-job-plan.component.js +192 -0
- package/src/lib/components/ai-job-plan.component.js.map +1 -0
- package/src/lib/components/ai-model-selector.component.d.ts +21 -0
- package/src/lib/components/ai-model-selector.component.js +109 -0
- package/src/lib/components/ai-model-selector.component.js.map +1 -0
- package/src/lib/components/ai-page-brief-dialog.component.d.ts +29 -0
- package/src/lib/components/ai-page-brief-dialog.component.js +27 -0
- package/src/lib/components/ai-page-brief-dialog.component.js.map +1 -0
- package/src/lib/components/ai-permissions-on-host.component.d.ts +55 -0
- package/src/lib/components/ai-permissions-on-host.component.js +91 -0
- package/src/lib/components/ai-permissions-on-host.component.js.map +1 -0
- package/src/lib/components/ai-product-copy-card.component.d.ts +25 -0
- package/src/lib/components/ai-product-copy-card.component.js +328 -0
- package/src/lib/components/ai-product-copy-card.component.js.map +1 -0
- package/src/lib/components/ai-product-import-option.component.d.ts +14 -0
- package/src/lib/components/ai-product-import-option.component.js +58 -0
- package/src/lib/components/ai-product-import-option.component.js.map +1 -0
- package/src/lib/components/ai-products-hub-card.component.d.ts +15 -0
- package/src/lib/components/ai-products-hub-card.component.js +418 -0
- package/src/lib/components/ai-products-hub-card.component.js.map +1 -0
- package/src/lib/components/ai-products-proposals.component.d.ts +19 -0
- package/src/lib/components/ai-products-proposals.component.js +547 -0
- package/src/lib/components/ai-products-proposals.component.js.map +1 -0
- package/src/lib/components/ai-save-as-component.component.d.ts +38 -0
- package/src/lib/components/ai-save-as-component.component.js +231 -0
- package/src/lib/components/ai-save-as-component.component.js.map +1 -0
- package/src/lib/components/ai-seo-audit-card.component.d.ts +9 -0
- package/src/lib/components/ai-seo-audit-card.component.js +620 -0
- package/src/lib/components/ai-seo-audit-card.component.js.map +1 -0
- package/src/lib/components/ai-seo-fields-card.component.d.ts +10 -0
- package/src/lib/components/ai-seo-fields-card.component.js +453 -0
- package/src/lib/components/ai-seo-fields-card.component.js.map +1 -0
- package/src/lib/components/ai-site-batch-card.component.d.ts +32 -0
- package/src/lib/components/ai-site-batch-card.component.js +531 -0
- package/src/lib/components/ai-site-batch-card.component.js.map +1 -0
- package/src/lib/components/ai-site-seo-start-card.component.d.ts +26 -0
- package/src/lib/components/ai-site-seo-start-card.component.js +178 -0
- package/src/lib/components/ai-site-seo-start-card.component.js.map +1 -0
- package/src/lib/components/ai-site-start-card.component.d.ts +19 -0
- package/src/lib/components/ai-site-start-card.component.js +348 -0
- package/src/lib/components/ai-site-start-card.component.js.map +1 -0
- package/src/lib/components/ai-template-collection-field.component.d.ts +32 -0
- package/src/lib/components/ai-template-collection-field.component.js +63 -0
- package/src/lib/components/ai-template-collection-field.component.js.map +1 -0
- package/src/lib/components/ai-theme-proposal-card.component.d.ts +6 -0
- package/src/lib/components/ai-theme-proposal-card.component.js +619 -0
- package/src/lib/components/ai-theme-proposal-card.component.js.map +1 -0
- package/src/lib/components/ai-usage-strip.component.d.ts +27 -0
- package/src/lib/components/ai-usage-strip.component.js +145 -0
- package/src/lib/components/ai-usage-strip.component.js.map +1 -0
- package/src/lib/components/assist-edit-canvas.d.ts +169 -0
- package/src/lib/components/assist-edit-canvas.js +636 -0
- package/src/lib/components/assist-edit-canvas.js.map +1 -0
- package/src/lib/components/assist-edit-card.component.d.ts +16 -0
- package/src/lib/components/assist-edit-card.component.js +181 -0
- package/src/lib/components/assist-edit-card.component.js.map +1 -0
- package/src/lib/components/assist-jobs-drawer.component.d.ts +72 -0
- package/src/lib/components/assist-jobs-drawer.component.js +626 -0
- package/src/lib/components/assist-jobs-drawer.component.js.map +1 -0
- package/src/lib/components/assist-panel.component.d.ts +136 -0
- package/src/lib/components/assist-panel.component.js +1099 -0
- package/src/lib/components/assist-panel.component.js.map +1 -0
- package/src/lib/components/assist-signals-page.component.d.ts +3 -0
- package/src/lib/components/assist-signals-page.component.js +1017 -0
- package/src/lib/components/assist-signals-page.component.js.map +1 -0
- package/src/lib/components/besigner-ai-controls.component.d.ts +29 -0
- package/src/lib/components/besigner-ai-controls.component.js +81 -0
- package/src/lib/components/besigner-ai-controls.component.js.map +1 -0
- package/src/lib/components/billing-ai-allotments.component.d.ts +36 -0
- package/src/lib/components/billing-ai-allotments.component.js +486 -0
- package/src/lib/components/billing-ai-allotments.component.js.map +1 -0
- package/src/lib/components/billing-ai-top-users.component.d.ts +44 -0
- package/src/lib/components/billing-ai-top-users.component.js +304 -0
- package/src/lib/components/billing-ai-top-users.component.js.map +1 -0
- package/src/lib/components/billing-assist-overage-card.component.d.ts +69 -0
- package/src/lib/components/billing-assist-overage-card.component.js +437 -0
- package/src/lib/components/billing-assist-overage-card.component.js.map +1 -0
- package/src/lib/components/host-ai-allotments.component.d.ts +40 -0
- package/src/lib/components/host-ai-allotments.component.js +239 -0
- package/src/lib/components/host-ai-allotments.component.js.map +1 -0
- package/src/lib/components/member-ai-allotment-card.component.d.ts +28 -0
- package/src/lib/components/member-ai-allotment-card.component.js +172 -0
- package/src/lib/components/member-ai-allotment-card.component.js.map +1 -0
- package/src/lib/components/member-ai-usage-card.component.d.ts +28 -0
- package/src/lib/components/member-ai-usage-card.component.js +240 -0
- package/src/lib/components/member-ai-usage-card.component.js.map +1 -0
- package/src/lib/components/staff-org-ai-card.component.d.ts +17 -0
- package/src/lib/components/staff-org-ai-card.component.js +739 -0
- package/src/lib/components/staff-org-ai-card.component.js.map +1 -0
- package/src/lib/components/staff-org-usage-ai-columns.component.d.ts +41 -0
- package/src/lib/components/staff-org-usage-ai-columns.component.js +65 -0
- package/src/lib/components/staff-org-usage-ai-columns.component.js.map +1 -0
- package/src/lib/components/staff-orgs-ai-spend-column.component.d.ts +28 -0
- package/src/lib/components/staff-orgs-ai-spend-column.component.js +89 -0
- package/src/lib/components/staff-orgs-ai-spend-column.component.js.map +1 -0
- package/src/lib/components/staff-user-ai-usage-card.component.d.ts +27 -0
- package/src/lib/components/staff-user-ai-usage-card.component.js +183 -0
- package/src/lib/components/staff-user-ai-usage-card.component.js.map +1 -0
- package/src/lib/components/use-ai-allotments.d.ts +49 -0
- package/src/lib/components/use-ai-allotments.js +171 -0
- package/src/lib/components/use-ai-allotments.js.map +1 -0
- package/src/lib/components/use-ai-crm-answer.d.ts +50 -0
- package/src/lib/components/use-ai-crm-answer.js +220 -0
- package/src/lib/components/use-ai-crm-answer.js.map +1 -0
- package/src/lib/components/use-ai-job-run.d.ts +51 -0
- package/src/lib/components/use-ai-job-run.js +176 -0
- package/src/lib/components/use-ai-job-run.js.map +1 -0
- package/src/lib/components/use-ai-model-choice.d.ts +47 -0
- package/src/lib/components/use-ai-model-choice.js +150 -0
- package/src/lib/components/use-ai-model-choice.js.map +1 -0
- package/src/lib/components/use-ai-products-jobs.d.ts +36 -0
- package/src/lib/components/use-ai-products-jobs.js +190 -0
- package/src/lib/components/use-ai-products-jobs.js.map +1 -0
- package/src/lib/components/use-ai-usage-meter.d.ts +11 -0
- package/src/lib/components/use-ai-usage-meter.js +96 -0
- package/src/lib/components/use-ai-usage-meter.js.map +1 -0
- package/src/lib/components/use-org-ai-usage.d.ts +42 -0
- package/src/lib/components/use-org-ai-usage.js +181 -0
- package/src/lib/components/use-org-ai-usage.js.map +1 -0
- package/src/lib/components/use-staff-orgs-ai-spend.d.ts +18 -0
- package/src/lib/components/use-staff-orgs-ai-spend.js +127 -0
- package/src/lib/components/use-staff-orgs-ai-spend.js.map +1 -0
- package/src/lib/constants.d.ts +24 -0
- package/src/lib/constants.js +23 -0
- package/src/lib/constants.js.map +1 -0
- package/src/lib/declarations.d.ts +48 -0
- package/src/lib/declarations.js +129 -0
- package/src/lib/declarations.js.map +1 -0
- package/src/lib/declarations.server.d.ts +35 -0
- package/src/lib/declarations.server.js +138 -0
- package/src/lib/declarations.server.js.map +1 -0
- package/src/lib/insights/ai-figure-readers.d.ts +90 -0
- package/src/lib/insights/ai-figure-readers.js +863 -0
- package/src/lib/insights/ai-figure-readers.js.map +1 -0
- package/src/lib/insights/ai-insight-digest.d.ts +165 -0
- package/src/lib/insights/ai-insight-digest.js +363 -0
- package/src/lib/insights/ai-insight-digest.js.map +1 -0
- package/src/lib/insights/ai-insight-readers.d.ts +71 -0
- package/src/lib/insights/ai-insight-readers.js +141 -0
- package/src/lib/insights/ai-insight-readers.js.map +1 -0
- package/src/lib/jobs/ai-crm-access.d.ts +61 -0
- package/src/lib/jobs/ai-crm-access.js +94 -0
- package/src/lib/jobs/ai-crm-access.js.map +1 -0
- package/src/lib/jobs/ai-email-bindings.d.ts +97 -0
- package/src/lib/jobs/ai-email-bindings.js +147 -0
- package/src/lib/jobs/ai-email-bindings.js.map +1 -0
- package/src/lib/jobs/ai-job-admission.d.ts +82 -0
- package/src/lib/jobs/ai-job-admission.js +45 -0
- package/src/lib/jobs/ai-job-admission.js.map +1 -0
- package/src/lib/jobs/ai-job-budget.d.ts +167 -0
- package/src/lib/jobs/ai-job-budget.js +161 -0
- package/src/lib/jobs/ai-job-budget.js.map +1 -0
- package/src/lib/jobs/ai-job-campaign-step.d.ts +108 -0
- package/src/lib/jobs/ai-job-campaign-step.js +340 -0
- package/src/lib/jobs/ai-job-campaign-step.js.map +1 -0
- package/src/lib/jobs/ai-job-component-checks.d.ts +74 -0
- package/src/lib/jobs/ai-job-component-checks.js +442 -0
- package/src/lib/jobs/ai-job-component-checks.js.map +1 -0
- package/src/lib/jobs/ai-job-component-step.d.ts +75 -0
- package/src/lib/jobs/ai-job-component-step.js +262 -0
- package/src/lib/jobs/ai-job-component-step.js.map +1 -0
- package/src/lib/jobs/ai-job-crm-step.d.ts +192 -0
- package/src/lib/jobs/ai-job-crm-step.js +734 -0
- package/src/lib/jobs/ai-job-crm-step.js.map +1 -0
- package/src/lib/jobs/ai-job-draft-ids.d.ts +62 -0
- package/src/lib/jobs/ai-job-draft-ids.js +132 -0
- package/src/lib/jobs/ai-job-draft-ids.js.map +1 -0
- package/src/lib/jobs/ai-job-drafts.d.ts +304 -0
- package/src/lib/jobs/ai-job-drafts.js +557 -0
- package/src/lib/jobs/ai-job-drafts.js.map +1 -0
- package/src/lib/jobs/ai-job-email-step.d.ts +195 -0
- package/src/lib/jobs/ai-job-email-step.js +547 -0
- package/src/lib/jobs/ai-job-email-step.js.map +1 -0
- package/src/lib/jobs/ai-job-experiment-step.d.ts +105 -0
- package/src/lib/jobs/ai-job-experiment-step.js +445 -0
- package/src/lib/jobs/ai-job-experiment-step.js.map +1 -0
- package/src/lib/jobs/ai-job-form-step.d.ts +250 -0
- package/src/lib/jobs/ai-job-form-step.js +634 -0
- package/src/lib/jobs/ai-job-form-step.js.map +1 -0
- package/src/lib/jobs/ai-job-generation.d.ts +114 -0
- package/src/lib/jobs/ai-job-generation.js +384 -0
- package/src/lib/jobs/ai-job-generation.js.map +1 -0
- package/src/lib/jobs/ai-job-insight-budget.d.ts +41 -0
- package/src/lib/jobs/ai-job-insight-budget.js +46 -0
- package/src/lib/jobs/ai-job-insight-budget.js.map +1 -0
- package/src/lib/jobs/ai-job-insight-step.d.ts +58 -0
- package/src/lib/jobs/ai-job-insight-step.js +350 -0
- package/src/lib/jobs/ai-job-insight-step.js.map +1 -0
- package/src/lib/jobs/ai-job-layout-step.d.ts +103 -0
- package/src/lib/jobs/ai-job-layout-step.js +340 -0
- package/src/lib/jobs/ai-job-layout-step.js.map +1 -0
- package/src/lib/jobs/ai-job-page-budget.d.ts +57 -0
- package/src/lib/jobs/ai-job-page-budget.js +60 -0
- package/src/lib/jobs/ai-job-page-budget.js.map +1 -0
- package/src/lib/jobs/ai-job-page-sections.d.ts +150 -0
- package/src/lib/jobs/ai-job-page-sections.js +450 -0
- package/src/lib/jobs/ai-job-page-sections.js.map +1 -0
- package/src/lib/jobs/ai-job-page-step.d.ts +198 -0
- package/src/lib/jobs/ai-job-page-step.js +667 -0
- package/src/lib/jobs/ai-job-page-step.js.map +1 -0
- package/src/lib/jobs/ai-job-plan-conformance.d.ts +107 -0
- package/src/lib/jobs/ai-job-plan-conformance.js +164 -0
- package/src/lib/jobs/ai-job-plan-conformance.js.map +1 -0
- package/src/lib/jobs/ai-job-plan-step.d.ts +196 -0
- package/src/lib/jobs/ai-job-plan-step.js +458 -0
- package/src/lib/jobs/ai-job-plan-step.js.map +1 -0
- package/src/lib/jobs/ai-job-plugin-drafts.d.ts +76 -0
- package/src/lib/jobs/ai-job-plugin-drafts.js +91 -0
- package/src/lib/jobs/ai-job-plugin-drafts.js.map +1 -0
- package/src/lib/jobs/ai-job-products-step.d.ts +106 -0
- package/src/lib/jobs/ai-job-products-step.js +436 -0
- package/src/lib/jobs/ai-job-products-step.js.map +1 -0
- package/src/lib/jobs/ai-job-seo-budget.d.ts +52 -0
- package/src/lib/jobs/ai-job-seo-budget.js +63 -0
- package/src/lib/jobs/ai-job-seo-budget.js.map +1 -0
- package/src/lib/jobs/ai-job-seo-step.d.ts +145 -0
- package/src/lib/jobs/ai-job-seo-step.js +809 -0
- package/src/lib/jobs/ai-job-seo-step.js.map +1 -0
- package/src/lib/jobs/ai-job-site-step.d.ts +252 -0
- package/src/lib/jobs/ai-job-site-step.js +538 -0
- package/src/lib/jobs/ai-job-site-step.js.map +1 -0
- package/src/lib/jobs/ai-job-template-step.d.ts +105 -0
- package/src/lib/jobs/ai-job-template-step.js +391 -0
- package/src/lib/jobs/ai-job-template-step.js.map +1 -0
- package/src/lib/jobs/ai-job-text-step.d.ts +125 -0
- package/src/lib/jobs/ai-job-text-step.js +128 -0
- package/src/lib/jobs/ai-job-text-step.js.map +1 -0
- package/src/lib/jobs/ai-job-theme-budget.d.ts +38 -0
- package/src/lib/jobs/ai-job-theme-budget.js +43 -0
- package/src/lib/jobs/ai-job-theme-budget.js.map +1 -0
- package/src/lib/jobs/ai-job-theme-step.d.ts +115 -0
- package/src/lib/jobs/ai-job-theme-step.js +337 -0
- package/src/lib/jobs/ai-job-theme-step.js.map +1 -0
- package/src/lib/jobs/ai-job-workflow-step.d.ts +139 -0
- package/src/lib/jobs/ai-job-workflow-step.js +530 -0
- package/src/lib/jobs/ai-job-workflow-step.js.map +1 -0
- package/src/lib/jobs/ai-jobs-beat.d.ts +78 -0
- package/src/lib/jobs/ai-jobs-beat.js +93 -0
- package/src/lib/jobs/ai-jobs-beat.js.map +1 -0
- package/src/lib/jobs/ai-jobs-pause.d.ts +38 -0
- package/src/lib/jobs/ai-jobs-pause.js +45 -0
- package/src/lib/jobs/ai-jobs-pause.js.map +1 -0
- package/src/lib/jobs/ai-jobs.d.ts +558 -0
- package/src/lib/jobs/ai-jobs.js +1410 -0
- package/src/lib/jobs/ai-jobs.js.map +1 -0
- package/src/lib/jobs/ai-media-asset-server.d.ts +34 -0
- package/src/lib/jobs/ai-media-asset-server.js +34 -0
- package/src/lib/jobs/ai-media-asset-server.js.map +1 -0
- package/src/lib/jobs/ai-media-asset.d.ts +59 -0
- package/src/lib/jobs/ai-media-asset.js +86 -0
- package/src/lib/jobs/ai-media-asset.js.map +1 -0
- package/src/lib/jobs/ai-product-image.d.ts +78 -0
- package/src/lib/jobs/ai-product-image.js +113 -0
- package/src/lib/jobs/ai-product-image.js.map +1 -0
- package/src/lib/jobs/ai-theme-brand-inputs.d.ts +125 -0
- package/src/lib/jobs/ai-theme-brand-inputs.js +378 -0
- package/src/lib/jobs/ai-theme-brand-inputs.js.map +1 -0
- package/src/lib/jobs/ai-theme-brand-server.d.ts +33 -0
- package/src/lib/jobs/ai-theme-brand-server.js +33 -0
- package/src/lib/jobs/ai-theme-brand-server.js.map +1 -0
- package/src/lib/jobs/ai-workflow-records.d.ts +84 -0
- package/src/lib/jobs/ai-workflow-records.js +158 -0
- package/src/lib/jobs/ai-workflow-records.js.map +1 -0
- package/src/lib/jobs/fixtures/ai-free-page-built-recording.d.ts +31 -0
- package/src/lib/jobs/fixtures/ai-free-page-built-recording.js +367 -0
- package/src/lib/jobs/fixtures/ai-free-page-built-recording.js.map +1 -0
- package/src/lib/jobs/fixtures/ai-free-page-recording.d.ts +69 -0
- package/src/lib/jobs/fixtures/ai-free-page-recording.js +442 -0
- package/src/lib/jobs/fixtures/ai-free-page-recording.js.map +1 -0
- package/src/lib/jobs/fixtures/ai-page-briefs.d.ts +146 -0
- package/src/lib/jobs/fixtures/ai-page-briefs.js +1850 -0
- package/src/lib/jobs/fixtures/ai-page-briefs.js.map +1 -0
- package/src/lib/model/ai-allotments.d.ts +208 -0
- package/src/lib/model/ai-allotments.js +269 -0
- package/src/lib/model/ai-allotments.js.map +1 -0
- package/src/lib/model/ai-automation-draft.d.ts +74 -0
- package/src/lib/model/ai-automation-draft.js +310 -0
- package/src/lib/model/ai-automation-draft.js.map +1 -0
- package/src/lib/model/ai-automation-outline.d.ts +50 -0
- package/src/lib/model/ai-automation-outline.js +262 -0
- package/src/lib/model/ai-automation-outline.js.map +1 -0
- package/src/lib/model/ai-build-plan.d.ts +197 -0
- package/src/lib/model/ai-build-plan.js +438 -0
- package/src/lib/model/ai-build-plan.js.map +1 -0
- package/src/lib/model/ai-crm.d.ts +237 -0
- package/src/lib/model/ai-crm.js +225 -0
- package/src/lib/model/ai-crm.js.map +1 -0
- package/src/lib/model/ai-experiment-proposal.d.ts +68 -0
- package/src/lib/model/ai-experiment-proposal.js +146 -0
- package/src/lib/model/ai-experiment-proposal.js.map +1 -0
- package/src/lib/model/ai-experiment.d.ts +309 -0
- package/src/lib/model/ai-experiment.js +395 -0
- package/src/lib/model/ai-experiment.js.map +1 -0
- package/src/lib/model/ai-insight.d.ts +178 -0
- package/src/lib/model/ai-insight.js +201 -0
- package/src/lib/model/ai-insight.js.map +1 -0
- package/src/lib/model/ai-jobs.types.d.ts +412 -0
- package/src/lib/model/ai-jobs.types.js +42 -0
- package/src/lib/model/ai-jobs.types.js.map +1 -0
- package/src/lib/model/ai-page-job.d.ts +92 -0
- package/src/lib/model/ai-page-job.js +159 -0
- package/src/lib/model/ai-page-job.js.map +1 -0
- package/src/lib/model/ai-permissions.d.ts +49 -0
- package/src/lib/model/ai-permissions.js +97 -0
- package/src/lib/model/ai-permissions.js.map +1 -0
- package/src/lib/model/ai-plan-capabilities.d.ts +139 -0
- package/src/lib/model/ai-plan-capabilities.js +149 -0
- package/src/lib/model/ai-plan-capabilities.js.map +1 -0
- package/src/lib/model/ai-products.d.ts +251 -0
- package/src/lib/model/ai-products.js +253 -0
- package/src/lib/model/ai-products.js.map +1 -0
- package/src/lib/model/ai-seo.d.ts +208 -0
- package/src/lib/model/ai-seo.js +150 -0
- package/src/lib/model/ai-seo.js.map +1 -0
- package/src/lib/model/ai-site-inventory.d.ts +164 -0
- package/src/lib/model/ai-site-inventory.js +145 -0
- package/src/lib/model/ai-site-inventory.js.map +1 -0
- package/src/lib/model/ai-site-job.d.ts +247 -0
- package/src/lib/model/ai-site-job.js +314 -0
- package/src/lib/model/ai-site-job.js.map +1 -0
- package/src/lib/model/ai-site-start-seo.d.ts +103 -0
- package/src/lib/model/ai-site-start-seo.js +154 -0
- package/src/lib/model/ai-site-start-seo.js.map +1 -0
- package/src/lib/model/ai-site-start.d.ts +122 -0
- package/src/lib/model/ai-site-start.js +159 -0
- package/src/lib/model/ai-site-start.js.map +1 -0
- package/src/lib/model/ai-site-switch.d.ts +56 -0
- package/src/lib/model/ai-site-switch.js +73 -0
- package/src/lib/model/ai-site-switch.js.map +1 -0
- package/src/lib/model/ai-storefront-claims.d.ts +70 -0
- package/src/lib/model/ai-storefront-claims.js +130 -0
- package/src/lib/model/ai-storefront-claims.js.map +1 -0
- package/src/lib/model/ai-template-subjects.d.ts +82 -0
- package/src/lib/model/ai-template-subjects.js +136 -0
- package/src/lib/model/ai-template-subjects.js.map +1 -0
- package/src/lib/model/ai-theme-proposal.d.ts +210 -0
- package/src/lib/model/ai-theme-proposal.js +506 -0
- package/src/lib/model/ai-theme-proposal.js.map +1 -0
- package/src/lib/model/ai-tokens.d.ts +96 -0
- package/src/lib/model/ai-tokens.js +117 -0
- package/src/lib/model/ai-tokens.js.map +1 -0
- package/src/lib/model/ai-usage-by-user.d.ts +120 -0
- package/src/lib/model/ai-usage-by-user.js +139 -0
- package/src/lib/model/ai-usage-by-user.js.map +1 -0
- package/src/lib/model/ai-workflow-job.d.ts +111 -0
- package/src/lib/model/ai-workflow-job.js +183 -0
- package/src/lib/model/ai-workflow-job.js.map +1 -0
- package/src/lib/model/assist-edit.d.ts +261 -0
- package/src/lib/model/assist-edit.js +175 -0
- package/src/lib/model/assist-edit.js.map +1 -0
- package/src/lib/plugin-config.d.ts +33 -0
- package/src/lib/plugin-config.js +118 -0
- package/src/lib/plugin-config.js.map +1 -0
- package/src/lib/plugin.d.ts +30 -0
- package/src/lib/plugin.js +525 -0
- package/src/lib/plugin.js.map +1 -0
- package/src/lib/providers/anthropic.d.ts +84 -0
- package/src/lib/providers/anthropic.js +432 -0
- package/src/lib/providers/anthropic.js.map +1 -0
- package/src/lib/providers/catalog.d.ts +197 -0
- package/src/lib/providers/catalog.js +312 -0
- package/src/lib/providers/catalog.js.map +1 -0
- package/src/lib/providers/contract.d.ts +464 -0
- package/src/lib/providers/contract.js +274 -0
- package/src/lib/providers/contract.js.map +1 -0
- package/src/lib/providers/model-choice.d.ts +119 -0
- package/src/lib/providers/model-choice.js +416 -0
- package/src/lib/providers/model-choice.js.map +1 -0
- package/src/lib/providers/openai-compatible.d.ts +58 -0
- package/src/lib/providers/openai-compatible.js +361 -0
- package/src/lib/providers/openai-compatible.js.map +1 -0
- package/src/lib/providers/registry.d.ts +49 -0
- package/src/lib/providers/registry.js +71 -0
- package/src/lib/providers/registry.js.map +1 -0
- package/src/lib/providers/routing.d.ts +98 -0
- package/src/lib/providers/routing.js +450 -0
- package/src/lib/providers/routing.js.map +1 -0
- package/src/lib/runtime/ai-abuse-guards.d.ts +113 -0
- package/src/lib/runtime/ai-abuse-guards.js +148 -0
- package/src/lib/runtime/ai-abuse-guards.js.map +1 -0
- package/src/lib/runtime/ai-component-bindings.d.ts +67 -0
- package/src/lib/runtime/ai-component-bindings.js +106 -0
- package/src/lib/runtime/ai-component-bindings.js.map +1 -0
- package/src/lib/runtime/ai-device-audit.d.ts +109 -0
- package/src/lib/runtime/ai-device-audit.js +97 -0
- package/src/lib/runtime/ai-device-audit.js.map +1 -0
- package/src/lib/runtime/ai-doctrine-validators.d.ts +720 -0
- package/src/lib/runtime/ai-doctrine-validators.js +3133 -0
- package/src/lib/runtime/ai-doctrine-validators.js.map +1 -0
- package/src/lib/runtime/ai-doctrine.d.ts +372 -0
- package/src/lib/runtime/ai-doctrine.js +944 -0
- package/src/lib/runtime/ai-doctrine.js.map +1 -0
- package/src/lib/runtime/ai-eval-live.d.ts +321 -0
- package/src/lib/runtime/ai-eval-live.js +1257 -0
- package/src/lib/runtime/ai-eval-live.js.map +1 -0
- package/src/lib/runtime/ai-eval-memory-firestore.d.ts +51 -0
- package/src/lib/runtime/ai-eval-memory-firestore.js +183 -0
- package/src/lib/runtime/ai-eval-memory-firestore.js.map +1 -0
- package/src/lib/runtime/ai-eval.d.ts +441 -0
- package/src/lib/runtime/ai-eval.js +1151 -0
- package/src/lib/runtime/ai-eval.js.map +1 -0
- package/src/lib/runtime/ai-gate.d.ts +130 -0
- package/src/lib/runtime/ai-gate.js +272 -0
- package/src/lib/runtime/ai-gate.js.map +1 -0
- package/src/lib/runtime/ai-generation-bounds.d.ts +24 -0
- package/src/lib/runtime/ai-generation-bounds.js +23 -0
- package/src/lib/runtime/ai-generation-bounds.js.map +1 -0
- package/src/lib/runtime/ai-insight-check.d.ts +76 -0
- package/src/lib/runtime/ai-insight-check.js +281 -0
- package/src/lib/runtime/ai-insight-check.js.map +1 -0
- package/src/lib/runtime/ai-node-tree.d.ts +181 -0
- package/src/lib/runtime/ai-node-tree.js +931 -0
- package/src/lib/runtime/ai-node-tree.js.map +1 -0
- package/src/lib/runtime/ai-page-links.d.ts +79 -0
- package/src/lib/runtime/ai-page-links.js +135 -0
- package/src/lib/runtime/ai-page-links.js.map +1 -0
- package/src/lib/runtime/ai-palette.d.ts +252 -0
- package/src/lib/runtime/ai-palette.generated.d.ts +34 -0
- package/src/lib/runtime/ai-palette.generated.js +5263 -0
- package/src/lib/runtime/ai-palette.generated.js.map +1 -0
- package/src/lib/runtime/ai-palette.js +187 -0
- package/src/lib/runtime/ai-palette.js.map +1 -0
- package/src/lib/runtime/ai-products-generation.d.ts +107 -0
- package/src/lib/runtime/ai-products-generation.js +250 -0
- package/src/lib/runtime/ai-products-generation.js.map +1 -0
- package/src/lib/runtime/ai-repeated-items.d.ts +95 -0
- package/src/lib/runtime/ai-repeated-items.js +397 -0
- package/src/lib/runtime/ai-repeated-items.js.map +1 -0
- package/src/lib/runtime/ai-runtime.d.ts +148 -0
- package/src/lib/runtime/ai-runtime.js +237 -0
- package/src/lib/runtime/ai-runtime.js.map +1 -0
- package/src/lib/runtime/ai-template-examples.d.ts +71 -0
- package/src/lib/runtime/ai-template-examples.js +135 -0
- package/src/lib/runtime/ai-template-examples.js.map +1 -0
- package/src/lib/runtime/assist-answer-cache.d.ts +80 -0
- package/src/lib/runtime/assist-answer-cache.js +184 -0
- package/src/lib/runtime/assist-answer-cache.js.map +1 -0
- package/src/lib/runtime/seo-audit.d.ts +93 -0
- package/src/lib/runtime/seo-audit.js +260 -0
- package/src/lib/runtime/seo-audit.js.map +1 -0
- package/src/lib/runtime/seo-content-fixes.d.ts +41 -0
- package/src/lib/runtime/seo-content-fixes.js +168 -0
- package/src/lib/runtime/seo-content-fixes.js.map +1 -0
- package/src/lib/runtime/seo-fields.d.ts +152 -0
- package/src/lib/runtime/seo-fields.js +215 -0
- package/src/lib/runtime/seo-fields.js.map +1 -0
- package/src/lib/runtime/seo-page-facts.d.ts +61 -0
- package/src/lib/runtime/seo-page-facts.js +150 -0
- package/src/lib/runtime/seo-page-facts.js.map +1 -0
- package/src/lib/runtime/site-inventory.d.ts +63 -0
- package/src/lib/runtime/site-inventory.js +230 -0
- package/src/lib/runtime/site-inventory.js.map +1 -0
- package/src/lib/server/ai-admin-org.d.ts +33 -0
- package/src/lib/server/ai-admin-org.js +381 -0
- package/src/lib/server/ai-admin-org.js.map +1 -0
- package/src/lib/server/ai-admin-orgs-spend.d.ts +40 -0
- package/src/lib/server/ai-admin-orgs-spend.js +129 -0
- package/src/lib/server/ai-admin-orgs-spend.js.map +1 -0
- package/src/lib/server/ai-admin-overage.d.ts +19 -0
- package/src/lib/server/ai-admin-overage.js +246 -0
- package/src/lib/server/ai-admin-overage.js.map +1 -0
- package/src/lib/server/ai-admin-signals.d.ts +34 -0
- package/src/lib/server/ai-admin-signals.js +330 -0
- package/src/lib/server/ai-admin-signals.js.map +1 -0
- package/src/lib/server/ai-admin-user.d.ts +27 -0
- package/src/lib/server/ai-admin-user.js +128 -0
- package/src/lib/server/ai-admin-user.js.map +1 -0
- package/src/lib/server/ai-allotments.d.ts +27 -0
- package/src/lib/server/ai-allotments.js +544 -0
- package/src/lib/server/ai-allotments.js.map +1 -0
- package/src/lib/server/ai-assist-prompts.d.ts +102 -0
- package/src/lib/server/ai-assist-prompts.js +207 -0
- package/src/lib/server/ai-assist-prompts.js.map +1 -0
- package/src/lib/server/ai-assist.d.ts +119 -0
- package/src/lib/server/ai-assist.js +517 -0
- package/src/lib/server/ai-assist.js.map +1 -0
- package/src/lib/server/ai-crm-answer.d.ts +30 -0
- package/src/lib/server/ai-crm-answer.js +98 -0
- package/src/lib/server/ai-crm-answer.js.map +1 -0
- package/src/lib/server/ai-generate-component.d.ts +111 -0
- package/src/lib/server/ai-generate-component.js +643 -0
- package/src/lib/server/ai-generate-component.js.map +1 -0
- package/src/lib/server/ai-host-permissions.d.ts +46 -0
- package/src/lib/server/ai-host-permissions.js +204 -0
- package/src/lib/server/ai-host-permissions.js.map +1 -0
- package/src/lib/server/ai-insight-answer.d.ts +30 -0
- package/src/lib/server/ai-insight-answer.js +83 -0
- package/src/lib/server/ai-insight-answer.js.map +1 -0
- package/src/lib/server/ai-insight-digest-route.d.ts +30 -0
- package/src/lib/server/ai-insight-digest-route.js +156 -0
- package/src/lib/server/ai-insight-digest-route.js.map +1 -0
- package/src/lib/server/ai-jobs-batch.d.ts +48 -0
- package/src/lib/server/ai-jobs-batch.js +306 -0
- package/src/lib/server/ai-jobs-batch.js.map +1 -0
- package/src/lib/server/ai-jobs-beat-route.d.ts +36 -0
- package/src/lib/server/ai-jobs-beat-route.js +86 -0
- package/src/lib/server/ai-jobs-beat-route.js.map +1 -0
- package/src/lib/server/ai-jobs-cancel.d.ts +30 -0
- package/src/lib/server/ai-jobs-cancel.js +74 -0
- package/src/lib/server/ai-jobs-cancel.js.map +1 -0
- package/src/lib/server/ai-jobs-events-route.d.ts +31 -0
- package/src/lib/server/ai-jobs-events-route.js +51 -0
- package/src/lib/server/ai-jobs-events-route.js.map +1 -0
- package/src/lib/server/ai-jobs-events.d.ts +55 -0
- package/src/lib/server/ai-jobs-events.js +144 -0
- package/src/lib/server/ai-jobs-events.js.map +1 -0
- package/src/lib/server/ai-jobs-gate.d.ts +47 -0
- package/src/lib/server/ai-jobs-gate.js +106 -0
- package/src/lib/server/ai-jobs-gate.js.map +1 -0
- package/src/lib/server/ai-jobs-resume.d.ts +23 -0
- package/src/lib/server/ai-jobs-resume.js +209 -0
- package/src/lib/server/ai-jobs-resume.js.map +1 -0
- package/src/lib/server/ai-jobs-route.d.ts +32 -0
- package/src/lib/server/ai-jobs-route.js +307 -0
- package/src/lib/server/ai-jobs-route.js.map +1 -0
- package/src/lib/server/ai-models.d.ts +18 -0
- package/src/lib/server/ai-models.js +134 -0
- package/src/lib/server/ai-models.js.map +1 -0
- package/src/lib/server/ai-seo-apply.d.ts +53 -0
- package/src/lib/server/ai-seo-apply.js +294 -0
- package/src/lib/server/ai-seo-apply.js.map +1 -0
- package/src/lib/server/ai-usage.d.ts +18 -0
- package/src/lib/server/ai-usage.js +220 -0
- package/src/lib/server/ai-usage.js.map +1 -0
- package/src/lib/server/assist-chat.d.ts +234 -0
- package/src/lib/server/assist-chat.js +1446 -0
- package/src/lib/server/assist-chat.js.map +1 -0
- package/src/lib/server/assist-edit-applied.d.ts +22 -0
- package/src/lib/server/assist-edit-applied.js +239 -0
- package/src/lib/server/assist-edit-applied.js.map +1 -0
- package/src/lib/server/assist-edit.d.ts +124 -0
- package/src/lib/server/assist-edit.js +1000 -0
- package/src/lib/server/assist-edit.js.map +1 -0
- package/src/lib/server/assist-feedback.d.ts +31 -0
- package/src/lib/server/assist-feedback.js +115 -0
- package/src/lib/server/assist-feedback.js.map +1 -0
- package/src/lib/server/assist-view-context.d.ts +343 -0
- package/src/lib/server/assist-view-context.js +690 -0
- package/src/lib/server/assist-view-context.js.map +1 -0
- package/src/lib/server/billing-credits.d.ts +59 -0
- package/src/lib/server/billing-credits.js +146 -0
- package/src/lib/server/billing-credits.js.map +1 -0
- package/src/lib/server/billing-overage.d.ts +19 -0
- package/src/lib/server/billing-overage.js +337 -0
- package/src/lib/server/billing-overage.js.map +1 -0
- package/src/lib/server.d.ts +32 -0
- package/src/lib/server.js +265 -0
- package/src/lib/server.js.map +1 -0
- package/src/lib/subprocessors.d.ts +18 -0
- package/src/lib/subprocessors.js +52 -0
- package/src/lib/subprocessors.js.map +1 -0
- package/src/lib/tools/ai-component-tool.d.ts +99 -0
- package/src/lib/tools/ai-component-tool.js +369 -0
- package/src/lib/tools/ai-component-tool.js.map +1 -0
- package/src/lib/tools/ai-crm-tool.d.ts +106 -0
- package/src/lib/tools/ai-crm-tool.js +488 -0
- package/src/lib/tools/ai-crm-tool.js.map +1 -0
- package/src/lib/tools/ai-duplicate-resource-tool.d.ts +71 -0
- package/src/lib/tools/ai-duplicate-resource-tool.js +164 -0
- package/src/lib/tools/ai-duplicate-resource-tool.js.map +1 -0
- package/src/lib/tools/ai-experiment-tool.d.ts +40 -0
- package/src/lib/tools/ai-experiment-tool.js +155 -0
- package/src/lib/tools/ai-experiment-tool.js.map +1 -0
- package/src/lib/tools/ai-insight-tool.d.ts +46 -0
- package/src/lib/tools/ai-insight-tool.js +200 -0
- package/src/lib/tools/ai-insight-tool.js.map +1 -0
- package/src/lib/tools/ai-inventory-lookup-tool.d.ts +86 -0
- package/src/lib/tools/ai-inventory-lookup-tool.js +164 -0
- package/src/lib/tools/ai-inventory-lookup-tool.js.map +1 -0
- package/src/lib/tools/ai-products-tool.d.ts +65 -0
- package/src/lib/tools/ai-products-tool.js +644 -0
- package/src/lib/tools/ai-products-tool.js.map +1 -0
- package/src/lib/tools/ai-seo-tool.d.ts +162 -0
- package/src/lib/tools/ai-seo-tool.js +546 -0
- package/src/lib/tools/ai-seo-tool.js.map +1 -0
- package/src/lib/tools/ai-theme-tool.d.ts +101 -0
- package/src/lib/tools/ai-theme-tool.js +562 -0
- package/src/lib/tools/ai-theme-tool.js.map +1 -0
- package/src/lib/tools/ai-workflow-tool.d.ts +166 -0
- package/src/lib/tools/ai-workflow-tool.js +860 -0
- package/src/lib/tools/ai-workflow-tool.js.map +1 -0
- package/src/lib/usage/ai-allotment-alerts.d.ts +72 -0
- package/src/lib/usage/ai-allotment-alerts.js +157 -0
- package/src/lib/usage/ai-allotment-alerts.js.map +1 -0
- package/src/lib/usage/ai-allotments.d.ts +125 -0
- package/src/lib/usage/ai-allotments.js +239 -0
- package/src/lib/usage/ai-allotments.js.map +1 -0
- package/src/lib/usage/ai-model-sample.d.ts +36 -0
- package/src/lib/usage/ai-model-sample.js +68 -0
- package/src/lib/usage/ai-model-sample.js.map +1 -0
- package/src/lib/usage/ai-usage-alerts.d.ts +55 -0
- package/src/lib/usage/ai-usage-alerts.js +114 -0
- package/src/lib/usage/ai-usage-alerts.js.map +1 -0
- package/src/lib/usage/ai-usage-by-user.d.ts +161 -0
- package/src/lib/usage/ai-usage-by-user.js +211 -0
- package/src/lib/usage/ai-usage-by-user.js.map +1 -0
- package/src/lib/usage/ai-usage-eraser.d.ts +29 -0
- package/src/lib/usage/ai-usage-eraser.js +40 -0
- package/src/lib/usage/ai-usage-eraser.js.map +1 -0
- package/src/lib/usage/ai-usage-meter.d.ts +39 -0
- package/src/lib/usage/ai-usage-meter.js +85 -0
- package/src/lib/usage/ai-usage-meter.js.map +1 -0
- package/src/lib/usage/ai-usage-wire.d.ts +184 -0
- package/src/lib/usage/ai-usage-wire.js +98 -0
- package/src/lib/usage/ai-usage-wire.js.map +1 -0
- package/src/lib/usage/assist-ceiling.d.ts +87 -0
- package/src/lib/usage/assist-ceiling.js +110 -0
- package/src/lib/usage/assist-ceiling.js.map +1 -0
- package/src/lib/usage/assist-free-taste.d.ts +225 -0
- package/src/lib/usage/assist-free-taste.js +308 -0
- package/src/lib/usage/assist-free-taste.js.map +1 -0
- package/src/lib/usage/assist-refusals.d.ts +69 -0
- package/src/lib/usage/assist-refusals.js +79 -0
- package/src/lib/usage/assist-refusals.js.map +1 -0
- package/src/lib/usage/assist-signal-mining.d.ts +375 -0
- package/src/lib/usage/assist-signal-mining.js +344 -0
- package/src/lib/usage/assist-signal-mining.js.map +1 -0
- package/src/lib/usage/assist-usage.d.ts +571 -0
- package/src/lib/usage/assist-usage.js +978 -0
- package/src/lib/usage/assist-usage.js.map +1 -0
- package/src/lib/usage/staff-org-ai.d.ts +242 -0
- package/src/lib/usage/staff-org-ai.js +173 -0
- package/src/lib/usage/staff-org-ai.js.map +1 -0
- package/src/lib/usage/staff-org-usage-ai.d.ts +83 -0
- package/src/lib/usage/staff-org-usage-ai.js +59 -0
- package/src/lib/usage/staff-org-usage-ai.js.map +1 -0
- package/src/lib/usage/staff-orgs-ai-spend.d.ts +83 -0
- package/src/lib/usage/staff-orgs-ai-spend.js +114 -0
- package/src/lib/usage/staff-orgs-ai-spend.js.map +1 -0
|
@@ -0,0 +1,644 @@
|
|
|
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
|
+
*/ import { SEO_LISTING_FIELDS } from "@aglyn/aglyn/app-utils/seo-listing-fields";
|
|
17
|
+
import { AI_CATALOG_DESCRIPTION_MAX_CHARS, AI_CATALOG_OPTION_VALUE_MAX_CHARS, AI_CATALOG_OPTION_VALUES_MAX, AI_CATALOG_OPTIONS_MAX, AI_CATALOG_PHOTO_MAX_CHARS, AI_CATALOG_PRODUCTS, AI_CATALOG_TAGS_MAX, AI_CATEGORIES_MAX, AI_CATEGORY_NAME_MAX_CHARS, AI_DISCOUNT_CODE, AI_DISCOUNT_MAX_FIXED_USD, AI_DISCOUNT_MAX_PERCENT, AI_DISCOUNTS_MAX, AI_PRODUCT_CATEGORIES_MAX, AI_PRODUCT_DESCRIPTION_MAX_CHARS, AI_PRODUCT_NAME_MAX_CHARS, AI_PRODUCT_OPTION_NAME_MAX_CHARS, AI_PRODUCT_TAG_MAX_CHARS, AI_PRODUCT_TAGS_MAX, AI_PRODUCT_TYPES, AI_PROPOSAL_WHY_MAX_CHARS } from "../model/ai-products.js";
|
|
18
|
+
import { findInventedPrices, findStorefrontClaims, storefrontClaimViolations } from "../model/ai-storefront-claims.js";
|
|
19
|
+
import { detectOffVoiceCopy } from "../runtime/ai-doctrine-validators.js";
|
|
20
|
+
/**
|
|
21
|
+
* The strict tools commerce by AI answers through (AGL-2916), and the checks
|
|
22
|
+
* that hold each answer to the commerce editor it proposes for.
|
|
23
|
+
*
|
|
24
|
+
* - `propose_product_copy` — one product's description, search listing, tags,
|
|
25
|
+
* categories and option names.
|
|
26
|
+
* - `propose_catalog` — a store's first products, from a brief.
|
|
27
|
+
* - `propose_categories_and_discounts` — store categories and a first set of
|
|
28
|
+
* discounts, from a brief.
|
|
29
|
+
*
|
|
30
|
+
* Each schema is kept small, and no field is nullable: "none" is an empty
|
|
31
|
+
* string, an empty list or zero. A strict schema accepts no length keyword,
|
|
32
|
+
* so every bound is stated in a description and enforced here. A check
|
|
33
|
+
* returns a value only when nothing in the answer is broken, and otherwise
|
|
34
|
+
* the violations and the parts at fault, for the generation call's one
|
|
35
|
+
* re-ask.
|
|
36
|
+
*/ export const AI_PRODUCT_COPY_TOOL_NAME = 'propose_product_copy';
|
|
37
|
+
export const AI_CATALOG_TOOL_NAME = 'propose_catalog';
|
|
38
|
+
export const AI_CATEGORIES_TOOL_NAME = 'propose_categories_and_discounts';
|
|
39
|
+
const SEO_TITLE_MAX = SEO_LISTING_FIELDS.title.maxLength;
|
|
40
|
+
const SEO_DESCRIPTION_MAX = SEO_LISTING_FIELDS.description.maxLength;
|
|
41
|
+
const string = (description)=>({
|
|
42
|
+
type: 'string',
|
|
43
|
+
description
|
|
44
|
+
});
|
|
45
|
+
const strings = (description)=>({
|
|
46
|
+
type: 'array',
|
|
47
|
+
items: {
|
|
48
|
+
type: 'string'
|
|
49
|
+
},
|
|
50
|
+
description
|
|
51
|
+
});
|
|
52
|
+
/* ------------------------------------------------------------------------ *
|
|
53
|
+
* Shared reads
|
|
54
|
+
* ------------------------------------------------------------------------ */ const isRecord = (value)=>typeof value === 'object' && value !== null && !Array.isArray(value);
|
|
55
|
+
/** One line: runs of white space folded to one space. */ const line = (value)=>typeof value === 'string' ? value.replace(/\s+/g, ' ').trim() : '';
|
|
56
|
+
/** Paragraphs: spaces folded within a line, at most one blank line between paragraphs. */ const paragraphs = (value)=>typeof value === 'string' ? value.replace(/\r\n?/g, '\n').split('\n').map((part)=>part.replace(/[ \t\f\v]+/g, ' ').trim()).join('\n').replace(/\n{3,}/g, '\n\n').trim() : '';
|
|
57
|
+
const MARKUP = /<\/?[a-z][^>]*>/i;
|
|
58
|
+
const MARKDOWN = /(^|\n)\s*#{1,6}\s|\*\*[^*\n]+\*\*|__[^_\n]+__|!\[[^\]]*\]\(|\[[^\]]+\]\(https?:/;
|
|
59
|
+
const EMOJI = RegExp("[\\u00A9\\u00AE\\u203C\\u2049\\u2122\\u2139\\u2194-\\u2199\\u21A9-\\u21AA\\u231A-\\u231B\\u2328\\u23CF\\u23E9-\\u23F3\\u23F8-\\u23FA\\u24C2\\u25AA-\\u25AB\\u25B6\\u25C0\\u25FB-\\u25FE\\u2600-\\u2604\\u260E\\u2611\\u2614-\\u2615\\u2618\\u261D\\u2620\\u2622-\\u2623\\u2626\\u262A\\u262E-\\u262F\\u2638-\\u263A\\u2640\\u2642\\u2648-\\u2653\\u265F-\\u2660\\u2663\\u2665-\\u2666\\u2668\\u267B\\u267E-\\u267F\\u2692-\\u2697\\u2699\\u269B-\\u269C\\u26A0-\\u26A1\\u26A7\\u26AA-\\u26AB\\u26B0-\\u26B1\\u26BD-\\u26BE\\u26C4-\\u26C5\\u26C8\\u26CE-\\u26CF\\u26D1\\u26D3-\\u26D4\\u26E9-\\u26EA\\u26F0-\\u26F5\\u26F7-\\u26FA\\u26FD\\u2702\\u2705\\u2708-\\u270D\\u270F\\u2712\\u2714\\u2716\\u271D\\u2721\\u2728\\u2733-\\u2734\\u2744\\u2747\\u274C\\u274E\\u2753-\\u2755\\u2757\\u2763-\\u2764\\u2795-\\u2797\\u27A1\\u27B0\\u27BF\\u2934-\\u2935\\u2B05-\\u2B07\\u2B1B-\\u2B1C\\u2B50\\u2B55\\u3030\\u303D\\u3297\\u3299\\u{1F004}\\u{1F02C}-\\u{1F02F}\\u{1F094}-\\u{1F09F}\\u{1F0AF}-\\u{1F0B0}\\u{1F0C0}\\u{1F0CF}-\\u{1F0D0}\\u{1F0F6}-\\u{1F0FF}\\u{1F170}-\\u{1F171}\\u{1F17E}-\\u{1F17F}\\u{1F18E}\\u{1F191}-\\u{1F19A}\\u{1F1AE}-\\u{1F1E5}\\u{1F201}-\\u{1F20F}\\u{1F21A}\\u{1F22F}\\u{1F232}-\\u{1F23A}\\u{1F23C}-\\u{1F23F}\\u{1F249}-\\u{1F25F}\\u{1F266}-\\u{1F321}\\u{1F324}-\\u{1F393}\\u{1F396}-\\u{1F397}\\u{1F399}-\\u{1F39B}\\u{1F39E}-\\u{1F3F0}\\u{1F3F3}-\\u{1F3F5}\\u{1F3F7}-\\u{1F3FA}\\u{1F400}-\\u{1F4FD}\\u{1F4FF}-\\u{1F53D}\\u{1F549}-\\u{1F54E}\\u{1F550}-\\u{1F567}\\u{1F56F}-\\u{1F570}\\u{1F573}-\\u{1F57A}\\u{1F587}\\u{1F58A}-\\u{1F58D}\\u{1F590}\\u{1F595}-\\u{1F596}\\u{1F5A4}-\\u{1F5A5}\\u{1F5A8}\\u{1F5B1}-\\u{1F5B2}\\u{1F5BC}\\u{1F5C2}-\\u{1F5C4}\\u{1F5D1}-\\u{1F5D3}\\u{1F5DC}-\\u{1F5DE}\\u{1F5E1}\\u{1F5E3}\\u{1F5E8}\\u{1F5EF}\\u{1F5F3}\\u{1F5FA}-\\u{1F64F}\\u{1F680}-\\u{1F6C5}\\u{1F6CB}-\\u{1F6D2}\\u{1F6D5}-\\u{1F6E5}\\u{1F6E9}\\u{1F6EB}-\\u{1F6F0}\\u{1F6F3}-\\u{1F6FF}\\u{1F7DA}-\\u{1F7FF}\\u{1F80C}-\\u{1F80F}\\u{1F848}-\\u{1F84F}\\u{1F85A}-\\u{1F85F}\\u{1F888}-\\u{1F88F}\\u{1F8AE}-\\u{1F8AF}\\u{1F8BC}-\\u{1F8BF}\\u{1F8C2}-\\u{1F8CF}\\u{1F8D9}-\\u{1F8FF}\\u{1F90C}-\\u{1F93A}\\u{1F93C}-\\u{1F945}\\u{1F947}-\\u{1F9FF}\\u{1FA58}-\\u{1FA5F}\\u{1FA6E}-\\u{1FAFF}\\u{1FC00}-\\u{1FFFD}]", "u");
|
|
60
|
+
const BRACKET = /[[\]]/;
|
|
61
|
+
const URL = /\bhttps?:\/\/|\bwww\./i;
|
|
62
|
+
function fail(findings, at, code, message, value) {
|
|
63
|
+
findings.violations.push({
|
|
64
|
+
rule: null,
|
|
65
|
+
code,
|
|
66
|
+
message,
|
|
67
|
+
paths: [
|
|
68
|
+
at
|
|
69
|
+
]
|
|
70
|
+
});
|
|
71
|
+
if (!(at in findings.offending)) findings.offending[at] = value;
|
|
72
|
+
}
|
|
73
|
+
/** A piece of copy a shopper reads: there, within its length, and plain text. */ function checkCopyText(findings, at, raw, bounds) {
|
|
74
|
+
if (typeof raw !== 'string') {
|
|
75
|
+
fail(findings, at, 'type', `${bounds.label} must be text.`, raw);
|
|
76
|
+
return '';
|
|
77
|
+
}
|
|
78
|
+
const value = bounds.multiline ? paragraphs(raw) : line(raw);
|
|
79
|
+
if (!value) {
|
|
80
|
+
fail(findings, at, 'missing', `${bounds.label} is required.`, raw);
|
|
81
|
+
return '';
|
|
82
|
+
}
|
|
83
|
+
if (value.length > bounds.max) {
|
|
84
|
+
fail(findings, at, 'too-long', `${bounds.label} is ${value.length} characters; it may have ${bounds.max}.`, raw);
|
|
85
|
+
}
|
|
86
|
+
if (MARKUP.test(value) || MARKDOWN.test(value)) {
|
|
87
|
+
fail(findings, at, 'markup', `${bounds.label} is plain text, with no markup or formatting marks.`, raw);
|
|
88
|
+
}
|
|
89
|
+
if (EMOJI.test(value)) fail(findings, at, 'emoji', `${bounds.label} holds no emoji.`, raw);
|
|
90
|
+
if (URL.test(value)) fail(findings, at, 'link', `${bounds.label} holds no link.`, raw);
|
|
91
|
+
if (bounds.brackets === false && BRACKET.test(value)) {
|
|
92
|
+
fail(findings, at, 'bracket', `${bounds.label} is published as written, so it marks no missing fact in brackets.`, raw);
|
|
93
|
+
}
|
|
94
|
+
return value;
|
|
95
|
+
}
|
|
96
|
+
/** Tags a shopper filters by: short, distinct, no `#`, no more than `max`. */ function checkTags(findings, at, raw, max = AI_PRODUCT_TAGS_MAX) {
|
|
97
|
+
if (!Array.isArray(raw)) {
|
|
98
|
+
fail(findings, at, 'type', 'Tags are a list of words or short phrases.', raw);
|
|
99
|
+
return [];
|
|
100
|
+
}
|
|
101
|
+
const seen = new Set();
|
|
102
|
+
const tags = [];
|
|
103
|
+
raw.forEach((entry, index)=>{
|
|
104
|
+
const tag = line(entry).replace(/^#+/, '').trim();
|
|
105
|
+
if (!tag) return;
|
|
106
|
+
if (tag.length > AI_PRODUCT_TAG_MAX_CHARS || EMOJI.test(tag) || BRACKET.test(tag)) {
|
|
107
|
+
fail(findings, `${at}[${index}]`, 'tag', `A tag is a plain word or phrase of at most ${AI_PRODUCT_TAG_MAX_CHARS} characters.`, entry);
|
|
108
|
+
return;
|
|
109
|
+
}
|
|
110
|
+
const key = tag.toLowerCase();
|
|
111
|
+
if (seen.has(key)) return;
|
|
112
|
+
seen.add(key);
|
|
113
|
+
tags.push(tag);
|
|
114
|
+
});
|
|
115
|
+
if (tags.length > max) {
|
|
116
|
+
fail(findings, at, 'too-many', `A product carries at most ${max} tags.`, raw);
|
|
117
|
+
}
|
|
118
|
+
return tags;
|
|
119
|
+
}
|
|
120
|
+
/** The claims and prices a set of copy may not make, as violations. */ function claimViolations(samples, merchantWords) {
|
|
121
|
+
return storefrontClaimViolations(findStorefrontClaims(samples, merchantWords), findInventedPrices(samples, merchantWords));
|
|
122
|
+
}
|
|
123
|
+
/* ------------------------------------------------------------------------ *
|
|
124
|
+
* One product's copy
|
|
125
|
+
* ------------------------------------------------------------------------ */ export const AI_PRODUCT_COPY_TOOL = {
|
|
126
|
+
name: AI_PRODUCT_COPY_TOOL_NAME,
|
|
127
|
+
description: 'Propose the storefront copy for one product. Every field is required.',
|
|
128
|
+
strict: true,
|
|
129
|
+
inputSchema: {
|
|
130
|
+
type: 'object',
|
|
131
|
+
additionalProperties: false,
|
|
132
|
+
required: [
|
|
133
|
+
'description',
|
|
134
|
+
'seoTitle',
|
|
135
|
+
'seoDescription',
|
|
136
|
+
'tags',
|
|
137
|
+
'categoryIds',
|
|
138
|
+
'optionNames'
|
|
139
|
+
],
|
|
140
|
+
properties: {
|
|
141
|
+
description: string(`The product description shoppers read, in short paragraphs, at most ${AI_PRODUCT_DESCRIPTION_MAX_CHARS} characters.`),
|
|
142
|
+
seoTitle: string(`The search result headline, published as written, at most ${SEO_TITLE_MAX} characters.`),
|
|
143
|
+
seoDescription: string(`The search result summary, at most ${SEO_DESCRIPTION_MAX} characters.`),
|
|
144
|
+
tags: strings(`At most ${AI_PRODUCT_TAGS_MAX} tags, each at most ${AI_PRODUCT_TAG_MAX_CHARS} characters.`),
|
|
145
|
+
categoryIds: strings(`At most ${AI_PRODUCT_CATEGORIES_MAX} category ids from the list you were given; empty when none fits.`),
|
|
146
|
+
optionNames: strings(`One name per option the product has, in order, each at most ${AI_PRODUCT_OPTION_NAME_MAX_CHARS} characters; empty when it has none.`)
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
};
|
|
150
|
+
/**
|
|
151
|
+
* A product copy answer held to the editor: every field written and within
|
|
152
|
+
* its length, plain text, the categories the request listed, one distinct
|
|
153
|
+
* name per option, and no claim or price the copy may not make.
|
|
154
|
+
*/ export function checkAiProductCopy(answer, context) {
|
|
155
|
+
const findings = {
|
|
156
|
+
violations: [],
|
|
157
|
+
offending: {}
|
|
158
|
+
};
|
|
159
|
+
const description = checkCopyText(findings, 'description', answer['description'], {
|
|
160
|
+
label: 'The description',
|
|
161
|
+
max: AI_PRODUCT_DESCRIPTION_MAX_CHARS,
|
|
162
|
+
multiline: true
|
|
163
|
+
});
|
|
164
|
+
const seoTitle = checkCopyText(findings, 'seoTitle', answer['seoTitle'], {
|
|
165
|
+
label: 'The search title',
|
|
166
|
+
max: SEO_TITLE_MAX,
|
|
167
|
+
brackets: false
|
|
168
|
+
});
|
|
169
|
+
const seoDescription = checkCopyText(findings, 'seoDescription', answer['seoDescription'], {
|
|
170
|
+
label: 'The search description',
|
|
171
|
+
max: SEO_DESCRIPTION_MAX,
|
|
172
|
+
brackets: false
|
|
173
|
+
});
|
|
174
|
+
const tags = checkTags(findings, 'tags', answer['tags']);
|
|
175
|
+
const allowed = new Set(context.categoryIds);
|
|
176
|
+
const categoryIds = [];
|
|
177
|
+
const rawCategories = answer['categoryIds'];
|
|
178
|
+
if (!Array.isArray(rawCategories)) {
|
|
179
|
+
fail(findings, 'categoryIds', 'type', 'Categories are a list of ids.', rawCategories);
|
|
180
|
+
} else {
|
|
181
|
+
for (const entry of rawCategories){
|
|
182
|
+
const id = line(entry);
|
|
183
|
+
if (!id || categoryIds.includes(id)) continue;
|
|
184
|
+
if (!allowed.has(id)) {
|
|
185
|
+
fail(findings, 'categoryIds', 'category-unknown', 'Use only the category ids you were given.', rawCategories);
|
|
186
|
+
continue;
|
|
187
|
+
}
|
|
188
|
+
categoryIds.push(id);
|
|
189
|
+
}
|
|
190
|
+
if (categoryIds.length > AI_PRODUCT_CATEGORIES_MAX) {
|
|
191
|
+
fail(findings, 'categoryIds', 'too-many', `A product goes in at most ${AI_PRODUCT_CATEGORIES_MAX} categories.`, rawCategories);
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
const optionNames = [];
|
|
195
|
+
const rawOptions = answer['optionNames'];
|
|
196
|
+
if (!Array.isArray(rawOptions)) {
|
|
197
|
+
fail(findings, 'optionNames', 'type', 'Option names are a list.', rawOptions);
|
|
198
|
+
} else {
|
|
199
|
+
if (rawOptions.length !== context.optionCount) {
|
|
200
|
+
fail(findings, 'optionNames', 'option-count', `The product has ${context.optionCount} ${context.optionCount === 1 ? 'option' : 'options'}; give one name for each.`, rawOptions);
|
|
201
|
+
}
|
|
202
|
+
rawOptions.slice(0, context.optionCount).forEach((entry, index)=>{
|
|
203
|
+
const name = line(entry);
|
|
204
|
+
if (!name || name.length > AI_PRODUCT_OPTION_NAME_MAX_CHARS || BRACKET.test(name) || EMOJI.test(name)) {
|
|
205
|
+
fail(findings, `optionNames[${index}]`, 'option-name', `An option name is a plain word or phrase of at most ${AI_PRODUCT_OPTION_NAME_MAX_CHARS} characters.`, entry);
|
|
206
|
+
}
|
|
207
|
+
optionNames.push(name);
|
|
208
|
+
});
|
|
209
|
+
if (new Set(optionNames.map((name)=>name.toLowerCase())).size !== optionNames.length) {
|
|
210
|
+
fail(findings, 'optionNames', 'option-duplicate', 'Each option needs its own name.', rawOptions);
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
const samples = [
|
|
214
|
+
{
|
|
215
|
+
at: 'description',
|
|
216
|
+
text: description
|
|
217
|
+
},
|
|
218
|
+
{
|
|
219
|
+
at: 'seoTitle',
|
|
220
|
+
text: seoTitle
|
|
221
|
+
},
|
|
222
|
+
{
|
|
223
|
+
at: 'seoDescription',
|
|
224
|
+
text: seoDescription
|
|
225
|
+
},
|
|
226
|
+
...tags.map((tag, index)=>({
|
|
227
|
+
at: `tags[${index}]`,
|
|
228
|
+
text: tag
|
|
229
|
+
}))
|
|
230
|
+
];
|
|
231
|
+
findings.violations.push(...claimViolations(samples, context.merchantWords), ...detectOffVoiceCopy(samples, null));
|
|
232
|
+
const value = findings.violations.length ? null : {
|
|
233
|
+
description,
|
|
234
|
+
seoTitle,
|
|
235
|
+
seoDescription,
|
|
236
|
+
tags,
|
|
237
|
+
categoryIds,
|
|
238
|
+
optionNames
|
|
239
|
+
};
|
|
240
|
+
return {
|
|
241
|
+
value,
|
|
242
|
+
violations: findings.violations,
|
|
243
|
+
offending: findings.offending
|
|
244
|
+
};
|
|
245
|
+
}
|
|
246
|
+
/* ------------------------------------------------------------------------ *
|
|
247
|
+
* A store's first products
|
|
248
|
+
* ------------------------------------------------------------------------ */ export const AI_CATALOG_TOOL = {
|
|
249
|
+
name: AI_CATALOG_TOOL_NAME,
|
|
250
|
+
description: 'Propose the products of a new store, each a draft its owner completes. Every field is required.',
|
|
251
|
+
strict: true,
|
|
252
|
+
inputSchema: {
|
|
253
|
+
type: 'object',
|
|
254
|
+
additionalProperties: false,
|
|
255
|
+
required: [
|
|
256
|
+
'products'
|
|
257
|
+
],
|
|
258
|
+
properties: {
|
|
259
|
+
products: {
|
|
260
|
+
type: 'array',
|
|
261
|
+
description: `Between ${AI_CATALOG_PRODUCTS.min} and ${AI_CATALOG_PRODUCTS.max} products.`,
|
|
262
|
+
items: {
|
|
263
|
+
type: 'object',
|
|
264
|
+
additionalProperties: false,
|
|
265
|
+
required: [
|
|
266
|
+
'name',
|
|
267
|
+
'type',
|
|
268
|
+
'description',
|
|
269
|
+
'tags',
|
|
270
|
+
'options',
|
|
271
|
+
'seoTitle',
|
|
272
|
+
'seoDescription',
|
|
273
|
+
'photo'
|
|
274
|
+
],
|
|
275
|
+
properties: {
|
|
276
|
+
name: string(`Distinct within the list, at most ${AI_PRODUCT_NAME_MAX_CHARS} characters.`),
|
|
277
|
+
type: {
|
|
278
|
+
type: 'string',
|
|
279
|
+
enum: [
|
|
280
|
+
...AI_PRODUCT_TYPES
|
|
281
|
+
]
|
|
282
|
+
},
|
|
283
|
+
description: string(`In short paragraphs, at most ${AI_CATALOG_DESCRIPTION_MAX_CHARS} characters.`),
|
|
284
|
+
tags: strings(`At most ${AI_CATALOG_TAGS_MAX} tags, each at most ${AI_PRODUCT_TAG_MAX_CHARS} characters.`),
|
|
285
|
+
options: {
|
|
286
|
+
type: 'array',
|
|
287
|
+
description: `The choices a shopper makes, at most ${AI_CATALOG_OPTIONS_MAX}; empty for a product with none.`,
|
|
288
|
+
items: {
|
|
289
|
+
type: 'object',
|
|
290
|
+
additionalProperties: false,
|
|
291
|
+
required: [
|
|
292
|
+
'name',
|
|
293
|
+
'values'
|
|
294
|
+
],
|
|
295
|
+
properties: {
|
|
296
|
+
name: string(`At most ${AI_PRODUCT_OPTION_NAME_MAX_CHARS} characters.`),
|
|
297
|
+
values: strings(`At most ${AI_CATALOG_OPTION_VALUES_MAX} distinct values, each at most ${AI_CATALOG_OPTION_VALUE_MAX_CHARS} characters.`)
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
},
|
|
301
|
+
seoTitle: string(`At most ${SEO_TITLE_MAX} characters.`),
|
|
302
|
+
seoDescription: string(`At most ${SEO_DESCRIPTION_MAX} characters.`),
|
|
303
|
+
photo: string(`What the product photo should show, in one sentence of at most ${AI_CATALOG_PHOTO_MAX_CHARS} characters.`)
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
}
|
|
307
|
+
}
|
|
308
|
+
}
|
|
309
|
+
};
|
|
310
|
+
/** A catalog answer held to the products editor and the storefront copy rules. */ export function checkAiCatalog(answer, context) {
|
|
311
|
+
const findings = {
|
|
312
|
+
violations: [],
|
|
313
|
+
offending: {}
|
|
314
|
+
};
|
|
315
|
+
const raw = answer['products'];
|
|
316
|
+
if (!Array.isArray(raw)) {
|
|
317
|
+
fail(findings, 'products', 'type', 'The products are a list.', raw);
|
|
318
|
+
return {
|
|
319
|
+
value: null,
|
|
320
|
+
violations: findings.violations,
|
|
321
|
+
offending: findings.offending
|
|
322
|
+
};
|
|
323
|
+
}
|
|
324
|
+
if (raw.length < AI_CATALOG_PRODUCTS.min || raw.length > AI_CATALOG_PRODUCTS.max) {
|
|
325
|
+
fail(findings, 'products', 'product-count', `Propose between ${AI_CATALOG_PRODUCTS.min} and ${AI_CATALOG_PRODUCTS.max} products.`, `${raw.length} products`);
|
|
326
|
+
}
|
|
327
|
+
const names = new Set();
|
|
328
|
+
const products = [];
|
|
329
|
+
const samples = [];
|
|
330
|
+
raw.slice(0, AI_CATALOG_PRODUCTS.max).forEach((entry, index)=>{
|
|
331
|
+
const at = `products[${index}]`;
|
|
332
|
+
if (!isRecord(entry)) {
|
|
333
|
+
fail(findings, at, 'type', 'Each product is an object.', entry);
|
|
334
|
+
return;
|
|
335
|
+
}
|
|
336
|
+
const name = checkCopyText(findings, `${at}.name`, entry['name'], {
|
|
337
|
+
label: 'A product name',
|
|
338
|
+
max: AI_PRODUCT_NAME_MAX_CHARS,
|
|
339
|
+
brackets: false
|
|
340
|
+
});
|
|
341
|
+
if (name && names.has(name.toLowerCase())) {
|
|
342
|
+
fail(findings, `${at}.name`, 'name-duplicate', 'Each product needs its own name.', entry['name']);
|
|
343
|
+
}
|
|
344
|
+
names.add(name.toLowerCase());
|
|
345
|
+
const type = entry['type'];
|
|
346
|
+
if (!AI_PRODUCT_TYPES.includes(type)) {
|
|
347
|
+
fail(findings, `${at}.type`, 'type', 'A product is physical, digital or a service.', type);
|
|
348
|
+
}
|
|
349
|
+
const description = checkCopyText(findings, `${at}.description`, entry['description'], {
|
|
350
|
+
label: 'A product description',
|
|
351
|
+
max: AI_CATALOG_DESCRIPTION_MAX_CHARS,
|
|
352
|
+
multiline: true
|
|
353
|
+
});
|
|
354
|
+
const tags = checkTags(findings, `${at}.tags`, entry['tags'], AI_CATALOG_TAGS_MAX);
|
|
355
|
+
const options = checkCatalogOptions(findings, `${at}.options`, entry['options']);
|
|
356
|
+
const seoTitle = checkCopyText(findings, `${at}.seoTitle`, entry['seoTitle'], {
|
|
357
|
+
label: 'A search title',
|
|
358
|
+
max: SEO_TITLE_MAX,
|
|
359
|
+
brackets: false
|
|
360
|
+
});
|
|
361
|
+
const seoDescription = checkCopyText(findings, `${at}.seoDescription`, entry['seoDescription'], {
|
|
362
|
+
label: 'A search description',
|
|
363
|
+
max: SEO_DESCRIPTION_MAX,
|
|
364
|
+
brackets: false
|
|
365
|
+
});
|
|
366
|
+
const photo = checkCopyText(findings, `${at}.photo`, entry['photo'], {
|
|
367
|
+
label: 'What the photo shows',
|
|
368
|
+
max: AI_CATALOG_PHOTO_MAX_CHARS,
|
|
369
|
+
brackets: false
|
|
370
|
+
});
|
|
371
|
+
samples.push({
|
|
372
|
+
at: `${at}.name`,
|
|
373
|
+
text: name
|
|
374
|
+
}, {
|
|
375
|
+
at: `${at}.description`,
|
|
376
|
+
text: description
|
|
377
|
+
}, {
|
|
378
|
+
at: `${at}.seoTitle`,
|
|
379
|
+
text: seoTitle
|
|
380
|
+
}, {
|
|
381
|
+
at: `${at}.seoDescription`,
|
|
382
|
+
text: seoDescription
|
|
383
|
+
}, ...tags.map((tag, tagIndex)=>({
|
|
384
|
+
at: `${at}.tags[${tagIndex}]`,
|
|
385
|
+
text: tag
|
|
386
|
+
})));
|
|
387
|
+
products.push({
|
|
388
|
+
name,
|
|
389
|
+
type: type,
|
|
390
|
+
description,
|
|
391
|
+
tags,
|
|
392
|
+
options,
|
|
393
|
+
seoTitle,
|
|
394
|
+
seoDescription,
|
|
395
|
+
photo
|
|
396
|
+
});
|
|
397
|
+
});
|
|
398
|
+
findings.violations.push(...claimViolations(samples, context.merchantWords), ...detectOffVoiceCopy(samples, null));
|
|
399
|
+
return {
|
|
400
|
+
value: findings.violations.length ? null : products,
|
|
401
|
+
violations: findings.violations,
|
|
402
|
+
offending: findings.offending
|
|
403
|
+
};
|
|
404
|
+
}
|
|
405
|
+
function checkCatalogOptions(findings, at, raw) {
|
|
406
|
+
if (!Array.isArray(raw)) {
|
|
407
|
+
fail(findings, at, 'type', 'Options are a list.', raw);
|
|
408
|
+
return [];
|
|
409
|
+
}
|
|
410
|
+
if (raw.length > AI_CATALOG_OPTIONS_MAX) {
|
|
411
|
+
fail(findings, at, 'too-many', `A proposed product has at most ${AI_CATALOG_OPTIONS_MAX} options.`, raw);
|
|
412
|
+
}
|
|
413
|
+
const options = [];
|
|
414
|
+
raw.slice(0, AI_CATALOG_OPTIONS_MAX).forEach((entry, index)=>{
|
|
415
|
+
const here = `${at}[${index}]`;
|
|
416
|
+
const record = isRecord(entry) ? entry : {};
|
|
417
|
+
const name = line(record['name']);
|
|
418
|
+
if (!name || name.length > AI_PRODUCT_OPTION_NAME_MAX_CHARS || BRACKET.test(name)) {
|
|
419
|
+
fail(findings, `${here}.name`, 'option-name', `An option name is a plain word or phrase of at most ${AI_PRODUCT_OPTION_NAME_MAX_CHARS} characters.`, record['name']);
|
|
420
|
+
}
|
|
421
|
+
const values = Array.isArray(record['values']) ? record['values'].map(line).filter(Boolean) : [];
|
|
422
|
+
if (!values.length || values.length > AI_CATALOG_OPTION_VALUES_MAX) {
|
|
423
|
+
fail(findings, `${here}.values`, 'too-many', `An option has between 1 and ${AI_CATALOG_OPTION_VALUES_MAX} values.`, record['values']);
|
|
424
|
+
}
|
|
425
|
+
if (values.some((value)=>value.length > AI_CATALOG_OPTION_VALUE_MAX_CHARS || BRACKET.test(value))) {
|
|
426
|
+
fail(findings, `${here}.values`, 'option-values', `An option value is a plain word or phrase of at most ${AI_CATALOG_OPTION_VALUE_MAX_CHARS} characters.`, record['values']);
|
|
427
|
+
}
|
|
428
|
+
if (new Set(values.map((value)=>value.toLowerCase())).size !== values.length) {
|
|
429
|
+
fail(findings, `${here}.values`, 'option-values', 'An option’s values are all different.', record['values']);
|
|
430
|
+
}
|
|
431
|
+
options.push({
|
|
432
|
+
name,
|
|
433
|
+
values: values.slice(0, AI_CATALOG_OPTION_VALUES_MAX)
|
|
434
|
+
});
|
|
435
|
+
});
|
|
436
|
+
if (new Set(options.map((option)=>option.name.toLowerCase())).size !== options.length) {
|
|
437
|
+
fail(findings, at, 'option-duplicate', 'Each option needs its own name.', raw);
|
|
438
|
+
}
|
|
439
|
+
return options;
|
|
440
|
+
}
|
|
441
|
+
/* ------------------------------------------------------------------------ *
|
|
442
|
+
* Categories and discounts
|
|
443
|
+
* ------------------------------------------------------------------------ */ export const AI_CATEGORIES_TOOL = {
|
|
444
|
+
name: AI_CATEGORIES_TOOL_NAME,
|
|
445
|
+
description: 'Propose store categories and a first set of discounts, each created only if the owner accepts it. Every field is required.',
|
|
446
|
+
strict: true,
|
|
447
|
+
inputSchema: {
|
|
448
|
+
type: 'object',
|
|
449
|
+
additionalProperties: false,
|
|
450
|
+
required: [
|
|
451
|
+
'categories',
|
|
452
|
+
'discounts'
|
|
453
|
+
],
|
|
454
|
+
properties: {
|
|
455
|
+
categories: {
|
|
456
|
+
type: 'array',
|
|
457
|
+
description: `At most ${AI_CATEGORIES_MAX} categories; empty when the brief gives no reason for any.`,
|
|
458
|
+
items: {
|
|
459
|
+
type: 'object',
|
|
460
|
+
additionalProperties: false,
|
|
461
|
+
required: [
|
|
462
|
+
'name',
|
|
463
|
+
'why'
|
|
464
|
+
],
|
|
465
|
+
properties: {
|
|
466
|
+
name: string(`At most ${AI_CATEGORY_NAME_MAX_CHARS} characters.`),
|
|
467
|
+
why: string(`One sentence of at most ${AI_PROPOSAL_WHY_MAX_CHARS} characters.`)
|
|
468
|
+
}
|
|
469
|
+
}
|
|
470
|
+
},
|
|
471
|
+
discounts: {
|
|
472
|
+
type: 'array',
|
|
473
|
+
description: `At most ${AI_DISCOUNTS_MAX} discounts; empty when the brief gives no reason for any.`,
|
|
474
|
+
items: {
|
|
475
|
+
type: 'object',
|
|
476
|
+
additionalProperties: false,
|
|
477
|
+
required: [
|
|
478
|
+
'name',
|
|
479
|
+
'code',
|
|
480
|
+
'kind',
|
|
481
|
+
'value',
|
|
482
|
+
'minimumOrderUsd',
|
|
483
|
+
'why'
|
|
484
|
+
],
|
|
485
|
+
properties: {
|
|
486
|
+
name: string(`At most ${AI_CATEGORY_NAME_MAX_CHARS} characters.`),
|
|
487
|
+
code: string('The code a shopper types: 3 to 20 capital letters, digits, dashes or underscores; empty for a discount that applies on its own.'),
|
|
488
|
+
kind: {
|
|
489
|
+
type: 'string',
|
|
490
|
+
enum: [
|
|
491
|
+
'percent',
|
|
492
|
+
'fixed',
|
|
493
|
+
'free_shipping'
|
|
494
|
+
]
|
|
495
|
+
},
|
|
496
|
+
value: {
|
|
497
|
+
type: 'number',
|
|
498
|
+
description: `percent: the percentage, 1 to ${AI_DISCOUNT_MAX_PERCENT}; fixed: dollars off, at most ${AI_DISCOUNT_MAX_FIXED_USD}; free_shipping: 0.`
|
|
499
|
+
},
|
|
500
|
+
minimumOrderUsd: {
|
|
501
|
+
type: 'number',
|
|
502
|
+
description: 'The smallest order it applies to, in dollars; 0 for any order.'
|
|
503
|
+
},
|
|
504
|
+
why: string(`One sentence of at most ${AI_PROPOSAL_WHY_MAX_CHARS} characters.`)
|
|
505
|
+
}
|
|
506
|
+
}
|
|
507
|
+
}
|
|
508
|
+
}
|
|
509
|
+
}
|
|
510
|
+
};
|
|
511
|
+
/** A categories answer held to the catalog and discount editors and the storefront copy rules. */ export function checkAiCategories(answer, context) {
|
|
512
|
+
const findings = {
|
|
513
|
+
violations: [],
|
|
514
|
+
offending: {}
|
|
515
|
+
};
|
|
516
|
+
const existing = new Set(context.existingCategoryNames.map((name)=>line(name).toLowerCase()));
|
|
517
|
+
const samples = [];
|
|
518
|
+
const categories = [];
|
|
519
|
+
const rawCategories = answer['categories'];
|
|
520
|
+
if (!Array.isArray(rawCategories)) {
|
|
521
|
+
fail(findings, 'categories', 'type', 'Categories are a list.', rawCategories);
|
|
522
|
+
} else {
|
|
523
|
+
if (rawCategories.length > AI_CATEGORIES_MAX) {
|
|
524
|
+
fail(findings, 'categories', 'too-many', `Propose at most ${AI_CATEGORIES_MAX} categories.`, `${rawCategories.length} categories`);
|
|
525
|
+
}
|
|
526
|
+
const seen = new Set();
|
|
527
|
+
rawCategories.slice(0, AI_CATEGORIES_MAX).forEach((entry, index)=>{
|
|
528
|
+
const at = `categories[${index}]`;
|
|
529
|
+
const record = isRecord(entry) ? entry : {};
|
|
530
|
+
const name = checkCopyText(findings, `${at}.name`, record['name'], {
|
|
531
|
+
label: 'A category name',
|
|
532
|
+
max: AI_CATEGORY_NAME_MAX_CHARS,
|
|
533
|
+
brackets: false
|
|
534
|
+
});
|
|
535
|
+
const key = name.toLowerCase();
|
|
536
|
+
if (name && existing.has(key)) {
|
|
537
|
+
fail(findings, `${at}.name`, 'category-exists', `The store already has a category named ${name}.`, record['name']);
|
|
538
|
+
} else if (name && seen.has(key)) {
|
|
539
|
+
fail(findings, `${at}.name`, 'category-duplicate', 'Each category needs its own name.', record['name']);
|
|
540
|
+
}
|
|
541
|
+
seen.add(key);
|
|
542
|
+
const why = checkCopyText(findings, `${at}.why`, record['why'], {
|
|
543
|
+
label: 'Why a category helps',
|
|
544
|
+
max: AI_PROPOSAL_WHY_MAX_CHARS,
|
|
545
|
+
brackets: false
|
|
546
|
+
});
|
|
547
|
+
samples.push({
|
|
548
|
+
at: `${at}.name`,
|
|
549
|
+
text: name
|
|
550
|
+
}, {
|
|
551
|
+
at: `${at}.why`,
|
|
552
|
+
text: why
|
|
553
|
+
});
|
|
554
|
+
categories.push({
|
|
555
|
+
name,
|
|
556
|
+
why
|
|
557
|
+
});
|
|
558
|
+
});
|
|
559
|
+
}
|
|
560
|
+
const discounts = [];
|
|
561
|
+
const rawDiscounts = answer['discounts'];
|
|
562
|
+
if (!Array.isArray(rawDiscounts)) {
|
|
563
|
+
fail(findings, 'discounts', 'type', 'Discounts are a list.', rawDiscounts);
|
|
564
|
+
} else {
|
|
565
|
+
if (rawDiscounts.length > AI_DISCOUNTS_MAX) {
|
|
566
|
+
fail(findings, 'discounts', 'too-many', `Propose at most ${AI_DISCOUNTS_MAX} discounts.`, `${rawDiscounts.length} discounts`);
|
|
567
|
+
}
|
|
568
|
+
const codes = new Set();
|
|
569
|
+
rawDiscounts.slice(0, AI_DISCOUNTS_MAX).forEach((entry, index)=>{
|
|
570
|
+
const at = `discounts[${index}]`;
|
|
571
|
+
const record = isRecord(entry) ? entry : {};
|
|
572
|
+
const name = checkCopyText(findings, `${at}.name`, record['name'], {
|
|
573
|
+
label: 'A discount name',
|
|
574
|
+
max: AI_CATEGORY_NAME_MAX_CHARS,
|
|
575
|
+
brackets: false
|
|
576
|
+
});
|
|
577
|
+
const typedCode = line(record['code']).toUpperCase();
|
|
578
|
+
if (typedCode && !AI_DISCOUNT_CODE.test(typedCode)) {
|
|
579
|
+
fail(findings, `${at}.code`, 'code', 'A code is 3 to 20 capital letters, digits, dashes or underscores.', record['code']);
|
|
580
|
+
} else if (typedCode && codes.has(typedCode)) {
|
|
581
|
+
fail(findings, `${at}.code`, 'code-duplicate', 'Each discount needs its own code.', record['code']);
|
|
582
|
+
}
|
|
583
|
+
if (typedCode) codes.add(typedCode);
|
|
584
|
+
const kind = record['kind'];
|
|
585
|
+
const value = Number(record['value']);
|
|
586
|
+
const minimum = Number(record['minimumOrderUsd']);
|
|
587
|
+
let valuePct = null;
|
|
588
|
+
let valueCents = null;
|
|
589
|
+
if (kind === 'percent') {
|
|
590
|
+
if (!Number.isInteger(value) || value < 1 || value > AI_DISCOUNT_MAX_PERCENT) {
|
|
591
|
+
fail(findings, `${at}.value`, 'discount-value', `A percentage is a whole number from 1 to ${AI_DISCOUNT_MAX_PERCENT}.`, record['value']);
|
|
592
|
+
}
|
|
593
|
+
valuePct = value;
|
|
594
|
+
} else if (kind === 'fixed') {
|
|
595
|
+
if (!Number.isFinite(value) || value <= 0 || value > AI_DISCOUNT_MAX_FIXED_USD) {
|
|
596
|
+
fail(findings, `${at}.value`, 'discount-value', `An amount off is more than 0 and at most ${AI_DISCOUNT_MAX_FIXED_USD} dollars.`, record['value']);
|
|
597
|
+
}
|
|
598
|
+
valueCents = Math.round(value * 100);
|
|
599
|
+
} else if (kind !== 'free_shipping') {
|
|
600
|
+
fail(findings, `${at}.kind`, 'type', 'A discount is a percentage, an amount off or free shipping.', kind);
|
|
601
|
+
}
|
|
602
|
+
if (!Number.isFinite(minimum) || minimum < 0 || minimum > 10000) {
|
|
603
|
+
fail(findings, `${at}.minimumOrderUsd`, 'discount-minimum', 'A minimum order is between 0 and 10,000 dollars.', record['minimumOrderUsd']);
|
|
604
|
+
}
|
|
605
|
+
const why = checkCopyText(findings, `${at}.why`, record['why'], {
|
|
606
|
+
label: 'Why a discount helps',
|
|
607
|
+
max: AI_PROPOSAL_WHY_MAX_CHARS,
|
|
608
|
+
brackets: false
|
|
609
|
+
});
|
|
610
|
+
// The discount's own amount is stated in its fields, so only its name
|
|
611
|
+
// and reason are read for a claim: "15% off" is the discount, not a price.
|
|
612
|
+
samples.push({
|
|
613
|
+
at: `${at}.name`,
|
|
614
|
+
text: name
|
|
615
|
+
}, {
|
|
616
|
+
at: `${at}.why`,
|
|
617
|
+
text: why
|
|
618
|
+
});
|
|
619
|
+
discounts.push({
|
|
620
|
+
name,
|
|
621
|
+
code: typedCode || null,
|
|
622
|
+
kind: kind,
|
|
623
|
+
valuePct,
|
|
624
|
+
valueCents,
|
|
625
|
+
minSubtotalCents: minimum > 0 ? Math.round(minimum * 100) : null,
|
|
626
|
+
why
|
|
627
|
+
});
|
|
628
|
+
});
|
|
629
|
+
}
|
|
630
|
+
if (!categories.length && !discounts.length && !findings.violations.length) {
|
|
631
|
+
fail(findings, 'categories', 'empty', 'Propose at least one category or one discount.', answer);
|
|
632
|
+
}
|
|
633
|
+
findings.violations.push(...storefrontClaimViolations(findStorefrontClaims(samples, context.merchantWords)), ...detectOffVoiceCopy(samples, null));
|
|
634
|
+
return {
|
|
635
|
+
value: findings.violations.length ? null : {
|
|
636
|
+
categories,
|
|
637
|
+
discounts
|
|
638
|
+
},
|
|
639
|
+
violations: findings.violations,
|
|
640
|
+
offending: findings.offending
|
|
641
|
+
};
|
|
642
|
+
}
|
|
643
|
+
|
|
644
|
+
//# sourceMappingURL=ai-products-tool.js.map
|