@saasicat/ui-vue 0.5.0 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +17 -0
- package/dist/{chunk-EH7TOD4H.js → chunk-A3W2N26K.js} +73 -77
- package/dist/{chunk-3YP2ZAOD.js → chunk-QZOSDCNP.js} +36 -1
- package/dist/chunk-X5SQ5HMB.js +3231 -0
- package/dist/client/index.cjs +3279 -76
- package/dist/client/index.d.cts +31 -5
- package/dist/client/index.d.ts +31 -5
- package/dist/client/index.js +23 -5
- package/dist/index.cjs +3709 -465
- package/dist/index.d.cts +37 -54
- package/dist/index.d.ts +37 -54
- package/dist/index.js +347 -311
- package/dist/messages-7b0P8W75.d.cts +1652 -0
- package/dist/messages-7b0P8W75.d.ts +1652 -0
- package/dist/quasar/index.cjs +3185 -4
- package/dist/quasar/index.d.cts +11 -2
- package/dist/quasar/index.d.ts +11 -2
- package/dist/quasar/index.js +8 -3
- package/dist/testing-e2e/admin-pages-suite.cjs +14 -11
- package/dist/testing-e2e/admin-pages-suite.js +14 -11
- package/dist/{ui-notify-COUzXEQ4.d.ts → use-super-admin-i18n-B3v3-SWZ.d.ts} +35 -3
- package/dist/{ui-notify-D_eAAwRh.d.cts → use-super-admin-i18n-DMktRVEt.d.cts} +35 -3
- package/package.json +2 -2
- package/src/client/action-registry.ts +4 -4
- package/src/client/batch-column-fetcher.ts +4 -4
- package/src/client/boot-loader.ts +3 -3
- package/src/client/i18n/currency.ts +42 -0
- package/src/client/i18n/define.ts +59 -0
- package/src/client/i18n/format.ts +12 -0
- package/src/client/i18n/index.ts +14 -0
- package/src/client/i18n/locale.ts +15 -0
- package/src/client/i18n/messages/audit.ts +42 -0
- package/src/client/i18n/messages/bundles.ts +459 -0
- package/src/client/i18n/messages/common.ts +147 -0
- package/src/client/i18n/messages/dashboard.ts +16 -0
- package/src/client/i18n/messages/discovery.ts +229 -0
- package/src/client/i18n/messages/email.ts +125 -0
- package/src/client/i18n/messages/marketing.ts +270 -0
- package/src/client/i18n/messages/nav.ts +72 -0
- package/src/client/i18n/messages/pilots.ts +192 -0
- package/src/client/i18n/messages/plan-detail.ts +266 -0
- package/src/client/i18n/messages/plan-editor.ts +177 -0
- package/src/client/i18n/messages/plan-versions.ts +251 -0
- package/src/client/i18n/messages/plans.ts +503 -0
- package/src/client/i18n/messages/promos.ts +202 -0
- package/src/client/i18n/messages/shell.ts +145 -0
- package/src/client/i18n/messages/tenants.ts +104 -0
- package/src/client/i18n/messages/users.ts +78 -0
- package/src/client/i18n/messages.ts +84 -0
- package/src/client/index.ts +2 -0
- package/src/client/manifest-loader.ts +4 -4
- package/src/client/nav-builder.ts +44 -51
- package/src/client/plan-versions-catalog.ts +42 -30
- package/src/components/BundleVersionPublishDialog.vue +35 -24
- package/src/components/MarketingPromotionsTab.vue +112 -59
- package/src/components/MfaPromptDialog.vue +11 -11
- package/src/components/TenantActionConfirmDialog.vue +19 -17
- package/src/components/VersionDiffPreview.vue +72 -43
- package/src/components/bundle-editor/BundleCreatePanel.vue +76 -63
- package/src/components/bundle-editor/BundleFeaturesEditor.vue +13 -6
- package/src/components/bundle-editor/BundlePlanCompatPicker.vue +19 -14
- package/src/components/bundle-editor/BundleQuotasEditor.vue +7 -4
- package/src/components/bundle-editor/BundleStatusBanner.vue +36 -19
- package/src/components/bundle-editor/BundleVersionInlineEditor.vue +51 -35
- package/src/components/bundle-editor/BundleVersionStrip.vue +24 -12
- package/src/components/bundle-editor/bundle-version-status.ts +29 -29
- package/src/components/dialogs/PilotCreateDialog.vue +58 -63
- package/src/components/dialogs/PilotEditDialog.vue +40 -34
- package/src/components/dialogs/PromoCodeCreateDialog.vue +89 -63
- package/src/components/dialogs/PromoCodeEditDialog.vue +98 -66
- package/src/components/dialogs/types.ts +3 -13
- package/src/components/plan/PlanCycleToggle.vue +20 -9
- package/src/components/plan-cockpit/PlanCockpit.vue +34 -15
- package/src/components/plan-cockpit/PlanCockpitAuditLog.vue +13 -6
- package/src/components/plan-cockpit/PlanCockpitDiffPanel.vue +18 -9
- package/src/components/plan-cockpit/PlanCockpitHeader.vue +9 -6
- package/src/components/plan-cockpit/PlanCockpitImpactPanel.vue +24 -11
- package/src/components/plan-cockpit/PlanCockpitKpis.vue +28 -17
- package/src/components/plan-cockpit/PlanCockpitVersions.vue +50 -25
- package/src/components/plan-create-dialog/PlanCreateDialog.vue +45 -35
- package/src/components/plan-detail/PlanAuditLog.vue +11 -6
- package/src/components/plan-detail/PlanDetail.vue +21 -23
- package/src/components/plan-detail/PlanDetailHeader.vue +20 -11
- package/src/components/plan-detail/PlanDetailKpis.vue +30 -17
- package/src/components/plan-detail/PlanTerminateDialog.vue +22 -9
- package/src/components/plan-detail/PlanVersionDiffPanel.vue +61 -27
- package/src/components/plan-detail/PlanVersionsPanel.vue +71 -36
- package/src/components/plan-list/PlanList.vue +99 -57
- package/src/components/plan-matrix/PlanMatrix.vue +85 -38
- package/src/components/plan-review/PlanReview.vue +105 -80
- package/src/components/plan-version-editor/PlanCatalogPreview.vue +43 -20
- package/src/components/plan-version-editor/PlanComponentPool.vue +15 -7
- package/src/components/plan-version-editor/PlanVersionBasket.vue +45 -24
- package/src/components/plan-version-editor/PlanVersionDiffDialog.vue +8 -7
- package/src/components/plan-version-editor/PlanVersionEditor.vue +74 -40
- package/src/components/plan-version-editor/PlanVersionEditorHeader.vue +24 -12
- package/src/index.ts +1 -1
- package/src/pages-standard/AdminLayout.vue +42 -17
- package/src/pages-standard/AdminManifestErrorPage.vue +10 -10
- package/src/pages-standard/AuditPage.vue +58 -19
- package/src/pages-standard/BundlesPage.vue +29 -18
- package/src/pages-standard/DashboardPage.vue +29 -15
- package/src/pages-standard/DiscoveryPage.vue +40 -28
- package/src/pages-standard/EmailHistoryPage.vue +92 -59
- package/src/pages-standard/MarketingCatalogPage.vue +35 -16
- package/src/pages-standard/PilotsPage.vue +57 -41
- package/src/pages-standard/PlanVersionsPage.vue +7 -3
- package/src/pages-standard/PlansPage.vue +89 -57
- package/src/pages-standard/PlatformEmailPage.vue +115 -50
- package/src/pages-standard/PromoCodeDetailPage.vue +66 -63
- package/src/pages-standard/PromoCodesPage.vue +46 -35
- package/src/pages-standard/SubscriptionsPage.vue +14 -9
- package/src/pages-standard/SuperAdminLoginPage.vue +16 -13
- package/src/pages-standard/SuperAdminSetupWizard.vue +51 -47
- package/src/pages-standard/TenantDetailPage.vue +50 -36
- package/src/pages-standard/TenantsPage.vue +54 -41
- package/src/pages-standard/UsersPage.vue +66 -42
- package/src/pages-standard/bundles-page/BundleAccordionList.vue +20 -8
- package/src/pages-standard/bundles-page/BundleDetailPanel.vue +28 -18
- package/src/pages-standard/bundles-page/BundlesFilterBar.vue +4 -1
- package/src/pages-standard/bundles-page/BundlesHeader.vue +9 -8
- package/src/pages-standard/bundles-page/BundlesKpis.vue +29 -11
- package/src/pages-standard/discovery-page/CatalogEntryTransPanel.vue +20 -8
- package/src/pages-standard/discovery-page/DiscoveryCapList.vue +5 -3
- package/src/pages-standard/discovery-page/DiscoveryFeatureCard.vue +43 -24
- package/src/pages-standard/discovery-page/DiscoveryHeader.vue +7 -4
- package/src/pages-standard/discovery-page/DiscoveryKpis.vue +28 -15
- package/src/pages-standard/discovery-page/DiscoveryQuotaCard.vue +20 -10
- package/src/pages-standard/discovery-page/DiscoveryStatusControl.vue +9 -6
- package/src/pages-standard/discovery-page/discovery-ui.ts +40 -52
- package/src/pages-standard/marketing-catalog/MarketingCatalogAdmin.vue +81 -49
- package/src/pages-standard/marketing-catalog/MarketingCatalogHeader.vue +13 -10
- package/src/pages-standard/marketing-catalog/MarketingCatalogPreview.vue +24 -20
- package/src/pages-standard/marketing-catalog/MarketingCatalogToolbar.vue +6 -3
- package/src/pages-standard/plan-versions/PlanDiffCard.vue +16 -6
- package/src/pages-standard/plan-versions/PlanVersionHeader.vue +41 -25
- package/src/pages-standard/plan-versions/PlanVersionsAudit.vue +45 -26
- package/src/pages-standard/plan-versions/PlanVersionsDiff.vue +7 -5
- package/src/pages-standard/plan-versions/PlanVersionsList.vue +39 -16
- package/src/pages-standard/plan-versions/PlanVersionsTimeline.vue +24 -12
- package/src/pages-standard/plan-versions/format.ts +33 -17
- package/src/pages-standard/plans-page/PlanArchiveDialog.vue +12 -8
- package/src/pages-standard/plans-page/PlanBundleOverview.vue +15 -6
- package/src/pages-standard/plans-page/PlanDiscardDraftDialog.vue +18 -7
- package/src/pages-standard/plans-page/PlanPublishDialog.vue +23 -12
- package/src/pages-standard/tenants/format.ts +3 -2
- package/src/pages-tenant/MySubscriptionBundlesPage.vue +72 -37
- package/src/pages-tenant/PlanChangeWizard.vue +8 -4
- package/src/pages-tenant/TenantPlanSection.vue +17 -13
- package/src/pages-tenant/default-i18n.ts +217 -1
- package/src/pages-tenant/tenant-plan-section/BundlePreviewDialog.vue +8 -6
- package/src/pages-tenant/tenant-plan-section/TenantBundleStore.vue +9 -10
- package/src/pages-tenant/tenant-plan-section/TenantFeatureMatrix.vue +4 -1
- package/src/quasar/create-super-admin-app.ts +19 -0
- package/src/testing-e2e/admin-pages-suite.ts +14 -11
- package/src/vue/project-page-host.ts +5 -3
- package/src/vue/use-audit-entries.ts +3 -3
- package/src/vue/use-bulk-publish.ts +6 -4
- package/src/vue/use-bundle-versions-map.ts +6 -4
- package/src/vue/use-bundles.ts +13 -13
- package/src/vue/use-catalog-entries.ts +13 -10
- package/src/vue/use-discovery.ts +8 -5
- package/src/vue/use-entitlement.ts +3 -3
- package/src/vue/use-live-plan-versions.ts +4 -4
- package/src/vue/use-marketing-projections.ts +9 -6
- package/src/vue/use-nav.ts +8 -2
- package/src/vue/use-plan-editor.ts +2 -2
- package/src/vue/use-plan-versions.ts +3 -3
- package/src/vue/use-plans.ts +12 -12
- package/src/vue/use-platform-tenant-actions.ts +9 -6
- package/src/vue/use-promotions.ts +9 -10
- package/src/vue/use-subscription-draft.ts +2 -3
- package/src/vue/use-super-admin-context.ts +3 -3
- package/src/vue/use-super-admin-i18n.ts +82 -0
- package/src/vue/use-tenant-action-flow.ts +11 -6
- package/src/vue/use-tenant-manifest.ts +1 -3
- package/src/vue/use-tenant-subscription-bundles.ts +4 -4
- package/src/vue/use-tenants.ts +3 -3
- package/dist/action-registry-CQ2wL3R-.d.cts +0 -85
- package/dist/action-registry-CQ2wL3R-.d.ts +0 -85
- package/dist/chunk-LVGUSD3T.js +0 -26
- package/src/components/BusinessTypeVersionEditorDialog.vue +0 -417
- package/src/components/BusinessTypeVersionPublishDialog.vue +0 -258
- package/src/pages-standard/BusinessTypesPage.vue +0 -662
- package/src/pages-standard/plan-versions/VersionDiffPreview.vue +0 -167
- package/src/vue/use-business-types.ts +0 -269
|
@@ -7,12 +7,8 @@
|
|
|
7
7
|
<q-card class="pc-dlg">
|
|
8
8
|
<q-card-section class="pc-dlg__head">
|
|
9
9
|
<div>
|
|
10
|
-
<div class="pc-dlg__title">
|
|
11
|
-
<div class="pc-dlg__sub">
|
|
12
|
-
{{
|
|
13
|
-
subtitle ?? 'Code, Rabatt-Logik, Laufzeit und Plan-Zuordnung festlegen.'
|
|
14
|
-
}}
|
|
15
|
-
</div>
|
|
10
|
+
<div class="pc-dlg__title">{{ msg.createDialog.title }}</div>
|
|
11
|
+
<div class="pc-dlg__sub">{{ subtitle ?? msg.createDialog.subtitle }}</div>
|
|
16
12
|
</div>
|
|
17
13
|
<q-btn
|
|
18
14
|
class="pc-dlg__close"
|
|
@@ -28,15 +24,15 @@
|
|
|
28
24
|
<q-card-section class="pc-dlg__body">
|
|
29
25
|
<!-- Section: Code & Discount -->
|
|
30
26
|
<div class="pc-section">
|
|
31
|
-
<div class="pc-section__title">
|
|
27
|
+
<div class="pc-section__title">{{ msg.form.sectionCodeDiscount }}</div>
|
|
32
28
|
<div class="pc-grid pc-grid--2">
|
|
33
29
|
<div class="pc-field">
|
|
34
|
-
<div class="pc-field__label">
|
|
30
|
+
<div class="pc-field__label">{{ msg.form.codeLabel }}</div>
|
|
35
31
|
<div class="pc-code-input">
|
|
36
32
|
<input
|
|
37
33
|
v-model="form.code"
|
|
38
34
|
class="pc-input pc-input--code"
|
|
39
|
-
placeholder="
|
|
35
|
+
:placeholder="msg.form.codePlaceholder"
|
|
40
36
|
@input="onCodeInput"
|
|
41
37
|
/>
|
|
42
38
|
<button
|
|
@@ -44,19 +40,17 @@
|
|
|
44
40
|
class="pc-btn-mini"
|
|
45
41
|
@click="form.code = randomCode()"
|
|
46
42
|
>
|
|
47
|
-
|
|
43
|
+
{{ msg.form.codeRandom }}
|
|
48
44
|
</button>
|
|
49
45
|
</div>
|
|
50
|
-
<div class="pc-field__hint">
|
|
51
|
-
Großbuchstaben, Zahlen, „-" und „_" · nach Anlage stabil
|
|
52
|
-
</div>
|
|
46
|
+
<div class="pc-field__hint">{{ msg.form.codeHint }}</div>
|
|
53
47
|
</div>
|
|
54
48
|
|
|
55
49
|
<div class="pc-field">
|
|
56
|
-
<div class="pc-field__label">
|
|
50
|
+
<div class="pc-field__label">{{ msg.form.valueTypeLabel }}</div>
|
|
57
51
|
<div class="pc-type-grid">
|
|
58
52
|
<button
|
|
59
|
-
v-for="o in
|
|
53
|
+
v-for="o in typeOptions"
|
|
60
54
|
:key="o.k"
|
|
61
55
|
type="button"
|
|
62
56
|
class="pc-type-opt"
|
|
@@ -72,7 +66,11 @@
|
|
|
72
66
|
|
|
73
67
|
<div class="pc-field" style="max-width: 280px">
|
|
74
68
|
<div class="pc-field__label">
|
|
75
|
-
{{
|
|
69
|
+
{{
|
|
70
|
+
form.valueType === 'PERCENT'
|
|
71
|
+
? msg.form.valuePercentLabel
|
|
72
|
+
: msg.form.valueAbsoluteLabel
|
|
73
|
+
}}
|
|
76
74
|
</div>
|
|
77
75
|
<input
|
|
78
76
|
v-model.number="form.value"
|
|
@@ -86,10 +84,10 @@
|
|
|
86
84
|
|
|
87
85
|
<!-- Section: Validity & Duration -->
|
|
88
86
|
<div class="pc-section">
|
|
89
|
-
<div class="pc-section__title">
|
|
87
|
+
<div class="pc-section__title">{{ msg.form.sectionValidity }}</div>
|
|
90
88
|
|
|
91
89
|
<div v-if="plans.length > 0" class="pc-field">
|
|
92
|
-
<div class="pc-field__label">
|
|
90
|
+
<div class="pc-field__label">{{ msg.form.plansLabel }}</div>
|
|
93
91
|
<div class="pc-plan-pick">
|
|
94
92
|
<button
|
|
95
93
|
v-for="p in plans"
|
|
@@ -108,16 +106,20 @@
|
|
|
108
106
|
</button>
|
|
109
107
|
</div>
|
|
110
108
|
<div class="pc-field__hint">
|
|
111
|
-
|
|
109
|
+
{{
|
|
110
|
+
formatMessage(msg.form.plansHint, {
|
|
111
|
+
count: form.appliesToPlans.length,
|
|
112
|
+
})
|
|
113
|
+
}}
|
|
112
114
|
</div>
|
|
113
115
|
</div>
|
|
114
116
|
|
|
115
117
|
<div class="pc-grid pc-grid--2">
|
|
116
118
|
<div class="pc-field">
|
|
117
|
-
<div class="pc-field__label">
|
|
119
|
+
<div class="pc-field__label">{{ msg.form.durationLabel }}</div>
|
|
118
120
|
<div class="pc-dur">
|
|
119
121
|
<button
|
|
120
|
-
v-for="o in
|
|
122
|
+
v-for="o in durationOptions"
|
|
121
123
|
:key="o.k"
|
|
122
124
|
type="button"
|
|
123
125
|
class="pc-dur-opt"
|
|
@@ -135,31 +137,35 @@
|
|
|
135
137
|
min="1"
|
|
136
138
|
style="margin-top: 8px; max-width: 120px"
|
|
137
139
|
:placeholder="
|
|
138
|
-
form.durationType === 'MONTHS'
|
|
140
|
+
form.durationType === 'MONTHS'
|
|
141
|
+
? msg.form.durationMonthsPlaceholder
|
|
142
|
+
: msg.form.durationCyclesPlaceholder
|
|
139
143
|
"
|
|
140
144
|
/>
|
|
141
145
|
</div>
|
|
142
146
|
|
|
143
147
|
<div class="pc-field">
|
|
144
|
-
<div class="pc-field__label">
|
|
148
|
+
<div class="pc-field__label">{{ msg.form.maxRedemptionsLabel }}</div>
|
|
145
149
|
<input
|
|
146
150
|
v-model.number="form.maxRedemptions"
|
|
147
151
|
class="pc-input"
|
|
148
152
|
type="number"
|
|
149
153
|
min="1"
|
|
150
|
-
placeholder="
|
|
154
|
+
:placeholder="msg.form.maxRedemptionsPlaceholder"
|
|
151
155
|
/>
|
|
152
|
-
<div class="pc-field__hint">
|
|
156
|
+
<div class="pc-field__hint">
|
|
157
|
+
{{ msg.form.maxRedemptionsHintCreate }}
|
|
158
|
+
</div>
|
|
153
159
|
</div>
|
|
154
160
|
</div>
|
|
155
161
|
|
|
156
162
|
<div class="pc-grid pc-grid--2">
|
|
157
163
|
<div class="pc-field">
|
|
158
|
-
<div class="pc-field__label">
|
|
164
|
+
<div class="pc-field__label">{{ msg.form.validFromLabel }}</div>
|
|
159
165
|
<input v-model="form.validFrom" class="pc-input" type="date" />
|
|
160
166
|
</div>
|
|
161
167
|
<div class="pc-field">
|
|
162
|
-
<div class="pc-field__label">
|
|
168
|
+
<div class="pc-field__label">{{ msg.form.validUntilLabel }}</div>
|
|
163
169
|
<input v-model="form.validUntil" class="pc-input" type="date" />
|
|
164
170
|
</div>
|
|
165
171
|
</div>
|
|
@@ -167,23 +173,23 @@
|
|
|
167
173
|
|
|
168
174
|
<!-- Section: Campaign & Note -->
|
|
169
175
|
<div class="pc-section">
|
|
170
|
-
<div class="pc-section__title">
|
|
176
|
+
<div class="pc-section__title">{{ msg.form.sectionCampaign }}</div>
|
|
171
177
|
<div v-if="showCampaignTag" class="pc-field">
|
|
172
|
-
<div class="pc-field__label">
|
|
178
|
+
<div class="pc-field__label">{{ msg.form.campaignLabel }}</div>
|
|
173
179
|
<input
|
|
174
180
|
v-model="form.campaignTag"
|
|
175
181
|
class="pc-input"
|
|
176
|
-
placeholder="
|
|
182
|
+
:placeholder="msg.form.campaignPlaceholder"
|
|
177
183
|
/>
|
|
178
|
-
<div class="pc-field__hint">
|
|
184
|
+
<div class="pc-field__hint">{{ msg.form.campaignHint }}</div>
|
|
179
185
|
</div>
|
|
180
186
|
<div class="pc-field">
|
|
181
|
-
<div class="pc-field__label">
|
|
187
|
+
<div class="pc-field__label">{{ msg.form.noteLabel }}</div>
|
|
182
188
|
<textarea
|
|
183
189
|
v-model="form.description"
|
|
184
190
|
class="pc-input"
|
|
185
191
|
rows="2"
|
|
186
|
-
placeholder="
|
|
192
|
+
:placeholder="msg.form.notePlaceholder"
|
|
187
193
|
/>
|
|
188
194
|
</div>
|
|
189
195
|
</div>
|
|
@@ -199,45 +205,47 @@
|
|
|
199
205
|
:name="advancedOpen ? 'expand_more' : 'chevron_right'"
|
|
200
206
|
size="16px"
|
|
201
207
|
/>
|
|
202
|
-
|
|
208
|
+
{{ msg.form.advancedToggle }}
|
|
203
209
|
</button>
|
|
204
210
|
<div v-if="advancedOpen" class="pc-advanced">
|
|
205
211
|
<div class="pc-grid pc-grid--2">
|
|
206
212
|
<div class="pc-field">
|
|
207
|
-
<div class="pc-field__label">
|
|
213
|
+
<div class="pc-field__label">{{ msg.form.billingCycleLabel }}</div>
|
|
208
214
|
<select v-model="form.appliesToBilling" class="pc-input">
|
|
209
|
-
<option :value="undefined">
|
|
210
|
-
|
|
211
|
-
|
|
215
|
+
<option :value="undefined">
|
|
216
|
+
{{ common.both }}
|
|
217
|
+
</option>
|
|
218
|
+
<option value="MONTHLY">{{ common.monthly }}</option>
|
|
219
|
+
<option value="YEARLY">{{ common.yearly }}</option>
|
|
212
220
|
</select>
|
|
213
221
|
</div>
|
|
214
222
|
<div class="pc-field">
|
|
215
|
-
<div class="pc-field__label">
|
|
223
|
+
<div class="pc-field__label">{{ msg.form.minAmountLabel }}</div>
|
|
216
224
|
<input
|
|
217
225
|
v-model.number="form.minimumPlanAmountGross"
|
|
218
226
|
class="pc-input"
|
|
219
227
|
type="number"
|
|
220
228
|
min="0"
|
|
221
|
-
placeholder="
|
|
229
|
+
:placeholder="msg.form.minAmountPlaceholder"
|
|
222
230
|
/>
|
|
223
231
|
</div>
|
|
224
232
|
</div>
|
|
225
233
|
<div class="pc-grid pc-grid--2">
|
|
226
234
|
<label class="pc-check">
|
|
227
235
|
<input v-model="form.firstTimeCustomersOnly" type="checkbox" />
|
|
228
|
-
<span>
|
|
236
|
+
<span>{{ msg.form.firstTimeOnly }}</span>
|
|
229
237
|
</label>
|
|
230
238
|
<label class="pc-check">
|
|
231
239
|
<input v-model="form.allowZeroInvoice" type="checkbox" />
|
|
232
|
-
<span>
|
|
240
|
+
<span>{{ msg.form.allowZeroInvoice }}</span>
|
|
233
241
|
</label>
|
|
234
242
|
</div>
|
|
235
243
|
<div class="pc-field">
|
|
236
|
-
<div class="pc-field__label">
|
|
244
|
+
<div class="pc-field__label">{{ msg.form.revenueAccountLabel }}</div>
|
|
237
245
|
<input
|
|
238
246
|
v-model="form.revenueDeductionAccount"
|
|
239
247
|
class="pc-input"
|
|
240
|
-
placeholder="
|
|
248
|
+
:placeholder="msg.form.revenueAccountPlaceholder"
|
|
241
249
|
/>
|
|
242
250
|
</div>
|
|
243
251
|
</div>
|
|
@@ -245,7 +253,7 @@
|
|
|
245
253
|
|
|
246
254
|
<!-- Live preview -->
|
|
247
255
|
<div class="pc-preview">
|
|
248
|
-
<div class="pc-preview__eyebrow">
|
|
256
|
+
<div class="pc-preview__eyebrow">{{ msg.form.previewEyebrow }}</div>
|
|
249
257
|
<div class="pc-preview__body">
|
|
250
258
|
<code class="pc-preview__code">{{ form.code || 'CODE' }}</code>
|
|
251
259
|
<span class="pc-preview__disc">{{ previewValue }}</span>
|
|
@@ -257,11 +265,11 @@
|
|
|
257
265
|
</q-card-section>
|
|
258
266
|
|
|
259
267
|
<q-card-actions align="right" class="pc-dlg__foot">
|
|
260
|
-
<q-btn flat label="
|
|
268
|
+
<q-btn flat :label="common.cancel" v-close-popup :disable="loading" />
|
|
261
269
|
<q-btn
|
|
262
270
|
unelevated
|
|
263
271
|
color="primary"
|
|
264
|
-
label="
|
|
272
|
+
:label="common.create"
|
|
265
273
|
:loading="loading"
|
|
266
274
|
:disable="!isValid"
|
|
267
275
|
@click="onSubmit"
|
|
@@ -273,6 +281,8 @@
|
|
|
273
281
|
|
|
274
282
|
<script setup lang="ts">
|
|
275
283
|
import { computed, reactive, ref, watch } from 'vue';
|
|
284
|
+
import { formatMessage } from '../../client/i18n/format.js';
|
|
285
|
+
import { useSaMessages } from '../../vue/use-super-admin-i18n.js';
|
|
276
286
|
import type {
|
|
277
287
|
PromoCodeCreatePayload,
|
|
278
288
|
PromoCodeDurationType,
|
|
@@ -304,16 +314,29 @@ const emit = defineEmits<{
|
|
|
304
314
|
(e: 'created'): void;
|
|
305
315
|
}>();
|
|
306
316
|
|
|
307
|
-
const
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
317
|
+
const msg = useSaMessages('promos');
|
|
318
|
+
const common = useSaMessages('common');
|
|
319
|
+
|
|
320
|
+
const typeOptions = computed<ReadonlyArray<{ k: PromoCodeValueType; label: string; sub: string }>>(
|
|
321
|
+
() => [
|
|
322
|
+
{
|
|
323
|
+
k: 'PERCENT',
|
|
324
|
+
label: msg.value.form.valueTypePercent,
|
|
325
|
+
sub: msg.value.form.valueTypePercentSub,
|
|
326
|
+
},
|
|
327
|
+
{
|
|
328
|
+
k: 'ABSOLUTE',
|
|
329
|
+
label: msg.value.form.valueTypeAbsolute,
|
|
330
|
+
sub: msg.value.form.valueTypeAbsoluteSub,
|
|
331
|
+
},
|
|
332
|
+
],
|
|
333
|
+
);
|
|
311
334
|
|
|
312
|
-
const
|
|
313
|
-
{ k: 'ONCE', label:
|
|
314
|
-
{ k: 'MONTHS', label:
|
|
315
|
-
{ k: 'BILLING_CYCLES', label:
|
|
316
|
-
];
|
|
335
|
+
const durationOptions = computed<ReadonlyArray<{ k: PromoCodeDurationType; label: string }>>(() => [
|
|
336
|
+
{ k: 'ONCE', label: msg.value.form.durationOnce },
|
|
337
|
+
{ k: 'MONTHS', label: msg.value.form.durationMonths },
|
|
338
|
+
{ k: 'BILLING_CYCLES', label: msg.value.form.durationBillingCycles },
|
|
339
|
+
]);
|
|
317
340
|
|
|
318
341
|
function emptyForm() {
|
|
319
342
|
return {
|
|
@@ -378,17 +401,20 @@ const previewValue = computed(() => {
|
|
|
378
401
|
|
|
379
402
|
const previewMeta = computed(() => {
|
|
380
403
|
const parts: string[] = [];
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
else
|
|
404
|
+
const count = form.durationValue || 0;
|
|
405
|
+
if (form.durationType === 'ONCE') parts.push(msg.value.form.previewOnce);
|
|
406
|
+
else if (form.durationType === 'MONTHS')
|
|
407
|
+
parts.push(formatMessage(msg.value.form.previewMonths, { count }));
|
|
408
|
+
else parts.push(formatMessage(msg.value.form.previewCycles, { count }));
|
|
384
409
|
parts.push(
|
|
385
410
|
form.appliesToPlans.length > 0
|
|
386
411
|
? form.appliesToPlans.join(', ')
|
|
387
412
|
: props.plans.length > 0
|
|
388
|
-
?
|
|
389
|
-
:
|
|
413
|
+
? msg.value.form.previewAllPlans
|
|
414
|
+
: msg.value.form.previewNoPlanFilter,
|
|
390
415
|
);
|
|
391
|
-
if (form.maxRedemptions)
|
|
416
|
+
if (form.maxRedemptions)
|
|
417
|
+
parts.push(formatMessage(msg.value.form.previewMax, { count: form.maxRedemptions }));
|
|
392
418
|
return parts.join(' · ');
|
|
393
419
|
});
|
|
394
420
|
|
|
@@ -441,7 +467,7 @@ async function onSubmit() {
|
|
|
441
467
|
error.value =
|
|
442
468
|
(err as { response?: { data?: { message?: string } } }).response?.data?.message ??
|
|
443
469
|
(err as Error).message ??
|
|
444
|
-
|
|
470
|
+
common.value.createFailed;
|
|
445
471
|
} finally {
|
|
446
472
|
loading.value = false;
|
|
447
473
|
}
|