@happyvertical/smrt-planner 0.0.0-stage → 0.0.2
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 +21 -0
- package/README.md +170 -2
- package/app/404.html +80 -0
- package/app/_app/immutable/assets/0.B5zXkXe_.css +1 -0
- package/app/_app/immutable/assets/10.hpcnxvK1.css +1 -0
- package/app/_app/immutable/assets/11.D7zoXfVV.css +1 -0
- package/app/_app/immutable/assets/12.CPobm1ED.css +1 -0
- package/app/_app/immutable/assets/2.CyaWdRdI.css +1 -0
- package/app/_app/immutable/assets/3.BlPQOes8.css +1 -0
- package/app/_app/immutable/assets/8.2gQeKBp_.css +1 -0
- package/app/_app/immutable/assets/9.HOPT4xtg.css +1 -0
- package/app/_app/immutable/assets/AiSetup.Cb22AigN.css +1 -0
- package/app/_app/immutable/assets/Button.DkP0qkG9.css +1 -0
- package/app/_app/immutable/assets/ConnectTools.BgIJOOGW.css +1 -0
- package/app/_app/immutable/assets/FieldMapForm.BCU-4pO4.css +1 -0
- package/app/_app/immutable/assets/ModelPage.Dd3LcMta.css +1 -0
- package/app/_app/immutable/assets/SectionActions.CTkVuNMF.css +1 -0
- package/app/_app/immutable/assets/SectionIcons.5Udq9vN-.css +1 -0
- package/app/_app/immutable/assets/SegmentedControl.B8SrQacd.css +1 -0
- package/app/_app/immutable/assets/dist.C5nHBk_O.css +1 -0
- package/app/_app/immutable/assets/feedback.BVKAwFck.css +1 -0
- package/app/_app/immutable/assets/forms.BChZ2RWM.css +1 -0
- package/app/_app/immutable/assets/inter-latin-ext.B_-bZUTo.woff2 +0 -0
- package/app/_app/immutable/assets/inter-latin.8kRkwJBP.woff2 +0 -0
- package/app/_app/immutable/assets/jetbrains-mono-latin-ext.Bnd2h4Br.woff2 +0 -0
- package/app/_app/immutable/assets/jetbrains-mono-latin.Db4Uuiha.woff2 +0 -0
- package/app/_app/immutable/assets/ort-wasm-simd-threaded.asyncify.CxOG5pUO.wasm +0 -0
- package/app/_app/immutable/assets/percent.LH0z-ozZ.css +1 -0
- package/app/_app/immutable/assets/space-grotesk-latin-ext.wJGaI8U0.woff2 +0 -0
- package/app/_app/immutable/assets/space-grotesk-latin.DPT1xrvW.woff2 +0 -0
- package/app/_app/immutable/assets/store.CGDwHkkF.css +1 -0
- package/app/_app/immutable/assets/ui.B1A1Zl2p.css +1 -0
- package/app/_app/immutable/assets/workspace.BIMkuZDb.css +1 -0
- package/app/_app/immutable/chunks/1okeBSoq.js +1 -0
- package/app/_app/immutable/chunks/2jFBkS1C.js +1 -0
- package/app/_app/immutable/chunks/6P9zxrzU.js +1 -0
- package/app/_app/immutable/chunks/B32EWqI8.js +9 -0
- package/app/_app/immutable/chunks/B4Kevpe0.js +1 -0
- package/app/_app/immutable/chunks/BJfAXhak.js +3 -0
- package/app/_app/immutable/chunks/BKwRT_1p.js +1 -0
- package/app/_app/immutable/chunks/BQxY8kkL.js +1 -0
- package/app/_app/immutable/chunks/BS4h9ES-.js +1 -0
- package/app/_app/immutable/chunks/BWPhGFHl.js +1 -0
- package/app/_app/immutable/chunks/BYcBM-fh.js +1 -0
- package/app/_app/immutable/chunks/BegKiy2G.js +1 -0
- package/app/_app/immutable/chunks/Bjy-W4x2.js +81 -0
- package/app/_app/immutable/chunks/BnRri03M.js +1 -0
- package/app/_app/immutable/chunks/C7zBd-pD.js +1 -0
- package/app/_app/immutable/chunks/CA-A9Ngs.js +1 -0
- package/app/_app/immutable/chunks/CMhpRMKg.js +1 -0
- package/app/_app/immutable/chunks/CPRHZZeW.js +1 -0
- package/app/_app/immutable/chunks/CRQ1Pmzr.js +1 -0
- package/app/_app/immutable/chunks/CWtfVMDz.js +1 -0
- package/app/_app/immutable/chunks/CgAkqYsL.js +1 -0
- package/app/_app/immutable/chunks/Chyo8rdT.js +3 -0
- package/app/_app/immutable/chunks/Ci0DUht6.js +34 -0
- package/app/_app/immutable/chunks/CmmuWmp6.js +2 -0
- package/app/_app/immutable/chunks/CrFNLK0f.js +1 -0
- package/app/_app/immutable/chunks/CrO3W89x.js +1 -0
- package/app/_app/immutable/chunks/CsprTb3f.js +2 -0
- package/app/_app/immutable/chunks/CyUMm_Wp.js +1 -0
- package/app/_app/immutable/chunks/CygC84VT.js +2 -0
- package/app/_app/immutable/chunks/D0VgZnk1.js +1 -0
- package/app/_app/immutable/chunks/D71UrO5c.js +1 -0
- package/app/_app/immutable/chunks/D7hhQvDO.js +1 -0
- package/app/_app/immutable/chunks/DD7gpKb2.js +1 -0
- package/app/_app/immutable/chunks/DNRgqfTx.js +1 -0
- package/app/_app/immutable/chunks/DRByVC-c.js +1 -0
- package/app/_app/immutable/chunks/DVRKjN-E.js +1 -0
- package/app/_app/immutable/chunks/D_J_XtJy.js +846 -0
- package/app/_app/immutable/chunks/Dbjm4OuC.js +1 -0
- package/app/_app/immutable/chunks/Dc4q22LH.js +42 -0
- package/app/_app/immutable/chunks/Dd_uD5pT.js +1 -0
- package/app/_app/immutable/chunks/DkR8_Ws6.js +2 -0
- package/app/_app/immutable/chunks/Dp9GVO-9.js +1 -0
- package/app/_app/immutable/chunks/DqcD-WtP.js +1 -0
- package/app/_app/immutable/chunks/Dt-HX3Vu.js +1 -0
- package/app/_app/immutable/chunks/FbOxj-PF.js +69 -0
- package/app/_app/immutable/chunks/QukgIHDX.js +1 -0
- package/app/_app/immutable/chunks/WxSPP8QW.js +4 -0
- package/app/_app/immutable/chunks/Xp1g1t4n.js +3 -0
- package/app/_app/immutable/chunks/iET62IRm.js +2 -0
- package/app/_app/immutable/chunks/leQCwW2d.js +1 -0
- package/app/_app/immutable/chunks/p6bgzXiY.js +1 -0
- package/app/_app/immutable/chunks/uBIymjUX.js +1 -0
- package/app/_app/immutable/chunks/xihTtKlq.js +1 -0
- package/app/_app/immutable/entry/app.IZIJXhgq.js +2 -0
- package/app/_app/immutable/entry/start.BuaYHD1N.js +1 -0
- package/app/_app/immutable/nodes/0.m_U8WC7E.js +10 -0
- package/app/_app/immutable/nodes/1.Crw8ULhB.js +1 -0
- package/app/_app/immutable/nodes/10.1nQxyH9H.js +4 -0
- package/app/_app/immutable/nodes/11.Cw0JnQF3.js +1 -0
- package/app/_app/immutable/nodes/12.BIocA1aI.js +1 -0
- package/app/_app/immutable/nodes/2.CR5BwGnt.js +17 -0
- package/app/_app/immutable/nodes/3.1B56hgAG.js +1 -0
- package/app/_app/immutable/nodes/4.SSIC7sUh.js +1 -0
- package/app/_app/immutable/nodes/5.DgdwleDQ.js +1 -0
- package/app/_app/immutable/nodes/6.DmD9rqLU.js +1 -0
- package/app/_app/immutable/nodes/7.DdngsBmo.js +1 -0
- package/app/_app/immutable/nodes/8.D2Mszsua.js +3 -0
- package/app/_app/immutable/nodes/9.CLYsywul.js +1 -0
- package/app/_app/immutable/workers/assets/ort-wasm-simd-threaded.asyncify-CxOG5pUO.wasm +0 -0
- package/app/_app/immutable/workers/llm.worker-wfCOG_uk.js +69 -0
- package/app/_app/immutable/workers/local-speech.worker-DWbfmFUk.js +51 -0
- package/app/_app/version.json +1 -0
- package/app/ai/index.html +89 -0
- package/app/blueprint/index.html +87 -0
- package/app/cookbook/index.html +87 -0
- package/app/index.html +103 -0
- package/app/m/ads/AdDeliveryTier/index.html +96 -0
- package/app/m/ads/AdEvent/index.html +96 -0
- package/app/m/ads/AdFormat/index.html +96 -0
- package/app/m/ads/AdGroup/index.html +96 -0
- package/app/m/ads/AdVariation/index.html +96 -0
- package/app/m/analytics/AnalyticsDataStream/index.html +96 -0
- package/app/m/analytics/AnalyticsEvent/index.html +96 -0
- package/app/m/analytics/AnalyticsProperty/index.html +96 -0
- package/app/m/analytics/AnalyticsReport/index.html +96 -0
- package/app/m/approvals/ApprovalEvent/index.html +96 -0
- package/app/m/approvals/ApprovalPolicy/index.html +96 -0
- package/app/m/approvals/ApprovalRequest/index.html +96 -0
- package/app/m/assets/Asset/index.html +96 -0
- package/app/m/assets/AssetAssociation/index.html +97 -0
- package/app/m/assets/AssetMetafield/index.html +96 -0
- package/app/m/assets/AssetStatus/index.html +96 -0
- package/app/m/assets/AssetType/index.html +96 -0
- package/app/m/assets/Folder/index.html +96 -0
- package/app/m/chat/AgentSession/index.html +96 -0
- package/app/m/chat/ChatMessage/index.html +97 -0
- package/app/m/chat/ChatParticipant/index.html +97 -0
- package/app/m/chat/ChatReaction/index.html +96 -0
- package/app/m/chat/ChatRoom/index.html +96 -0
- package/app/m/chat/ChatThread/index.html +97 -0
- package/app/m/chat/VoiceGatewayTurn/index.html +96 -0
- package/app/m/chat/VoiceSession/index.html +96 -0
- package/app/m/commerce/Agreement/index.html +96 -0
- package/app/m/commerce/Cart/index.html +96 -0
- package/app/m/commerce/Contract/index.html +96 -0
- package/app/m/commerce/ContractLineItem/index.html +97 -0
- package/app/m/commerce/Customer/index.html +96 -0
- package/app/m/commerce/Estimate/index.html +96 -0
- package/app/m/commerce/Fulfillment/index.html +96 -0
- package/app/m/commerce/FulfillmentLineItem/index.html +97 -0
- package/app/m/commerce/Invoice/index.html +96 -0
- package/app/m/commerce/InvoiceLineItem/index.html +97 -0
- package/app/m/commerce/Lease/index.html +96 -0
- package/app/m/commerce/LicenseSale/index.html +96 -0
- package/app/m/commerce/Order/index.html +96 -0
- package/app/m/commerce/Payment/index.html +96 -0
- package/app/m/commerce/PaymentAllocation/index.html +97 -0
- package/app/m/commerce/PaymentInstrument/index.html +96 -0
- package/app/m/commerce/PaymentIntent/index.html +96 -0
- package/app/m/commerce/Payout/index.html +96 -0
- package/app/m/commerce/ProductionOrder/index.html +96 -0
- package/app/m/commerce/PurchaseOrder/index.html +96 -0
- package/app/m/commerce/Vendor/index.html +96 -0
- package/app/m/commerce/WholesaleOrder/index.html +96 -0
- package/app/m/content/Content/index.html +96 -0
- package/app/m/content/ContentContribution/index.html +96 -0
- package/app/m/content/ContentContributionAttachment/index.html +96 -0
- package/app/m/content/ContentContributionRevision/index.html +96 -0
- package/app/m/content/ContentContributionType/index.html +96 -0
- package/app/m/content/ContentContributor/index.html +96 -0
- package/app/m/content/ContentCorrection/index.html +96 -0
- package/app/m/content/ContentFeedSource/index.html +96 -0
- package/app/m/content/ContentGovernanceAssignment/index.html +96 -0
- package/app/m/content/ContentGovernancePolicy/index.html +96 -0
- package/app/m/content/ContentGovernanceProfile/index.html +96 -0
- package/app/m/content/ContentReference/index.html +96 -0
- package/app/m/content/ContentReview/index.html +96 -0
- package/app/m/content/ContentVersion/index.html +96 -0
- package/app/m/content/Contents/index.html +96 -0
- package/app/m/events/Event/index.html +96 -0
- package/app/m/events/EventParticipant/index.html +97 -0
- package/app/m/events/EventSeries/index.html +96 -0
- package/app/m/events/EventType/index.html +96 -0
- package/app/m/facts/Fact/index.html +96 -0
- package/app/m/facts/FactContent/index.html +96 -0
- package/app/m/facts/FactEvidence/index.html +96 -0
- package/app/m/facts/FactSource/index.html +96 -0
- package/app/m/facts/FactSubject/index.html +96 -0
- package/app/m/facts/FactTag/index.html +96 -0
- package/app/m/fields/FieldPolicy/index.html +96 -0
- package/app/m/fields/FieldPolicySuggestion/index.html +96 -0
- package/app/m/fields/FieldUsageCounter/index.html +96 -0
- package/app/m/images/Image/index.html +96 -0
- package/app/m/inventory/InventoryLocation/index.html +96 -0
- package/app/m/inventory/StockLevel/index.html +96 -0
- package/app/m/inventory/StockMovement/index.html +96 -0
- package/app/m/ledgers/Account/index.html +96 -0
- package/app/m/ledgers/Journal/index.html +96 -0
- package/app/m/ledgers/JournalEntry/index.html +97 -0
- package/app/m/manufacturing/Assembly/index.html +96 -0
- package/app/m/manufacturing/BillOfMaterials/index.html +96 -0
- package/app/m/manufacturing/BomLine/index.html +96 -0
- package/app/m/manufacturing/Operation/index.html +96 -0
- package/app/m/manufacturing/ProductionRun/index.html +96 -0
- package/app/m/manufacturing/ProductionRunCompletion/index.html +96 -0
- package/app/m/manufacturing/RoutingStep/index.html +96 -0
- package/app/m/marketing/Campaign/index.html +96 -0
- package/app/m/marketing/CampaignChannel/index.html +96 -0
- package/app/m/marketing/CampaignMetricSnapshot/index.html +96 -0
- package/app/m/messages/Account/index.html +96 -0
- package/app/m/messages/Attachment/index.html +96 -0
- package/app/m/messages/Blacklist/index.html +96 -0
- package/app/m/messages/Email/failed-sends/index.html +96 -0
- package/app/m/messages/Email/index.html +96 -0
- package/app/m/messages/Email/mailbox/index.html +96 -0
- package/app/m/messages/EmailAccount/index.html +96 -0
- package/app/m/messages/EmailFolder/index.html +96 -0
- package/app/m/messages/Message/index.html +96 -0
- package/app/m/messages/MessagingEndpoint/index.html +96 -0
- package/app/m/messages/PersonaMessageRoute/index.html +96 -0
- package/app/m/messages/SlackAccount/index.html +96 -0
- package/app/m/messages/SlackMessage/index.html +96 -0
- package/app/m/messages/TelegramAccount/index.html +96 -0
- package/app/m/messages/Tweet/index.html +96 -0
- package/app/m/messages/TwitterAccount/index.html +96 -0
- package/app/m/messages/Whitelist/index.html +96 -0
- package/app/m/messages/ZulipAccount/index.html +96 -0
- package/app/m/places/Place/index.html +96 -0
- package/app/m/places/PlaceType/index.html +96 -0
- package/app/m/preferences/UiPreferenceRecord/index.html +96 -0
- package/app/m/products/Category/index.html +96 -0
- package/app/m/products/Material/index.html +96 -0
- package/app/m/products/Product/index.html +96 -0
- package/app/m/products/Product/ingredients/index.html +96 -0
- package/app/m/products/ProductVariant/index.html +97 -0
- package/app/m/products/Sku/index.html +97 -0
- package/app/m/profiles/ApiKey/index.html +96 -0
- package/app/m/profiles/Bot/index.html +96 -0
- package/app/m/profiles/MagicLinkToken/index.html +96 -0
- package/app/m/profiles/NostrIdentity/index.html +96 -0
- package/app/m/profiles/OidcIdentity/index.html +96 -0
- package/app/m/profiles/Organization/index.html +96 -0
- package/app/m/profiles/Person/index.html +96 -0
- package/app/m/profiles/Profile/index.html +96 -0
- package/app/m/profiles/ProfileMetadata/index.html +96 -0
- package/app/m/profiles/ProfileMetafield/index.html +96 -0
- package/app/m/profiles/ProfileRelationship/index.html +96 -0
- package/app/m/profiles/ProfileRelationshipTerm/index.html +96 -0
- package/app/m/profiles/ProfileRelationshipType/index.html +96 -0
- package/app/m/profiles/ProfileType/index.html +96 -0
- package/app/m/projects/Comment/index.html +97 -0
- package/app/m/projects/Issue/index.html +96 -0
- package/app/m/projects/Label/index.html +96 -0
- package/app/m/projects/Project/index.html +96 -0
- package/app/m/projects/ProjectIntegration/index.html +96 -0
- package/app/m/projects/PullRequest/index.html +96 -0
- package/app/m/projects/Repository/index.html +96 -0
- package/app/m/properties/Property/index.html +96 -0
- package/app/m/properties/Zone/index.html +96 -0
- package/app/m/reports/RuntimeReport/index.html +96 -0
- package/app/m/reports/SmrtPrincipalReportRefreshTask/index.html +96 -0
- package/app/m/reports/SmrtReportLock/index.html +96 -0
- package/app/m/reports/SmrtReportRefreshTask/index.html +96 -0
- package/app/m/reports/SmrtReportRun/index.html +96 -0
- package/app/m/reports/SmrtReportSchedule/index.html +96 -0
- package/app/m/reports/SmrtReportWatermark/index.html +96 -0
- package/app/m/sales/AttributionException/index.html +96 -0
- package/app/m/sales/AttributionPolicy/index.html +96 -0
- package/app/m/sales/Commission/index.html +96 -0
- package/app/m/sales/CommissionAdjustment/index.html +96 -0
- package/app/m/sales/CommissionPayout/index.html +96 -0
- package/app/m/sales/CommissionPlan/index.html +96 -0
- package/app/m/sales/Earner/index.html +96 -0
- package/app/m/sales/EarnerSourceAttribution/index.html +96 -0
- package/app/m/sales/EarningEvent/index.html +96 -0
- package/app/m/sales/ExecutedAgreement/index.html +96 -0
- package/app/m/sales/Lead/index.html +96 -0
- package/app/m/sales/Opportunity/index.html +96 -0
- package/app/m/sales/OpportunityConversion/index.html +96 -0
- package/app/m/sales/PipelineDefinition/index.html +96 -0
- package/app/m/sales/PipelineStage/index.html +97 -0
- package/app/m/sales/Referral/index.html +96 -0
- package/app/m/sales/ReferralAgreement/index.html +96 -0
- package/app/m/sales/ReferralLink/index.html +96 -0
- package/app/m/sales/ReferralProgram/index.html +96 -0
- package/app/m/sales/ReferralTermSnapshot/index.html +96 -0
- package/app/m/sales/ReferralTouch/index.html +96 -0
- package/app/m/sales/Referrer/index.html +96 -0
- package/app/m/sales/SalesActivity/index.html +96 -0
- package/app/m/sales/SalesRepresentative/index.html +96 -0
- package/app/m/sites/Site/index.html +96 -0
- package/app/m/sites/SiteAgentBinding/index.html +96 -0
- package/app/m/social/OAuthState/index.html +96 -0
- package/app/m/social/SocialAccount/index.html +96 -0
- package/app/m/social/SocialPost/index.html +96 -0
- package/app/m/social/SocialPostAnalyticsSnapshot/index.html +96 -0
- package/app/m/subscriptions/BillingAdjustment/index.html +96 -0
- package/app/m/subscriptions/ClientCharge/index.html +96 -0
- package/app/m/subscriptions/CreditGrant/index.html +96 -0
- package/app/m/subscriptions/PricingRule/index.html +96 -0
- package/app/m/subscriptions/RetailCharge/index.html +96 -0
- package/app/m/subscriptions/SpendingPolicy/index.html +96 -0
- package/app/m/subscriptions/SubscriptionPlan/index.html +96 -0
- package/app/m/subscriptions/TenantSubscription/index.html +96 -0
- package/app/m/subscriptions/TenantUsageMetric/index.html +96 -0
- package/app/m/support/ServiceTimeEntry/index.html +96 -0
- package/app/m/support/SupportAiRun/index.html +96 -0
- package/app/m/support/SupportAvailability/index.html +96 -0
- package/app/m/support/SupportCase/index.html +96 -0
- package/app/m/support/SupportCaseEvent/index.html +96 -0
- package/app/m/support/SupportChannelBinding/index.html +96 -0
- package/app/m/support/SupportCharge/index.html +96 -0
- package/app/m/support/SupportCompensation/index.html +96 -0
- package/app/m/support/SupportCompensationPlan/index.html +96 -0
- package/app/m/support/SupportEscalation/index.html +96 -0
- package/app/m/support/SupportInteraction/index.html +96 -0
- package/app/m/support/SupportPlan/index.html +96 -0
- package/app/m/support/SupportPolicy/index.html +96 -0
- package/app/m/support/SupportQualification/index.html +96 -0
- package/app/m/support/SupportServiceTarget/index.html +96 -0
- package/app/m/support/SupportSpecialist/index.html +96 -0
- package/app/m/support/SupportWorkLink/index.html +96 -0
- package/app/m/tags/Tag/index.html +96 -0
- package/app/m/tags/TagAlias/index.html +96 -0
- package/app/m/timesheets/AttendanceBreak/index.html +96 -0
- package/app/m/timesheets/AttendancePunch/index.html +96 -0
- package/app/m/timesheets/ServiceChargeSnapshot/index.html +96 -0
- package/app/m/timesheets/ServiceCompensationSnapshot/index.html +96 -0
- package/app/m/timesheets/ServiceTimeEntry/index.html +96 -0
- package/app/m/users/AccessRequest/index.html +96 -0
- package/app/m/users/Group/index.html +96 -0
- package/app/m/users/GroupMember/index.html +96 -0
- package/app/m/users/GroupRole/index.html +96 -0
- package/app/m/users/Membership/index.html +97 -0
- package/app/m/users/MembershipOverride/index.html +96 -0
- package/app/m/users/Permission/index.html +96 -0
- package/app/m/users/ResourceGrant/index.html +96 -0
- package/app/m/users/Role/index.html +96 -0
- package/app/m/users/RolePermission/index.html +96 -0
- package/app/m/users/Session/index.html +96 -0
- package/app/m/users/Tenant/index.html +96 -0
- package/app/m/users/TenantIntegration/index.html +96 -0
- package/app/m/users/TenantPermissionOverride/index.html +96 -0
- package/app/m/users/User/index.html +96 -0
- package/app/m/users/UsersCliAuthRequest/index.html +96 -0
- package/app/m/users/UsersMagicLinkToken/index.html +96 -0
- package/app/m/video/Character/index.html +96 -0
- package/app/m/video/CharacterAsset/index.html +96 -0
- package/app/m/video/CompositeJob/index.html +96 -0
- package/app/m/video/Performer/index.html +96 -0
- package/app/m/video/PerformerAsset/index.html +96 -0
- package/app/m/video/Scene/index.html +96 -0
- package/app/m/video/SceneAsset/index.html +96 -0
- package/app/m/video/VideoComposition/index.html +96 -0
- package/app/m/video/VideoCompositionAsset/index.html +96 -0
- package/app/m/video/VideoSequence/index.html +96 -0
- package/app/m/video/VideoSequenceAsset/index.html +96 -0
- package/app/m/video/VideoShot/index.html +96 -0
- package/app/m/video/VideoShotAsset/index.html +96 -0
- package/app/m/video/VideoShotCharacter/index.html +96 -0
- package/app/m/video/VideoWorkflow/index.html +96 -0
- package/app/m/voice/VoiceOutput/index.html +96 -0
- package/app/m/voice/VoiceProfile/index.html +96 -0
- package/app/m/voice/VoiceSample/index.html +96 -0
- package/app/packages/ads/index.html +92 -0
- package/app/packages/analytics/index.html +92 -0
- package/app/packages/approvals/index.html +92 -0
- package/app/packages/assets/index.html +92 -0
- package/app/packages/chat/index.html +92 -0
- package/app/packages/comments/index.html +92 -0
- package/app/packages/commerce/index.html +92 -0
- package/app/packages/content/index.html +92 -0
- package/app/packages/events/index.html +92 -0
- package/app/packages/expenses/index.html +92 -0
- package/app/packages/facts/index.html +92 -0
- package/app/packages/fields/index.html +92 -0
- package/app/packages/human-resources/index.html +92 -0
- package/app/packages/images/index.html +92 -0
- package/app/packages/index.html +90 -0
- package/app/packages/inventory/index.html +92 -0
- package/app/packages/ledgers/index.html +92 -0
- package/app/packages/manufacturing/index.html +92 -0
- package/app/packages/marketing/index.html +92 -0
- package/app/packages/messages/index.html +92 -0
- package/app/packages/places/index.html +92 -0
- package/app/packages/preferences/index.html +92 -0
- package/app/packages/products/index.html +92 -0
- package/app/packages/profiles/index.html +92 -0
- package/app/packages/projects/index.html +92 -0
- package/app/packages/properties/index.html +92 -0
- package/app/packages/reports/index.html +92 -0
- package/app/packages/sales/index.html +92 -0
- package/app/packages/sites/index.html +92 -0
- package/app/packages/social/index.html +92 -0
- package/app/packages/subscriptions/index.html +92 -0
- package/app/packages/support/index.html +92 -0
- package/app/packages/tags/index.html +92 -0
- package/app/packages/timesheets/index.html +92 -0
- package/app/packages/users/index.html +92 -0
- package/app/packages/video/index.html +92 -0
- package/app/packages/voice/index.html +92 -0
- package/app/recipes/account-access/help/index.html +93 -0
- package/app/recipes/account-access/index.html +95 -0
- package/app/recipes/activity/help/index.html +93 -0
- package/app/recipes/activity/index.html +94 -0
- package/app/recipes/agreements/help/index.html +93 -0
- package/app/recipes/agreements/index.html +96 -0
- package/app/recipes/analytics.reports/help/index.html +93 -0
- package/app/recipes/analytics.reports/index.html +94 -0
- package/app/recipes/assets/help/index.html +93 -0
- package/app/recipes/assets/index.html +95 -0
- package/app/recipes/billing/help/index.html +93 -0
- package/app/recipes/billing/index.html +95 -0
- package/app/recipes/chat.assistant/help/index.html +93 -0
- package/app/recipes/chat.assistant/index.html +94 -0
- package/app/recipes/comments/help/index.html +93 -0
- package/app/recipes/comments/index.html +94 -0
- package/app/recipes/commerce.customers/help/index.html +93 -0
- package/app/recipes/commerce.customers/index.html +94 -0
- package/app/recipes/commerce.estimates/help/index.html +93 -0
- package/app/recipes/commerce.estimates/index.html +94 -0
- package/app/recipes/commerce.purchases/help/index.html +93 -0
- package/app/recipes/commerce.purchases/index.html +94 -0
- package/app/recipes/commerce.sales/help/index.html +93 -0
- package/app/recipes/commerce.sales/index.html +94 -0
- package/app/recipes/commerce.vendors/help/index.html +93 -0
- package/app/recipes/commerce.vendors/index.html +94 -0
- package/app/recipes/commerce.wholesale/help/index.html +93 -0
- package/app/recipes/commerce.wholesale/index.html +94 -0
- package/app/recipes/events.calendar/help/index.html +93 -0
- package/app/recipes/events.calendar/index.html +94 -0
- package/app/recipes/fields.form-customization/help/index.html +93 -0
- package/app/recipes/fields.form-customization/index.html +94 -0
- package/app/recipes/inventory.stock/help/index.html +93 -0
- package/app/recipes/inventory.stock/index.html +94 -0
- package/app/recipes/ledgers.bookkeeping/help/index.html +93 -0
- package/app/recipes/ledgers.bookkeeping/index.html +94 -0
- package/app/recipes/messages/help/index.html +93 -0
- package/app/recipes/messages/index.html +95 -0
- package/app/recipes/products/help/index.html +93 -0
- package/app/recipes/products/index.html +96 -0
- package/app/recipes/projects.tracker/help/index.html +93 -0
- package/app/recipes/projects.tracker/index.html +94 -0
- package/app/recipes/reports.materialized/help/index.html +93 -0
- package/app/recipes/reports.materialized/index.html +94 -0
- package/app/recipes/sales.pipeline/help/index.html +93 -0
- package/app/recipes/sales.pipeline/index.html +94 -0
- package/app/recipes/tags.taxonomy/help/index.html +93 -0
- package/app/recipes/tags.taxonomy/index.html +94 -0
- package/app/recipes/team-collaboration/help/index.html +93 -0
- package/app/recipes/team-collaboration/index.html +94 -0
- package/app/s/custom-billing/index.html +89 -0
- package/app/s/custom-buying/index.html +89 -0
- package/app/s/custom-classes/index.html +89 -0
- package/app/s/custom-jobs/index.html +89 -0
- package/app/s/custom-kitchen/index.html +89 -0
- package/app/s/custom-material/index.html +89 -0
- package/app/s/custom-members/index.html +89 -0
- package/app/s/custom-parts/index.html +89 -0
- package/app/s/custom-schedule/index.html +89 -0
- package/app/s/custom-shop/index.html +89 -0
- package/app/s/custom-wholesale/index.html +89 -0
- package/app/s/section-access-control/index.html +89 -0
- package/app/s/section-account-security/index.html +89 -0
- package/app/s/section-accounting/index.html +89 -0
- package/app/s/section-activity/index.html +89 -0
- package/app/s/section-agreements/index.html +89 -0
- package/app/s/section-analytics/index.html +89 -0
- package/app/s/section-assets/index.html +89 -0
- package/app/s/section-billing/index.html +89 -0
- package/app/s/section-calendar/index.html +89 -0
- package/app/s/section-catalog/index.html +89 -0
- package/app/s/section-chat.assistant/index.html +89 -0
- package/app/s/section-comments/index.html +89 -0
- package/app/s/section-fields.form-customization/index.html +89 -0
- package/app/s/section-messages/index.html +89 -0
- package/app/s/section-more/index.html +89 -0
- package/app/s/section-operations/index.html +89 -0
- package/app/s/section-projects/index.html +89 -0
- package/app/s/section-purchasing/index.html +89 -0
- package/app/s/section-reports.materialized/index.html +89 -0
- package/app/s/section-sales/index.html +89 -0
- package/app/s/section-taxonomy/index.html +89 -0
- package/app/s/section-team/index.html +89 -0
- package/dist/ai/echo-gate.d.ts +13 -0
- package/dist/ai/echo-gate.js +21 -0
- package/dist/ai/icons.d.ts +9 -0
- package/dist/ai/icons.js +9 -0
- package/dist/ai/instance.d.ts +3 -0
- package/dist/ai/instance.js +25 -0
- package/dist/ai/state.svelte.d.ts +130 -0
- package/dist/ai/state.svelte.js +316 -0
- package/dist/ai/status.d.ts +67 -0
- package/dist/ai/status.js +125 -0
- package/dist/assets/smrt-mark.svg +38 -0
- package/dist/assistant/change.d.ts +101 -0
- package/dist/assistant/change.js +209 -0
- package/dist/assistant/engine.d.ts +20 -0
- package/dist/assistant/engine.js +43 -0
- package/dist/assistant/llm.worker.d.ts +1 -0
- package/dist/assistant/llm.worker.js +7 -0
- package/dist/assistant/match.d.ts +59 -0
- package/dist/assistant/match.js +271 -0
- package/dist/assistant/models.d.ts +38 -0
- package/dist/assistant/models.js +57 -0
- package/dist/assistant/offers.svelte.d.ts +36 -0
- package/dist/assistant/offers.svelte.js +59 -0
- package/dist/assistant/prefs.d.ts +14 -0
- package/dist/assistant/prefs.js +32 -0
- package/dist/assistant/prompt.d.ts +23 -0
- package/dist/assistant/prompt.js +163 -0
- package/dist/assistant/session.svelte.d.ts +74 -0
- package/dist/assistant/session.svelte.js +181 -0
- package/dist/assistant/theme-undo.svelte.d.ts +38 -0
- package/dist/assistant/theme-undo.svelte.js +50 -0
- package/dist/assistant/transport.d.ts +73 -0
- package/dist/assistant/transport.js +231 -0
- package/dist/assistant/voice-host.d.ts +10 -0
- package/dist/assistant/voice-host.js +17 -0
- package/dist/assistant/voice.svelte.d.ts +107 -0
- package/dist/assistant/voice.svelte.js +261 -0
- package/dist/catalog/catalog.json +89663 -0
- package/dist/catalog/generate/build.d.ts +33 -0
- package/dist/catalog/generate/build.js +131 -0
- package/dist/catalog/generate/exclusions.d.ts +18 -0
- package/dist/catalog/generate/exclusions.js +33 -0
- package/dist/catalog/generate/extract.d.ts +90 -0
- package/dist/catalog/generate/extract.js +326 -0
- package/dist/catalog/generate/local.d.ts +8 -0
- package/dist/catalog/generate/local.js +45 -0
- package/dist/catalog/generate/recipe-demo.d.ts +11 -0
- package/dist/catalog/generate/recipe-demo.js +29 -0
- package/dist/catalog/generate/recipe-metadata.d.ts +12 -0
- package/dist/catalog/generate/recipe-metadata.js +138 -0
- package/dist/catalog/generate/registry.d.ts +14 -0
- package/dist/catalog/generate/registry.js +83 -0
- package/dist/catalog/index.d.ts +21 -0
- package/dist/catalog/index.js +53 -0
- package/dist/catalog/types.d.ts +141 -0
- package/dist/catalog/types.js +8 -0
- package/dist/components/AiSetup.svelte +528 -0
- package/dist/components/AiSetup.svelte.d.ts +8 -0
- package/dist/components/AiStatusIcons.svelte +86 -0
- package/dist/components/AiStatusIcons.svelte.d.ts +18 -0
- package/dist/components/AppSettings.svelte +100 -0
- package/dist/components/AppSettings.svelte.d.ts +10 -0
- package/dist/components/BrowserAssistant.svelte +318 -0
- package/dist/components/BrowserAssistant.svelte.d.ts +8 -0
- package/dist/components/ChildRecords.svelte +331 -0
- package/dist/components/ChildRecords.svelte.d.ts +15 -0
- package/dist/components/ConnectTools.svelte +145 -0
- package/dist/components/ConnectTools.svelte.d.ts +8 -0
- package/dist/components/CookbooksPanel.svelte +308 -0
- package/dist/components/CookbooksPanel.svelte.d.ts +3 -0
- package/dist/components/ExportPanel.svelte +217 -0
- package/dist/components/ExportPanel.svelte.d.ts +3 -0
- package/dist/components/FeatureCard.svelte +197 -0
- package/dist/components/FeatureCard.svelte.d.ts +13 -0
- package/dist/components/FeaturesPanel.svelte +155 -0
- package/dist/components/FeaturesPanel.svelte.d.ts +3 -0
- package/dist/components/FieldInput.svelte +307 -0
- package/dist/components/FieldInput.svelte.d.ts +24 -0
- package/dist/components/FieldMapForm.svelte +173 -0
- package/dist/components/FieldMapForm.svelte.d.ts +18 -0
- package/dist/components/FormWorkspace.svelte +274 -0
- package/dist/components/FormWorkspace.svelte.d.ts +19 -0
- package/dist/components/HelpView.svelte +129 -0
- package/dist/components/HelpView.svelte.d.ts +12 -0
- package/dist/components/ModelOptions.svelte +239 -0
- package/dist/components/ModelOptions.svelte.d.ts +12 -0
- package/dist/components/ModelPage.svelte +295 -0
- package/dist/components/ModelPage.svelte.d.ts +9 -0
- package/dist/components/ModelWorkspace.svelte +488 -0
- package/dist/components/ModelWorkspace.svelte.d.ts +32 -0
- package/dist/components/PlannerEditBridge.svelte +36 -0
- package/dist/components/PlannerEditBridge.svelte.d.ts +3 -0
- package/dist/components/PlannerPalette.svelte +38 -0
- package/dist/components/PlannerPalette.svelte.d.ts +18 -0
- package/dist/components/RecipeCards.svelte +145 -0
- package/dist/components/RecipeCards.svelte.d.ts +3 -0
- package/dist/components/RecipeHelp.svelte +54 -0
- package/dist/components/RecipeHelp.svelte.d.ts +9 -0
- package/dist/components/RecipeOptions.svelte +160 -0
- package/dist/components/RecipeOptions.svelte.d.ts +9 -0
- package/dist/components/RecordFeatures.svelte +240 -0
- package/dist/components/RecordFeatures.svelte.d.ts +3 -0
- package/dist/components/RelationField.svelte +175 -0
- package/dist/components/RelationField.svelte.d.ts +16 -0
- package/dist/components/SectionActions.svelte +91 -0
- package/dist/components/SectionActions.svelte.d.ts +12 -0
- package/dist/components/SectionIcons.svelte +98 -0
- package/dist/components/SectionIcons.svelte.d.ts +15 -0
- package/dist/components/SectionOverview.svelte +65 -0
- package/dist/components/SectionOverview.svelte.d.ts +14 -0
- package/dist/components/SectionPage.svelte +230 -0
- package/dist/components/SectionPage.svelte.d.ts +7 -0
- package/dist/components/SettingsPanel.svelte +60 -0
- package/dist/components/SettingsPanel.svelte.d.ts +7 -0
- package/dist/components/ThemeBridge.svelte +56 -0
- package/dist/components/ThemeBridge.svelte.d.ts +3 -0
- package/dist/components/ThemeSection.svelte +167 -0
- package/dist/components/ThemeSection.svelte.d.ts +11 -0
- package/dist/components/VariantGridForm.svelte +309 -0
- package/dist/components/VariantGridForm.svelte.d.ts +12 -0
- package/dist/components/VoiceTyping.svelte +108 -0
- package/dist/components/VoiceTyping.svelte.d.ts +7 -0
- package/dist/cookbook/assemble.d.ts +16 -0
- package/dist/cookbook/assemble.js +29 -0
- package/dist/cookbook/file.d.ts +7 -0
- package/dist/cookbook/file.js +25 -0
- package/dist/cookbook/legacy.d.ts +9 -0
- package/dist/cookbook/legacy.js +87 -0
- package/dist/cookbook/migrate.d.ts +22 -0
- package/dist/cookbook/migrate.js +106 -0
- package/dist/cookbook/parse.d.ts +16 -0
- package/dist/cookbook/parse.js +246 -0
- package/dist/cookbook/storage.d.ts +45 -0
- package/dist/cookbook/storage.js +98 -0
- package/dist/cookbook/store.svelte.d.ts +94 -0
- package/dist/cookbook/store.svelte.js +231 -0
- package/dist/cookbook/types.d.ts +76 -0
- package/dist/cookbook/types.js +11 -0
- package/dist/cookbook/validate.d.ts +14 -0
- package/dist/cookbook/validate.js +29 -0
- package/dist/core/app.d.ts +37 -0
- package/dist/core/app.js +119 -0
- package/dist/core/catalog.d.ts +19 -0
- package/dist/core/catalog.js +9 -0
- package/dist/core/headless.d.ts +52 -0
- package/dist/core/headless.js +39 -0
- package/dist/core/index.d.ts +28 -0
- package/dist/core/index.js +28 -0
- package/dist/core/prompt.d.ts +38 -0
- package/dist/core/prompt.js +95 -0
- package/dist/core/reply.d.ts +60 -0
- package/dist/core/reply.js +89 -0
- package/dist/core/request.d.ts +15 -0
- package/dist/core/request.js +55 -0
- package/dist/data/children.d.ts +20 -0
- package/dist/data/children.js +80 -0
- package/dist/data/columns.d.ts +56 -0
- package/dist/data/columns.js +150 -0
- package/dist/data/context.d.ts +8 -0
- package/dist/data/context.js +19 -0
- package/dist/data/derived.d.ts +79 -0
- package/dist/data/derived.js +139 -0
- package/dist/data/display.d.ts +23 -0
- package/dist/data/display.js +84 -0
- package/dist/data/fakes.d.ts +52 -0
- package/dist/data/fakes.js +443 -0
- package/dist/data/format.d.ts +48 -0
- package/dist/data/format.js +121 -0
- package/dist/data/labels.d.ts +45 -0
- package/dist/data/labels.js +179 -0
- package/dist/data/packs.d.ts +95 -0
- package/dist/data/packs.js +830 -0
- package/dist/data/payments.d.ts +17 -0
- package/dist/data/payments.js +60 -0
- package/dist/data/planner-source.d.ts +7 -0
- package/dist/data/planner-source.js +32 -0
- package/dist/data/source.d.ts +119 -0
- package/dist/data/source.js +432 -0
- package/dist/features/catalogue.d.ts +96 -0
- package/dist/features/catalogue.js +225 -0
- package/dist/features/demo.d.ts +36 -0
- package/dist/features/demo.js +66 -0
- package/dist/features/palette.d.ts +39 -0
- package/dist/features/palette.js +53 -0
- package/dist/fields/address.d.ts +23 -0
- package/dist/fields/address.js +39 -0
- package/dist/fields/invalid.d.ts +2 -0
- package/dist/fields/invalid.js +8 -0
- package/dist/fields/modal.d.ts +7 -0
- package/dist/fields/modal.js +14 -0
- package/dist/fields/percent.d.ts +8 -0
- package/dist/fields/percent.js +16 -0
- package/dist/fields/renderer.d.ts +17 -0
- package/dist/fields/renderer.js +43 -0
- package/dist/forms/active.d.ts +16 -0
- package/dist/forms/active.js +24 -0
- package/dist/forms/fieldMap.d.ts +44 -0
- package/dist/forms/fieldMap.js +134 -0
- package/dist/forms/shared.d.ts +41 -0
- package/dist/forms/shared.js +138 -0
- package/dist/forms/stock.d.ts +28 -0
- package/dist/forms/stock.js +104 -0
- package/dist/forms/variantGrid.d.ts +83 -0
- package/dist/forms/variantGrid.js +283 -0
- package/dist/index.d.ts +17 -0
- package/dist/index.js +16 -0
- package/dist/inference/byo.svelte.d.ts +90 -0
- package/dist/inference/byo.svelte.js +295 -0
- package/dist/inference/config.d.ts +77 -0
- package/dist/inference/config.js +205 -0
- package/dist/inference/host.d.ts +40 -0
- package/dist/inference/host.js +57 -0
- package/dist/inference/openai.d.ts +59 -0
- package/dist/inference/openai.js +207 -0
- package/dist/inference/presets.d.ts +5 -0
- package/dist/inference/presets.js +46 -0
- package/dist/kitchen/client.d.ts +39 -0
- package/dist/kitchen/client.js +115 -0
- package/dist/kitchen/fragment.d.ts +30 -0
- package/dist/kitchen/fragment.js +49 -0
- package/dist/kitchen/state.svelte.d.ts +26 -0
- package/dist/kitchen/state.svelte.js +45 -0
- package/dist/library/apply.d.ts +17 -0
- package/dist/library/apply.js +32 -0
- package/dist/library/document.d.ts +12 -0
- package/dist/library/document.js +27 -0
- package/dist/library/icons.d.ts +6 -0
- package/dist/library/icons.js +26 -0
- package/dist/library/index.d.ts +8 -0
- package/dist/library/index.js +12 -0
- package/dist/library/library.json +788 -0
- package/dist/library/menu.d.ts +18 -0
- package/dist/library/menu.js +72 -0
- package/dist/library/state.svelte.d.ts +10 -0
- package/dist/library/state.svelte.js +28 -0
- package/dist/library/types.d.ts +57 -0
- package/dist/library/types.js +1 -0
- package/dist/overviews/definitions.d.ts +24 -0
- package/dist/overviews/definitions.js +97 -0
- package/dist/overviews/page.d.ts +21 -0
- package/dist/overviews/page.js +36 -0
- package/dist/overviews/registry.d.ts +44 -0
- package/dist/overviews/registry.js +191 -0
- package/dist/overviews/validate.d.ts +32 -0
- package/dist/overviews/validate.js +91 -0
- package/dist/planner/Planner.svelte +204 -0
- package/dist/planner/Planner.svelte.d.ts +4 -0
- package/dist/planner/app.svelte.d.ts +6 -0
- package/dist/planner/app.svelte.js +23 -0
- package/dist/planner/assistant.d.ts +46 -0
- package/dist/planner/assistant.js +122 -0
- package/dist/planner/commands/adapter.d.ts +121 -0
- package/dist/planner/commands/adapter.js +597 -0
- package/dist/planner/commands/catalog.d.ts +19 -0
- package/dist/planner/commands/catalog.js +54 -0
- package/dist/planner/commands/controller.svelte.d.ts +13 -0
- package/dist/planner/commands/controller.svelte.js +77 -0
- package/dist/planner/commands/index.d.ts +15 -0
- package/dist/planner/commands/index.js +15 -0
- package/dist/planner/commands/schemas.d.ts +25 -0
- package/dist/planner/commands/schemas.js +67 -0
- package/dist/planner/commands/slices.d.ts +18 -0
- package/dist/planner/commands/slices.js +49 -0
- package/dist/planner/commands/types.d.ts +80 -0
- package/dist/planner/commands/types.js +18 -0
- package/dist/planner/create.d.ts +4 -0
- package/dist/planner/create.js +22 -0
- package/dist/planner/instance.d.ts +15 -0
- package/dist/planner/instance.js +22 -0
- package/dist/planner/query.d.ts +16 -0
- package/dist/planner/query.js +28 -0
- package/dist/planner/selection.d.ts +15 -0
- package/dist/planner/selection.js +38 -0
- package/dist/planner/selection.svelte.d.ts +29 -0
- package/dist/planner/selection.svelte.js +54 -0
- package/dist/planner/tab.svelte.d.ts +11 -0
- package/dist/planner/tab.svelte.js +22 -0
- package/dist/planner/types.d.ts +41 -0
- package/dist/planner/types.js +1 -0
- package/dist/recipes/cards.d.ts +55 -0
- package/dist/recipes/cards.js +80 -0
- package/dist/recipes/features.d.ts +53 -0
- package/dist/recipes/features.js +97 -0
- package/dist/recipes/help/descriptions.json +373 -0
- package/dist/recipes/help.d.ts +121 -0
- package/dist/recipes/help.js +262 -0
- package/dist/recipes/index.d.ts +65 -0
- package/dist/recipes/index.js +95 -0
- package/dist/recipes/merge.d.ts +26 -0
- package/dist/recipes/merge.js +21 -0
- package/dist/recipes/overlay.json +409 -0
- package/dist/recipes/plan-data.d.ts +41 -0
- package/dist/recipes/plan-data.js +97 -0
- package/dist/recipes/plumbing.d.ts +70 -0
- package/dist/recipes/plumbing.js +185 -0
- package/dist/recipes/policy.d.ts +118 -0
- package/dist/recipes/policy.js +268 -0
- package/dist/recipes/resolve.d.ts +19 -0
- package/dist/recipes/resolve.js +65 -0
- package/dist/recipes/scope.d.ts +25 -0
- package/dist/recipes/scope.js +31 -0
- package/dist/recipes/sections.d.ts +49 -0
- package/dist/recipes/sections.js +84 -0
- package/dist/recipes/state.svelte.d.ts +67 -0
- package/dist/recipes/state.svelte.js +112 -0
- package/dist/recipes/types.d.ts +322 -0
- package/dist/recipes/types.js +8 -0
- package/dist/sections/entries.d.ts +30 -0
- package/dist/sections/entries.js +57 -0
- package/dist/sections/info.d.ts +16 -0
- package/dist/sections/info.js +39 -0
- package/dist/sections/path.d.ts +12 -0
- package/dist/sections/path.js +18 -0
- package/dist/settings/app-settings.d.ts +44 -0
- package/dist/settings/app-settings.js +138 -0
- package/dist/settings/currencies.d.ts +2 -0
- package/dist/settings/currencies.js +8 -0
- package/dist/theme/runtime.d.ts +14 -0
- package/dist/theme/runtime.js +27 -0
- package/dist/theme/theme.d.ts +47 -0
- package/dist/theme/theme.js +122 -0
- package/dist/upstream/CustomerSelect.svelte +60 -0
- package/dist/upstream/CustomerSelect.svelte.d.ts +17 -0
- package/dist/upstream/VendorSelect.svelte +60 -0
- package/dist/upstream/VendorSelect.svelte.d.ts +17 -0
- package/dist/upstream/overlay.d.ts +10 -0
- package/dist/upstream/overlay.js +49 -0
- package/dist/upstream/partySelect.d.ts +8 -0
- package/dist/upstream/partySelect.js +21 -0
- package/dist/upstream/partyTypes.d.ts +64 -0
- package/dist/upstream/partyTypes.js +8 -0
- package/dist/upstream/relations.d.ts +2 -0
- package/dist/upstream/relations.js +24 -0
- package/dist/upstream/selects.d.ts +26 -0
- package/dist/upstream/selects.js +20 -0
- package/dist/upstream/widgets.d.ts +20 -0
- package/dist/upstream/widgets.js +30 -0
- package/package.json +81 -3
|
@@ -0,0 +1,185 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Plumbing vs feature. The Features tab lists models a visitor can add to the
|
|
3
|
+
* menu; most of the ~220 uncovered models are rows that only make sense inside
|
|
4
|
+
* another model (a line item, a link table, a lookup list), so they are hidden
|
|
5
|
+
* unless "Show all" is on. The rules are data-driven where the catalog allows:
|
|
6
|
+
*
|
|
7
|
+
* 1. Extends a junction/association base (`SmrtJunction`, `SmrtJunctionBase`,
|
|
8
|
+
* `SmrtPolymorphicAssociation`). The catalog keeps `extends` only for
|
|
9
|
+
* same-package STI parents, so this fires once the generator carries bases.
|
|
10
|
+
* 2. Looks like a link table: two or more foreign keys and at most one other
|
|
11
|
+
* own field (`GroupMember`, `RolePermission`, `ProfileMetadata`).
|
|
12
|
+
* 3. Child/extension record, by name suffix: `Metafield`, `Metadata`,
|
|
13
|
+
* `Association`, `LineItem`, `Allocation`, `Revision`, `Attachment`,
|
|
14
|
+
* `Snapshot`, `Completion`, `Override`, `Alias`. Each appears in the catalog
|
|
15
|
+
* only as a dependent of a parent model (`InvoiceLineItem`,
|
|
16
|
+
* `ContentContributionRevision`, `CampaignMetricSnapshot`).
|
|
17
|
+
* 4. Tiny lookup list: a name ending `Status` or `Type` with at most three
|
|
18
|
+
* non-system fields (`AssetStatus`, `PlaceType`, `ProfileType`). Richer
|
|
19
|
+
* types such as `ContentContributionType` stay features.
|
|
20
|
+
*/
|
|
21
|
+
export const JUNCTION_BASES = [
|
|
22
|
+
'SmrtJunction',
|
|
23
|
+
'SmrtJunctionBase',
|
|
24
|
+
'SmrtPolymorphicAssociation',
|
|
25
|
+
];
|
|
26
|
+
export const CHILD_SUFFIXES = [
|
|
27
|
+
'Metafield',
|
|
28
|
+
'Metadata',
|
|
29
|
+
'Association',
|
|
30
|
+
'LineItem',
|
|
31
|
+
'Allocation',
|
|
32
|
+
'Revision',
|
|
33
|
+
'Attachment',
|
|
34
|
+
'Snapshot',
|
|
35
|
+
'Completion',
|
|
36
|
+
'Override',
|
|
37
|
+
'Alias',
|
|
38
|
+
];
|
|
39
|
+
export const LOOKUP_SUFFIXES = ['Status', 'Type'];
|
|
40
|
+
export const LOOKUP_MAX_FIELDS = 3;
|
|
41
|
+
export const LINK_MIN_REFS = 2;
|
|
42
|
+
export const LINK_MAX_OTHER_FIELDS = 1;
|
|
43
|
+
const REF_TYPES = new Set(['foreignKey', 'crossPackageRef']);
|
|
44
|
+
/** The reason a model is plumbing, or null when it is a feature. */
|
|
45
|
+
export function plumbingReason(model) {
|
|
46
|
+
const base = model.extends?.split(':').pop();
|
|
47
|
+
if (base && JUNCTION_BASES.includes(base))
|
|
48
|
+
return 'junction';
|
|
49
|
+
const own = model.fields.filter((f) => !f.system);
|
|
50
|
+
const refs = own.filter((f) => REF_TYPES.has(f.type)).length;
|
|
51
|
+
if (refs >= LINK_MIN_REFS && own.length - refs <= LINK_MAX_OTHER_FIELDS) {
|
|
52
|
+
return 'link';
|
|
53
|
+
}
|
|
54
|
+
if (CHILD_SUFFIXES.some((s) => model.name.endsWith(s)))
|
|
55
|
+
return 'child';
|
|
56
|
+
if (own.length <= LOOKUP_MAX_FIELDS &&
|
|
57
|
+
LOOKUP_SUFFIXES.some((s) => model.name.endsWith(s))) {
|
|
58
|
+
return 'lookup';
|
|
59
|
+
}
|
|
60
|
+
return null;
|
|
61
|
+
}
|
|
62
|
+
export function isPlumbing(model) {
|
|
63
|
+
return plumbingReason(model) !== null;
|
|
64
|
+
}
|
|
65
|
+
/** Plumbing reasons that make a model a dependent record of what it points at. */
|
|
66
|
+
const CHILD_REASONS = new Set(['junction', 'link', 'child']);
|
|
67
|
+
/** A field's `related` as a qualified name, given the package it is declared in. */
|
|
68
|
+
function qualify(related, ownerId) {
|
|
69
|
+
return related.includes(':')
|
|
70
|
+
? related
|
|
71
|
+
: `${ownerId.slice(0, ownerId.lastIndexOf(':'))}:${related}`;
|
|
72
|
+
}
|
|
73
|
+
/**
|
|
74
|
+
* The model and its STI ancestors, nearest first (`ProductionOrder` extends
|
|
75
|
+
* `Contract`, whose `ContractLineItem` rows belong to every Contract subtype).
|
|
76
|
+
*/
|
|
77
|
+
function lineage(byId, modelId) {
|
|
78
|
+
const ids = [];
|
|
79
|
+
let current = byId.get(modelId);
|
|
80
|
+
while (current && !ids.includes(current.id)) {
|
|
81
|
+
ids.push(current.id);
|
|
82
|
+
current = current.extends
|
|
83
|
+
? byId.get(qualify(current.extends, current.id))
|
|
84
|
+
: undefined;
|
|
85
|
+
}
|
|
86
|
+
return ids;
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Child records of a model, found from the catalog: models with a foreign key
|
|
90
|
+
* to the model (or to a model it extends) that are line items, allocations,
|
|
91
|
+
* link tables and the like (`plumbingReason` of junction, link or child, never
|
|
92
|
+
* a plain lookup list). They ride along with the model and have no menu entry.
|
|
93
|
+
*/
|
|
94
|
+
export function childModels(catalog, modelId) {
|
|
95
|
+
const all = catalog.packages.flatMap((p) => p.models);
|
|
96
|
+
const byId = new Map(all.map((m) => [m.id, m]));
|
|
97
|
+
const parents = new Set(lineage(byId, modelId));
|
|
98
|
+
if (!parents.size)
|
|
99
|
+
return [];
|
|
100
|
+
return all.filter((candidate) => {
|
|
101
|
+
if (parents.has(candidate.id))
|
|
102
|
+
return false;
|
|
103
|
+
const reason = plumbingReason(candidate);
|
|
104
|
+
if (!reason || !CHILD_REASONS.has(reason))
|
|
105
|
+
return false;
|
|
106
|
+
return candidate.fields.some((f) => REF_TYPES.has(f.type) &&
|
|
107
|
+
f.related &&
|
|
108
|
+
parents.has(qualify(f.related, candidate.id)));
|
|
109
|
+
});
|
|
110
|
+
}
|
|
111
|
+
function linkTo(candidate, parents) {
|
|
112
|
+
const field = candidate.fields.find((f) => REF_TYPES.has(f.type) &&
|
|
113
|
+
f.related &&
|
|
114
|
+
parents.has(qualify(f.related, candidate.id)));
|
|
115
|
+
return field ? { model: candidate, fk: field.name } : undefined;
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* The records that live inside a model's own record view. When the model is in
|
|
119
|
+
* a recipe, a child is a model the recipe lists but gives no menu entry (so it
|
|
120
|
+
* has no page of its own) whose foreign key targets the model or a class it
|
|
121
|
+
* extends: `ContractLineItem` under every Contract subtype, `InvoiceLineItem`
|
|
122
|
+
* and `PaymentAllocation` under Invoice, `JournalEntry` under Journal. A model
|
|
123
|
+
* in no recipe (a Feature) falls back to {@link childModels}.
|
|
124
|
+
*/
|
|
125
|
+
export function childLinks(catalog, recipes, modelId) {
|
|
126
|
+
const all = catalog.packages.flatMap((p) => p.models);
|
|
127
|
+
const byId = new Map(all.map((m) => [m.id, m]));
|
|
128
|
+
const parents = new Set(lineage(byId, modelId));
|
|
129
|
+
if (!parents.size)
|
|
130
|
+
return [];
|
|
131
|
+
const scoped = recipes.filter((r) => r.models.includes(modelId));
|
|
132
|
+
if (!scoped.length) {
|
|
133
|
+
return childModels(catalog, modelId).flatMap((m) => {
|
|
134
|
+
const link = linkTo(m, parents);
|
|
135
|
+
return link ? [link] : [];
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
const found = new Map();
|
|
139
|
+
for (const recipe of scoped) {
|
|
140
|
+
const navIds = new Set(recipe.nav.map((e) => e.model));
|
|
141
|
+
for (const id of recipe.models) {
|
|
142
|
+
const candidate = byId.get(id);
|
|
143
|
+
if (!candidate || navIds.has(id) || parents.has(id) || found.has(id)) {
|
|
144
|
+
continue;
|
|
145
|
+
}
|
|
146
|
+
const link = linkTo(candidate, parents);
|
|
147
|
+
if (link)
|
|
148
|
+
found.set(id, link);
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
return [...found.values()];
|
|
152
|
+
}
|
|
153
|
+
/** Does any recipe give the model a menu entry of its own? */
|
|
154
|
+
export function hasNavPage(recipes, modelId) {
|
|
155
|
+
return recipes.some((r) => r.nav.some((e) => e.model === modelId));
|
|
156
|
+
}
|
|
157
|
+
/**
|
|
158
|
+
* Title of a child table: the child's name without the parent's prefix,
|
|
159
|
+
* pluralised ("ContractLineItem" under Agreement/Contract is "Line items").
|
|
160
|
+
*/
|
|
161
|
+
export function childTitle(childName, parentNames) {
|
|
162
|
+
let name = childName;
|
|
163
|
+
for (const parent of parentNames) {
|
|
164
|
+
if (name.length > parent.length && name.startsWith(parent)) {
|
|
165
|
+
name = name.slice(parent.length);
|
|
166
|
+
break;
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
const spaced = name.replace(/([a-z0-9])([A-Z])/g, '$1 $2').toLowerCase();
|
|
170
|
+
const plural = /[^aeiou]y$/.test(spaced)
|
|
171
|
+
? `${spaced.slice(0, -1)}ies`
|
|
172
|
+
: /(s|x|ch|sh)$/.test(spaced)
|
|
173
|
+
? `${spaced}es`
|
|
174
|
+
: `${spaced}s`;
|
|
175
|
+
return plural.charAt(0).toUpperCase() + plural.slice(1);
|
|
176
|
+
}
|
|
177
|
+
/** Names of the model and its STI ancestors, for {@link childTitle}. */
|
|
178
|
+
export function lineageNames(catalog, modelId) {
|
|
179
|
+
const all = catalog.packages.flatMap((p) => p.models);
|
|
180
|
+
const byId = new Map(all.map((m) => [m.id, m]));
|
|
181
|
+
return lineage(byId, modelId).flatMap((id) => {
|
|
182
|
+
const m = byId.get(id);
|
|
183
|
+
return m ? [m.name] : [];
|
|
184
|
+
});
|
|
185
|
+
}
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
import type { CatalogField, CatalogModel } from '../catalog/types.ts';
|
|
2
|
+
import type { ExposureSurface, RecipeModelHints } from './types.ts';
|
|
3
|
+
/**
|
|
4
|
+
* Field policies in the vocabulary of `@happyvertical/smrt-fields`
|
|
5
|
+
* (`FieldPolicyOptions`, `FieldPolicyVisibility`). The shapes are mirrored
|
|
6
|
+
* here, not imported: the package becomes a dependency with PGlite in
|
|
7
|
+
* smrt-planner#4, when these rows become real `_smrt_field_policies` rows.
|
|
8
|
+
*/
|
|
9
|
+
export type FieldPolicyVisibility = 'basic' | 'advanced' | 'hidden';
|
|
10
|
+
/**
|
|
11
|
+
* One stored policy row, as `FieldPolicyOptions` names it. Only the keys a
|
|
12
|
+
* person changed are present; everything else inherits from the code seed (the
|
|
13
|
+
* catalog's `ui` hints plus the recipe's hints).
|
|
14
|
+
*/
|
|
15
|
+
export interface FieldPolicyRow {
|
|
16
|
+
/** Qualified class name, `@scope/pkg:Class`. */
|
|
17
|
+
objectRef: string;
|
|
18
|
+
fieldName: string;
|
|
19
|
+
/** The planner writes app-scope rows only. */
|
|
20
|
+
scopeType: 'app';
|
|
21
|
+
/** ENCODED channel: JSON text exactly as the column stores it (`'"Net 30"'`). */
|
|
22
|
+
defaultValue?: string | null;
|
|
23
|
+
visibility?: FieldPolicyVisibility | null;
|
|
24
|
+
help?: string | null;
|
|
25
|
+
label?: string | null;
|
|
26
|
+
displayOrder?: number | null;
|
|
27
|
+
locked?: boolean | null;
|
|
28
|
+
}
|
|
29
|
+
/** A field's merged policy: catalog hints, then recipe hints, then rows. */
|
|
30
|
+
export interface ResolvedField {
|
|
31
|
+
field: CatalogField;
|
|
32
|
+
visibility: FieldPolicyVisibility;
|
|
33
|
+
label: string;
|
|
34
|
+
help: string | null;
|
|
35
|
+
order: number;
|
|
36
|
+
group: string | null;
|
|
37
|
+
/** Policy-locked: rows may not change it. */
|
|
38
|
+
locked: boolean;
|
|
39
|
+
required: boolean;
|
|
40
|
+
hasDefault: boolean;
|
|
41
|
+
default: unknown;
|
|
42
|
+
/** The required-field invariant forced `basic`. */
|
|
43
|
+
visibilityForced?: boolean;
|
|
44
|
+
}
|
|
45
|
+
/** A field as the generated list and form show it. */
|
|
46
|
+
export interface ViewField extends CatalogField {
|
|
47
|
+
label: string;
|
|
48
|
+
help?: string;
|
|
49
|
+
}
|
|
50
|
+
/** Fields a person edits: everything the framework does not manage. */
|
|
51
|
+
export declare function policyFields(model: CatalogModel): CatalogField[];
|
|
52
|
+
/**
|
|
53
|
+
* The single-table-inheritance discriminator: an enumerated `...Type` field of
|
|
54
|
+
* a subclass that lists the model's own snake_case name, like `contractType`
|
|
55
|
+
* on a ProductionOrder. A root class's own enumeration (a Product's
|
|
56
|
+
* `productType`: product, material) is data, not a discriminator. It tells the classes of a shared table
|
|
57
|
+
* apart, so a form never offers it.
|
|
58
|
+
*/
|
|
59
|
+
export declare function isDiscriminatorField(model: CatalogModel, field: CatalogField): boolean;
|
|
60
|
+
/**
|
|
61
|
+
* Merge a model's field policies: catalog `ui` hints and the recipe's hints are
|
|
62
|
+
* the code seed, `rows` (app scope) layer on top. A locked field ignores rows
|
|
63
|
+
* unless a row explicitly unlocks it. Result is ordered by `order`, then by
|
|
64
|
+
* declaration.
|
|
65
|
+
*/
|
|
66
|
+
export declare function resolveFields(model: CatalogModel, hints: RecipeModelHints | undefined, rows?: readonly FieldPolicyRow[]): ResolvedField[];
|
|
67
|
+
/** The fields the generated list and form show: basic ones, policy applied. */
|
|
68
|
+
export declare function viewFields(resolved: readonly ResolvedField[]): ViewField[];
|
|
69
|
+
/**
|
|
70
|
+
* Defaults for fields the views do not show (hidden or off), so records still
|
|
71
|
+
* carry them: the `contractType` discriminator of a shared Contract table.
|
|
72
|
+
*/
|
|
73
|
+
export declare function backgroundDefaults(resolved: readonly ResolvedField[]): Record<string, unknown>;
|
|
74
|
+
/** What the options form edits for one field. */
|
|
75
|
+
export interface FieldDraft {
|
|
76
|
+
/** The "use this field" switch. */
|
|
77
|
+
use: boolean;
|
|
78
|
+
label: string;
|
|
79
|
+
help: string;
|
|
80
|
+
default: unknown;
|
|
81
|
+
order: number;
|
|
82
|
+
}
|
|
83
|
+
export type ExposureDraft = Record<ExposureSurface, boolean>;
|
|
84
|
+
export interface ModelDraft {
|
|
85
|
+
fields: Record<string, FieldDraft>;
|
|
86
|
+
exposure: ExposureDraft;
|
|
87
|
+
}
|
|
88
|
+
export declare const SURFACES: readonly ExposureSurface[];
|
|
89
|
+
export declare const SURFACE_LABEL: Record<ExposureSurface, string>;
|
|
90
|
+
export declare function surfaceAvailable(model: CatalogModel, surface: ExposureSurface): boolean;
|
|
91
|
+
export interface ExposureState {
|
|
92
|
+
/** The class declares this surface. */
|
|
93
|
+
available: boolean;
|
|
94
|
+
/** Currently exposed. */
|
|
95
|
+
on: boolean;
|
|
96
|
+
/** Cannot be changed: the class has none, or the recipe already narrowed it. */
|
|
97
|
+
locked: boolean;
|
|
98
|
+
}
|
|
99
|
+
/**
|
|
100
|
+
* Exposure can only be narrowed: a surface is on when the class declares it,
|
|
101
|
+
* the recipe did not narrow it off, and the person did not switch it off.
|
|
102
|
+
*/
|
|
103
|
+
export declare function resolveExposure(model: CatalogModel, hints: RecipeModelHints | undefined, narrowed?: readonly ExposureSurface[]): Record<ExposureSurface, ExposureState>;
|
|
104
|
+
/** The model as exposed: narrowed surfaces list nothing. */
|
|
105
|
+
export declare function narrowModel(model: CatalogModel, exposure: Record<ExposureSurface, ExposureState>): CatalogModel;
|
|
106
|
+
/** Fields the options form lets a person switch off or edit. */
|
|
107
|
+
export declare function formFields(model: CatalogModel, hints: RecipeModelHints | undefined, rows?: readonly FieldPolicyRow[]): ResolvedField[];
|
|
108
|
+
/** Can the "use this field" switch move? Required and locked fields cannot. */
|
|
109
|
+
export declare function isFieldLockedOn(r: ResolvedField): boolean;
|
|
110
|
+
export declare function draftFrom(model: CatalogModel, hints: RecipeModelHints | undefined, rows: readonly FieldPolicyRow[], narrowed: readonly ExposureSurface[]): ModelDraft;
|
|
111
|
+
/**
|
|
112
|
+
* Turn a draft into app-scope policy rows. Only differences from the code seed
|
|
113
|
+
* are written, so an untouched form writes nothing and a row never repeats a
|
|
114
|
+
* value the seed already gives.
|
|
115
|
+
*/
|
|
116
|
+
export declare function rowsFromDraft(model: CatalogModel, hints: RecipeModelHints | undefined, draft: ModelDraft): FieldPolicyRow[];
|
|
117
|
+
/** The surfaces a draft switches off, beyond what the recipe already narrowed. */
|
|
118
|
+
export declare function narrowedFromDraft(model: CatalogModel, hints: RecipeModelHints | undefined, draft: ModelDraft): ExposureSurface[];
|
|
@@ -0,0 +1,268 @@
|
|
|
1
|
+
import { fieldLabel } from "../data/format.js";
|
|
2
|
+
/** Fields a person edits: everything the framework does not manage. */
|
|
3
|
+
export function policyFields(model) {
|
|
4
|
+
return model.fields.filter((f) => !f.system);
|
|
5
|
+
}
|
|
6
|
+
const snakeCase = (name) => name.replace(/([a-z0-9])([A-Z])/g, '$1_$2').toLowerCase();
|
|
7
|
+
/**
|
|
8
|
+
* The single-table-inheritance discriminator: an enumerated `...Type` field of
|
|
9
|
+
* a subclass that lists the model's own snake_case name, like `contractType`
|
|
10
|
+
* on a ProductionOrder. A root class's own enumeration (a Product's
|
|
11
|
+
* `productType`: product, material) is data, not a discriminator. It tells the classes of a shared table
|
|
12
|
+
* apart, so a form never offers it.
|
|
13
|
+
*/
|
|
14
|
+
export function isDiscriminatorField(model, field) {
|
|
15
|
+
return (/Type$/.test(field.name) &&
|
|
16
|
+
Array.isArray(field.enum) &&
|
|
17
|
+
field.enum.length > 0 &&
|
|
18
|
+
Boolean(model.extends) &&
|
|
19
|
+
field.enum.includes(snakeCase(model.name)));
|
|
20
|
+
}
|
|
21
|
+
/** The cold-start rule: with no `ui.basic` marker anywhere, all fields are basic. */
|
|
22
|
+
function hasBasicMarkers(fields) {
|
|
23
|
+
return fields.some((f) => f.ui?.basic === true);
|
|
24
|
+
}
|
|
25
|
+
function usableRequiredDefault(value) {
|
|
26
|
+
return value !== null && value !== undefined && value !== '';
|
|
27
|
+
}
|
|
28
|
+
function parseDefault(encoded) {
|
|
29
|
+
if (encoded === null || encoded === undefined)
|
|
30
|
+
return null;
|
|
31
|
+
try {
|
|
32
|
+
return { value: JSON.parse(encoded) };
|
|
33
|
+
}
|
|
34
|
+
catch {
|
|
35
|
+
return null;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Merge a model's field policies: catalog `ui` hints and the recipe's hints are
|
|
40
|
+
* the code seed, `rows` (app scope) layer on top. A locked field ignores rows
|
|
41
|
+
* unless a row explicitly unlocks it. Result is ordered by `order`, then by
|
|
42
|
+
* declaration.
|
|
43
|
+
*/
|
|
44
|
+
export function resolveFields(model, hints, rows = []) {
|
|
45
|
+
const fields = policyFields(model);
|
|
46
|
+
const markers = hasBasicMarkers(fields);
|
|
47
|
+
const own = new Map(rows.filter((r) => r.objectRef === model.id).map((r) => [r.fieldName, r]));
|
|
48
|
+
const resolved = fields.map((field, index) => {
|
|
49
|
+
const hint = hints?.fields?.[field.name] ?? {};
|
|
50
|
+
const discriminator = isDiscriminatorField(model, field);
|
|
51
|
+
let visibility = hint.visibility ??
|
|
52
|
+
(discriminator
|
|
53
|
+
? 'hidden'
|
|
54
|
+
: !markers || field.ui?.basic === true
|
|
55
|
+
? 'basic'
|
|
56
|
+
: 'advanced');
|
|
57
|
+
let label = hint.label ?? fieldLabel(field);
|
|
58
|
+
let help = hint.help ?? null;
|
|
59
|
+
let order = hint.order ?? field.ui?.order ?? index;
|
|
60
|
+
let locked = hint.locked ?? field.ui?.locked ?? discriminator;
|
|
61
|
+
const ownType = snakeCase(model.name);
|
|
62
|
+
const fallback = field.default !== undefined
|
|
63
|
+
? field.default
|
|
64
|
+
: discriminator && field.enum?.includes(ownType)
|
|
65
|
+
? ownType
|
|
66
|
+
: undefined;
|
|
67
|
+
let hasDefault = 'default' in hint || fallback !== undefined;
|
|
68
|
+
let value = 'default' in hint ? hint.default : fallback;
|
|
69
|
+
const row = own.get(field.name);
|
|
70
|
+
if (row && (!locked || row.locked === false)) {
|
|
71
|
+
if (row.visibility)
|
|
72
|
+
visibility = row.visibility;
|
|
73
|
+
if (row.label)
|
|
74
|
+
label = row.label;
|
|
75
|
+
if (row.help !== undefined)
|
|
76
|
+
help = row.help || null;
|
|
77
|
+
if (typeof row.displayOrder === 'number')
|
|
78
|
+
order = row.displayOrder;
|
|
79
|
+
const parsed = parseDefault(row.defaultValue);
|
|
80
|
+
if (parsed) {
|
|
81
|
+
hasDefault = true;
|
|
82
|
+
value = parsed.value;
|
|
83
|
+
}
|
|
84
|
+
if (typeof row.locked === 'boolean')
|
|
85
|
+
locked = row.locked;
|
|
86
|
+
}
|
|
87
|
+
// The required-field invariant: a required field may only leave the basic
|
|
88
|
+
// tier when a usable default fills it in.
|
|
89
|
+
let visibilityForced;
|
|
90
|
+
const required = hint.required ?? field.required;
|
|
91
|
+
if (required &&
|
|
92
|
+
visibility !== 'basic' &&
|
|
93
|
+
!(hasDefault && usableRequiredDefault(value))) {
|
|
94
|
+
visibility = 'basic';
|
|
95
|
+
visibilityForced = true;
|
|
96
|
+
}
|
|
97
|
+
return {
|
|
98
|
+
field,
|
|
99
|
+
visibility,
|
|
100
|
+
label,
|
|
101
|
+
help,
|
|
102
|
+
order,
|
|
103
|
+
group: field.ui?.group ?? null,
|
|
104
|
+
locked,
|
|
105
|
+
required,
|
|
106
|
+
hasDefault,
|
|
107
|
+
default: value,
|
|
108
|
+
...(visibilityForced ? { visibilityForced } : {}),
|
|
109
|
+
};
|
|
110
|
+
});
|
|
111
|
+
return resolved
|
|
112
|
+
.map((entry, index) => ({ entry, index }))
|
|
113
|
+
.sort((a, b) => a.entry.order - b.entry.order || a.index - b.index)
|
|
114
|
+
.map(({ entry }) => entry);
|
|
115
|
+
}
|
|
116
|
+
function primitive(value) {
|
|
117
|
+
return typeof value === 'string' ||
|
|
118
|
+
typeof value === 'number' ||
|
|
119
|
+
typeof value === 'boolean' ||
|
|
120
|
+
value === null
|
|
121
|
+
? value
|
|
122
|
+
: undefined;
|
|
123
|
+
}
|
|
124
|
+
/** The fields the generated list and form show: basic ones, policy applied. */
|
|
125
|
+
export function viewFields(resolved) {
|
|
126
|
+
return resolved
|
|
127
|
+
.filter((r) => r.visibility === 'basic')
|
|
128
|
+
.map((r) => {
|
|
129
|
+
const { default: _unused, ...rest } = r.field;
|
|
130
|
+
const fallback = r.hasDefault ? primitive(r.default) : undefined;
|
|
131
|
+
return {
|
|
132
|
+
...rest,
|
|
133
|
+
required: r.required,
|
|
134
|
+
...(fallback !== undefined ? { default: fallback } : {}),
|
|
135
|
+
label: r.label,
|
|
136
|
+
...(r.help ? { help: r.help } : {}),
|
|
137
|
+
};
|
|
138
|
+
});
|
|
139
|
+
}
|
|
140
|
+
/**
|
|
141
|
+
* Defaults for fields the views do not show (hidden or off), so records still
|
|
142
|
+
* carry them: the `contractType` discriminator of a shared Contract table.
|
|
143
|
+
*/
|
|
144
|
+
export function backgroundDefaults(resolved) {
|
|
145
|
+
const values = {};
|
|
146
|
+
for (const r of resolved) {
|
|
147
|
+
if (r.visibility !== 'basic' && r.hasDefault && r.default !== undefined) {
|
|
148
|
+
values[r.field.name] = r.default;
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
return values;
|
|
152
|
+
}
|
|
153
|
+
export const SURFACES = ['api', 'mcp', 'cli'];
|
|
154
|
+
export const SURFACE_LABEL = {
|
|
155
|
+
api: 'REST',
|
|
156
|
+
mcp: 'MCP',
|
|
157
|
+
cli: 'CLI',
|
|
158
|
+
};
|
|
159
|
+
export function surfaceAvailable(model, surface) {
|
|
160
|
+
const count = surface === 'api'
|
|
161
|
+
? model.rest.length
|
|
162
|
+
: surface === 'mcp'
|
|
163
|
+
? model.mcp.length
|
|
164
|
+
: model.cli.length;
|
|
165
|
+
return count > 0;
|
|
166
|
+
}
|
|
167
|
+
/**
|
|
168
|
+
* Exposure can only be narrowed: a surface is on when the class declares it,
|
|
169
|
+
* the recipe did not narrow it off, and the person did not switch it off.
|
|
170
|
+
*/
|
|
171
|
+
export function resolveExposure(model, hints, narrowed = []) {
|
|
172
|
+
const result = {};
|
|
173
|
+
for (const surface of SURFACES) {
|
|
174
|
+
const available = surfaceAvailable(model, surface);
|
|
175
|
+
const recipeOff = hints?.exposure?.[surface] === false;
|
|
176
|
+
result[surface] = {
|
|
177
|
+
available,
|
|
178
|
+
on: available && !recipeOff && !narrowed.includes(surface),
|
|
179
|
+
locked: !available || recipeOff,
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
return result;
|
|
183
|
+
}
|
|
184
|
+
/** The model as exposed: narrowed surfaces list nothing. */
|
|
185
|
+
export function narrowModel(model, exposure) {
|
|
186
|
+
const mcp = exposure.mcp.on;
|
|
187
|
+
return {
|
|
188
|
+
...model,
|
|
189
|
+
rest: exposure.api.on ? model.rest : [],
|
|
190
|
+
mcp: mcp ? model.mcp : [],
|
|
191
|
+
cli: exposure.cli.on ? model.cli : [],
|
|
192
|
+
methods: model.methods.map((m) => ({
|
|
193
|
+
...m,
|
|
194
|
+
aiCallable: m.aiCallable && mcp,
|
|
195
|
+
})),
|
|
196
|
+
};
|
|
197
|
+
}
|
|
198
|
+
/** Fields the options form lets a person switch off or edit. */
|
|
199
|
+
export function formFields(model, hints, rows = []) {
|
|
200
|
+
return resolveFields(model, hints, rows).filter((r) => hints?.fields?.[r.field.name]?.visibility !== 'hidden');
|
|
201
|
+
}
|
|
202
|
+
/** Can the "use this field" switch move? Required and locked fields cannot. */
|
|
203
|
+
export function isFieldLockedOn(r) {
|
|
204
|
+
return r.required || r.locked;
|
|
205
|
+
}
|
|
206
|
+
export function draftFrom(model, hints, rows, narrowed) {
|
|
207
|
+
const fields = {};
|
|
208
|
+
for (const r of formFields(model, hints, rows)) {
|
|
209
|
+
fields[r.field.name] = {
|
|
210
|
+
use: r.visibility === 'basic',
|
|
211
|
+
label: r.label,
|
|
212
|
+
help: r.help ?? '',
|
|
213
|
+
default: r.hasDefault ? r.default : null,
|
|
214
|
+
order: r.order,
|
|
215
|
+
};
|
|
216
|
+
}
|
|
217
|
+
const exposure = resolveExposure(model, hints, narrowed);
|
|
218
|
+
return {
|
|
219
|
+
fields,
|
|
220
|
+
exposure: {
|
|
221
|
+
api: exposure.api.on,
|
|
222
|
+
mcp: exposure.mcp.on,
|
|
223
|
+
cli: exposure.cli.on,
|
|
224
|
+
},
|
|
225
|
+
};
|
|
226
|
+
}
|
|
227
|
+
const sameJson = (a, b) => JSON.stringify(a ?? null) === JSON.stringify(b ?? null);
|
|
228
|
+
/**
|
|
229
|
+
* Turn a draft into app-scope policy rows. Only differences from the code seed
|
|
230
|
+
* are written, so an untouched form writes nothing and a row never repeats a
|
|
231
|
+
* value the seed already gives.
|
|
232
|
+
*/
|
|
233
|
+
export function rowsFromDraft(model, hints, draft) {
|
|
234
|
+
const seed = formFields(model, hints);
|
|
235
|
+
const rows = [];
|
|
236
|
+
for (const base of seed) {
|
|
237
|
+
const edited = draft.fields[base.field.name];
|
|
238
|
+
if (!edited || base.locked)
|
|
239
|
+
continue;
|
|
240
|
+
const row = {
|
|
241
|
+
objectRef: model.id,
|
|
242
|
+
fieldName: base.field.name,
|
|
243
|
+
scopeType: 'app',
|
|
244
|
+
};
|
|
245
|
+
const use = isFieldLockedOn(base) ? true : edited.use;
|
|
246
|
+
const seedUse = base.visibility === 'basic';
|
|
247
|
+
if (use !== seedUse)
|
|
248
|
+
row.visibility = use ? 'basic' : 'hidden';
|
|
249
|
+
if (edited.label.trim() && edited.label !== base.label) {
|
|
250
|
+
row.label = edited.label.trim();
|
|
251
|
+
}
|
|
252
|
+
if (edited.help !== (base.help ?? ''))
|
|
253
|
+
row.help = edited.help || null;
|
|
254
|
+
if (!sameJson(edited.default, base.hasDefault ? base.default : null)) {
|
|
255
|
+
row.defaultValue = JSON.stringify(edited.default ?? null);
|
|
256
|
+
}
|
|
257
|
+
if (edited.order !== base.order)
|
|
258
|
+
row.displayOrder = edited.order;
|
|
259
|
+
if (Object.keys(row).length > 3)
|
|
260
|
+
rows.push(row);
|
|
261
|
+
}
|
|
262
|
+
return rows;
|
|
263
|
+
}
|
|
264
|
+
/** The surfaces a draft switches off, beyond what the recipe already narrowed. */
|
|
265
|
+
export function narrowedFromDraft(model, hints, draft) {
|
|
266
|
+
const seed = resolveExposure(model, hints);
|
|
267
|
+
return SURFACES.filter((surface) => seed[surface].on && !draft.exposure[surface]);
|
|
268
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import type { Recipe } from './types.ts';
|
|
2
|
+
/** Sorted and de-duplicated, so the same selection is always the same URL. */
|
|
3
|
+
export declare function normalizeRecipes(ids: Iterable<string>): string[];
|
|
4
|
+
/**
|
|
5
|
+
* `ids` plus every recipe they transitively `require`, as a sorted set. A
|
|
6
|
+
* `requiresAny` list with none of its alternatives present adds the first
|
|
7
|
+
* known one.
|
|
8
|
+
*/
|
|
9
|
+
export declare function withRequirements(ids: Iterable<string>, recipes: ReadonlyMap<string, Recipe>): string[];
|
|
10
|
+
/**
|
|
11
|
+
* Selected recipes that would force any of `ids` back on if they were all
|
|
12
|
+
* removed: they require one directly, or `ids` hold the last alternative of
|
|
13
|
+
* one of their `requiresAny` lists.
|
|
14
|
+
*/
|
|
15
|
+
export declare function removalBlockers(ids: readonly string[], selected: readonly string[], recipes: ReadonlyMap<string, Recipe>): string[];
|
|
16
|
+
/** Ids of the selected recipes that require `id` and so keep it on. */
|
|
17
|
+
export declare function recipesRequiring(id: string, selected: readonly string[], recipes: ReadonlyMap<string, Recipe>): string[];
|
|
18
|
+
/** Keep only ids that name a known recipe. */
|
|
19
|
+
export declare function knownRecipes(ids: Iterable<string>, recipes: ReadonlyMap<string, Recipe>): string[];
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/** Sorted and de-duplicated, so the same selection is always the same URL. */
|
|
2
|
+
export function normalizeRecipes(ids) {
|
|
3
|
+
return [...new Set(ids)].sort();
|
|
4
|
+
}
|
|
5
|
+
/**
|
|
6
|
+
* `ids` plus every recipe they transitively `require`, as a sorted set. A
|
|
7
|
+
* `requiresAny` list with none of its alternatives present adds the first
|
|
8
|
+
* known one.
|
|
9
|
+
*/
|
|
10
|
+
export function withRequirements(ids, recipes) {
|
|
11
|
+
const result = new Set();
|
|
12
|
+
const visit = (id) => {
|
|
13
|
+
const recipe = recipes.get(id);
|
|
14
|
+
if (!recipe || result.has(id))
|
|
15
|
+
return;
|
|
16
|
+
result.add(id);
|
|
17
|
+
for (const required of recipe.requires)
|
|
18
|
+
visit(required);
|
|
19
|
+
};
|
|
20
|
+
for (const id of ids)
|
|
21
|
+
visit(id);
|
|
22
|
+
let changed = true;
|
|
23
|
+
while (changed) {
|
|
24
|
+
changed = false;
|
|
25
|
+
for (const id of [...result]) {
|
|
26
|
+
for (const alternatives of recipes.get(id)?.requiresAny ?? []) {
|
|
27
|
+
if (alternatives.some((alt) => result.has(alt)))
|
|
28
|
+
continue;
|
|
29
|
+
const first = alternatives.find((alt) => recipes.has(alt));
|
|
30
|
+
if (first) {
|
|
31
|
+
visit(first);
|
|
32
|
+
changed = true;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
return normalizeRecipes(result);
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Selected recipes that would force any of `ids` back on if they were all
|
|
41
|
+
* removed: they require one directly, or `ids` hold the last alternative of
|
|
42
|
+
* one of their `requiresAny` lists.
|
|
43
|
+
*/
|
|
44
|
+
export function removalBlockers(ids, selected, recipes) {
|
|
45
|
+
const removing = new Set(ids);
|
|
46
|
+
const remaining = selected.filter((id) => !removing.has(id));
|
|
47
|
+
const keep = new Set(remaining);
|
|
48
|
+
return remaining.filter((other) => {
|
|
49
|
+
const recipe = recipes.get(other);
|
|
50
|
+
if (!recipe)
|
|
51
|
+
return false;
|
|
52
|
+
if (recipe.requires.some((id) => removing.has(id)))
|
|
53
|
+
return true;
|
|
54
|
+
return (recipe.requiresAny ?? []).some((alternatives) => alternatives.some((alt) => removing.has(alt)) &&
|
|
55
|
+
!alternatives.some((alt) => keep.has(alt)));
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
/** Ids of the selected recipes that require `id` and so keep it on. */
|
|
59
|
+
export function recipesRequiring(id, selected, recipes) {
|
|
60
|
+
return removalBlockers([id], selected, recipes);
|
|
61
|
+
}
|
|
62
|
+
/** Keep only ids that name a known recipe. */
|
|
63
|
+
export function knownRecipes(ids, recipes) {
|
|
64
|
+
return normalizeRecipes([...ids].filter((id) => recipes.has(id)));
|
|
65
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { RecipeNavTarget } from './index.ts';
|
|
2
|
+
/**
|
|
3
|
+
* Which rows a model page lists. A keyed nav entry with a `filter` lists only
|
|
4
|
+
* the rows matching it (`equals`); the model's plain entry lists the rest
|
|
5
|
+
* (`notIn`) once such an entry's recipe is added, so a row shows in one place.
|
|
6
|
+
*/
|
|
7
|
+
export interface RowScope {
|
|
8
|
+
field: string;
|
|
9
|
+
equals?: string;
|
|
10
|
+
notIn?: string[];
|
|
11
|
+
}
|
|
12
|
+
type ScopedEntry = Pick<RecipeNavTarget, 'key' | 'filter'> & {
|
|
13
|
+
model: {
|
|
14
|
+
id: string;
|
|
15
|
+
};
|
|
16
|
+
};
|
|
17
|
+
/**
|
|
18
|
+
* The scope of a page: `view` is the entry key in the path (none for the
|
|
19
|
+
* plain entry); `added` are the nav entries of the added recipes.
|
|
20
|
+
*/
|
|
21
|
+
export declare function pageScope(modelId: string, view: string | undefined, added: readonly ScopedEntry[]): RowScope | undefined;
|
|
22
|
+
export declare function inScope(scope: RowScope | undefined, row: Record<string, unknown>): boolean;
|
|
23
|
+
/** Values a row created from the page carries, so it stays in view. */
|
|
24
|
+
export declare function scopePreset(scope: RowScope | undefined): Record<string, unknown>;
|
|
25
|
+
export {};
|