refactor: event types kbar action (#7423)
* refactor: event types action * chore : wrap actions inside useMemo --------- Co-authored-by: Peer Richelsen <peeroke@gmail.com> Co-authored-by: Alex van Andel <me@alexvanandel.com>
This commit is contained in:
co-authored by
Peer Richelsen
Alex van Andel
parent
84f7924215
commit
77df4117d0
@@ -21,7 +21,8 @@ const PasswordView = () => {
|
||||
const { t } = useLocale();
|
||||
const utils = trpc.useContext();
|
||||
const { data: user } = trpc.viewer.me.useQuery();
|
||||
const metadata = userMetadata.parse(user?.metadata);
|
||||
const metadata = userMetadata.safeParse(user?.metadata);
|
||||
const sessionTimeout = metadata.success ? metadata.data?.sessionTimeout : undefined;
|
||||
|
||||
const sessionMutation = trpc.viewer.updateProfile.useMutation({
|
||||
onSuccess: () => {
|
||||
@@ -36,10 +37,10 @@ const PasswordView = () => {
|
||||
const previousValue = utils.viewer.me.getData();
|
||||
const previousMetadata = userMetadata.parse(previousValue?.metadata);
|
||||
|
||||
if (previousValue && metadata?.sessionTimeout) {
|
||||
if (previousValue && sessionTimeout) {
|
||||
utils.viewer.me.setData(undefined, {
|
||||
...previousValue,
|
||||
metadata: { ...previousMetadata, sessionTimeout: metadata?.sessionTimeout },
|
||||
metadata: { ...previousMetadata, sessionTimeout: sessionTimeout },
|
||||
});
|
||||
}
|
||||
return { previousValue };
|
||||
@@ -81,19 +82,19 @@ const PasswordView = () => {
|
||||
defaultValues: {
|
||||
oldPassword: "",
|
||||
newPassword: "",
|
||||
sessionTimeout: metadata?.sessionTimeout,
|
||||
sessionTimeout,
|
||||
},
|
||||
});
|
||||
|
||||
const sessionTimeoutWatch = formMethods.watch("sessionTimeout");
|
||||
|
||||
const handleSubmit = (values: ChangePasswordSessionFormValues) => {
|
||||
const { oldPassword, newPassword, sessionTimeout } = values;
|
||||
const { oldPassword, newPassword, sessionTimeout: newSessionTimeout } = values;
|
||||
if (oldPassword && newPassword) {
|
||||
passwordMutation.mutate({ oldPassword, newPassword });
|
||||
}
|
||||
if (metadata?.sessionTimeout !== sessionTimeout) {
|
||||
sessionMutation.mutate({ metadata: { ...metadata, sessionTimeout } });
|
||||
if (sessionTimeout !== newSessionTimeout) {
|
||||
sessionMutation.mutate({ metadata: { ...metadata, sessionTimeout: newSessionTimeout } });
|
||||
}
|
||||
};
|
||||
|
||||
@@ -106,6 +107,7 @@ const PasswordView = () => {
|
||||
|
||||
const passwordMinLength = data?.user.role === "USER" ? 7 : 15;
|
||||
const isUser = data?.user.role === "USER";
|
||||
|
||||
return (
|
||||
<>
|
||||
<Meta title={t("password")} description={t("password_description")} />
|
||||
@@ -176,8 +178,8 @@ const PasswordView = () => {
|
||||
<Select
|
||||
options={timeoutOptions}
|
||||
defaultValue={
|
||||
metadata?.sessionTimeout
|
||||
? timeoutOptions.find((tmo) => tmo.value === metadata.sessionTimeout)
|
||||
sessionTimeout
|
||||
? timeoutOptions.find((tmo) => tmo.value === sessionTimeout)
|
||||
: timeoutOptions[1]
|
||||
}
|
||||
isSearchable={false}
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { useRouter } from "next/router";
|
||||
import { useEffect } from "react";
|
||||
|
||||
import { HOSTED_CAL_FEATURES } from "@calcom/lib/constants";
|
||||
import { useLocale } from "@calcom/lib/hooks/useLocale";
|
||||
@@ -13,10 +14,6 @@ const SAMLSSO = () => {
|
||||
const { t } = useLocale();
|
||||
const router = useRouter();
|
||||
|
||||
if (!HOSTED_CAL_FEATURES) {
|
||||
router.push("/404");
|
||||
}
|
||||
|
||||
const teamId = Number(router.query.id);
|
||||
|
||||
const { data: team, isLoading } = trpc.viewer.teams.get.useQuery(
|
||||
@@ -28,6 +25,12 @@ const SAMLSSO = () => {
|
||||
}
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
if (!HOSTED_CAL_FEATURES) {
|
||||
router.push("/404");
|
||||
}
|
||||
}, []);
|
||||
|
||||
if (isLoading) {
|
||||
return <SkeletonLoader />;
|
||||
}
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { useRouter } from "next/router";
|
||||
import { useEffect } from "react";
|
||||
|
||||
import { HOSTED_CAL_FEATURES } from "@calcom/lib/constants";
|
||||
import { useLocale } from "@calcom/lib/hooks/useLocale";
|
||||
@@ -11,9 +12,11 @@ const SAMLSSO = () => {
|
||||
const { t } = useLocale();
|
||||
const router = useRouter();
|
||||
|
||||
if (HOSTED_CAL_FEATURES) {
|
||||
router.push("/404");
|
||||
}
|
||||
useEffect(() => {
|
||||
if (HOSTED_CAL_FEATURES) {
|
||||
router.push("/404");
|
||||
}
|
||||
}, []);
|
||||
|
||||
return (
|
||||
<div className="w-full bg-white sm:mx-0 xl:mt-0">
|
||||
|
||||
+192
-206
@@ -7,14 +7,17 @@ import {
|
||||
KBarSearch,
|
||||
useKBar,
|
||||
useMatches,
|
||||
useRegisterActions,
|
||||
} from "kbar";
|
||||
import type { Action } from "kbar";
|
||||
import { useRouter } from "next/router";
|
||||
import { useMemo } from "react";
|
||||
|
||||
import { appStoreMetadata } from "@calcom/app-store/appStoreMetaData";
|
||||
import { useLocale } from "@calcom/lib/hooks/useLocale";
|
||||
import { isMac } from "@calcom/lib/isMac";
|
||||
import { RouterOutputs, trpc } from "@calcom/trpc/react";
|
||||
import type { RouterOutputs } from "@calcom/trpc/react";
|
||||
import { trpc } from "@calcom/trpc/react";
|
||||
import { Tooltip } from "@calcom/ui";
|
||||
import { FiSearch, FiArrowUp, FiArrowDown, FiCornerDownLeft, FiCommand } from "@calcom/ui/components/icon";
|
||||
|
||||
@@ -24,15 +27,6 @@ type shortcutArrayType = {
|
||||
|
||||
type EventTypeGroups = RouterOutputs["viewer"]["eventTypes"]["getByViewer"]["eventTypeGroups"];
|
||||
type EventTypeGroup = EventTypeGroups[number];
|
||||
type EventType = EventTypeGroup["eventTypes"][number];
|
||||
|
||||
type KBarAction = {
|
||||
perform: () => Promise<boolean>;
|
||||
id: string;
|
||||
name: string;
|
||||
section: string;
|
||||
keywords: string;
|
||||
};
|
||||
|
||||
const getApps = Object.values(appStoreMetadata).map(({ name, slug }) => ({
|
||||
id: slug,
|
||||
@@ -41,216 +35,208 @@ const getApps = Object.values(appStoreMetadata).map(({ name, slug }) => ({
|
||||
keywords: `app ${name}`,
|
||||
}));
|
||||
|
||||
export const KBarRoot = ({ children }: { children: React.ReactNode }) => {
|
||||
const useEventTypesAction = () => {
|
||||
const router = useRouter();
|
||||
const { data } = trpc.viewer.eventTypes.getByViewer.useQuery();
|
||||
const eventTypeActions = data?.eventTypeGroups.reduce<Action[]>((acc: Action[], group: EventTypeGroup) => {
|
||||
const item: Action[] = group.eventTypes.map((item) => ({
|
||||
id: `event-type-${item.id}`,
|
||||
name: item.title,
|
||||
section: "event_types_page_title",
|
||||
keywords: "event types",
|
||||
perform: () => router.push(`/event-types/${item.id}`),
|
||||
}));
|
||||
acc.push(...item);
|
||||
return acc;
|
||||
}, []);
|
||||
|
||||
const actions = eventTypeActions?.length ? eventTypeActions : [];
|
||||
|
||||
return useRegisterActions(actions);
|
||||
};
|
||||
|
||||
export const KBarRoot = ({ children }: { children: React.ReactNode }) => {
|
||||
const router = useRouter();
|
||||
|
||||
// grab link to events
|
||||
// quick nested actions would be extremely useful
|
||||
const appStoreActions = useMemo(
|
||||
() => getApps.map((item) => ({ ...item, perform: () => router.push(`/apps/${item.id}`) })),
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
[]
|
||||
);
|
||||
|
||||
if (!data) return null;
|
||||
|
||||
const eventTypes =
|
||||
data?.eventTypeGroups.reduce((acc: EventType[], group: EventTypeGroup): EventType[] => {
|
||||
acc.push(...group.eventTypes);
|
||||
return acc;
|
||||
}, [] as EventType[]) || [];
|
||||
|
||||
const eventTypeActions =
|
||||
eventTypes.map(
|
||||
(item: EventType): KBarAction => ({
|
||||
id: `event-type-${item.id}`,
|
||||
name: item.title,
|
||||
const actions = useMemo(() => {
|
||||
const appStoreActions = getApps.map((item) => ({
|
||||
...item,
|
||||
perform: () => router.push(`/apps/${item.id}`),
|
||||
}));
|
||||
return [
|
||||
{
|
||||
id: "workflows",
|
||||
name: "workflows",
|
||||
section: "workflows",
|
||||
shortcut: ["w", "f"],
|
||||
keywords: "workflows automation",
|
||||
perform: () => router.push("/workflows"),
|
||||
},
|
||||
{
|
||||
id: "event-types",
|
||||
name: "event_types_page_title",
|
||||
section: "event_types_page_title",
|
||||
shortcut: ["e", "t"],
|
||||
keywords: "event types",
|
||||
perform: () => router.push(`/event-types/${item.id}`),
|
||||
})
|
||||
) || [];
|
||||
|
||||
const actions = [
|
||||
// {
|
||||
// id: "toggle-idle",
|
||||
// name: "Test Function",
|
||||
// section: "Status",
|
||||
// shortcut: ["t", "f"],
|
||||
// keywords: "set yourself away bookings",
|
||||
// perform: () => alert("Hello World"),
|
||||
// },
|
||||
|
||||
{
|
||||
id: "workflows",
|
||||
name: "workflows",
|
||||
section: "workflows",
|
||||
shortcut: ["w", "f"],
|
||||
keywords: "workflows automation",
|
||||
perform: () => router.push("/workflows"),
|
||||
},
|
||||
{
|
||||
id: "event-types",
|
||||
name: "event_types_page_title",
|
||||
section: "event_types_page_title",
|
||||
shortcut: ["e", "t"],
|
||||
keywords: "event types",
|
||||
perform: () => router.push("/event-types"),
|
||||
},
|
||||
{
|
||||
id: "app-store",
|
||||
name: "app_store",
|
||||
section: "apps",
|
||||
shortcut: ["a", "s"],
|
||||
keywords: "app store",
|
||||
perform: () => router.push("/apps"),
|
||||
},
|
||||
{
|
||||
id: "upcoming-bookings",
|
||||
name: "upcoming",
|
||||
section: "bookings",
|
||||
shortcut: ["u", "b"],
|
||||
keywords: "upcoming bookings",
|
||||
perform: () => router.push("/bookings/upcoming"),
|
||||
},
|
||||
{
|
||||
id: "recurring-bookings",
|
||||
name: "recurring",
|
||||
section: "bookings",
|
||||
shortcut: ["r", "b"],
|
||||
keywords: "recurring bookings",
|
||||
perform: () => router.push("/bookings/recurring"),
|
||||
},
|
||||
{
|
||||
id: "past-bookings",
|
||||
name: "past",
|
||||
section: "bookings",
|
||||
shortcut: ["p", "b"],
|
||||
keywords: "past bookings",
|
||||
perform: () => router.push("/bookings/past"),
|
||||
},
|
||||
{
|
||||
id: "cancelled-bookings",
|
||||
name: "cancelled",
|
||||
section: "bookings",
|
||||
shortcut: ["c", "b"],
|
||||
keywords: "cancelled bookings",
|
||||
perform: () => router.push("/bookings/cancelled"),
|
||||
},
|
||||
{
|
||||
id: "schedule",
|
||||
name: "availability",
|
||||
section: "availability",
|
||||
shortcut: ["s", "a"],
|
||||
keywords: "schedule availability",
|
||||
perform: () => router.push("/availability"),
|
||||
},
|
||||
{
|
||||
id: "profile",
|
||||
name: "profile",
|
||||
section: "profile",
|
||||
shortcut: ["p", "s"],
|
||||
keywords: "setting profile",
|
||||
perform: () => router.push("/settings/my-account/profile"),
|
||||
},
|
||||
{
|
||||
id: "avatar",
|
||||
name: "change_avatar",
|
||||
section: "profile",
|
||||
shortcut: ["c", "a"],
|
||||
keywords: "remove change modify avatar",
|
||||
perform: () => router.push("/settings/my-account/profile"),
|
||||
},
|
||||
{
|
||||
id: "timezone",
|
||||
name: "timezone",
|
||||
section: "profile",
|
||||
shortcut: ["c", "t"],
|
||||
keywords: "change modify timezone",
|
||||
perform: () => router.push("/settings/my-account/general"),
|
||||
},
|
||||
{
|
||||
id: "brand-color",
|
||||
name: "brand_color",
|
||||
section: "profile",
|
||||
shortcut: ["b", "c"],
|
||||
keywords: "change modify brand color",
|
||||
perform: () => router.push("/settings/my-account/appearance"),
|
||||
},
|
||||
{
|
||||
id: "teams",
|
||||
name: "teams",
|
||||
shortcut: ["t", "s"],
|
||||
keywords: "add manage modify team",
|
||||
perform: () => router.push("/settings/teams"),
|
||||
},
|
||||
{
|
||||
id: "password",
|
||||
name: "change_password",
|
||||
section: "security",
|
||||
shortcut: ["c", "p"],
|
||||
keywords: "change modify password",
|
||||
perform: () => router.push("/settings/security/password"),
|
||||
},
|
||||
{
|
||||
id: "two-factor",
|
||||
name: "two_factor_auth",
|
||||
section: "security",
|
||||
shortcut: ["t", "f", "a"],
|
||||
keywords: "two factor authentication",
|
||||
perform: () => router.push("/settings/security/two-factor-auth"),
|
||||
},
|
||||
{
|
||||
id: "impersonation",
|
||||
name: "user_impersonation_heading",
|
||||
section: "security",
|
||||
shortcut: ["u", "i"],
|
||||
keywords: "user impersonation",
|
||||
perform: () => router.push("/settings/security/impersonation"),
|
||||
},
|
||||
{
|
||||
id: "license",
|
||||
name: "choose_a_license",
|
||||
section: "admin",
|
||||
shortcut: ["u", "l"],
|
||||
keywords: "license",
|
||||
perform: () => router.push("/auth/setup?step=1"),
|
||||
},
|
||||
{
|
||||
id: "webhooks",
|
||||
name: "Webhooks",
|
||||
section: "developer",
|
||||
shortcut: ["w", "h"],
|
||||
keywords: "webhook automation",
|
||||
perform: () => router.push("/settings/developer/webhooks"),
|
||||
},
|
||||
{
|
||||
id: "api-keys",
|
||||
name: "api_keys",
|
||||
section: "developer",
|
||||
shortcut: ["a", "p", "i"],
|
||||
keywords: "api keys",
|
||||
perform: () => router.push("/settings/developer/api-keys"),
|
||||
},
|
||||
{
|
||||
id: "billing",
|
||||
name: "manage_billing",
|
||||
section: "billing",
|
||||
shortcut: ["m", "b"],
|
||||
keywords: "billing view manage",
|
||||
perform: () => router.push("/settings/billing"),
|
||||
},
|
||||
...appStoreActions,
|
||||
...eventTypeActions,
|
||||
];
|
||||
perform: () => router.push("/event-types"),
|
||||
},
|
||||
{
|
||||
id: "app-store",
|
||||
name: "app_store",
|
||||
section: "apps",
|
||||
shortcut: ["a", "s"],
|
||||
keywords: "app store",
|
||||
perform: () => router.push("/apps"),
|
||||
},
|
||||
{
|
||||
id: "upcoming-bookings",
|
||||
name: "upcoming",
|
||||
section: "bookings",
|
||||
shortcut: ["u", "b"],
|
||||
keywords: "upcoming bookings",
|
||||
perform: () => router.push("/bookings/upcoming"),
|
||||
},
|
||||
{
|
||||
id: "recurring-bookings",
|
||||
name: "recurring",
|
||||
section: "bookings",
|
||||
shortcut: ["r", "b"],
|
||||
keywords: "recurring bookings",
|
||||
perform: () => router.push("/bookings/recurring"),
|
||||
},
|
||||
{
|
||||
id: "past-bookings",
|
||||
name: "past",
|
||||
section: "bookings",
|
||||
shortcut: ["p", "b"],
|
||||
keywords: "past bookings",
|
||||
perform: () => router.push("/bookings/past"),
|
||||
},
|
||||
{
|
||||
id: "cancelled-bookings",
|
||||
name: "cancelled",
|
||||
section: "bookings",
|
||||
shortcut: ["c", "b"],
|
||||
keywords: "cancelled bookings",
|
||||
perform: () => router.push("/bookings/cancelled"),
|
||||
},
|
||||
{
|
||||
id: "schedule",
|
||||
name: "availability",
|
||||
section: "availability",
|
||||
shortcut: ["s", "a"],
|
||||
keywords: "schedule availability",
|
||||
perform: () => router.push("/availability"),
|
||||
},
|
||||
{
|
||||
id: "profile",
|
||||
name: "profile",
|
||||
section: "profile",
|
||||
shortcut: ["p", "s"],
|
||||
keywords: "setting profile",
|
||||
perform: () => router.push("/settings/my-account/profile"),
|
||||
},
|
||||
{
|
||||
id: "avatar",
|
||||
name: "change_avatar",
|
||||
section: "profile",
|
||||
shortcut: ["c", "a"],
|
||||
keywords: "remove change modify avatar",
|
||||
perform: () => router.push("/settings/my-account/profile"),
|
||||
},
|
||||
{
|
||||
id: "timezone",
|
||||
name: "timezone",
|
||||
section: "profile",
|
||||
shortcut: ["c", "t"],
|
||||
keywords: "change modify timezone",
|
||||
perform: () => router.push("/settings/my-account/general"),
|
||||
},
|
||||
{
|
||||
id: "brand-color",
|
||||
name: "brand_color",
|
||||
section: "profile",
|
||||
shortcut: ["b", "c"],
|
||||
keywords: "change modify brand color",
|
||||
perform: () => router.push("/settings/my-account/appearance"),
|
||||
},
|
||||
{
|
||||
id: "teams",
|
||||
name: "teams",
|
||||
shortcut: ["t", "s"],
|
||||
keywords: "add manage modify team",
|
||||
perform: () => router.push("/settings/teams"),
|
||||
},
|
||||
{
|
||||
id: "password",
|
||||
name: "change_password",
|
||||
section: "security",
|
||||
shortcut: ["c", "p"],
|
||||
keywords: "change modify password",
|
||||
perform: () => router.push("/settings/security/password"),
|
||||
},
|
||||
{
|
||||
id: "two-factor",
|
||||
name: "two_factor_auth",
|
||||
section: "security",
|
||||
shortcut: ["t", "f", "a"],
|
||||
keywords: "two factor authentication",
|
||||
perform: () => router.push("/settings/security/two-factor-auth"),
|
||||
},
|
||||
{
|
||||
id: "impersonation",
|
||||
name: "user_impersonation_heading",
|
||||
section: "security",
|
||||
shortcut: ["u", "i"],
|
||||
keywords: "user impersonation",
|
||||
perform: () => router.push("/settings/security/impersonation"),
|
||||
},
|
||||
{
|
||||
id: "license",
|
||||
name: "choose_a_license",
|
||||
section: "admin",
|
||||
shortcut: ["u", "l"],
|
||||
keywords: "license",
|
||||
perform: () => router.push("/auth/setup?step=1"),
|
||||
},
|
||||
{
|
||||
id: "webhooks",
|
||||
name: "Webhooks",
|
||||
section: "developer",
|
||||
shortcut: ["w", "h"],
|
||||
keywords: "webhook automation",
|
||||
perform: () => router.push("/settings/developer/webhooks"),
|
||||
},
|
||||
{
|
||||
id: "api-keys",
|
||||
name: "api_keys",
|
||||
section: "developer",
|
||||
shortcut: ["a", "p", "i"],
|
||||
keywords: "api keys",
|
||||
perform: () => router.push("/settings/developer/api-keys"),
|
||||
},
|
||||
{
|
||||
id: "billing",
|
||||
name: "manage_billing",
|
||||
section: "billing",
|
||||
shortcut: ["m", "b"],
|
||||
keywords: "billing view manage",
|
||||
perform: () => router.push("/settings/billing"),
|
||||
},
|
||||
...appStoreActions,
|
||||
];
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
}, []);
|
||||
|
||||
return <KBarProvider actions={actions}>{children}</KBarProvider>;
|
||||
};
|
||||
|
||||
export const KBarContent = () => {
|
||||
const { t } = useLocale();
|
||||
|
||||
useEventTypesAction();
|
||||
return (
|
||||
<KBarPortal>
|
||||
<KBarPositioner>
|
||||
|
||||
Reference in New Issue
Block a user