Skip to content

Commit

Permalink
Merge branch 'main' into platform-onboarding
Browse files Browse the repository at this point in the history
  • Loading branch information
Ryukemeister committed May 9, 2024
2 parents e6325c8 + 6d8fbfc commit 15f8f99
Show file tree
Hide file tree
Showing 15 changed files with 236 additions and 69 deletions.
6 changes: 4 additions & 2 deletions apps/api/v2/src/ee/gcal/gcal.controller.ts
Expand Up @@ -26,6 +26,7 @@ import {
} from "@nestjs/common";
import { ConfigService } from "@nestjs/config";
import { ApiTags as DocsTags } from "@nestjs/swagger";
import { Prisma } from "@prisma/client";
import { Request } from "express";
import { google } from "googleapis";
import { z } from "zod";
Expand Down Expand Up @@ -106,10 +107,11 @@ export class GcalController {

const oAuth2Client = await this.gcalService.getOAuthClient(this.redirectUri);
const token = await oAuth2Client.getToken(parsedCode);
const key = token.res?.data;
// Google oAuth Credentials are stored in token.tokens
const key = token.tokens;
const credential = await this.credentialRepository.createAppCredential(
GOOGLE_CALENDAR_TYPE,
key,
key as Prisma.InputJsonValue,
ownerId
);

Expand Down
Expand Up @@ -139,6 +139,8 @@ describe("OAuth Client Users Endpoints", () => {
const requestBody: CreateManagedUserInput = {
email: userEmail,
timeZone: userTimeZone,
weekStart: "Monday",
timeFormat: 24,
};

const response = await request(app.getHttpServer())
Expand All @@ -158,6 +160,9 @@ describe("OAuth Client Users Endpoints", () => {
expect(responseBody.status).toEqual(SUCCESS_STATUS);
expect(responseBody.data).toBeDefined();
expect(responseBody.data.user.email).toEqual(getOAuthUserEmail(oAuthClient.id, requestBody.email));
expect(responseBody.data.user.timeZone).toEqual(requestBody.timeZone);
expect(responseBody.data.user.weekStart).toEqual(requestBody.weekStart);
expect(responseBody.data.user.timeFormat).toEqual(requestBody.timeFormat);
expect(responseBody.data.accessToken).toBeDefined();
expect(responseBody.data.refreshToken).toBeDefined();

Expand Down
Expand Up @@ -53,6 +53,9 @@ export class OAuthClientUsersService {
},
},
isPlatformManaged,
timeFormat: body.timeFormat,
weekStart: body.weekStart,
timeZone: body.timeZone,
})
)[0];
await this.userRepository.addToOAuthClient(user.id, oAuthClientId);
Expand Down
22 changes: 11 additions & 11 deletions apps/api/v2/src/modules/users/inputs/create-managed-user.input.ts
@@ -1,8 +1,8 @@
import { IsTimeFormat } from "@/modules/users/inputs/validators/is-time-format";
import { IsWeekStart } from "@/modules/users/inputs/validators/is-week-start";
import { ApiProperty } from "@nestjs/swagger";
import { IsNumber, IsOptional, IsTimeZone, IsString, Validate } from "class-validator";
import { IsOptional, IsTimeZone, IsString } from "class-validator";

export type WeekDay = "Monday" | "Tuesday" | "Wednesday" | "Thursday" | "Friday" | "Saturday" | "Sunday";
export type TimeFormat = 12 | 24;
export class CreateManagedUserInput {
@IsString()
@ApiProperty({ example: "alice@example.com" })
Expand All @@ -12,17 +12,17 @@ export class CreateManagedUserInput {
@IsOptional()
name?: string;

@IsNumber()
@IsOptional()
@Validate(IsTimeFormat)
@ApiProperty({ example: 12 })
timeFormat?: number;
@ApiProperty({ example: 12, enum: [12, 24], description: "Must be 12 or 24" })
timeFormat?: TimeFormat;

@IsString()
@IsOptional()
@Validate(IsWeekStart)
@ApiProperty({ example: "Sunday" })
weekStart?: string;
@IsString()
@ApiProperty({
example: "Monday",
enum: ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"],
})
weekStart?: WeekDay;

@IsTimeZone()
@IsOptional()
Expand Down
20 changes: 11 additions & 9 deletions apps/api/v2/src/modules/users/inputs/update-managed-user.input.ts
@@ -1,6 +1,6 @@
import { IsTimeFormat } from "@/modules/users/inputs/validators/is-time-format";
import { IsWeekStart } from "@/modules/users/inputs/validators/is-week-start";
import { IsNumber, IsOptional, IsString, IsTimeZone, Validate } from "class-validator";
import { TimeFormat, WeekDay } from "@/modules/users/inputs/create-managed-user.input";
import { ApiProperty } from "@nestjs/swagger";
import { IsNumber, IsOptional, IsString, IsTimeZone } from "class-validator";

export class UpdateManagedUserInput {
@IsString()
Expand All @@ -11,19 +11,21 @@ export class UpdateManagedUserInput {
@IsOptional()
name?: string;

@IsNumber()
@IsOptional()
@Validate(IsTimeFormat)
timeFormat?: number;
@ApiProperty({ example: 12, enum: [12, 24], description: "Must be 12 or 24" })
timeFormat?: TimeFormat;

@IsNumber()
@IsOptional()
defaultScheduleId?: number;

@IsString()
@IsOptional()
@Validate(IsWeekStart)
weekStart?: string;
@IsString()
@ApiProperty({
example: "Monday",
enum: ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"],
})
weekStart?: WeekDay;

@IsTimeZone()
@IsOptional()
Expand Down
12 changes: 0 additions & 12 deletions apps/api/v2/src/modules/users/inputs/validators/is-time-format.ts

This file was deleted.

23 changes: 0 additions & 23 deletions apps/api/v2/src/modules/users/inputs/validators/is-week-start.ts

This file was deleted.

2 changes: 1 addition & 1 deletion apps/api/v2/src/modules/users/users.repository.ts
Expand Up @@ -157,7 +157,7 @@ export class UsersRepository {

formatInput(userInput: CreateManagedUserInput | UpdateManagedUserInput) {
if (userInput.weekStart) {
userInput.weekStart = capitalize(userInput.weekStart);
userInput.weekStart = userInput.weekStart;
}

if (userInput.timeZone) {
Expand Down
46 changes: 38 additions & 8 deletions apps/api/v2/swagger/documentation.json
Expand Up @@ -1651,11 +1651,25 @@
},
"timeFormat": {
"type": "number",
"example": 12
"example": 12,
"enum": [
12,
24
],
"description": "Must be 12 or 24"
},
"weekStart": {
"type": "string",
"example": "Sunday"
"example": "Monday",
"enum": [
"Monday",
"Tuesday",
"Wednesday",
"Thursday",
"Friday",
"Saturday",
"Sunday"
]
},
"timeZone": {
"type": "string",
Expand Down Expand Up @@ -1731,21 +1745,37 @@
"UpdateManagedUserInput": {
"type": "object",
"properties": {
"timeFormat": {
"type": "number",
"example": 12,
"enum": [
12,
24
],
"description": "Must be 12 or 24"
},
"weekStart": {
"type": "string",
"example": "Monday",
"enum": [
"Monday",
"Tuesday",
"Wednesday",
"Thursday",
"Friday",
"Saturday",
"Sunday"
]
},
"email": {
"type": "string"
},
"name": {
"type": "string"
},
"timeFormat": {
"type": "number"
},
"defaultScheduleId": {
"type": "number"
},
"weekStart": {
"type": "string"
},
"timeZone": {
"type": "string"
}
Expand Down
2 changes: 2 additions & 0 deletions apps/api/v2/test/setEnvVars.ts
Expand Up @@ -8,6 +8,8 @@ const env: Partial<Omit<Environment, "NODE_ENV">> = {
JWT_SECRET: "XF+Hws3A5g2eyWA5uGYYVJ74X+wrCWJ8oWo6kAfU6O8=",
LOG_LEVEL: "trace",
REDIS_URL: "redis://localhost:9199",
STRIPE_API_KEY: "sk_test_51J4",
STRIPE_WEBHOOK_SECRET: "whsec_51J4",
};
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
Expand Down
3 changes: 2 additions & 1 deletion apps/web/components/eventtype/EventLimitsTab.tsx
Expand Up @@ -8,6 +8,7 @@ import { Controller, useFormContext } from "react-hook-form";
import type { SingleValue } from "react-select";

import useLockedFieldsManager from "@calcom/features/ee/managed-event-types/hooks/useLockedFieldsManager";
import { getDefinedBufferTimes } from "@calcom/features/eventtypes/lib/getDefinedBufferTimes";
import type { FormValues } from "@calcom/features/eventtypes/lib/types";
import { classNames } from "@calcom/lib";
import type { DurationType } from "@calcom/lib/convertToNewDurationType";
Expand Down Expand Up @@ -172,7 +173,7 @@ export const EventLimitsTab = ({ eventType }: Pick<EventTypeSetupProps, "eventTy
label: t("event_buffer_default"),
value: 0,
},
...[5, 10, 15, 20, 30, 45, 60, 90, 120].map((minutes) => ({
...getDefinedBufferTimes().map((minutes) => ({
label: `${minutes} ${t("minutes")}`,
value: minutes,
})),
Expand Down
12 changes: 10 additions & 2 deletions packages/core/getBusyTimes.ts
Expand Up @@ -14,6 +14,8 @@ import { stringToDayjs } from "@calcom/prisma/zod-utils";
import type { EventBusyDetails, IntervalLimit } from "@calcom/types/Calendar";
import type { CredentialPayload } from "@calcom/types/Credential";

import { getDefinedBufferTimes } from "../features/eventtypes/lib/getDefinedBufferTimes";

export async function getBusyTimes(params: {
credentials: CredentialPayload[];
userId: number;
Expand Down Expand Up @@ -85,10 +87,16 @@ export async function getBusyTimes(params: {
const endTimeDate =
rescheduleUid && duration ? dayjs(endTime).add(duration, "minute").toDate() : new Date(endTime);

// to also get bookings that are outside of start and end time, but the buffer falls within the start and end time
const definedBufferTimes = getDefinedBufferTimes();
const maxBuffer = definedBufferTimes[definedBufferTimes.length - 1];
const startTimeAdjustedWithMaxBuffer = dayjs(startTimeDate).subtract(maxBuffer, "minute").toDate();
const endTimeAdjustedWithMaxBuffer = dayjs(endTimeDate).add(maxBuffer, "minute").toDate();

// startTime is less than endTimeDate and endTime grater than startTimeDate
const sharedQuery = {
startTime: { lte: endTimeDate },
endTime: { gte: startTimeDate },
startTime: { lte: endTimeAdjustedWithMaxBuffer },
endTime: { gte: startTimeAdjustedWithMaxBuffer },
status: {
in: [BookingStatus.ACCEPTED],
},
Expand Down

0 comments on commit 15f8f99

Please sign in to comment.