@rancher/shell 3.0.6 → 3.0.8-rc.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/images/pl/dark/rancher-logo.svg +131 -44
- package/assets/images/pl/rancher-logo.svg +120 -44
- package/assets/images/vendor/githubapp.svg +13 -0
- package/assets/styles/base/_basic.scss +2 -2
- package/assets/styles/base/_color-classic.scss +51 -0
- package/assets/styles/base/_color.scss +3 -3
- package/assets/styles/base/_mixins.scss +1 -1
- package/assets/styles/base/_typography.scss +1 -1
- package/assets/styles/base/_variables-classic.scss +47 -0
- package/assets/styles/global/_button.scss +49 -17
- package/assets/styles/global/_form.scss +1 -1
- package/assets/styles/themes/_dark.scss +4 -0
- package/assets/styles/themes/_light.scss +3 -69
- package/assets/styles/themes/_modern.scss +194 -50
- package/assets/styles/vendor/vue-select.scss +1 -2
- package/assets/translations/en-us.yaml +124 -32
- package/assets/translations/zh-hans.yaml +0 -4
- package/components/ClusterIconMenu.vue +1 -1
- package/components/ClusterProviderIcon.vue +1 -1
- package/components/CodeMirror.vue +1 -1
- package/components/IconOrSvg.vue +40 -29
- package/components/Inactivity.vue +222 -106
- package/components/InstallHelmCharts.vue +2 -2
- package/components/ResourceDetail/index.vue +2 -1
- package/components/SortableTable/index.vue +17 -2
- package/components/SortableTable/sorting.js +3 -1
- package/components/Tabbed/index.vue +5 -5
- package/components/fleet/FleetConfigMapSelector.vue +117 -0
- package/components/fleet/FleetSecretSelector.vue +127 -0
- package/components/fleet/__tests__/FleetConfigMapSelector.test.ts +125 -0
- package/components/fleet/__tests__/FleetSecretSelector.test.ts +82 -0
- package/components/form/FileImageSelector.vue +13 -4
- package/components/form/FileSelector.vue +11 -2
- package/components/form/ResourceLabeledSelect.vue +1 -0
- package/components/form/ResourceTabs/index.vue +37 -18
- package/components/form/SecretSelector.vue +6 -2
- package/components/form/__tests__/ResourceLabeledSelect.test.ts +90 -0
- package/components/nav/Group.vue +29 -9
- package/components/nav/Header.vue +7 -8
- package/components/nav/NamespaceFilter.vue +1 -1
- package/components/nav/TopLevelMenu.helper.ts +47 -20
- package/components/nav/TopLevelMenu.vue +44 -14
- package/components/nav/Type.vue +0 -5
- package/components/nav/__tests__/TopLevelMenu.test.ts +2 -0
- package/config/pagination-table-headers.js +10 -2
- package/config/product/auth.js +1 -0
- package/config/product/explorer.js +4 -3
- package/config/query-params.js +1 -0
- package/config/settings.ts +8 -1
- package/config/table-headers.js +9 -0
- package/config/types.js +2 -0
- package/core/plugin.ts +18 -6
- package/core/types.ts +8 -0
- package/detail/provisioning.cattle.io.cluster.vue +1 -0
- package/dialog/AddonConfigConfirmationDialog.vue +45 -1
- package/dialog/InstallExtensionDialog.vue +71 -45
- package/dialog/UninstallExtensionDialog.vue +2 -1
- package/dialog/__tests__/InstallExtensionDialog.test.ts +111 -0
- package/edit/__tests__/fleet.cattle.io.helmop.test.ts +52 -11
- package/edit/auth/AuthProviderWarningBanners.vue +14 -1
- package/edit/auth/github-app-steps.vue +97 -0
- package/edit/auth/github-steps.vue +75 -0
- package/edit/auth/github.vue +94 -65
- package/edit/auth/oidc.vue +86 -16
- package/edit/fleet.cattle.io.helmop.vue +51 -2
- package/edit/networking.k8s.io.networkpolicy/PolicyRuleTarget.vue +15 -5
- package/edit/provisioning.cattle.io.cluster/__tests__/rke2.test.ts +11 -9
- package/edit/provisioning.cattle.io.cluster/rke2.vue +56 -9
- package/edit/provisioning.cattle.io.cluster/tabs/AddOnConfig.vue +28 -2
- package/list/projectsecret.vue +1 -1
- package/machine-config/azure.vue +1 -1
- package/mixins/__tests__/chart.test.ts +1 -1
- package/mixins/chart.js +2 -2
- package/models/__tests__/chart.test.ts +17 -9
- package/models/__tests__/compliance.cattle.io.clusterscanprofile.spec.js +30 -0
- package/models/catalog.cattle.io.app.js +1 -1
- package/models/chart.js +3 -1
- package/models/compliance.cattle.io.clusterscanprofile.js +1 -1
- package/models/event.js +7 -0
- package/models/management.cattle.io.authconfig.js +1 -0
- package/models/provisioning.cattle.io.cluster.js +9 -0
- package/package.json +2 -2
- package/pages/auth/login.vue +5 -2
- package/pages/auth/verify.vue +1 -1
- package/pages/c/_cluster/apps/charts/AppChartCardSubHeader.vue +3 -2
- package/pages/c/_cluster/apps/charts/chart.vue +2 -2
- package/pages/c/_cluster/explorer/EventsTable.vue +92 -9
- package/pages/c/_cluster/explorer/tools/index.vue +3 -3
- package/pages/c/_cluster/settings/performance.vue +13 -26
- package/pages/c/_cluster/uiplugins/PluginInfoPanel.vue +159 -62
- package/pages/c/_cluster/uiplugins/__tests__/PluginInfoPanel.test.ts +102 -0
- package/pages/c/_cluster/uiplugins/__tests__/{index.spec.ts → index.test.ts} +121 -55
- package/pages/c/_cluster/uiplugins/index.vue +110 -94
- package/pages/home.vue +313 -12
- package/plugins/__tests__/subscribe.events.test.ts +194 -0
- package/plugins/axios.js +2 -1
- package/plugins/dashboard-store/actions.js +4 -1
- package/plugins/dashboard-store/getters.js +1 -1
- package/plugins/dashboard-store/resource-class.js +20 -5
- package/plugins/steve/__tests__/subscribe.spec.ts +27 -24
- package/plugins/steve/index.js +18 -10
- package/plugins/steve/mutations.js +2 -2
- package/plugins/steve/resourceWatcher.js +2 -2
- package/plugins/steve/steve-pagination-utils.ts +12 -9
- package/plugins/steve/subscribe.js +113 -85
- package/plugins/subscribe-events.ts +211 -0
- package/rancher-components/BadgeState/BadgeState.vue +8 -6
- package/rancher-components/Banner/Banner.vue +2 -1
- package/rancher-components/Form/Checkbox/Checkbox.vue +3 -3
- package/rancher-components/Form/Radio/RadioButton.vue +3 -3
- package/scripts/extension/publish +1 -1
- package/store/auth.js +8 -3
- package/store/aws.js +8 -6
- package/store/features.js +1 -0
- package/store/index.js +21 -25
- package/store/prefs.js +6 -0
- package/types/extension-manager.ts +8 -1
- package/types/kube/kube-api.ts +2 -1
- package/types/rancher/index.d.ts +1 -0
- package/types/resources/settings.d.ts +52 -23
- package/types/shell/index.d.ts +412 -336
- package/types/store/subscribe-events.types.ts +70 -0
- package/types/store/subscribe.types.ts +6 -22
- package/utils/__tests__/cluster.test.ts +379 -1
- package/utils/cluster.js +157 -3
- package/utils/dynamic-content/__tests__/config.test.ts +187 -0
- package/utils/dynamic-content/__tests__/index.test.ts +390 -0
- package/utils/dynamic-content/__tests__/info.test.ts +263 -0
- package/utils/dynamic-content/__tests__/new-release.test.ts +216 -0
- package/utils/dynamic-content/__tests__/support-notice.test.ts +262 -0
- package/utils/dynamic-content/__tests__/util.test.ts +235 -0
- package/utils/dynamic-content/config.ts +55 -0
- package/utils/dynamic-content/index.ts +273 -0
- package/utils/dynamic-content/info.ts +219 -0
- package/utils/dynamic-content/new-release.ts +126 -0
- package/utils/dynamic-content/support-notice.ts +169 -0
- package/utils/dynamic-content/types.d.ts +101 -0
- package/utils/dynamic-content/util.ts +122 -0
- package/utils/inactivity.ts +104 -0
- package/utils/pagination-utils.ts +105 -31
- package/utils/pagination-wrapper.ts +6 -8
- package/utils/release-notes.ts +1 -1
- package/utils/sort.js +5 -0
- package/utils/unit-tests/pagination-utils.spec.ts +283 -0
- package/utils/validators/formRules/__tests__/index.test.ts +7 -0
- package/utils/validators/formRules/index.ts +2 -2
package/components/nav/Group.vue
CHANGED
|
@@ -381,21 +381,21 @@ export default {
|
|
|
381
381
|
}
|
|
382
382
|
|
|
383
383
|
&.active {
|
|
384
|
-
color: var(--primary-hover-text);
|
|
385
|
-
background-color: var(--primary-hover-bg);
|
|
384
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
385
|
+
background-color: var(--active-nav, var(--primary-hover-bg));
|
|
386
386
|
|
|
387
387
|
h6 {
|
|
388
388
|
padding: 8px 0 8px 16px;
|
|
389
389
|
font-weight: bold;
|
|
390
|
-
color: var(--primary-hover-text);
|
|
390
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
391
391
|
}
|
|
392
392
|
|
|
393
393
|
&:hover {
|
|
394
|
-
background-color: var(--primary-hover-bg);
|
|
394
|
+
background-color: var(--nav-active-hover, var(--primary-hover-bg));
|
|
395
395
|
}
|
|
396
396
|
|
|
397
397
|
~ I {
|
|
398
|
-
color: var(--primary-hover-text);
|
|
398
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
399
399
|
}
|
|
400
400
|
}
|
|
401
401
|
&:hover:not(.active) {
|
|
@@ -433,8 +433,24 @@ export default {
|
|
|
433
433
|
margin-left: 0;
|
|
434
434
|
}
|
|
435
435
|
|
|
436
|
+
.child:hover {
|
|
437
|
+
background: var(--nav-hover, var(--nav-active));
|
|
438
|
+
}
|
|
439
|
+
|
|
436
440
|
&.group-highlight {
|
|
437
|
-
background: var(--nav-active);
|
|
441
|
+
background: var(--category-active, var(--nav-active));
|
|
442
|
+
|
|
443
|
+
.active.header {
|
|
444
|
+
&:hover {
|
|
445
|
+
background-color: var(--nav-active-hover)
|
|
446
|
+
}
|
|
447
|
+
}
|
|
448
|
+
|
|
449
|
+
.child, .header {
|
|
450
|
+
&:hover {
|
|
451
|
+
background: var(--category-active-hover, var(--primary));
|
|
452
|
+
}
|
|
453
|
+
}
|
|
438
454
|
}
|
|
439
455
|
}
|
|
440
456
|
|
|
@@ -480,13 +496,17 @@ export default {
|
|
|
480
496
|
padding: 0;
|
|
481
497
|
|
|
482
498
|
A, A I {
|
|
483
|
-
color: var(--primary-hover-text);
|
|
499
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
484
500
|
}
|
|
485
501
|
|
|
486
502
|
A {
|
|
487
|
-
color: var(--primary-hover-text);
|
|
488
|
-
background-color: var(--primary-hover-bg);
|
|
503
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
504
|
+
background-color: var(--active-nav, var(--primary-hover-bg));
|
|
489
505
|
font-weight: bold;
|
|
506
|
+
|
|
507
|
+
&:hover {
|
|
508
|
+
background: var(--nav-active-hover);
|
|
509
|
+
}
|
|
490
510
|
}
|
|
491
511
|
}
|
|
492
512
|
|
|
@@ -842,17 +842,16 @@ export default {
|
|
|
842
842
|
.side-menu-logo {
|
|
843
843
|
align-items: center;
|
|
844
844
|
display: flex;
|
|
845
|
-
margin-right: 8px;
|
|
846
845
|
height: 55px;
|
|
847
|
-
margin-
|
|
846
|
+
margin-right: 8px;
|
|
848
847
|
max-width: 200px;
|
|
849
848
|
padding: 12px 0;
|
|
850
849
|
}
|
|
851
850
|
|
|
852
851
|
.side-menu-logo-img {
|
|
853
852
|
object-fit: contain;
|
|
854
|
-
height: 21px;
|
|
855
853
|
max-width: 200px;
|
|
854
|
+
height: 36px;
|
|
856
855
|
}
|
|
857
856
|
|
|
858
857
|
> * {
|
|
@@ -933,8 +932,8 @@ export default {
|
|
|
933
932
|
:deep() div .btn.role-tertiary {
|
|
934
933
|
border: 1px solid var(--header-btn-bg);
|
|
935
934
|
border: none;
|
|
936
|
-
background: var(--header-btn-bg);
|
|
937
|
-
color: var(--header-btn-text);
|
|
935
|
+
background: var(--tertiary-header, var(--header-btn-bg));
|
|
936
|
+
color: var(--on-tertiary-header, var(--header-btn-text));
|
|
938
937
|
padding: 0 10px;
|
|
939
938
|
line-height: 32px;
|
|
940
939
|
min-height: 32px;
|
|
@@ -945,8 +944,8 @@ export default {
|
|
|
945
944
|
}
|
|
946
945
|
|
|
947
946
|
&:hover {
|
|
948
|
-
background: var(--primary);
|
|
949
|
-
color: #fff;
|
|
947
|
+
background: var(--tertiary-header-hover, var(--primary));
|
|
948
|
+
color: var(--on-tertiary-header-hover, #fff);
|
|
950
949
|
}
|
|
951
950
|
|
|
952
951
|
&[disabled=disabled] {
|
|
@@ -1079,7 +1078,7 @@ export default {
|
|
|
1079
1078
|
.user-name {
|
|
1080
1079
|
display: flex;
|
|
1081
1080
|
align-items: center;
|
|
1082
|
-
color: var(--secondary);
|
|
1081
|
+
color: var(--body-text, var(--secondary));
|
|
1083
1082
|
}
|
|
1084
1083
|
|
|
1085
1084
|
.user-menu {
|
|
@@ -139,12 +139,6 @@ export abstract class BaseTopLevelMenuHelper {
|
|
|
139
139
|
this.$store = $store;
|
|
140
140
|
|
|
141
141
|
this.hasProvCluster = this.$store.getters[`management/schemaFor`](CAPI.RANCHER_CLUSTER);
|
|
142
|
-
|
|
143
|
-
// Reduce flicker when component is recreated on a different layout
|
|
144
|
-
const { clustersPinned = [], clustersOthers = [] } = this.$store.getters['sideNavCache'] || {};
|
|
145
|
-
|
|
146
|
-
this.clustersPinned.push(...clustersPinned);
|
|
147
|
-
this.clustersOthers.push(...clustersOthers);
|
|
148
142
|
}
|
|
149
143
|
|
|
150
144
|
protected convertToCluster(mgmtCluster: MgmtCluster, provCluster: ProvCluster): TopLevelMenuCluster {
|
|
@@ -163,10 +157,6 @@ export abstract class BaseTopLevelMenuHelper {
|
|
|
163
157
|
clusterRoute: { name: 'c-cluster-explorer', params: { cluster: mgmtCluster.id } }
|
|
164
158
|
};
|
|
165
159
|
}
|
|
166
|
-
|
|
167
|
-
protected cacheClusters() {
|
|
168
|
-
this.$store.dispatch('setSideNavCache', { clustersPinned: this.clustersPinned, clustersOthers: this.clustersOthers });
|
|
169
|
-
}
|
|
170
160
|
}
|
|
171
161
|
|
|
172
162
|
/**
|
|
@@ -202,9 +192,9 @@ export class TopLevelMenuHelperPagination extends BaseTopLevelMenuHelper impleme
|
|
|
202
192
|
this.clustersOthersWrapper = new PaginationWrapper({
|
|
203
193
|
$store,
|
|
204
194
|
id: 'tlm-unpinned-clusters',
|
|
205
|
-
onChange: () => {
|
|
195
|
+
onChange: async() => {
|
|
206
196
|
if (this.args) {
|
|
207
|
-
this.update(this.args);
|
|
197
|
+
await this.update(this.args);
|
|
208
198
|
}
|
|
209
199
|
},
|
|
210
200
|
enabledFor: {
|
|
@@ -220,9 +210,9 @@ export class TopLevelMenuHelperPagination extends BaseTopLevelMenuHelper impleme
|
|
|
220
210
|
this.provClusterWrapper = new PaginationWrapper({
|
|
221
211
|
$store,
|
|
222
212
|
id: 'tlm-prov-clusters',
|
|
223
|
-
onChange: () => {
|
|
213
|
+
onChange: async() => {
|
|
224
214
|
if (this.args) {
|
|
225
|
-
this.update(this.args);
|
|
215
|
+
await this.update(this.args);
|
|
226
216
|
}
|
|
227
217
|
},
|
|
228
218
|
enabledFor: {
|
|
@@ -276,8 +266,6 @@ export class TopLevelMenuHelperPagination extends BaseTopLevelMenuHelper impleme
|
|
|
276
266
|
|
|
277
267
|
this.clustersPinned.push(..._clustersPinned);
|
|
278
268
|
this.clustersOthers.push(..._clustersNotPinned);
|
|
279
|
-
|
|
280
|
-
this.cacheClusters();
|
|
281
269
|
}
|
|
282
270
|
|
|
283
271
|
async destroy() {
|
|
@@ -390,7 +378,6 @@ export class TopLevelMenuHelperPagination extends BaseTopLevelMenuHelper impleme
|
|
|
390
378
|
private async updateProvCluster(notPinned: MgmtCluster[], pinned: MgmtCluster[]): Promise<ProvCluster[]> {
|
|
391
379
|
return this.provClusterWrapper.request({
|
|
392
380
|
pagination: {
|
|
393
|
-
|
|
394
381
|
filters: [
|
|
395
382
|
PaginationParamFilter.createMultipleFields(
|
|
396
383
|
[...notPinned, ...pinned]
|
|
@@ -399,7 +386,6 @@ export class TopLevelMenuHelperPagination extends BaseTopLevelMenuHelper impleme
|
|
|
399
386
|
}))
|
|
400
387
|
)
|
|
401
388
|
],
|
|
402
|
-
|
|
403
389
|
page: 1,
|
|
404
390
|
sort: [],
|
|
405
391
|
projectsOrNamespaces: []
|
|
@@ -432,8 +418,6 @@ export class TopLevelMenuHelperLegacy extends BaseTopLevelMenuHelper implements
|
|
|
432
418
|
|
|
433
419
|
this.clustersPinned.push(..._clustersPinned);
|
|
434
420
|
this.clustersOthers.push(..._clustersNotPinned);
|
|
435
|
-
|
|
436
|
-
this.cacheClusters();
|
|
437
421
|
}
|
|
438
422
|
|
|
439
423
|
async destroy() {
|
|
@@ -581,3 +565,46 @@ export class TopLevelMenuHelperLegacy extends BaseTopLevelMenuHelper implements
|
|
|
581
565
|
return sorted;
|
|
582
566
|
}
|
|
583
567
|
}
|
|
568
|
+
|
|
569
|
+
/**
|
|
570
|
+
* Retain state of the side nav, no matter when the TopLevelMenu component is created/deleted (on layout change)
|
|
571
|
+
*
|
|
572
|
+
* This means there's no flickering when the user changes pages and the side nav component re-renders
|
|
573
|
+
*
|
|
574
|
+
* Also it means we're not unwatching then watching the clusters
|
|
575
|
+
*/
|
|
576
|
+
class TopLevelMenuHelperService {
|
|
577
|
+
private _helper?: TopLevelMenuHelper;
|
|
578
|
+
public init($store: VuexStore) {
|
|
579
|
+
if (this._helper) {
|
|
580
|
+
return;
|
|
581
|
+
}
|
|
582
|
+
|
|
583
|
+
const canPagination = $store.getters[`management/paginationEnabled`]({
|
|
584
|
+
id: MANAGEMENT.CLUSTER,
|
|
585
|
+
context: 'side-bar',
|
|
586
|
+
}) && $store.getters[`management/paginationEnabled`]({
|
|
587
|
+
id: CAPI.RANCHER_CLUSTER,
|
|
588
|
+
context: 'side-bar',
|
|
589
|
+
});
|
|
590
|
+
|
|
591
|
+
this._helper = canPagination ? new TopLevelMenuHelperPagination({ $store }) : new TopLevelMenuHelperLegacy({ $store });
|
|
592
|
+
}
|
|
593
|
+
|
|
594
|
+
public async reset() {
|
|
595
|
+
await this._helper?.destroy();
|
|
596
|
+
delete this._helper;
|
|
597
|
+
}
|
|
598
|
+
|
|
599
|
+
get helper(): TopLevelMenuHelper {
|
|
600
|
+
if (!this._helper) {
|
|
601
|
+
throw new Error('Unable to use the side nav cluster helper (not initialised)');
|
|
602
|
+
}
|
|
603
|
+
|
|
604
|
+
return this._helper;
|
|
605
|
+
}
|
|
606
|
+
}
|
|
607
|
+
|
|
608
|
+
const instance = new TopLevelMenuHelperService();
|
|
609
|
+
|
|
610
|
+
export default instance;
|
|
@@ -14,7 +14,7 @@ import { SETTING } from '@shell/config/settings';
|
|
|
14
14
|
import { getProductFromRoute } from '@shell/utils/router';
|
|
15
15
|
import { isRancherPrime } from '@shell/config/version';
|
|
16
16
|
import Pinned from '@shell/components/nav/Pinned';
|
|
17
|
-
import
|
|
17
|
+
import sideNavService from '@shell/components/nav/TopLevelMenu.helper';
|
|
18
18
|
import { debounce } from 'lodash';
|
|
19
19
|
import { sameContents } from '@shell/utils/array';
|
|
20
20
|
|
|
@@ -27,6 +27,8 @@ export default {
|
|
|
27
27
|
},
|
|
28
28
|
|
|
29
29
|
data() {
|
|
30
|
+
sideNavService.init(this.$store);
|
|
31
|
+
|
|
30
32
|
const { displayVersion, fullVersion } = getVersionInfo(this.$store);
|
|
31
33
|
const hasProvCluster = this.$store.getters[`management/schemaFor`](CAPI.RANCHER_CLUSTER);
|
|
32
34
|
|
|
@@ -37,7 +39,7 @@ export default {
|
|
|
37
39
|
id: CAPI.RANCHER_CLUSTER,
|
|
38
40
|
context: 'side-bar',
|
|
39
41
|
});
|
|
40
|
-
const helper =
|
|
42
|
+
const helper = sideNavService.helper;
|
|
41
43
|
const provClusters = !canPagination && hasProvCluster ? this.$store.getters[`management/all`](CAPI.RANCHER_CLUSTER) : [];
|
|
42
44
|
const mgmtClusters = !canPagination ? this.$store.getters[`management/all`](MANAGEMENT.CLUSTER) : [];
|
|
43
45
|
|
|
@@ -327,7 +329,6 @@ export default {
|
|
|
327
329
|
|
|
328
330
|
beforeUnmount() {
|
|
329
331
|
document.removeEventListener('keyup', this.handler);
|
|
330
|
-
this.helper?.destroy();
|
|
331
332
|
},
|
|
332
333
|
|
|
333
334
|
methods: {
|
|
@@ -1073,6 +1074,14 @@ export default {
|
|
|
1073
1074
|
width: 300px;
|
|
1074
1075
|
overflow: auto;
|
|
1075
1076
|
|
|
1077
|
+
& .category {
|
|
1078
|
+
& a.router-link-active {
|
|
1079
|
+
&:hover {
|
|
1080
|
+
color: var(--on-active, var(--default));
|
|
1081
|
+
}
|
|
1082
|
+
}
|
|
1083
|
+
}
|
|
1084
|
+
|
|
1076
1085
|
.option {
|
|
1077
1086
|
align-items: center;
|
|
1078
1087
|
cursor: pointer;
|
|
@@ -1119,6 +1128,15 @@ export default {
|
|
|
1119
1128
|
}
|
|
1120
1129
|
}
|
|
1121
1130
|
|
|
1131
|
+
&:not(.active-menu-link) {
|
|
1132
|
+
&:hover {
|
|
1133
|
+
.pin {
|
|
1134
|
+
display: block;
|
|
1135
|
+
color: var(--body-text-hover);
|
|
1136
|
+
}
|
|
1137
|
+
}
|
|
1138
|
+
}
|
|
1139
|
+
|
|
1122
1140
|
&:hover {
|
|
1123
1141
|
text-decoration: none;
|
|
1124
1142
|
|
|
@@ -1178,19 +1196,31 @@ export default {
|
|
|
1178
1196
|
outline-offset: -4px;
|
|
1179
1197
|
}
|
|
1180
1198
|
|
|
1181
|
-
background: var(--primary-hover-bg);
|
|
1182
|
-
color: var(--primary-hover-text);
|
|
1199
|
+
background: var(--active-nav, var(--primary-hover-bg));
|
|
1200
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
1183
1201
|
|
|
1184
1202
|
svg {
|
|
1185
|
-
fill: var(--primary-hover-text);
|
|
1203
|
+
fill: var(--on-active, var(--primary-hover-text));
|
|
1186
1204
|
}
|
|
1187
1205
|
|
|
1188
1206
|
i {
|
|
1189
|
-
color: var(--primary-hover-text);
|
|
1207
|
+
color: var(--on-active, var(--primary-hover-text));
|
|
1190
1208
|
}
|
|
1191
1209
|
|
|
1192
1210
|
div .description {
|
|
1193
|
-
color: var(--default);
|
|
1211
|
+
color: var(--on-active, var(--default));
|
|
1212
|
+
}
|
|
1213
|
+
|
|
1214
|
+
&:hover {
|
|
1215
|
+
background: var(--active-hover, var(--primary-hover-bg));
|
|
1216
|
+
|
|
1217
|
+
div {
|
|
1218
|
+
color: var(--on-active, var(--default));
|
|
1219
|
+
}
|
|
1220
|
+
|
|
1221
|
+
svg {
|
|
1222
|
+
fill: var(--on-active, var(--primary-hover-text));
|
|
1223
|
+
}
|
|
1194
1224
|
}
|
|
1195
1225
|
}
|
|
1196
1226
|
|
|
@@ -1201,8 +1231,8 @@ export default {
|
|
|
1201
1231
|
}
|
|
1202
1232
|
|
|
1203
1233
|
&:hover {
|
|
1204
|
-
color: var(--primary-hover-text);
|
|
1205
|
-
background: var(--primary-hover-bg);
|
|
1234
|
+
color: var(--tertiary-hover-app-bar, var(--primary-hover-text));
|
|
1235
|
+
background: var(--nav-hover-top-level, var(--primary-hover-bg));
|
|
1206
1236
|
> div {
|
|
1207
1237
|
color: var(--primary-hover-text);
|
|
1208
1238
|
|
|
@@ -1211,10 +1241,10 @@ export default {
|
|
|
1211
1241
|
}
|
|
1212
1242
|
}
|
|
1213
1243
|
svg {
|
|
1214
|
-
fill: var(--primary-hover-text);
|
|
1244
|
+
fill: var(--tertiary-hover-app-bar, var(--primary-hover-text));
|
|
1215
1245
|
}
|
|
1216
1246
|
div {
|
|
1217
|
-
color: var(--primary-hover-text);
|
|
1247
|
+
color: var(--tertiary-hover-app-bar, var(--primary-hover-text));
|
|
1218
1248
|
}
|
|
1219
1249
|
&.disabled {
|
|
1220
1250
|
background: transparent;
|
|
@@ -1549,8 +1579,8 @@ export default {
|
|
|
1549
1579
|
overflow: hidden;
|
|
1550
1580
|
& IMG {
|
|
1551
1581
|
object-fit: contain;
|
|
1552
|
-
height: 21px;
|
|
1553
1582
|
max-width: 200px;
|
|
1583
|
+
height: 36px;
|
|
1554
1584
|
}
|
|
1555
1585
|
}
|
|
1556
1586
|
|
|
@@ -1592,7 +1622,7 @@ export default {
|
|
|
1592
1622
|
padding: 8px 20px;
|
|
1593
1623
|
|
|
1594
1624
|
&:hover {
|
|
1595
|
-
background-color: var(--primary-hover-bg);
|
|
1625
|
+
background-color: var(--active-hover, var(--primary-hover-bg));
|
|
1596
1626
|
color: var(--primary-hover-text);
|
|
1597
1627
|
text-decoration: none;
|
|
1598
1628
|
}
|
package/components/nav/Type.vue
CHANGED
|
@@ -3,6 +3,7 @@ import { mount, Wrapper } from '@vue/test-utils';
|
|
|
3
3
|
import { CAPI, COUNT, MANAGEMENT } from '@shell/config/types';
|
|
4
4
|
import { PINNED_CLUSTERS } from '@shell/store/prefs';
|
|
5
5
|
import { nextTick } from 'vue';
|
|
6
|
+
import sideNavService from '@shell/components/nav/TopLevelMenu.helper';
|
|
6
7
|
|
|
7
8
|
/**
|
|
8
9
|
* `clusters` doubles up as both mgmt and prov clusters (don't shoot the messenger)
|
|
@@ -53,6 +54,7 @@ const waitForIt = async() => {
|
|
|
53
54
|
describe('topLevelMenu', () => {
|
|
54
55
|
beforeEach(() => {
|
|
55
56
|
jest.useFakeTimers();
|
|
57
|
+
sideNavService.reset();
|
|
56
58
|
});
|
|
57
59
|
|
|
58
60
|
afterEach(() => {
|
|
@@ -3,7 +3,8 @@ import {
|
|
|
3
3
|
STATE, NAME as NAME_COL, NAMESPACE as NAMESPACE_COL, AGE, OBJECT,
|
|
4
4
|
EVENT_LAST_SEEN_TIME,
|
|
5
5
|
EVENT_TYPE,
|
|
6
|
-
SECRET_CLONE
|
|
6
|
+
SECRET_CLONE,
|
|
7
|
+
EVENT_FIRST_SEEN_TIME
|
|
7
8
|
} from '@shell/config/table-headers';
|
|
8
9
|
|
|
9
10
|
// This file contains table headers
|
|
@@ -56,10 +57,17 @@ export const STEVE_EVENT_OBJECT = {
|
|
|
56
57
|
search: 'involvedObject.kind',
|
|
57
58
|
};
|
|
58
59
|
|
|
60
|
+
export const STEVE_EVENT_FIRST_SEEN = {
|
|
61
|
+
...EVENT_FIRST_SEEN_TIME,
|
|
62
|
+
|
|
63
|
+
value: 'metadata.fields.7',
|
|
64
|
+
sort: 'metadata.fields.7:desc',
|
|
65
|
+
};
|
|
66
|
+
|
|
59
67
|
export const STEVE_EVENT_LAST_SEEN = {
|
|
60
68
|
...EVENT_LAST_SEEN_TIME,
|
|
61
69
|
value: 'metadata.fields.0',
|
|
62
|
-
sort: 'metadata.fields.0',
|
|
70
|
+
sort: 'metadata.fields.0:desc',
|
|
63
71
|
};
|
|
64
72
|
|
|
65
73
|
export const STEVE_EVENT_TYPE = {
|
package/config/product/auth.js
CHANGED
|
@@ -177,6 +177,7 @@ export function init(store) {
|
|
|
177
177
|
});
|
|
178
178
|
|
|
179
179
|
componentForType(`${ MANAGEMENT.AUTH_CONFIG }/github`, 'auth/github');
|
|
180
|
+
componentForType(`${ MANAGEMENT.AUTH_CONFIG }/githubapp`, 'auth/github');
|
|
180
181
|
componentForType(`${ MANAGEMENT.AUTH_CONFIG }/openldap`, 'auth/ldap/index');
|
|
181
182
|
componentForType(`${ MANAGEMENT.AUTH_CONFIG }/freeipa`, 'auth/ldap/index');
|
|
182
183
|
componentForType(`${ MANAGEMENT.AUTH_CONFIG }/activedirectory`, 'auth/ldap/index');
|
|
@@ -22,11 +22,12 @@ import {
|
|
|
22
22
|
ACCESS_KEY, DESCRIPTION, EXPIRES, EXPIRY_STATE, LAST_USED, SUB_TYPE, AGE_NORMAN, SCOPE_NORMAN, PERSISTENT_VOLUME_CLAIM, RECLAIM_POLICY, PV_REASON, WORKLOAD_HEALTH_SCALE, POD_RESTARTS,
|
|
23
23
|
DURATION, MESSAGE, REASON, EVENT_TYPE, OBJECT, ROLE, ROLES, VERSION, INTERNAL_EXTERNAL_IP, KUBE_NODE_OS, CPU, RAM, SECRET_DATA,
|
|
24
24
|
EVENT_LAST_SEEN_TIME,
|
|
25
|
+
EVENT_FIRST_SEEN_TIME,
|
|
25
26
|
} from '@shell/config/table-headers';
|
|
26
27
|
|
|
27
28
|
import { DSL } from '@shell/store/type-map';
|
|
28
29
|
import {
|
|
29
|
-
STEVE_AGE_COL, STEVE_EVENT_LAST_SEEN, STEVE_EVENT_OBJECT, STEVE_EVENT_TYPE, STEVE_LIST_GROUPS, STEVE_NAMESPACE_COL, STEVE_NAME_COL, STEVE_STATE_COL
|
|
30
|
+
STEVE_AGE_COL, STEVE_EVENT_FIRST_SEEN, STEVE_EVENT_LAST_SEEN, STEVE_EVENT_OBJECT, STEVE_EVENT_TYPE, STEVE_LIST_GROUPS, STEVE_NAMESPACE_COL, STEVE_NAME_COL, STEVE_STATE_COL
|
|
30
31
|
} from '@shell/config/pagination-table-headers';
|
|
31
32
|
|
|
32
33
|
import { COLUMN_BREAKPOINTS } from '@shell/types/store/type-map';
|
|
@@ -337,7 +338,7 @@ export function init(store) {
|
|
|
337
338
|
);
|
|
338
339
|
|
|
339
340
|
headers(EVENT,
|
|
340
|
-
[STATE, EVENT_LAST_SEEN_TIME, EVENT_TYPE, REASON, OBJECT, 'Subobject', 'Source', MESSAGE,
|
|
341
|
+
[STATE, EVENT_LAST_SEEN_TIME, EVENT_TYPE, REASON, OBJECT, 'Subobject', 'Source', MESSAGE, EVENT_FIRST_SEEN_TIME, 'Count', NAME_COL, NAMESPACE_COL],
|
|
341
342
|
[
|
|
342
343
|
STEVE_STATE_COL,
|
|
343
344
|
STEVE_EVENT_LAST_SEEN,
|
|
@@ -347,7 +348,7 @@ export function init(store) {
|
|
|
347
348
|
'Subobject',
|
|
348
349
|
'Source',
|
|
349
350
|
MESSAGE,
|
|
350
|
-
|
|
351
|
+
STEVE_EVENT_FIRST_SEEN,
|
|
351
352
|
'Count',
|
|
352
353
|
STEVE_NAME_COL,
|
|
353
354
|
STEVE_NAMESPACE_COL,
|
package/config/query-params.js
CHANGED
|
@@ -8,6 +8,7 @@ export const STEP = 'step';
|
|
|
8
8
|
export const LOGGED_OUT = 'logged-out';
|
|
9
9
|
export const IS_SSO = 'is-sso';
|
|
10
10
|
export const IS_SLO = 'is-slo';
|
|
11
|
+
export const IS_SESSION_IDLE = 'is-session-idle';
|
|
11
12
|
export const UPGRADED = 'upgraded';
|
|
12
13
|
export const TIMED_OUT = 'timed-out';
|
|
13
14
|
export const AUTH_TEST = 'test';
|
package/config/settings.ts
CHANGED
|
@@ -52,6 +52,7 @@ export const SETTING = {
|
|
|
52
52
|
RKE_METADATA_CONFIG: 'rke-metadata-config',
|
|
53
53
|
EULA_AGREED: 'eula-agreed',
|
|
54
54
|
AUTH_USER_INFO_MAX_AGE_SECONDS: 'auth-user-info-max-age-seconds',
|
|
55
|
+
AUTH_USER_SESSION_IDLE_TTL_MINUTES: 'auth-user-session-idle-ttl-minutes',
|
|
55
56
|
AUTH_USER_SESSION_TTL_MINUTES: 'auth-user-session-ttl-minutes',
|
|
56
57
|
AUTH_USER_INFO_RESYNC_CRON: 'auth-user-info-resync-cron',
|
|
57
58
|
AUTH_LOCAL_VALIDATE_DESC: 'auth-password-requirements-description',
|
|
@@ -109,7 +110,12 @@ export const SETTING = {
|
|
|
109
110
|
SYSTEM_AGENT_UPGRADER_INSTALL_CONCURRENCY: 'system-agent-upgrader-install-concurrency',
|
|
110
111
|
IMPORTED_CLUSTER_VERSION_MANAGEMENT: 'imported-cluster-version-management',
|
|
111
112
|
CLUSTER_AGENT_DEFAULT_PRIORITY_CLASS: 'cluster-agent-default-priority-class',
|
|
112
|
-
CLUSTER_AGENT_DEFAULT_POD_DISTRIBUTION_BUDGET: 'cluster-agent-default-pod-disruption-budget'
|
|
113
|
+
CLUSTER_AGENT_DEFAULT_POD_DISTRIBUTION_BUDGET: 'cluster-agent-default-pod-disruption-budget',
|
|
114
|
+
/**
|
|
115
|
+
* Dynamic Content settings
|
|
116
|
+
*/
|
|
117
|
+
DYNAMIC_CONTENT_ENABLED: 'ui-content-enabled',
|
|
118
|
+
DYNAMIC_CONTENT_ENDPOINT: 'ui-content-endpoint',
|
|
113
119
|
} as const;
|
|
114
120
|
|
|
115
121
|
// These are the settings that are allowed to be edited via the UI
|
|
@@ -140,6 +146,7 @@ export const ALLOWED_SETTINGS: GlobalSetting = {
|
|
|
140
146
|
},
|
|
141
147
|
[SETTING.INGRESS_IP_DOMAIN]: {},
|
|
142
148
|
[SETTING.AUTH_USER_INFO_MAX_AGE_SECONDS]: {},
|
|
149
|
+
[SETTING.AUTH_USER_SESSION_IDLE_TTL_MINUTES]: {},
|
|
143
150
|
[SETTING.AUTH_USER_SESSION_TTL_MINUTES]: {},
|
|
144
151
|
[SETTING.AUTH_TOKEN_MAX_TTL_MINUTES]: {},
|
|
145
152
|
[SETTING.KUBECONFIG_GENERATE_TOKEN]: { kind: 'boolean' },
|
package/config/table-headers.js
CHANGED
|
@@ -541,6 +541,15 @@ export const LAST_SEEN_TIME = {
|
|
|
541
541
|
tooltip: 'tableHeaders.lastSeenTooltip'
|
|
542
542
|
};
|
|
543
543
|
|
|
544
|
+
export const EVENT_FIRST_SEEN_TIME = {
|
|
545
|
+
name: 'firstSeen',
|
|
546
|
+
labelKey: 'tableHeaders.firstSeen',
|
|
547
|
+
tooltip: 'tableHeaders.firstSeenTooltip',
|
|
548
|
+
|
|
549
|
+
value: 'firstSeen',
|
|
550
|
+
sort: 'firstSeen:desc',
|
|
551
|
+
};
|
|
552
|
+
|
|
544
553
|
export const EVENT_LAST_SEEN_TIME = {
|
|
545
554
|
...LAST_SEEN_TIME,
|
|
546
555
|
defaultSort: true,
|
package/config/types.js
CHANGED
|
@@ -222,6 +222,8 @@ export const MANAGEMENT = {
|
|
|
222
222
|
OIDC_CLIENT: 'management.cattle.io.oidcclient'
|
|
223
223
|
};
|
|
224
224
|
|
|
225
|
+
export const EXT = { USER_ACTIVITY: 'ext.cattle.io.useractivity' };
|
|
226
|
+
|
|
225
227
|
export const CAPI = {
|
|
226
228
|
CAPI_CLUSTER: 'cluster.x-k8s.io.cluster',
|
|
227
229
|
MACHINE_DEPLOYMENT: 'cluster.x-k8s.io.machinedeployment',
|
package/core/plugin.ts
CHANGED
|
@@ -17,24 +17,31 @@ import {
|
|
|
17
17
|
PluginRouteRecordRaw, RegisterStore, UnregisterStore, CoreStoreSpecifics, CoreStoreConfig,
|
|
18
18
|
NavHooks, OnNavToPackage, OnNavAwayFromPackage, OnLogIn, OnLogOut,
|
|
19
19
|
PaginationTableColumn,
|
|
20
|
-
ExtensionEnvironment
|
|
20
|
+
ExtensionEnvironment,
|
|
21
|
+
ServerSidePaginationExtensionConfig
|
|
21
22
|
} from './types';
|
|
22
23
|
import coreStore, { coreStoreModule, coreStoreState } from '@shell/plugins/dashboard-store';
|
|
23
24
|
import { defineAsyncComponent, markRaw, Component } from 'vue';
|
|
24
25
|
import { getVersionData, CURRENT_RANCHER_VERSION } from '@shell/config/version';
|
|
26
|
+
import { ExtensionManagerTypes } from '@shell/types/extension-manager';
|
|
25
27
|
|
|
26
|
-
|
|
28
|
+
/** Registration IDs used for different extension points in the extensions catalog */
|
|
27
29
|
export const EXT_IDS = {
|
|
28
|
-
MODELS:
|
|
29
|
-
MODEL_EXTENSION:
|
|
30
|
-
|
|
30
|
+
MODELS: 'models',
|
|
31
|
+
MODEL_EXTENSION: 'model-extension',
|
|
32
|
+
/**
|
|
33
|
+
* Extension can provide resources that use server-side-pagination
|
|
34
|
+
*/
|
|
35
|
+
SERVER_SIDE_PAGINATION_RESOURCES: 'server-side-pagination',
|
|
36
|
+
} as const;
|
|
37
|
+
export type EXT_IDS_VALUES = (typeof EXT_IDS)[keyof typeof EXT_IDS];
|
|
31
38
|
|
|
32
39
|
export type ProductFunction = (plugin: IPlugin, store: any) => void;
|
|
33
40
|
|
|
34
41
|
export class Plugin implements IPlugin {
|
|
35
42
|
public id: string;
|
|
36
43
|
public name: string;
|
|
37
|
-
public types:
|
|
44
|
+
public types: ExtensionManagerTypes = {};
|
|
38
45
|
public l10n: { [key: string]: Function[] } = {};
|
|
39
46
|
public modelExtensions: { [key: string]: Function[] } = {};
|
|
40
47
|
public locales: { locale: string, label: string}[] = [];
|
|
@@ -360,6 +367,11 @@ export class Plugin implements IPlugin {
|
|
|
360
367
|
}
|
|
361
368
|
}
|
|
362
369
|
|
|
370
|
+
public enableServerSidePagination(config: ServerSidePaginationExtensionConfig) {
|
|
371
|
+
console.info(`Extension "${ this.name || this.id }" is enabling server-side pagination for some resources`, config); // eslint-disable-line no-console
|
|
372
|
+
this.register(EXT_IDS.SERVER_SIDE_PAGINATION_RESOURCES, this.id, () => config);
|
|
373
|
+
}
|
|
374
|
+
|
|
363
375
|
public async onLogOut(store: any) {
|
|
364
376
|
await Promise.all(this.stores.map((s: any) => store.dispatch(`${ s.storeName }/onLogout`)));
|
|
365
377
|
|
package/core/types.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { ProductFunction } from './plugin';
|
|
2
2
|
import { RouteRecordRaw } from 'vue-router';
|
|
3
3
|
import type { ExtensionManager } from '@shell/types/extension-manager';
|
|
4
|
+
import { PaginationSettingsStores } from '@shell/types/resources/settings';
|
|
4
5
|
|
|
5
6
|
// Cluster Provisioning types
|
|
6
7
|
export * from './types-provisioning';
|
|
@@ -351,6 +352,11 @@ export type TableColumn = HeaderOptions;
|
|
|
351
352
|
*/
|
|
352
353
|
export type PaginationTableColumn = PaginationHeaderOptions;
|
|
353
354
|
|
|
355
|
+
/**
|
|
356
|
+
* External extension configuration for @PaginationSettingsStores
|
|
357
|
+
*/
|
|
358
|
+
export type ServerSidePaginationExtensionConfig = PaginationSettingsStores;
|
|
359
|
+
|
|
354
360
|
export interface ConfigureTypeOptions {
|
|
355
361
|
/**
|
|
356
362
|
* Override for the create button string on a list view
|
|
@@ -693,6 +699,8 @@ export interface IPlugin {
|
|
|
693
699
|
): void;
|
|
694
700
|
addNavHooks(hooks: NavHooks): void;
|
|
695
701
|
|
|
702
|
+
enableServerSidePagination(config: ServerSidePaginationExtensionConfig): void;
|
|
703
|
+
|
|
696
704
|
/**
|
|
697
705
|
* Adds a model extension
|
|
698
706
|
* @experimental May change or be removed in the future
|