mirror of
https://github.com/lensapp/lens.git
synced 2025-05-20 05:10:56 +00:00
Split root and cluster frames in smaller pieces (#5737)
* Make root frame child components comply with open closed principle and include it in the behavioural unit tests Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Make cluster frame child components comply with open closed principle and include it in behavioural unit tests Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Remove duplication Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Simplify test Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Make a component more determistic in unit tests Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Mock uninterested, non-deterministic third party library in unit tests Co-authored-by: Mikko Aspiala <mikko.aspiala@gmail.com> Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Optimize registration of injectables in unit tests to make tests faster Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Update snapshots Signed-off-by: Janne Savolainen <janne.savolainen@live.fi> * Remove import time side-effect causing memory leak Signed-off-by: Janne Savolainen <janne.savolainen@live.fi>
This commit is contained in:
parent
1a9fa699c9
commit
14d5a1c3cc
15
__mocks__/react-beautiful-dnd.tsx
Normal file
15
__mocks__/react-beautiful-dnd.tsx
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import React from "react";
|
||||||
|
|
||||||
|
import type {
|
||||||
|
DragDropContextProps,
|
||||||
|
DraggableProps,
|
||||||
|
DroppableProps,
|
||||||
|
} from "react-beautiful-dnd";
|
||||||
|
|
||||||
|
export const DragDropContext = ({ children }: DragDropContextProps) => <>{ children }</>;
|
||||||
|
export const Draggable = ({ children }: DraggableProps) => <>{ children }</>;
|
||||||
|
export const Droppable = ({ children }: DroppableProps) => <>{ children }</>;
|
||||||
10
package.json
10
package.json
@ -209,11 +209,11 @@
|
|||||||
"@hapi/subtext": "^7.0.4",
|
"@hapi/subtext": "^7.0.4",
|
||||||
"@kubernetes/client-node": "^0.16.3",
|
"@kubernetes/client-node": "^0.16.3",
|
||||||
"@material-ui/styles": "^4.11.5",
|
"@material-ui/styles": "^4.11.5",
|
||||||
"@ogre-tools/fp": "9.0.0",
|
"@ogre-tools/fp": "9.0.1",
|
||||||
"@ogre-tools/injectable": "9.0.0",
|
"@ogre-tools/injectable": "9.0.1",
|
||||||
"@ogre-tools/injectable-extension-for-auto-registration": "9.0.0",
|
"@ogre-tools/injectable-extension-for-auto-registration": "9.0.1",
|
||||||
"@ogre-tools/injectable-extension-for-mobx": "9.0.0",
|
"@ogre-tools/injectable-extension-for-mobx": "9.0.1",
|
||||||
"@ogre-tools/injectable-react": "9.0.0",
|
"@ogre-tools/injectable-react": "9.0.1",
|
||||||
"@sentry/electron": "^3.0.7",
|
"@sentry/electron": "^3.0.7",
|
||||||
"@sentry/integrations": "^6.19.3",
|
"@sentry/integrations": "^6.19.3",
|
||||||
"@side/jest-runtime": "^1.0.1",
|
"@side/jest-runtime": "^1.0.1",
|
||||||
|
|||||||
@ -3,71 +3,206 @@
|
|||||||
exports[`extension special characters in page registrations renders 1`] = `
|
exports[`extension special characters in page registrations renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
>
|
>
|
||||||
No new updates available
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
@ -78,74 +213,126 @@ exports[`extension special characters in page registrations renders 1`] = `
|
|||||||
exports[`extension special characters in page registrations when navigating to route with ID having special characters renders 1`] = `
|
exports[`extension special characters in page registrations when navigating to route with ID having special characters renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
>
|
>
|
||||||
<div
|
<i
|
||||||
data-testid="app-update-not-available"
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
No new updates available
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div>
|
||||||
|
Some page
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
</div>
|
class="leftSide"
|
||||||
<div>
|
data-testid="status-bar-left"
|
||||||
Some page
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@ -3,78 +3,130 @@
|
|||||||
exports[`navigating between routes given route with optional path parameters when navigating to route with path parameters renders 1`] = `
|
exports[`navigating between routes given route with optional path parameters when navigating to route with path parameters renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
>
|
>
|
||||||
<div
|
<i
|
||||||
data-testid="app-update-not-available"
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
No new updates available
|
<span
|
||||||
</div>
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
</div>
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<main>
|
||||||
class="rightSide"
|
<div
|
||||||
data-testid="status-bar-right"
|
id="lens-views"
|
||||||
/>
|
/>
|
||||||
</div>
|
<pre>
|
||||||
<pre>
|
{
|
||||||
{
|
|
||||||
"someParameter": "some-value",
|
"someParameter": "some-value",
|
||||||
"someOtherParameter": "some-other-value"
|
"someOtherParameter": "some-other-value"
|
||||||
}
|
}
|
||||||
</pre>
|
</pre>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="StatusBar"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
/>
|
/>
|
||||||
@ -84,74 +136,126 @@ exports[`navigating between routes given route with optional path parameters whe
|
|||||||
exports[`navigating between routes given route without path parameters when navigating to route renders 1`] = `
|
exports[`navigating between routes given route without path parameters when navigating to route renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
>
|
>
|
||||||
<div
|
<i
|
||||||
data-testid="app-update-not-available"
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
No new updates available
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div>
|
||||||
|
Some component
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
</div>
|
class="leftSide"
|
||||||
<div>
|
data-testid="status-bar-left"
|
||||||
Some component
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
|
|||||||
@ -3,71 +3,206 @@
|
|||||||
exports[`add-cluster - navigation using application menu renders 1`] = `
|
exports[`add-cluster - navigation using application menu renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
>
|
>
|
||||||
No new updates available
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
@ -78,151 +213,203 @@ exports[`add-cluster - navigation using application menu renders 1`] = `
|
|||||||
exports[`add-cluster - navigation using application menu when navigating to add cluster using application menu renders 1`] = `
|
exports[`add-cluster - navigation using application menu when navigating to add cluster using application menu renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
>
|
>
|
||||||
<div
|
<i
|
||||||
data-testid="app-update-not-available"
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
No new updates available
|
<span
|
||||||
</div>
|
class="icon"
|
||||||
</div>
|
data-icon-name="home"
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="rightSide"
|
|
||||||
data-testid="status-bar-right"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SettingLayout AddClusters"
|
|
||||||
data-testid="add-cluster-page"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="contentRegion"
|
|
||||||
id="ScrollSpyRoot"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content flex column gaps"
|
|
||||||
>
|
|
||||||
<h2>
|
|
||||||
Add Clusters from Kubeconfig
|
|
||||||
</h2>
|
|
||||||
<p>
|
|
||||||
Clusters added here are
|
|
||||||
<b>
|
|
||||||
not
|
|
||||||
</b>
|
|
||||||
merged into the
|
|
||||||
<code>
|
|
||||||
~/.kube/config
|
|
||||||
</code>
|
|
||||||
file.
|
|
||||||
<a
|
|
||||||
href="https://docs.k8slens.dev/main/catalog/add-cluster/"
|
|
||||||
rel="noreferrer"
|
|
||||||
target="_blank"
|
|
||||||
>
|
>
|
||||||
Read more about adding clusters.
|
home
|
||||||
</a>
|
</span>
|
||||||
</p>
|
</i>
|
||||||
<div
|
<i
|
||||||
class="flex column"
|
class="Icon material interactive disabled focusable"
|
||||||
/>
|
data-testid="history-back"
|
||||||
<div
|
|
||||||
class="actions-panel"
|
|
||||||
>
|
>
|
||||||
<button
|
<span
|
||||||
class="Button primary"
|
class="icon"
|
||||||
disabled=""
|
data-icon-name="arrow_back"
|
||||||
type="button"
|
|
||||||
>
|
>
|
||||||
Add clusters
|
arrow_back
|
||||||
</button>
|
</span>
|
||||||
</div>
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="toolsRegion"
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="SettingLayout AddClusters"
|
||||||
|
data-testid="add-cluster-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="fixed top-[60px]"
|
class="contentRegion"
|
||||||
|
id="ScrollSpyRoot"
|
||||||
>
|
>
|
||||||
<div>
|
<div
|
||||||
<div
|
class="content flex column gaps"
|
||||||
aria-label="Close"
|
>
|
||||||
class="closeButton"
|
<h2>
|
||||||
role="button"
|
Add Clusters from Kubeconfig
|
||||||
>
|
</h2>
|
||||||
<i
|
<p>
|
||||||
class="Icon icon material focusable"
|
Clusters added here are
|
||||||
|
<b>
|
||||||
|
not
|
||||||
|
</b>
|
||||||
|
merged into the
|
||||||
|
<code>
|
||||||
|
~/.kube/config
|
||||||
|
</code>
|
||||||
|
file.
|
||||||
|
<a
|
||||||
|
href="https://docs.k8slens.dev/main/catalog/add-cluster/"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
>
|
>
|
||||||
<span
|
Read more about adding clusters.
|
||||||
class="icon"
|
</a>
|
||||||
data-icon-name="close"
|
</p>
|
||||||
>
|
|
||||||
close
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
<div
|
||||||
aria-hidden="true"
|
class="flex column"
|
||||||
class="esc"
|
/>
|
||||||
|
<div
|
||||||
|
class="actions-panel"
|
||||||
>
|
>
|
||||||
ESC
|
<button
|
||||||
|
class="Button primary"
|
||||||
|
disabled=""
|
||||||
|
type="button"
|
||||||
|
>
|
||||||
|
Add clusters
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="toolsRegion"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="fixed top-[60px]"
|
||||||
|
>
|
||||||
|
<div>
|
||||||
|
<div
|
||||||
|
aria-label="Close"
|
||||||
|
class="closeButton"
|
||||||
|
role="button"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="close"
|
||||||
|
>
|
||||||
|
close
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
aria-hidden="true"
|
||||||
|
class="esc"
|
||||||
|
>
|
||||||
|
ESC
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="StatusBar"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
|
|||||||
@ -9,10 +9,6 @@ import { getApplicationBuilder } from "../../renderer/components/test-utils/get-
|
|||||||
import React from "react";
|
import React from "react";
|
||||||
|
|
||||||
// TODO: Make components free of side effects by making them deterministic
|
// TODO: Make components free of side effects by making them deterministic
|
||||||
jest.mock("../../renderer/components/tooltip/tooltip", () => ({
|
|
||||||
Tooltip: () => null,
|
|
||||||
}));
|
|
||||||
|
|
||||||
jest.mock("../../renderer/components/tooltip/withTooltip", () => ({
|
jest.mock("../../renderer/components/tooltip/withTooltip", () => ({
|
||||||
withTooltip: (Target: any) => ({ tooltip, tooltipOverrideDisabled, ...props }: any) => <Target {...props} />,
|
withTooltip: (Target: any) => ({ tooltip, tooltipOverrideDisabled, ...props }: any) => <Target {...props} />,
|
||||||
}));
|
}));
|
||||||
|
|||||||
@ -4,71 +4,206 @@ exports[`encourage user to update when sufficient time passed since update was d
|
|||||||
<body>
|
<body>
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
>
|
>
|
||||||
No new updates available
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -4,71 +4,206 @@ exports[`periodical checking of updates given updater is enabled and configurati
|
|||||||
<body>
|
<body>
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
>
|
>
|
||||||
No new updates available
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
|
|||||||
@ -4,71 +4,206 @@ exports[`selection of update stability when started renders 1`] = `
|
|||||||
<body>
|
<body>
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
>
|
>
|
||||||
No new updates available
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -22,6 +22,7 @@ import pathExistsInjectable from "../../common/fs/path-exists.injectable";
|
|||||||
import readJsonFileInjectable from "../../common/fs/read-json-file.injectable";
|
import readJsonFileInjectable from "../../common/fs/read-json-file.injectable";
|
||||||
import { navigateToRouteInjectionToken } from "../../common/front-end-routing/navigate-to-route-injection-token";
|
import { navigateToRouteInjectionToken } from "../../common/front-end-routing/navigate-to-route-injection-token";
|
||||||
import sidebarStorageInjectable from "../../renderer/components/layout/sidebar-storage/sidebar-storage.injectable";
|
import sidebarStorageInjectable from "../../renderer/components/layout/sidebar-storage/sidebar-storage.injectable";
|
||||||
|
import hostedClusterIdInjectable from "../../renderer/cluster-frame-context/hosted-cluster-id.injectable";
|
||||||
import { advanceFakeTime, useFakeTime } from "../../common/test-utils/use-fake-time";
|
import { advanceFakeTime, useFakeTime } from "../../common/test-utils/use-fake-time";
|
||||||
|
|
||||||
describe("cluster - sidebar and tab navigation for core", () => {
|
describe("cluster - sidebar and tab navigation for core", () => {
|
||||||
@ -38,6 +39,8 @@ describe("cluster - sidebar and tab navigation for core", () => {
|
|||||||
applicationBuilder.setEnvironmentToClusterFrame();
|
applicationBuilder.setEnvironmentToClusterFrame();
|
||||||
|
|
||||||
applicationBuilder.beforeApplicationStart(({ rendererDi }) => {
|
applicationBuilder.beforeApplicationStart(({ rendererDi }) => {
|
||||||
|
rendererDi.override(hostedClusterIdInjectable, () => "some-hosted-cluster-id");
|
||||||
|
|
||||||
rendererDi.override(
|
rendererDi.override(
|
||||||
directoryForLensLocalStorageInjectable,
|
directoryForLensLocalStorageInjectable,
|
||||||
() => "/some-directory-for-lens-local-storage",
|
() => "/some-directory-for-lens-local-storage",
|
||||||
@ -94,7 +97,7 @@ describe("cluster - sidebar and tab navigation for core", () => {
|
|||||||
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
||||||
|
|
||||||
await writeJsonFileFake(
|
await writeJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
{
|
{
|
||||||
sidebar: {
|
sidebar: {
|
||||||
expanded: { "some-parent-id": true },
|
expanded: { "some-parent-id": true },
|
||||||
@ -136,7 +139,7 @@ describe("cluster - sidebar and tab navigation for core", () => {
|
|||||||
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
||||||
|
|
||||||
await writeJsonFileFake(
|
await writeJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
{
|
{
|
||||||
sidebar: {
|
sidebar: {
|
||||||
expanded: { "some-unknown-parent-id": true },
|
expanded: { "some-unknown-parent-id": true },
|
||||||
@ -166,7 +169,7 @@ describe("cluster - sidebar and tab navigation for core", () => {
|
|||||||
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
||||||
|
|
||||||
await writeJsonFileFake(
|
await writeJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
{
|
{
|
||||||
someThingButSidebar: {},
|
someThingButSidebar: {},
|
||||||
},
|
},
|
||||||
@ -268,7 +271,7 @@ describe("cluster - sidebar and tab navigation for core", () => {
|
|||||||
const pathExistsFake = rendererDi.inject(pathExistsInjectable);
|
const pathExistsFake = rendererDi.inject(pathExistsInjectable);
|
||||||
|
|
||||||
const actual = await pathExistsFake(
|
const actual = await pathExistsFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(actual).toBe(false);
|
expect(actual).toBe(false);
|
||||||
@ -280,7 +283,7 @@ describe("cluster - sidebar and tab navigation for core", () => {
|
|||||||
const readJsonFileFake = rendererDi.inject(readJsonFileInjectable);
|
const readJsonFileFake = rendererDi.inject(readJsonFileInjectable);
|
||||||
|
|
||||||
const actual = await readJsonFileFake(
|
const actual = await readJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(actual).toEqual({
|
expect(actual).toEqual({
|
||||||
|
|||||||
@ -18,8 +18,14 @@ import { navigateToRouteInjectionToken } from "../../common/front-end-routing/na
|
|||||||
import assert from "assert";
|
import assert from "assert";
|
||||||
import type { FakeExtensionData } from "../../renderer/components/test-utils/get-renderer-extension-fake";
|
import type { FakeExtensionData } from "../../renderer/components/test-utils/get-renderer-extension-fake";
|
||||||
import { getRendererExtensionFakeFor } from "../../renderer/components/test-utils/get-renderer-extension-fake";
|
import { getRendererExtensionFakeFor } from "../../renderer/components/test-utils/get-renderer-extension-fake";
|
||||||
|
import hostedClusterIdInjectable from "../../renderer/cluster-frame-context/hosted-cluster-id.injectable";
|
||||||
import { advanceFakeTime, useFakeTime } from "../../common/test-utils/use-fake-time";
|
import { advanceFakeTime, useFakeTime } from "../../common/test-utils/use-fake-time";
|
||||||
|
|
||||||
|
// TODO: Make tooltips free of side effects by making it deterministic
|
||||||
|
jest.mock("../../renderer/components/tooltip/withTooltip", () => ({
|
||||||
|
withTooltip: (target: any) => target,
|
||||||
|
}));
|
||||||
|
|
||||||
describe("cluster - sidebar and tab navigation for extensions", () => {
|
describe("cluster - sidebar and tab navigation for extensions", () => {
|
||||||
let applicationBuilder: ApplicationBuilder;
|
let applicationBuilder: ApplicationBuilder;
|
||||||
let rendererDi: DiContainer;
|
let rendererDi: DiContainer;
|
||||||
@ -34,6 +40,8 @@ describe("cluster - sidebar and tab navigation for extensions", () => {
|
|||||||
applicationBuilder.setEnvironmentToClusterFrame();
|
applicationBuilder.setEnvironmentToClusterFrame();
|
||||||
|
|
||||||
applicationBuilder.beforeApplicationStart(({ rendererDi }) => {
|
applicationBuilder.beforeApplicationStart(({ rendererDi }) => {
|
||||||
|
rendererDi.override(hostedClusterIdInjectable, () => "some-hosted-cluster-id");
|
||||||
|
|
||||||
rendererDi.override(
|
rendererDi.override(
|
||||||
directoryForLensLocalStorageInjectable,
|
directoryForLensLocalStorageInjectable,
|
||||||
() => "/some-directory-for-lens-local-storage",
|
() => "/some-directory-for-lens-local-storage",
|
||||||
@ -96,7 +104,7 @@ describe("cluster - sidebar and tab navigation for extensions", () => {
|
|||||||
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
||||||
|
|
||||||
await writeJsonFileFake(
|
await writeJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
{
|
{
|
||||||
sidebar: {
|
sidebar: {
|
||||||
expanded: { "some-extension-name-some-parent-id": true },
|
expanded: { "some-extension-name-some-parent-id": true },
|
||||||
@ -132,7 +140,7 @@ describe("cluster - sidebar and tab navigation for extensions", () => {
|
|||||||
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
||||||
|
|
||||||
await writeJsonFileFake(
|
await writeJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
{
|
{
|
||||||
sidebar: {
|
sidebar: {
|
||||||
expanded: { "some-extension-name-some-unknown-parent-id": true },
|
expanded: { "some-extension-name-some-unknown-parent-id": true },
|
||||||
@ -162,7 +170,7 @@ describe("cluster - sidebar and tab navigation for extensions", () => {
|
|||||||
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
const writeJsonFileFake = rendererDi.inject(writeJsonFileInjectable);
|
||||||
|
|
||||||
await writeJsonFileFake(
|
await writeJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
{
|
{
|
||||||
someThingButSidebar: {},
|
someThingButSidebar: {},
|
||||||
},
|
},
|
||||||
@ -284,7 +292,7 @@ describe("cluster - sidebar and tab navigation for extensions", () => {
|
|||||||
const pathExistsFake = rendererDi.inject(pathExistsInjectable);
|
const pathExistsFake = rendererDi.inject(pathExistsInjectable);
|
||||||
|
|
||||||
const actual = await pathExistsFake(
|
const actual = await pathExistsFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(actual).toBe(false);
|
expect(actual).toBe(false);
|
||||||
@ -296,7 +304,7 @@ describe("cluster - sidebar and tab navigation for extensions", () => {
|
|||||||
const readJsonFileFake = rendererDi.inject(readJsonFileInjectable);
|
const readJsonFileFake = rendererDi.inject(readJsonFileInjectable);
|
||||||
|
|
||||||
const actual = await readJsonFileFake(
|
const actual = await readJsonFileFake(
|
||||||
"/some-directory-for-lens-local-storage/app.json",
|
"/some-directory-for-lens-local-storage/some-hosted-cluster-id.json",
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(actual).toEqual({
|
expect(actual).toEqual({
|
||||||
|
|||||||
@ -3,71 +3,206 @@
|
|||||||
exports[`extensions - navigation using application menu renders 1`] = `
|
exports[`extensions - navigation using application menu renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
>
|
>
|
||||||
No new updates available
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
>
|
||||||
/>
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="Notifications flex column align-flex-end"
|
class="Notifications flex column align-flex-end"
|
||||||
@ -78,184 +213,236 @@ exports[`extensions - navigation using application menu renders 1`] = `
|
|||||||
exports[`extensions - navigation using application menu when navigating to extensions using application menu renders 1`] = `
|
exports[`extensions - navigation using application menu when navigating to extensions using application menu renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive focusable"
|
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="home"
|
|
||||||
>
|
|
||||||
home
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-back"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_back"
|
|
||||||
>
|
|
||||||
arrow_back
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<i
|
|
||||||
class="Icon material interactive disabled focusable"
|
|
||||||
data-testid="history-forward"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_forward"
|
|
||||||
>
|
|
||||||
arrow_forward
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="items"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="items"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="home"
|
||||||
|
>
|
||||||
|
home
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-back"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_back"
|
||||||
|
>
|
||||||
|
arrow_back
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive disabled focusable"
|
||||||
|
data-testid="history-forward"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="SettingLayout DropFileInput Extensions"
|
||||||
|
data-testid="extensions-page"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="app-update-not-available"
|
class="contentRegion"
|
||||||
|
id="ScrollSpyRoot"
|
||||||
>
|
>
|
||||||
No new updates available
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="rightSide"
|
|
||||||
data-testid="status-bar-right"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SettingLayout DropFileInput Extensions"
|
|
||||||
data-testid="extensions-page"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="contentRegion"
|
|
||||||
id="ScrollSpyRoot"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
|
||||||
<section>
|
|
||||||
<h1>
|
|
||||||
Extensions
|
|
||||||
</h1>
|
|
||||||
<div
|
<div
|
||||||
class="notice mb-14 mt-3"
|
class="content"
|
||||||
>
|
>
|
||||||
<p>
|
<section>
|
||||||
Add new features via Lens Extensions. Check out the
|
<h1>
|
||||||
<a
|
Extensions
|
||||||
href="https://docs.k8slens.dev/main/extensions/"
|
</h1>
|
||||||
rel="noreferrer"
|
|
||||||
target="_blank"
|
|
||||||
>
|
|
||||||
docs
|
|
||||||
</a>
|
|
||||||
and list of
|
|
||||||
<a
|
|
||||||
href="https://github.com/lensapp/lens-extensions/blob/main/README.md"
|
|
||||||
rel="noreferrer"
|
|
||||||
target="_blank"
|
|
||||||
>
|
|
||||||
available extensions
|
|
||||||
</a>
|
|
||||||
.
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
<section
|
|
||||||
class="mt-2"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="SubTitle"
|
|
||||||
>
|
|
||||||
Name or file path or URL to an extension package (tar, tgz)
|
|
||||||
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="flex"
|
|
||||||
>
|
|
||||||
<div
|
<div
|
||||||
class="flex-1"
|
class="notice mb-14 mt-3"
|
||||||
/>
|
|
||||||
<div
|
|
||||||
class="flex-initial"
|
|
||||||
>
|
>
|
||||||
<button
|
<p>
|
||||||
class="Button w-80 h-full primary"
|
Add new features via Lens Extensions. Check out the
|
||||||
type="button"
|
<a
|
||||||
|
href="https://docs.k8slens.dev/main/extensions/"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
docs
|
||||||
|
</a>
|
||||||
|
and list of
|
||||||
|
<a
|
||||||
|
href="https://github.com/lensapp/lens-extensions/blob/main/README.md"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
available extensions
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<section
|
||||||
|
class="mt-2"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="SubTitle"
|
||||||
>
|
>
|
||||||
Install
|
Name or file path or URL to an extension package (tar, tgz)
|
||||||
</button>
|
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="flex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="flex-1"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex-initial"
|
||||||
|
>
|
||||||
|
<button
|
||||||
|
class="Button w-80 h-full primary"
|
||||||
|
type="button"
|
||||||
|
>
|
||||||
|
Install
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<small
|
||||||
|
class="mt-3"
|
||||||
|
>
|
||||||
|
<b>
|
||||||
|
Pro-Tip
|
||||||
|
</b>
|
||||||
|
: you can drag-n-drop tarball-file to this area
|
||||||
|
</small>
|
||||||
|
</section>
|
||||||
|
<div>
|
||||||
|
<div
|
||||||
|
class="Spinner singleColor center"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="toolsRegion"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="fixed top-[60px]"
|
||||||
|
>
|
||||||
|
<div>
|
||||||
|
<div
|
||||||
|
aria-label="Close"
|
||||||
|
class="closeButton"
|
||||||
|
role="button"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="close"
|
||||||
|
>
|
||||||
|
close
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
aria-hidden="true"
|
||||||
|
class="esc"
|
||||||
|
>
|
||||||
|
ESC
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<small
|
|
||||||
class="mt-3"
|
|
||||||
>
|
|
||||||
<b>
|
|
||||||
Pro-Tip
|
|
||||||
</b>
|
|
||||||
: you can drag-n-drop tarball-file to this area
|
|
||||||
</small>
|
|
||||||
</section>
|
|
||||||
<div>
|
|
||||||
<div
|
|
||||||
class="Spinner singleColor center"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</section>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="toolsRegion"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="fixed top-[60px]"
|
|
||||||
>
|
|
||||||
<div>
|
|
||||||
<div
|
|
||||||
aria-label="Close"
|
|
||||||
class="closeButton"
|
|
||||||
role="button"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon icon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="close"
|
|
||||||
>
|
|
||||||
close
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
aria-hidden="true"
|
|
||||||
class="esc"
|
|
||||||
>
|
|
||||||
ESC
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</main>
|
||||||
|
<div
|
||||||
|
class="HotbarMenu flex column"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="HotbarItems flex column gaps"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="HotbarSelector"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_left"
|
||||||
|
>
|
||||||
|
arrow_left
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="HotbarIndex"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="StatusBar"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -3,451 +3,586 @@
|
|||||||
exports[`helm-charts - navigation to Helm charts when navigating to Helm charts renders 1`] = `
|
exports[`helm-charts - navigation to Helm charts when navigating to Helm charts renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="flex flex-col"
|
class="Notifications flex column align-flex-end"
|
||||||
data-testid="cluster-sidebar"
|
/>
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="SidebarCluster"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="Avatar rounded loadingAvatar"
|
|
||||||
style="width: 40px; height: 40px;"
|
|
||||||
>
|
|
||||||
??
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="loadingClusterName"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="sidebarNav sidebar-active-status"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="sidebar-item-workloads"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
class="nav-item flex gaps align-center expandable"
|
|
||||||
data-testid="sidebar-item-link-for-workloads"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon svg focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
/>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Workloads
|
|
||||||
</span>
|
|
||||||
<i
|
|
||||||
class="Icon expand-icon box right material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="keyboard_arrow_down"
|
|
||||||
>
|
|
||||||
keyboard_arrow_down
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="sidebar-item-config"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
class="nav-item flex gaps align-center"
|
|
||||||
data-testid="sidebar-item-link-for-config"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="list"
|
|
||||||
>
|
|
||||||
list
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Config
|
|
||||||
</span>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="sidebar-item-network"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
class="nav-item flex gaps align-center expandable"
|
|
||||||
data-testid="sidebar-item-link-for-network"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="device_hub"
|
|
||||||
>
|
|
||||||
device_hub
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Network
|
|
||||||
</span>
|
|
||||||
<i
|
|
||||||
class="Icon expand-icon box right material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="keyboard_arrow_down"
|
|
||||||
>
|
|
||||||
keyboard_arrow_down
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="sidebar-item-storage"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
class="nav-item flex gaps align-center"
|
|
||||||
data-testid="sidebar-item-link-for-storage"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="storage"
|
|
||||||
>
|
|
||||||
storage
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Storage
|
|
||||||
</span>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="true"
|
|
||||||
data-testid="sidebar-item-helm"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
aria-current="page"
|
|
||||||
class="nav-item flex gaps align-center expandable active"
|
|
||||||
data-testid="sidebar-item-link-for-helm"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon svg focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
/>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Helm
|
|
||||||
</span>
|
|
||||||
<i
|
|
||||||
class="Icon expand-icon box right material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="keyboard_arrow_down"
|
|
||||||
>
|
|
||||||
keyboard_arrow_down
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="sidebar-item-user-management"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
class="nav-item flex gaps align-center"
|
|
||||||
data-testid="sidebar-item-link-for-user-management"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="security"
|
|
||||||
>
|
|
||||||
security
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Access Control
|
|
||||||
</span>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="SidebarItem"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="sidebar-item-custom-resources"
|
|
||||||
>
|
|
||||||
<a
|
|
||||||
class="nav-item flex gaps align-center expandable"
|
|
||||||
data-testid="sidebar-item-link-for-custom-resources"
|
|
||||||
href="/"
|
|
||||||
>
|
|
||||||
<i
|
|
||||||
class="Icon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="extension"
|
|
||||||
>
|
|
||||||
extension
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
<span
|
|
||||||
class="link-text box grow"
|
|
||||||
>
|
|
||||||
Custom Resources
|
|
||||||
</span>
|
|
||||||
<i
|
|
||||||
class="Icon expand-icon box right material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="keyboard_arrow_down"
|
|
||||||
>
|
|
||||||
keyboard_arrow_down
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
<div
|
||||||
class="TabLayout"
|
class="mainLayout"
|
||||||
data-testid="tab-layout"
|
style="--sidebar-width: 200px;"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="Tabs center scrollable"
|
class="sidebar"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="Tab flex gaps align-center active"
|
class="flex flex-col"
|
||||||
data-is-active-test="true"
|
data-testid="cluster-sidebar"
|
||||||
data-testid="tab-link-for-charts"
|
|
||||||
role="tab"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="label"
|
class="SidebarCluster"
|
||||||
>
|
|
||||||
Charts
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="Tab flex gaps align-center"
|
|
||||||
data-is-active-test="false"
|
|
||||||
data-testid="tab-link-for-releases"
|
|
||||||
role="tab"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="label"
|
|
||||||
>
|
|
||||||
Releases
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<main>
|
|
||||||
<div
|
|
||||||
data-testid="page-for-helm-charts"
|
|
||||||
style="display: none;"
|
|
||||||
/>
|
|
||||||
<div
|
|
||||||
class="ItemListLayout flex column HelmCharts"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="header flex gaps align-center"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="Input SearchInput focused"
|
class="Avatar rounded loadingAvatar"
|
||||||
|
style="width: 40px; height: 40px;"
|
||||||
>
|
>
|
||||||
<label
|
??
|
||||||
class="input-area flex gaps align-center"
|
</div>
|
||||||
id=""
|
<div
|
||||||
|
class="loadingClusterName"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="sidebarNav sidebar-active-status"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="SidebarItem"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="sidebar-item-workloads"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
class="nav-item flex gaps align-center expandable"
|
||||||
|
data-testid="sidebar-item-link-for-workloads"
|
||||||
|
href="/"
|
||||||
>
|
>
|
||||||
<input
|
|
||||||
class="input box grow"
|
|
||||||
placeholder="Search Helm Charts..."
|
|
||||||
spellcheck="false"
|
|
||||||
value=""
|
|
||||||
/>
|
|
||||||
<i
|
<i
|
||||||
class="Icon material focusable small"
|
class="Icon svg focusable"
|
||||||
>
|
>
|
||||||
<span
|
<span
|
||||||
class="icon"
|
class="icon"
|
||||||
data-icon-name="search"
|
/>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Workloads
|
||||||
|
</span>
|
||||||
|
<i
|
||||||
|
class="Icon expand-icon box right material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="keyboard_arrow_down"
|
||||||
>
|
>
|
||||||
search
|
keyboard_arrow_down
|
||||||
</span>
|
</span>
|
||||||
</i>
|
</i>
|
||||||
</label>
|
</a>
|
||||||
<div
|
</div>
|
||||||
class="input-info flex gaps"
|
<div
|
||||||
/>
|
class="SidebarItem"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="sidebar-item-config"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
class="nav-item flex gaps align-center"
|
||||||
|
data-testid="sidebar-item-link-for-config"
|
||||||
|
href="/"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="list"
|
||||||
|
>
|
||||||
|
list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Config
|
||||||
|
</span>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="SidebarItem"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="sidebar-item-network"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
class="nav-item flex gaps align-center expandable"
|
||||||
|
data-testid="sidebar-item-link-for-network"
|
||||||
|
href="/"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="device_hub"
|
||||||
|
>
|
||||||
|
device_hub
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Network
|
||||||
|
</span>
|
||||||
|
<i
|
||||||
|
class="Icon expand-icon box right material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="keyboard_arrow_down"
|
||||||
|
>
|
||||||
|
keyboard_arrow_down
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="SidebarItem"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="sidebar-item-storage"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
class="nav-item flex gaps align-center"
|
||||||
|
data-testid="sidebar-item-link-for-storage"
|
||||||
|
href="/"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="storage"
|
||||||
|
>
|
||||||
|
storage
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Storage
|
||||||
|
</span>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="SidebarItem"
|
||||||
|
data-is-active-test="true"
|
||||||
|
data-testid="sidebar-item-helm"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
aria-current="page"
|
||||||
|
class="nav-item flex gaps align-center expandable active"
|
||||||
|
data-testid="sidebar-item-link-for-helm"
|
||||||
|
href="/"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Helm
|
||||||
|
</span>
|
||||||
|
<i
|
||||||
|
class="Icon expand-icon box right material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="keyboard_arrow_down"
|
||||||
|
>
|
||||||
|
keyboard_arrow_down
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="SidebarItem"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="sidebar-item-user-management"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
class="nav-item flex gaps align-center"
|
||||||
|
data-testid="sidebar-item-link-for-user-management"
|
||||||
|
href="/"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="security"
|
||||||
|
>
|
||||||
|
security
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Access Control
|
||||||
|
</span>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="SidebarItem"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="sidebar-item-custom-resources"
|
||||||
|
>
|
||||||
|
<a
|
||||||
|
class="nav-item flex gaps align-center expandable"
|
||||||
|
data-testid="sidebar-item-link-for-custom-resources"
|
||||||
|
href="/"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="extension"
|
||||||
|
>
|
||||||
|
extension
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<span
|
||||||
|
class="link-text box grow"
|
||||||
|
>
|
||||||
|
Custom Resources
|
||||||
|
</span>
|
||||||
|
<i
|
||||||
|
class="Icon expand-icon box right material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="keyboard_arrow_down"
|
||||||
|
>
|
||||||
|
keyboard_arrow_down
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="ResizingAnchor horizontal trailing"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="contents"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="TabLayout"
|
||||||
|
data-testid="tab-layout"
|
||||||
|
>
|
||||||
<div
|
<div
|
||||||
class="items box grow flex column"
|
class="Tabs center scrollable"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="Table flex column HelmCharts box grow dark selectable scrollable sortable autoSize virtual"
|
class="Tab flex gaps align-center active"
|
||||||
|
data-is-active-test="true"
|
||||||
|
data-testid="tab-link-for-charts"
|
||||||
|
role="tab"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="TableHead sticky nowrap topLine"
|
class="label"
|
||||||
|
>
|
||||||
|
Charts
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="Tab flex gaps align-center"
|
||||||
|
data-is-active-test="false"
|
||||||
|
data-testid="tab-link-for-releases"
|
||||||
|
role="tab"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="label"
|
||||||
|
>
|
||||||
|
Releases
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
data-testid="page-for-helm-charts"
|
||||||
|
style="display: none;"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="ItemListLayout flex column HelmCharts"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="header flex gaps align-center"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="TableCell icon nowrap"
|
class="Input SearchInput focused"
|
||||||
>
|
>
|
||||||
<div
|
<label
|
||||||
class="content"
|
class="input-area flex gaps align-center"
|
||||||
/>
|
id=""
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="TableCell name nowrap sorting"
|
|
||||||
id="name"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
|
||||||
Name
|
|
||||||
</div>
|
|
||||||
<i
|
|
||||||
class="Icon sortIcon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_drop_down"
|
|
||||||
>
|
|
||||||
arrow_drop_down
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="TableCell description nowrap"
|
|
||||||
id="description"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
|
||||||
Description
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="TableCell version nowrap"
|
|
||||||
id="version"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
|
||||||
Version
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="TableCell app-version nowrap"
|
|
||||||
id="app-version"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
|
||||||
App Version
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="TableCell repository nowrap sorting"
|
|
||||||
id="repo"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
|
||||||
Repository
|
|
||||||
</div>
|
|
||||||
<i
|
|
||||||
class="Icon sortIcon material focusable"
|
|
||||||
>
|
|
||||||
<span
|
|
||||||
class="icon"
|
|
||||||
data-icon-name="arrow_drop_down"
|
|
||||||
>
|
|
||||||
arrow_drop_down
|
|
||||||
</span>
|
|
||||||
</i>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="TableCell menu nowrap"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="content"
|
|
||||||
>
|
>
|
||||||
|
<input
|
||||||
|
class="input box grow"
|
||||||
|
placeholder="Search Helm Charts..."
|
||||||
|
spellcheck="false"
|
||||||
|
value=""
|
||||||
|
/>
|
||||||
<i
|
<i
|
||||||
class="Icon material interactive focusable"
|
class="Icon material focusable small"
|
||||||
id="menu_actions_17"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
>
|
||||||
<span
|
<span
|
||||||
class="icon"
|
class="icon"
|
||||||
data-icon-name="more_vert"
|
data-icon-name="search"
|
||||||
>
|
>
|
||||||
more_vert
|
search
|
||||||
</span>
|
</span>
|
||||||
</i>
|
</i>
|
||||||
</div>
|
</label>
|
||||||
|
<div
|
||||||
|
class="input-info flex gaps"
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="NoItems flex box grow"
|
class="items box grow flex column"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="box center"
|
class="Table flex column HelmCharts box grow dark selectable scrollable sortable autoSize virtual"
|
||||||
>
|
>
|
||||||
Item list is empty
|
<div
|
||||||
|
class="TableHead sticky nowrap topLine"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="TableCell icon nowrap"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="TableCell name nowrap sorting"
|
||||||
|
id="name"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
>
|
||||||
|
Name
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon sortIcon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_drop_down"
|
||||||
|
>
|
||||||
|
arrow_drop_down
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="TableCell description nowrap"
|
||||||
|
id="description"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
>
|
||||||
|
Description
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="TableCell version nowrap"
|
||||||
|
id="version"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
>
|
||||||
|
Version
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="TableCell app-version nowrap"
|
||||||
|
id="app-version"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
>
|
||||||
|
App Version
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="TableCell repository nowrap sorting"
|
||||||
|
id="repo"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
>
|
||||||
|
Repository
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon sortIcon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_drop_down"
|
||||||
|
>
|
||||||
|
arrow_drop_down
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="TableCell menu nowrap"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="content"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
id="menu_actions_27"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="more_vert"
|
||||||
|
>
|
||||||
|
more_vert
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="NoItems flex box grow"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="box center"
|
||||||
|
>
|
||||||
|
Item list is empty
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="AddRemoveButtons flex gaps"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="footer"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="Dock"
|
||||||
|
tabindex="-1"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="ResizingAnchor vertical leading"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="tabs-container flex align-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="dockTabs"
|
||||||
|
role="tablist"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="Tabs tabs"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="Tab flex gaps align-center DockTab TerminalTab active"
|
||||||
|
id="tab-terminal"
|
||||||
|
role="tab"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="terminal"
|
||||||
|
>
|
||||||
|
terminal
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="label"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
class="flex align-center"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="title"
|
||||||
|
>
|
||||||
|
Terminal
|
||||||
|
</span>
|
||||||
|
<div
|
||||||
|
class="close"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable small"
|
||||||
|
id="tooltip_target_13"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="close"
|
||||||
|
>
|
||||||
|
close
|
||||||
|
</span>
|
||||||
|
<div />
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="AddRemoveButtons flex gaps"
|
class="toolbar flex gaps align-center box grow"
|
||||||
/>
|
>
|
||||||
|
<div
|
||||||
|
class="dock-menu box grow"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon new-dock-tab material interactive focusable"
|
||||||
|
id="menu_actions_14"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="add"
|
||||||
|
>
|
||||||
|
add
|
||||||
|
</span>
|
||||||
|
<div />
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
id="tooltip_target_16"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="fullscreen"
|
||||||
|
>
|
||||||
|
fullscreen
|
||||||
|
</span>
|
||||||
|
<div />
|
||||||
|
</i>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
id="tooltip_target_17"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="keyboard_arrow_up"
|
||||||
|
>
|
||||||
|
keyboard_arrow_up
|
||||||
|
</span>
|
||||||
|
<div />
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</main>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
|
||||||
class="Notifications flex column align-flex-end"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -4,115 +4,250 @@ exports[`status-bar-items-originating-from-extensions when application starts wh
|
|||||||
<body>
|
<body>
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
class="topBar"
|
class="ClusterManager"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="topBar"
|
||||||
>
|
>
|
||||||
<i
|
<div
|
||||||
class="Icon material interactive focusable"
|
class="items"
|
||||||
data-testid="home-button"
|
|
||||||
tabindex="0"
|
|
||||||
>
|
>
|
||||||
<span
|
<i
|
||||||
class="icon"
|
class="Icon material interactive focusable"
|
||||||
data-icon-name="home"
|
data-testid="home-button"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
home
|
<span
|
||||||
</span>
|
class="icon"
|
||||||
</i>
|
data-icon-name="home"
|
||||||
<i
|
>
|
||||||
class="Icon material interactive disabled focusable"
|
home
|
||||||
data-testid="history-back"
|
</span>
|
||||||
>
|
</i>
|
||||||
<span
|
<i
|
||||||
class="icon"
|
class="Icon material interactive disabled focusable"
|
||||||
data-icon-name="arrow_back"
|
data-testid="history-back"
|
||||||
>
|
>
|
||||||
arrow_back
|
<span
|
||||||
</span>
|
class="icon"
|
||||||
</i>
|
data-icon-name="arrow_back"
|
||||||
<i
|
>
|
||||||
class="Icon material interactive disabled focusable"
|
arrow_back
|
||||||
data-testid="history-forward"
|
</span>
|
||||||
>
|
</i>
|
||||||
<span
|
<i
|
||||||
class="icon"
|
class="Icon material interactive disabled focusable"
|
||||||
data-icon-name="arrow_forward"
|
data-testid="history-forward"
|
||||||
>
|
>
|
||||||
arrow_forward
|
<span
|
||||||
</span>
|
class="icon"
|
||||||
</i>
|
data-icon-name="arrow_forward"
|
||||||
|
>
|
||||||
|
arrow_forward
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="items"
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
<main>
|
||||||
|
<div
|
||||||
|
id="lens-views"
|
||||||
|
/>
|
||||||
|
<div
|
||||||
|
class="flex justify-center Welcome align-center"
|
||||||
|
data-testid="welcome-page"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-banner-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon logo svg focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
</i>
|
||||||
|
<div
|
||||||
|
class="flex justify-center"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="welcome-text-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<h2>
|
||||||
|
Welcome to OpenLens 5!
|
||||||
|
</h2>
|
||||||
|
<p>
|
||||||
|
To get you started we have auto-detected your clusters in your
|
||||||
|
|
||||||
|
kubeconfig file and added them to the catalog, your centralized
|
||||||
|
|
||||||
|
view for managing all your cloud-native resources.
|
||||||
|
<br />
|
||||||
|
<br />
|
||||||
|
If you have any questions or feedback, please join our
|
||||||
|
<a
|
||||||
|
class="link"
|
||||||
|
href="https://join.slack.com/t/k8slens/shared_invite/zt-wcl8jq3k-68R5Wcmk1o95MLBE5igUDQ"
|
||||||
|
rel="noreferrer"
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
Lens Community slack channel
|
||||||
|
</a>
|
||||||
|
.
|
||||||
|
</p>
|
||||||
|
<ul
|
||||||
|
class="block"
|
||||||
|
data-testid="welcome-menu-container"
|
||||||
|
style="width: 320px;"
|
||||||
|
>
|
||||||
|
<li
|
||||||
|
class="flex grid-12"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="view_list"
|
||||||
|
>
|
||||||
|
view_list
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
<a
|
||||||
|
class="box col-10"
|
||||||
|
>
|
||||||
|
Browse Clusters in Catalog
|
||||||
|
</a>
|
||||||
|
<i
|
||||||
|
class="Icon box col-1 material focusable"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="navigate_next"
|
||||||
|
>
|
||||||
|
navigate_next
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
<div
|
<div
|
||||||
class="items"
|
class="HotbarMenu flex column"
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
class="StatusBar"
|
|
||||||
>
|
|
||||||
<div
|
|
||||||
class="leftSide"
|
|
||||||
data-testid="status-bar-left"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="HotbarItems flex column gaps"
|
||||||
>
|
/>
|
||||||
<div
|
|
||||||
data-testid="app-update-not-available"
|
|
||||||
>
|
|
||||||
No new updates available
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="HotbarSelector"
|
||||||
>
|
>
|
||||||
<div
|
<i
|
||||||
data-testid="some-testId"
|
class="Icon Icon previous material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
>
|
>
|
||||||
left1
|
<span
|
||||||
</div>
|
class="icon"
|
||||||
</div>
|
data-icon-name="arrow_left"
|
||||||
<div
|
>
|
||||||
class="item"
|
arrow_left
|
||||||
>
|
</span>
|
||||||
|
</i>
|
||||||
<div
|
<div
|
||||||
data-testid="some-testId"
|
class="HotbarIndex"
|
||||||
>
|
>
|
||||||
left2
|
<div
|
||||||
|
class="badge Badge small clickable"
|
||||||
|
id="hotbarIndex"
|
||||||
|
>
|
||||||
|
0
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<i
|
||||||
|
class="Icon material interactive focusable"
|
||||||
|
tabindex="0"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
class="icon"
|
||||||
|
data-icon-name="arrow_right"
|
||||||
|
>
|
||||||
|
arrow_right
|
||||||
|
</span>
|
||||||
|
</i>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="rightSide"
|
class="StatusBar"
|
||||||
data-testid="status-bar-right"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="leftSide"
|
||||||
|
data-testid="status-bar-left"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
data-testid="some-testId"
|
class="item"
|
||||||
>
|
>
|
||||||
right3
|
<div
|
||||||
|
data-testid="app-update-not-available"
|
||||||
|
>
|
||||||
|
No new updates available
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="some-testId"
|
||||||
|
>
|
||||||
|
left1
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<div
|
||||||
|
data-testid="some-testId"
|
||||||
|
>
|
||||||
|
left2
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="item"
|
class="rightSide"
|
||||||
|
data-testid="status-bar-right"
|
||||||
>
|
>
|
||||||
<span
|
<div
|
||||||
data-testid="some-testId"
|
class="item"
|
||||||
>
|
>
|
||||||
right2
|
<div
|
||||||
</span>
|
data-testid="some-testId"
|
||||||
</div>
|
>
|
||||||
<div
|
right3
|
||||||
class="item"
|
</div>
|
||||||
>
|
</div>
|
||||||
<span
|
<div
|
||||||
data-testid="some-testId"
|
class="item"
|
||||||
>
|
>
|
||||||
right1
|
<span
|
||||||
</span>
|
data-testid="some-testId"
|
||||||
|
>
|
||||||
|
right2
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="item"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
data-testid="some-testId"
|
||||||
|
>
|
||||||
|
right1
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@ -21,25 +21,41 @@ describe("welcome - navigation using application menu", () => {
|
|||||||
expect(rendered.container).toMatchSnapshot();
|
expect(rendered.container).toMatchSnapshot();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("does not show welcome page yet", () => {
|
it("shows welcome page being front page", () => {
|
||||||
const actual = rendered.queryByTestId("welcome-page");
|
const actual = rendered.getByTestId("welcome-page");
|
||||||
|
|
||||||
expect(actual).toBeNull();
|
expect(actual).not.toBeNull();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("when navigating to welcome using application menu", () => {
|
describe("when navigated somewhere else", () => {
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
applicationBuilder.applicationMenu.click("help.welcome");
|
applicationBuilder.applicationMenu.click("root.preferences");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("renders", () => {
|
it("renders", () => {
|
||||||
expect(rendered.container).toMatchSnapshot();
|
expect(rendered.baseElement).toMatchSnapshot();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("shows welcome page", () => {
|
it("does not show welcome page", () => {
|
||||||
const actual = rendered.getByTestId("welcome-page");
|
const actual = rendered.queryByTestId("welcome-page");
|
||||||
|
|
||||||
expect(actual).not.toBeNull();
|
expect(actual).toBeNull();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("when navigated to welcome using application menu", () => {
|
||||||
|
beforeEach(() => {
|
||||||
|
applicationBuilder.applicationMenu.click("help.welcome");
|
||||||
|
});
|
||||||
|
|
||||||
|
it("renders", () => {
|
||||||
|
expect(rendered.container).toMatchSnapshot();
|
||||||
|
});
|
||||||
|
|
||||||
|
it("shows welcome page", () => {
|
||||||
|
const actual = rendered.getByTestId("welcome-page");
|
||||||
|
|
||||||
|
expect(actual).not.toBeNull();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@ -4,7 +4,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import glob from "glob";
|
import glob from "glob";
|
||||||
import { kebabCase, memoize, noop } from "lodash/fp";
|
import { kebabCase, memoize, noop, chunk } from "lodash/fp";
|
||||||
import type { DiContainer, Injectable } from "@ogre-tools/injectable";
|
import type { DiContainer, Injectable } from "@ogre-tools/injectable";
|
||||||
import { createContainer } from "@ogre-tools/injectable";
|
import { createContainer } from "@ogre-tools/injectable";
|
||||||
import { Environments, setLegacyGlobalDiForExtensionApi } from "../extensions/as-legacy-globals-for-extension-api/legacy-global-di-for-extension-api";
|
import { Environments, setLegacyGlobalDiForExtensionApi } from "../extensions/as-legacy-globals-for-extension-api/legacy-global-di-for-extension-api";
|
||||||
@ -99,6 +99,7 @@ import updateHelmReleaseInjectable from "./helm/helm-service/update-helm-release
|
|||||||
import waitUntilBundledExtensionsAreLoadedInjectable from "./start-main-application/lens-window/application-window/wait-until-bundled-extensions-are-loaded.injectable";
|
import waitUntilBundledExtensionsAreLoadedInjectable from "./start-main-application/lens-window/application-window/wait-until-bundled-extensions-are-loaded.injectable";
|
||||||
import { registerMobX } from "@ogre-tools/injectable-extension-for-mobx";
|
import { registerMobX } from "@ogre-tools/injectable-extension-for-mobx";
|
||||||
import electronInjectable from "./utils/resolve-system-proxy/electron.injectable";
|
import electronInjectable from "./utils/resolve-system-proxy/electron.injectable";
|
||||||
|
import type { HotbarStore } from "../common/hotbars/store";
|
||||||
|
|
||||||
export function getDiForUnitTesting(opts: { doGeneralOverrides?: boolean } = {}) {
|
export function getDiForUnitTesting(opts: { doGeneralOverrides?: boolean } = {}) {
|
||||||
const {
|
const {
|
||||||
@ -111,15 +112,13 @@ export function getDiForUnitTesting(opts: { doGeneralOverrides?: boolean } = {})
|
|||||||
|
|
||||||
setLegacyGlobalDiForExtensionApi(di, Environments.main);
|
setLegacyGlobalDiForExtensionApi(di, Environments.main);
|
||||||
|
|
||||||
for (const filePath of getInjectableFilePaths()) {
|
const filePaths = getInjectableFilePaths();
|
||||||
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
||||||
const injectableInstance = require(filePath).default;
|
|
||||||
|
|
||||||
di.register({
|
const injectables = filePaths.map(filePath => require(filePath).default);
|
||||||
...injectableInstance,
|
|
||||||
aliases: [injectableInstance, ...(injectableInstance.aliases || [])],
|
chunk(100)(injectables).forEach(chunkInjectables => {
|
||||||
});
|
di.register(...chunkInjectables);
|
||||||
}
|
});
|
||||||
|
|
||||||
di.preventSideEffects();
|
di.preventSideEffects();
|
||||||
|
|
||||||
@ -127,7 +126,13 @@ export function getDiForUnitTesting(opts: { doGeneralOverrides?: boolean } = {})
|
|||||||
di.override(electronInjectable, () => ({}));
|
di.override(electronInjectable, () => ({}));
|
||||||
di.override(waitUntilBundledExtensionsAreLoadedInjectable, () => async () => {});
|
di.override(waitUntilBundledExtensionsAreLoadedInjectable, () => async () => {});
|
||||||
di.override(getRandomIdInjectable, () => () => "some-irrelevant-random-id");
|
di.override(getRandomIdInjectable, () => () => "some-irrelevant-random-id");
|
||||||
di.override(hotbarStoreInjectable, () => ({ load: () => {} }));
|
|
||||||
|
di.override(hotbarStoreInjectable, () => ({
|
||||||
|
load: () => {},
|
||||||
|
getActive: () => ({ name: "some-hotbar", items: [] }),
|
||||||
|
getDisplayIndex: () => "0",
|
||||||
|
}) as unknown as HotbarStore);
|
||||||
|
|
||||||
di.override(userStoreInjectable, () => ({ startMainReactions: () => {}, extensionRegistryUrl: { customUrl: "some-custom-url" }}) as UserStore);
|
di.override(userStoreInjectable, () => ({ startMainReactions: () => {}, extensionRegistryUrl: { customUrl: "some-custom-url" }}) as UserStore);
|
||||||
di.override(extensionsStoreInjectable, () => ({ isEnabled: (opts) => (void opts, false) }) as ExtensionsStore);
|
di.override(extensionsStoreInjectable, () => ({ isEnabled: (opts) => (void opts, false) }) as ExtensionsStore);
|
||||||
di.override(clusterStoreInjectable, () => ({ provideInitialFromMain: () => {}, getById: (id) => (void id, {}) as Cluster }) as ClusterStore);
|
di.override(clusterStoreInjectable, () => ({ provideInitialFromMain: () => {}, getById: (id) => (void id, {}) as Cluster }) as ClusterStore);
|
||||||
|
|||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { CronJobTriggerDialog } from "./cronjob-trigger-dialog";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const cronJobTriggerDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "cron-job-trigger-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "cron-job-trigger-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: CronJobTriggerDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default cronJobTriggerDialogClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { DeploymentScaleDialog } from "./dialog";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const deploymentScaleDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "deployment-scale-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "deployment-scale-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: DeploymentScaleDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default deploymentScaleDialogClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
import { ReplicaSetScaleDialog } from "./dialog";
|
||||||
|
|
||||||
|
const replicasetScaleDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "replicaset-scale-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "replicaset-scale-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: ReplicaSetScaleDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default replicasetScaleDialogClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { StatefulSetScaleDialog } from "./dialog";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const statefulsetScaleDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "statefulset-scale-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "statefulset-scale-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: StatefulSetScaleDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default statefulsetScaleDialogClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,30 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import React from "react";
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { rootFrameChildComponentInjectionToken } from "../../frames/root-frame/root-frame-child-component-injection-token";
|
||||||
|
import { ClusterManager } from "./cluster-manager";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { ErrorBoundary } from "../error-boundary";
|
||||||
|
|
||||||
|
const clusterManagerRootFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "cluster-manager-root-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "cluster-manager",
|
||||||
|
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
|
||||||
|
Component: () => (
|
||||||
|
<ErrorBoundary>
|
||||||
|
<ClusterManager />
|
||||||
|
</ErrorBoundary>
|
||||||
|
),
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: rootFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default clusterManagerRootFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { CommandContainer } from "./command-container";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const commandContainerClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "command-container-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "command-container",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: CommandContainer,
|
||||||
|
}),
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default commandContainerClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { rootFrameChildComponentInjectionToken } from "../../frames/root-frame/root-frame-child-component-injection-token";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { CommandContainer } from "./command-container";
|
||||||
|
|
||||||
|
const commandContainerRootFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "command-container-root-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "command-container",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: CommandContainer,
|
||||||
|
}),
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
|
||||||
|
injectionToken: rootFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default commandContainerRootFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,22 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { ConfirmDialog } from "./confirm-dialog";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const confirmDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "confirm-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "confirm-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: ConfirmDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default confirmDialogClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,22 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { rootFrameChildComponentInjectionToken } from "../../frames/root-frame/root-frame-child-component-injection-token";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { ConfirmDialog } from "./confirm-dialog";
|
||||||
|
|
||||||
|
const confirmDialogRootFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "confirm-dialog-root-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "confirm-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: ConfirmDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: rootFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default confirmDialogRootFrameChildComponentInjectable;
|
||||||
@ -7,9 +7,7 @@ import { KubeConfig } from "@kubernetes/client-node";
|
|||||||
import { fireEvent } from "@testing-library/react";
|
import { fireEvent } from "@testing-library/react";
|
||||||
import type { RenderResult } from "@testing-library/react";
|
import type { RenderResult } from "@testing-library/react";
|
||||||
import mockFs from "mock-fs";
|
import mockFs from "mock-fs";
|
||||||
import React from "react";
|
|
||||||
import * as selectEvent from "react-select-event";
|
import * as selectEvent from "react-select-event";
|
||||||
import { DeleteClusterDialog } from "../view";
|
|
||||||
import type { CreateCluster } from "../../../../common/cluster/create-cluster-injection-token";
|
import type { CreateCluster } from "../../../../common/cluster/create-cluster-injection-token";
|
||||||
import { createClusterInjectionToken } from "../../../../common/cluster/create-cluster-injection-token";
|
import { createClusterInjectionToken } from "../../../../common/cluster/create-cluster-injection-token";
|
||||||
import createContextHandlerInjectable from "../../../../main/context-handler/create-context-handler.injectable";
|
import createContextHandlerInjectable from "../../../../main/context-handler/create-context-handler.injectable";
|
||||||
@ -19,12 +17,6 @@ import storesAndApisCanBeCreatedInjectable from "../../../stores-apis-can-be-cre
|
|||||||
import createKubeconfigManagerInjectable from "../../../../main/kubeconfig-manager/create-kubeconfig-manager.injectable";
|
import createKubeconfigManagerInjectable from "../../../../main/kubeconfig-manager/create-kubeconfig-manager.injectable";
|
||||||
import type { ApplicationBuilder } from "../../test-utils/get-application-builder";
|
import type { ApplicationBuilder } from "../../test-utils/get-application-builder";
|
||||||
import { getApplicationBuilder } from "../../test-utils/get-application-builder";
|
import { getApplicationBuilder } from "../../test-utils/get-application-builder";
|
||||||
import { frontEndRouteInjectionToken } from "../../../../common/front-end-routing/front-end-route-injection-token";
|
|
||||||
import { getInjectable } from "@ogre-tools/injectable";
|
|
||||||
import { computed } from "mobx";
|
|
||||||
import { routeSpecificComponentInjectionToken } from "../../../routes/route-specific-component-injection-token";
|
|
||||||
import { navigateToRouteInjectionToken } from "../../../../common/front-end-routing/navigate-to-route-injection-token";
|
|
||||||
import hotbarStoreInjectable from "../../../../common/hotbars/store.injectable";
|
|
||||||
import normalizedPlatformInjectable from "../../../../common/vars/normalized-platform.injectable";
|
import normalizedPlatformInjectable from "../../../../common/vars/normalized-platform.injectable";
|
||||||
import kubectlBinaryNameInjectable from "../../../../main/kubectl/binary-name.injectable";
|
import kubectlBinaryNameInjectable from "../../../../main/kubectl/binary-name.injectable";
|
||||||
import kubectlDownloadingNormalizedArchInjectable from "../../../../main/kubectl/normalized-arch.injectable";
|
import kubectlDownloadingNormalizedArchInjectable from "../../../../main/kubectl/normalized-arch.injectable";
|
||||||
@ -111,22 +103,9 @@ describe("<DeleteClusterDialog />", () => {
|
|||||||
mainDi.override(kubectlBinaryNameInjectable, () => "kubectl");
|
mainDi.override(kubectlBinaryNameInjectable, () => "kubectl");
|
||||||
mainDi.override(kubectlDownloadingNormalizedArchInjectable, () => "amd64");
|
mainDi.override(kubectlDownloadingNormalizedArchInjectable, () => "amd64");
|
||||||
mainDi.override(normalizedPlatformInjectable, () => "darwin");
|
mainDi.override(normalizedPlatformInjectable, () => "darwin");
|
||||||
|
|
||||||
rendererDi.override(hotbarStoreInjectable, () => ({}));
|
|
||||||
rendererDi.override(storesAndApisCanBeCreatedInjectable, () => true);
|
rendererDi.override(storesAndApisCanBeCreatedInjectable, () => true);
|
||||||
});
|
});
|
||||||
|
|
||||||
const { rendererDi } = applicationBuilder.dis;
|
|
||||||
|
|
||||||
rendererDi.register(testRouteInjectable, testRouteComponentInjectable);
|
|
||||||
|
|
||||||
applicationBuilder.beforeRender(({ rendererDi }) => {
|
|
||||||
const navigateToRoute = rendererDi.inject(navigateToRouteInjectionToken);
|
|
||||||
const testRoute = rendererDi.inject(testRouteInjectable);
|
|
||||||
|
|
||||||
navigateToRoute(testRoute);
|
|
||||||
});
|
|
||||||
|
|
||||||
mockFs();
|
mockFs();
|
||||||
|
|
||||||
applicationBuilder.beforeRender(({ rendererDi }) => {
|
applicationBuilder.beforeRender(({ rendererDi }) => {
|
||||||
@ -321,26 +300,3 @@ describe("<DeleteClusterDialog />", () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
const testRouteInjectable = getInjectable({
|
|
||||||
id: "some-test-route",
|
|
||||||
|
|
||||||
instantiate: () => ({
|
|
||||||
path: "/some-test-path",
|
|
||||||
clusterFrame: false,
|
|
||||||
isEnabled: computed(() => true),
|
|
||||||
}),
|
|
||||||
|
|
||||||
injectionToken: frontEndRouteInjectionToken,
|
|
||||||
});
|
|
||||||
|
|
||||||
const testRouteComponentInjectable = getInjectable({
|
|
||||||
id: "some-test-component",
|
|
||||||
|
|
||||||
instantiate: (di) => ({
|
|
||||||
route: di.inject(testRouteInjectable),
|
|
||||||
Component: () => <DeleteClusterDialog />,
|
|
||||||
}),
|
|
||||||
|
|
||||||
injectionToken: routeSpecificComponentInjectionToken,
|
|
||||||
});
|
|
||||||
|
|||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { DeleteClusterDialog } from "./view";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const deleteClusterDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "delete-cluster-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "delete-cluster-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: DeleteClusterDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default deleteClusterDialogClusterFrameChildComponentInjectable;
|
||||||
@ -14,10 +14,10 @@ import { Tab } from "../tabs";
|
|||||||
import { Icon } from "../icon";
|
import { Icon } from "../icon";
|
||||||
import { Menu, MenuItem } from "../menu";
|
import { Menu, MenuItem } from "../menu";
|
||||||
import { observable } from "mobx";
|
import { observable } from "mobx";
|
||||||
import { isMac } from "../../../common/vars";
|
|
||||||
import { withInjectables } from "@ogre-tools/injectable-react";
|
import { withInjectables } from "@ogre-tools/injectable-react";
|
||||||
import dockStoreInjectable from "./dock/store.injectable";
|
import dockStoreInjectable from "./dock/store.injectable";
|
||||||
import { Tooltip, TooltipPosition } from "../tooltip";
|
import { Tooltip, TooltipPosition } from "../tooltip";
|
||||||
|
import isMacInjectable from "../../../common/vars/is-mac.injectable";
|
||||||
|
|
||||||
export interface DockTabProps extends TabProps<DockTabModel> {
|
export interface DockTabProps extends TabProps<DockTabModel> {
|
||||||
moreActions?: React.ReactNode;
|
moreActions?: React.ReactNode;
|
||||||
@ -25,6 +25,7 @@ export interface DockTabProps extends TabProps<DockTabModel> {
|
|||||||
|
|
||||||
interface Dependencies {
|
interface Dependencies {
|
||||||
dockStore: DockStore;
|
dockStore: DockStore;
|
||||||
|
isMac: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
@observer
|
@observer
|
||||||
@ -73,7 +74,7 @@ class NonInjectedDockTab extends React.Component<DockTabProps & Dependencies> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
const { className, moreActions, dockStore, active, ...tabProps } = this.props;
|
const { className, moreActions, dockStore, active, isMac, ...tabProps } = this.props;
|
||||||
|
|
||||||
if (!tabProps.value) {
|
if (!tabProps.value) {
|
||||||
return;
|
return;
|
||||||
@ -100,7 +101,7 @@ class NonInjectedDockTab extends React.Component<DockTabProps & Dependencies> {
|
|||||||
<Icon
|
<Icon
|
||||||
small
|
small
|
||||||
material="close"
|
material="close"
|
||||||
tooltip={`Close ${isMac ? "⌘+W" : "Ctrl+W"}`}
|
tooltip={`Close ${this.props.isMac ? "⌘+W" : "Ctrl+W"}`}
|
||||||
onClick={close}
|
onClick={close}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
@ -124,6 +125,7 @@ class NonInjectedDockTab extends React.Component<DockTabProps & Dependencies> {
|
|||||||
export const DockTab = withInjectables<Dependencies, DockTabProps>(NonInjectedDockTab, {
|
export const DockTab = withInjectables<Dependencies, DockTabProps>(NonInjectedDockTab, {
|
||||||
getProps: (di, props) => ({
|
getProps: (di, props) => ({
|
||||||
dockStore: di.inject(dockStoreInjectable),
|
dockStore: di.inject(dockStoreInjectable),
|
||||||
|
isMac: di.inject(isMacInjectable),
|
||||||
...props,
|
...props,
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
|
|||||||
@ -184,7 +184,9 @@ class NonInjectedHotbarMenu extends React.Component<Dependencies & HotbarMenuPro
|
|||||||
return (
|
return (
|
||||||
<div className={cssNames("HotbarMenu flex column", { draggingOver: this.draggingOver }, className)}>
|
<div className={cssNames("HotbarMenu flex column", { draggingOver: this.draggingOver }, className)}>
|
||||||
<div className="HotbarItems flex column gaps">
|
<div className="HotbarItems flex column gaps">
|
||||||
<DragDropContext onDragStart={() => this.onDragStart()} onDragEnd={(result) => this.onDragEnd(result)}>
|
<DragDropContext
|
||||||
|
onDragStart={() => this.onDragStart()}
|
||||||
|
onDragEnd={(result) => this.onDragEnd(result)}>
|
||||||
{this.renderGrid()}
|
{this.renderGrid()}
|
||||||
</DragDropContext>
|
</DragDropContext>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { KubeObjectDetails } from "./kube-object-details";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const kubeObjectDetailsClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "kube-object-details-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "kube-object-details",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: KubeObjectDetails,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default kubeObjectDetailsClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
import { KubeConfigDialog } from "./kubeconfig-dialog";
|
||||||
|
|
||||||
|
const kubeconfigDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "kubeconfig-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "kubeconfig-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: KubeConfigDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default kubeconfigDialogClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,22 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { Notifications } from "./notifications";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const notificationsClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "notifications-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "notifications",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: Notifications,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default notificationsClusterFrameChildComponentInjectable;
|
||||||
@ -0,0 +1,22 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { rootFrameChildComponentInjectionToken } from "../../frames/root-frame/root-frame-child-component-injection-token";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { Notifications } from "./notifications";
|
||||||
|
|
||||||
|
const notificationsRootFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "notifications-root-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "notifications",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: Notifications,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: rootFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default notificationsRootFrameChildComponentInjectable;
|
||||||
@ -7,21 +7,17 @@ import rendererExtensionsInjectable from "../../../extensions/renderer-extension
|
|||||||
import currentlyInClusterFrameInjectable from "../../routes/currently-in-cluster-frame.injectable";
|
import currentlyInClusterFrameInjectable from "../../routes/currently-in-cluster-frame.injectable";
|
||||||
import type { IObservableArray, ObservableSet } from "mobx";
|
import type { IObservableArray, ObservableSet } from "mobx";
|
||||||
import { computed, observable, runInAction } from "mobx";
|
import { computed, observable, runInAction } from "mobx";
|
||||||
import { renderFor } from "./renderFor";
|
|
||||||
import React from "react";
|
import React from "react";
|
||||||
import { Router } from "react-router";
|
import { Router } from "react-router";
|
||||||
import { Observer } from "mobx-react";
|
|
||||||
import subscribeStoresInjectable from "../../kube-watch-api/subscribe-stores.injectable";
|
import subscribeStoresInjectable from "../../kube-watch-api/subscribe-stores.injectable";
|
||||||
import allowedResourcesInjectable from "../../cluster-frame-context/allowed-resources.injectable";
|
import allowedResourcesInjectable from "../../cluster-frame-context/allowed-resources.injectable";
|
||||||
import type { RenderResult } from "@testing-library/react";
|
import type { RenderResult } from "@testing-library/react";
|
||||||
import { getByText, fireEvent } from "@testing-library/react";
|
import { getByText, fireEvent } from "@testing-library/react";
|
||||||
import type { KubeResource } from "../../../common/rbac";
|
import type { KubeResource } from "../../../common/rbac";
|
||||||
import { Sidebar } from "../layout/sidebar";
|
|
||||||
import type { DiContainer } from "@ogre-tools/injectable";
|
import type { DiContainer } from "@ogre-tools/injectable";
|
||||||
import clusterStoreInjectable from "../../../common/cluster-store/cluster-store.injectable";
|
import clusterStoreInjectable from "../../../common/cluster-store/cluster-store.injectable";
|
||||||
import type { ClusterStore } from "../../../common/cluster-store/cluster-store";
|
import type { ClusterStore } from "../../../common/cluster-store/cluster-store";
|
||||||
import mainExtensionsInjectable from "../../../extensions/main-extensions.injectable";
|
import mainExtensionsInjectable from "../../../extensions/main-extensions.injectable";
|
||||||
import currentRouteComponentInjectable from "../../routes/current-route-component.injectable";
|
|
||||||
import { pipeline } from "@ogre-tools/fp";
|
import { pipeline } from "@ogre-tools/fp";
|
||||||
import { flatMap, compact, join, get, filter, map, matches, last } from "lodash/fp";
|
import { flatMap, compact, join, get, filter, map, matches, last } from "lodash/fp";
|
||||||
import preferenceNavigationItemsInjectable from "../+preferences/preferences-navigation/preference-navigation-items.injectable";
|
import preferenceNavigationItemsInjectable from "../+preferences/preferences-navigation/preference-navigation-items.injectable";
|
||||||
@ -44,8 +40,6 @@ import historyInjectable from "../../navigation/history.injectable";
|
|||||||
import type { MinimalTrayMenuItem } from "../../../main/tray/electron-tray/electron-tray.injectable";
|
import type { MinimalTrayMenuItem } from "../../../main/tray/electron-tray/electron-tray.injectable";
|
||||||
import electronTrayInjectable from "../../../main/tray/electron-tray/electron-tray.injectable";
|
import electronTrayInjectable from "../../../main/tray/electron-tray/electron-tray.injectable";
|
||||||
import applicationWindowInjectable from "../../../main/start-main-application/lens-window/application-window/application-window.injectable";
|
import applicationWindowInjectable from "../../../main/start-main-application/lens-window/application-window/application-window.injectable";
|
||||||
import { Notifications } from "../notifications/notifications";
|
|
||||||
import broadcastThatRootFrameIsRenderedInjectable from "../../frames/root-frame/broadcast-that-root-frame-is-rendered.injectable";
|
|
||||||
import { getDiForUnitTesting as getRendererDi } from "../../getDiForUnitTesting";
|
import { getDiForUnitTesting as getRendererDi } from "../../getDiForUnitTesting";
|
||||||
import { getDiForUnitTesting as getMainDi } from "../../../main/getDiForUnitTesting";
|
import { getDiForUnitTesting as getMainDi } from "../../../main/getDiForUnitTesting";
|
||||||
import { overrideChannels } from "../../../test-utils/channel-fakes/override-channels";
|
import { overrideChannels } from "../../../test-utils/channel-fakes/override-channels";
|
||||||
@ -53,7 +47,6 @@ import trayIconPathsInjectable from "../../../main/tray/tray-icon-path.injectabl
|
|||||||
import assert from "assert";
|
import assert from "assert";
|
||||||
import { openMenu } from "react-select-event";
|
import { openMenu } from "react-select-event";
|
||||||
import userEvent from "@testing-library/user-event";
|
import userEvent from "@testing-library/user-event";
|
||||||
import { StatusBar } from "../status-bar/status-bar";
|
|
||||||
import lensProxyPortInjectable from "../../../main/lens-proxy/lens-proxy-port.injectable";
|
import lensProxyPortInjectable from "../../../main/lens-proxy/lens-proxy-port.injectable";
|
||||||
import type { Route } from "../../../common/front-end-routing/front-end-route-injection-token";
|
import type { Route } from "../../../common/front-end-routing/front-end-route-injection-token";
|
||||||
import type { NavigateToRouteOptions } from "../../../common/front-end-routing/navigate-to-route-injection-token";
|
import type { NavigateToRouteOptions } from "../../../common/front-end-routing/navigate-to-route-injection-token";
|
||||||
@ -62,7 +55,10 @@ import type { LensMainExtension } from "../../../extensions/lens-main-extension"
|
|||||||
import type { LensExtension } from "../../../extensions/lens-extension";
|
import type { LensExtension } from "../../../extensions/lens-extension";
|
||||||
|
|
||||||
import extensionInjectable from "../../../extensions/extension-loader/extension/extension.injectable";
|
import extensionInjectable from "../../../extensions/extension-loader/extension/extension.injectable";
|
||||||
import { TopBar } from "../layout/top-bar/top-bar";
|
import { renderFor } from "./renderFor";
|
||||||
|
import { RootFrame } from "../../frames/root-frame/root-frame";
|
||||||
|
import { ClusterFrame } from "../../frames/cluster-frame/cluster-frame";
|
||||||
|
import hostedClusterIdInjectable from "../../cluster-frame-context/hosted-cluster-id.injectable";
|
||||||
|
|
||||||
type Callback = (dis: DiContainers) => void | Promise<void>;
|
type Callback = (dis: DiContainers) => void | Promise<void>;
|
||||||
|
|
||||||
@ -125,10 +121,7 @@ interface DiContainers {
|
|||||||
}
|
}
|
||||||
|
|
||||||
interface Environment {
|
interface Environment {
|
||||||
renderSidebar: () => React.ReactNode;
|
RootComponent: React.ElementType;
|
||||||
renderTopBar: () => React.ReactNode;
|
|
||||||
renderStatusBar: () => React.ReactNode;
|
|
||||||
beforeRender: () => void;
|
|
||||||
onAllowKubeResource: () => void;
|
onAllowKubeResource: () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -166,17 +159,7 @@ export const getApplicationBuilder = () => {
|
|||||||
|
|
||||||
const environments = {
|
const environments = {
|
||||||
application: {
|
application: {
|
||||||
renderSidebar: () => null,
|
RootComponent: RootFrame,
|
||||||
|
|
||||||
renderTopBar: () => <TopBar />,
|
|
||||||
|
|
||||||
renderStatusBar: () => <StatusBar />,
|
|
||||||
|
|
||||||
beforeRender: () => {
|
|
||||||
const nofifyThatRootFrameIsRendered = rendererDi.inject(broadcastThatRootFrameIsRenderedInjectable);
|
|
||||||
|
|
||||||
nofifyThatRootFrameIsRendered();
|
|
||||||
},
|
|
||||||
|
|
||||||
onAllowKubeResource: () => {
|
onAllowKubeResource: () => {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
@ -186,10 +169,7 @@ export const getApplicationBuilder = () => {
|
|||||||
} as Environment,
|
} as Environment,
|
||||||
|
|
||||||
clusterFrame: {
|
clusterFrame: {
|
||||||
renderSidebar: () => <Sidebar />,
|
RootComponent: ClusterFrame,
|
||||||
renderStatusBar: () => null,
|
|
||||||
renderTopBar: () => null,
|
|
||||||
beforeRender: () => {},
|
|
||||||
onAllowKubeResource: () => {},
|
onAllowKubeResource: () => {},
|
||||||
} as Environment,
|
} as Environment,
|
||||||
};
|
};
|
||||||
@ -401,6 +381,7 @@ export const getApplicationBuilder = () => {
|
|||||||
|
|
||||||
const namespaceStoreStub = {
|
const namespaceStoreStub = {
|
||||||
contextNamespaces: [],
|
contextNamespaces: [],
|
||||||
|
items: [],
|
||||||
} as unknown as NamespaceStore;
|
} as unknown as NamespaceStore;
|
||||||
|
|
||||||
const clusterFrameContextFake = new ClusterFrameContext(
|
const clusterFrameContextFake = new ClusterFrameContext(
|
||||||
@ -413,6 +394,7 @@ export const getApplicationBuilder = () => {
|
|||||||
|
|
||||||
rendererDi.override(namespaceStoreInjectable, () => namespaceStoreStub);
|
rendererDi.override(namespaceStoreInjectable, () => namespaceStoreStub);
|
||||||
rendererDi.override(hostedClusterInjectable, () => clusterStub);
|
rendererDi.override(hostedClusterInjectable, () => clusterStub);
|
||||||
|
rendererDi.override(hostedClusterIdInjectable, () => "irrelevant-hosted-cluster-id");
|
||||||
rendererDi.override(clusterFrameContextInjectable, () => clusterFrameContextFake);
|
rendererDi.override(clusterFrameContextInjectable, () => clusterFrameContextFake);
|
||||||
|
|
||||||
// Todo: get rid of global state.
|
// Todo: get rid of global state.
|
||||||
@ -474,35 +456,17 @@ export const getApplicationBuilder = () => {
|
|||||||
|
|
||||||
await startFrame();
|
await startFrame();
|
||||||
|
|
||||||
const render = renderFor(rendererDi);
|
|
||||||
const history = rendererDi.inject(historyInjectable);
|
|
||||||
const currentRouteComponent = rendererDi.inject(currentRouteComponentInjectable);
|
|
||||||
|
|
||||||
for (const callback of beforeRenderCallbacks) {
|
for (const callback of beforeRenderCallbacks) {
|
||||||
await callback(dis);
|
await callback(dis);
|
||||||
}
|
}
|
||||||
|
|
||||||
environment.beforeRender();
|
const history = rendererDi.inject(historyInjectable);
|
||||||
|
|
||||||
|
const render = renderFor(rendererDi);
|
||||||
|
|
||||||
rendered = render(
|
rendered = render(
|
||||||
<Router history={history}>
|
<Router history={history}>
|
||||||
{environment.renderSidebar()}
|
<environment.RootComponent />
|
||||||
{environment.renderTopBar()}
|
|
||||||
{environment.renderStatusBar()}
|
|
||||||
|
|
||||||
<Observer>
|
|
||||||
{() => {
|
|
||||||
const Component = currentRouteComponent.get();
|
|
||||||
|
|
||||||
if (!Component) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return <Component />;
|
|
||||||
}}
|
|
||||||
</Observer>
|
|
||||||
|
|
||||||
<Notifications />
|
|
||||||
</Router>,
|
</Router>,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|||||||
@ -2,6 +2,9 @@
|
|||||||
|
|
||||||
exports[`<ClusterFrame /> given cluster with list nodes and namespaces permissions given no matching component given current url is starting url renders 1`] = `
|
exports[`<ClusterFrame /> given cluster with list nodes and namespaces permissions given no matching component given current url is starting url renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
|
<div
|
||||||
|
class="Notifications flex column align-flex-end"
|
||||||
|
/>
|
||||||
<div
|
<div
|
||||||
class="mainLayout"
|
class="mainLayout"
|
||||||
style="--sidebar-width: 200px;"
|
style="--sidebar-width: 200px;"
|
||||||
@ -467,14 +470,14 @@ exports[`<ClusterFrame /> given cluster with list nodes and namespaces permissio
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
|
||||||
class="Notifications flex column align-flex-end"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
exports[`<ClusterFrame /> given cluster with list nodes and namespaces permissions renders 1`] = `
|
exports[`<ClusterFrame /> given cluster with list nodes and namespaces permissions renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
|
<div
|
||||||
|
class="Notifications flex column align-flex-end"
|
||||||
|
/>
|
||||||
<div
|
<div
|
||||||
class="mainLayout"
|
class="mainLayout"
|
||||||
style="--sidebar-width: 200px;"
|
style="--sidebar-width: 200px;"
|
||||||
@ -947,14 +950,14 @@ exports[`<ClusterFrame /> given cluster with list nodes and namespaces permissio
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
|
||||||
class="Notifications flex column align-flex-end"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
exports[`<ClusterFrame /> given cluster without list nodes, but with namespaces permissions renders 1`] = `
|
exports[`<ClusterFrame /> given cluster without list nodes, but with namespaces permissions renders 1`] = `
|
||||||
<div>
|
<div>
|
||||||
|
<div
|
||||||
|
class="Notifications flex column align-flex-end"
|
||||||
|
/>
|
||||||
<div
|
<div
|
||||||
class="mainLayout"
|
class="mainLayout"
|
||||||
style="--sidebar-width: 200px;"
|
style="--sidebar-width: 200px;"
|
||||||
@ -1483,8 +1486,5 @@ exports[`<ClusterFrame /> given cluster without list nodes, but with namespaces
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
|
||||||
class="Notifications flex column align-flex-end"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|||||||
@ -0,0 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
|
||||||
|
import { getInjectionToken } from "@ogre-tools/injectable";
|
||||||
|
import type { IComputedValue } from "mobx";
|
||||||
|
|
||||||
|
export interface ClusterFrameChildComponent {
|
||||||
|
id: string;
|
||||||
|
Component: React.ElementType;
|
||||||
|
shouldRender: IComputedValue<boolean>;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const clusterFrameChildComponentInjectionToken = getInjectionToken<ClusterFrameChildComponent>({
|
||||||
|
id: "cluster-frame-child-component",
|
||||||
|
});
|
||||||
@ -0,0 +1,61 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import React from "react";
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "./cluster-frame-child-component-injection-token";
|
||||||
|
import { MainLayout } from "../../components/layout/main-layout";
|
||||||
|
import { Sidebar } from "../../components/layout/sidebar";
|
||||||
|
import { Dock } from "../../components/dock";
|
||||||
|
import styles from "./cluster-frame.module.css";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import currentRouteComponentInjectable from "../../routes/current-route-component.injectable";
|
||||||
|
import { Redirect } from "react-router";
|
||||||
|
import startUrlInjectable from "./start-url.injectable";
|
||||||
|
import currentPathInjectable from "../../routes/current-path.injectable";
|
||||||
|
import { observer } from "mobx-react";
|
||||||
|
|
||||||
|
const clusterFrameLayoutChildComponentInjectable = getInjectable({
|
||||||
|
id: "cluster-frame-layout-child-component",
|
||||||
|
|
||||||
|
instantiate: (di) => {
|
||||||
|
const currentRouteComponent = di.inject(currentRouteComponentInjectable);
|
||||||
|
const startUrl = di.inject(startUrlInjectable);
|
||||||
|
const currentPath = di.inject(currentPathInjectable);
|
||||||
|
|
||||||
|
return {
|
||||||
|
id: "cluster-frame-layout",
|
||||||
|
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
|
||||||
|
Component: observer(() => {
|
||||||
|
const Component = currentRouteComponent.get();
|
||||||
|
const starting = startUrl.get();
|
||||||
|
const current = currentPath.get();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<MainLayout sidebar={<Sidebar />} footer={<Dock />}>
|
||||||
|
{Component ? (
|
||||||
|
<Component />
|
||||||
|
) : // NOTE: this check is to prevent an infinite loop
|
||||||
|
starting !== current ? (
|
||||||
|
<Redirect to={startUrl.get()} />
|
||||||
|
) : (
|
||||||
|
<div className={styles.centering}>
|
||||||
|
<div className="error">
|
||||||
|
An error has occured. No route can be found matching the
|
||||||
|
current route, which is also the starting route.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</MainLayout>
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default clusterFrameLayoutChildComponentInjectable;
|
||||||
@ -2,52 +2,30 @@
|
|||||||
* Copyright (c) OpenLens Authors. All rights reserved.
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
* Licensed under MIT License. See LICENSE in root directory for more information.
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
*/
|
*/
|
||||||
import styles from "./cluster-frame.module.css";
|
|
||||||
import React, { useEffect } from "react";
|
import React, { useEffect } from "react";
|
||||||
import type { IComputedValue } from "mobx";
|
import { Observer, observer } from "mobx-react";
|
||||||
import { observer } from "mobx-react";
|
|
||||||
import { Redirect } from "react-router";
|
|
||||||
import { ConfirmDialog } from "../../components/confirm-dialog";
|
|
||||||
import { DeploymentScaleDialog } from "../../components/+workloads-deployments/scale/dialog";
|
|
||||||
import { CronJobTriggerDialog } from "../../components/+workloads-cronjobs/cronjob-trigger-dialog";
|
|
||||||
import { StatefulSetScaleDialog } from "../../components/+workloads-statefulsets/scale/dialog";
|
|
||||||
import { ReplicaSetScaleDialog } from "../../components/+workloads-replicasets/scale-dialog/dialog";
|
|
||||||
import { CommandContainer } from "../../components/command-palette/command-container";
|
|
||||||
import { ErrorBoundary } from "../../components/error-boundary";
|
import { ErrorBoundary } from "../../components/error-boundary";
|
||||||
import { MainLayout } from "../../components/layout/main-layout";
|
|
||||||
import { Notifications } from "../../components/notifications";
|
|
||||||
import { KubeObjectDetails } from "../../components/kube-object-details";
|
|
||||||
import { KubeConfigDialog } from "../../components/kubeconfig-dialog";
|
|
||||||
import { Sidebar } from "../../components/layout/sidebar";
|
|
||||||
import { Dock } from "../../components/dock";
|
|
||||||
import { PortForwardDialog } from "../../port-forward";
|
|
||||||
import { DeleteClusterDialog } from "../../components/delete-cluster-dialog";
|
|
||||||
import type { NamespaceStore } from "../../components/+namespaces/store";
|
import type { NamespaceStore } from "../../components/+namespaces/store";
|
||||||
import { withInjectables } from "@ogre-tools/injectable-react";
|
import { withInjectables } from "@ogre-tools/injectable-react";
|
||||||
import namespaceStoreInjectable from "../../components/+namespaces/store.injectable";
|
import namespaceStoreInjectable from "../../components/+namespaces/store.injectable";
|
||||||
import type { SubscribeStores } from "../../kube-watch-api/kube-watch-api";
|
import type { SubscribeStores } from "../../kube-watch-api/kube-watch-api";
|
||||||
import { disposer } from "../../utils";
|
import { disposer } from "../../utils";
|
||||||
import currentRouteComponentInjectable from "../../routes/current-route-component.injectable";
|
|
||||||
import startUrlInjectable from "./start-url.injectable";
|
|
||||||
import subscribeStoresInjectable from "../../kube-watch-api/subscribe-stores.injectable";
|
import subscribeStoresInjectable from "../../kube-watch-api/subscribe-stores.injectable";
|
||||||
import currentPathInjectable from "../../routes/current-path.injectable";
|
import type { ClusterFrameChildComponent } from "./cluster-frame-child-component-injection-token";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "./cluster-frame-child-component-injection-token";
|
||||||
import watchHistoryStateInjectable from "../../remote-helpers/watch-history-state.injectable";
|
import watchHistoryStateInjectable from "../../remote-helpers/watch-history-state.injectable";
|
||||||
|
|
||||||
interface Dependencies {
|
interface Dependencies {
|
||||||
namespaceStore: NamespaceStore;
|
namespaceStore: NamespaceStore;
|
||||||
currentRouteComponent: IComputedValue<React.ElementType<{}> | undefined>;
|
|
||||||
startUrl: IComputedValue<string>;
|
|
||||||
subscribeStores: SubscribeStores;
|
subscribeStores: SubscribeStores;
|
||||||
currentPath: IComputedValue<string>;
|
childComponents: ClusterFrameChildComponent[];
|
||||||
watchHistoryState: () => () => void;
|
watchHistoryState: () => () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const NonInjectedClusterFrame = observer(({
|
export const NonInjectedClusterFrame = observer(({
|
||||||
namespaceStore,
|
namespaceStore,
|
||||||
currentRouteComponent,
|
|
||||||
startUrl,
|
|
||||||
subscribeStores,
|
subscribeStores,
|
||||||
currentPath,
|
childComponents,
|
||||||
watchHistoryState,
|
watchHistoryState,
|
||||||
}: Dependencies) => {
|
}: Dependencies) => {
|
||||||
useEffect(() => disposer(
|
useEffect(() => disposer(
|
||||||
@ -57,43 +35,14 @@ export const NonInjectedClusterFrame = observer(({
|
|||||||
watchHistoryState(),
|
watchHistoryState(),
|
||||||
), []);
|
), []);
|
||||||
|
|
||||||
const Component = currentRouteComponent.get();
|
|
||||||
const starting = startUrl.get();
|
|
||||||
const current = currentPath.get();
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<ErrorBoundary>
|
<ErrorBoundary>
|
||||||
<MainLayout
|
{childComponents
|
||||||
sidebar={<Sidebar />}
|
.map((child) => (
|
||||||
footer={<Dock />}
|
<Observer key={child.id}>
|
||||||
>
|
{() => (child.shouldRender.get() ? <child.Component /> : null) }
|
||||||
{
|
</Observer>
|
||||||
Component
|
))}
|
||||||
? <Component />
|
|
||||||
// NOTE: this check is to prevent an infinite loop
|
|
||||||
: starting !== current
|
|
||||||
? <Redirect to={startUrl.get()} />
|
|
||||||
: (
|
|
||||||
<div className={styles.centering}>
|
|
||||||
<div className="error">
|
|
||||||
An error has occured. No route can be found matching the current route, which is also the starting route.
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
</MainLayout>
|
|
||||||
|
|
||||||
<Notifications />
|
|
||||||
<ConfirmDialog />
|
|
||||||
<KubeObjectDetails />
|
|
||||||
<KubeConfigDialog />
|
|
||||||
<DeploymentScaleDialog />
|
|
||||||
<StatefulSetScaleDialog />
|
|
||||||
<ReplicaSetScaleDialog />
|
|
||||||
<CronJobTriggerDialog />
|
|
||||||
<PortForwardDialog />
|
|
||||||
<DeleteClusterDialog />
|
|
||||||
<CommandContainer />
|
|
||||||
</ErrorBoundary>
|
</ErrorBoundary>
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
@ -102,9 +51,7 @@ export const ClusterFrame = withInjectables<Dependencies>(NonInjectedClusterFram
|
|||||||
getProps: di => ({
|
getProps: di => ({
|
||||||
namespaceStore: di.inject(namespaceStoreInjectable),
|
namespaceStore: di.inject(namespaceStoreInjectable),
|
||||||
subscribeStores: di.inject(subscribeStoresInjectable),
|
subscribeStores: di.inject(subscribeStoresInjectable),
|
||||||
startUrl: di.inject(startUrlInjectable),
|
childComponents: di.injectMany(clusterFrameChildComponentInjectionToken),
|
||||||
currentRouteComponent: di.inject(currentRouteComponentInjectable),
|
|
||||||
currentPath: di.inject(currentPathInjectable),
|
|
||||||
watchHistoryState: di.inject(watchHistoryStateInjectable),
|
watchHistoryState: di.inject(watchHistoryStateInjectable),
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
|
|||||||
@ -0,0 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
|
||||||
|
import { getInjectionToken } from "@ogre-tools/injectable";
|
||||||
|
import type { IComputedValue } from "mobx";
|
||||||
|
|
||||||
|
export interface RootFrameChildComponent {
|
||||||
|
id: string;
|
||||||
|
Component: React.ElementType;
|
||||||
|
shouldRender: IComputedValue<boolean>;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const rootFrameChildComponentInjectionToken = getInjectionToken<RootFrameChildComponent>({
|
||||||
|
id: "root-frame-child-component",
|
||||||
|
});
|
||||||
@ -3,25 +3,18 @@
|
|||||||
* Licensed under MIT License. See LICENSE in root directory for more information.
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { injectSystemCAs } from "../../../common/system-ca";
|
|
||||||
import React from "react";
|
import React from "react";
|
||||||
import { observer } from "mobx-react";
|
import { Observer } from "mobx-react";
|
||||||
import { ClusterManager } from "../../components/cluster-manager";
|
|
||||||
import { ErrorBoundary } from "../../components/error-boundary";
|
|
||||||
import { Notifications } from "../../components/notifications";
|
|
||||||
import { ConfirmDialog } from "../../components/confirm-dialog";
|
|
||||||
import { CommandContainer } from "../../components/command-palette/command-container";
|
|
||||||
import { withInjectables } from "@ogre-tools/injectable-react";
|
import { withInjectables } from "@ogre-tools/injectable-react";
|
||||||
import broadcastThatRootFrameIsRenderedInjectable from "./broadcast-that-root-frame-is-rendered.injectable";
|
import broadcastThatRootFrameIsRenderedInjectable from "./broadcast-that-root-frame-is-rendered.injectable";
|
||||||
|
import type { RootFrameChildComponent } from "./root-frame-child-component-injection-token";
|
||||||
// Todo: remove import-time side-effect.
|
import { rootFrameChildComponentInjectionToken } from "./root-frame-child-component-injection-token";
|
||||||
injectSystemCAs();
|
|
||||||
|
|
||||||
interface Dependencies {
|
interface Dependencies {
|
||||||
broadcastThatRootFrameIsRendered: () => void;
|
broadcastThatRootFrameIsRendered: () => void;
|
||||||
|
childComponents: RootFrameChildComponent[];
|
||||||
}
|
}
|
||||||
|
|
||||||
@observer
|
|
||||||
class NonInjectedRootFrame extends React.Component<Dependencies> {
|
class NonInjectedRootFrame extends React.Component<Dependencies> {
|
||||||
static displayName = "RootFrame";
|
static displayName = "RootFrame";
|
||||||
|
|
||||||
@ -32,12 +25,12 @@ class NonInjectedRootFrame extends React.Component<Dependencies> {
|
|||||||
render() {
|
render() {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<ErrorBoundary>
|
{this.props.childComponents
|
||||||
<ClusterManager />
|
.map((child) => (
|
||||||
</ErrorBoundary>
|
<Observer key={child.id}>
|
||||||
<Notifications />
|
{() => (child.shouldRender.get() ? <child.Component /> : null) }
|
||||||
<ConfirmDialog />
|
</Observer>
|
||||||
<CommandContainer />
|
))}
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -49,6 +42,7 @@ export const RootFrame = withInjectables<Dependencies>(
|
|||||||
{
|
{
|
||||||
getProps: (di, props) => ({
|
getProps: (di, props) => ({
|
||||||
broadcastThatRootFrameIsRendered: di.inject(broadcastThatRootFrameIsRenderedInjectable),
|
broadcastThatRootFrameIsRendered: di.inject(broadcastThatRootFrameIsRenderedInjectable),
|
||||||
|
childComponents: di.injectMany(rootFrameChildComponentInjectionToken),
|
||||||
...props,
|
...props,
|
||||||
}),
|
}),
|
||||||
},
|
},
|
||||||
|
|||||||
23
src/renderer/frames/root-frame/setup-system-ca.injectable.ts
Normal file
23
src/renderer/frames/root-frame/setup-system-ca.injectable.ts
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { injectSystemCAs } from "../../../common/system-ca";
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { beforeFrameStartsInjectionToken } from "../../before-frame-starts/before-frame-starts-injection-token";
|
||||||
|
|
||||||
|
const setupSystemCaInjectable = getInjectable({
|
||||||
|
id: "setup-system-ca",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
run: async () => {
|
||||||
|
await injectSystemCAs();
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
|
||||||
|
injectionToken: beforeFrameStartsInjectionToken,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default setupSystemCaInjectable;
|
||||||
@ -4,10 +4,8 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import glob from "glob";
|
import glob from "glob";
|
||||||
import { memoize, noop } from "lodash/fp";
|
import { memoize, noop, chunk } from "lodash/fp";
|
||||||
import type {
|
import type { DiContainer, Injectable } from "@ogre-tools/injectable";
|
||||||
DiContainer,
|
|
||||||
Injectable } from "@ogre-tools/injectable";
|
|
||||||
import {
|
import {
|
||||||
createContainer,
|
createContainer,
|
||||||
} from "@ogre-tools/injectable";
|
} from "@ogre-tools/injectable";
|
||||||
@ -41,7 +39,7 @@ import apiManagerInjectable from "../common/k8s-api/api-manager/manager.injectab
|
|||||||
import ipcRendererInjectable from "./utils/channel/ipc-renderer.injectable";
|
import ipcRendererInjectable from "./utils/channel/ipc-renderer.injectable";
|
||||||
import type { IpcRenderer } from "electron";
|
import type { IpcRenderer } from "electron";
|
||||||
import setupOnApiErrorListenersInjectable from "./api/setup-on-api-errors.injectable";
|
import setupOnApiErrorListenersInjectable from "./api/setup-on-api-errors.injectable";
|
||||||
import { observable } from "mobx";
|
import { observable, computed } from "mobx";
|
||||||
import defaultShellInjectable from "./components/+preferences/default-shell.injectable";
|
import defaultShellInjectable from "./components/+preferences/default-shell.injectable";
|
||||||
import appVersionInjectable from "../common/get-configuration-file-model/app-version/app-version.injectable";
|
import appVersionInjectable from "../common/get-configuration-file-model/app-version/app-version.injectable";
|
||||||
import provideInitialValuesForSyncBoxesInjectable from "./utils/sync-box/provide-initial-values-for-sync-boxes.injectable";
|
import provideInitialValuesForSyncBoxesInjectable from "./utils/sync-box/provide-initial-values-for-sync-boxes.injectable";
|
||||||
@ -59,6 +57,18 @@ import goForwardInjectable from "./components/layout/top-bar/go-forward.injectab
|
|||||||
import closeWindowInjectable from "./components/layout/top-bar/close-window.injectable";
|
import closeWindowInjectable from "./components/layout/top-bar/close-window.injectable";
|
||||||
import maximizeWindowInjectable from "./components/layout/top-bar/maximize-window.injectable";
|
import maximizeWindowInjectable from "./components/layout/top-bar/maximize-window.injectable";
|
||||||
import toggleMaximizeWindowInjectable from "./components/layout/top-bar/toggle-maximize-window.injectable";
|
import toggleMaximizeWindowInjectable from "./components/layout/top-bar/toggle-maximize-window.injectable";
|
||||||
|
import commandContainerRootFrameChildComponentInjectable from "./components/command-palette/command-container-root-frame-child-component.injectable";
|
||||||
|
import type { HotbarStore } from "../common/hotbars/store";
|
||||||
|
import commandContainerClusterFrameChildComponentInjectable from "./components/command-palette/command-container-cluster-frame-child-component.injectable";
|
||||||
|
import cronJobTriggerDialogClusterFrameChildComponentInjectable from "./components/+workloads-cronjobs/cron-job-trigger-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import deploymentScaleDialogClusterFrameChildComponentInjectable from "./components/+workloads-deployments/scale/deployment-scale-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import replicasetScaleDialogClusterFrameChildComponentInjectable from "./components/+workloads-replicasets/scale-dialog/replicaset-scale-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import statefulsetScaleDialogClusterFrameChildComponentInjectable from "./components/+workloads-statefulsets/scale/statefulset-scale-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import deleteClusterDialogClusterFrameChildComponentInjectable from "./components/delete-cluster-dialog/delete-cluster-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import kubeObjectDetailsClusterFrameChildComponentInjectable from "./components/kube-object-details/kube-object-details-cluster-frame-child-component.injectable";
|
||||||
|
import kubeconfigDialogClusterFrameChildComponentInjectable from "./components/kubeconfig-dialog/kubeconfig-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import portForwardDialogClusterFrameChildComponentInjectable from "./port-forward/port-forward-dialog-cluster-frame-child-component.injectable";
|
||||||
|
import setupSystemCaInjectable from "./frames/root-frame/setup-system-ca.injectable";
|
||||||
|
|
||||||
export const getDiForUnitTesting = (opts: { doGeneralOverrides?: boolean } = {}) => {
|
export const getDiForUnitTesting = (opts: { doGeneralOverrides?: boolean } = {}) => {
|
||||||
const {
|
const {
|
||||||
@ -71,14 +81,13 @@ export const getDiForUnitTesting = (opts: { doGeneralOverrides?: boolean } = {})
|
|||||||
|
|
||||||
setLegacyGlobalDiForExtensionApi(di, Environments.renderer);
|
setLegacyGlobalDiForExtensionApi(di, Environments.renderer);
|
||||||
|
|
||||||
for (const filePath of getInjectableFilePaths()) {
|
const filePaths = getInjectableFilePaths();
|
||||||
const injectableInstance = require(filePath).default;
|
|
||||||
|
|
||||||
di.register({
|
const injectables = filePaths.map(filePath => require(filePath).default);
|
||||||
...injectableInstance,
|
|
||||||
aliases: [injectableInstance, ...(injectableInstance.aliases || [])],
|
chunk(100)(injectables).forEach(chunkInjectables => {
|
||||||
});
|
di.register(...chunkInjectables);
|
||||||
}
|
});
|
||||||
|
|
||||||
di.preventSideEffects();
|
di.preventSideEffects();
|
||||||
|
|
||||||
@ -103,8 +112,35 @@ export const getDiForUnitTesting = (opts: { doGeneralOverrides?: boolean } = {})
|
|||||||
|
|
||||||
di.override(lensResourcesDirInjectable, () => "/irrelevant");
|
di.override(lensResourcesDirInjectable, () => "/irrelevant");
|
||||||
|
|
||||||
di.override(watchHistoryStateInjectable, () => () => () => {});
|
// TODO: Remove side-effects and shared global state
|
||||||
|
di.override(commandContainerRootFrameChildComponentInjectable, () => ({
|
||||||
|
Component: () => null,
|
||||||
|
id: "command-container",
|
||||||
|
shouldRender: computed(() => false),
|
||||||
|
}));
|
||||||
|
|
||||||
|
// TODO: Remove side-effects and shared global state
|
||||||
|
const clusterFrameChildComponentInjectables: Injectable<any, any, any>[] = [
|
||||||
|
commandContainerClusterFrameChildComponentInjectable,
|
||||||
|
cronJobTriggerDialogClusterFrameChildComponentInjectable,
|
||||||
|
deploymentScaleDialogClusterFrameChildComponentInjectable,
|
||||||
|
replicasetScaleDialogClusterFrameChildComponentInjectable,
|
||||||
|
statefulsetScaleDialogClusterFrameChildComponentInjectable,
|
||||||
|
deleteClusterDialogClusterFrameChildComponentInjectable,
|
||||||
|
kubeObjectDetailsClusterFrameChildComponentInjectable,
|
||||||
|
kubeconfigDialogClusterFrameChildComponentInjectable,
|
||||||
|
portForwardDialogClusterFrameChildComponentInjectable,
|
||||||
|
];
|
||||||
|
|
||||||
|
clusterFrameChildComponentInjectables.forEach((injectable) => {
|
||||||
|
di.override(injectable, () => ({
|
||||||
|
Component: () => null,
|
||||||
|
id: injectable.id,
|
||||||
|
shouldRender: computed(() => false),
|
||||||
|
}));
|
||||||
|
});
|
||||||
|
|
||||||
|
di.override(watchHistoryStateInjectable, () => () => () => {});
|
||||||
di.override(openAppContextMenuInjectable, () => () => {});
|
di.override(openAppContextMenuInjectable, () => () => {});
|
||||||
di.override(goBackInjectable, () => () => {});
|
di.override(goBackInjectable, () => () => {});
|
||||||
di.override(goForwardInjectable, () => () => {});
|
di.override(goForwardInjectable, () => () => {});
|
||||||
@ -126,13 +162,17 @@ export const getDiForUnitTesting = (opts: { doGeneralOverrides?: boolean } = {})
|
|||||||
// eslint-disable-next-line unused-imports/no-unused-vars-ts
|
// eslint-disable-next-line unused-imports/no-unused-vars-ts
|
||||||
di.override(extensionsStoreInjectable, () => ({ isEnabled: ({ id, isBundled }) => false }) as ExtensionsStore);
|
di.override(extensionsStoreInjectable, () => ({ isEnabled: ({ id, isBundled }) => false }) as ExtensionsStore);
|
||||||
|
|
||||||
di.override(hotbarStoreInjectable, () => ({}));
|
di.override(hotbarStoreInjectable, () => ({
|
||||||
|
getActive: () => ({ name: "some-hotbar", items: [] }),
|
||||||
|
getDisplayIndex: () => "0",
|
||||||
|
}) as unknown as HotbarStore);
|
||||||
|
|
||||||
di.override(fileSystemProvisionerStoreInjectable, () => ({}) as FileSystemProvisionerStore);
|
di.override(fileSystemProvisionerStoreInjectable, () => ({}) as FileSystemProvisionerStore);
|
||||||
|
|
||||||
// eslint-disable-next-line unused-imports/no-unused-vars-ts
|
// eslint-disable-next-line unused-imports/no-unused-vars-ts
|
||||||
di.override(clusterStoreInjectable, () => ({ getById: (id): Cluster => ({}) as Cluster }) as ClusterStore);
|
di.override(clusterStoreInjectable, () => ({ getById: (id): Cluster => ({}) as Cluster }) as ClusterStore);
|
||||||
|
|
||||||
|
di.override(setupSystemCaInjectable, () => ({ run: () => {} }));
|
||||||
di.override(setupOnApiErrorListenersInjectable, () => ({ run: () => {} }));
|
di.override(setupOnApiErrorListenersInjectable, () => ({ run: () => {} }));
|
||||||
di.override(provideInitialValuesForSyncBoxesInjectable, () => ({ run: () => {} }));
|
di.override(provideInitialValuesForSyncBoxesInjectable, () => ({ run: () => {} }));
|
||||||
|
|
||||||
|
|||||||
@ -0,0 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) OpenLens Authors. All rights reserved.
|
||||||
|
* Licensed under MIT License. See LICENSE in root directory for more information.
|
||||||
|
*/
|
||||||
|
import { getInjectable } from "@ogre-tools/injectable";
|
||||||
|
import { computed } from "mobx";
|
||||||
|
import { PortForwardDialog } from "./port-forward-dialog";
|
||||||
|
import { clusterFrameChildComponentInjectionToken } from "../frames/cluster-frame/cluster-frame-child-component-injection-token";
|
||||||
|
|
||||||
|
const portForwardDialogClusterFrameChildComponentInjectable = getInjectable({
|
||||||
|
id: "port-forward-dialog-cluster-frame-child-component",
|
||||||
|
|
||||||
|
instantiate: () => ({
|
||||||
|
id: "port-forward-dialog",
|
||||||
|
shouldRender: computed(() => true),
|
||||||
|
Component: PortForwardDialog,
|
||||||
|
}),
|
||||||
|
|
||||||
|
injectionToken: clusterFrameChildComponentInjectionToken,
|
||||||
|
|
||||||
|
causesSideEffects: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default portForwardDialogClusterFrameChildComponentInjectable;
|
||||||
54
yarn.lock
54
yarn.lock
@ -1211,46 +1211,46 @@
|
|||||||
"@nodelib/fs.scandir" "2.1.5"
|
"@nodelib/fs.scandir" "2.1.5"
|
||||||
fastq "^1.6.0"
|
fastq "^1.6.0"
|
||||||
|
|
||||||
"@ogre-tools/fp@9.0.0", "@ogre-tools/fp@^9.0.0":
|
"@ogre-tools/fp@9.0.1", "@ogre-tools/fp@^9.0.1":
|
||||||
version "9.0.0"
|
version "9.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/@ogre-tools/fp/-/fp-9.0.0.tgz#926cd4f13b52961156161feeeafddf22a0ad39c0"
|
resolved "https://registry.yarnpkg.com/@ogre-tools/fp/-/fp-9.0.1.tgz#22c23bd209f6f56bf66a5ff4514930334a3a4782"
|
||||||
integrity sha512-kMUgzhdjHuph0UWteOfyXNGBavZJX23NOA5su6fx9NdTzWhl9yB5Uf6Q//nOvL9COftjZDwnAgIaDU4MPdjyqA==
|
integrity sha512-7kORUcvR9DZz5/2qDSSKExGeisXzfmOafP+Z6l8C+WQXEmEQm7CmFMyBEyMkei0eNFzNghlKYgRFpsvBdU3KAg==
|
||||||
dependencies:
|
dependencies:
|
||||||
lodash "^4.17.21"
|
lodash "^4.17.21"
|
||||||
|
|
||||||
"@ogre-tools/injectable-extension-for-auto-registration@9.0.0":
|
"@ogre-tools/injectable-extension-for-auto-registration@9.0.1":
|
||||||
version "9.0.0"
|
version "9.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable-extension-for-auto-registration/-/injectable-extension-for-auto-registration-9.0.0.tgz#69463737ef4f7777db4703964b8a72a5fb82d6b3"
|
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable-extension-for-auto-registration/-/injectable-extension-for-auto-registration-9.0.1.tgz#e00dff5bd833068faa58d8fa514b218515c55775"
|
||||||
integrity sha512-+3I9Z0GfA04zZoj7Nw5WhJLDFLJgr5xv8Kp1zPDuT9/OvE9EA6hzAqakMDLbvn1zZOJjkJCGk44x6UjSQJp/9w==
|
integrity sha512-reyhW2wWPrNnGXo88QKWUsLyhjF195i0/iXfdAoR8/4lRxWmzka58bc8r6jFvTBBJ6eXaGidhUa5DqZe+Oia2Q==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@ogre-tools/fp" "^9.0.0"
|
"@ogre-tools/fp" "^9.0.1"
|
||||||
"@ogre-tools/injectable" "^9.0.0"
|
"@ogre-tools/injectable" "^9.0.1"
|
||||||
lodash "^4.17.21"
|
lodash "^4.17.21"
|
||||||
|
|
||||||
"@ogre-tools/injectable-extension-for-mobx@9.0.0":
|
"@ogre-tools/injectable-extension-for-mobx@9.0.1":
|
||||||
version "9.0.0"
|
version "9.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable-extension-for-mobx/-/injectable-extension-for-mobx-9.0.0.tgz#ed14df39b266e521272977821d3e05bcbd647577"
|
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable-extension-for-mobx/-/injectable-extension-for-mobx-9.0.1.tgz#3d9e6e119b7db5a4e4309e89ba6b301635c8da90"
|
||||||
integrity sha512-9Hrtr7AdibcD+Fqn2qNsjiOUakAACO55TB1IqNsOJMMuqQHVB5SFZTHBzdVRqqqY2MwQvWYvd4xfy+beItD/xw==
|
integrity sha512-wNHIG73NTGfmRb0b2nNhJD9ek4RcyBp/189KfrXhTt6/5KwMEuOeJjAbh8xwbhpYJnWFcMzWKLTqePozc+Ntww==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@ogre-tools/fp" "^9.0.0"
|
"@ogre-tools/fp" "^9.0.1"
|
||||||
"@ogre-tools/injectable" "^9.0.0"
|
"@ogre-tools/injectable" "^9.0.1"
|
||||||
lodash "^4.17.21"
|
lodash "^4.17.21"
|
||||||
|
|
||||||
"@ogre-tools/injectable-react@9.0.0":
|
"@ogre-tools/injectable-react@9.0.1":
|
||||||
version "9.0.0"
|
version "9.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable-react/-/injectable-react-9.0.0.tgz#c5c510e893a5c1d7994d8709f70606967cabdec2"
|
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable-react/-/injectable-react-9.0.1.tgz#d72a155b914873f1a5e35ee167aa14dd7c0e7454"
|
||||||
integrity sha512-vGQrwkcWibRUWFPbu392riBYY4dXK051FxwyMsDYNRqmvaLo8HuumwjzS1DWS7db/P9Li+Kc+Ms670xIZepcpA==
|
integrity sha512-GjkhhONy4hamw5Mx79ZxhL3Pbgnfnf1mrkixDkqlXFzhdPBHDtCYIZu9Y6NjSRLgEwXTrAPYv9lDqREnRbUwLA==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@ogre-tools/fp" "^9.0.0"
|
"@ogre-tools/fp" "^9.0.1"
|
||||||
"@ogre-tools/injectable" "^9.0.0"
|
"@ogre-tools/injectable" "^9.0.1"
|
||||||
lodash "^4.17.21"
|
lodash "^4.17.21"
|
||||||
|
|
||||||
"@ogre-tools/injectable@9.0.0", "@ogre-tools/injectable@^9.0.0":
|
"@ogre-tools/injectable@9.0.1", "@ogre-tools/injectable@^9.0.1":
|
||||||
version "9.0.0"
|
version "9.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable/-/injectable-9.0.0.tgz#0819bc7b5fbae0a467f3250b10b4adb003268067"
|
resolved "https://registry.yarnpkg.com/@ogre-tools/injectable/-/injectable-9.0.1.tgz#611a2dd8468bfe3610f005178837d76071a44a70"
|
||||||
integrity sha512-z9X86Q9AEkkilLu9V33j/aXv/IUoG944AdfN6WX2zZgJqRNjESN9spoOMqdKqib6JmEjCRxpMvaMwHLQSh14fg==
|
integrity sha512-orcERUOeUEP2oBAcr9rKYbik+r/xJEIb5uedPMMqPzPJnNwZ9JA/1rDEJcx1/I9aHgjUQpeFANjYI4eYDcwEYQ==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@ogre-tools/fp" "^9.0.0"
|
"@ogre-tools/fp" "^9.0.1"
|
||||||
lodash "^4.17.21"
|
lodash "^4.17.21"
|
||||||
|
|
||||||
"@panva/asn1.js@^1.0.0":
|
"@panva/asn1.js@^1.0.0":
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user