@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.
Files changed (322) hide show
  1. package/assets/styles/global/_button.scss +5 -1
  2. package/assets/styles/global/_columns.scss +4 -0
  3. package/assets/styles/global/_layout.scss +1 -2
  4. package/assets/styles/global/_select.scss +1 -4
  5. package/assets/styles/themes/_dark.scss +4 -4
  6. package/assets/styles/themes/_light.scss +4 -3
  7. package/assets/styles/themes/_suse.scss +1 -1
  8. package/assets/styles/vendor/vue-select.scss +4 -3
  9. package/assets/translations/en-us.yaml +669 -73
  10. package/assets/translations/zh-hans.yaml +547 -165
  11. package/chart/monitoring/steps/uninstall-v1.vue +2 -2
  12. package/cloud-credential/azure.vue +23 -0
  13. package/cloud-credential/harvester.vue +25 -62
  14. package/cloud-credential/pnap.vue +80 -0
  15. package/components/.DS_Store +0 -0
  16. package/components/AdvancedSection.vue +9 -2
  17. package/components/Alert.vue +2 -2
  18. package/components/ButtonDropdown.vue +0 -2
  19. package/components/ButtonGroup.vue +1 -0
  20. package/components/CollapsibleCard.vue +0 -1
  21. package/components/CruResource.vue +41 -4
  22. package/components/DetailTop.vue +58 -3
  23. package/components/DisableAuthProviderModal.vue +106 -0
  24. package/{rancher-components/components/Utils/DraggableZone → components}/DraggableZone.vue +0 -0
  25. package/components/ExplorerMembers.vue +253 -30
  26. package/components/ExplorerProjectsNamespaces.vue +77 -33
  27. package/components/GrowlManager.vue +3 -3
  28. package/components/IconOrSvg.vue +149 -0
  29. package/components/LogItem.vue +69 -0
  30. package/components/PodSecurityAdmission.vue +302 -0
  31. package/components/PromptModal.vue +1 -0
  32. package/components/ResourceDetail/Masthead.vue +54 -2
  33. package/components/ResourceDetail/index.vue +12 -5
  34. package/components/ResourceList/Masthead.vue +11 -1
  35. package/components/ResourceList/ResourceLoadingIndicator.vue +12 -2
  36. package/components/ResourceList/index.vue +53 -12
  37. package/components/ResourceList/resource-list.config.js +7 -0
  38. package/components/ResourceTable.vue +31 -6
  39. package/components/SimpleBox.vue +1 -1
  40. package/components/SortableTable/THead.vue +15 -5
  41. package/components/SortableTable/index.vue +21 -10
  42. package/components/Tabbed/index.vue +20 -15
  43. package/components/__tests__/.DS_Store +0 -0
  44. package/components/__tests__/AsyncButton.test.ts +140 -0
  45. package/components/__tests__/BackLink.test.ts +33 -0
  46. package/components/__tests__/ButtonGroup.test.ts +124 -0
  47. package/components/__tests__/ClusterBadge.test.ts +32 -0
  48. package/components/__tests__/CollapsibleCard.test.ts +64 -0
  49. package/components/__tests__/ConsumptionGauge.test.ts +88 -0
  50. package/components/__tests__/CruResource.test.ts +3 -2
  51. package/components/__tests__/FixedBanner.test.ts +129 -0
  52. package/components/__tests__/GrowlManager.test.ts +147 -0
  53. package/components/__tests__/NamespaceFilter.test.ts +33 -25
  54. package/components/__tests__/PercentageBar.test.ts +32 -0
  55. package/components/__tests__/PodSecurityAdmission.test.ts +398 -0
  56. package/components/auth/AuthBanner.vue +20 -10
  57. package/components/auth/RoleDetailEdit.vue +26 -17
  58. package/components/auth/SelectPrincipal.vue +36 -5
  59. package/components/form/ArrayList.vue +3 -35
  60. package/components/form/ArrayListGrouped.vue +13 -4
  61. package/components/form/ArrayListSelect.vue +5 -5
  62. package/components/form/Error.vue +8 -0
  63. package/components/form/KeyValue.vue +39 -7
  64. package/components/form/LabeledSelect.vue +5 -2
  65. package/components/form/Labels.vue +46 -16
  66. package/components/form/Members/ClusterPermissionsEditor.vue +17 -17
  67. package/components/form/Members/MembershipEditor.vue +12 -12
  68. package/components/form/NameNsDescription.vue +1 -1
  69. package/components/form/NodeScheduling.vue +1 -1
  70. package/components/form/Probe.vue +3 -3
  71. package/components/form/ResourceQuota/Project.vue +6 -6
  72. package/components/form/ResourceTabs/index.vue +1 -6
  73. package/components/form/Security.vue +7 -6
  74. package/components/form/Select.vue +3 -2
  75. package/components/form/SelectOrCreateAuthSecret.vue +22 -29
  76. package/components/form/ServicePorts.vue +8 -0
  77. package/components/form/WorkloadPorts.vue +7 -1
  78. package/components/form/__tests__/ArrayList.test.ts +74 -0
  79. package/components/form/__tests__/ArrayListGrouped.test.ts +6 -4
  80. package/components/formatter/Checked.vue +1 -1
  81. package/components/formatter/ClusterLink.vue +5 -0
  82. package/components/formatter/IconIsDefault.vue +2 -2
  83. package/components/formatter/InternalExternalIP.vue +11 -8
  84. package/components/formatter/LiveDuration.vue +78 -0
  85. package/components/formatter/WorkloadHealthScale.vue +5 -3
  86. package/components/nav/Header.vue +6 -3
  87. package/components/nav/NamespaceFilter.vue +146 -63
  88. package/components/nav/TopLevelMenu.vue +22 -19
  89. package/components/nav/WindowManager/ContainerLogs.vue +83 -126
  90. package/components/nav/WindowManager/ContainerShell.vue +9 -7
  91. package/components/nav/WindowManager/Window.vue +2 -0
  92. package/components/nav/WindowManager/index.vue +10 -0
  93. package/config/elemental-types.js +9 -0
  94. package/config/features.js +2 -0
  95. package/config/home-links.js +4 -1
  96. package/config/pod-security-admission.ts +82 -0
  97. package/config/product/apps.js +1 -1
  98. package/config/product/auth.js +6 -5
  99. package/config/product/explorer.js +6 -6
  100. package/config/product/fleet.js +1 -1
  101. package/config/product/manager.js +6 -2
  102. package/config/secret.js +0 -1
  103. package/config/settings.ts +26 -9
  104. package/config/table-headers.js +22 -11
  105. package/config/types.js +4 -1
  106. package/content/docs/zh-hans/getting-started.md +113 -137
  107. package/content/docs/zh-hans/whats-new.md +8 -46
  108. package/creators/pkg/package-lock.json +37 -0
  109. package/creators/pkg/package.json +1 -1
  110. package/detail/catalog.cattle.io.app.vue +1 -1
  111. package/detail/pod.vue +1 -1
  112. package/detail/provisioning.cattle.io.cluster.vue +35 -9
  113. package/detail/service.vue +2 -9
  114. package/detail/workload/index.vue +0 -1
  115. package/dialog/AddClusterMemberDialog.vue +22 -28
  116. package/dialog/AddProjectMemberDialog.vue +53 -9
  117. package/dialog/DiagnosticTimingsDialog.vue +8 -7
  118. package/dialog/DrainNode.vue +44 -48
  119. package/dialog/ForceMachineRemoveDialog.vue +5 -7
  120. package/dialog/GenericPrompt.vue +15 -20
  121. package/dialog/RollbackWorkloadDialog.vue +15 -46
  122. package/dialog/RotateCertificatesDialog.vue +5 -7
  123. package/dialog/RotateEncryptionKeyDialog.vue +5 -9
  124. package/dialog/SaveAsRKETemplateDialog.vue +5 -13
  125. package/dialog/ScaleMachineDownDialog.vue +1 -1
  126. package/dialog/ScalePoolDownDialog.vue +121 -0
  127. package/edit/__tests__/management.cattle.io.setting.test.ts +3 -3
  128. package/edit/auth/azuread.vue +16 -16
  129. package/edit/auth/github.vue +8 -0
  130. package/edit/auth/googleoauth.vue +10 -1
  131. package/edit/auth/ldap/index.vue +10 -0
  132. package/edit/auth/oidc.vue +10 -0
  133. package/edit/auth/saml.vue +10 -0
  134. package/edit/autoscaling.horizontalpodautoscaler/index.vue +1 -1
  135. package/edit/cloudcredential.vue +3 -7
  136. package/edit/logging-flow/Match.vue +39 -8
  137. package/edit/logging-flow/index.vue +27 -4
  138. package/edit/management.cattle.io.podsecurityadmissionconfigurationtemplate.vue +107 -0
  139. package/edit/management.cattle.io.project.vue +8 -1
  140. package/edit/management.cattle.io.setting.vue +5 -2
  141. package/edit/management.cattle.io.user.vue +7 -1
  142. package/edit/monitoring.coreos.com.alertmanagerconfig/receiverConfig.vue +23 -7
  143. package/edit/monitoring.coreos.com.alertmanagerconfig/types/email.vue +2 -2
  144. package/edit/monitoring.coreos.com.prometheusrule/GroupRules.vue +14 -6
  145. package/edit/namespace.vue +18 -4
  146. package/edit/networking.k8s.io.ingress/Certificate.vue +1 -0
  147. package/edit/networking.k8s.io.ingress/IngressClass.vue +8 -6
  148. package/edit/networking.k8s.io.ingress/RulePath.vue +12 -6
  149. package/edit/networking.k8s.io.ingress/index.vue +8 -6
  150. package/edit/persistentvolume/index.vue +30 -27
  151. package/edit/persistentvolume/plugins/cephfs.vue +29 -29
  152. package/edit/persistentvolume/plugins/csi.vue +102 -62
  153. package/edit/persistentvolume/plugins/fc.vue +19 -19
  154. package/edit/persistentvolume/plugins/iscsi.vue +45 -45
  155. package/edit/persistentvolume/plugins/rbd.vue +39 -39
  156. package/edit/persistentvolumeclaim.vue +78 -75
  157. package/edit/provisioning.cattle.io.cluster/MachinePool.vue +11 -7
  158. package/edit/provisioning.cattle.io.cluster/RegistryConfigs.vue +10 -1
  159. package/edit/provisioning.cattle.io.cluster/RegistryMirrors.vue +87 -27
  160. package/edit/provisioning.cattle.io.cluster/SelectCredential.vue +3 -6
  161. package/edit/provisioning.cattle.io.cluster/__tests__/rke2.test.ts +93 -0
  162. package/edit/provisioning.cattle.io.cluster/import.vue +1 -1
  163. package/edit/provisioning.cattle.io.cluster/index.vue +29 -6
  164. package/edit/provisioning.cattle.io.cluster/rke2.vue +440 -152
  165. package/edit/secret/index.vue +3 -7
  166. package/edit/service.vue +3 -1
  167. package/edit/storage.k8s.io.storageclass/index.vue +100 -16
  168. package/edit/storage.k8s.io.storageclass/provisioners/driver.harvesterhci.io.vue +114 -0
  169. package/edit/workload/__tests__/index.test.ts +98 -0
  170. package/edit/workload/index.vue +58 -8
  171. package/edit/workload/mixins/workload.js +107 -70
  172. package/edit/workload/storage/ContainerMountPaths.vue +0 -10
  173. package/edit/workload/storage/emptyDir.vue +88 -0
  174. package/edit/workload/storage/ephemeralVolume/index.vue +1 -1
  175. package/edit/workload/storage/index.vue +8 -0
  176. package/edit/workload/storage/persistentVolumeClaim/index.vue +1 -1
  177. package/layouts/default.vue +57 -44
  178. package/list/__tests__/workload.test.ts +5 -2
  179. package/list/catalog.cattle.io.app.vue +1 -0
  180. package/list/cis.cattle.io.clusterscan.vue +1 -0
  181. package/list/fleet.cattle.io.bundle.vue +5 -6
  182. package/list/fleet.cattle.io.cluster.vue +6 -3
  183. package/list/fleet.cattle.io.clusterregistrationtoken.vue +5 -6
  184. package/list/fleet.cattle.io.gitrepo.vue +4 -9
  185. package/list/helm.cattle.io.projecthelmchart.vue +1 -5
  186. package/list/logging.banzaicloud.io.clusterflow.vue +4 -1
  187. package/list/logging.banzaicloud.io.flow.vue +6 -5
  188. package/list/management.cattle.io.cluster.vue +1 -0
  189. package/list/management.cattle.io.feature.vue +3 -4
  190. package/list/management.cattle.io.podsecurityadmissionconfigurationtemplate.vue +47 -0
  191. package/list/management.cattle.io.setting.vue +2 -2
  192. package/list/management.cattle.io.user.vue +4 -10
  193. package/list/monitoring.coreos.com.alertmanagerconfig.vue +2 -7
  194. package/list/node.vue +8 -5
  195. package/list/persistentvolume.vue +3 -3
  196. package/list/persistentvolumeclaim.vue +3 -4
  197. package/list/provisioning.cattle.io.cluster.vue +18 -19
  198. package/list/service.vue +6 -14
  199. package/list/workload.vue +43 -38
  200. package/machine-config/azure.vue +429 -60
  201. package/machine-config/pnap.vue +288 -0
  202. package/mixins/auth-config.js +1 -3
  203. package/mixins/browser-tab-visibility.js +8 -14
  204. package/mixins/chart.js +1 -1
  205. package/mixins/create-edit-view/impl.js +4 -0
  206. package/mixins/create-edit-view/index.js +4 -2
  207. package/mixins/resource-fetch-namespaced.js +98 -0
  208. package/mixins/resource-fetch.js +79 -45
  209. package/mixins/resource-manager.js +1 -23
  210. package/models/apps.controllerrevision.js +7 -0
  211. package/models/apps.daemonset.js +18 -0
  212. package/models/apps.deployment.js +44 -0
  213. package/models/apps.replicaset.js +7 -0
  214. package/models/apps.statefulset.js +18 -0
  215. package/models/batch.job.js +7 -14
  216. package/models/cluster/node.js +10 -2
  217. package/models/cluster.x-k8s.io.machine.js +26 -4
  218. package/models/cluster.x-k8s.io.machinedeployment.js +12 -2
  219. package/models/event.js +7 -0
  220. package/models/logging.banzaicloud.io.flow.js +4 -0
  221. package/models/management.cattle.io.cluster.js +1 -1
  222. package/models/management.cattle.io.clusterroletemplatebinding.js +1 -1
  223. package/models/management.cattle.io.globalrole.js +2 -2
  224. package/models/management.cattle.io.node.js +37 -2
  225. package/models/management.cattle.io.podsecurityadmissionconfigurationtemplate.ts +4 -0
  226. package/models/management.cattle.io.project.js +30 -11
  227. package/models/management.cattle.io.setting.js +1 -1
  228. package/models/management.cattle.io.user.js +37 -1
  229. package/models/namespace.js +42 -5
  230. package/models/persistentvolume.js +14 -2
  231. package/models/pod.js +15 -0
  232. package/models/projectroletemplatebinding.js +7 -0
  233. package/models/provisioning.cattle.io.cluster.js +61 -10
  234. package/models/rke-machine.cattle.io.pnapmachinetemplate.js +15 -0
  235. package/models/service.js +14 -13
  236. package/models/storage.k8s.io.storageclass.js +33 -18
  237. package/models/workload.js +38 -7
  238. package/nuxt.config.js +27 -17
  239. package/package.json +7 -7
  240. package/pages/about.vue +14 -2
  241. package/pages/c/_cluster/apps/charts/index.vue +4 -3
  242. package/pages/c/_cluster/apps/charts/install.vue +59 -22
  243. package/pages/c/_cluster/auth/config/_id.vue +6 -0
  244. package/pages/c/_cluster/auth/config/index.vue +8 -6
  245. package/pages/c/_cluster/auth/group.principal/assign-edit.vue +1 -1
  246. package/pages/c/_cluster/auth/roles/index.vue +1 -1
  247. package/pages/c/_cluster/explorer/index.vue +12 -6
  248. package/pages/c/_cluster/longhorn/index.vue +1 -1
  249. package/pages/c/_cluster/monitoring/alertmanagerconfig/_alertmanagerconfigid/receiver.vue +15 -4
  250. package/pages/c/_cluster/monitoring/index.vue +1 -1
  251. package/pages/c/_cluster/neuvector/index.vue +1 -1
  252. package/pages/c/_cluster/settings/performance.vue +48 -2
  253. package/pages/c/_cluster/uiplugins/PluginInfoPanel.vue +34 -1
  254. package/pages/c/_cluster/uiplugins/index.vue +28 -2
  255. package/pages/diagnostic.vue +5 -4
  256. package/pages/home.vue +105 -30
  257. package/pages/prefs.vue +23 -12
  258. package/pages/rio/mesh.vue +1 -1
  259. package/pkg/dynamic-importer.lib.js +8 -0
  260. package/pkg/vue.config.js +4 -0
  261. package/plugins/dashboard-store/__tests__/mutations.spec.js +406 -0
  262. package/plugins/dashboard-store/actions.js +32 -25
  263. package/plugins/dashboard-store/getters.js +50 -33
  264. package/plugins/dashboard-store/mutations.js +134 -28
  265. package/plugins/dashboard-store/resource-class.js +21 -41
  266. package/plugins/steve/actions.js +30 -0
  267. package/plugins/steve/caches/resourceCache.js +60 -0
  268. package/plugins/steve/getters.js +44 -1
  269. package/plugins/steve/mutations.js +97 -36
  270. package/plugins/steve/resourceWatcher.js +277 -0
  271. package/plugins/steve/schema.utils.js +25 -0
  272. package/plugins/steve/subscribe.js +288 -115
  273. package/plugins/steve/worker/index.js +17 -0
  274. package/plugins/steve/worker/web-worker.advanced.js +302 -0
  275. package/plugins/steve/{web-worker.steve-sub-worker.js → worker/web-worker.basic.js} +3 -44
  276. package/rancher-components/Card/Card.vue +3 -3
  277. package/rancher-components/Form/TextArea/TextAreaAutoGrow.vue +1 -0
  278. package/rancher-components/StringList/StringList.test.ts +45 -420
  279. package/rancher-components/StringList/StringList.vue +1 -10
  280. package/rancher-components/components/Banner/Banner.test.ts +44 -0
  281. package/rancher-components/components/Banner/Banner.vue +129 -61
  282. package/rancher-components/components/Form/Checkbox/Checkbox.test.ts +13 -22
  283. package/rancher-components/components/Form/Checkbox/Checkbox.vue +8 -6
  284. package/rancher-components/components/Form/ToggleSwitch/ToggleSwitch.test.ts +9 -9
  285. package/rancher-components/components/LabeledTooltip/LabeledTooltip.vue +0 -1
  286. package/rancher-components/components/StringList/StringList.test.ts +7 -7
  287. package/rancher-components/components/StringList/StringList.vue +21 -15
  288. package/scripts/test-plugins-build.sh +8 -0
  289. package/static/loading-indicator.html +1 -1
  290. package/store/index.js +54 -3
  291. package/store/plugins.js +0 -17
  292. package/store/pnap.js +128 -0
  293. package/store/prefs.js +4 -2
  294. package/store/type-map.js +55 -13
  295. package/types/pod-security-admission.ts +36 -0
  296. package/types/shell/index.d.ts +496 -396
  297. package/utils/__tests__/object.test.ts +17 -1
  298. package/utils/__tests__/pod-security-admission.test.ts +61 -0
  299. package/utils/async.ts +36 -0
  300. package/utils/color.js +45 -0
  301. package/utils/crypto/browserHashUtils.js +18 -0
  302. package/utils/dynamic-importer.js +8 -0
  303. package/utils/install-redirect.js +1 -1
  304. package/utils/object.js +24 -0
  305. package/utils/pod-security-admission.ts +39 -0
  306. package/utils/socket.js +61 -24
  307. package/utils/string.js +2 -0
  308. package/utils/svg-filter.js +301 -0
  309. package/utils/time.js +49 -0
  310. package/utils/validators/cidr.js +4 -0
  311. package/utils/validators/formRules/__tests__/index.test.ts +23 -3
  312. package/utils/validators/formRules/index.ts +14 -0
  313. package/config/product/harvester-manager.js +0 -162
  314. package/edit/harvesterhci.io.management.cluster.vue +0 -153
  315. package/list/harvesterhci.io.management.cluster.vue +0 -241
  316. package/machine-config/harvester.vue +0 -693
  317. package/models/harvesterhci.io.management.cluster.js +0 -228
  318. package/pages/c/_cluster/harvesterManager/index.vue +0 -24
  319. package/rancher-components/Card/Card.test.ts +0 -39
  320. package/rancher-components/Utils/DraggableZone/DraggableZone.vue +0 -181
  321. package/rancher-components/Utils/DraggableZone/index.ts +0 -1
  322. package/rancher-components/components/Utils/DraggableZone/index.ts +0 -1
