Skip to content

Commit

Permalink
Merge branch 'main' into chore-cypress-integration-login-module
Browse files Browse the repository at this point in the history
  • Loading branch information
JeevaRamu0104 authored Jan 18, 2024
2 parents 7f488a5 + 038a714 commit f9da50e
Show file tree
Hide file tree
Showing 20 changed files with 344 additions and 209 deletions.
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,18 @@ All notable changes to this project will be documented in this file. See [conven

- - -

## 1.25.1 (2024-01-17)

### Miscellaneous Tasks

- Sidebar refactoring & permissions added ([#264](https://github.com/juspay/hyperswitch-control-center/pull/264)) ([`f428679`](https://github.com/juspay/hyperswitch-control-center/commit/f428679fa9b98e002e8bb1f670af65595ae64845))
- Access Control Module added ([#266](https://github.com/juspay/hyperswitch-control-center/pull/266)) ([`59d0b53`](https://github.com/juspay/hyperswitch-control-center/commit/59d0b5387476536ed3a7f6a9f3468a3bd115232f))

**Full Changelog:** [`v1.25.0...v1.25.1`](https://github.com/juspay/hyperswitch-control-center/compare/v1.25.0...v1.25.1)

- - -


## 1.25.0 (2024-01-16)

### Features
Expand Down
79 changes: 11 additions & 68 deletions src/components/EntityScaffold.res
Original file line number Diff line number Diff line change
@@ -1,89 +1,32 @@
module ComingSoon = {
@react.component
let make = (~title) => {
<div className="h-full w-full flex flex-col items-center justify-center">
<div className="text-2xl text-gray-500 pb-4"> {React.string(title)} </div>
<div> {React.string("Coming soon...")} </div>
</div>
}
}

module ShowPage = {
@react.component
let make = (~entityName, ~id) => {
<div className="h-full w-fit flex flex-col m-12">
<div className="text-2xl text-gray-500 pb-4">
{React.string(`Show ${entityName} `)}
<span className="text-sm"> {React.string(`#${id}`)} </span>
</div>
<div> {React.string("Coming soon...")} </div>
</div>
}
}

module UnauthorizedPage = {
@react.component
let make = (~entityName) => {
<div className="h-full w-fit flex flex-col m-12">
<div className="text-2xl text-gray-500 pb-4"> {React.string(entityName)} </div>
<div> {React.string("You don't have access to this module. Contact admin for access")} </div>
</div>
}
}

@react.component
let make = (
~entityName="",
~remainingPath,
~isAdminAccount=false,
~access: AuthTypes.authorization=ReadWrite,
~renderList=() => <ComingSoon title="List" />,
~renderNewForm=() => <ComingSoon title="New Form" />,
~access: AuthTypes.authorization=Access,
~renderList,
~renderNewForm=?,
~renderShow=?,
~renderOrder=?,
~renderEdit=_id => <ComingSoon title="Edit Form" />,
~renderEditWithMultiId=(_id1, _id2) => <ComingSoon title="Edit Form" />,
~renderClone=_id => <ComingSoon title="Clone Form" />,
) => {
if access === NoAccess {
<UnauthorizedPage entityName />
<UnauthorizedPage />
} else {
switch remainingPath {
| list{"new"} =>
switch access {
| ReadWrite => renderNewForm()
| Checker => isAdminAccount ? renderNewForm() : <UnauthorizedPage entityName />
| _ => <UnauthorizedPage entityName />
}
| list{id, "clone"} =>
switch access {
| ReadWrite => renderClone(id)
| _ => <UnauthorizedPage entityName />
| Access =>
switch renderNewForm {
| Some(element) => element()
| None => React.null
}
| NoAccess => <UnauthorizedPage />
}
| list{id} =>
let page = switch renderShow {
| Some(fn) => fn(id)
| None => <ShowPage entityName id />
| None => React.null
}
page
| list{id, "edit"} =>
switch access {
| ReadWrite => renderEdit(id)
| Checker => isAdminAccount ? renderEdit(id) : <UnauthorizedPage entityName />
| _ => <UnauthorizedPage entityName />
}
| list{id1, id2, "edit"} =>
switch access {
| ReadWrite => renderEditWithMultiId(id1, id2)
| Checker =>
isAdminAccount ? renderEditWithMultiId(id1, id2) : <UnauthorizedPage entityName />
| _ => <UnauthorizedPage entityName />
}
| list{"order", id} =>
switch renderOrder {
| Some(fn) => fn(id)
| None => <NotFoundPage />
}
| list{} => renderList()
| _ => <NotFoundPage />
}
Expand Down
19 changes: 19 additions & 0 deletions src/components/UnauthorizedPage.res
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
@react.component
let make = (~message="You don't have access to this module. Contact admin for access") => {
let {setDashboardPageState} = React.useContext(GlobalProvider.defaultContext)
React.useEffect0(() => {
RescriptReactRouter.replace("/unauthorized")
None
})
<NoDataFound message renderType={Locked}>
<Button
text={"Go to Home"}
buttonType=Primary
onClick={_ => {
setDashboardPageState(_ => #HOME)
RescriptReactRouter.replace("/home")
}}
customButtonStyle="mt-4 !p-2"
/>
</NoDataFound>
}
11 changes: 2 additions & 9 deletions src/components/form/BoolInput.res
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,6 @@ let make = (
~boolCustomClass="",
~addAttributeId="",
) => {
let accessLevel = React.useContext(FormAuthContext.formAuthContext)
let boolInput = baseInput->ffInputToBoolInput
let boolValue: Js.Json.t = boolInput.value

Expand All @@ -126,14 +125,8 @@ let make = (
let setIsSelected = boolInput.onChange

isCheckBox
? <CheckBoxIcon
isSelected setIsSelected isDisabled={isDisabled || accessLevel == AuthTypes.Read}
/>
? <CheckBoxIcon isSelected setIsSelected isDisabled={isDisabled} />
: <BaseComponent
isSelected
setIsSelected
isDisabled={isDisabled || accessLevel == AuthTypes.Read}
boolCustomClass
addAttributeId
isSelected setIsSelected isDisabled={isDisabled} boolCustomClass addAttributeId
/>
}
2 changes: 1 addition & 1 deletion src/context/FormAuthContext.res
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
let formAuthContext = React.createContext(AuthTypes.ReadWrite)
let formAuthContext = React.createContext(AuthTypes.Access)

let make = React.Context.provider(formAuthContext)
74 changes: 27 additions & 47 deletions src/entryPoints/hyperswitch/HyperSwitchApp.res
Original file line number Diff line number Diff line change
Expand Up @@ -4,19 +4,6 @@ open HSLocalStorage
open HSwitchGlobalVars
open APIUtils

module FeatureFlagEnabledComponent = {
@react.component
let make = (~isEnabled, ~children) => {
let {setDashboardPageState} = React.useContext(GlobalProvider.defaultContext)
let updateRoute = () => {
setDashboardPageState(_ => #HOME)
RescriptReactRouter.replace("/home")
React.null
}
<> {isEnabled ? children : updateRoute()} </>
}
}

@react.component
let make = () => {
let url = RescriptReactRouter.useUrl()
Expand All @@ -40,7 +27,6 @@ let make = () => {
->QuickStartUtils.getTypedValueFromDict

let featureFlagDetails = HyperswitchAtom.featureFlagAtom->Recoil.useRecoilValueFromAtom

let getEnumDetails = EnumVariantHook.useFetchEnumDetails()
let verificationDays = getFromMerchantDetails("verification")->LogicUtils.getIntFromString(-1)
let userRole = getFromUserDetails("user_role")
Expand All @@ -55,12 +41,7 @@ let make = () => {
let isReconEnabled =
(merchantDetailsValue->MerchantAccountUtils.getMerchantDetails).recon_status === Active

let hyperSwitchAppSidebars = SidebarValues.getHyperSwitchAppSidebars(
~isReconEnabled,
~featureFlagDetails,
~userRole,
(),
)
let hyperSwitchAppSidebars = SidebarValues.useGetSidebarValues(~isReconEnabled)

let comingSoonPage =
<DefaultLandingPage
Expand Down Expand Up @@ -225,19 +206,19 @@ let make = () => {
<ErrorBoundary>
{switch url.path {
| list{"home"} =>
<FeatureFlagEnabledComponent isEnabled={featureFlagDetails.default}>
<AccessControl isEnabled={featureFlagDetails.default}>
{featureFlagDetails.quickStart ? <HomeV2 /> : <Home />}
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"fraud-risk-management", ...remainingPath} =>
<FeatureFlagEnabledComponent isEnabled={featureFlagDetails.frm}>
<AccessControl isEnabled={featureFlagDetails.frm}>
<EntityScaffold
entityName="risk-management"
remainingPath
renderList={() => <FRMSelect />}
renderNewForm={() => <FRMConfigure />}
renderShow={_ => <FRMConfigure />}
/>
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"connectors", ...remainingPath} =>
<EntityScaffold
entityName="Connectors"
Expand All @@ -259,7 +240,7 @@ let make = () => {
<EntityScaffold
entityName="Payments"
remainingPath
access=ReadWrite
access=Access
renderList={() => <Orders />}
renderShow={id => <ShowOrder id />}
/>
Expand All @@ -269,7 +250,7 @@ let make = () => {
<EntityScaffold
entityName="Refunds"
remainingPath
access=ReadWrite
access=Access
renderList={() => <Refund />}
renderShow={id => <ShowRefund id />}
/>
Expand All @@ -278,20 +259,20 @@ let make = () => {
<EntityScaffold
entityName="Disputes"
remainingPath
access=ReadWrite
access=Access
renderList={() => <Disputes />}
renderShow={id => <ShowDisputes id />}
/>
| list{"customers", ...remainingPath} =>
<FeatureFlagEnabledComponent isEnabled=featureFlagDetails.customersModule>
<AccessControl isEnabled=featureFlagDetails.customersModule>
<EntityScaffold
entityName="Customers"
remainingPath
access=ReadWrite
access=Access
renderList={() => <Customers />}
renderShow={id => <ShowCustomers id />}
/>
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"routing", ...remainingPath} =>
<EntityScaffold
entityName="Routing"
Expand All @@ -304,7 +285,7 @@ let make = () => {
<EntityScaffold
entityName="UserManagement"
remainingPath
access=ReadWrite
access=Access
renderList={() => <UserRoleEntry />}
renderShow={_ => <UserRoleShowData />}
/>
Expand All @@ -317,12 +298,11 @@ let make = () => {
<RefundsAnalytics />
</FilterContext>
| list{"analytics-user-journey"} =>
<FeatureFlagEnabledComponent
isEnabled=featureFlagDetails.userJourneyAnalytics>
<AccessControl isEnabled=featureFlagDetails.userJourneyAnalytics>
<FilterContext key="UserJourneyAnalytics" index="UserJourneyAnalytics">
<UserJourneyAnalytics />
</FilterContext>
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"monitoring"} => comingSoonPage
| list{"developer-api-keys"} => <KeyManagement.KeysManagement />
| list{"developer-system-metrics"} =>
Expand All @@ -342,35 +322,35 @@ let make = () => {
<PaymentSettings webhookOnly=false showFormOnly=false />}
/>
| list{"recon"} =>
<FeatureFlagEnabledComponent isEnabled=featureFlagDetails.recon>
<AccessControl isEnabled=featureFlagDetails.recon>
<Recon />
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"sdk"} =>
<FeatureFlagEnabledComponent isEnabled={!featureFlagDetails.isLiveMode}>
<AccessControl isEnabled={!featureFlagDetails.isLiveMode}>
<SDKPage />
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"3ds"} => <HSwitchThreeDS />
| list{"surcharge"} =>
<FeatureFlagEnabledComponent isEnabled={featureFlagDetails.surcharge}>
<AccessControl isEnabled={featureFlagDetails.surcharge}>
<Surcharge />
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"account-settings"} =>
<FeatureFlagEnabledComponent isEnabled=featureFlagDetails.sampleData>
<AccessControl isEnabled=featureFlagDetails.sampleData>
<HSwitchSettings />
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"account-settings", "profile"} => <HSwitchProfileSettings />
| list{"business-details"} =>
<FeatureFlagEnabledComponent isEnabled=featureFlagDetails.default>
<AccessControl isEnabled=featureFlagDetails.default>
<BusinessDetails />
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"business-profiles"} =>
<FeatureFlagEnabledComponent isEnabled=featureFlagDetails.businessProfile>
<AccessControl isEnabled=featureFlagDetails.businessProfile>
<BusinessProfile />
</FeatureFlagEnabledComponent>
</AccessControl>
| list{"quick-start"} => determineQuickStartPageState()
| list{"woocommerce"} => determineWooCommerce()
| list{"stripe-plus-paypal"} => determineStripePlusPayPal()

| list{"unauthorized"} => <UnauthorizedPage />
| _ =>
RescriptReactRouter.replace(`${hyperSwitchFEPrefix}/home`)
<Home />
Expand Down
5 changes: 4 additions & 1 deletion src/entryPoints/hyperswitch/HyperswitchAtom.res
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,11 @@ let featureFlagAtom: Recoil.recoilAtom<FeatureFlagUtils.featureFlag> = Recoil.at
"featureFlag",
Js.Json.null->FeatureFlagUtils.featureFlagType,
)

let paypalAccountStatusAtom: Recoil.recoilAtom<PayPalFlowTypes.setupAccountStatus> = Recoil.atom(.
"paypalAccountStatusAtom",
PayPalFlowTypes.Account_not_found,
)
let userPermissionAtom: Recoil.recoilAtom<array<PermissionUtils.permissionType>> = Recoil.atom(.
"userPermissionAtom",
[],
)
Loading

0 comments on commit f9da50e

Please sign in to comment.