Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion portal-ui/src/MainRouter.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ import LoadingComponent from "./common/LoadingComponent";
import AppConsole from "./screens/Console/ConsoleKBar";
import { baseUrl } from "./history";

const Login = React.lazy(() => import("./screens/LoginPage/LoginPage"));
const Login = React.lazy(() => import("./screens/LoginPage/Login"));
const Logout = React.lazy(() => import("./screens/LogoutPage/LogoutPage"));
const LoginCallback = React.lazy(
() => import("./screens/LoginPage/LoginCallback")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,21 +17,16 @@
import React, { Fragment, useEffect } from "react";
import { useNavigate } from "react-router-dom";
import { Box, Button, Loader, LoginWrapper, RefreshIcon } from "mds";
import { loginStrategyType, redirectRule } from "./types";
import { loginStrategyType } from "./login.types";
import MainError from "../Console/Common/MainError/MainError";
import { AppState, useAppDispatch } from "../../store";
import { useSelector } from "react-redux";
import { getFetchConfigurationAsync, getVersionAsync } from "./loginThunks";
import { resetForm } from "./loginSlice";
import StrategyForm from "./StrategyForm";
import { redirectRules } from "../../utils/sortFunctions";
import { getLogoVar } from "../../config";

export interface LoginStrategyPayload {
accessKey: string;
secretKey: string;
sts?: string;
}
import { RedirectRule } from "api/consoleApi";
import { redirectRules } from "./login.utils";

export const getTargetPath = () => {
let targetPath = "/";
Expand Down Expand Up @@ -90,7 +85,7 @@ const Login = () => {
switch (loginStrategy.loginStrategy) {
case loginStrategyType.redirect:
case loginStrategyType.form: {
let redirectItems: redirectRule[] = [];
let redirectItems: RedirectRule[] = [];

if (
loginStrategy.redirectRules &&
Expand Down
6 changes: 3 additions & 3 deletions portal-ui/src/screens/LoginPage/StrategyForm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -38,9 +38,9 @@ import { LinearProgress } from "@mui/material";
import { AppState, useAppDispatch } from "../../store";
import { useSelector } from "react-redux";
import { doLoginAsync } from "./loginThunks";
import { IStrategyForm } from "./types";
import { RedirectRule } from "api/consoleApi";

const StrategyForm = ({ redirectRules }: IStrategyForm) => {
const StrategyForm = ({ redirectRules }: { redirectRules: RedirectRule[] }) => {
const dispatch = useAppDispatch();

const [ssoOptionsOpen, ssoOptionsSetOpen] = useState<boolean>(false);
Expand Down Expand Up @@ -137,7 +137,7 @@ const StrategyForm = ({ redirectRules }: IStrategyForm) => {
setAnchorEl(e.currentTarget);
return;
}
submitSSOInitRequest(redirectRules[0].redirect);
submitSSOInitRequest(`${redirectRules[0].redirect}`);
}}
/>
{redirectRules.length > 1 && (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,23 +14,6 @@
// 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/>.

export interface ILoginDetails {
loginStrategy: loginStrategyType;
redirectRules: redirectRule[];
isK8S?: boolean;
animatedLogin?: boolean;
}

export interface redirectRule {
redirect: string;
displayName: string;
serviceType?: string;
}

export interface IStrategyForm {
redirectRules: redirectRule[];
}

export enum loginStrategyType {
unknown = "unknown",
form = "form",
Expand Down
29 changes: 29 additions & 0 deletions portal-ui/src/screens/LoginPage/login.utils.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
// This file is part of MinIO Console Server
// Copyright (c) 2023 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 { RedirectRule } from "api/consoleApi";

export const redirectRules = (a: RedirectRule, b: RedirectRule) => {
if (a.displayName && b.displayName) {
if (a.displayName > b.displayName) {
return 1;
}
if (a.displayName < b.displayName) {
return -1;
}
}
return 0;
};
6 changes: 3 additions & 3 deletions portal-ui/src/screens/LoginPage/loginSlice.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>.

import { createSlice, PayloadAction } from "@reduxjs/toolkit";
import { ILoginDetails, loginStrategyType } from "./types";
import { LoginDetails } from "api/consoleApi";
import {
doLoginAsync,
getFetchConfigurationAsync,
Expand All @@ -28,7 +28,7 @@ export interface LoginState {
sts: string;
useSTS: boolean;
backgroundAnimation: boolean;
loginStrategy: ILoginDetails;
loginStrategy: LoginDetails;
loginSending: boolean;
loadingFetchConfiguration: boolean;
latestMinIOVersion: string;
Expand All @@ -44,7 +44,7 @@ const initialState: LoginState = {
sts: "",
useSTS: false,
loginStrategy: {
loginStrategy: loginStrategyType.unknown,
loginStrategy: undefined,
redirectRules: [],
},
loginSending: false,
Expand Down
72 changes: 40 additions & 32 deletions portal-ui/src/screens/LoginPage/loginThunks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,18 @@

import { createAsyncThunk } from "@reduxjs/toolkit";
import { AppState } from "../../store";
import api from "../../common/api";
import { ErrorResponseHandler } from "../../common/types";
import { setErrorSnackMessage, userLogged } from "../../systemSlice";
import { ILoginDetails } from "./types";
import { setNavigateTo } from "./loginSlice";
import { getTargetPath, LoginStrategyPayload } from "./LoginPage";
import { getTargetPath } from "./Login";
import { api } from "api";
import {
CheckVersionResponse,
Error,
HttpResponse,
LoginDetails,
LoginRequest,
} from "api/consoleApi";
import { errorToHandler } from "api/errors";

export const doLoginAsync = createAsyncThunk(
"login/doLoginAsync",
Expand All @@ -32,63 +38,65 @@ export const doLoginAsync = createAsyncThunk(
const sts = state.login.sts;
const useSTS = state.login.useSTS;

let loginStrategyPayload: LoginStrategyPayload = {
let payload: LoginRequest = {
accessKey,
secretKey,
};
if (useSTS) {
loginStrategyPayload = {
payload = {
accessKey,
secretKey,
sts,
};
}

return api
.invoke("POST", "/api/v1/login", loginStrategyPayload)
.then((res) => {
return api.login
.login(payload)
.then((res: HttpResponse<void, Error>) => {
// We set the state in redux
dispatch(userLogged(true));
localStorage.setItem("userLoggedIn", accessKey);
dispatch(setNavigateTo(getTargetPath()));
})
.catch((err) => {
dispatch(setErrorSnackMessage(err));
.catch(async (res: HttpResponse<void, Error>) => {
const err = (await res.json()) as Error;
dispatch(setErrorSnackMessage(errorToHandler(err)));
return rejectWithValue(false);
});
}
);
export const getFetchConfigurationAsync = createAsyncThunk(
"login/getFetchConfigurationAsync",
async (_, { getState, rejectWithValue, dispatch }) => {
return api
.invoke("GET", "/api/v1/login")
.then((loginDetails: ILoginDetails) => {
return loginDetails;
async (_, { dispatch, rejectWithValue }) => {
return api.login
.loginDetail()
.then((res: HttpResponse<LoginDetails, Error>) => {
if (res.data) {
return res.data;
}
})
.catch((err: ErrorResponseHandler) => {
dispatch(setErrorSnackMessage(err));
.catch(async (res: HttpResponse<LoginDetails, Error>) => {
const err = (await res.json()) as Error;
dispatch(setErrorSnackMessage(errorToHandler(err)));
return rejectWithValue(false);
});
}
);

export const getVersionAsync = createAsyncThunk(
"login/getVersionAsync",
async (_, { getState, rejectWithValue, dispatch }) => {
return api
.invoke("GET", "/api/v1/check-version")
.then(
({
current_version,
latest_version,
}: {
current_version: string;
latest_version: string;
}) => {
return latest_version;
return api.checkVersion
.checkMinIoVersion()
.then((res: HttpResponse<CheckVersionResponse, Error>) => {
if (res.data !== undefined) {
return res.data.latest_version;
}
)
.catch((err: ErrorResponseHandler) => {
return err.errorMessage;
})
.catch(async (res: HttpResponse<CheckVersionResponse, Error>) => {
const err = (await res.json()) as Error;
dispatch(setErrorSnackMessage(errorToHandler(err)));
return rejectWithValue(false);
});
}
);
13 changes: 1 addition & 12 deletions portal-ui/src/utils/sortFunctions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,7 @@
// 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 { Policy } from "../api/consoleApi";
import { redirectRule } from "../screens/LoginPage/types";
import { Policy } from "api/consoleApi";

interface userInterface {
accessKey: string;
Expand Down Expand Up @@ -71,13 +70,3 @@ export const policyDetailsSort = (
// a must be equal to b
return 0;
};

export const redirectRules = (a: redirectRule, b: redirectRule) => {
if (a.displayName > b.displayName) {
return 1;
}
if (a.displayName < b.displayName) {
return -1;
}
return 0;
};
4 changes: 3 additions & 1 deletion portal-ui/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
"noEmit": true,
"jsx": "react-jsx",
"downlevelIteration": true,
"noFallthroughCasesInSwitch": true
"noFallthroughCasesInSwitch": true,
"baseUrl": "./src",
"rootDir": "./src"
},
"include": ["src"]
}