fix: Show messaging app in locations list (#10741)

* Get messaging app as well through query because a messaging app is also a location app

* Fix type error

---------

Co-authored-by: Joe Au-Yeung <65426560+joeauyeung@users.noreply.github.com>
This commit is contained in:
Hariom Balhara 2023-08-14 20:32:29 +05:30 committed by GitHub
parent 1b3f676e57
commit 0f9c3571fe
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 34 additions and 17 deletions

View File

@ -1,6 +1,7 @@
import type { TFunction } from "next-i18next";
import type { CredentialDataWithTeamName } from "@calcom/app-store/utils";
import { defaultVideoAppCategories } from "@calcom/app-store/utils";
import getEnabledApps from "@calcom/lib/apps/getEnabledApps";
import { prisma } from "@calcom/prisma";
import { AppCategories } from "@calcom/prisma/enums";
@ -56,7 +57,7 @@ export async function getLocationGroupedOptions(
...idToSearchObject,
app: {
categories: {
hasSome: [AppCategories.conferencing, AppCategories.video],
hasSome: defaultVideoAppCategories,
},
},
},
@ -79,26 +80,24 @@ export async function getLocationGroupedOptions(
const integrations = await getEnabledApps(credentials, true);
integrations.forEach((app) => {
// All apps that are labeled as a locationOption are video apps.
if (app.locationOption) {
// All apps that are labeled as a locationOption are video apps. Extract the secondary category if available
let category =
let groupByCategory =
app.categories.length >= 2
? app.categories.find(
(category) =>
!([AppCategories.video, AppCategories.conferencing] as string[]).includes(category)
)
: app.category;
if (!category) category = AppCategories.conferencing;
? app.categories.find((groupByCategory) => !defaultVideoAppCategories.includes(groupByCategory))
: app.categories[0] || app.category;
if (!groupByCategory) groupByCategory = AppCategories.conferencing;
for (const credential of app.credentials) {
const label = `${app.locationOption.label} ${
credential.team?.name ? `(${credential.team.name})` : ""
}`;
const option = { ...app.locationOption, label, icon: app.logo, slug: app.slug, credential };
if (apps[category]) {
apps[category] = [...apps[category], option];
if (apps[groupByCategory]) {
apps[groupByCategory] = [...apps[groupByCategory], option];
} else {
apps[category] = [option];
apps[groupByCategory] = [option];
}
}
}

View File

@ -1,3 +1,4 @@
import type { AppCategories } from "@prisma/client";
import { Prisma } from "@prisma/client";
// If you import this file on any app it should produce circular dependency
@ -143,8 +144,17 @@ export function doesAppSupportTeamInstall(
concurrentMeetings: boolean | undefined = undefined
) {
return !appCategories.some(
(category) => category === "calendar" || (category === "conferencing" && !concurrentMeetings)
(category) =>
category === "calendar" ||
(defaultVideoAppCategories.includes(category as AppCategories) && !concurrentMeetings)
);
}
export const defaultVideoAppCategories: AppCategories[] = [
"conferencing",
"messaging",
// Legacy name for conferencing
"video",
];
export default getApps;

View File

@ -1,4 +1,4 @@
import type { Prisma } from "@prisma/client";
import type { AppCategories, Prisma } from "@prisma/client";
import type { Tag } from "@calcom/app-store/types";
@ -31,6 +31,10 @@ type DynamicLinkBasedEventLocation = {
export type EventLocationTypeFromAppMeta = StaticLinkBasedEventLocation | DynamicLinkBasedEventLocation;
type AppData = {
/**
* TODO: We must assert that if `location` is set in App config.json, then it must have atleast Messaging or Conferencing as a category.
* This is because we fetch only those credentials(as an optimization) which match that category.
*/
location?: EventLocationTypeFromAppMeta;
tag?: Tag;
} | null;
@ -81,14 +85,17 @@ export interface App {
/** The slug for the app store public page inside `/apps/[slug] */
slug: string;
/** The category to which this app belongs, currently we have `calendar`, `payment` or `video` */
/** The category to which this app belongs. Remove all usages of category and then remove the prop */
/*
* @deprecated Use categories
*/
category?: string;
/** The category to which this app belongs, currently we have `calendar`, `payment` or `video` */
categories: string[];
/** The category to which this app belongs. */
/**
* Messaging and Conferencing(Earlier called Video) are considered location apps and are fetched when configuring an event-type location.
*/
categories: AppCategories[];
/**
* `User` is the broadest category. `EventType` is when you want to add features to EventTypes.
* See https://app.gitbook.com/o/6snd8PyPYMhg0wUw6CeQ/s/VXRprBTuMlihk37NQgUU/~/changes/6xkqZ4qvJ3Xh9k8UaWaZ/engineering/product-specs/app-store#user-apps for more details

View File

@ -1,4 +1,5 @@
import { useAutoAnimate } from "@formkit/auto-animate/react";
import type { AppCategories } from "@prisma/client";
import { usePathname, useRouter, useSearchParams } from "next/navigation";
import type { UIEvent } from "react";
import { useEffect, useRef, useState } from "react";
@ -156,7 +157,7 @@ export function AllApps({ apps, searchText, categories, userAdminTeams }: AllApp
.filter((app) =>
selectedCategory !== null
? app.categories
? app.categories.includes(selectedCategory)
? app.categories.includes(selectedCategory as AppCategories)
: app.category === selectedCategory
: true
)