Skip to content

Commit fadafcd

Browse files
authored
♻️ 크루장도 다가오는 일정 리스트 조회 가능하게끔 수정
♻️ 크루장도 다가오는 일정 리스트 조회 가능하게끔 수정
2 parents 6051e01 + 727fb42 commit fadafcd

3 files changed

Lines changed: 219 additions & 75 deletions

File tree

src/crew/page/plan/controller/plan.controller.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -896,8 +896,10 @@ export const getUpcomingPlans = async (req, res, next) => {
896896
const page = parseInt(req.query.page) || 1;
897897
const size = parseInt(req.query.size) || 5;
898898
const userId = req.payload?.id; // JWT 토큰에서 사용자 ID 추출 (선택적)
899+
const { crewId } = req.params; // URL 파라미터에서 crewId 추출
899900

900901
const result = await planService.CrewPlanService.getUpcomingPlans(
902+
Number(crewId),
901903
page,
902904
size,
903905
userId

src/crew/page/plan/repository/plan.repository.js

Lines changed: 214 additions & 73 deletions
Original file line numberDiff line numberDiff line change
@@ -293,100 +293,241 @@ export const CrewPlanRepository = {
293293
},
294294

295295
// 사용자가 신청완료한 다가오는 일정 조회
296-
findUpcomingPlansByUserId: async (userId, page = 1, size = 5) => {
296+
findUpcomingPlansByUserId: async (crewId, userId, page = 1, size = 5) => {
297297
const skip = (page - 1) * size;
298298
// 한국 시간(KST, UTC+9)으로 오늘 날짜 설정
299299
const today = new Date();
300300
today.setHours(today.getHours() + 9); // UTC+9 (한국 시간)
301301
today.setHours(0, 0, 0, 0); // 오늘 날짜의 시작 (00:00:00)
302302

303-
//Promise.all : 여러 비동기 작업을 동시에 실행하고 모든 결과를 기다리는 메소드
304-
const [totalCount, plans] = await Promise.all([
305-
// 첫 번째 Promise: 전체 개수 조회
306-
prisma.crewPlanRequest.count({
307-
where: {
308-
crewMember: {
309-
userId: Number(userId)
303+
// 먼저 사용자의 CrewMember 정보를 조회하여 role 확인
304+
const crewMember = await prisma.crewMember.findFirst({
305+
where: {
306+
userId: Number(userId),
307+
crewId: Number(crewId) // 특정 크루에서의 멤버 정보만 조회
308+
},
309+
select: {
310+
id: true,
311+
role: true
312+
}
313+
});
314+
315+
if (!crewMember) {
316+
// CrewMember가 없는 경우 빈 결과 반환
317+
return {
318+
plans: [],
319+
pagination: {
320+
totalElements: 0,
321+
currentPage: page,
322+
pageSize: size,
323+
totalPages: 0,
324+
hasNext: false,
325+
hasPrevious: false
326+
}
327+
};
328+
}
329+
330+
let totalCount, plans;
331+
332+
// 크루장(role = 2)인 경우: 직접 생성한 일정 + 신청한 일정 모두 조회
333+
if (crewMember.role === 2) {
334+
[totalCount, plans] = await Promise.all([
335+
// 전체 개수 조회 (생성한 일정 + 신청한 일정)
336+
prisma.crewPlan.count({
337+
where: {
338+
crewId: Number(crewId), // 특정 크루의 일정만 조회
339+
OR: [
340+
// 직접 생성한 일정
341+
{
342+
crewMemberId: crewMember.id,
343+
day: {
344+
gte: today
345+
}
346+
},
347+
// 신청한 일정
348+
{
349+
crewPlanRequest: {
350+
some: {
351+
crewMemberId: crewMember.id,
352+
status: 1
353+
}
354+
},
355+
day: {
356+
gte: today
357+
}
358+
}
359+
]
360+
}
361+
}),
362+
// 일정 목록 조회
363+
prisma.crewPlan.findMany({
364+
where: {
365+
crewId: Number(crewId), // 특정 크루의 일정만 조회
366+
OR: [
367+
// 직접 생성한 일정
368+
{
369+
crewMemberId: crewMember.id,
370+
day: {
371+
gte: today
372+
}
373+
},
374+
// 신청한 일정
375+
{
376+
crewPlanRequest: {
377+
some: {
378+
crewMemberId: crewMember.id,
379+
status: 1
380+
}
381+
},
382+
day: {
383+
gte: today
384+
}
385+
}
386+
]
310387
},
311-
status: 1, // 신청완료 상태
312-
crewPlan: {
313-
day: {
314-
gte: today // 오늘 이후의 일정만(today: 한국시간 기준 오늘 날짜)
388+
orderBy: {
389+
day: 'asc'
390+
},
391+
skip,
392+
take: size,
393+
select: {
394+
id: true,
395+
title: true,
396+
day: true,
397+
crew: {
398+
select: {
399+
title: true
400+
}
315401
}
316402
}
403+
})
404+
]);
405+
406+
// 크루장의 경우 직접 조회한 일정 데이터를 그대로 사용
407+
const processedPlans = plans.map(plan => {
408+
const planDate = new Date(plan.day);
409+
const todayDate = new Date();
410+
todayDate.setHours(todayDate.getHours() + 9);
411+
todayDate.setHours(0, 0, 0, 0);
412+
planDate.setHours(0, 0, 0, 0);
413+
414+
const daysUntil = Math.ceil((planDate - todayDate) / (1000 * 60 * 60 * 24));
415+
416+
return {
417+
id: plan.id,
418+
crew_name: plan.crew.title,
419+
title: plan.title,
420+
day: plan.day,
421+
daysUntil: daysUntil
422+
};
423+
});
424+
425+
const totalPages = Math.ceil(totalCount / size);
426+
427+
return {
428+
plans: processedPlans,
429+
pagination: {
430+
totalElements: totalCount,
431+
currentPage: page,
432+
pageSize: size,
433+
totalPages: totalPages,
434+
hasNext: page < totalPages,
435+
hasPrevious: page > 1
317436
}
318-
}),
319-
// 두 번째 Promise: 일정 목록 조회
320-
prisma.crewPlanRequest.findMany({
321-
where: {
322-
crewMember: {
323-
userId: Number(userId)
324-
},
325-
status: 1, // 신청완료 상태
326-
crewPlan: {
327-
day: {
328-
gte: today // 오늘 이후의 일정만
437+
};
438+
} else {
439+
// 크루원(role = 0) 또는 운영진(role = 1)인 경우: 기존 로직 사용
440+
[totalCount, plans] = await Promise.all([
441+
// 첫 번째 Promise: 전체 개수 조회
442+
prisma.crewPlanRequest.count({
443+
where: {
444+
crewMember: {
445+
userId: Number(userId),
446+
crewId: Number(crewId) // 특정 크루의 멤버만 조회
447+
},
448+
status: 1, // 신청완료 상태
449+
crewPlan: {
450+
crewId: Number(crewId), // 특정 크루의 일정만 조회
451+
day: {
452+
gte: today // 오늘 이후의 일정만(today: 한국시간 기준 오늘 날짜)
453+
}
329454
}
330455
}
331-
},
332-
orderBy: {
333-
crewPlan: {
334-
day: 'asc' // 날짜순으로 정렬 (가까운 일정부터)
335-
}
336-
},
337-
skip,
338-
take: size,
339-
select: {
340-
crewPlan: {
341-
select: {
342-
id: true,
343-
title: true,
344-
day: true,
345-
crew: {
346-
select: {
347-
title: true
456+
}),
457+
// 두 번째 Promise: 일정 목록 조회
458+
prisma.crewPlanRequest.findMany({
459+
where: {
460+
crewMember: {
461+
userId: Number(userId),
462+
crewId: Number(crewId) // 특정 크루의 멤버만 조회
463+
},
464+
status: 1, // 신청완료 상태
465+
crewPlan: {
466+
crewId: Number(crewId), // 특정 크루의 일정만 조회
467+
day: {
468+
gte: today // 오늘 이후의 일정만
469+
}
470+
}
471+
},
472+
orderBy: {
473+
crewPlan: {
474+
day: 'asc' // 날짜순으로 정렬 (가까운 일정부터)
475+
}
476+
},
477+
skip,
478+
take: size,
479+
select: {
480+
crewPlan: {
481+
select: {
482+
id: true,
483+
title: true,
484+
day: true,
485+
crew: {
486+
select: {
487+
title: true
488+
}
348489
}
349490
}
350491
}
351492
}
352-
}
353-
})
354-
]);
493+
})
494+
]);
355495

356-
const totalPages = Math.ceil(totalCount / size);
357-
358-
// 일정 데이터를 가공하여 daysUntil 계산
359-
const processedPlans = plans.map(request => {
360-
const plan = request.crewPlan;
361-
const planDate = new Date(plan.day); // 일정 날짜
362-
// 한국 시간(KST, UTC+9)으로 오늘 날짜 설정
363-
const todayDate = new Date(); // 오늘 날짜
364-
todayDate.setHours(todayDate.getHours() + 9); // UTC+9 (한국 시간)
365-
todayDate.setHours(0, 0, 0, 0);
366-
planDate.setHours(0, 0, 0, 0);
496+
const totalPages = Math.ceil(totalCount / size);
367497

368-
const daysUntil = Math.ceil((planDate - todayDate) / (1000 * 60 * 60 * 24)); // 일정 날짜와 오늘날짜의 차이로 남은 날짜 계산 -> D-Day까지 몇일 남았는지 계산
498+
// 일정 데이터를 가공하여 daysUntil 계산
499+
const processedPlans = plans.map(request => {
500+
const plan = request.crewPlan;
501+
const planDate = new Date(plan.day); // 일정 날짜
502+
// 한국 시간(KST, UTC+9)으로 오늘 날짜 설정
503+
const todayDate = new Date(); // 오늘 날짜
504+
todayDate.setHours(todayDate.getHours() + 9); // UTC+9 (한국 시간)
505+
todayDate.setHours(0, 0, 0, 0);
506+
planDate.setHours(0, 0, 0, 0);
507+
508+
const daysUntil = Math.ceil((planDate - todayDate) / (1000 * 60 * 60 * 24)); // 일정 날짜와 오늘날짜의 차이로 남은 날짜 계산 -> D-Day까지 몇일 남았는지 계산
509+
510+
return {
511+
id: plan.id,
512+
crew_name: plan.crew.title,
513+
title: plan.title,
514+
day: plan.day,
515+
daysUntil: daysUntil
516+
};
517+
});
369518

370519
return {
371-
id: plan.id,
372-
crew_name: plan.crew.title,
373-
title: plan.title,
374-
day: plan.day,
375-
daysUntil: daysUntil
520+
plans: processedPlans,
521+
pagination: {
522+
totalElements: totalCount,
523+
currentPage: page,
524+
pageSize: size,
525+
totalPages: totalPages,
526+
hasNext: page < totalPages,
527+
hasPrevious: page > 1
528+
}
376529
};
377-
});
378-
379-
return {
380-
plans: processedPlans,
381-
pagination: {
382-
totalElements: totalCount,
383-
currentPage: page,
384-
pageSize: size,
385-
totalPages: totalPages,
386-
hasNext: page < totalPages,
387-
hasPrevious: page > 1
388-
}
389-
};
530+
}
390531
}
391532

392533
}

src/crew/page/plan/service/plan.service.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -320,7 +320,7 @@ export const CrewPlanService = {
320320
},
321321

322322
//다가오는 일정 리스트 조회 서비스
323-
getUpcomingPlans: async (page = 1, size = 5, userId) => {
323+
getUpcomingPlans: async (crewId, page = 1, size = 5, userId) => {
324324
if (!userId) {
325325
// 로그인하지 않은 사용자의 경우 빈 결과 반환
326326
return new planResponse.GetUpcomingPlansResponse(
@@ -338,14 +338,15 @@ export const CrewPlanService = {
338338

339339
const result =
340340
await planRepository.CrewPlanRepository.findUpcomingPlansByUserId(
341+
Number(crewId),
341342
Number(userId),
342343
page,
343344
size,
344345
);
345346

346347
return new planResponse.GetUpcomingPlansResponse(
347348
result.plans,
348-
result.pagination,
349+
result.pagination
349350
);
350351
},
351352
};

0 commit comments

Comments
 (0)