Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add personal mentoring dates #2587

Merged
merged 7 commits into from
Feb 4, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 48 additions & 0 deletions client/src/api/api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1030,6 +1030,18 @@ export interface CourseDto {
* @memberof CourseDto
*/
'personalMentoring': boolean;
/**
*
* @type {string}
* @memberof CourseDto
*/
'personalMentoringStartDate': string | null;
/**
*
* @type {string}
* @memberof CourseDto
*/
'personalMentoringEndDate': string | null;
/**
*
* @type {string}
Expand Down Expand Up @@ -1925,6 +1937,18 @@ export interface CreateCourseDto {
* @memberof CreateCourseDto
*/
'personalMentoring'?: boolean;
/**
*
* @type {string}
* @memberof CreateCourseDto
*/
'personalMentoringStartDate'?: string;
/**
*
* @type {string}
* @memberof CreateCourseDto
*/
'personalMentoringEndDate'?: string;
/**
*
* @type {string}
Expand Down Expand Up @@ -4806,6 +4830,18 @@ export interface ProfileCourseDto {
* @memberof ProfileCourseDto
*/
'personalMentoring': boolean;
/**
*
* @type {string}
* @memberof ProfileCourseDto
*/
'personalMentoringStartDate': string | null;
/**
*
* @type {string}
* @memberof ProfileCourseDto
*/
'personalMentoringEndDate': string | null;
/**
*
* @type {string}
Expand Down Expand Up @@ -6609,6 +6645,18 @@ export interface UpdateCourseDto {
* @memberof UpdateCourseDto
*/
'personalMentoring'?: boolean;
/**
*
* @type {string}
* @memberof UpdateCourseDto
*/
'personalMentoringStartDate'?: string | null;
/**
*
* @type {string}
* @memberof UpdateCourseDto
*/
'personalMentoringEndDate'?: string | null;
/**
*
* @type {string}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,9 @@ type FormData = {
logo?: string;
usePrivateRepositories?: boolean;
personalMentoring?: boolean;
personalMentoringStartDate?: string | null;
personalMentoringEndDate?: string | null;
personalMentoringDateRange: [dayjs.Dayjs | null, dayjs.Dayjs | null] | null;
certificateIssuer?: string;
discipline?: { id: number } | null;
courseId?: number;
Expand Down Expand Up @@ -308,9 +311,28 @@ export function CourseModal(props: CourseModalProps) {
<Checkbox>Use Private Repositories</Checkbox>
</Form.Item>

<Form.Item name="personalMentoring" valuePropName="checked">
<Checkbox>Personal mentoring</Checkbox>
</Form.Item>
<Row gutter={24}>
<Col md={8} sm={12} span={24}>
<Form.Item name="personalMentoring" valuePropName="checked">
<Checkbox>Personal mentoring</Checkbox>
</Form.Item>
</Col>
<Col md={8} sm={12} span={24}>
<Form.Item dependencies={['personalMentoring']}>
{({ getFieldValue }) =>
getFieldValue('personalMentoring') ? (
<Form.Item
name="personalMentoringDateRange"
label="Personal Mentoring Dates"
rules={[{ required: true, type: 'array', message: 'Please enter mentoring dates' }]}
>
<DatePicker.RangePicker style={{ width: '100%' }} />
</Form.Item>
) : null
}
</Form.Item>
</Col>
</Row>

<Form.Item name="inviteOnly" valuePropName="checked">
<Checkbox>Invite Only Course</Checkbox>
Expand All @@ -323,6 +345,10 @@ export function CourseModal(props: CourseModalProps) {

function createRecord(values: FormData) {
const [startDate, endDate] = values.range as [dayjs.Dayjs, dayjs.Dayjs];
const [personalMentoringStartDate, personalMentoringEndDate] = values.personalMentoringDateRange
? (values.personalMentoringDateRange as [dayjs.Dayjs, dayjs.Dayjs])
: [null, null];

const record: UpdateCourseDto = {
name: values.name,
fullName: values.fullName,
Expand All @@ -339,6 +365,12 @@ function createRecord(values: FormData) {
discordServerId: values.discordServerId,
usePrivateRepositories: values.usePrivateRepositories,
personalMentoring: values.personalMentoring,
personalMentoringStartDate: personalMentoringStartDate
? dayjs.utc(personalMentoringStartDate).startOf('day').format()
: null,
personalMentoringEndDate: personalMentoringEndDate
? dayjs.utc(personalMentoringEndDate).startOf('day').format()
: null,
logo: values.logo,
minStudentsPerMentor: values.minStudentsPerMentor,
certificateThreshold: values.certificateThreshold,
Expand All @@ -347,7 +379,17 @@ function createRecord(values: FormData) {
return record;
}

function getDateRange(
startDate?: string | null,
endDate?: string | null,
): [dayjs.Dayjs | null, dayjs.Dayjs | null] | null {
return startDate && endDate ? [startDate ? dayjs.utc(startDate) : null, endDate ? dayjs.utc(endDate) : null] : null;
}

function getInitialValues(modalData: Partial<Course>): FormData {
const range = getDateRange(modalData.startDate, modalData.endDate);
const personalMentoringDateRange =
getDateRange(modalData.personalMentoringStartDate, modalData.personalMentoringEndDate) || range;
return {
...modalData,
wearecommunityUrl: modalData.wearecommunityUrl ?? undefined,
Expand All @@ -356,12 +398,7 @@ function getInitialValues(modalData: Partial<Course>): FormData {
inviteOnly: !!modalData.inviteOnly,
state: modalData.completed ? 'completed' : modalData.planned ? 'planned' : 'active',
registrationEndDate: modalData.registrationEndDate ? dayjs.utc(modalData.registrationEndDate) : null,
range:
modalData.startDate && modalData.endDate
? [
modalData.startDate ? dayjs.utc(modalData.startDate) : null,
modalData.endDate ? dayjs.utc(modalData.endDate) : null,
]
: null,
range: range,
personalMentoringDateRange: personalMentoringDateRange,
};
}
8 changes: 8 additions & 0 deletions nestjs/src/courses/dto/course.dto.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ export class CourseDto {
this.usePrivateRepositories = course.usePrivateRepositories;
this.registrationEndDate = course.registrationEndDate?.toISOString() ?? null;
this.personalMentoring = course.personalMentoring;
this.personalMentoringStartDate = course.personalMentoringStartDate?.toISOString() ?? null;
this.personalMentoringEndDate = course.personalMentoringEndDate?.toISOString() ?? null;
this.logo = course.logo;
this.discipline = course.discipline ? { id: course.discipline.id, name: course.discipline.name } : null;
this.minStudentsPerMentor = course.minStudentsPerMentor;
Expand Down Expand Up @@ -96,6 +98,12 @@ export class CourseDto {
@ApiProperty()
personalMentoring: boolean;

@ApiProperty({ type: 'string', nullable: true })
personalMentoringStartDate: string | null;

@ApiProperty({ type: 'string', nullable: true })
personalMentoringEndDate: string | null;

@ApiProperty()
logo: string;

Expand Down
10 changes: 10 additions & 0 deletions nestjs/src/courses/dto/create-course.dto.ts
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,16 @@ export class CreateCourseDto {
@ApiProperty({ required: false })
personalMentoring?: boolean;

@IsString()
@IsOptional()
@ApiProperty({ required: false })
personalMentoringStartDate?: string;

@IsString()
@IsOptional()
@ApiProperty({ required: false })
personalMentoringEndDate?: string;

@IsString()
@IsOptional()
@ApiProperty({ required: false })
Expand Down
4 changes: 4 additions & 0 deletions nestjs/src/courses/dto/export-course.dto.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ export class ExportCourseDto {
this.description = course.description;
this.descriptionUrl = course.descriptionUrl;
this.registrationEndDate = course.registrationEndDate?.toISOString() ?? null;
this.personalMentoringStateDate = course.personalMentoringStartDate?.toISOString() ?? null;
this.personalMentoringEndDate = course.personalMentoringEndDate?.toISOString() ?? null;
this.wearecommunityUrl = course.wearecommunityUrl || null;
}

Expand All @@ -25,5 +27,7 @@ export class ExportCourseDto {
registrationEndDate: string | null;
startDate: string;
endDate: string;
personalMentoringStateDate: string | null;
personalMentoringEndDate: string | null;
wearecommunityUrl: string | null;
}
10 changes: 10 additions & 0 deletions nestjs/src/courses/dto/update-course.dto.ts
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,16 @@ export class UpdateCourseDto {
@ApiPropertyOptional()
personalMentoring?: boolean;

@IsString()
@IsOptional()
@ApiPropertyOptional({ type: 'string', nullable: true })
personalMentoringStartDate?: string | null;

@IsString()
@IsOptional()
@ApiPropertyOptional({ type: 'string', nullable: true })
personalMentoringEndDate?: string | null;

@IsString()
@IsOptional()
@ApiPropertyOptional()
Expand Down
12 changes: 12 additions & 0 deletions nestjs/src/spec.json
Original file line number Diff line number Diff line change
Expand Up @@ -2940,6 +2940,8 @@
"certificateIssuer": { "type": "string" },
"usePrivateRepositories": { "type": "boolean" },
"personalMentoring": { "type": "boolean" },
"personalMentoringStartDate": { "type": "string", "nullable": true },
"personalMentoringEndDate": { "type": "string", "nullable": true },
"logo": { "type": "string" },
"discipline": { "nullable": true, "allOf": [{ "$ref": "#/components/schemas/IdNameDto" }] },
"minStudentsPerMentor": { "type": "number" },
Expand Down Expand Up @@ -2969,6 +2971,8 @@
"certificateIssuer",
"usePrivateRepositories",
"personalMentoring",
"personalMentoringStartDate",
"personalMentoringEndDate",
"logo",
"discipline",
"minStudentsPerMentor",
Expand All @@ -2995,6 +2999,8 @@
"usePrivateRepositories": { "type": "boolean" },
"certificateIssuer": { "type": "string" },
"personalMentoring": { "type": "boolean" },
"personalMentoringStartDate": { "type": "string" },
"personalMentoringEndDate": { "type": "string" },
"logo": { "type": "string" },
"minStudentsPerMentor": { "type": "number" },
"certificateThreshold": { "type": "number" },
Expand Down Expand Up @@ -3022,6 +3028,8 @@
"certificateIssuer": { "type": "string" },
"usePrivateRepositories": { "type": "boolean" },
"personalMentoring": { "type": "boolean" },
"personalMentoringStartDate": { "type": "string", "nullable": true },
"personalMentoringEndDate": { "type": "string", "nullable": true },
"logo": { "type": "string" },
"disciplineId": { "type": "number" },
"minStudentsPerMentor": { "type": "number" },
Expand Down Expand Up @@ -4443,6 +4451,8 @@
"certificateIssuer": { "type": "string" },
"usePrivateRepositories": { "type": "boolean" },
"personalMentoring": { "type": "boolean" },
"personalMentoringStartDate": { "type": "string", "nullable": true },
"personalMentoringEndDate": { "type": "string", "nullable": true },
"logo": { "type": "string" },
"discipline": { "nullable": true, "allOf": [{ "$ref": "#/components/schemas/IdNameDto" }] },
"minStudentsPerMentor": { "type": "number" },
Expand Down Expand Up @@ -4472,6 +4482,8 @@
"certificateIssuer",
"usePrivateRepositories",
"personalMentoring",
"personalMentoringStartDate",
"personalMentoringEndDate",
"logo",
"discipline",
"minStudentsPerMentor",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import { MigrationInterface, QueryRunner } from 'typeorm';

export class CoursePersonalMentoringDates1738250779923 implements MigrationInterface {
name = 'CoursePersonalMentoringDates1738250779923';

public async up(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(`ALTER TABLE "course" ADD "personalMentoringStartDate" TIMESTAMP WITH TIME ZONE`);
await queryRunner.query(`ALTER TABLE "course" ADD "personalMentoringEndDate" TIMESTAMP WITH TIME ZONE`);
}

public async down(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(`ALTER TABLE "course" DROP COLUMN "personalMentoringStartDate"`);
await queryRunner.query(`ALTER TABLE "course" DROP COLUMN "personalMentoringEndDate"`);
}
}
2 changes: 2 additions & 0 deletions server/src/migrations/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ import { Course1712137476312 } from './1712137476312-Course';
import { CourseTask1730926720293 } from './1730926720293-CourseTask';
import { Contributor1734874453585 } from './1734874453585-Contributor';
import { Course1736458672717 } from './1736458672717-Course';
import { CoursePersonalMentoringDates1738250779923 } from './1738250779923-CoursePersonalMentoringDates';

export const migrations = [
UserMigration1630340371992,
Expand Down Expand Up @@ -120,4 +121,5 @@ export const migrations = [
CourseTask1730926720293,
Contributor1734874453585,
Course1736458672717,
CoursePersonalMentoringDates1738250779923,
];
6 changes: 6 additions & 0 deletions server/src/models/course.ts
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,12 @@ export class Course {
@Column({ default: true })
personalMentoring: boolean;

@Column({ type: 'timestamptz', nullable: true })
personalMentoringStartDate: Date | null;

@Column({ type: 'timestamptz', nullable: true })
personalMentoringEndDate: Date | null;

@Column({ nullable: true })
logo: string;

Expand Down
17 changes: 10 additions & 7 deletions setup/backup-local.sql
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
--

-- Dumped from database version 15.5 (Debian 15.5-1.pgdg120+1)
-- Dumped by pg_dump version 15.10 (Homebrew)
-- Dumped by pg_dump version 15.10

SET statement_timeout = 0;
SET lock_timeout = 0;
Expand Down Expand Up @@ -250,7 +250,9 @@ CREATE TABLE public.course (
"disciplineId" integer,
"minStudentsPerMentor" integer DEFAULT 2,
"certificateThreshold" integer DEFAULT 70 NOT NULL,
"wearecommunityUrl" character varying
"wearecommunityUrl" character varying,
"personalMentoringStartDate" timestamp with time zone,
"personalMentoringEndDate" timestamp with time zone
);


Expand Down Expand Up @@ -2603,10 +2605,10 @@ COPY public.contributor (id, created_date, updated_date, deleted_date, user_id,
-- Data for Name: course; Type: TABLE DATA; Schema: public; Owner: rs_master
--

COPY public.course (id, "createdDate", "updatedDate", name, year, "primarySkillId", "primarySkillName", "locationName", alias, completed, description, "descriptionUrl", planned, "startDate", "endDate", "fullName", "registrationEndDate", "inviteOnly", "discordServerId", "certificateIssuer", "usePrivateRepositories", "personalMentoring", logo, "disciplineId", "minStudentsPerMentor", "certificateThreshold", "wearecommunityUrl") FROM stdin;
11 2019-08-27 07:36:13.565873 2020-03-13 15:39:41.477995 RS 2019 Q3 \N javascript JavaScript \N rs-2019-q3 t RS 2019 Q3 \N f 2019-09-09 07:35:20.981+00 2020-01-31 07:35:20.981+00 Rolling Scopes School 2019 Q3 \N f \N \N t t \N \N 2 70 \N
13 2019-10-21 08:05:31.068833 2020-04-06 15:14:44.116961 RS 2020 Q1 \N javascript JavaScript \N rs-2020-q1 f Javascript / Frontend Курс.\nВводное занятие - 2 февраля\nОрганизационный вебинар начнется 2 февраля в 12:00 по минскому времени (GMT+3). Мы расскажем о процессе обучения в RS School и выдадим задания для первого этапа обучения.\n\nВебинар будет транслироваться на канале https://www.youtube.com/c/rollingscopesschool.\nРекомендуем подписаться на канал и нажать колокольчик, чтобы не пропустить начало трансляции. \n\nЕсли у вас не будет возможности присоединиться к онлайн-трансляции, не переживайте! \nЗапись вебинара будет размещена на канале в открытом доступе.\n\nОписание тренинга\nОсновной сайт: https://rs.school/js/\n\nПодробная информация о школе: https://docs.rs.school \N f 2020-02-02 09:01:56.398+00 2020-07-31 08:01:56.398+00 Rolling Scopes School 2020 Q1: JavaScript/Front-end 2020-04-15 08:40:46.24+00 f \N \N t t \N \N 2 70 \N
23 2020-02-25 09:28:08.842897 2021-07-28 20:44:30.259905 TEST COURSE \N javascript JavaScript \N test-course f TEST COURSE \N f 2021-05-31 21:00:00+00 2023-06-30 21:00:00+00 TEST COURSE \N t 2 \N t t \N \N 2 70 \N
COPY public.course (id, "createdDate", "updatedDate", name, year, "primarySkillId", "primarySkillName", "locationName", alias, completed, description, "descriptionUrl", planned, "startDate", "endDate", "fullName", "registrationEndDate", "inviteOnly", "discordServerId", "certificateIssuer", "usePrivateRepositories", "personalMentoring", logo, "disciplineId", "minStudentsPerMentor", "certificateThreshold", "wearecommunityUrl", "personalMentoringStartDate", "personalMentoringEndDate") FROM stdin;
13 2019-10-21 08:05:31.068833 2020-04-06 15:14:44.116961 RS 2020 Q1 \N javascript JavaScript \N rs-2020-q1 f Javascript / Frontend Курс.\nВводное занятие - 2 февраля\nОрганизационный вебинар начнется 2 февраля в 12:00 по минскому времени (GMT+3). Мы расскажем о процессе обучения в RS School и выдадим задания для первого этапа обучения.\n\nВебинар будет транслироваться на канале https://www.youtube.com/c/rollingscopesschool.\nРекомендуем подписаться на канал и нажать колокольчик, чтобы не пропустить начало трансляции. \n\nЕсли у вас не будет возможности присоединиться к онлайн-трансляции, не переживайте! \nЗапись вебинара будет размещена на канале в открытом доступе.\n\nОписание тренинга\nОсновной сайт: https://rs.school/js/\n\nПодробная информация о школе: https://docs.rs.school \N f 2020-02-02 09:01:56.398+00 2020-07-31 08:01:56.398+00 Rolling Scopes School 2020 Q1: JavaScript/Front-end 2020-04-15 08:40:46.24+00 f \N \N t t \N \N 2 70 \N \N \N
23 2020-02-25 09:28:08.842897 2021-07-28 20:44:30.259905 TEST COURSE \N javascript JavaScript \N test-course f TEST COURSE \N f 2021-05-31 21:00:00+00 2023-06-30 21:00:00+00 TEST COURSE \N t 2 \N t t \N \N 2 70 \N \N \N
11 2019-08-27 07:36:13.565873 2025-01-30 19:25:33.198749 RS 2019 Q3 \N javascript JavaScript \N rs-2019-q3 t RS 2019 Q3 https://rs.school/courses/javascript-preschool-ru f 2019-09-09 00:00:00+00 2020-01-31 00:00:00+00 Rolling Scopes School 2019 Q3 \N f 2 \N t t \N 1 2 70 \N 2019-09-23 00:00:00+00 2020-01-31 00:00:00+00
\.


Expand Down Expand Up @@ -3317,6 +3319,7 @@ COPY public.migrations (id, "timestamp", name) FROM stdin;
58 1730926720293 CourseTask1730926720293
59 1734874453585 Contributor1734874453585
60 1736458672717 Course1736458672717
61 1738250779923 CoursePersonalMentoringDates1738250779923
\.


Expand Down Expand Up @@ -4250,7 +4253,7 @@ SELECT pg_catalog.setval('public.mentor_registry_id_seq', 290, true);
-- Name: migrations_id_seq; Type: SEQUENCE SET; Schema: public; Owner: rs_master
--

SELECT pg_catalog.setval('public.migrations_id_seq', 60, true);
SELECT pg_catalog.setval('public.migrations_id_seq', 61, true);


--
Expand Down
Loading