@@ -47,6 +47,7 @@ import { BEFORE_SAVE_HOOKS } from '@shell/mixins/child-hook';
47
47
  import NameNsDescription from '@shell/components/form/NameNsDescription';
48
48
  import formRulesGenerator from '@shell/utils/validators/formRules';
49
49
  import { TYPES as SECRET_TYPES } from '@shell/models/secret';
50
+ import { defaultContainer } from '@shell/models/workload';
50
51
 
51
52
  const TAB_WEIGHT_MAP = {
52
53
  general: 99,
@@ -63,6 +64,28 @@ const TAB_WEIGHT_MAP = {
63
64
  };
64
65
 
65
66
  const GPU_KEY = 'nvidia.com/gpu';
67
+ const ID_KEY = Symbol('container-id');
68
+
69
+ const serialMaker = function() {
70
+ let prefix = '';
71
+ let seq = 0;
72
+
73
+ return {
74
+ setPrefix(p) {
75
+ prefix = p;
76
+ },
77
+ setSeq(s) {
78
+ seq = s;
79
+ },
80
+ genSym() {
81
+ const result = prefix + seq;
82
+
83
+ seq += 1;
84
+
85
+ return result;
86
+ }
87
+ };
88
+ }();
66
89
 
67
90
  export default {
68
91
  name: 'CruWorkload',
@@ -127,9 +150,10 @@ export default {
127
150
  },
128
151
 
129
152
  data() {
153
+ serialMaker.setPrefix('container-');
154
+ serialMaker.setSeq(0);
130
155
  let type = this.$route.params.resource;
131
156
  const createSidecar = !!this.$route.query.sidecar;
132
- const isInitContainer = !!this.$route.query.init;
133
157
 
134
158
  if (type === 'workload') {
135
159
  type = null;
@@ -190,6 +214,7 @@ export default {
190
214
  podTemplateSpec.initContainers.push({
191
215
  imagePullPolicy: 'Always',
192
216
  name: `container-${ allContainers.length }`,
217
+ _init: true,
193
218
  });
194
219
 
195
220
  containers = podTemplateSpec.initContainers;
@@ -198,6 +223,7 @@ export default {
198
223
  container = {
199
224
  imagePullPolicy: 'Always',
200
225
  name: `container-${ allContainers.length }`,
226
+ _init: false,
201
227
  };
202
228
 
203
229
  containers.push(container);
@@ -209,47 +235,7 @@ export default {
209
235
  this.selectContainer(container);
210
236
 
211
237
  return {
212
- secondaryResourceData: {
213
- namespace: this.value?.metadata?.namespace || null,
214
- data: {
215
- [CONFIG_MAP]: { applyTo: [{ var: 'namespacedConfigMaps' }] },
216
- [PVC]: { applyTo: [{ var: 'pvcs' }] },
217
- [SERVICE_ACCOUNT]: { applyTo: [{ var: 'namespacedServiceNames' }] },
218
- [SECRET]: {
219
- applyTo: [
220
- { var: 'namespacedSecrets' },
221
- {
222
- var: 'imagePullNamespacedSecrets',
223
- parsingFunc: (data) => {
224
- return data.filter(secret => (secret._type === SECRET_TYPES.DOCKER || secret._type === SECRET_TYPES.DOCKER_JSON));
225
- }
226
- }
227
- ]
228
- },
229
- [NODE]: {
230
- applyTo: [
231
- { var: 'allNodeObjects' },
232
- {
233
- var: 'allNodes',
234
- parsingFunc: (data) => {
235
- return data.map(node => node.id);
236
- }
237
- }
238
- ]
239
- },
240
- [SERVICE]: {
241
- applyTo: [
242
- { var: 'allServices' },
243
- {
244
- var: 'headlessServices',
245
- parsingFunc: (data) => {
246
- return data.filter(service => service.spec.clusterIP === 'None');
247
- }
248
- }
249
- ]
250
- },
251
- }
252
- },
238
+ secondaryResourceData: this.secondaryResourceDataConfig(),
253
239
  namespacedConfigMaps: [],
254
240
  allNodes: null,
255
241
  allNodeObjects: [],
@@ -267,7 +253,6 @@ export default {
267
253
  servicesOwned: [],
268
254
  servicesToRemove: [],
269
255
  portsForServices: [],
270
- isInitContainer,
271
256
  container,
272
257
  containerChange: 0,
273
258
  tabChange: 0,
@@ -279,6 +264,7 @@ export default {
279
264
  }],
280
265
  fvReportedValidationPaths: ['spec'],
281
266
  isNamespaceNew: false,
267
+ idKey: ID_KEY
282
268
  };
283
269
  },
284
270
 
@@ -290,10 +276,12 @@ export default {
290
276
 
291
277
  defaultTab() {
292
278
  if (!!this.$route.query.sidecar || this.$route.query.init || this.mode === _CREATE) {
293
- return 'container-0';
279
+ const container = this.allContainers.find(c => c.__active);
280
+
281
+ return container?.name ?? 'container-0';
294
282
  }
295
283
 
296
- return this.allContainers.length ? this.allContainers[0].name : '';
284
+ return this.allContainers.length ? this.allContainers[0][this.idKey] : '';
297
285
  },
298
286
 
299
287
  isEdit() {
@@ -395,11 +383,22 @@ export default {
395
383
  allContainers() {
396
384
  const containers = this.podTemplateSpec?.containers || [];
397
385
  const initContainers = this.podTemplateSpec?.initContainers || [];
386
+ const key = this.idKey;
398
387
 
399
388
  return [
400
- ...containers,
389
+ ...containers.map((each) => {
390
+ each._init = false;
391
+ if (!each[key]) {
392
+ each[key] = serialMaker.genSym();
393
+ }
394
+
395
+ return each;
396
+ }),
401
397
  ...initContainers.map((each) => {
402
398
  each._init = true;
399
+ if (!each[key]) {
400
+ each[key] = serialMaker.genSym();
401
+ }
403
402
 
404
403
  return each;
405
404
  }),
@@ -587,13 +586,6 @@ export default {
587
586
  this.$set(this.value, 'type', neu);
588
587
  delete this.value.apiVersion;
589
588
  },
590
-
591
- container(neu) {
592
- const containers = this.isInitContainer ? this.podTemplateSpec.initContainers : this.podTemplateSpec.containers;
593
- const existing = containers.find(container => container.__active) || {};
594
-
595
- Object.assign(existing, neu);
596
- },
597
589
  },
598
590
 
599
591
  created() {
@@ -604,6 +596,49 @@ export default {
604
596
  },
605
597
 
606
598
  methods: {
599
+ secondaryResourceDataConfig() {
600
+ return {
601
+ namespace: this.value?.metadata?.namespace || null,
602
+ data: {
603
+ [CONFIG_MAP]: { applyTo: [{ var: 'namespacedConfigMaps' }] },
604
+ [PVC]: { applyTo: [{ var: 'pvcs' }] },
605
+ [SERVICE_ACCOUNT]: { applyTo: [{ var: 'namespacedServiceNames' }] },
606
+ [SECRET]: {
607
+ applyTo: [
608
+ { var: 'namespacedSecrets' },
609
+ {
610
+ var: 'imagePullNamespacedSecrets',
611
+ parsingFunc: (data) => {
612
+ return data.filter(secret => (secret._type === SECRET_TYPES.DOCKER || secret._type === SECRET_TYPES.DOCKER_JSON));
613
+ }
614
+ }
615
+ ]
616
+ },
617
+ [NODE]: {
618
+ applyTo: [
619
+ { var: 'allNodeObjects' },
620
+ {
621
+ var: 'allNodes',
622
+ parsingFunc: (data) => {
623
+ return data.map(node => node.id);
624
+ }
625
+ }
626
+ ]
627
+ },
628
+ [SERVICE]: {
629
+ applyTo: [
630
+ { var: 'allServices' },
631
+ {
632
+ var: 'headlessServices',
633
+ parsingFunc: (data) => {
634
+ return data.filter(service => service.spec.clusterIP === 'None');
635
+ }
636
+ }
637
+ ]
638
+ },
639
+ }
640
+ };
641
+ },
607
642
  addContainerBtn() {
608
643
  this.selectContainer({ name: 'Add Container', __add: true });
609
644
  },
@@ -855,7 +890,6 @@ export default {
855
890
  });
856
891
  container.__active = true;
857
892
  this.container = container;
858
- this.isInitContainer = !!container._init;
859
893
  this.containerChange++;
860
894
  },
861
895
 
@@ -871,13 +905,16 @@ export default {
871
905
  nameNumber++;
872
906
  }
873
907
  const container = {
874
- imagePullPolicy: 'Always',
875
- name: `container-${ nameNumber }`,
876
- active: true
908
+ ...defaultContainer,
909
+ name: `container-${ nameNumber }`,
910
+ active: true
877
911
  };
878
912
 
879
913
  this.podTemplateSpec.containers.push(container);
880
914
  this.selectContainer(container);
915
+ this.$nextTick(() => {
916
+ this.$refs.containersTabbed?.select(container.name);
917
+ });
881
918
  },
882
919
 
883
920
  removeContainer(container) {
@@ -889,27 +926,27 @@ export default {
889
926
  this.selectContainer(this.allContainers[0]);
890
927
  },
891
928
 
892
- updateInitContainer(neu) {
893
- if (!this.container) {
929
+ updateInitContainer(neu, container) {
930
+ if (!container) {
894
931
  return;
895
932
  }
896
933
  const containers = this.podTemplateSpec.containers;
934
+ const initContainers = this.podTemplateSpec.initContainers ?? [];
897
935
 
898
936
  if (neu) {
899
- if (!this.podTemplateSpec.initContainers) {
900
- this.podTemplateSpec.initContainers = [];
937
+ this.podTemplateSpec.initContainers = initContainers;
938
+ container._init = true;
939
+ if (!initContainers.includes(container)) {
940
+ initContainers.push(container);
901
941
  }
902
- this.podTemplateSpec.initContainers.push(this.container);
903
-
904
- removeObject(containers, this.container);
942
+ removeObject(containers, container);
905
943
  } else {
906
- delete this.container._init;
907
- const initContainers = this.podTemplateSpec.initContainers;
908
-
909
- removeObject(initContainers, this.container);
910
- containers.push(this.container);
944
+ container._init = false;
945
+ removeObject(initContainers, container);
946
+ if (!containers.includes(container)) {
947
+ containers.push(container);
948
+ }
911
949
  }
912
- this.isInitContainer = neu;
913
950
  },
914
951
  clearPvcFormState(hookName) {
915
952
  // On the `closePvcForm` event, remove the
@@ -1,5 +1,4 @@
1
1
  <script>
2
- import { PVC } from '@shell/config/types';
3
2
  import ButtonDropdown from '@shell/components/ButtonDropdown';
4
3
  import Mount from '@shell/edit/workload/storage/Mount';
5
4
  import { _VIEW } from '@shell/config/query-params';
@@ -34,20 +33,11 @@ export default {
34
33
  },
35
34
  },
36
35
 
37
- async fetch() {
38
- if ( this.$store.getters['cluster/schemaFor'](PVC) ) {
39
- this.pvcs = await this.$store.dispatch('cluster/findAll', { type: PVC });
40
- } else {
41
- this.pvcs = [];
42
- }
43
- },
44
-
45
36
  data() {
46
37
  this.initializeStorage();
47
38
 
48
39
  return {
49
40
  containerVolumes: [],
50
- pvcs: [],
51
41
  storageVolumes: this.getStorageVolumes(),
52
42
  selectedContainerVolumes: this.getSelectedContainerVolumes()
53
43
  };
@@ -0,0 +1,88 @@
1
+ <script>
2
+ import { LabeledInput } from '@components/Form/LabeledInput';
3
+ import LabeledSelect from '@shell/components/form/LabeledSelect';
4
+ import UnitInput from '@shell/components/form/UnitInput';
5
+
6
+ export default {
7
+ components: {
8
+ LabeledInput,
9
+ LabeledSelect,
10
+ UnitInput
11
+ },
12
+ props: {
13
+ podSpec: {
14
+ type: Object,
15
+ default: () => {
16
+ return {};
17
+ }
18
+ },
19
+ mode: {
20
+ type: String,
21
+ default: 'create'
22
+ },
23
+ value: {
24
+ type: Object,
25
+ default: () => {
26
+ return {};
27
+ }
28
+ },
29
+ },
30
+ data() {
31
+ return {
32
+ mediumOpts: [{
33
+ label: 'workload.storage.emptyDir.medium.default',
34
+ value: ''
35
+ }, {
36
+ label: 'workload.storage.emptyDir.medium.memory',
37
+ value: 'Memory'
38
+ }]
39
+ };
40
+ },
41
+ computed: {
42
+ medium: {
43
+ get() {
44
+ return this.value.emptyDir.medium ?? '';
45
+ },
46
+ set(v) {
47
+ this.$set(this.value.emptyDir, 'medium', v);
48
+ }
49
+ },
50
+ },
51
+ };
52
+ </script>
53
+ <template>
54
+ <div>
55
+ <div class="row mb-10">
56
+ <div class="col span-6">
57
+ <LabeledInput
58
+ v-model="value.name"
59
+ :required="true"
60
+ :mode="mode"
61
+ :label="t('workload.storage.volumeName')"
62
+ />
63
+ </div>
64
+ <div class="col span-6">
65
+ <LabeledSelect
66
+ v-model="medium"
67
+ :mode="mode"
68
+ :label="t('workload.storage.emptyDir.medium.label')"
69
+ :options="mediumOpts"
70
+ localized-label
71
+ />
72
+ </div>
73
+ </div>
74
+ <div class="row mb-10">
75
+ <div class="col span-6">
76
+ <UnitInput
77
+ v-model="value.emptyDir.sizeLimit"
78
+ :mode="mode"
79
+ :label="t('workload.storage.emptyDir.sizeLimit.label')"
80
+ :increment="1024"
81
+ :input-exponent="2"
82
+ :output-modifier="true"
83
+ :placeholder="t('workload.storage.emptyDir.sizeLimit.placeholder')"
84
+ />
85
+ </div>
86
+ </div>
87
+ </div>
88
+ </template>
@@ -54,7 +54,7 @@ export default {
54
54
  class="role-link btn btn-lg remove-vol"
55
55
  @click="$emit('remove')"
56
56
  >
57
- <i class="icon icon-2x icon-x" />
57
+ <i class="icon icon-x" />
58
58
  </button>
59
59
  <div>
60
60
  <h3>{{ t('workload.storage.subtypes.csi') }}</h3>
@@ -8,6 +8,8 @@ import ArrayListGrouped from '@shell/components/form/ArrayListGrouped';
8
8
  import { randomStr } from '@shell/utils/string';
9
9
 
10
10
  export default {
11
+ name: 'Storage',
12
+
11
13
  components: {
12
14
  ArrayListGrouped, ButtonDropdown, Mount, CodeMirror
13
15
  },
@@ -155,6 +157,12 @@ export default {
155
157
  csi: { volumeAttributes: {} },
156
158
  name,
157
159
  });
160
+ } else if (type === 'emptyDir') {
161
+ this.value.volumes.push({
162
+ _type: type,
163
+ emptyDir: { medium: '' },
164
+ name,
165
+ });
158
166
  } else {
159
167
  this.value.volumes.push({
160
168
  _type: type,
@@ -87,7 +87,7 @@ export default {
87
87
 
88
88
  watch: {
89
89
  namespace(neu) {
90
- this.__newPvc.metadata.namespace = neu;
90
+ this.value.__newPvc.metadata.namespace = neu;
91
91
  },
92
92
 
93
93
  'value.__newPvc.metadata.name'(neu) {
@@ -20,6 +20,7 @@ import Brand from '@shell/mixins/brand';
20
20
  import FixedBanner from '@shell/components/FixedBanner';
21
21
  import AwsComplianceBanner from '@shell/components/AwsComplianceBanner';
22
22
  import AzureWarning from '@shell/components/auth/AzureWarning';
23
+ import DraggableZone from '@shell/components/DraggableZone';
23
24
  import {
24
25
  COUNT, SCHEMA, MANAGEMENT, UI, CATALOG
25
26
  } from '@shell/config/types';
@@ -27,7 +28,7 @@ import { BASIC, FAVORITE, USED } from '@shell/store/type-map';
27
28
  import { addObjects, replaceWith, clear, addObject } from '@shell/utils/array';
28
29
  import { NAME as EXPLORER } from '@shell/config/product/explorer';
29
30
  import { NAME as NAVLINKS } from '@shell/config/product/navlinks';
30
- import { HARVESTER_NAME as HARVESTER } from '@shell/config/product/harvester-manager';
31
+ import { HARVESTER_NAME as HARVESTER } from '@shell/config/features';
31
32
  import isEqual from 'lodash/isEqual';
32
33
  import { ucFirst } from '@shell/utils/string';
33
34
  import { getVersionInfo, markSeenReleaseNotes } from '@shell/utils/version';
@@ -36,7 +37,6 @@ import PageHeaderActions from '@shell/mixins/page-actions';
36
37
  import BrowserTabVisibility from '@shell/mixins/browser-tab-visibility';
37
38
  import { getProductFromRoute } from '@shell/middleware/authenticated';
38
39
  import { BOTTOM } from '@shell/utils/position';
39
- import { DraggableZone } from '@components/Utils/DraggableZone';
40
40
 
41
41
  const SET_LOGIN_ACTION = 'set-as-login';
42
42
 
@@ -69,6 +69,7 @@ export default {
69
69
  wantNavSync: false,
70
70
  unwatchPin: undefined,
71
71
  wmPin: null,
72
+ draggable: false,
72
73
  };
73
74
  },
74
75
 
@@ -364,48 +365,9 @@ export default {
364
365
  });
365
366
  },
366
367
 
367
- getGroups() {
368
- if ( this.gettingGroups ) {
369
- return;
370
- }
371
- this.gettingGroups = true;
372
-
373
- if ( !this.clusterReady ) {
374
- clear(this.groups);
375
- this.gettingGroups = false;
376
-
377
- return;
378
- }
379
-
368
+ getProductsGroups(out, loadProducts, namespaceMode, namespaces, productMap) {
380
369
  const clusterId = this.$store.getters['clusterId'];
381
- const currentProduct = this.$store.getters['productId'];
382
370
  const currentType = this.$route.params.resource || '';
383
- let namespaces = null;
384
-
385
- if ( !this.$store.getters['isAllNamespaces'] ) {
386
- const namespacesObject = this.$store.getters['namespaces']();
387
-
388
- namespaces = Object.keys(namespacesObject);
389
- }
390
-
391
- // Always show cluster-level types, regardless of the namespace filter
392
- const namespaceMode = 'both';
393
- const out = [];
394
- const loadProducts = this.isExplorer ? [EXPLORER] : [];
395
- const productMap = this.activeProducts.reduce((acc, p) => {
396
- return { ...acc, [p.name]: p };
397
- }, {});
398
-
399
- if ( this.isExplorer ) {
400
- for ( const product of this.activeProducts ) {
401
- if ( product.inStore === 'cluster' ) {
402
- addObject(loadProducts, product.name);
403
- }
404
- }
405
- }
406
-
407
- // This should already have come into the list from above, but in case it hasn't...
408
- addObject(loadProducts, currentProduct);
409
371
 
410
372
  for ( const productId of loadProducts ) {
411
373
  const modes = [BASIC];
@@ -442,7 +404,9 @@ export default {
442
404
  }
443
405
  }
444
406
  }
407
+ },
445
408
 
409
+ getExplorerGroups(out) {
446
410
  if ( this.isExplorer ) {
447
411
  const allNavLinks = this.allNavLinks;
448
412
  const toAdd = [];
@@ -508,6 +472,55 @@ export default {
508
472
 
509
473
  addObjects(out, toAdd);
510
474
  }
475
+ },
476
+
477
+ /**
478
+ * Fetch navigation by creating groups from product schemas
479
+ */
480
+ getGroups() {
481
+ if ( this.gettingGroups ) {
482
+ return;
483
+ }
484
+ this.gettingGroups = true;
485
+
486
+ if ( !this.clusterReady ) {
487
+ clear(this.groups);
488
+ this.gettingGroups = false;
489
+
490
+ return;
491
+ }
492
+
493
+ const currentProduct = this.$store.getters['productId'];
494
+ let namespaces = null;
495
+
496
+ if ( !this.$store.getters['isAllNamespaces'] ) {
497
+ const namespacesObject = this.$store.getters['namespaces']();
498
+
499
+ namespaces = Object.keys(namespacesObject);
500
+ }
501
+
502
+ // Always show cluster-level types, regardless of the namespace filter
503
+ const namespaceMode = 'both';
504
+ const out = [];
505
+ const loadProducts = this.isExplorer ? [EXPLORER] : [];
506
+
507
+ const productMap = this.activeProducts.reduce((acc, p) => {
508
+ return { ...acc, [p.name]: p };
509
+ }, {});
510
+
511
+ if ( this.isExplorer ) {
512
+ for ( const product of this.activeProducts ) {
513
+ if ( product.inStore === 'cluster' ) {
514
+ addObject(loadProducts, product.name);
515
+ }
516
+ }
517
+ }
518
+
519
+ // This should already have come into the list from above, but in case it hasn't...
520
+ addObject(loadProducts, currentProduct);
521
+
522
+ this.getProductsGroups(out, loadProducts, namespaceMode, namespaces, productMap);
523
+ this.getExplorerGroups(out);
511
524
 
512
525
  replaceWith(this.groups, ...sortBy(out, ['weight:desc', 'label']));
513
526
  this.gettingGroups = false;
@@ -739,11 +752,11 @@ export default {
739
752
  'drag-end': !$refs.draggableZone.drag.active,
740
753
  'drag-start': $refs.draggableZone.drag.active,
741
754
  }"
742
- draggable="true"
755
+ :draggable="draggable"
743
756
  @dragstart="$refs.draggableZone.onDragStart($event)"
744
757
  @dragend="$refs.draggableZone.onDragEnd($event)"
745
758
  >
746
- <WindowManager />
759
+ <WindowManager @draggable="draggable=$event" />
747
760
  </div>
748
761
  </div>
749
762
  <FixedBanner :footer="true" />
@@ -23,8 +23,9 @@ describe('component: workload', () => {
23
23
  mixins: [ResourceFetch],
24
24
  mocks: {
25
25
  $store: {
26
- getters: {
27
- currentStore: () => jest.fn(),
26
+ dispatch: () => jest.fn(),
27
+ getters: {
28
+ currentStore: () => 'cluster',
28
29
  namespaces: () => jest.fn(),
29
30
  'management/byId': () => jest.fn(),
30
31
  'resource-fetch/refreshFlag': () => jest.fn(),
@@ -33,6 +34,8 @@ describe('component: workload', () => {
33
34
  'type-map/optionsFor': () => jest.fn(),
34
35
  'type-map/headersFor': () => jest.fn(),
35
36
  'prefs/get': () => resource,
37
+ 'cluster/schemaFor': () => {},
38
+ 'cluster/all': () => [{}],
36
39
  }
37
40
  },
38
41
  $fetchState: {
@@ -38,6 +38,7 @@ export default {
38
38
  :rows="rows"
39
39
  :loading="loading"
40
40
  :use-query-params-for-simple-filtering="useQueryParamsForSimpleFiltering"
41
+ :force-update-live-and-delayed="forceUpdateLiveAndDelayed"
41
42
  >
42
43
  <template #cell:upgrade="{row}">
43
44
  <span
@@ -66,5 +66,6 @@ export default {
66
66
  :headers="headers"
67
67
  :loading="loading"
68
68
  :use-query-params-for-simple-filtering="useQueryParamsForSimpleFiltering"
69
+ :force-update-live-and-delayed="forceUpdateLiveAndDelayed"
69
70
  />
70
71
  </template>
@@ -30,8 +30,8 @@ export default {
30
30
  },
31
31
 
32
32
  async fetch() {
33
- await this.$fetchType(FLEET.BUNDLE);
34
- this.allFleet = await this.$store.dispatch('management/findAll', { type: FLEET.CLUSTER });
33
+ await this.$fetchType(this.resource);
34
+ this.allFleet = await this.$fetchType(FLEET.CLUSTER);
35
35
  },
36
36
 
37
37
  data() {
@@ -90,10 +90,8 @@ export default {
90
90
 
91
91
  // override with relevant info for the loading indicator since this doesn't use it's own masthead
92
92
  $loadingResources() {
93
- return {
94
- loadResources: [FLEET.BUNDLE],
95
- loadIndeterminate: true, // results are filtered so we wouldn't get the correct count on indicator...
96
- };
93
+ // results are filtered so we wouldn't get the correct count on indicator...
94
+ return { loadIndeterminate: true };
97
95
  },
98
96
  };
99
97
  </script>
@@ -111,6 +109,7 @@ export default {
111
109
  :rows="bundles"
112
110
  :loading="loading"
113
111
  :use-query-params-for-simple-filtering="useQueryParamsForSimpleFiltering"
112
+ :force-update-live-and-delayed="forceUpdateLiveAndDelayed"
114
113
  >
115
114
  <template #cell:deploymentsReady="{row}">
116
115
  <span