@rancher/shell 0.3.0 → 0.3.1
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/assets/styles/global/_button.scss +5 -1
- package/assets/styles/global/_columns.scss +4 -0
- package/assets/styles/global/_layout.scss +1 -2
- package/assets/styles/global/_select.scss +1 -4
- package/assets/styles/themes/_dark.scss +4 -4
- package/assets/styles/themes/_light.scss +4 -3
- package/assets/styles/themes/_suse.scss +1 -1
- package/assets/styles/vendor/vue-select.scss +4 -3
- package/assets/translations/en-us.yaml +669 -73
- package/assets/translations/zh-hans.yaml +547 -165
- package/chart/monitoring/steps/uninstall-v1.vue +2 -2
- package/cloud-credential/azure.vue +23 -0
- package/cloud-credential/harvester.vue +25 -62
- package/cloud-credential/pnap.vue +80 -0
- package/components/.DS_Store +0 -0
- package/components/AdvancedSection.vue +9 -2
- package/components/Alert.vue +2 -2
- package/components/ButtonDropdown.vue +0 -2
- package/components/ButtonGroup.vue +1 -0
- package/components/CollapsibleCard.vue +0 -1
- package/components/CruResource.vue +41 -4
- package/components/DetailTop.vue +58 -3
- package/components/DisableAuthProviderModal.vue +106 -0
- package/{rancher-components/components/Utils/DraggableZone → components}/DraggableZone.vue +0 -0
- package/components/ExplorerMembers.vue +253 -30
- package/components/ExplorerProjectsNamespaces.vue +77 -33
- package/components/GrowlManager.vue +3 -3
- package/components/IconOrSvg.vue +149 -0
- package/components/LogItem.vue +69 -0
- package/components/PodSecurityAdmission.vue +302 -0
- package/components/PromptModal.vue +1 -0
- package/components/ResourceDetail/Masthead.vue +54 -2
- package/components/ResourceDetail/index.vue +12 -5
- package/components/ResourceList/Masthead.vue +11 -1
- package/components/ResourceList/ResourceLoadingIndicator.vue +12 -2
- package/components/ResourceList/index.vue +53 -12
- package/components/ResourceList/resource-list.config.js +7 -0
- package/components/ResourceTable.vue +31 -6
- package/components/SimpleBox.vue +1 -1
- package/components/SortableTable/THead.vue +15 -5
- package/components/SortableTable/index.vue +21 -10
- package/components/Tabbed/index.vue +20 -15
- package/components/__tests__/.DS_Store +0 -0
- package/components/__tests__/AsyncButton.test.ts +140 -0
- package/components/__tests__/BackLink.test.ts +33 -0
- package/components/__tests__/ButtonGroup.test.ts +124 -0
- package/components/__tests__/ClusterBadge.test.ts +32 -0
- package/components/__tests__/CollapsibleCard.test.ts +64 -0
- package/components/__tests__/ConsumptionGauge.test.ts +88 -0
- package/components/__tests__/CruResource.test.ts +3 -2
- package/components/__tests__/FixedBanner.test.ts +129 -0
- package/components/__tests__/GrowlManager.test.ts +147 -0
- package/components/__tests__/NamespaceFilter.test.ts +33 -25
- package/components/__tests__/PercentageBar.test.ts +32 -0
- package/components/__tests__/PodSecurityAdmission.test.ts +398 -0
- package/components/auth/AuthBanner.vue +20 -10
- package/components/auth/RoleDetailEdit.vue +26 -17
- package/components/auth/SelectPrincipal.vue +36 -5
- package/components/form/ArrayList.vue +3 -35
- package/components/form/ArrayListGrouped.vue +13 -4
- package/components/form/ArrayListSelect.vue +5 -5
- package/components/form/Error.vue +8 -0
- package/components/form/KeyValue.vue +39 -7
- package/components/form/LabeledSelect.vue +5 -2
- package/components/form/Labels.vue +46 -16
- package/components/form/Members/ClusterPermissionsEditor.vue +17 -17
- package/components/form/Members/MembershipEditor.vue +12 -12
- package/components/form/NameNsDescription.vue +1 -1
- package/components/form/NodeScheduling.vue +1 -1
- package/components/form/Probe.vue +3 -3
- package/components/form/ResourceQuota/Project.vue +6 -6
- package/components/form/ResourceTabs/index.vue +1 -6
- package/components/form/Security.vue +7 -6
- package/components/form/Select.vue +3 -2
- package/components/form/SelectOrCreateAuthSecret.vue +22 -29
- package/components/form/ServicePorts.vue +8 -0
- package/components/form/WorkloadPorts.vue +7 -1
- package/components/form/__tests__/ArrayList.test.ts +74 -0
- package/components/form/__tests__/ArrayListGrouped.test.ts +6 -4
- package/components/formatter/Checked.vue +1 -1
- package/components/formatter/ClusterLink.vue +5 -0
- package/components/formatter/IconIsDefault.vue +2 -2
- package/components/formatter/InternalExternalIP.vue +11 -8
- package/components/formatter/LiveDuration.vue +78 -0
- package/components/formatter/WorkloadHealthScale.vue +5 -3
- package/components/nav/Header.vue +6 -3
- package/components/nav/NamespaceFilter.vue +146 -63
- package/components/nav/TopLevelMenu.vue +22 -19
- package/components/nav/WindowManager/ContainerLogs.vue +83 -126
- package/components/nav/WindowManager/ContainerShell.vue +9 -7
- package/components/nav/WindowManager/Window.vue +2 -0
- package/components/nav/WindowManager/index.vue +10 -0
- package/config/elemental-types.js +9 -0
- package/config/features.js +2 -0
- package/config/home-links.js +4 -1
- package/config/pod-security-admission.ts +82 -0
- package/config/product/apps.js +1 -1
- package/config/product/auth.js +6 -5
- package/config/product/explorer.js +6 -6
- package/config/product/fleet.js +1 -1
- package/config/product/manager.js +6 -2
- package/config/secret.js +0 -1
- package/config/settings.ts +26 -9
- package/config/table-headers.js +22 -11
- package/config/types.js +4 -1
- package/content/docs/zh-hans/getting-started.md +113 -137
- package/content/docs/zh-hans/whats-new.md +8 -46
- package/creators/pkg/package-lock.json +37 -0
- package/creators/pkg/package.json +1 -1
- package/detail/catalog.cattle.io.app.vue +1 -1
- package/detail/pod.vue +1 -1
- package/detail/provisioning.cattle.io.cluster.vue +35 -9
- package/detail/service.vue +2 -9
- package/detail/workload/index.vue +0 -1
- package/dialog/AddClusterMemberDialog.vue +22 -28
- package/dialog/AddProjectMemberDialog.vue +53 -9
- package/dialog/DiagnosticTimingsDialog.vue +8 -7
- package/dialog/DrainNode.vue +44 -48
- package/dialog/ForceMachineRemoveDialog.vue +5 -7
- package/dialog/GenericPrompt.vue +15 -20
- package/dialog/RollbackWorkloadDialog.vue +15 -46
- package/dialog/RotateCertificatesDialog.vue +5 -7
- package/dialog/RotateEncryptionKeyDialog.vue +5 -9
- package/dialog/SaveAsRKETemplateDialog.vue +5 -13
- package/dialog/ScaleMachineDownDialog.vue +1 -1
- package/dialog/ScalePoolDownDialog.vue +121 -0
- package/edit/__tests__/management.cattle.io.setting.test.ts +3 -3
- package/edit/auth/azuread.vue +16 -16
- package/edit/auth/github.vue +8 -0
- package/edit/auth/googleoauth.vue +10 -1
- package/edit/auth/ldap/index.vue +10 -0
- package/edit/auth/oidc.vue +10 -0
- package/edit/auth/saml.vue +10 -0
- package/edit/autoscaling.horizontalpodautoscaler/index.vue +1 -1
- package/edit/cloudcredential.vue +3 -7
- package/edit/logging-flow/Match.vue +39 -8
- package/edit/logging-flow/index.vue +27 -4
- package/edit/management.cattle.io.podsecurityadmissionconfigurationtemplate.vue +107 -0
- package/edit/management.cattle.io.project.vue +8 -1
- package/edit/management.cattle.io.setting.vue +5 -2
- package/edit/management.cattle.io.user.vue +7 -1
- package/edit/monitoring.coreos.com.alertmanagerconfig/receiverConfig.vue +23 -7
- package/edit/monitoring.coreos.com.alertmanagerconfig/types/email.vue +2 -2
- package/edit/monitoring.coreos.com.prometheusrule/GroupRules.vue +14 -6
- package/edit/namespace.vue +18 -4
- package/edit/networking.k8s.io.ingress/Certificate.vue +1 -0
- package/edit/networking.k8s.io.ingress/IngressClass.vue +8 -6
- package/edit/networking.k8s.io.ingress/RulePath.vue +12 -6
- package/edit/networking.k8s.io.ingress/index.vue +8 -6
- package/edit/persistentvolume/index.vue +30 -27
- package/edit/persistentvolume/plugins/cephfs.vue +29 -29
- package/edit/persistentvolume/plugins/csi.vue +102 -62
- package/edit/persistentvolume/plugins/fc.vue +19 -19
- package/edit/persistentvolume/plugins/iscsi.vue +45 -45
- package/edit/persistentvolume/plugins/rbd.vue +39 -39
- package/edit/persistentvolumeclaim.vue +78 -75
- package/edit/provisioning.cattle.io.cluster/MachinePool.vue +11 -7
- package/edit/provisioning.cattle.io.cluster/RegistryConfigs.vue +10 -1
- package/edit/provisioning.cattle.io.cluster/RegistryMirrors.vue +87 -27
- package/edit/provisioning.cattle.io.cluster/SelectCredential.vue +3 -6
- package/edit/provisioning.cattle.io.cluster/__tests__/rke2.test.ts +93 -0
- package/edit/provisioning.cattle.io.cluster/import.vue +1 -1
- package/edit/provisioning.cattle.io.cluster/index.vue +29 -6
- package/edit/provisioning.cattle.io.cluster/rke2.vue +440 -152
- package/edit/secret/index.vue +3 -7
- package/edit/service.vue +3 -1
- package/edit/storage.k8s.io.storageclass/index.vue +100 -16
- package/edit/storage.k8s.io.storageclass/provisioners/driver.harvesterhci.io.vue +114 -0
- package/edit/workload/__tests__/index.test.ts +98 -0
- package/edit/workload/index.vue +58 -8
- package/edit/workload/mixins/workload.js +107 -70
- package/edit/workload/storage/ContainerMountPaths.vue +0 -10
- package/edit/workload/storage/emptyDir.vue +88 -0
- package/edit/workload/storage/ephemeralVolume/index.vue +1 -1
- package/edit/workload/storage/index.vue +8 -0
- package/edit/workload/storage/persistentVolumeClaim/index.vue +1 -1
- package/layouts/default.vue +57 -44
- package/list/__tests__/workload.test.ts +5 -2
- package/list/catalog.cattle.io.app.vue +1 -0
- package/list/cis.cattle.io.clusterscan.vue +1 -0
- package/list/fleet.cattle.io.bundle.vue +5 -6
- package/list/fleet.cattle.io.cluster.vue +6 -3
- package/list/fleet.cattle.io.clusterregistrationtoken.vue +5 -6
- package/list/fleet.cattle.io.gitrepo.vue +4 -9
- package/list/helm.cattle.io.projecthelmchart.vue +1 -5
- package/list/logging.banzaicloud.io.clusterflow.vue +4 -1
- package/list/logging.banzaicloud.io.flow.vue +6 -5
- package/list/management.cattle.io.cluster.vue +1 -0
- package/list/management.cattle.io.feature.vue +3 -4
- package/list/management.cattle.io.podsecurityadmissionconfigurationtemplate.vue +47 -0
- package/list/management.cattle.io.setting.vue +2 -2
- package/list/management.cattle.io.user.vue +4 -10
- package/list/monitoring.coreos.com.alertmanagerconfig.vue +2 -7
- package/list/node.vue +8 -5
- package/list/persistentvolume.vue +3 -3
- package/list/persistentvolumeclaim.vue +3 -4
- package/list/provisioning.cattle.io.cluster.vue +18 -19
- package/list/service.vue +6 -14
- package/list/workload.vue +43 -38
- package/machine-config/azure.vue +429 -60
- package/machine-config/pnap.vue +288 -0
- package/mixins/auth-config.js +1 -3
- package/mixins/browser-tab-visibility.js +8 -14
- package/mixins/chart.js +1 -1
- package/mixins/create-edit-view/impl.js +4 -0
- package/mixins/create-edit-view/index.js +4 -2
- package/mixins/resource-fetch-namespaced.js +98 -0
- package/mixins/resource-fetch.js +79 -45
- package/mixins/resource-manager.js +1 -23
- package/models/apps.controllerrevision.js +7 -0
- package/models/apps.daemonset.js +18 -0
- package/models/apps.deployment.js +44 -0
- package/models/apps.replicaset.js +7 -0
- package/models/apps.statefulset.js +18 -0
- package/models/batch.job.js +7 -14
- package/models/cluster/node.js +10 -2
- package/models/cluster.x-k8s.io.machine.js +26 -4
- package/models/cluster.x-k8s.io.machinedeployment.js +12 -2
- package/models/event.js +7 -0
- package/models/logging.banzaicloud.io.flow.js +4 -0
- package/models/management.cattle.io.cluster.js +1 -1
- package/models/management.cattle.io.clusterroletemplatebinding.js +1 -1
- package/models/management.cattle.io.globalrole.js +2 -2
- package/models/management.cattle.io.node.js +37 -2
- package/models/management.cattle.io.podsecurityadmissionconfigurationtemplate.ts +4 -0
- package/models/management.cattle.io.project.js +30 -11
- package/models/management.cattle.io.setting.js +1 -1
- package/models/management.cattle.io.user.js +37 -1
- package/models/namespace.js +42 -5
- package/models/persistentvolume.js +14 -2
- package/models/pod.js +15 -0
- package/models/projectroletemplatebinding.js +7 -0
- package/models/provisioning.cattle.io.cluster.js +61 -10
- package/models/rke-machine.cattle.io.pnapmachinetemplate.js +15 -0
- package/models/service.js +14 -13
- package/models/storage.k8s.io.storageclass.js +33 -18
- package/models/workload.js +38 -7
- package/nuxt.config.js +27 -17
- package/package.json +7 -7
- package/pages/about.vue +14 -2
- package/pages/c/_cluster/apps/charts/index.vue +4 -3
- package/pages/c/_cluster/apps/charts/install.vue +59 -22
- package/pages/c/_cluster/auth/config/_id.vue +6 -0
- package/pages/c/_cluster/auth/config/index.vue +8 -6
- package/pages/c/_cluster/auth/group.principal/assign-edit.vue +1 -1
- package/pages/c/_cluster/auth/roles/index.vue +1 -1
- package/pages/c/_cluster/explorer/index.vue +12 -6
- package/pages/c/_cluster/longhorn/index.vue +1 -1
- package/pages/c/_cluster/monitoring/alertmanagerconfig/_alertmanagerconfigid/receiver.vue +15 -4
- package/pages/c/_cluster/monitoring/index.vue +1 -1
- package/pages/c/_cluster/neuvector/index.vue +1 -1
- package/pages/c/_cluster/settings/performance.vue +48 -2
- package/pages/c/_cluster/uiplugins/PluginInfoPanel.vue +34 -1
- package/pages/c/_cluster/uiplugins/index.vue +28 -2
- package/pages/diagnostic.vue +5 -4
- package/pages/home.vue +105 -30
- package/pages/prefs.vue +23 -12
- package/pages/rio/mesh.vue +1 -1
- package/pkg/dynamic-importer.lib.js +8 -0
- package/pkg/vue.config.js +4 -0
- package/plugins/dashboard-store/__tests__/mutations.spec.js +406 -0
- package/plugins/dashboard-store/actions.js +32 -25
- package/plugins/dashboard-store/getters.js +50 -33
- package/plugins/dashboard-store/mutations.js +134 -28
- package/plugins/dashboard-store/resource-class.js +21 -41
- package/plugins/steve/actions.js +30 -0
- package/plugins/steve/caches/resourceCache.js +60 -0
- package/plugins/steve/getters.js +44 -1
- package/plugins/steve/mutations.js +97 -36
- package/plugins/steve/resourceWatcher.js +277 -0
- package/plugins/steve/schema.utils.js +25 -0
- package/plugins/steve/subscribe.js +288 -115
- package/plugins/steve/worker/index.js +17 -0
- package/plugins/steve/worker/web-worker.advanced.js +302 -0
- package/plugins/steve/{web-worker.steve-sub-worker.js → worker/web-worker.basic.js} +3 -44
- package/rancher-components/Card/Card.vue +3 -3
- package/rancher-components/Form/TextArea/TextAreaAutoGrow.vue +1 -0
- package/rancher-components/StringList/StringList.test.ts +45 -420
- package/rancher-components/StringList/StringList.vue +1 -10
- package/rancher-components/components/Banner/Banner.test.ts +44 -0
- package/rancher-components/components/Banner/Banner.vue +129 -61
- package/rancher-components/components/Form/Checkbox/Checkbox.test.ts +13 -22
- package/rancher-components/components/Form/Checkbox/Checkbox.vue +8 -6
- package/rancher-components/components/Form/ToggleSwitch/ToggleSwitch.test.ts +9 -9
- package/rancher-components/components/LabeledTooltip/LabeledTooltip.vue +0 -1
- package/rancher-components/components/StringList/StringList.test.ts +7 -7
- package/rancher-components/components/StringList/StringList.vue +21 -15
- package/scripts/test-plugins-build.sh +8 -0
- package/static/loading-indicator.html +1 -1
- package/store/index.js +54 -3
- package/store/plugins.js +0 -17
- package/store/pnap.js +128 -0
- package/store/prefs.js +4 -2
- package/store/type-map.js +55 -13
- package/types/pod-security-admission.ts +36 -0
- package/types/shell/index.d.ts +496 -396
- package/utils/__tests__/object.test.ts +17 -1
- package/utils/__tests__/pod-security-admission.test.ts +61 -0
- package/utils/async.ts +36 -0
- package/utils/color.js +45 -0
- package/utils/crypto/browserHashUtils.js +18 -0
- package/utils/dynamic-importer.js +8 -0
- package/utils/install-redirect.js +1 -1
- package/utils/object.js +24 -0
- package/utils/pod-security-admission.ts +39 -0
- package/utils/socket.js +61 -24
- package/utils/string.js +2 -0
- package/utils/svg-filter.js +301 -0
- package/utils/time.js +49 -0
- package/utils/validators/cidr.js +4 -0
- package/utils/validators/formRules/__tests__/index.test.ts +23 -3
- package/utils/validators/formRules/index.ts +14 -0
- package/config/product/harvester-manager.js +0 -162
- package/edit/harvesterhci.io.management.cluster.vue +0 -153
- package/list/harvesterhci.io.management.cluster.vue +0 -241
- package/machine-config/harvester.vue +0 -693
- package/models/harvesterhci.io.management.cluster.js +0 -228
- package/pages/c/_cluster/harvesterManager/index.vue +0 -24
- package/rancher-components/Card/Card.test.ts +0 -39
- package/rancher-components/Utils/DraggableZone/DraggableZone.vue +0 -181
- package/rancher-components/Utils/DraggableZone/index.ts +0 -1
- package/rancher-components/components/Utils/DraggableZone/index.ts +0 -1
|
@@ -6,7 +6,9 @@ import Loading from '@shell/components/Loading';
|
|
|
6
6
|
import NameNsDescription from '@shell/components/form/NameNsDescription';
|
|
7
7
|
import Tabbed from '@shell/components/Tabbed';
|
|
8
8
|
import Tab from '@shell/components/Tabbed/Tab';
|
|
9
|
-
import {
|
|
9
|
+
import {
|
|
10
|
+
LOGGING, NAMESPACE, NODE, POD, SCHEMA
|
|
11
|
+
} from '@shell/config/types';
|
|
10
12
|
import jsyaml from 'js-yaml';
|
|
11
13
|
import { createYaml } from '@shell/utils/create-yaml';
|
|
12
14
|
import YamlEditor, { EDITOR_MODES } from '@shell/components/YamlEditor';
|
|
@@ -51,6 +53,7 @@ export default {
|
|
|
51
53
|
async fetch() {
|
|
52
54
|
const hasAccessToClusterOutputs = this.$store.getters[`cluster/schemaFor`](LOGGING.CLUSTER_OUTPUT);
|
|
53
55
|
const hasAccessToOutputs = this.$store.getters[`cluster/schemaFor`](LOGGING.OUTPUT);
|
|
56
|
+
const hasAccessToNamespaces = this.$store.getters[`cluster/schemaFor`](NAMESPACE);
|
|
54
57
|
const hasAccessToNodes = this.$store.getters[`cluster/schemaFor`](NODE);
|
|
55
58
|
const hasAccessToPods = this.$store.getters[`cluster/schemaFor`](POD);
|
|
56
59
|
const isFlow = this.value.type === LOGGING.FLOW;
|
|
@@ -62,6 +65,7 @@ export default {
|
|
|
62
65
|
const hash = await allHash({
|
|
63
66
|
allOutputs: getAllOrDefault(LOGGING.OUTPUT, isFlow && hasAccessToOutputs),
|
|
64
67
|
allClusterOutputs: getAllOrDefault(LOGGING.CLUSTER_OUTPUT, hasAccessToClusterOutputs),
|
|
68
|
+
allNamespaces: getAllOrDefault(NAMESPACE, hasAccessToNamespaces),
|
|
65
69
|
allNodes: getAllOrDefault(NODE, hasAccessToNodes),
|
|
66
70
|
allPods: getAllOrDefault(POD, hasAccessToPods),
|
|
67
71
|
});
|
|
@@ -113,6 +117,7 @@ export default {
|
|
|
113
117
|
matches,
|
|
114
118
|
allOutputs: null,
|
|
115
119
|
allClusterOutputs: null,
|
|
120
|
+
allNamespaces: null,
|
|
116
121
|
allNodes: null,
|
|
117
122
|
allPods: null,
|
|
118
123
|
filtersYaml,
|
|
@@ -166,6 +171,22 @@ export default {
|
|
|
166
171
|
});
|
|
167
172
|
},
|
|
168
173
|
|
|
174
|
+
namespaceChoices() {
|
|
175
|
+
if (!this.allNamespaces) {
|
|
176
|
+
// Handle the case where the user doesn't have permission
|
|
177
|
+
// to see namespaces
|
|
178
|
+
return [];
|
|
179
|
+
}
|
|
180
|
+
const out = this.allNamespaces.map((namespace) => {
|
|
181
|
+
return {
|
|
182
|
+
label: namespace.nameDisplay,
|
|
183
|
+
value: namespace.metadata.name
|
|
184
|
+
};
|
|
185
|
+
});
|
|
186
|
+
|
|
187
|
+
return out;
|
|
188
|
+
},
|
|
189
|
+
|
|
169
190
|
nodeChoices() {
|
|
170
191
|
if (!this.allNodes) {
|
|
171
192
|
// Handle the case where the user doesn't have permission
|
|
@@ -349,7 +370,7 @@ export default {
|
|
|
349
370
|
<Banner
|
|
350
371
|
color="info"
|
|
351
372
|
class="mt-0"
|
|
352
|
-
label="
|
|
373
|
+
:label="t('logging.flow.matches.banner')"
|
|
353
374
|
/>
|
|
354
375
|
<ArrayListGrouped
|
|
355
376
|
v-model="matches"
|
|
@@ -362,8 +383,10 @@ export default {
|
|
|
362
383
|
class="rule mb-20"
|
|
363
384
|
:value="props.row.value"
|
|
364
385
|
:mode="mode"
|
|
386
|
+
:namespaces="namespaceChoices"
|
|
365
387
|
:nodes="nodeChoices"
|
|
366
388
|
:containers="containerChoices"
|
|
389
|
+
:is-cluster-flow="value.type === LOGGING.CLUSTER_FLOW"
|
|
367
390
|
@remove="e=>removeMatch(props.row.i)"
|
|
368
391
|
@input="e=>updateMatch(e,props.row.i)"
|
|
369
392
|
/>
|
|
@@ -394,7 +417,7 @@ export default {
|
|
|
394
417
|
>
|
|
395
418
|
<Banner
|
|
396
419
|
v-if="value.type !== LOGGING.CLUSTER_FLOW"
|
|
397
|
-
label="
|
|
420
|
+
:label="t('logging.flow.outputs.sameNamespaceError')"
|
|
398
421
|
color="info"
|
|
399
422
|
/>
|
|
400
423
|
<LabeledSelect
|
|
@@ -457,7 +480,7 @@ export default {
|
|
|
457
480
|
</CruResource>
|
|
458
481
|
<Banner
|
|
459
482
|
v-else
|
|
460
|
-
label="
|
|
483
|
+
:label="t('logging.flow.matches.unsupportedConfig')"
|
|
461
484
|
color="error"
|
|
462
485
|
/>
|
|
463
486
|
</template>
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import Vue, { PropType, VueConstructor } from 'vue';
|
|
3
|
+
import CreateEditView from '@shell/mixins/create-edit-view';
|
|
4
|
+
import CruResource from '@shell/components/CruResource.vue';
|
|
5
|
+
import PodSecurityAdmission from '@shell/components/PodSecurityAdmission.vue';
|
|
6
|
+
import Loading from '@shell/components/Loading.vue';
|
|
7
|
+
import NameNsDescription from '@shell/components/form/NameNsDescription.vue';
|
|
8
|
+
import { PSA, PSAConfig, PSADefaults, PSAExemptions } from '@shell/types/pod-security-admission';
|
|
9
|
+
import { PSADimensions } from '@shell/config/pod-security-admission';
|
|
10
|
+
import { MANAGEMENT } from '@shell/config/types';
|
|
11
|
+
|
|
12
|
+
export default (Vue as VueConstructor<Vue & InstanceType<typeof CreateEditView>>).extend({
|
|
13
|
+
mixins: [CreateEditView],
|
|
14
|
+
components: {
|
|
15
|
+
CruResource,
|
|
16
|
+
Loading,
|
|
17
|
+
NameNsDescription,
|
|
18
|
+
PodSecurityAdmission,
|
|
19
|
+
},
|
|
20
|
+
|
|
21
|
+
async fetch() {
|
|
22
|
+
await this.$store.dispatch('management/findAll', { type: MANAGEMENT.PSA });
|
|
23
|
+
},
|
|
24
|
+
|
|
25
|
+
props: {
|
|
26
|
+
value: {
|
|
27
|
+
type: Object as PropType<PSA>,
|
|
28
|
+
required: true,
|
|
29
|
+
default: () => ({}) as PSA
|
|
30
|
+
},
|
|
31
|
+
|
|
32
|
+
mode: {
|
|
33
|
+
type: String,
|
|
34
|
+
required: true,
|
|
35
|
+
}
|
|
36
|
+
},
|
|
37
|
+
computed: {
|
|
38
|
+
/**
|
|
39
|
+
* Get or initialize exemptions if none
|
|
40
|
+
*/
|
|
41
|
+
exemptions(): PSAExemptions {
|
|
42
|
+
return this.value?.configuration?.exemptions || {};
|
|
43
|
+
},
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Get or initialize defaults labels if none
|
|
47
|
+
*/
|
|
48
|
+
defaults(): PSADefaults {
|
|
49
|
+
return this.value?.configuration?.defaults || {};
|
|
50
|
+
},
|
|
51
|
+
},
|
|
52
|
+
|
|
53
|
+
methods: {
|
|
54
|
+
/**
|
|
55
|
+
* Replace exemption with new values
|
|
56
|
+
*/
|
|
57
|
+
setExemptions(exemptions: PSAExemptions) {
|
|
58
|
+
this.value.configuration.exemptions = exemptions;
|
|
59
|
+
},
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Replace defaults with new values
|
|
63
|
+
*/
|
|
64
|
+
setDefaults(labels: PSADefaults) {
|
|
65
|
+
this.value.configuration.defaults = labels;
|
|
66
|
+
},
|
|
67
|
+
},
|
|
68
|
+
|
|
69
|
+
created() {
|
|
70
|
+
// Initialize configuration if none, as default value resource case
|
|
71
|
+
if (!this.value.configuration) {
|
|
72
|
+
this.value.configuration = {
|
|
73
|
+
defaults: {},
|
|
74
|
+
exemptions: Object.assign({}, ...PSADimensions.map(dimension => ({ [dimension]: [] }))),
|
|
75
|
+
} as PSAConfig;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
});
|
|
79
|
+
</script>
|
|
80
|
+
|
|
81
|
+
<template>
|
|
82
|
+
<Loading v-if="$fetchState.pending" />
|
|
83
|
+
<CruResource
|
|
84
|
+
v-else
|
|
85
|
+
:mode="mode"
|
|
86
|
+
:resource="value"
|
|
87
|
+
:errors="errors"
|
|
88
|
+
:cancel-event="true"
|
|
89
|
+
@error="setErrors"
|
|
90
|
+
@finish="save"
|
|
91
|
+
@cancel="done()"
|
|
92
|
+
>
|
|
93
|
+
<NameNsDescription
|
|
94
|
+
:value="value"
|
|
95
|
+
:namespaced="false"
|
|
96
|
+
:mode="mode"
|
|
97
|
+
/>
|
|
98
|
+
<PodSecurityAdmission
|
|
99
|
+
:labels="defaults"
|
|
100
|
+
:labels-always-active="true"
|
|
101
|
+
:exemptions="exemptions"
|
|
102
|
+
:mode="mode"
|
|
103
|
+
@updateLabels="setDefaults($event)"
|
|
104
|
+
@updateExemptions="setExemptions($event)"
|
|
105
|
+
/>
|
|
106
|
+
</CruResource>
|
|
107
|
+
</template>
|
|
@@ -16,7 +16,7 @@ import { NAME } from '@shell/config/product/explorer';
|
|
|
16
16
|
import { PROJECT_ID, _VIEW, _CREATE, _EDIT } from '@shell/config/query-params';
|
|
17
17
|
import ProjectMembershipEditor from '@shell/components/form/Members/ProjectMembershipEditor';
|
|
18
18
|
import { canViewProjectMembershipEditor } from '@shell/components/form/Members/ProjectMembershipEditor.vue';
|
|
19
|
-
import { HARVESTER_NAME as HARVESTER } from '@shell/config/
|
|
19
|
+
import { HARVESTER_NAME as HARVESTER } from '@shell/config/features';
|
|
20
20
|
import { Banner } from '@components/Banner';
|
|
21
21
|
|
|
22
22
|
export default {
|
|
@@ -146,6 +146,13 @@ export default {
|
|
|
146
146
|
} else if (this.mode === _EDIT) {
|
|
147
147
|
if (this.canEditProject) {
|
|
148
148
|
await this.value.save(true);
|
|
149
|
+
|
|
150
|
+
// We updated the Norman resource - re-fetch the Steve resource so we know it is definitely updated in the store
|
|
151
|
+
await this.$store.dispatch('management/find', {
|
|
152
|
+
type: MANAGEMENT.PROJECT,
|
|
153
|
+
id: this.value.id,
|
|
154
|
+
opt: { force: true }
|
|
155
|
+
});
|
|
149
156
|
}
|
|
150
157
|
|
|
151
158
|
// // we allow users with permissions for projectroletemplatebindings to be able to manage members on projects
|
|
@@ -57,8 +57,11 @@ export default {
|
|
|
57
57
|
// We map the setting rulesets to use values to define validation from factory
|
|
58
58
|
return this.setting?.ruleSet ? mapValues(
|
|
59
59
|
keyBy(this.setting.ruleSet, 'name'),
|
|
60
|
-
|
|
61
|
-
|
|
60
|
+
// The validation is curried and may require the factory argument for the ValidatorFactory
|
|
61
|
+
({ key, name, factoryArg }) => {
|
|
62
|
+
const rule = formRulesGenerator(t, key ? { key } : {})[name];
|
|
63
|
+
|
|
64
|
+
return factoryArg ? rule(factoryArg) : rule;
|
|
62
65
|
}) : {};
|
|
63
66
|
}
|
|
64
67
|
},
|
|
@@ -167,7 +167,13 @@ export default {
|
|
|
167
167
|
normanUser._name = this.form.displayName;
|
|
168
168
|
normanUser.mustChangePassword = this.form.password.userChangeOnLogin;
|
|
169
169
|
|
|
170
|
-
|
|
170
|
+
await normanUser.save();
|
|
171
|
+
|
|
172
|
+
return await this.$store.dispatch('management/find', {
|
|
173
|
+
type: MANAGEMENT.USER,
|
|
174
|
+
id: this.value.id,
|
|
175
|
+
opt: { force: true }
|
|
176
|
+
});
|
|
171
177
|
},
|
|
172
178
|
|
|
173
179
|
async updateRoles(userId) {
|
|
@@ -12,6 +12,7 @@ import CreateEditView from '@shell/mixins/create-edit-view';
|
|
|
12
12
|
import jsyaml from 'js-yaml';
|
|
13
13
|
import ButtonDropdown from '@shell/components/ButtonDropdown';
|
|
14
14
|
import { _CREATE, _VIEW } from '@shell/config/query-params';
|
|
15
|
+
import FormValidation from '@shell/mixins/form-validation';
|
|
15
16
|
|
|
16
17
|
export const RECEIVERS_TYPES = [
|
|
17
18
|
{
|
|
@@ -100,7 +101,7 @@ export default {
|
|
|
100
101
|
},
|
|
101
102
|
},
|
|
102
103
|
|
|
103
|
-
mixins: [CreateEditView],
|
|
104
|
+
mixins: [CreateEditView, FormValidation],
|
|
104
105
|
|
|
105
106
|
data(props) {
|
|
106
107
|
const currentReceiver = {};
|
|
@@ -144,14 +145,18 @@ export default {
|
|
|
144
145
|
}
|
|
145
146
|
|
|
146
147
|
return {
|
|
147
|
-
create:
|
|
148
|
+
create: _CREATE,
|
|
148
149
|
EDITOR_MODES,
|
|
149
150
|
expectedFields,
|
|
150
|
-
fileFound:
|
|
151
|
-
receiverTypes:
|
|
151
|
+
fileFound: false,
|
|
152
|
+
receiverTypes: RECEIVERS_TYPES,
|
|
152
153
|
suffixYaml,
|
|
153
|
-
view:
|
|
154
|
-
yamlError:
|
|
154
|
+
view: _VIEW,
|
|
155
|
+
yamlError: '',
|
|
156
|
+
fvFormRuleSets: [
|
|
157
|
+
{ path: 'name', rules: ['required'] }
|
|
158
|
+
],
|
|
159
|
+
fvReportedValidationPaths: ['value']
|
|
155
160
|
};
|
|
156
161
|
},
|
|
157
162
|
|
|
@@ -235,6 +240,14 @@ export default {
|
|
|
235
240
|
createAddOptions(receiverType) {
|
|
236
241
|
return receiverType.addOptions.map();
|
|
237
242
|
},
|
|
243
|
+
|
|
244
|
+
setError(err) {
|
|
245
|
+
if (!err) {
|
|
246
|
+
this.errors = [];
|
|
247
|
+
} else {
|
|
248
|
+
this.errors = [err];
|
|
249
|
+
}
|
|
250
|
+
}
|
|
238
251
|
}
|
|
239
252
|
};
|
|
240
253
|
</script>
|
|
@@ -249,8 +262,9 @@ export default {
|
|
|
249
262
|
:can-yaml="true"
|
|
250
263
|
:errors="errors"
|
|
251
264
|
:cancel-event="true"
|
|
265
|
+
:validation-passed="fvFormIsValid"
|
|
252
266
|
@error="e=>errors = e"
|
|
253
|
-
@finish="saveOverride
|
|
267
|
+
@finish="saveOverride"
|
|
254
268
|
@cancel="redirectAfterCancel"
|
|
255
269
|
>
|
|
256
270
|
<div class="row mb-10">
|
|
@@ -259,7 +273,9 @@ export default {
|
|
|
259
273
|
v-model="value.name"
|
|
260
274
|
:is-disabled="receiverNameDisabled"
|
|
261
275
|
:label="t('generic.name')"
|
|
276
|
+
:required="true"
|
|
262
277
|
:mode="mode"
|
|
278
|
+
:rules="fvGetAndReportPathRules('name')"
|
|
263
279
|
/>
|
|
264
280
|
</div>
|
|
265
281
|
</div>
|
|
@@ -25,7 +25,7 @@ export default {
|
|
|
25
25
|
},
|
|
26
26
|
data() {
|
|
27
27
|
this.$set(this.value, 'sendResolved', this.value.sendResolved || false);
|
|
28
|
-
this.$set(this.value, '
|
|
28
|
+
this.$set(this.value, 'requireTLS', this.value.requireTLS || false);
|
|
29
29
|
|
|
30
30
|
return {
|
|
31
31
|
view: _VIEW,
|
|
@@ -123,7 +123,7 @@ export default {
|
|
|
123
123
|
</div>
|
|
124
124
|
<div class="col span-6">
|
|
125
125
|
<Checkbox
|
|
126
|
-
v-model="value.
|
|
126
|
+
v-model="value.requireTLS"
|
|
127
127
|
:mode="mode"
|
|
128
128
|
class="mt-20"
|
|
129
129
|
label="Use TLS"
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
<script>
|
|
2
2
|
import has from 'lodash/has';
|
|
3
|
-
|
|
4
3
|
import { Banner } from '@components/Banner';
|
|
5
4
|
import { removeAt } from '@shell/utils/array';
|
|
6
5
|
import { _VIEW } from '@shell/config/query-params';
|
|
@@ -34,8 +33,9 @@ export default {
|
|
|
34
33
|
expr: '',
|
|
35
34
|
for: '0s',
|
|
36
35
|
labels: {
|
|
37
|
-
severity:
|
|
38
|
-
namespace:
|
|
36
|
+
severity: 'none',
|
|
37
|
+
namespace: 'default',
|
|
38
|
+
cluster_id: this.$store.getters['clusterId']
|
|
39
39
|
},
|
|
40
40
|
};
|
|
41
41
|
|
|
@@ -91,7 +91,15 @@ export default {
|
|
|
91
91
|
|
|
92
92
|
switch (ruleType) {
|
|
93
93
|
case 'record':
|
|
94
|
-
value.push({
|
|
94
|
+
value.push({
|
|
95
|
+
record: '',
|
|
96
|
+
expr: '',
|
|
97
|
+
labels: {
|
|
98
|
+
severity: 'none',
|
|
99
|
+
namespace: 'default',
|
|
100
|
+
cluster_id: this.$store.getters['clusterId']
|
|
101
|
+
},
|
|
102
|
+
});
|
|
95
103
|
break;
|
|
96
104
|
case 'alert':
|
|
97
105
|
value.push(this.defaultAlert);
|
|
@@ -145,7 +153,7 @@ export default {
|
|
|
145
153
|
class="btn role-link close btn-sm"
|
|
146
154
|
@click="removeRule(props.i)"
|
|
147
155
|
>
|
|
148
|
-
<i class="icon icon-
|
|
156
|
+
<i class="icon icon-x" />
|
|
149
157
|
</button>
|
|
150
158
|
<span v-else />
|
|
151
159
|
</template>
|
|
@@ -194,7 +202,7 @@ export default {
|
|
|
194
202
|
class="btn role-link close btn-sm"
|
|
195
203
|
@click="removeRule(props.i)"
|
|
196
204
|
>
|
|
197
|
-
<i class="icon icon-
|
|
205
|
+
<i class="icon icon-x" />
|
|
198
206
|
</button>
|
|
199
207
|
<span v-else />
|
|
200
208
|
</template>
|
package/edit/namespace.vue
CHANGED
|
@@ -6,16 +6,17 @@ import LabeledSelect from '@shell/components/form/LabeledSelect';
|
|
|
6
6
|
import { MANAGEMENT } from '@shell/config/types';
|
|
7
7
|
import { CONTAINER_DEFAULT_RESOURCE_LIMIT, PROJECT } from '@shell/config/labels-annotations';
|
|
8
8
|
import ContainerResourceLimit from '@shell/components/ContainerResourceLimit';
|
|
9
|
+
import PodSecurityAdmission from '@shell/components/PodSecurityAdmission';
|
|
9
10
|
import Tabbed from '@shell/components/Tabbed';
|
|
10
11
|
import Tab from '@shell/components/Tabbed/Tab';
|
|
11
12
|
import CruResource from '@shell/components/CruResource';
|
|
12
|
-
import Labels from '@shell/components/form/Labels';
|
|
13
13
|
import { PROJECT_ID, _VIEW } from '@shell/config/query-params';
|
|
14
14
|
import MoveModal from '@shell/components/MoveModal';
|
|
15
15
|
import ResourceQuota from '@shell/components/form/ResourceQuota/Namespace';
|
|
16
16
|
import Loading from '@shell/components/Loading';
|
|
17
17
|
import { HARVESTER_TYPES, RANCHER_TYPES } from '@shell/components/form/ResourceQuota/shared';
|
|
18
|
-
import { HARVESTER_NAME as HARVESTER } from '@shell/config/
|
|
18
|
+
import { HARVESTER_NAME as HARVESTER } from '@shell/config/features';
|
|
19
|
+
import Labels from '@shell/components/form/Labels';
|
|
19
20
|
|
|
20
21
|
export default {
|
|
21
22
|
components: {
|
|
@@ -25,6 +26,7 @@ export default {
|
|
|
25
26
|
Labels,
|
|
26
27
|
Loading,
|
|
27
28
|
NameNsDescription,
|
|
29
|
+
PodSecurityAdmission,
|
|
28
30
|
ResourceQuota,
|
|
29
31
|
Tab,
|
|
30
32
|
Tabbed,
|
|
@@ -101,7 +103,8 @@ export default {
|
|
|
101
103
|
|
|
102
104
|
showContainerResourceLimit() {
|
|
103
105
|
return !this.isSingleHarvester;
|
|
104
|
-
}
|
|
106
|
+
},
|
|
107
|
+
|
|
105
108
|
},
|
|
106
109
|
|
|
107
110
|
watch: {
|
|
@@ -222,7 +225,6 @@ export default {
|
|
|
222
225
|
/>
|
|
223
226
|
</Tab>
|
|
224
227
|
<Tab
|
|
225
|
-
v-if="!isView"
|
|
226
228
|
name="labels-and-annotations"
|
|
227
229
|
label-key="generic.labelsAndAnnotations"
|
|
228
230
|
:weight="-1"
|
|
@@ -234,6 +236,18 @@ export default {
|
|
|
234
236
|
:display-side-by-side="false"
|
|
235
237
|
/>
|
|
236
238
|
</Tab>
|
|
239
|
+
<Tab
|
|
240
|
+
name="pod-security-admission"
|
|
241
|
+
label-key="podSecurityAdmission.name"
|
|
242
|
+
:label="t('podSecurityAdmission.name')"
|
|
243
|
+
>
|
|
244
|
+
<PodSecurityAdmission
|
|
245
|
+
:labels="value.labels"
|
|
246
|
+
:mode="mode"
|
|
247
|
+
labels-prefix="pod-security.kubernetes.io/"
|
|
248
|
+
@updateLabels="value.setLabels($event)"
|
|
249
|
+
/>
|
|
250
|
+
</Tab>
|
|
237
251
|
</Tabbed>
|
|
238
252
|
<MoveModal v-if="projects" />
|
|
239
253
|
</CruResource>
|
|
@@ -37,12 +37,13 @@ export default {
|
|
|
37
37
|
},
|
|
38
38
|
methods: {
|
|
39
39
|
update(e) {
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
if (this.ingressClassName) {
|
|
43
|
-
set(this.value, 'spec.ingressClassName', this.ingressClassName);
|
|
44
|
-
} else {
|
|
40
|
+
if (!e || e.label === this.t('generic.none')) {
|
|
45
41
|
remove(this.value, 'spec.ingressClassName');
|
|
42
|
+
this.ingressClassName = '';
|
|
43
|
+
} else {
|
|
44
|
+
// when a user manually types an ingress class name, the event emitted has a 'label' but no 'value'
|
|
45
|
+
this.ingressClassName = e.value ? e.value : e.label;
|
|
46
|
+
set(this.value, 'spec.ingressClassName', this.ingressClassName);
|
|
46
47
|
}
|
|
47
48
|
}
|
|
48
49
|
}
|
|
@@ -53,11 +54,12 @@ export default {
|
|
|
53
54
|
<LabeledSelect
|
|
54
55
|
v-model="ingressClassName"
|
|
55
56
|
:taggable="true"
|
|
57
|
+
:searchable="true"
|
|
56
58
|
:mode="mode"
|
|
57
59
|
:label="t('ingress.ingressClass.label')"
|
|
58
60
|
:options="ingressClassOptions"
|
|
59
61
|
option-label="label"
|
|
60
|
-
@
|
|
62
|
+
@selecting="update"
|
|
61
63
|
/>
|
|
62
64
|
</div>
|
|
63
65
|
</template>
|
|
@@ -66,7 +66,11 @@ export default {
|
|
|
66
66
|
return isValueAnOption ? null : 'warning';
|
|
67
67
|
},
|
|
68
68
|
serviceTargetTooltip() {
|
|
69
|
-
|
|
69
|
+
if (this.serviceTargetStatus === 'warning' ) {
|
|
70
|
+
return this.t('ingress.rules.target.doesntExist');
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
return this.t('ingress.rules.target.tooltip');
|
|
70
74
|
},
|
|
71
75
|
},
|
|
72
76
|
created() {
|
|
@@ -178,17 +182,19 @@ export default {
|
|
|
178
182
|
</div>
|
|
179
183
|
</template>
|
|
180
184
|
<style lang="scss" scoped>
|
|
185
|
+
$row-height: 40px;
|
|
186
|
+
|
|
181
187
|
.labeled-input ::v-deep, ::v-deep .labeled-input {
|
|
182
188
|
padding: 0 !important;
|
|
183
189
|
height: 100%;
|
|
184
190
|
input.no-label {
|
|
185
|
-
height: calc($
|
|
191
|
+
height: calc($row-height - 2px);
|
|
186
192
|
padding: 10px;
|
|
187
193
|
}
|
|
188
194
|
}
|
|
189
195
|
.rule-path ::v-deep {
|
|
190
|
-
.col {
|
|
191
|
-
height: $
|
|
196
|
+
.col, INPUT {
|
|
197
|
+
height: $row-height;
|
|
192
198
|
}
|
|
193
199
|
|
|
194
200
|
.unlabeled-select {
|
|
@@ -202,7 +208,7 @@ export default {
|
|
|
202
208
|
}
|
|
203
209
|
|
|
204
210
|
&, .input-container {
|
|
205
|
-
height: $
|
|
211
|
+
height: $row-height;
|
|
206
212
|
}
|
|
207
213
|
|
|
208
214
|
.input-container .in-input.unlabeled-select {
|
|
@@ -210,7 +216,7 @@ export default {
|
|
|
210
216
|
}
|
|
211
217
|
|
|
212
218
|
button {
|
|
213
|
-
line-height:
|
|
219
|
+
line-height: $row-height;
|
|
214
220
|
}
|
|
215
221
|
|
|
216
222
|
.v-select INPUT {
|
|
@@ -44,11 +44,11 @@ export default {
|
|
|
44
44
|
}
|
|
45
45
|
},
|
|
46
46
|
async fetch() {
|
|
47
|
-
|
|
47
|
+
this.ingressClassSchema = this.$store.getters[`cluster/schemaFor`](INGRESS_CLASS);
|
|
48
48
|
const hash = await allHash({
|
|
49
49
|
secrets: this.$store.dispatch('cluster/findAll', { type: SECRET }),
|
|
50
50
|
services: this.$store.dispatch('cluster/findAll', { type: SERVICE }),
|
|
51
|
-
ingressClasses: ingressClassSchema ? this.$store.dispatch('cluster/findAll', { type: INGRESS_CLASS }) : Promise.resolve([]),
|
|
51
|
+
ingressClasses: this.ingressClassSchema ? this.$store.dispatch('cluster/findAll', { type: INGRESS_CLASS }) : Promise.resolve([]),
|
|
52
52
|
});
|
|
53
53
|
|
|
54
54
|
this.allServices = hash.services;
|
|
@@ -57,10 +57,11 @@ export default {
|
|
|
57
57
|
},
|
|
58
58
|
data() {
|
|
59
59
|
return {
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
60
|
+
ingressClassSchema: null,
|
|
61
|
+
allSecrets: [],
|
|
62
|
+
allServices: [],
|
|
63
|
+
allIngressClasses: [],
|
|
64
|
+
fvFormRuleSets: [
|
|
64
65
|
{
|
|
65
66
|
path: 'metadata.name', rules: ['required', 'hostname'], translationKey: 'nameNsDescription.name.label'
|
|
66
67
|
},
|
|
@@ -197,6 +198,7 @@ export default {
|
|
|
197
198
|
:subtypes="[]"
|
|
198
199
|
:validation-passed="fvFormIsValid"
|
|
199
200
|
:errors="fvUnreportedValidationErrors"
|
|
201
|
+
:description="t('ingress.description')"
|
|
200
202
|
@error="e=>errors = e"
|
|
201
203
|
@finish="save"
|
|
202
204
|
@cancel="done"
|