fix: add isAdminOrOwner and useIsOrgAdminOrOwner (#20429)

* fix: add isAdminOrOwner and useIsOrgAdminOrOwner

* make useIsOrgAdminOrOwner to accept session

* revert change

* remove useIsOrgAdminOrOwner and rename isAdminOrOwner to checkAdminOrOwner

* fix type

* fix type

* fix import
This commit is contained in:
Eunjae Lee
2025-03-28 17:01:06 +00:00
committed by GitHub
parent 3456477012
commit 5b08b9f11f
32 changed files with 88 additions and 124 deletions
@@ -9,7 +9,8 @@ import { UsersService } from "@/modules/users/services/users.service";
import { UserWithProfile } from "@/modules/users/users.repository";
import { Injectable, NotFoundException, ForbiddenException } from "@nestjs/common";
import { MembershipRole, getClientSecretFromPayment } from "@calcom/platform-libraries";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { getClientSecretFromPayment } from "@calcom/platform-libraries";
import type { TeamQuery } from "@calcom/platform-libraries";
import { enrichUserWithDelegationConferencingCredentialsWithoutOrgId } from "@calcom/platform-libraries/app-store";
import { getEnabledAppsFromCredentials, getAppFromSlug } from "@calcom/platform-libraries/app-store";
@@ -259,9 +260,7 @@ export class EventTypesAtomService {
name: team.name,
logoUrl: team.logoUrl,
credentialId: c.id,
isAdmin:
team.members[0].role === MembershipRole.ADMIN ||
team.members[0].role === MembershipRole.OWNER,
isAdmin: checkAdminOrOwner(team.members[0].role),
};
})
);
@@ -7,6 +7,7 @@ import { usePathname, useRouter } from "next/navigation";
import type { ComponentProps } from "react";
import React, { useEffect, useState, useMemo } from "react";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { useOrgBranding } from "@calcom/features/ee/organizations/context/provider";
import type { OrganizationBranding } from "@calcom/features/ee/organizations/context/provider";
import Shell from "@calcom/features/shell/Shell";
@@ -16,7 +17,7 @@ import { getUserAvatarUrl } from "@calcom/lib/getAvatarUrl";
import { useCompatSearchParams } from "@calcom/lib/hooks/useCompatSearchParams";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import type { OrganizationRepository } from "@calcom/lib/server/repository/organization";
import { IdentityProvider, MembershipRole, UserPermissionRole } from "@calcom/prisma/enums";
import { IdentityProvider, UserPermissionRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import classNames from "@calcom/ui/classNames";
import { Badge } from "@calcom/ui/components/badge";
@@ -182,8 +183,7 @@ const useTabs = ({ isDelegationCredentialEnabled }: { isDelegationCredentialEnab
const { data: user } = trpc.viewer.me.get.useQuery({ includePasswordAdded: true });
const orgBranding = useOrgBranding();
const isAdmin = session.data?.user.role === UserPermissionRole.ADMIN;
const isOrgAdminOrOwner =
orgBranding?.role === MembershipRole.ADMIN || orgBranding?.role === MembershipRole.OWNER;
const isOrgAdminOrOwner = checkAdminOrOwner(orgBranding?.role);
const processTabsMemod = useMemo(() => {
const processedTabs = getTabs(orgBranding).map((tab) => {
@@ -380,8 +380,7 @@ const TeamListCollapsible = () => {
textClassNames="px-3 text-emphasis font-medium text-sm"
disableChevron
/>
{(team.role === MembershipRole.OWNER ||
team.role === MembershipRole.ADMIN ||
{(checkAdminOrOwner(team.role) ||
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore this exists wtf?
(team.isOrgAdmin && team.isOrgAdmin)) && (
@@ -5,6 +5,7 @@ import Link from "next/link";
import { useRouter, usePathname } from "next/navigation";
import { useCallback, useState } from "react";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import SkeletonLoader from "@calcom/features/availability/components/SkeletonLoader";
import { BulkEditDefaultForEventsModal } from "@calcom/features/eventtypes/components/BulkEditDefaultForEventsModal";
import type { BulkUpdatParams } from "@calcom/features/eventtypes/components/BulkEditDefaultForEventsModal";
@@ -14,7 +15,6 @@ import { useCompatSearchParams } from "@calcom/lib/hooks/useCompatSearchParams";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { HttpError } from "@calcom/lib/http-error";
import type { OrganizationRepository } from "@calcom/lib/server/repository/organization";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import useMeQuery from "@calcom/trpc/react/hooks/useMeQuery";
import { EmptyScreen } from "@calcom/ui/components/empty-screen";
@@ -204,8 +204,7 @@ export const AvailabilityCTA = () => {
);
const { data } = trpc.viewer.organizations.listCurrent.useQuery();
const isOrgAdminOrOwner =
(data && (data.user.role === MembershipRole.OWNER || data.user.role === MembershipRole.ADMIN)) ?? false;
const isOrgAdminOrOwner = (data && checkAdminOrOwner(data.user.role)) ?? false;
const isOrgAndPrivate = data?.isOrganization && data.isPrivate;
const canViewTeamAvailability = isOrgAdminOrOwner || !isOrgAndPrivate;
@@ -241,8 +240,7 @@ export default function AvailabilityPage({ currentOrg }: PageProps) {
const data = currentOrg ?? _data;
const isOrg = Boolean(data);
const isOrgAdminOrOwner =
(data && (data.user.role === MembershipRole.OWNER || data.user.role === MembershipRole.ADMIN)) ?? false;
const isOrgAdminOrOwner = (data && checkAdminOrOwner(data.user.role)) ?? false;
const isOrgAndPrivate = data?.isOrganization && data.isPrivate;
const canViewTeamAvailability = isOrgAdminOrOwner || !isOrgAndPrivate;
@@ -0,0 +1,5 @@
import type { MembershipRole } from "@calcom/prisma/enums";
export function checkAdminOrOwner(role: MembershipRole | null | undefined): role is "OWNER" | "ADMIN" {
return role === "OWNER" || role === "ADMIN";
}
@@ -1,18 +1,16 @@
"use client";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import LicenseRequired from "@calcom/features/ee/common/components/LicenseRequired";
import { UserListTable } from "@calcom/features/users/components/UserTable/UserListTable";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
const MembersView = () => {
const { t } = useLocale();
const { data: currentOrg, isPending } = trpc.viewer.organizations.listCurrent.useQuery();
const isOrgAdminOrOwner =
currentOrg &&
(currentOrg.user.role === MembershipRole.OWNER || currentOrg.user.role === MembershipRole.ADMIN);
const isOrgAdminOrOwner = currentOrg && checkAdminOrOwner(currentOrg.user.role);
const canLoggedInUserSeeMembers =
(currentOrg?.isPrivate && isOrgAdminOrOwner) || isOrgAdminOrOwner || !currentOrg?.isPrivate;
@@ -5,6 +5,7 @@ import { useRouter } from "next/navigation";
import { useState, useEffect } from "react";
import { useForm } from "react-hook-form";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import BrandColorsForm from "@calcom/features/ee/components/BrandColorsForm";
import { AppearanceSkeletonLoader } from "@calcom/features/ee/components/CommonSkeletonLoaders";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
@@ -12,12 +13,11 @@ import ThemeLabel from "@calcom/features/settings/ThemeLabel";
import { DEFAULT_LIGHT_BRAND_COLOR, DEFAULT_DARK_BRAND_COLOR } from "@calcom/lib/constants";
import { APP_NAME } from "@calcom/lib/constants";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import type { RouterOutputs } from "@calcom/trpc/react";
import { Button } from "@calcom/ui/components/button";
import { Form } from "@calcom/ui/components/form";
import { SettingsToggle } from "@calcom/ui/components/form";
import { Button } from "@calcom/ui/components/button";
import { showToast } from "@calcom/ui/components/toast";
type BrandColorsFormValues = {
@@ -198,9 +198,9 @@ const OrgAppearanceView = ({
const OrgAppearanceViewWrapper = () => {
const router = useRouter();
const session = useSession();
const orgRole = session?.data?.user?.org?.role;
const { data: currentOrg, isPending, error } = trpc.viewer.organizations.listCurrent.useQuery();
const session = useSession();
const isAdminOrOwner = checkAdminOrOwner(session.data?.user?.org?.role);
useEffect(
function refactorMeWithoutEffect() {
@@ -217,8 +217,6 @@ const OrgAppearanceViewWrapper = () => {
if (!currentOrg) return null;
const isAdminOrOwner = orgRole === MembershipRole.OWNER || orgRole === MembershipRole.ADMIN;
return <OrgAppearanceView currentOrg={currentOrg} isAdminOrOwner={isAdminOrOwner} />;
};
@@ -5,25 +5,20 @@ import { useRouter } from "next/navigation";
import { useEffect } from "react";
import { Controller, useForm } from "react-hook-form";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { TimezoneSelect } from "@calcom/features/components/timezone-select";
import LicenseRequired from "@calcom/features/ee/common/components/LicenseRequired";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { nameOfDay } from "@calcom/lib/weekday";
import { MembershipRole } from "@calcom/prisma/enums";
import type { RouterOutputs } from "@calcom/trpc/react";
import { trpc } from "@calcom/trpc/react";
import classNames from "@calcom/ui/classNames";
import { Button } from "@calcom/ui/components/button";
import { Form } from "@calcom/ui/components/form";
import { Label } from "@calcom/ui/components/form";
import { Select } from "@calcom/ui/components/form";
import { Button } from "@calcom/ui/components/button";
import classNames from "@calcom/ui/classNames";
import {
SkeletonButton,
SkeletonContainer,
SkeletonText,
SkeletonAvatar,
} from "@calcom/ui/components/skeleton";
import { SkeletonButton, SkeletonContainer, SkeletonText } from "@calcom/ui/components/skeleton";
import { showToast } from "@calcom/ui/components/toast";
import { LockEventTypeSwitch } from "../components/LockEventTypeSwitch";
@@ -54,7 +49,7 @@ const OrgGeneralView = () => {
const { t } = useLocale();
const router = useRouter();
const session = useSession();
const orgRole = session?.data?.user?.org?.role;
const isAdminOrOwner = checkAdminOrOwner(session.data?.user?.org?.role);
const {
data: currentOrg,
@@ -76,7 +71,6 @@ const OrgGeneralView = () => {
if (!currentOrg) {
return null;
}
const isAdminOrOwner = orgRole === MembershipRole.OWNER || orgRole === MembershipRole.ADMIN;
return (
<LicenseRequired>
@@ -7,10 +7,10 @@ import { useRouter } from "next/navigation";
import { useState, useEffect } from "react";
import MemberInvitationModal from "@calcom/ee/teams/components/MemberInvitationModal";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { useParamsWithFallback } from "@calcom/lib/hooks/useParamsWithFallback";
import { CreationSource } from "@calcom/prisma/enums";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import type { RouterOutputs } from "@calcom/trpc/react";
import { Button } from "@calcom/ui/components/button";
@@ -72,9 +72,7 @@ export const TeamMembersCTA = () => {
enabled: !!session.data?.user?.org,
});
const isOrgAdminOrOwner =
currentOrg &&
(currentOrg.user.role === MembershipRole.OWNER || currentOrg.user.role === MembershipRole.ADMIN);
const isOrgAdminOrOwner = currentOrg && checkAdminOrOwner(currentOrg.user.role);
if (!isOrgAdminOrOwner) return null;
@@ -1,15 +1,13 @@
"use client";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import LicenseRequired from "@calcom/features/ee/common/components/LicenseRequired";
import MakeTeamPrivateSwitch from "@calcom/features/ee/teams/components/MakeTeamPrivateSwitch";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
const PrivacyView = () => {
const { data: currentOrg } = trpc.viewer.organizations.listCurrent.useQuery();
const isOrgAdminOrOwner =
currentOrg &&
(currentOrg.user.role === MembershipRole.OWNER || currentOrg.user.role === MembershipRole.ADMIN);
const isOrgAdminOrOwner = currentOrg && checkAdminOrOwner(currentOrg.user.role);
const isInviteOpen = !currentOrg?.user.accepted;
const isDisabled = isInviteOpen || !isOrgAdminOrOwner;
@@ -7,6 +7,7 @@ import { useEffect, useLayoutEffect, useState } from "react";
import { Controller, useForm } from "react-hook-form";
import { z } from "zod";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import LicenseRequired from "@calcom/features/ee/common/components/LicenseRequired";
import { subdomainSuffix } from "@calcom/features/ee/organizations/lib/orgDomains";
import OrgAppearanceViewWrapper from "@calcom/features/ee/organizations/pages/settings/appearance";
@@ -16,7 +17,6 @@ import { useLocale } from "@calcom/lib/hooks/useLocale";
import { md } from "@calcom/lib/markdownIt";
import { markdownToSafeHTML } from "@calcom/lib/markdownToSafeHTML";
import turndown from "@calcom/lib/turndownService";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import { Avatar } from "@calcom/ui/components/avatar";
import { Button } from "@calcom/ui/components/button";
@@ -103,9 +103,7 @@ const OrgProfileView = () => {
return <SkeletonLoader />;
}
const isOrgAdminOrOwner =
currentOrganisation.user.role === MembershipRole.OWNER ||
currentOrganisation.user.role === MembershipRole.ADMIN;
const isOrgAdminOrOwner = checkAdminOrOwner(currentOrganisation.user.role);
const isBioEmpty =
!currentOrganisation ||
@@ -1,10 +1,10 @@
"use client";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { CTA_CONTAINER_CLASS_NAME } from "@calcom/features/data-table/lib/utils";
import Shell from "@calcom/features/shell/Shell";
import { UserListTable } from "@calcom/features/users/components/UserTable/UserListTable";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import { Button } from "@calcom/ui/components/button";
import NoPlatformPlan from "@calcom/web/components/settings/platform/dashboard/NoPlatformPlan";
@@ -17,9 +17,7 @@ const PlatformMembersView = () => {
useGetUserAttributes();
const { data: currentOrg, isPending } = trpc.viewer.organizations.listCurrent.useQuery();
const isOrgAdminOrOwner =
currentOrg &&
(currentOrg.user.role === MembershipRole.OWNER || currentOrg.user.role === MembershipRole.ADMIN);
const isOrgAdminOrOwner = currentOrg && checkAdminOrOwner(currentOrg.user.role);
const canLoggedInUserSeeMembers =
(currentOrg?.isPrivate && isOrgAdminOrOwner) || isOrgAdminOrOwner || !currentOrg?.isPrivate;
@@ -3,8 +3,8 @@
import { useSession } from "next-auth/react";
import { SkeletonLoader } from "@calcom/features/apps/components/SkeletonLoader";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole } from "@calcom/prisma/enums";
import SSOConfiguration from "../components/SSOConfiguration";
@@ -12,6 +12,7 @@ const SAMLSSO = () => {
const { t } = useLocale();
const { data, status } = useSession();
const isAdminOrOwner = checkAdminOrOwner(data?.user?.org?.role);
const org = data?.user.org;
if (status === "loading") <SkeletonLoader />;
@@ -20,8 +21,6 @@ const SAMLSSO = () => {
return null;
}
const isAdminOrOwner = org.role === MembershipRole.OWNER || org.role === MembershipRole.ADMIN;
return !!isAdminOrOwner ? (
<div className="bg-default w-full sm:mx-0 xl:mt-0">
<SSOConfiguration teamId={org.id} />
@@ -5,6 +5,7 @@ import { useSession } from "next-auth/react";
import { useRouter } from "next/navigation";
import { useEffect, useState, useMemo } from "react";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { useOrgBranding } from "@calcom/features/ee/organizations/context/provider";
import InviteLinkSettingsModal from "@calcom/features/ee/teams/components/InviteLinkSettingsModal";
import { MemberInvitationModalWithoutMembers } from "@calcom/features/ee/teams/components/MemberInvitationModal";
@@ -205,7 +206,7 @@ const PendingMemberItem = (props: { member: TeamMember; index: number; teamId: n
const { t } = useLocale();
const utils = trpc.useUtils();
const session = useSession();
const orgRole = session?.data?.user.org?.role;
const isAdminOrOwner = checkAdminOrOwner(session.data?.user?.org?.role);
const bookerUrl = member.bookerUrl;
const removeMemberMutation = trpc.viewer.teams.removeMember.useMutation({
async onSuccess() {
@@ -219,8 +220,6 @@ const PendingMemberItem = (props: { member: TeamMember; index: number; teamId: n
},
});
const isOrgAdminOrOwner = orgRole === MembershipRole.OWNER || orgRole === MembershipRole.ADMIN;
return (
<li
key={member.email}
@@ -249,7 +248,7 @@ const PendingMemberItem = (props: { member: TeamMember; index: number; teamId: n
)}
</div>
</div>
{(member.role !== "OWNER" || isOrgAdminOrOwner) && member.id !== session.data?.user.id && (
{(member.role !== "OWNER" || isAdminOrOwner) && member.id !== session.data?.user.id && (
<Button
data-testid="remove-member-button"
StartIcon="trash-2"
@@ -4,9 +4,9 @@ import { useAutoAnimate } from "@formkit/auto-animate/react";
import { useMemo } from "react";
import { useForm, useFieldArray, Controller } from "react-hook-form";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import type { RouterOutputs } from "@calcom/trpc/react";
import classNames from "@calcom/ui/classNames";
@@ -77,8 +77,7 @@ const InternalNotePresetsView = ({ team }: ProfileViewProps) => {
const [animateRef] = useAutoAnimate<HTMLDivElement>();
const isAdmin =
team && (team.membership.role === MembershipRole.OWNER || team.membership.role === MembershipRole.ADMIN);
const isAdmin = team && checkAdminOrOwner(team.membership.role);
if (!isAdmin) {
return (
@@ -4,6 +4,7 @@ import { useMemo, useRef, useState } from "react";
import { Controller, useForm } from "react-hook-form";
import TeamInviteFromOrg from "@calcom/ee/organizations/components/TeamInviteFromOrg";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { Dialog } from "@calcom/features/components/controlled-dialog";
import ServerTrans from "@calcom/lib/components/ServerTrans";
import { IS_TEAM_BILLING_ENABLED_CLIENT, MAX_NB_INVITES } from "@calcom/lib/constants";
@@ -77,9 +78,7 @@ export default function MemberInvitationModal(props: MemberInvitationModalProps)
const checkIfMembershipExistsMutation = trpc.viewer.teams.checkIfMembershipExists.useMutation();
// Check current org role and not team role
const isOrgAdminOrOwner =
currentOrg &&
(currentOrg.user.role === MembershipRole.OWNER || currentOrg.user.role === MembershipRole.ADMIN);
const isOrgAdminOrOwner = currentOrg && checkAdminOrOwner(currentOrg.user.role);
const canSeeOrganization = currentOrg?.isPrivate
? isOrgAdminOrOwner
@@ -16,6 +16,7 @@ import { useQueryState, parseAsBoolean } from "nuqs";
import { useMemo, useReducer, useRef, useState } from "react";
import type { Dispatch, SetStateAction } from "react";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { Dialog } from "@calcom/features/components/controlled-dialog";
import {
DataTable,
@@ -277,9 +278,7 @@ function MemberListContent(props: Props) {
// return owners.length;
// };
const isAdminOrOwner =
props.team.membership.role === MembershipRole.OWNER ||
props.team.membership.role === MembershipRole.ADMIN;
const isAdminOrOwner = checkAdminOrOwner(props.team.membership.role);
const removeMember = () =>
removeMemberMutation.mutate({
@@ -2,14 +2,15 @@
import { useForm, Controller } from "react-hook-form";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole, RRResetInterval } from "@calcom/prisma/enums";
import { RRResetInterval } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import type { RouterOutputs } from "@calcom/trpc/react";
import { Button } from "@calcom/ui/components/button";
import { Label } from "@calcom/ui/components/form";
import { Select } from "@calcom/ui/components/form";
import { Button } from "@calcom/ui/components/button";
import { Form } from "@calcom/ui/components/form";
import { showToast } from "@calcom/ui/components/toast";
@@ -51,8 +52,7 @@ const RoundRobinResetInterval = ({ team }: ProfileViewProps) => {
},
});
const isAdmin =
team && (team.membership.role === MembershipRole.OWNER || team.membership.role === MembershipRole.ADMIN);
const isAdmin = team && checkAdminOrOwner(team.membership.role);
if (!isAdmin) {
return (
@@ -4,6 +4,7 @@ import { useState } from "react";
import InviteLinkSettingsModal from "@calcom/ee/teams/components/InviteLinkSettingsModal";
import { MemberInvitationModalWithoutMembers } from "@calcom/ee/teams/components/MemberInvitationModal";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { Dialog } from "@calcom/features/components/controlled-dialog";
import { getPlaceholderAvatar } from "@calcom/lib/defaultAvatarImage";
import { getTeamUrlSync } from "@calcom/lib/getBookerUrl/client";
@@ -82,7 +83,7 @@ export default function TeamListItem(props: Props) {
const isOwner = props.team.role === MembershipRole.OWNER;
const isInvitee = !props.team.accepted;
const isAdmin = props.team.role === MembershipRole.OWNER || props.team.role === MembershipRole.ADMIN;
const isAdmin = checkAdminOrOwner(props.team.role);
const { hideDropdown, setHideDropdown } = props;
const hideInvitationModal = () => {
@@ -4,6 +4,7 @@ import { useRouter } from "next/navigation";
import { useState, useEffect } from "react";
import { useForm } from "react-hook-form";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import BrandColorsForm from "@calcom/features/ee/components/BrandColorsForm";
import { AppearanceSkeletonLoader } from "@calcom/features/ee/components/CommonSkeletonLoaders";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
@@ -11,7 +12,6 @@ import { APP_NAME } from "@calcom/lib/constants";
import { DEFAULT_LIGHT_BRAND_COLOR, DEFAULT_DARK_BRAND_COLOR } from "@calcom/lib/constants";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { useParamsWithFallback } from "@calcom/lib/hooks/useParamsWithFallback";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import type { RouterOutputs } from "@calcom/trpc/react";
import { Button } from "@calcom/ui/components/button";
@@ -78,8 +78,7 @@ const ProfileView = ({ team }: ProfileViewProps) => {
mutation.mutate({ ...values, id: team.id });
};
const isAdmin =
team && (team.membership.role === MembershipRole.OWNER || team.membership.role === MembershipRole.ADMIN);
const isAdmin = team && checkAdminOrOwner(team.membership.role);
return (
<>
@@ -4,9 +4,9 @@ import { useSession } from "next-auth/react";
import { useRouter } from "next/navigation";
import { useEffect, useState } from "react";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { useParamsWithFallback } from "@calcom/lib/hooks/useParamsWithFallback";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import DisableTeamImpersonation from "../components/DisableTeamImpersonation";
@@ -50,10 +50,9 @@ const MembersView = () => {
const isInviteOpen = !team?.membership.accepted;
const isAdmin =
team && (team.membership.role === MembershipRole.OWNER || team.membership.role === MembershipRole.ADMIN);
const isAdmin = team && checkAdminOrOwner(team.membership.role);
const isOrgAdminOrOwner = org?.role === MembershipRole.OWNER || org?.role === MembershipRole.ADMIN;
const isOrgAdminOrOwner = checkAdminOrOwner(org?.role);
const hideInvitationModal = () => {
setShowMemberInvitationModal(false);
@@ -9,6 +9,7 @@ import { useEffect, useLayoutEffect, useState } from "react";
import { Controller, useForm } from "react-hook-form";
import { z } from "zod";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { Dialog } from "@calcom/features/components/controlled-dialog";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
import { IS_TEAM_BILLING_ENABLED, WEBAPP_URL } from "@calcom/lib/constants";
@@ -22,7 +23,6 @@ import { markdownToSafeHTML } from "@calcom/lib/markdownToSafeHTML";
import objectKeys from "@calcom/lib/objectKeys";
import slugify from "@calcom/lib/slugify";
import turndown from "@calcom/lib/turndownService";
import { MembershipRole } from "@calcom/prisma/enums";
import type { RouterOutputs } from "@calcom/trpc/react";
import { trpc } from "@calcom/trpc/react";
import { Avatar } from "@calcom/ui/components/avatar";
@@ -106,8 +106,7 @@ const ProfileView = () => {
},
[error]
);
const isAdmin =
team && (team.membership.role === MembershipRole.OWNER || team.membership.role === MembershipRole.ADMIN);
const isAdmin = team && checkAdminOrOwner(team.membership.role);
const permalink = team
? `${getTeamUrlSync({
@@ -4,6 +4,7 @@ import { useRouter } from "next/navigation";
import { useEffect } from "react";
import { useForm, Controller } from "react-hook-form";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { AppearanceSkeletonLoader } from "@calcom/features/ee/components/CommonSkeletonLoaders";
import { IntervalLimitsManager } from "@calcom/features/eventtypes/components/tabs/limits/EventLimitsTab";
import SectionBottomActions from "@calcom/features/settings/SectionBottomActions";
@@ -11,13 +12,12 @@ import { useLocale } from "@calcom/lib/hooks/useLocale";
import { useParamsWithFallback } from "@calcom/lib/hooks/useParamsWithFallback";
import type { IntervalLimit } from "@calcom/lib/intervalLimits/intervalLimitSchema";
import { validateIntervalLimitOrder } from "@calcom/lib/intervalLimits/validateIntervalLimitOrder";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import type { RouterOutputs } from "@calcom/trpc/react";
import classNames from "@calcom/ui/classNames";
import { Button } from "@calcom/ui/components/button";
import { Form } from "@calcom/ui/components/form";
import { SettingsToggle } from "@calcom/ui/components/form";
import { Button } from "@calcom/ui/components/button";
import classNames from "@calcom/ui/classNames";
import { CheckboxField } from "@calcom/ui/components/form";
import { showToast } from "@calcom/ui/components/toast";
@@ -58,8 +58,7 @@ const BookingLimitsView = ({ team }: ProfileViewProps) => {
},
});
const isAdmin =
team && (team.membership.role === MembershipRole.OWNER || team.membership.role === MembershipRole.ADMIN);
const isAdmin = team && checkAdminOrOwner(team.membership.role);
return (
<>
@@ -3,13 +3,15 @@ import { isValidPhoneNumber } from "libphonenumber-js";
import { useRouter } from "next/navigation";
import { z } from "zod";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { Dialog } from "@calcom/features/components/controlled-dialog";
import { useOrgBranding } from "@calcom/features/ee/organizations/context/provider";
import { TeamEventTypeForm } from "@calcom/features/ee/teams/components/TeamEventTypeForm";
import { useCreateEventType } from "@calcom/lib/hooks/useCreateEventType";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { useTypedQuery } from "@calcom/lib/hooks/useTypedQuery";
import { MembershipRole, SchedulingType } from "@calcom/prisma/enums";
import type { MembershipRole } from "@calcom/prisma/enums";
import { SchedulingType } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import { Button } from "@calcom/ui/components/button";
import { DialogContent, DialogFooter, DialogClose } from "@calcom/ui/components/dialog";
@@ -73,10 +75,7 @@ export default function CreateEventTypeDialog({
const teamProfile = profileOptions.find((profile) => profile.teamId === teamId);
const isTeamAdminOrOwner =
teamId !== undefined &&
(teamProfile?.membershipRole === MembershipRole.OWNER ||
teamProfile?.membershipRole === MembershipRole.ADMIN);
const isTeamAdminOrOwner = teamId !== undefined && checkAdminOrOwner(teamProfile?.membershipRole);
const onSuccessMutation = (eventType: EventType) => {
router.replace(`/event-types/${eventType.id}${teamId ? "?tabName=team" : ""}`);
@@ -3,7 +3,7 @@
import { useSession } from "next-auth/react";
import { createContext, useState } from "react";
import { MembershipRole } from "@calcom/prisma/enums";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import type { OrgTeamsType } from "../filters/OrgTeamsFilter";
@@ -19,8 +19,8 @@ export const InsightsOrgTeamsContext = createContext<InsightsOrgTeamsContextType
export function InsightsOrgTeamsProvider({ children }: { children: React.ReactNode }) {
const session = useSession();
const currentOrgId = session.data?.user.org?.id;
const orgRole = session?.data?.user?.org?.role;
const isAdminOrOwner = orgRole === MembershipRole.OWNER || orgRole === MembershipRole.ADMIN;
const isAdminOrOwner = checkAdminOrOwner(session.data?.user?.org?.role);
const [orgTeamsType, setOrgTeamsType] = useState<OrgTeamsType>(
isAdminOrOwner && currentOrgId ? "org" : "yours"
);
@@ -2,9 +2,9 @@
import { useState, useEffect } from "react";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { useCompatSearchParams } from "@calcom/lib/hooks/useCompatSearchParams";
import { useLocale } from "@calcom/lib/hooks/useLocale";
import { MembershipRole } from "@calcom/prisma/enums";
import { trpc } from "@calcom/trpc/react";
import useMeQuery from "@calcom/trpc/react/hooks/useMeQuery";
import type { ButtonProps } from "@calcom/ui/components/button";
@@ -23,8 +23,7 @@ const CreateNewOutOfOfficeEntry = ({
const { t } = useLocale();
const me = useMeQuery();
const { data: orgData } = trpc.viewer.organizations.listCurrent.useQuery();
const isOrgAdminOrOwner =
orgData && (orgData.user.role === MembershipRole.OWNER || orgData.user.role === MembershipRole.ADMIN);
const isOrgAdminOrOwner = orgData && checkAdminOrOwner(orgData.user.role);
const hasTeamOOOAdminAccess = isOrgAdminOrOwner || me?.data?.isTeamAdminOrOwner;
const params = useCompatSearchParams();
+2 -4
View File
@@ -4,12 +4,12 @@ import appStore from "@calcom/app-store";
import type { TDependencyData } from "@calcom/app-store/_appRegistry";
import type { CredentialOwner } from "@calcom/app-store/types";
import { getAppFromSlug } from "@calcom/app-store/utils";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import getEnabledAppsFromCredentials from "@calcom/lib/apps/getEnabledAppsFromCredentials";
import getInstallCountPerApp from "@calcom/lib/apps/getInstallCountPerApp";
import { getUsersCredentials } from "@calcom/lib/server/getUsersCredentials";
import type { PrismaClient } from "@calcom/prisma";
import type { User } from "@calcom/prisma/client";
import { MembershipRole } from "@calcom/prisma/enums";
import type { AppCategories } from "@calcom/prisma/enums";
import { credentialForCalendarServiceSelect } from "@calcom/prisma/selects/credential";
import type { PaymentApp } from "@calcom/types/PaymentService";
@@ -168,9 +168,7 @@ export async function getConnectedApps({
name: team.name,
logoUrl: team.logoUrl,
credentialId: c.id,
isAdmin:
team.members[0].role === MembershipRole.ADMIN ||
team.members[0].role === MembershipRole.OWNER,
isAdmin: checkAdminOrOwner(team.members[0].role),
};
})
);
@@ -1,9 +1,10 @@
import { z } from "zod";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { markdownToSafeHTML } from "@calcom/lib/markdownToSafeHTML";
import type { EventTypeRepository } from "@calcom/lib/server/repository/eventType";
import { UserRepository } from "@calcom/lib/server/repository/user";
import { MembershipRole, PeriodType } from "@calcom/prisma/enums";
import { PeriodType } from "@calcom/prisma/enums";
import type { CustomInputSchema } from "@calcom/prisma/zod-utils";
import { EventTypeMetaDataSchema } from "@calcom/prisma/zod-utils";
@@ -60,7 +61,7 @@ export const eventOwnerProcedure = authedProcedure
const isOrgAdmin = !!ctx.user?.organization?.isOrgAdmin;
return (
event.team.members
.filter((member) => member.role === MembershipRole.OWNER || member.role === MembershipRole.ADMIN)
.filter((member) => checkAdminOrOwner(member.role))
.map((member) => member.userId)
.includes(ctx.user.id) || isOrgAdmin
);
@@ -1,6 +1,6 @@
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { getTranslation } from "@calcom/lib/server/i18n";
import prisma from "@calcom/prisma";
import { MembershipRole } from "@calcom/prisma/enums";
import type { TrpcSessionUser } from "@calcom/trpc/server/types";
import { TRPCError } from "@trpc/server";
@@ -43,7 +43,7 @@ export const outOfOfficeEntriesList = async ({ ctx, input }: GetOptions) => {
throw new TRPCError({ code: "NOT_FOUND", message: t("user_has_no_team_yet") });
}
const ownerOrAdminTeamIds = teams
.filter((team) => team.role === MembershipRole.OWNER || team.role === MembershipRole.ADMIN)
.filter((team) => checkAdminOrOwner(team.role))
.map((team) => team.teamId);
// Fetch team member userIds
@@ -1,6 +1,7 @@
import type { Prisma, PrismaPromise, User, Membership, Profile } from "@prisma/client";
import { ensureOrganizationIsReviewed } from "@calcom/ee/organizations/lib/ensureOrganizationIsReviewed";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { uploadAvatar } from "@calcom/lib/server/avatar";
import { checkRegularUsername } from "@calcom/lib/server/checkRegularUsername";
import { isOrganisationAdmin, isOrganisationOwner } from "@calcom/lib/server/queries/organisations";
@@ -177,7 +178,7 @@ export const updateUserHandler = async ({ ctx, input }: UpdateUserOptions) => {
});
}
if (input.role === MembershipRole.ADMIN || input.role === MembershipRole.OWNER) {
if (checkAdminOrOwner(input.role)) {
const teamIds = requestedMember.team.children
.map((sub_team) => sub_team.members.find((item) => item.userId === input.userId)?.teamId)
.filter(Boolean) as number[]; //filter out undefined
@@ -3,6 +3,7 @@ import type { TFunction } from "i18next";
import { getOrgFullOrigin } from "@calcom/ee/organizations/lib/orgDomains";
import { sendTeamInviteEmail } from "@calcom/emails";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { DEFAULT_SCHEDULE, getAvailabilityFromSchedule } from "@calcom/lib/availability";
import { ENABLE_PROFILE_SWITCHER, WEBAPP_URL } from "@calcom/lib/constants";
import { createAProfileForAnExistingUser } from "@calcom/lib/createAProfileForAnExistingUser";
@@ -417,10 +418,7 @@ export async function createMemberships({
teamId,
userId: invitee.id,
accepted,
role:
organizationRole === MembershipRole.ADMIN || organizationRole === MembershipRole.OWNER
? organizationRole
: invitee.newRole,
role: checkAdminOrOwner(organizationRole) ? organizationRole : invitee.newRole,
});
// membership for the org
@@ -1,9 +1,9 @@
import { Prisma } from "@prisma/client";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { getBookerBaseUrlSync } from "@calcom/lib/getBookerUrl/client";
import { UserRepository } from "@calcom/lib/server/repository/user";
import { prisma } from "@calcom/prisma";
import { MembershipRole } from "@calcom/prisma/enums";
import type { TrpcSessionUser } from "@calcom/trpc/server/types";
import { TRPCError } from "@trpc/server";
@@ -144,8 +144,7 @@ const checkCanAccessMembers = async (ctx: ListMembersHandlerOptions["ctx"], team
if (!membership) return false;
const isTeamAdminOrOwner =
membership?.role === MembershipRole.OWNER || membership?.role === MembershipRole.ADMIN;
const isTeamAdminOrOwner = checkAdminOrOwner(membership?.role);
if (team?.isPrivate && !isTeamAdminOrOwner) {
return false;
@@ -1,7 +1,7 @@
import type { Membership } from "@prisma/client";
import { checkAdminOrOwner } from "@calcom/features/auth/lib/checkAdminOrOwner";
import { prisma } from "@calcom/prisma";
import { MembershipRole } from "@calcom/prisma/enums";
import { TRPCError } from "@trpc/server";
@@ -19,15 +19,11 @@ export const webhookProcedure = authedProcedure
if (!memberships) return false;
if (teamId) {
return memberships.some(
(membership) =>
membership.teamId === teamId &&
(membership.role === MembershipRole.ADMIN || membership.role === MembershipRole.OWNER)
(membership) => membership.teamId === teamId && checkAdminOrOwner(membership.role)
);
}
return memberships.some(
(membership) =>
membership.userId === ctx.user.id &&
(membership.role === MembershipRole.ADMIN || membership.role === MembershipRole.OWNER)
(membership) => membership.userId === ctx.user.id && checkAdminOrOwner(membership.role)
);
};
@@ -70,9 +66,7 @@ export const webhookProcedure = authedProcedure
const userHasAdminOwnerPermissionInTeam =
user &&
user.teams.some(
(membership) =>
membership.teamId === webhook.teamId &&
(membership.role === MembershipRole.ADMIN || membership.role === MembershipRole.OWNER)
(membership) => membership.teamId === webhook.teamId && checkAdminOrOwner(membership.role)
);
if (!userHasAdminOwnerPermissionInTeam) {