diff --git a/dashboard/src/App.tsx b/dashboard/src/App.tsx
index 001e7a9..c8ac2cf 100644
--- a/dashboard/src/App.tsx
+++ b/dashboard/src/App.tsx
@@ -1,4 +1,5 @@
import * as React from 'react';
+import { Fragment } from "react"
import { ChakraProvider, extendTheme } from '@chakra-ui/react';
import { BrowserRouter } from 'react-router-dom';
import { createClient, Provider } from 'urql';
@@ -36,6 +37,7 @@ const theme = extendTheme({
export default function App() {
return (
+
@@ -45,5 +47,6 @@ export default function App() {
+
);
}
diff --git a/dashboard/src/components/EnvComponents/AccessToken.tsx b/dashboard/src/components/EnvComponents/AccessToken.tsx
new file mode 100644
index 0000000..9fba521
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/AccessToken.tsx
@@ -0,0 +1,65 @@
+import React from "react";
+import { Flex, Stack, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../../components/InputField";
+import { TextInputType, TextAreaInputType } from "../../constants";
+
+const AccessToken = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Access Token
+
+
+
+
+ Access Token Expiry Time:
+
+
+
+
+
+
+
+ Custom Scripts:
+
+ (Used to add custom fields in ID token)
+
+
+
+
+
+
+
+
+ );
+};
+
+export default AccessToken;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/DatabaseCredentials.tsx b/dashboard/src/components/EnvComponents/DatabaseCredentials.tsx
new file mode 100644
index 0000000..12c85e1
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/DatabaseCredentials.tsx
@@ -0,0 +1,88 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+
+import InputField from "../../components/InputField";
+import { TextInputType } from "../../constants";
+
+const DatabaseCredentials = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Database Credentials
+
+
+
+ Note: Database related environment variables cannot be updated from
+ dashboard :(
+
+
+
+ DataBase Name:
+
+
+
+
+
+
+
+ DataBase Type:
+
+
+
+
+
+
+
+ DataBase URL:
+
+
+
+
+
+
+
+ );
+};
+
+export default DatabaseCredentials;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/DomainWhitelisting.tsx b/dashboard/src/components/EnvComponents/DomainWhitelisting.tsx
new file mode 100644
index 0000000..d7ed13f
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/DomainWhitelisting.tsx
@@ -0,0 +1,35 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../../components/InputField";
+import { ArrayInputType} from "../../constants";
+
+const DomainWhiteListing = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Domain White Listing
+
+
+
+
+ Allowed Origins:
+
+
+
+
+
+
+
+ );
+};
+
+export default DomainWhiteListing;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/EmailConfiguration.tsx b/dashboard/src/components/EnvComponents/EmailConfiguration.tsx
new file mode 100644
index 0000000..17a1eed
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/EmailConfiguration.tsx
@@ -0,0 +1,114 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../../components/InputField";
+import { TextInputType, HiddenInputType} from "../../constants";
+const EmailConfigurations = ({
+ variables,
+ setVariables,
+ fieldVisibility,
+ setFieldVisibility,
+}: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Email Configurations
+
+
+
+
+ SMTP Host:
+
+
+
+
+
+
+
+ SMTP Port:
+
+
+
+
+
+
+
+ SMTP Username:
+
+
+
+
+
+
+
+ SMTP Password:
+
+
+
+
+
+
+
+ From Email:
+
+
+
+
+
+
+
+ );
+};
+
+export default EmailConfigurations;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/JWTConfiguration.tsx b/dashboard/src/components/EnvComponents/JWTConfiguration.tsx
new file mode 100644
index 0000000..4424725
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/JWTConfiguration.tsx
@@ -0,0 +1,154 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+import {
+ HiddenInputType,
+ TextInputType,
+ TextAreaInputType,
+} from "../../constants";
+import GenerateKeysModal from "../GenerateKeysModal";
+import InputField from "../InputField";
+
+const JSTConfigurations = ({
+ variables,
+ setVariables,
+ fieldVisibility,
+ setFieldVisibility,
+ SelectInputType,
+ getData,
+ HMACEncryptionType,
+ RSAEncryptionType,
+ ECDSAEncryptionType,
+}: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+
+ return (
+
+ {" "}
+
+
+ JWT (JSON Web Tokens) Configurations
+
+
+
+
+
+
+
+
+ JWT Type:
+
+
+
+
+
+ {Object.values(HMACEncryptionType).includes(variables.JWT_TYPE) ? (
+
+
+ JWT Secret
+
+
+
+
+
+ ) : (
+ <>
+
+
+ Public Key
+
+
+
+
+
+
+
+ Private Key
+
+
+
+
+
+ >
+ )}
+
+
+
+ JWT Role Claim:
+
+
+
+
+
+
+
+
+ );
+};
+
+export default JSTConfigurations;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/OAuthConfig.tsx b/dashboard/src/components/EnvComponents/OAuthConfig.tsx
new file mode 100644
index 0000000..b06d595
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/OAuthConfig.tsx
@@ -0,0 +1,191 @@
+import React from "react";
+import InputField from "../InputField";
+import {
+ Flex,
+ Stack,
+ Center,
+ Text,
+ Box,
+ Divider,
+ useMediaQuery,
+} from "@chakra-ui/react";
+import { FaGoogle, FaGithub, FaFacebookF } from "react-icons/fa";
+import { TextInputType, HiddenInputType } from "../../constants";
+
+const OAuthConfig = ({
+ envVariables,
+ setVariables,
+ fieldVisibility,
+ setFieldVisibility,
+}: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:667px)");
+ return (
+
+
+
+ Your instance information
+
+
+
+
+ Client ID
+
+
+ {}}
+ inputType={TextInputType.CLIENT_ID}
+ placeholder="Client ID"
+ readOnly={true}
+ />
+
+
+
+
+ Client Secret
+
+
+
+
+
+
+
+ {/* ################ SOCIAL MEDIA LOGIN ################ */}
+
+ Social Media Logins
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ );
+};
+
+export default OAuthConfig;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/OrganizationInfo.tsx b/dashboard/src/components/EnvComponents/OrganizationInfo.tsx
new file mode 100644
index 0000000..c5f7e36
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/OrganizationInfo.tsx
@@ -0,0 +1,60 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../InputField";
+import { TextInputType } from "../../constants";
+
+const OrganizationInfo = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Organization Information
+
+
+
+
+ Organization Name:
+
+
+
+
+
+
+
+ Organization Logo:
+
+
+
+
+
+
+
+ );
+};
+
+export default OrganizationInfo;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/Roles.tsx b/dashboard/src/components/EnvComponents/Roles.tsx
new file mode 100644
index 0000000..ac610ab
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/Roles.tsx
@@ -0,0 +1,67 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+import { ArrayInputType } from "../../constants";
+import InputField from "../InputField";
+
+const Roles = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Roles
+
+
+
+
+ Roles:
+
+
+
+
+
+
+
+ Default Roles:
+
+
+
+
+
+
+
+ Protected Roles:
+
+
+
+
+
+
+
+ );
+};
+
+export default Roles;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/SecurityAdminSecret.tsx b/dashboard/src/components/EnvComponents/SecurityAdminSecret.tsx
new file mode 100644
index 0000000..b3e27d8
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/SecurityAdminSecret.tsx
@@ -0,0 +1,138 @@
+import React from "react";
+import {
+ Flex,
+ Stack,
+ Center,
+ Text,
+ Input,
+ InputGroup,
+ InputRightElement,
+ useMediaQuery,
+} from "@chakra-ui/react";
+import { FaRegEyeSlash, FaRegEye } from "react-icons/fa";
+import InputField from "../InputField";
+import { TextInputType, HiddenInputType } from "../../constants";
+const SecurityAdminSecret = ({
+ variables,
+ setVariables,
+ fieldVisibility,
+ setFieldVisibility,
+ validateAdminSecretHandler,
+ adminSecret,
+}: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Security (Admin Secret)
+
+
+
+
+ Old Admin Secret:
+
+
+
+ validateAdminSecretHandler(event)}
+ type={
+ !fieldVisibility[HiddenInputType.OLD_ADMIN_SECRET]
+ ? "password"
+ : "text"
+ }
+ />
+
+ {fieldVisibility[HiddenInputType.OLD_ADMIN_SECRET] ? (
+
+ setFieldVisibility({
+ ...fieldVisibility,
+ [HiddenInputType.OLD_ADMIN_SECRET]: false,
+ })
+ }
+ >
+
+
+ ) : (
+
+ setFieldVisibility({
+ ...fieldVisibility,
+ [HiddenInputType.OLD_ADMIN_SECRET]: true,
+ })
+ }
+ >
+
+
+ )}
+
+ }
+ />
+
+
+
+
+
+ New Admin Secret:
+
+
+
+
+
+
+
+ );
+};
+
+export default SecurityAdminSecret;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/SessionStorage.tsx b/dashboard/src/components/EnvComponents/SessionStorage.tsx
new file mode 100644
index 0000000..8570f47
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/SessionStorage.tsx
@@ -0,0 +1,36 @@
+import React from "react";
+import { Flex, Stack, Center, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../InputField";
+
+const SessionStorage = ({ variables, setVariables, RedisURL }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Session Storage
+
+
+
+
+ Redis URL:
+
+
+
+
+
+
+
+ );
+};
+
+export default SessionStorage;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/SocialMediaLogin.tsx b/dashboard/src/components/EnvComponents/SocialMediaLogin.tsx
new file mode 100644
index 0000000..38df534
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/SocialMediaLogin.tsx
@@ -0,0 +1,80 @@
+import React from "react";
+import { Flex, Stack, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../InputField";
+import { SwitchInputType } from "../../constants";
+
+const UICustomization = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Disable Features
+
+
+
+
+ Disable Login Page:
+
+
+
+
+
+
+
+ Disable Email Verification:
+
+
+
+
+
+
+
+ Disable Magic Login Link:
+
+
+
+
+
+
+
+ Disable Basic Authentication:
+
+
+
+
+
+
+
+ Disable Sign Up:
+
+
+
+
+
+
+
+ );
+};
+
+export default UICustomization;
\ No newline at end of file
diff --git a/dashboard/src/components/EnvComponents/UICustomization.tsx b/dashboard/src/components/EnvComponents/UICustomization.tsx
new file mode 100644
index 0000000..38df534
--- /dev/null
+++ b/dashboard/src/components/EnvComponents/UICustomization.tsx
@@ -0,0 +1,80 @@
+import React from "react";
+import { Flex, Stack, Text, useMediaQuery } from "@chakra-ui/react";
+import InputField from "../InputField";
+import { SwitchInputType } from "../../constants";
+
+const UICustomization = ({ variables, setVariables }: any) => {
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+ {" "}
+
+ Disable Features
+
+
+
+
+ Disable Login Page:
+
+
+
+
+
+
+
+ Disable Email Verification:
+
+
+
+
+
+
+
+ Disable Magic Login Link:
+
+
+
+
+
+
+
+ Disable Basic Authentication:
+
+
+
+
+
+
+
+ Disable Sign Up:
+
+
+
+
+
+
+
+ );
+};
+
+export default UICustomization;
\ No newline at end of file
diff --git a/dashboard/src/components/InputField.tsx b/dashboard/src/components/InputField.tsx
index ede074d..8e58189 100644
--- a/dashboard/src/components/InputField.tsx
+++ b/dashboard/src/components/InputField.tsx
@@ -116,7 +116,7 @@ const InputField = ({
3 ? "scroll" : "hidden"}
+ overflowY="hidden"
+ justifyContent="start"
+ alignItems="center"
>
{variables[inputType].map((role: string, index: number) => (
@@ -220,7 +221,7 @@ const InputField = ({
size="xs"
minW="150px"
placeholder="add a new value"
- value={inputData[inputType]}
+ value={inputData[inputType] ?? ''}
onChange={(e: any) => {
setInputData({ ...inputData, [inputType]: e.target.value });
}}
diff --git a/dashboard/src/components/Menu.tsx b/dashboard/src/components/Menu.tsx
index a8e2fdd..8c1883b 100644
--- a/dashboard/src/components/Menu.tsx
+++ b/dashboard/src/components/Menu.tsx
@@ -1,233 +1,362 @@
-import React, { ReactNode } from 'react';
+import React, { ReactNode } from "react";
import {
- IconButton,
- Box,
- CloseButton,
- Flex,
- Image,
- HStack,
- VStack,
- Icon,
- useColorModeValue,
- Link,
- Text,
- BoxProps,
- FlexProps,
- Menu,
- MenuButton,
- MenuItem,
- MenuList,
-} from '@chakra-ui/react';
+ IconButton,
+ Box,
+ CloseButton,
+ Flex,
+ Image,
+ HStack,
+ VStack,
+ Icon,
+ useColorModeValue,
+ Link,
+ Text,
+ BoxProps,
+ FlexProps,
+ Menu,
+ MenuButton,
+ MenuItem,
+ MenuList,
+ Accordion,
+ AccordionButton,
+ AccordionPanel,
+ AccordionItem,
+ AccordionIcon,
+ useMediaQuery,
+} from "@chakra-ui/react";
import {
- FiHome,
- FiCode,
- FiSettings,
- FiMenu,
- FiUser,
- FiUsers,
- FiChevronDown,
-} from 'react-icons/fi';
-import { IconType } from 'react-icons';
-import { ReactText } from 'react';
-import { useMutation, useQuery } from 'urql';
-import { NavLink, useNavigate, useLocation } from 'react-router-dom';
-import { useAuthContext } from '../contexts/AuthContext';
-import { AdminLogout } from '../graphql/mutation';
-import { MetaQuery } from '../graphql/queries';
+ FiHome,
+ FiUser,
+ FiGlobe,
+ FiCode,
+ FiSettings,
+ FiMenu,
+ FiUsers,
+ FiChevronDown,
+ FiShieldOff,
+} from "react-icons/fi";
+import { BiCustomize } from "react-icons/bi";
+import { FcDatabase } from "react-icons/fc";
+import { AiOutlineKey } from "react-icons/ai";
+import { SiOpenaccess, SiJsonwebtokens } from "react-icons/si";
+import { MdSecurity } from "react-icons/md";
+import { RiSkullLine } from "react-icons/ri";
+import { RiDatabase2Line } from "react-icons/ri";
+import { BsCheck2Circle } from "react-icons/bs";
+import { HiOutlineMail, HiOutlineOfficeBuilding } from "react-icons/hi";
+import { IconType } from "react-icons";
+import { ReactText } from "react";
+import { useMutation, useQuery } from "urql";
+import { NavLink, useNavigate, useLocation } from "react-router-dom";
+import { useAuthContext } from "../contexts/AuthContext";
+import { AdminLogout } from "../graphql/mutation";
+import { MetaQuery } from "../graphql/queries";
+
+interface SubRoutes {
+ name: string;
+ icon: IconType;
+ route: string;
+}
interface LinkItemProps {
- name: string;
- icon: IconType;
- route: string;
+ name: string;
+ icon: IconType;
+ route: string;
+ subRoutes?: SubRoutes[];
}
const LinkItems: Array = [
- // { name: 'Home', icon: FiHome, route: '/' },
- { name: 'Environment Variables', icon: FiSettings, route: '/' },
- { name: 'Users', icon: FiUsers, route: '/users' },
+ {
+ name: "Environment ",
+ icon: FiSettings,
+ route: "/",
+ subRoutes: [
+ {
+ name: "OAuth Config",
+ icon: AiOutlineKey,
+ route: "/oauth-setting",
+ },
+
+ { name: "Roles", icon: FiUser, route: "/roles" },
+ {
+ name: "JWT Secrets",
+ icon: SiJsonwebtokens,
+ route: "/jwt-config",
+ },
+ {
+ name: "Session Storage",
+ icon: RiDatabase2Line,
+ route: "/session-storage",
+ },
+ {
+ name: "Email Configurations",
+ icon: HiOutlineMail,
+ route: "/email-config",
+ },
+ {
+ name: "Domain White Listing",
+ icon: BsCheck2Circle,
+ route: "/whitelist-variables",
+ },
+ {
+ name: "Organization Info",
+ icon: HiOutlineOfficeBuilding,
+ route: "/organization-info",
+ },
+ { name: "Access Token", icon: SiOpenaccess, route: "/access-token" },
+ {
+ name: "UI Customization",
+ icon: BiCustomize,
+ route: "/ui-customization",
+ },
+ { name: "Database", icon: RiDatabase2Line, route: "/db-cred" },
+ {
+ name: " Security",
+ icon: MdSecurity,
+ route: "/admin-secret",
+ },
+ ],
+ },
+ { name: "Users", icon: FiUsers, route: "/users" },
+ // { name: "AUsers", icon: FiUsers, route: "/usersa" },
];
interface SidebarProps extends BoxProps {
- onClose: () => void;
+ onClose: () => void;
}
export const Sidebar = ({ onClose, ...rest }: SidebarProps) => {
- const { pathname } = useLocation();
- const [{ fetching, data }] = useQuery({ query: MetaQuery });
- return (
-
-
-
-
-
-
- AUTHORIZER
-
-
-
-
-
- {LinkItems.map((link) => (
-
-
- {link.name}
-
-
- ))}
+ const { pathname } = useLocation();
+ const [{ fetching, data }] = useQuery({ query: MetaQuery });
+ const [isNotSmallerScreen] = useMediaQuery("(min-width:600px)");
+ return (
+
+
+
+
+
+
+ AUTHORIZER
+
+
+
+
+
-
- API Playground
-
+
+
+ {LinkItems.map((link) =>
+ link?.subRoutes ? (
+
+
+
+
+ {link.name}
+
+
+
+
+
+
+
+ {link.subRoutes?.map((sublink) => (
+
+ {" "}
+
+
+ {sublink.name}
+ {" "}
+
+
+ ))}
+
+
+ ) : (
+
+ {" "}
+
+
+ {link.name}
+ {" "}
+
+
+ )
+ )}
+
+ API Playground
+
+
+
- {data?.meta?.version && (
-
- Current Version: {data.meta.version}
-
- )}
-
- );
+ {data?.meta?.version && (
+
+ {" "}
+
+ Current Version: {data.meta.version}
+
+
+ )}
+
+ );
};
interface NavItemProps extends FlexProps {
- icon: IconType;
- children: ReactText;
+ icon: IconType;
+ children: ReactText;
}
export const NavItem = ({ icon, children, ...rest }: NavItemProps) => {
- return (
-
- {icon && (
-
- )}
- {children}
-
- );
+ return (
+
+ {icon && (
+
+ )}
+ {children}
+
+ );
};
interface MobileProps extends FlexProps {
- onOpen: () => void;
+ onOpen: () => void;
}
export const MobileNav = ({ onOpen, ...rest }: MobileProps) => {
- const [_, logout] = useMutation(AdminLogout);
- const { setIsLoggedIn } = useAuthContext();
- const navigate = useNavigate();
+ const [_, logout] = useMutation(AdminLogout);
+ const { setIsLoggedIn } = useAuthContext();
+ const navigate = useNavigate();
- const handleLogout = async () => {
- await logout();
- setIsLoggedIn(false);
- navigate('/', { replace: true });
- };
+ const handleLogout = async () => {
+ await logout();
+ setIsLoggedIn(false);
+ navigate("/", { replace: true });
+ };
- return (
-
- }
- />
+ return (
+
+ }
+ />
-
+
-
-
-
-
-
-
- );
-};
+
+
+
+
+
+
+ );
+};
\ No newline at end of file
diff --git a/dashboard/src/pages/Environment.tsx b/dashboard/src/pages/Environment.tsx
index a6ef5a5..db09298 100644
--- a/dashboard/src/pages/Environment.tsx
+++ b/dashboard/src/pages/Environment.tsx
@@ -1,847 +1,324 @@
-import React, { useEffect } from 'react';
+import React, { useEffect } from "react";
+import { useParams } from "react-router-dom";
+import { Box, Flex, Stack, Button, useToast } from "@chakra-ui/react";
+import { useClient } from "urql";
+import { FaSave } from "react-icons/fa";
+import _ from "lodash";
+import { EnvVariablesQuery } from "../graphql/queries";
import {
- Box,
- Divider,
- Flex,
- Stack,
- Center,
- Text,
- Button,
- Input,
- InputGroup,
- InputRightElement,
- useToast,
-} from '@chakra-ui/react';
-import { useClient } from 'urql';
-import {
- FaGoogle,
- FaGithub,
- FaFacebookF,
- FaSave,
- FaRegEyeSlash,
- FaRegEye,
-} from 'react-icons/fa';
-import _ from 'lodash';
-import InputField from '../components/InputField';
-import { EnvVariablesQuery } from '../graphql/queries';
-import {
- ArrayInputType,
- SelectInputType,
- HiddenInputType,
- TextInputType,
- TextAreaInputType,
- SwitchInputType,
- HMACEncryptionType,
- RSAEncryptionType,
- ECDSAEncryptionType,
- envVarTypes,
-} from '../constants';
-import { UpdateEnvVariables } from '../graphql/mutation';
-import { getObjectDiff, capitalizeFirstLetter } from '../utils';
-import GenerateKeysModal from '../components/GenerateKeysModal';
+ SelectInputType,
+ HiddenInputType,
+ TextInputType,
+ HMACEncryptionType,
+ RSAEncryptionType,
+ ECDSAEncryptionType,
+ envVarTypes,
+} from "../constants";
+import { UpdateEnvVariables } from "../graphql/mutation";
+import { getObjectDiff, capitalizeFirstLetter } from "../utils";
+// Component inputs
+import OAuthConfig from "../components/EnvComponents/OAuthConfig";
+import Roles from "../components/EnvComponents/Roles";
+import JWTConfigurations from "../components/EnvComponents/JWTConfiguration";
+import SessionStorage from "../components/EnvComponents/SessionStorage";
+import EmailConfigurations from "../components/EnvComponents/EmailConfiguration";
+import DomainWhiteListing from "../components/EnvComponents/DomainWhitelisting";
+import OrganizationInfo from "../components/EnvComponents/OrganizationInfo";
+import AccessToken from "../components/EnvComponents/AccessToken";
+import UICustomization from "../components/EnvComponents/UICustomization"
+import SecurityAdminSecret from "../components/EnvComponents/SecurityAdminSecret";
+import DatabaseCredentials from "../components/EnvComponents/DatabaseCredentials";
-export default function Environment() {
- const client = useClient();
- const toast = useToast();
- const [adminSecret, setAdminSecret] = React.useState<
- Record
- >({
- value: '',
- disableInputField: true,
- });
- const [loading, setLoading] = React.useState(true);
- const [envVariables, setEnvVariables] = React.useState({
- GOOGLE_CLIENT_ID: '',
- GOOGLE_CLIENT_SECRET: '',
- GITHUB_CLIENT_ID: '',
- GITHUB_CLIENT_SECRET: '',
- FACEBOOK_CLIENT_ID: '',
- FACEBOOK_CLIENT_SECRET: '',
- ROLES: [],
- DEFAULT_ROLES: [],
- PROTECTED_ROLES: [],
- JWT_TYPE: '',
- JWT_SECRET: '',
- JWT_ROLE_CLAIM: '',
- JWT_PRIVATE_KEY: '',
- JWT_PUBLIC_KEY: '',
- REDIS_URL: '',
- SMTP_HOST: '',
- SMTP_PORT: '',
- SMTP_USERNAME: '',
- SMTP_PASSWORD: '',
- SENDER_EMAIL: '',
- ALLOWED_ORIGINS: [],
- ORGANIZATION_NAME: '',
- ORGANIZATION_LOGO: '',
- CUSTOM_ACCESS_TOKEN_SCRIPT: '',
- ADMIN_SECRET: '',
- DISABLE_LOGIN_PAGE: false,
- DISABLE_MAGIC_LINK_LOGIN: false,
- DISABLE_EMAIL_VERIFICATION: false,
- DISABLE_BASIC_AUTHENTICATION: false,
- DISABLE_SIGN_UP: false,
- OLD_ADMIN_SECRET: '',
- DATABASE_NAME: '',
- DATABASE_TYPE: '',
- DATABASE_URL: '',
- ACCESS_TOKEN_EXPIRY_TIME: '',
- });
+const Environment = () => {
+ const client = useClient();
+ const toast = useToast();
+ const [adminSecret, setAdminSecret] = React.useState<
+ Record
+ >({
+ value: "",
+ disableInputField: true,
+ });
+ const [loading, setLoading] = React.useState(true);
+ const [envVariables, setEnvVariables] = React.useState({
+ GOOGLE_CLIENT_ID: "",
+ GOOGLE_CLIENT_SECRET: "",
+ GITHUB_CLIENT_ID: "",
+ GITHUB_CLIENT_SECRET: "",
+ FACEBOOK_CLIENT_ID: "",
+ FACEBOOK_CLIENT_SECRET: "",
+ ROLES: [],
+ DEFAULT_ROLES: [],
+ PROTECTED_ROLES: [],
+ JWT_TYPE: "",
+ JWT_SECRET: "",
+ JWT_ROLE_CLAIM: "",
+ JWT_PRIVATE_KEY: "",
+ JWT_PUBLIC_KEY: "",
+ REDIS_URL: "",
+ SMTP_HOST: "",
+ SMTP_PORT: "",
+ SMTP_USERNAME: "",
+ SMTP_PASSWORD: "",
+ SENDER_EMAIL: "",
+ ALLOWED_ORIGINS: [],
+ ORGANIZATION_NAME: "",
+ ORGANIZATION_LOGO: "",
+ CUSTOM_ACCESS_TOKEN_SCRIPT: "",
+ ADMIN_SECRET: "",
+ DISABLE_LOGIN_PAGE: false,
+ DISABLE_MAGIC_LINK_LOGIN: false,
+ DISABLE_EMAIL_VERIFICATION: false,
+ DISABLE_BASIC_AUTHENTICATION: false,
+ DISABLE_SIGN_UP: false,
+ OLD_ADMIN_SECRET: "",
+ DATABASE_NAME: "",
+ DATABASE_TYPE: "",
+ DATABASE_URL: "",
+ ACCESS_TOKEN_EXPIRY_TIME: "",
+ });
- const [fieldVisibility, setFieldVisibility] = React.useState<
- Record
- >({
- GOOGLE_CLIENT_SECRET: false,
- GITHUB_CLIENT_SECRET: false,
- FACEBOOK_CLIENT_SECRET: false,
- JWT_SECRET: false,
- SMTP_PASSWORD: false,
- ADMIN_SECRET: false,
- OLD_ADMIN_SECRET: false,
- });
+ const [fieldVisibility, setFieldVisibility] = React.useState<
+ Record
+ >({
+ GOOGLE_CLIENT_SECRET: false,
+ GITHUB_CLIENT_SECRET: false,
+ FACEBOOK_CLIENT_SECRET: false,
+ JWT_SECRET: false,
+ SMTP_PASSWORD: false,
+ ADMIN_SECRET: false,
+ OLD_ADMIN_SECRET: false,
+ });
- async function getData() {
- const {
- data: { _env: envData },
- } = await client.query(EnvVariablesQuery).toPromise();
- setLoading(false);
- setEnvVariables({
- ...envData,
- OLD_ADMIN_SECRET: envData.ADMIN_SECRET,
- ADMIN_SECRET: '',
- });
- setAdminSecret({
- value: '',
- disableInputField: true,
- });
- }
+ const { sec } = useParams();
- useEffect(() => {
- getData();
- }, []);
+ async function getData() {
+ const {
+ data: { _env: envData },
+ } = await client.query(EnvVariablesQuery).toPromise();
+ setLoading(false);
- const validateAdminSecretHandler = (event: any) => {
- if (envVariables.OLD_ADMIN_SECRET === event.target.value) {
- setAdminSecret({
- ...adminSecret,
- value: event.target.value,
- disableInputField: false,
- });
- } else {
- setAdminSecret({
- ...adminSecret,
- value: event.target.value,
- disableInputField: true,
- });
- }
- if (envVariables.ADMIN_SECRET !== '') {
- setEnvVariables({ ...envVariables, ADMIN_SECRET: '' });
- }
- };
+ setEnvVariables({
+ ...envData,
+ OLD_ADMIN_SECRET: envData.ADMIN_SECRET,
+ ADMIN_SECRET: "",
+ });
+ setAdminSecret({
+ value: "",
+ disableInputField: true,
+ });
+ }
- const saveHandler = async () => {
- setLoading(true);
- const {
- data: { _env: envData },
- } = await client.query(EnvVariablesQuery).toPromise();
- const diff = getObjectDiff(envVariables, envData);
- const updatedEnvVariables = diff.reduce(
- (acc: any, property: string) => ({
- ...acc,
- // @ts-ignore
- [property]: envVariables[property],
- }),
- {}
- );
- if (
- updatedEnvVariables[HiddenInputType.ADMIN_SECRET] === '' ||
- updatedEnvVariables[HiddenInputType.OLD_ADMIN_SECRET] !==
- envData.ADMIN_SECRET
- ) {
- delete updatedEnvVariables.OLD_ADMIN_SECRET;
- delete updatedEnvVariables.ADMIN_SECRET;
- }
+ useEffect(() => {
+ getData();
+ }, [sec]);
- delete updatedEnvVariables.DATABASE_URL;
- delete updatedEnvVariables.DATABASE_TYPE;
- delete updatedEnvVariables.DATABASE_NAME;
+ const validateAdminSecretHandler = (event: any) => {
+ if (envVariables.OLD_ADMIN_SECRET === event.target.value) {
+ setAdminSecret({
+ ...adminSecret,
+ value: event.target.value,
+ disableInputField: false,
+ });
+ } else {
+ setAdminSecret({
+ ...adminSecret,
+ value: event.target.value,
+ disableInputField: true,
+ });
+ }
+ if (envVariables.ADMIN_SECRET !== "") {
+ setEnvVariables({ ...envVariables, ADMIN_SECRET: "" });
+ }
+ };
- const res = await client
- .mutation(UpdateEnvVariables, { params: updatedEnvVariables })
- .toPromise();
+ const saveHandler = async () => {
+ setLoading(true);
+ const {
+ data: { _env: envData },
+ } = await client.query(EnvVariablesQuery).toPromise();
+ const diff = getObjectDiff(envVariables, envData);
+ const updatedEnvVariables = diff.reduce(
+ (acc: any, property: string) => ({
+ ...acc,
+ // @ts-ignore
+ [property]: envVariables[property],
+ }),
+ {}
+ );
+ if (
+ updatedEnvVariables[HiddenInputType.ADMIN_SECRET] === "" ||
+ updatedEnvVariables[HiddenInputType.OLD_ADMIN_SECRET] !==
+ envData.ADMIN_SECRET
+ ) {
+ delete updatedEnvVariables.OLD_ADMIN_SECRET;
+ delete updatedEnvVariables.ADMIN_SECRET;
+ }
- setLoading(false);
+ delete updatedEnvVariables.DATABASE_URL;
+ delete updatedEnvVariables.DATABASE_TYPE;
+ delete updatedEnvVariables.DATABASE_NAME;
- if (res.error) {
- toast({
- title: capitalizeFirstLetter(res.error.message),
- isClosable: true,
- status: 'error',
- position: 'bottom-right',
- });
+ const res = await client
+ .mutation(UpdateEnvVariables, { params: updatedEnvVariables })
+ .toPromise();
- return;
- }
+ setLoading(false);
- setAdminSecret({
- value: '',
- disableInputField: true,
- });
+ if (res.error) {
+ toast({
+ title: capitalizeFirstLetter(res.error.message),
+ isClosable: true,
+ status: "error",
+ position: "bottom-right",
+ });
- getData();
+ return;
+ }
- toast({
- title: `Successfully updated ${
- Object.keys(updatedEnvVariables).length
- } variables`,
- isClosable: true,
- status: 'success',
- position: 'bottom-right',
- });
- };
+ setAdminSecret({
+ value: "",
+ disableInputField: true,
+ });
- return (
-
-
- Your instance information
-
-
-
-
- Client ID
-
-
- {}}
- inputType={TextInputType.CLIENT_ID}
- placeholder="Client ID"
- readOnly={true}
- />
-
-
-
-
- Client Secret
-
-
-
-
-
-
-
-
- Social Media Logins
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- Roles
-
-
-
-
- Roles:
-
-
-
-
-
-
-
- Default Roles:
-
-
-
-
-
-
-
- Protected Roles:
-
-
-
-
-
-
-
-
-
- JWT (JSON Web Tokens) Configurations
-
-
-
-
-
-
-
-
- JWT Type:
-
-
-
-
-
- {Object.values(HMACEncryptionType).includes(envVariables.JWT_TYPE) ? (
-
-
- JWT Secret
-
-
-
-
-
- ) : (
- <>
-
-
- Public Key
-
-
-
-
-
-
-
- Private Key
-
-
-
-
-
- >
- )}
-
-
- JWT Role Claim:
-
-
-
-
-
-
-
-
- Session Storage
-
-
-
-
- Redis URL:
-
-
-
-
-
-
-
-
- Email Configurations
-
-
-
-
- SMTP Host:
-
-
-
-
-
-
-
- SMTP Port:
-
-
-
-
-
-
-
- SMTP Username:
-
-
-
-
-
-
-
- SMTP Password:
-
-
-
-
-
-
-
- From Email:
-
-
-
-
-
-
-
-
- White Listing
-
-
-
-
- Allowed Origins:
-
-
-
-
-
-
-
-
- Organization Information
-
-
-
-
- Organization Name:
-
-
-
-
-
-
-
- Organization Logo:
-
-
-
-
-
-
-
-
- Access Token
-
-
-
-
- Access Token Expiry Time:
-
-
-
-
-
-
-
- Custom Scripts:
- Used to add custom fields in ID token
-
-
-
-
-
-
-
-
- Disable Features
-
-
-
-
- Disable Login Page:
-
-
-
-
-
-
-
- Disable Email Verification:
-
-
-
-
-
-
-
- Disable Magic Login Link:
-
-
-
-
-
-
-
- Disable Basic Authentication:
-
-
-
-
-
-
-
- Disable Sign Up:
-
-
-
-
-
-
-
-
- Danger
-
-
-
-
- Note: Database related environment variables cannot be updated from
- dashboard :(
-
-
-
- DataBase Name:
-
-
-
-
-
-
-
- DataBase Type:
-
-
-
-
-
-
-
- DataBase URL:
-
-
-
-
-
-
-
-
- Old Admin Secret:
-
-
-
- validateAdminSecretHandler(event)}
- type={
- !fieldVisibility[HiddenInputType.OLD_ADMIN_SECRET]
- ? 'password'
- : 'text'
- }
- />
-
- {fieldVisibility[HiddenInputType.OLD_ADMIN_SECRET] ? (
-
- setFieldVisibility({
- ...fieldVisibility,
- [HiddenInputType.OLD_ADMIN_SECRET]: false,
- })
- }
- >
-
-
- ) : (
-
- setFieldVisibility({
- ...fieldVisibility,
- [HiddenInputType.OLD_ADMIN_SECRET]: true,
- })
- }
- >
-
-
- )}
-
- }
- />
-
-
-
-
-
- New Admin Secret:
-
-
-
-
-
-
-
-
-
- }
- colorScheme="blue"
- variant="solid"
- onClick={saveHandler}
- isDisabled={loading}
- >
- Save
-
-
-
-
- );
-}
+ getData();
+
+ toast({
+ title: `Successfully updated ${
+ Object.keys(updatedEnvVariables).length
+ } variables`,
+ isClosable: true,
+ status: "success",
+ position: "bottom-right",
+ });
+ };
+
+ const getCorrectScreen = (tab: any) => {
+ switch (tab) {
+ case "instance-info":
+ return (
+
+ );
+
+ case "roles":
+ return (
+
+ );
+ case "jwt-config":
+ return (
+
+ );
+ case "session-storage":
+ return (
+
+ );
+ case "email-config":
+ return (
+
+ );
+ case "whitelist-variables":
+ return (
+
+ );
+ case "organization-info":
+ return (
+
+ );
+ case "access-token":
+ return (
+
+ );
+ case "ui-customization":
+ return (
+
+ );
+ case "admin-secret":
+ return (
+
+ );
+ case "db-cred":
+ return (
+
+ );
+ default:
+ return (
+
+ );
+ }
+ };
+ return (
+
+ {getCorrectScreen(sec)}
+
+
+ }
+ colorScheme="blue"
+ variant="solid"
+ onClick={saveHandler}
+ isDisabled={loading}
+ >
+ Save
+
+
+
+
+ );
+};
+
+export default Environment;
\ No newline at end of file
diff --git a/dashboard/src/routes/index.tsx b/dashboard/src/routes/index.tsx
index 8443372..f611e92 100644
--- a/dashboard/src/routes/index.tsx
+++ b/dashboard/src/routes/index.tsx
@@ -14,6 +14,7 @@ export const AppRoutes = () => {
if (isLoggedIn) {
return (
+
>}>
{
+
);
}
return (