chore: dashboard fixes (#14968)
* add rewrites for platform dashboard * fix loading checking * add checks * dont display banner for platform client * custom hooks for pllatform * add comment for better explanation * get data from custom hook * update returned user attributes * get data from custom hook
This commit is contained in:
1 parent
57abb26c31
commit
bc42c27230
6 files changed
+122
-67
No files matched your search
@@ -0,0 +1,14 @@
|
||||
import { useCheckTeamBilling } from "@lib/hooks/settings/platform/oauth-clients/usePersistOAuthClient";
|
||||
import useMeQuery from "@lib/hooks/useMeQuery";
|
||||
|
||||
export const useGetUserAttributes = () => {
|
||||
const { data: user, isLoading: isUserLoading } = useMeQuery();
|
||||
const { data: userBillingData, isFetching: isUserBillingDataLoading } = useCheckTeamBilling(
|
||||
user?.organizationId
|
||||
);
|
||||
const isPlatformUser = user?.organization.isPlatform;
|
||||
const isPaidUser = userBillingData?.valid;
|
||||
const userOrgId = user?.organizationId;
|
||||
|
||||
return { isUserLoading, isUserBillingDataLoading, isPlatformUser, isPaidUser, userBillingData, userOrgId };
|
||||
};
|
||||
@@ -537,6 +537,11 @@ const nextConfig = {
|
||||
destination: "/apps/installed/calendar",
|
||||
permanent: true,
|
||||
},
|
||||
{
|
||||
source: "/settings/organizations/platform/:path*",
|
||||
destination: "/settings/platform",
|
||||
permanent: true,
|
||||
},
|
||||
// OAuth callbacks when sent to localhost:3000(w would be expected) should be redirected to corresponding to WEBAPP_URL
|
||||
...(process.env.NODE_ENV === "development" &&
|
||||
// Safer to enable the redirect only when the user is opting to test out organizations
|
||||
|
||||
@@ -8,15 +8,12 @@ import {
|
||||
useOAuthClients,
|
||||
useGetOAuthClientManagedUsers,
|
||||
} from "@lib/hooks/settings/platform/oauth-clients/useOAuthClients";
|
||||
import {
|
||||
useDeleteOAuthClient,
|
||||
useCheckTeamBilling,
|
||||
} from "@lib/hooks/settings/platform/oauth-clients/usePersistOAuthClient";
|
||||
import useMeQuery from "@lib/hooks/useMeQuery";
|
||||
import { useDeleteOAuthClient } from "@lib/hooks/settings/platform/oauth-clients/usePersistOAuthClient";
|
||||
|
||||
import PageWrapper from "@components/PageWrapper";
|
||||
import { ManagedUserList } from "@components/settings/platform/dashboard/managed-user-list";
|
||||
import { OAuthClientsList } from "@components/settings/platform/dashboard/oauth-clients-list";
|
||||
import { useGetUserAttributes } from "@components/settings/platform/hooks/useGetUserAttributes";
|
||||
import { PlatformPricing } from "@components/settings/platform/pricing/platform-pricing";
|
||||
|
||||
const queryClient = new QueryClient();
|
||||
@@ -25,17 +22,15 @@ export default function Platform() {
|
||||
const [initialClientId, setInitialClientId] = useState("");
|
||||
const [initialClientName, setInitialClientName] = useState("");
|
||||
|
||||
const { data: user, isLoading } = useMeQuery();
|
||||
const { data, isLoading: isOAuthClientLoading, refetch: refetchClients } = useOAuthClients();
|
||||
const {
|
||||
isLoading: isManagedUserLoading,
|
||||
data: managedUserData,
|
||||
refetch: refetchManagedUsers,
|
||||
} = useGetOAuthClientManagedUsers(initialClientId);
|
||||
const { data: userBillingData } = useCheckTeamBilling(user?.organizationId);
|
||||
|
||||
const isPlatformUser = user?.organization.isPlatform;
|
||||
const isPaidUser = userBillingData?.valid;
|
||||
const { isUserLoading, isUserBillingDataLoading, isPlatformUser, isPaidUser, userBillingData, userOrgId } =
|
||||
useGetUserAttributes();
|
||||
|
||||
const { mutateAsync, isPending: isDeleting } = useDeleteOAuthClient({
|
||||
onSuccess: () => {
|
||||
@@ -54,9 +49,13 @@ export default function Platform() {
|
||||
setInitialClientName(data[0]?.name);
|
||||
}, [data]);
|
||||
|
||||
if (isLoading || isOAuthClientLoading) return <div className="m-5">Loading...</div>;
|
||||
if (isUserLoading || isOAuthClientLoading) return <div className="m-5">Loading...</div>;
|
||||
|
||||
if (isPlatformUser && !isPaidUser) return <PlatformPricing teamId={user?.organizationId} />;
|
||||
if (isUserBillingDataLoading && !userBillingData) {
|
||||
return <div className="m-5">Loading...</div>;
|
||||
}
|
||||
|
||||
if (isPlatformUser && !isPaidUser) return <PlatformPricing teamId={userOrgId} />;
|
||||
|
||||
if (isPlatformUser) {
|
||||
return (
|
||||
@@ -90,7 +89,13 @@ export default function Platform() {
|
||||
|
||||
return (
|
||||
<div>
|
||||
<Shell hideHeadingOnMobile withoutMain={false} SidebarContainer={<></>}>
|
||||
<Shell
|
||||
// we want to hide org banner and have different sidebar tabs for platform clients
|
||||
// hence we pass isPlatformUser boolean as prop
|
||||
isPlatformUser={true}
|
||||
hideHeadingOnMobile
|
||||
withoutMain={false}
|
||||
SidebarContainer={<></>}>
|
||||
You are not subscribed to a Platform plan.
|
||||
</Shell>
|
||||
</div>
|
||||
|
||||
@@ -9,6 +9,7 @@ import { useOAuthClient } from "@lib/hooks/settings/platform/oauth-clients/useOA
|
||||
import { useUpdateOAuthClient } from "@lib/hooks/settings/platform/oauth-clients/usePersistOAuthClient";
|
||||
|
||||
import PageWrapper from "@components/PageWrapper";
|
||||
import { useGetUserAttributes } from "@components/settings/platform/hooks/useGetUserAttributes";
|
||||
import type { FormValues } from "@components/settings/platform/oauth-clients/oauth-client-form";
|
||||
import { OAuthClientForm as EditOAuthClientForm } from "@components/settings/platform/oauth-clients/oauth-client-form";
|
||||
|
||||
@@ -29,6 +30,9 @@ export default function EditOAuthClient() {
|
||||
const router = useRouter();
|
||||
const params = useParams<{ clientId: string }>();
|
||||
const clientId = params?.clientId || "";
|
||||
|
||||
const { isUserLoading, isPlatformUser, isPaidUser } = useGetUserAttributes();
|
||||
|
||||
const { data, isFetched, isFetching, isError, refetch } = useOAuthClient(clientId);
|
||||
const { mutateAsync: update, isPending: isUpdating } = useUpdateOAuthClient({
|
||||
onSuccess: () => {
|
||||
@@ -66,48 +70,60 @@ export default function EditOAuthClient() {
|
||||
});
|
||||
};
|
||||
|
||||
if (isUserLoading) return <div className="m-5">Loading...</div>;
|
||||
|
||||
if (isPlatformUser && isPaidUser) {
|
||||
return (
|
||||
<div>
|
||||
<Shell title="OAuth client updation form" isPlatformUser={true}>
|
||||
<div className="m-2 md:mx-14 md:mx-5">
|
||||
<div className="border-subtle mx-auto block justify-between rounded-t-lg border px-4 py-6 sm:flex sm:px-6">
|
||||
<div className="flex w-full flex-col">
|
||||
<h1 className="font-cal text-emphasis mb-1 text-xl font-semibold leading-5 tracking-wide">
|
||||
OAuth client updation form
|
||||
</h1>
|
||||
<p className="text-default text-sm ltr:mr-4 rtl:ml-4">
|
||||
This is the form to edit an existing OAuth client
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
{(!Boolean(clientId) || (isFetched && !data)) && <p>OAuth Client not found.</p>}
|
||||
{isFetched && !!data && (
|
||||
<EditOAuthClientForm
|
||||
defaultValues={{
|
||||
name: data?.name ?? "",
|
||||
areEmailsEnabled: data.areEmailsEnabled ?? false,
|
||||
redirectUris: data?.redirectUris?.map((uri) => ({ uri })) ?? [{ uri: "" }],
|
||||
bookingRedirectUri: data?.bookingRedirectUri ?? "",
|
||||
bookingCancelRedirectUri: data?.bookingCancelRedirectUri ?? "",
|
||||
bookingRescheduleRedirectUri: data?.bookingRescheduleRedirectUri ?? "",
|
||||
appsRead: hasAppsReadPermission(data?.permissions),
|
||||
appsWrite: hasAppsWritePermission(data?.permissions),
|
||||
bookingRead: hasBookingReadPermission(data?.permissions),
|
||||
bookingWrite: hasBookingWritePermission(data?.permissions),
|
||||
eventTypeRead: hasEventTypeReadPermission(data?.permissions),
|
||||
eventTypeWrite: hasEventTypeWritePermission(data?.permissions),
|
||||
profileRead: hasProfileReadPermission(data?.permissions),
|
||||
profileWrite: hasProfileWritePermission(data?.permissions),
|
||||
scheduleRead: hasScheduleReadPermission(data?.permissions),
|
||||
scheduleWrite: hasScheduleWritePermission(data?.permissions),
|
||||
}}
|
||||
onSubmit={onSubmit}
|
||||
isPending={isUpdating}
|
||||
/>
|
||||
)}
|
||||
{isFetching && <p>Loading...</p>}
|
||||
{isError && <p>Something went wrong.</p>}
|
||||
</div>
|
||||
</Shell>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div>
|
||||
<Shell title="OAuth client updation form" isPlatformUser={true}>
|
||||
<div className="m-2 md:mx-14 md:mx-5">
|
||||
<div className="border-subtle mx-auto block justify-between rounded-t-lg border px-4 py-6 sm:flex sm:px-6">
|
||||
<div className="flex w-full flex-col">
|
||||
<h1 className="font-cal text-emphasis mb-1 text-xl font-semibold leading-5 tracking-wide">
|
||||
OAuth client updation form
|
||||
</h1>
|
||||
<p className="text-default text-sm ltr:mr-4 rtl:ml-4">
|
||||
This is the form to edit an existing OAuth client
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
{(!Boolean(clientId) || (isFetched && !data)) && <p>OAuth Client not found.</p>}
|
||||
{isFetched && !!data && (
|
||||
<EditOAuthClientForm
|
||||
defaultValues={{
|
||||
name: data?.name ?? "",
|
||||
areEmailsEnabled: data.areEmailsEnabled ?? false,
|
||||
redirectUris: data?.redirectUris?.map((uri) => ({ uri })) ?? [{ uri: "" }],
|
||||
bookingRedirectUri: data?.bookingRedirectUri ?? "",
|
||||
bookingCancelRedirectUri: data?.bookingCancelRedirectUri ?? "",
|
||||
bookingRescheduleRedirectUri: data?.bookingRescheduleRedirectUri ?? "",
|
||||
appsRead: hasAppsReadPermission(data?.permissions),
|
||||
appsWrite: hasAppsWritePermission(data?.permissions),
|
||||
bookingRead: hasBookingReadPermission(data?.permissions),
|
||||
bookingWrite: hasBookingWritePermission(data?.permissions),
|
||||
eventTypeRead: hasEventTypeReadPermission(data?.permissions),
|
||||
eventTypeWrite: hasEventTypeWritePermission(data?.permissions),
|
||||
profileRead: hasProfileReadPermission(data?.permissions),
|
||||
profileWrite: hasProfileWritePermission(data?.permissions),
|
||||
scheduleRead: hasScheduleReadPermission(data?.permissions),
|
||||
scheduleWrite: hasScheduleWritePermission(data?.permissions),
|
||||
}}
|
||||
onSubmit={onSubmit}
|
||||
isPending={isUpdating}
|
||||
/>
|
||||
)}
|
||||
{isFetching && <p>Loading...</p>}
|
||||
{isError && <p>Something went wrong.</p>}
|
||||
</div>
|
||||
<Shell isPlatformUser={true} hideHeadingOnMobile withoutMain={false} SidebarContainer={<></>}>
|
||||
You are not subscribed to a Platform plan.
|
||||
</Shell>
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -8,6 +8,7 @@ import { showToast } from "@calcom/ui";
|
||||
import { useCreateOAuthClient } from "@lib/hooks/settings/platform/oauth-clients/usePersistOAuthClient";
|
||||
|
||||
import PageWrapper from "@components/PageWrapper";
|
||||
import { useGetUserAttributes } from "@components/settings/platform/hooks/useGetUserAttributes";
|
||||
import type { FormValues } from "@components/settings/platform/oauth-clients/oauth-client-form";
|
||||
import { OAuthClientForm } from "@components/settings/platform/oauth-clients/oauth-client-form";
|
||||
|
||||
@@ -16,6 +17,8 @@ export default function CreateOAuthClient() {
|
||||
const router = useRouter();
|
||||
const clientId = searchParams?.get("clientId") || "";
|
||||
|
||||
const { isUserLoading, isPlatformUser, isPaidUser } = useGetUserAttributes();
|
||||
|
||||
const { mutateAsync: save, isPending: isSaving } = useCreateOAuthClient({
|
||||
onSuccess: () => {
|
||||
showToast("OAuth client created successfully", "success");
|
||||
@@ -51,22 +54,34 @@ export default function CreateOAuthClient() {
|
||||
});
|
||||
};
|
||||
|
||||
if (isUserLoading) return <div className="m-5">Loading...</div>;
|
||||
|
||||
if (isPlatformUser && isPaidUser) {
|
||||
return (
|
||||
<div>
|
||||
<Shell title={`OAuth client ${!!clientId ? "updation" : "creation"} form`} isPlatformUser={true}>
|
||||
<div className="m-2 md:mx-14 md:mx-5">
|
||||
<div className="border-subtle mx-auto block justify-between rounded-t-lg border px-4 py-6 sm:flex sm:px-6">
|
||||
<div className="flex w-full flex-col">
|
||||
<h1 className="font-cal text-emphasis mb-1 text-xl font-semibold leading-5 tracking-wide">
|
||||
OAuth client creation form
|
||||
</h1>
|
||||
<p className="text-default text-sm ltr:mr-4 rtl:ml-4">
|
||||
This is the form to create a new OAuth client
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<OAuthClientForm isPending={isSaving} onSubmit={onSubmit} />
|
||||
</div>
|
||||
</Shell>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div>
|
||||
<Shell title={`OAuth client ${!!clientId ? "updation" : "creation"} form`} isPlatformUser={true}>
|
||||
<div className="m-2 md:mx-14 md:mx-5">
|
||||
<div className="border-subtle mx-auto block justify-between rounded-t-lg border px-4 py-6 sm:flex sm:px-6">
|
||||
<div className="flex w-full flex-col">
|
||||
<h1 className="font-cal text-emphasis mb-1 text-xl font-semibold leading-5 tracking-wide">
|
||||
OAuth client creation form
|
||||
</h1>
|
||||
<p className="text-default text-sm ltr:mr-4 rtl:ml-4">
|
||||
This is the form to create a new OAuth client
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<OAuthClientForm isPending={isSaving} onSubmit={onSubmit} />
|
||||
</div>
|
||||
<Shell isPlatformUser={true} hideHeadingOnMobile withoutMain={false} SidebarContainer={<></>}>
|
||||
You are not subscribed to a Platform plan.
|
||||
</Shell>
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -255,7 +255,7 @@ const Layout = (props: LayoutProps) => {
|
||||
<TimezoneChangeDialog />
|
||||
|
||||
<div className="flex min-h-screen flex-col">
|
||||
{banners && (
|
||||
{banners && !props.isPlatformUser && (
|
||||
<div className="sticky top-0 z-10 w-full divide-y divide-black">
|
||||
<UserV2OptInBanner />
|
||||
{Object.keys(banners).map((key) => {
|
||||
|
||||
Reference in new issue
Block a user