Security Tab for operator-ui (#804)
Security Tab allow users to set various configurations related to TLS certificates for MinIO and Console - Enable/Disable AutoCert - Add/Delete MinIO and Console Certificates - Add/Delete MinIO and Console CA Certificates Signed-off-by: Lenin Alevski <alevsk.8772@gmail.com>
This commit is contained in:
@@ -1,25 +1,25 @@
|
||||
{
|
||||
"files": {
|
||||
"main.css": "/static/css/main.8cfac526.chunk.css",
|
||||
"main.js": "/static/js/main.03b04a1b.chunk.js",
|
||||
"main.js.map": "/static/js/main.03b04a1b.chunk.js.map",
|
||||
"main.js": "/static/js/main.7915d40b.chunk.js",
|
||||
"main.js.map": "/static/js/main.7915d40b.chunk.js.map",
|
||||
"runtime-main.js": "/static/js/runtime-main.43a31377.js",
|
||||
"runtime-main.js.map": "/static/js/runtime-main.43a31377.js.map",
|
||||
"static/css/2.60e04a19.chunk.css": "/static/css/2.60e04a19.chunk.css",
|
||||
"static/js/2.d609c10f.chunk.js": "/static/js/2.d609c10f.chunk.js",
|
||||
"static/js/2.d609c10f.chunk.js.map": "/static/js/2.d609c10f.chunk.js.map",
|
||||
"static/js/2.06e58ba0.chunk.js": "/static/js/2.06e58ba0.chunk.js",
|
||||
"static/js/2.06e58ba0.chunk.js.map": "/static/js/2.06e58ba0.chunk.js.map",
|
||||
"index.html": "/index.html",
|
||||
"static/css/2.60e04a19.chunk.css.map": "/static/css/2.60e04a19.chunk.css.map",
|
||||
"static/css/main.8cfac526.chunk.css.map": "/static/css/main.8cfac526.chunk.css.map",
|
||||
"static/js/2.d609c10f.chunk.js.LICENSE.txt": "/static/js/2.d609c10f.chunk.js.LICENSE.txt",
|
||||
"static/js/2.06e58ba0.chunk.js.LICENSE.txt": "/static/js/2.06e58ba0.chunk.js.LICENSE.txt",
|
||||
"static/media/minio_console_logo.0837460e.svg": "/static/media/minio_console_logo.0837460e.svg",
|
||||
"static/media/minio_operator_logo.1312b7c9.svg": "/static/media/minio_operator_logo.1312b7c9.svg"
|
||||
},
|
||||
"entrypoints": [
|
||||
"static/js/runtime-main.43a31377.js",
|
||||
"static/css/2.60e04a19.chunk.css",
|
||||
"static/js/2.d609c10f.chunk.js",
|
||||
"static/js/2.06e58ba0.chunk.js",
|
||||
"static/css/main.8cfac526.chunk.css",
|
||||
"static/js/main.03b04a1b.chunk.js"
|
||||
"static/js/main.7915d40b.chunk.js"
|
||||
]
|
||||
}
|
||||
@@ -1 +1 @@
|
||||
<!doctype html><html lang="en"><head><meta charset="utf-8"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#000000"/><meta name="description" content="MinIO Console"/><link href="https://fonts.googleapis.com/css2?family=Lato:wght@400;500;700;900&display=swap" rel="stylesheet"/><link rel="apple-touch-icon" sizes="180x180" href="/apple-icon-180x180.png"/><link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png"/><link rel="icon" type="image/png" sizes="96x96" href="/favicon-96x96.png"/><link rel="icon" type="image/png" sizes="16x16" href="/favicon-16x16.png"/><link rel="manifest" href="/manifest.json"/><link rel="mask-icon" href="/safari-pinned-tab.svg" color="#3a4e54"/><title>MinIO Console</title><link href="/static/css/2.60e04a19.chunk.css" rel="stylesheet"><link href="/static/css/main.8cfac526.chunk.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div><script>!function(e){function r(r){for(var n,l,i=r[0],a=r[1],p=r[2],c=0,s=[];c<i.length;c++)l=i[c],Object.prototype.hasOwnProperty.call(o,l)&&o[l]&&s.push(o[l][0]),o[l]=0;for(n in a)Object.prototype.hasOwnProperty.call(a,n)&&(e[n]=a[n]);for(f&&f(r);s.length;)s.shift()();return u.push.apply(u,p||[]),t()}function t(){for(var e,r=0;r<u.length;r++){for(var t=u[r],n=!0,i=1;i<t.length;i++){var a=t[i];0!==o[a]&&(n=!1)}n&&(u.splice(r--,1),e=l(l.s=t[0]))}return e}var n={},o={1:0},u=[];function l(r){if(n[r])return n[r].exports;var t=n[r]={i:r,l:!1,exports:{}};return e[r].call(t.exports,t,t.exports,l),t.l=!0,t.exports}l.m=e,l.c=n,l.d=function(e,r,t){l.o(e,r)||Object.defineProperty(e,r,{enumerable:!0,get:t})},l.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},l.t=function(e,r){if(1&r&&(e=l(e)),8&r)return e;if(4&r&&"object"==typeof e&&e&&e.__esModule)return e;var t=Object.create(null);if(l.r(t),Object.defineProperty(t,"default",{enumerable:!0,value:e}),2&r&&"string"!=typeof e)for(var n in e)l.d(t,n,function(r){return e[r]}.bind(null,n));return t},l.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return l.d(r,"a",r),r},l.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},l.p="/";var i=this["webpackJsonpportal-ui"]=this["webpackJsonpportal-ui"]||[],a=i.push.bind(i);i.push=r,i=i.slice();for(var p=0;p<i.length;p++)r(i[p]);var f=a;t()}([])</script><script src="/static/js/2.d609c10f.chunk.js"></script><script src="/static/js/main.03b04a1b.chunk.js"></script></body></html>
|
||||
<!doctype html><html lang="en"><head><meta charset="utf-8"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#000000"/><meta name="description" content="MinIO Console"/><link href="https://fonts.googleapis.com/css2?family=Lato:wght@400;500;700;900&display=swap" rel="stylesheet"/><link rel="apple-touch-icon" sizes="180x180" href="/apple-icon-180x180.png"/><link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png"/><link rel="icon" type="image/png" sizes="96x96" href="/favicon-96x96.png"/><link rel="icon" type="image/png" sizes="16x16" href="/favicon-16x16.png"/><link rel="manifest" href="/manifest.json"/><link rel="mask-icon" href="/safari-pinned-tab.svg" color="#3a4e54"/><title>MinIO Console</title><link href="/static/css/2.60e04a19.chunk.css" rel="stylesheet"><link href="/static/css/main.8cfac526.chunk.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div><script>!function(e){function r(r){for(var n,l,i=r[0],a=r[1],p=r[2],c=0,s=[];c<i.length;c++)l=i[c],Object.prototype.hasOwnProperty.call(o,l)&&o[l]&&s.push(o[l][0]),o[l]=0;for(n in a)Object.prototype.hasOwnProperty.call(a,n)&&(e[n]=a[n]);for(f&&f(r);s.length;)s.shift()();return u.push.apply(u,p||[]),t()}function t(){for(var e,r=0;r<u.length;r++){for(var t=u[r],n=!0,i=1;i<t.length;i++){var a=t[i];0!==o[a]&&(n=!1)}n&&(u.splice(r--,1),e=l(l.s=t[0]))}return e}var n={},o={1:0},u=[];function l(r){if(n[r])return n[r].exports;var t=n[r]={i:r,l:!1,exports:{}};return e[r].call(t.exports,t,t.exports,l),t.l=!0,t.exports}l.m=e,l.c=n,l.d=function(e,r,t){l.o(e,r)||Object.defineProperty(e,r,{enumerable:!0,get:t})},l.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},l.t=function(e,r){if(1&r&&(e=l(e)),8&r)return e;if(4&r&&"object"==typeof e&&e&&e.__esModule)return e;var t=Object.create(null);if(l.r(t),Object.defineProperty(t,"default",{enumerable:!0,value:e}),2&r&&"string"!=typeof e)for(var n in e)l.d(t,n,function(r){return e[r]}.bind(null,n));return t},l.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return l.d(r,"a",r),r},l.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},l.p="/";var i=this["webpackJsonpportal-ui"]=this["webpackJsonpportal-ui"]||[],a=i.push.bind(i);i.push=r,i=i.slice();for(var p=0;p<i.length;p++)r(i[p]);var f=a;t()}([])</script><script src="/static/js/2.06e58ba0.chunk.js"></script><script src="/static/js/main.7915d40b.chunk.js"></script></body></html>
|
||||
File diff suppressed because one or more lines are too long
1
portal-ui/build/static/js/2.06e58ba0.chunk.js.map
Normal file
1
portal-ui/build/static/js/2.06e58ba0.chunk.js.map
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
1
portal-ui/build/static/js/main.7915d40b.chunk.js.map
Normal file
1
portal-ui/build/static/js/main.7915d40b.chunk.js.map
Normal file
File diff suppressed because one or more lines are too long
@@ -378,6 +378,10 @@ const Console = ({
|
||||
component: TenantDetails,
|
||||
path: "/namespaces/:tenantNamespace/tenants/:tenantName/license",
|
||||
},
|
||||
{
|
||||
component: TenantDetails,
|
||||
path: "/namespaces/:tenantNamespace/tenants/:tenantName/security",
|
||||
},
|
||||
{
|
||||
component: License,
|
||||
path: "/license",
|
||||
|
||||
@@ -92,6 +92,9 @@ export interface ITenant {
|
||||
logEnabled: boolean;
|
||||
monitoringEnabled: boolean;
|
||||
encryptionEnabled: boolean;
|
||||
minioTLS: boolean;
|
||||
consoleTLS: boolean;
|
||||
consoleEnabled: boolean;
|
||||
idpAdEnabled: boolean;
|
||||
idpOicEnabled: boolean;
|
||||
health_status: string;
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
import { ITenant } from "../ListTenants/types";
|
||||
import { createStyles, Theme, withStyles } from "@material-ui/core/styles";
|
||||
import {
|
||||
containerForHeader,
|
||||
tenantDetailsStyles,
|
||||
} from "../../Common/FormComponents/common/styleLibrary";
|
||||
import {
|
||||
Button,
|
||||
Dialog,
|
||||
DialogActions,
|
||||
DialogContent,
|
||||
DialogContentText,
|
||||
DialogTitle,
|
||||
LinearProgress,
|
||||
} from "@material-ui/core";
|
||||
import React, { useState } from "react";
|
||||
|
||||
interface IConfirmationDialog {
|
||||
classes: any;
|
||||
open: boolean;
|
||||
cancelLabel: string;
|
||||
okLabel: string;
|
||||
onClose: any;
|
||||
cancelOnClick: any;
|
||||
okOnClick: any;
|
||||
title: string;
|
||||
description: string;
|
||||
}
|
||||
|
||||
const styles = (theme: Theme) =>
|
||||
createStyles({
|
||||
...tenantDetailsStyles,
|
||||
...containerForHeader(theme.spacing(4)),
|
||||
});
|
||||
|
||||
const ConfirmationDialog = ({
|
||||
classes,
|
||||
open,
|
||||
cancelLabel,
|
||||
okLabel,
|
||||
onClose,
|
||||
cancelOnClick,
|
||||
okOnClick,
|
||||
title,
|
||||
description,
|
||||
}: IConfirmationDialog) => {
|
||||
const [isSending, setIsSending] = useState<boolean>(false);
|
||||
const onClick = () => {
|
||||
setIsSending(true);
|
||||
if (okOnClick !== null) {
|
||||
okOnClick();
|
||||
}
|
||||
setIsSending(false);
|
||||
};
|
||||
if (!open) return null;
|
||||
return (
|
||||
<Dialog
|
||||
open={open}
|
||||
onClose={onClose}
|
||||
aria-labelledby="alert-dialog-title"
|
||||
aria-describedby="alert-dialog-description"
|
||||
>
|
||||
<DialogTitle id="alert-dialog-title">{title}</DialogTitle>
|
||||
<DialogContent>
|
||||
{isSending && <LinearProgress />}
|
||||
<DialogContentText id="alert-dialog-description">
|
||||
{description}
|
||||
</DialogContentText>
|
||||
</DialogContent>
|
||||
<DialogActions>
|
||||
<Button onClick={cancelOnClick} color="primary" disabled={isSending}>
|
||||
{cancelLabel || "Cancel"}
|
||||
</Button>
|
||||
<Button onClick={onClick} color="secondary" autoFocus>
|
||||
{okLabel || "Ok"}
|
||||
</Button>
|
||||
</DialogActions>
|
||||
</Dialog>
|
||||
);
|
||||
};
|
||||
|
||||
export default withStyles(styles)(ConfirmationDialog);
|
||||
@@ -45,6 +45,7 @@ import PoolsSummary from "./PoolsSummary";
|
||||
import PodsSummary from "./PodsSummary";
|
||||
import { AppState } from "../../../../store";
|
||||
import TenantMetrics from "./TenantMetrics";
|
||||
import TenantSecurity from "./TenantSecurity";
|
||||
|
||||
interface ITenantDetailsProps {
|
||||
classes: any;
|
||||
@@ -156,6 +157,7 @@ const TenantDetails = ({
|
||||
case "pods":
|
||||
case "metrics":
|
||||
case "license":
|
||||
case "security":
|
||||
setTenantTab(section);
|
||||
break;
|
||||
default:
|
||||
@@ -235,6 +237,7 @@ const TenantDetails = ({
|
||||
>
|
||||
<Tab value="summary" label="Summary" />
|
||||
<Tab value="metrics" label="Metrics" />
|
||||
<Tab value="security" label="Security" />
|
||||
<Tab value="pools" label="Pools" />
|
||||
<Tab value="pods" label="Pods" />
|
||||
<Tab value="license" label="License" />
|
||||
@@ -251,6 +254,10 @@ const TenantDetails = ({
|
||||
path="/namespaces/:tenantNamespace/tenants/:tenantName/metrics"
|
||||
component={TenantMetrics}
|
||||
/>
|
||||
<Route
|
||||
path="/namespaces/:tenantNamespace/tenants/:tenantName/security"
|
||||
component={TenantSecurity}
|
||||
/>
|
||||
<Route
|
||||
path="/namespaces/:tenantNamespace/tenants/:tenantName/pools"
|
||||
component={PoolsSummary}
|
||||
|
||||
@@ -0,0 +1,950 @@
|
||||
// This file is part of MinIO Console Server
|
||||
// Copyright (c) 2021 MinIO, Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU Affero General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU Affero General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Affero General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import { ITenant } from "../ListTenants/types";
|
||||
import { ICertificateInfo, ITenantSecurityResponse } from "../types";
|
||||
import { createStyles, Theme, withStyles } from "@material-ui/core/styles";
|
||||
import {
|
||||
containerForHeader,
|
||||
tenantDetailsStyles,
|
||||
} from "../../Common/FormComponents/common/styleLibrary";
|
||||
import Paper from "@material-ui/core/Paper";
|
||||
import Grid from "@material-ui/core/Grid";
|
||||
import Chip from "@material-ui/core/Chip";
|
||||
import React, { Fragment, useEffect, useState } from "react";
|
||||
import Moment from "react-moment";
|
||||
import FormSwitchWrapper from "../../Common/FormComponents/FormSwitchWrapper/FormSwitchWrapper";
|
||||
import {
|
||||
Button,
|
||||
CircularProgress,
|
||||
Divider,
|
||||
LinearProgress,
|
||||
Typography,
|
||||
Dialog,
|
||||
DialogActions,
|
||||
DialogContent,
|
||||
DialogContentText,
|
||||
DialogTitle,
|
||||
} from "@material-ui/core";
|
||||
import { KeyPair } from "../ListTenants/utils";
|
||||
import FileSelector from "../../Common/FormComponents/FileSelector/FileSelector";
|
||||
import api from "../../../../common/api";
|
||||
import { setErrorSnackMessage } from "../../../../actions";
|
||||
import { connect } from "react-redux";
|
||||
import { AppState } from "../../../../store";
|
||||
import { setTenantDetailsLoad } from "../actions";
|
||||
import ConfirmationDialog from "./ConfirmationDialog";
|
||||
|
||||
interface ITenantSecurity {
|
||||
classes: any;
|
||||
loadingTenant: boolean;
|
||||
tenant: ITenant | null;
|
||||
setErrorSnackMessage: typeof setErrorSnackMessage;
|
||||
setTenantDetailsLoad: typeof setTenantDetailsLoad;
|
||||
}
|
||||
|
||||
const styles = (theme: Theme) =>
|
||||
createStyles({
|
||||
...tenantDetailsStyles,
|
||||
loaderAlign: {
|
||||
textAlign: "center",
|
||||
},
|
||||
title: {
|
||||
marginTop: 35,
|
||||
},
|
||||
bold: { fontWeight: "bold" },
|
||||
italic: { fontStyle: "italic" },
|
||||
underline: { textDecorationLine: "underline" },
|
||||
paperContainer: {
|
||||
padding: "15px 15px 15px 50px",
|
||||
},
|
||||
verifiedIcon: {
|
||||
width: 96,
|
||||
position: "absolute",
|
||||
right: 0,
|
||||
bottom: 29,
|
||||
},
|
||||
noUnderLine: {
|
||||
textDecoration: "none",
|
||||
},
|
||||
certificateInfo: {
|
||||
height: "auto",
|
||||
margin: 5,
|
||||
},
|
||||
certificateInfoName: {
|
||||
fontWeight: "bold",
|
||||
},
|
||||
...containerForHeader(theme.spacing(4)),
|
||||
});
|
||||
|
||||
const TenantSecurity = ({
|
||||
classes,
|
||||
tenant,
|
||||
loadingTenant,
|
||||
setErrorSnackMessage,
|
||||
setTenantDetailsLoad,
|
||||
}: ITenantSecurity) => {
|
||||
const [isSending, setIsSending] = useState<boolean>(false);
|
||||
const [dialogOpen, setDialogOpen] = useState<boolean>(false);
|
||||
const [enableAutoCert, setEnableAutoCert] = useState<boolean>(false);
|
||||
const [enableCustomCerts, setEnableCustomCerts] = useState<boolean>(false);
|
||||
const [certificatesToBeRemoved, setCertificatesToBeRemoved] = useState<
|
||||
string[]
|
||||
>([]);
|
||||
// Console certificates
|
||||
const [consoleCertificates, setConsoleCertificates] = useState<KeyPair[]>([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
const [consoleCaCertificates, setConsoleCaCertificates] = useState<KeyPair[]>(
|
||||
[
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]
|
||||
);
|
||||
const [consoleTLSCertificateSecrets, setConsoleTLSCertificateSecrets] =
|
||||
useState<ICertificateInfo[]>([]);
|
||||
const [consoleTLSCaCertificateSecrets, setConsoleTLSCaCertificateSecrets] =
|
||||
useState<ICertificateInfo[]>([]);
|
||||
// MinIO certificates
|
||||
const [minioCertificates, setMinioCertificates] = useState<KeyPair[]>([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
const [minioCaCertificates, setMinioCaCertificates] = useState<KeyPair[]>([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
const [minioTLSCertificateSecrets, setMinioTLSCertificateSecrets] = useState<
|
||||
ICertificateInfo[]
|
||||
>([]);
|
||||
const [minioTLSCaCertificateSecrets, setMinioTLSCaCertificateSecrets] =
|
||||
useState<ICertificateInfo[]>([]);
|
||||
|
||||
useEffect(() => {
|
||||
if (tenant) {
|
||||
getTenantSecurityInfo();
|
||||
}
|
||||
}, [tenant]);
|
||||
|
||||
const getTenantSecurityInfo = () => {
|
||||
api
|
||||
.invoke(
|
||||
"GET",
|
||||
`/api/v1/namespaces/${tenant?.namespace}/tenants/${tenant?.name}/security`
|
||||
)
|
||||
.then((res: ITenantSecurityResponse) => {
|
||||
setEnableAutoCert(res.autoCert);
|
||||
if (
|
||||
res.customCertificates.minio ||
|
||||
res.customCertificates.minioCAs ||
|
||||
res.customCertificates.console ||
|
||||
res.customCertificates.consoleCAs
|
||||
) {
|
||||
setEnableCustomCerts(true);
|
||||
}
|
||||
setMinioTLSCertificateSecrets(res.customCertificates.minio || []);
|
||||
setMinioTLSCaCertificateSecrets(res.customCertificates.minioCAs || []);
|
||||
setConsoleTLSCertificateSecrets(res.customCertificates.console || []);
|
||||
setConsoleTLSCaCertificateSecrets(
|
||||
res.customCertificates.consoleCAs || []
|
||||
);
|
||||
})
|
||||
.catch((err) => {
|
||||
setErrorSnackMessage(err.message);
|
||||
});
|
||||
};
|
||||
|
||||
const updateTenantSecurity = () => {
|
||||
setIsSending(true);
|
||||
let payload = {
|
||||
autoCert: enableAutoCert,
|
||||
customCertificates: {},
|
||||
};
|
||||
if (enableCustomCerts) {
|
||||
payload["customCertificates"] = {
|
||||
secretsToBeDeleted: certificatesToBeRemoved,
|
||||
minio: minioCertificates
|
||||
.map((keyPair: KeyPair) => ({
|
||||
crt: keyPair.encoded_cert,
|
||||
key: keyPair.encoded_key,
|
||||
}))
|
||||
.filter((cert: any) => cert.crt && cert.key),
|
||||
minioCAs: minioCaCertificates
|
||||
.map((keyPair: KeyPair) => keyPair.encoded_cert)
|
||||
.filter((cert: any) => cert),
|
||||
console: consoleCertificates
|
||||
.map((keyPair: KeyPair) => ({
|
||||
crt: keyPair.encoded_cert,
|
||||
key: keyPair.encoded_key,
|
||||
}))
|
||||
.filter((cert: any) => cert.crt && cert.key),
|
||||
consoleCAs: consoleCaCertificates
|
||||
.map((keyPair: KeyPair) => keyPair.encoded_cert)
|
||||
.filter((cert: any) => cert),
|
||||
};
|
||||
} else {
|
||||
payload["customCertificates"] = {
|
||||
secretsToBeDeleted: [
|
||||
...minioTLSCertificateSecrets.map((cert) => cert.name),
|
||||
...minioTLSCaCertificateSecrets.map((cert) => cert.name),
|
||||
...consoleTLSCertificateSecrets.map((cert) => cert.name),
|
||||
...consoleTLSCaCertificateSecrets.map((cert) => cert.name),
|
||||
],
|
||||
minio: [],
|
||||
minioCAs: [],
|
||||
console: [],
|
||||
consoleCAs: [],
|
||||
};
|
||||
}
|
||||
api
|
||||
.invoke(
|
||||
"POST",
|
||||
`/api/v1/namespaces/${tenant?.namespace}/tenants/${tenant?.name}/security`,
|
||||
payload
|
||||
)
|
||||
.then(() => {
|
||||
setIsSending(false);
|
||||
// Close confirmation modal
|
||||
setDialogOpen(false);
|
||||
// Refresh Information and reset forms
|
||||
setMinioCertificates([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
setMinioCaCertificates([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
setConsoleCertificates([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
setConsoleCaCertificates([
|
||||
{
|
||||
cert: "",
|
||||
encoded_cert: "",
|
||||
encoded_key: "",
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
},
|
||||
]);
|
||||
getTenantSecurityInfo();
|
||||
})
|
||||
.catch((err) => {
|
||||
setErrorSnackMessage(err);
|
||||
setIsSending(false);
|
||||
});
|
||||
};
|
||||
|
||||
const removeCertificate = (certificateInfo: ICertificateInfo) => {
|
||||
// TLS certificate secrets can be referenced MinIO, Console or KES, we need to remove the secret from all list and update
|
||||
// the arrays
|
||||
// Add certificate to the global list of secrets to be removed
|
||||
setCertificatesToBeRemoved([
|
||||
...certificatesToBeRemoved,
|
||||
certificateInfo.name,
|
||||
]);
|
||||
|
||||
// Update MinIO TLS certificate secrets
|
||||
const updatedMinIOTLSCertificateSecrets = minioTLSCertificateSecrets.filter(
|
||||
(certificateSecret) => certificateSecret.name != certificateInfo.name
|
||||
);
|
||||
const updatedMinIOTLSCaCertificateSecrets =
|
||||
minioTLSCaCertificateSecrets.filter(
|
||||
(certificateSecret) => certificateSecret.name != certificateInfo.name
|
||||
);
|
||||
setMinioTLSCertificateSecrets(updatedMinIOTLSCertificateSecrets);
|
||||
setMinioTLSCaCertificateSecrets(updatedMinIOTLSCaCertificateSecrets);
|
||||
|
||||
// Update Console TLS certificate secrets
|
||||
const updatedConsoleTLSCertificateSecrets =
|
||||
consoleTLSCertificateSecrets.filter(
|
||||
(certificateSecret) => certificateSecret.name != certificateInfo.name
|
||||
);
|
||||
const updatedConsoleTLSCaCertificateSecrets =
|
||||
consoleTLSCaCertificateSecrets.filter(
|
||||
(certificateSecret) => certificateSecret.name != certificateInfo.name
|
||||
);
|
||||
setConsoleTLSCertificateSecrets(updatedConsoleTLSCertificateSecrets);
|
||||
setConsoleTLSCaCertificateSecrets(updatedConsoleTLSCaCertificateSecrets);
|
||||
};
|
||||
|
||||
const addFileToKeyPair = (
|
||||
type: string,
|
||||
id: string,
|
||||
key: string,
|
||||
fileName: string,
|
||||
value: string
|
||||
) => {
|
||||
let certificates = minioCertificates;
|
||||
let updateCertificates: any = () => {};
|
||||
|
||||
switch (type) {
|
||||
case "minio": {
|
||||
certificates = minioCertificates;
|
||||
updateCertificates = setMinioCertificates;
|
||||
break;
|
||||
}
|
||||
case "minioCAs": {
|
||||
certificates = minioCaCertificates;
|
||||
updateCertificates = setMinioCaCertificates;
|
||||
break;
|
||||
}
|
||||
case "console": {
|
||||
certificates = consoleCertificates;
|
||||
updateCertificates = setConsoleCertificates;
|
||||
break;
|
||||
}
|
||||
case "consoleCAs": {
|
||||
certificates = consoleCaCertificates;
|
||||
updateCertificates = setConsoleCaCertificates;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
}
|
||||
|
||||
const NCertList = certificates.map((item: KeyPair) => {
|
||||
if (item.id === id) {
|
||||
return {
|
||||
...item,
|
||||
[key]: fileName,
|
||||
[`encoded_${key}`]: value,
|
||||
};
|
||||
}
|
||||
return item;
|
||||
});
|
||||
updateCertificates(NCertList);
|
||||
};
|
||||
|
||||
const deleteKeyPair = (type: string, id: string) => {
|
||||
let certificates = minioCertificates;
|
||||
let updateCertificates: any = () => {};
|
||||
|
||||
switch (type) {
|
||||
case "minio": {
|
||||
certificates = minioCertificates;
|
||||
updateCertificates = setMinioCertificates;
|
||||
break;
|
||||
}
|
||||
case "minioCAs": {
|
||||
certificates = minioCaCertificates;
|
||||
updateCertificates = setMinioCaCertificates;
|
||||
break;
|
||||
}
|
||||
case "console": {
|
||||
certificates = consoleCertificates;
|
||||
updateCertificates = setConsoleCertificates;
|
||||
break;
|
||||
}
|
||||
case "consoleCAs": {
|
||||
certificates = consoleCaCertificates;
|
||||
updateCertificates = setConsoleCaCertificates;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
}
|
||||
|
||||
if (certificates.length > 1) {
|
||||
const cleanCertsList = certificates.filter(
|
||||
(item: KeyPair) => item.id !== id
|
||||
);
|
||||
updateCertificates(cleanCertsList);
|
||||
}
|
||||
};
|
||||
|
||||
const addKeyPair = (type: string) => {
|
||||
let certificates = minioCertificates;
|
||||
let updateCertificates: any = () => {};
|
||||
|
||||
switch (type) {
|
||||
case "minio": {
|
||||
certificates = minioCertificates;
|
||||
updateCertificates = setMinioCertificates;
|
||||
break;
|
||||
}
|
||||
case "minioCAs": {
|
||||
certificates = minioCaCertificates;
|
||||
updateCertificates = setMinioCaCertificates;
|
||||
break;
|
||||
}
|
||||
case "console": {
|
||||
certificates = consoleCertificates;
|
||||
updateCertificates = setConsoleCertificates;
|
||||
break;
|
||||
}
|
||||
case "consoleCAs": {
|
||||
certificates = consoleCaCertificates;
|
||||
updateCertificates = setConsoleCaCertificates;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
}
|
||||
const updatedCertificates = [
|
||||
...certificates,
|
||||
{
|
||||
id: Date.now().toString(),
|
||||
key: "",
|
||||
cert: "",
|
||||
encoded_key: "",
|
||||
encoded_cert: "",
|
||||
},
|
||||
];
|
||||
updateCertificates(updatedCertificates);
|
||||
};
|
||||
return (
|
||||
<React.Fragment>
|
||||
<ConfirmationDialog
|
||||
open={dialogOpen}
|
||||
title="Save and Restart"
|
||||
description="Are you sure you want to save the changes and restart the service?"
|
||||
onClose={() => setDialogOpen(false)}
|
||||
cancelOnClick={() => setDialogOpen(false)}
|
||||
okOnClick={updateTenantSecurity}
|
||||
cancelLabel="Cancel"
|
||||
okLabel={"Restart"}
|
||||
/>
|
||||
<br />
|
||||
<Paper className={classes.paperContainer}>
|
||||
{loadingTenant ? (
|
||||
<div className={classes.loaderAlign}>
|
||||
<CircularProgress />
|
||||
</div>
|
||||
) : (
|
||||
<Fragment>
|
||||
<Grid item xs={12} className={classes.title}>
|
||||
<FormSwitchWrapper
|
||||
value="enableAutoCert"
|
||||
id="enableAutoCert"
|
||||
name="enableAutoCert"
|
||||
checked={enableAutoCert}
|
||||
onChange={(e) => {
|
||||
const targetD = e.target;
|
||||
const checked = targetD.checked;
|
||||
setEnableAutoCert(checked);
|
||||
}}
|
||||
label={"Enable AutoCert"}
|
||||
/>
|
||||
<FormSwitchWrapper
|
||||
value="enableCustomCerts"
|
||||
id="enableCustomCerts"
|
||||
name="enableCustomCerts"
|
||||
checked={enableCustomCerts}
|
||||
onChange={(e) => {
|
||||
const targetD = e.target;
|
||||
const checked = targetD.checked;
|
||||
setEnableCustomCerts(checked);
|
||||
}}
|
||||
label={"Custom Certificates"}
|
||||
/>
|
||||
</Grid>
|
||||
{enableCustomCerts && (
|
||||
<Fragment>
|
||||
<Grid container>
|
||||
<Grid container item xs={12}>
|
||||
<Typography variant="overline" display="block" gutterBottom>
|
||||
MinIO Certificates
|
||||
</Typography>
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{minioTLSCertificateSecrets.map(
|
||||
(certificateInfo: ICertificateInfo) => (
|
||||
<Chip
|
||||
key={certificateInfo.name}
|
||||
variant="outlined"
|
||||
color="primary"
|
||||
className={classes.certificateInfo}
|
||||
label={
|
||||
<div>
|
||||
<Typography
|
||||
variant="subtitle1"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.name}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.italic}
|
||||
variant="caption"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.domains.join(", ")}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.bold}
|
||||
variant="overline"
|
||||
gutterBottom
|
||||
>
|
||||
Expiry:
|
||||
</Typography>
|
||||
<Typography variant="caption" gutterBottom>
|
||||
<Moment format="YYYY-MM-DD">
|
||||
{certificateInfo.expiry}
|
||||
</Moment>
|
||||
</Typography>
|
||||
</div>
|
||||
}
|
||||
onDelete={() => removeCertificate(certificateInfo)}
|
||||
/>
|
||||
)
|
||||
)}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<br />
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{minioCertificates.map((keyPair) => (
|
||||
<Fragment key={keyPair.id}>
|
||||
<Grid item xs={5}>
|
||||
<FileSelector
|
||||
onChange={(encodedValue, fileName) =>
|
||||
addFileToKeyPair(
|
||||
"minio",
|
||||
keyPair.id,
|
||||
"cert",
|
||||
fileName,
|
||||
encodedValue
|
||||
)
|
||||
}
|
||||
accept=".cer,.crt,.cert,.pem"
|
||||
id="tlsCert"
|
||||
name="tlsCert"
|
||||
label="Cert"
|
||||
value={keyPair.cert}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item xs={5}>
|
||||
<FileSelector
|
||||
onChange={(encodedValue, fileName) =>
|
||||
addFileToKeyPair(
|
||||
"minio",
|
||||
keyPair.id,
|
||||
"key",
|
||||
fileName,
|
||||
encodedValue
|
||||
)
|
||||
}
|
||||
accept=".key,.pem"
|
||||
id="tlsKey"
|
||||
name="tlsKey"
|
||||
label="Key"
|
||||
value={keyPair.key}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item xs={1}>
|
||||
<Button
|
||||
onClick={() => deleteKeyPair("minio", keyPair.id)}
|
||||
color="secondary"
|
||||
>
|
||||
Remove
|
||||
</Button>
|
||||
</Grid>
|
||||
</Fragment>
|
||||
))}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<Button onClick={() => addKeyPair("minio")} color="primary">
|
||||
Add More
|
||||
</Button>
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<br />
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<Typography variant="overline" display="block" gutterBottom>
|
||||
MinIO CA Certificates
|
||||
</Typography>
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{minioTLSCaCertificateSecrets.map(
|
||||
(certificateInfo: ICertificateInfo) => (
|
||||
<Chip
|
||||
key={certificateInfo.name}
|
||||
variant="outlined"
|
||||
color="primary"
|
||||
className={classes.certificateInfo}
|
||||
label={
|
||||
<div>
|
||||
<Typography
|
||||
variant="subtitle1"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.name}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.italic}
|
||||
variant="caption"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.domains.join(", ")}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.bold}
|
||||
variant="overline"
|
||||
gutterBottom
|
||||
>
|
||||
Expiry:
|
||||
</Typography>
|
||||
<Typography variant="caption" gutterBottom>
|
||||
<Moment format="YYYY-MM-DD">
|
||||
{certificateInfo.expiry}
|
||||
</Moment>
|
||||
</Typography>
|
||||
</div>
|
||||
}
|
||||
onDelete={() => removeCertificate(certificateInfo)}
|
||||
/>
|
||||
)
|
||||
)}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<br />
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{minioCaCertificates.map((keyPair: KeyPair) => (
|
||||
<Fragment key={keyPair.id}>
|
||||
<Grid item xs={10}>
|
||||
<FileSelector
|
||||
onChange={(encodedValue, fileName) =>
|
||||
addFileToKeyPair(
|
||||
"minioCAs",
|
||||
keyPair.id,
|
||||
"cert",
|
||||
fileName,
|
||||
encodedValue
|
||||
)
|
||||
}
|
||||
accept=".cer,.crt,.cert,.pem"
|
||||
id="tlsCert"
|
||||
name="tlsCert"
|
||||
label="Cert"
|
||||
value={keyPair.cert}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item xs={1}>
|
||||
<Button
|
||||
onClick={() =>
|
||||
deleteKeyPair("minioCAs", keyPair.id)
|
||||
}
|
||||
color="secondary"
|
||||
>
|
||||
Remove
|
||||
</Button>
|
||||
</Grid>
|
||||
</Fragment>
|
||||
))}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<Button
|
||||
onClick={() => addKeyPair("minioCAs")}
|
||||
color="primary"
|
||||
>
|
||||
Add More
|
||||
</Button>
|
||||
</Grid>
|
||||
</Grid>
|
||||
<Grid container>
|
||||
<Grid item xs={12}>
|
||||
<br />
|
||||
<Divider />
|
||||
<br />
|
||||
</Grid>
|
||||
</Grid>
|
||||
{tenant?.consoleEnabled ? (
|
||||
<Fragment>
|
||||
<Grid container>
|
||||
<Grid container item xs={12}>
|
||||
<Typography
|
||||
variant="overline"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
Console Certificates
|
||||
</Typography>
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{consoleTLSCertificateSecrets.map(
|
||||
(certificateInfo: ICertificateInfo) => (
|
||||
<Chip
|
||||
key={certificateInfo.name}
|
||||
variant="outlined"
|
||||
color="primary"
|
||||
className={classes.certificateInfo}
|
||||
label={
|
||||
<div>
|
||||
<Typography
|
||||
variant="subtitle1"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.name}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.italic}
|
||||
variant="caption"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.domains.join(", ")}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.bold}
|
||||
variant="overline"
|
||||
gutterBottom
|
||||
>
|
||||
Expiry:
|
||||
</Typography>
|
||||
<Typography variant="caption" gutterBottom>
|
||||
<Moment format="YYYY-MM-DD">
|
||||
{certificateInfo.expiry}
|
||||
</Moment>
|
||||
</Typography>
|
||||
</div>
|
||||
}
|
||||
onDelete={() =>
|
||||
removeCertificate(certificateInfo)
|
||||
}
|
||||
/>
|
||||
)
|
||||
)}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<br />
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{consoleCertificates.map((keyPair: KeyPair) => (
|
||||
<Fragment key={keyPair.id}>
|
||||
<Grid item xs={6}>
|
||||
<FileSelector
|
||||
onChange={(encodedValue, fileName) =>
|
||||
addFileToKeyPair(
|
||||
"console",
|
||||
keyPair.id,
|
||||
"cert",
|
||||
fileName,
|
||||
encodedValue
|
||||
)
|
||||
}
|
||||
accept=".cer,.crt,.cert,.pem"
|
||||
id="consoleCert"
|
||||
name="consoleCert"
|
||||
label="Cert"
|
||||
value={keyPair.cert}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item xs={6}>
|
||||
<FileSelector
|
||||
onChange={(encodedValue, fileName) =>
|
||||
addFileToKeyPair(
|
||||
"console",
|
||||
keyPair.id,
|
||||
"key",
|
||||
fileName,
|
||||
encodedValue
|
||||
)
|
||||
}
|
||||
accept=".key,.pem"
|
||||
id="consoleKey"
|
||||
name="consoleKey"
|
||||
label="Key"
|
||||
value={keyPair.key}
|
||||
/>
|
||||
</Grid>
|
||||
</Fragment>
|
||||
))}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<Typography
|
||||
variant="overline"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
Console CA Certificates
|
||||
</Typography>
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{consoleTLSCaCertificateSecrets.map(
|
||||
(certificateInfo: ICertificateInfo) => (
|
||||
<Chip
|
||||
key={certificateInfo.name}
|
||||
variant="outlined"
|
||||
color="primary"
|
||||
className={classes.certificateInfo}
|
||||
label={
|
||||
<div>
|
||||
<Typography
|
||||
variant="subtitle1"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.name}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.italic}
|
||||
variant="caption"
|
||||
display="block"
|
||||
gutterBottom
|
||||
>
|
||||
{certificateInfo.domains.join(", ")}
|
||||
</Typography>
|
||||
<Typography
|
||||
className={classes.bold}
|
||||
variant="overline"
|
||||
gutterBottom
|
||||
>
|
||||
Expiry:
|
||||
</Typography>
|
||||
<Typography variant="caption" gutterBottom>
|
||||
<Moment format="YYYY-MM-DD">
|
||||
{certificateInfo.expiry}
|
||||
</Moment>
|
||||
</Typography>
|
||||
</div>
|
||||
}
|
||||
onDelete={() =>
|
||||
removeCertificate(certificateInfo)
|
||||
}
|
||||
/>
|
||||
)
|
||||
)}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<br />
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
{consoleCaCertificates.map((keyPair: KeyPair) => (
|
||||
<Fragment key={keyPair.id}>
|
||||
<Grid item xs={10}>
|
||||
<FileSelector
|
||||
onChange={(encodedValue, fileName) =>
|
||||
addFileToKeyPair(
|
||||
"consoleCAs",
|
||||
keyPair.id,
|
||||
"cert",
|
||||
fileName,
|
||||
encodedValue
|
||||
)
|
||||
}
|
||||
accept=".cer,.crt,.cert,.pem"
|
||||
id="tlsCert"
|
||||
name="tlsCert"
|
||||
label="Cert"
|
||||
value={keyPair.cert}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item xs={1}>
|
||||
<Button
|
||||
onClick={() =>
|
||||
deleteKeyPair("consoleCAs", keyPair.id)
|
||||
}
|
||||
color="secondary"
|
||||
>
|
||||
Remove
|
||||
</Button>
|
||||
</Grid>
|
||||
</Fragment>
|
||||
))}
|
||||
</Grid>
|
||||
<Grid container item xs={12}>
|
||||
<Button
|
||||
onClick={() => addKeyPair("consoleCAs")}
|
||||
color="primary"
|
||||
>
|
||||
Add More
|
||||
</Button>
|
||||
</Grid>
|
||||
</Grid>
|
||||
<Grid container>
|
||||
<Grid item xs={12}>
|
||||
<br />
|
||||
<Divider />
|
||||
<br />
|
||||
</Grid>
|
||||
</Grid>
|
||||
</Fragment>
|
||||
) : null}
|
||||
</Fragment>
|
||||
)}
|
||||
<Grid item xs={12} className={classes.buttonContainer}>
|
||||
<Button
|
||||
type="submit"
|
||||
variant="contained"
|
||||
color="primary"
|
||||
disabled={dialogOpen}
|
||||
onClick={() => setDialogOpen(true)}
|
||||
>
|
||||
Save
|
||||
</Button>
|
||||
</Grid>
|
||||
</Fragment>
|
||||
)}
|
||||
</Paper>
|
||||
</React.Fragment>
|
||||
);
|
||||
};
|
||||
|
||||
const mapState = (state: AppState) => ({
|
||||
loadingTenant: state.tenants.tenantDetails.loadingTenant,
|
||||
selectedTenant: state.tenants.tenantDetails.currentTenant,
|
||||
tenant: state.tenants.tenantDetails.tenantInfo,
|
||||
});
|
||||
|
||||
const mapDispatchToProps = {
|
||||
setErrorSnackMessage,
|
||||
setTenantDetailsLoad,
|
||||
};
|
||||
|
||||
const connector = connect(mapState, mapDispatchToProps);
|
||||
|
||||
export default withStyles(styles)(connector(TenantSecurity));
|
||||
@@ -39,6 +39,9 @@ interface ITenantsSummary {
|
||||
logEnabled: boolean;
|
||||
monitoringEnabled: boolean;
|
||||
encryptionEnabled: boolean;
|
||||
minioTLS: boolean;
|
||||
consoleTLS: boolean;
|
||||
consoleEnabled: boolean;
|
||||
adEnabled: boolean;
|
||||
oicEnabled: boolean;
|
||||
loadingTenant: boolean;
|
||||
@@ -77,6 +80,9 @@ const TenantSummary = ({
|
||||
logEnabled,
|
||||
monitoringEnabled,
|
||||
encryptionEnabled,
|
||||
minioTLS,
|
||||
consoleTLS,
|
||||
consoleEnabled,
|
||||
adEnabled,
|
||||
oicEnabled,
|
||||
loadingTenant,
|
||||
@@ -359,6 +365,32 @@ const TenantSummary = ({
|
||||
</Button>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td className={classes.titleCol}>MinIO TLS:</td>
|
||||
<td>
|
||||
<Button
|
||||
color="primary"
|
||||
className={classes.anchorButton}
|
||||
>
|
||||
{minioTLS ? "Enabled" : "Disabled"}
|
||||
</Button>
|
||||
</td>
|
||||
{consoleEnabled ? (
|
||||
<Fragment>
|
||||
<td className={classes.titleCol}>Console TLS:</td>
|
||||
<td>
|
||||
<Button
|
||||
color="primary"
|
||||
className={classes.anchorButton}
|
||||
>
|
||||
{consoleTLS ? "Enabled" : "Disabled"}
|
||||
</Button>
|
||||
</td>
|
||||
</Fragment>
|
||||
) : (
|
||||
<td />
|
||||
)}
|
||||
</tr>
|
||||
<tr>
|
||||
<td className={classes.titleCol}>Encryption:</td>
|
||||
<td>
|
||||
@@ -430,6 +462,13 @@ const mapState = (state: AppState) => ({
|
||||
"encryptionEnabled",
|
||||
false
|
||||
),
|
||||
minioTLS: get(state.tenants.tenantDetails.tenantInfo, "minioTLS", false),
|
||||
consoleTLS: get(state.tenants.tenantDetails.tenantInfo, "consoleTLS", false),
|
||||
consoleEnabled: get(
|
||||
state.tenants.tenantDetails.tenantInfo,
|
||||
"consoleEnabled",
|
||||
false
|
||||
),
|
||||
adEnabled: get(state.tenants.tenantDetails.tenantInfo, "idpAdEnabled", false),
|
||||
oicEnabled: get(
|
||||
state.tenants.tenantDetails.tenantInfo,
|
||||
|
||||
@@ -58,6 +58,24 @@ export const TENANT_DETAILS_SET_CURRENT_TENANT =
|
||||
"TENANT_DETAILS/SET_CURRENT_TENANT";
|
||||
export const TENANT_DETAILS_SET_TENANT = "TENANT_DETAILS/SET_TENANT";
|
||||
export const TENANT_DETAILS_SET_TAB = "TENANT_DETAILS/SET_TAB";
|
||||
export interface ICertificateInfo {
|
||||
name: string;
|
||||
serialNumber: string;
|
||||
domains: string[];
|
||||
expiry: string;
|
||||
}
|
||||
|
||||
export interface ICustomCertificates {
|
||||
minio: ICertificateInfo[];
|
||||
minioCAs: ICertificateInfo[];
|
||||
console: ICertificateInfo[];
|
||||
consoleCAs: ICertificateInfo[];
|
||||
}
|
||||
|
||||
export interface ITenantSecurityResponse {
|
||||
autoCert: boolean;
|
||||
customCertificates: ICustomCertificates;
|
||||
}
|
||||
|
||||
export interface ICreateTenant {
|
||||
page: number;
|
||||
|
||||
Reference in New Issue
Block a user