Skip to content

Commit

Permalink
Merge pull request #43 from Team-UMC/feature/#30/member-active-manage…
Browse files Browse the repository at this point in the history
…ment

[FEAT] 유저의 마지막 활동 시간 기록 기능 및 온라인 상태 확인 기능 구현
  • Loading branch information
junseokkim authored Jan 27, 2024
2 parents 46e7c90 + 40dafcd commit 7b59f15
Show file tree
Hide file tree
Showing 34 changed files with 195 additions and 174 deletions.
22 changes: 22 additions & 0 deletions src/main/java/com/umc/networkingService/config/WebMvcConfig.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.umc.networkingService.config;

import com.umc.networkingService.domain.member.interceptor.LastActiveInterceptor;
import lombok.RequiredArgsConstructor;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration
@RequiredArgsConstructor
public class WebMvcConfig implements WebMvcConfigurer {

private final LastActiveInterceptor lastActiveInterceptor;

@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(lastActiveInterceptor)
.addPathPatterns("/**") // 모든 요청에 대해 인터셉터 적용
.excludePathPatterns("/v3/**", "/swagger-ui/**") // 스웨거 요청은 제외
.excludePathPatterns("/members/login"); // 로그인 API 제외
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,6 @@
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@Tag(name = "초대 API", description = "초대 관련 API")
@RestController
@RequiredArgsConstructor
Expand All @@ -43,7 +41,7 @@ public BaseResponse<InviteCreateResponse> createInviteCode(@CurrentMember Member
@ApiResponse(responseCode = "COMMON200", description = "성공")
})
@GetMapping("/staff/invites")
public BaseResponse<List<InviteInquiryMineResponse>> inquiryMyInviteCode(@CurrentMember Member member) {
public BaseResponse<InviteInquiryMineResponse> inquiryMyInviteCode(@CurrentMember Member member) {
return BaseResponse.onSuccess(inviteService.inquiryMyInviteCode(member));
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,20 @@
import lombok.Getter;

import java.time.LocalDateTime;
import java.util.List;

@Getter
@AllArgsConstructor
public class InviteInquiryMineResponse {
private String inviteCode;
private Role role;
private LocalDateTime createdAt;

private List<InviteInfo> invites;

@Getter
@AllArgsConstructor
public static class InviteInfo {
private String inviteCode;
private Role role;
private LocalDateTime createdAt;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
@Component
public class InviteMapper {

public InviteInquiryMineResponse toInquiryMineResponse(Invite invite) {
return new InviteInquiryMineResponse(invite.getCode(), invite.getRole(), invite.getCreatedAt());
public InviteInquiryMineResponse.InviteInfo toInquiryMineResponse(Invite invite) {
return new InviteInquiryMineResponse.InviteInfo(invite.getCode(), invite.getRole(), invite.getCreatedAt());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,8 @@
import com.umc.networkingService.domain.member.entity.Member;
import com.umc.networkingService.global.common.enums.Role;

import java.util.List;

public interface InviteService {
InviteCreateResponse createInviteCode(Member member, Role role);
InviteAuthenticateResponse authenticateInviteCode(Member member, String inviteCode);
List<InviteInquiryMineResponse> inquiryMyInviteCode(Member member);
InviteInquiryMineResponse inquiryMyInviteCode(Member member);
}
Original file line number Diff line number Diff line change
Expand Up @@ -62,13 +62,15 @@ public InviteAuthenticateResponse authenticateInviteCode(Member member, String i

// 나의 초대 코드 조회 함수
@Override
public List<InviteInquiryMineResponse> inquiryMyInviteCode(Member member) {
public InviteInquiryMineResponse inquiryMyInviteCode(Member member) {
// 본인이 생성한 초대 코드 조회
List<Invite> savedInvites = inviteRepository.findAllByMember(member);

return savedInvites.stream()
List<InviteInquiryMineResponse.InviteInfo> invites = savedInvites.stream()
.map(inviteMapper::toInquiryMineResponse)
.toList();

return new InviteInquiryMineResponse(invites);
}

// 본인의 역할 이상의 역할 부여를 확인하는 함수
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ public class AuthController {

@Operation(summary = "소셜 로그인", description = "네이버, 카카오, 구글, 애플 로그인")
@ApiResponses(value = {
@ApiResponse(responseCode = "200", description = "로그인 성공"),
@ApiResponse(responseCode = "COMMON200", description = "로그인 성공"),
@ApiResponse(responseCode = "AUTH007", description = "외부 소셜 서버와의 통신 에러" , content =
@Content(schema = @Schema(implementation = BaseResponse.class)))
})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import com.umc.networkingService.config.security.auth.CurrentMember;
import com.umc.networkingService.domain.member.dto.request.MemberUpdateProfileRequest;
import com.umc.networkingService.domain.member.dto.response.MemberIdResponse;
import com.umc.networkingService.domain.member.dto.response.MemberSearchInfoResponse;
import com.umc.networkingService.domain.member.dto.response.MemberSearchInfosResponse;
import com.umc.networkingService.domain.member.entity.Member;
import com.umc.networkingService.domain.member.service.MemberService;
import com.umc.networkingService.global.common.base.BaseResponse;
Expand All @@ -14,7 +14,6 @@
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.UUID;

@Tag(name = "운영진용 멤버 API", description = "운영진용 멤버 관련 API")
Expand Down Expand Up @@ -42,8 +41,8 @@ public BaseResponse<MemberIdResponse> updateProfile(@CurrentMember Member member
@ApiResponse(responseCode = "MEMBER006", description = "[닉네임/이름] 양식에 맞지 않을 경우 발생")
})
@GetMapping("/search")
public BaseResponse<List<MemberSearchInfoResponse>> searchMemberInfo(@CurrentMember Member member,
@RequestParam String keyword) {
public BaseResponse<MemberSearchInfosResponse> searchMemberInfo(@CurrentMember Member member,
@RequestParam String keyword) {
return BaseResponse.onSuccess(memberService.searchMemberInfo(member, keyword));
}

Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package com.umc.networkingService.domain.member.dto.response;

import com.umc.networkingService.domain.member.dto.SemesterPartInfo;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Getter;

import java.util.List;
import java.util.UUID;

@Getter
@AllArgsConstructor
public class MemberSearchInfosResponse {
private List<MemberInfo> members;

@Getter
@Builder
public static class MemberInfo {
private UUID memberId;
private String universityName;
private List<String> campusPositions;
private List<String> centerPositions;
private List<SemesterPartInfo> semesterParts;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
import org.hibernate.annotations.SQLRestriction;
import org.hibernate.annotations.UuidGenerator;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
Expand Down Expand Up @@ -72,39 +73,55 @@ public class Member extends BaseEntity {

private String gitNickname;

private String notionLink;
private String notionLink;

private LocalDateTime lastActiveTime;

// 기본 정보 설정 함수
public void setMemberInfo(String name, String nickname, University university, Branch branch) {
this.name = name;
this.nickname = nickname;
this.university = university;
this.branch = branch;
}

// 기본 정보 업데이트 함수
public void updateMemberInfo(MemberUpdateMyProfileRequest request, String profileImage) {
this.name = request.getName();
this.nickname = request.getNickname();
this.statusMessage = request.getStatusMessage();
this.profileImage = profileImage;
}

// 직책 업데이트 함수
public void updatePositions(List<MemberPosition> memberPositions) {
this.positions = memberPositions;
}

// 기수별 파트 업데이트 함수
public void updateSemesterParts(List<SemesterPart> semesterParts) {
this.semesterParts = semesterParts;
}

// 깃허브 닉네임 업데이트 함수
public void authenticateGithub(String gitNickname) {
this.gitNickname = gitNickname;
}

// 기여도 포인트 업데이트 함수
public void updateContributionPoint(Long usedPoint) {
if (this.contributionPoint == null) this.contributionPoint = usedPoint;
else this.contributionPoint += usedPoint;
}

// Role 업데이트 함수
public void updateRole(Role role) {
this.role = role;
}

// 최근 활동 시간 업데이트 함수
public void updateLastActiveTime(LocalDateTime lastActiveTime) {
this.lastActiveTime = lastActiveTime;
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package com.umc.networkingService.domain.member.interceptor;

import com.umc.networkingService.config.security.auth.PrincipalDetails;
import com.umc.networkingService.domain.member.entity.Member;
import com.umc.networkingService.domain.member.service.MemberService;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;

@Component
public class LastActiveInterceptor implements HandlerInterceptor {
@Autowired
private MemberService memberService;

@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
PrincipalDetails principalDetails = (PrincipalDetails) authentication.getPrincipal();
Member member = principalDetails.getMember();
memberService.updateMemberActiveTime(member.getId());

return true;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -84,9 +84,10 @@ public MemberInquiryPointsResponse toInquiryPointsResponse(Long point,
.build();
}

public MemberSearchInfoResponse toSearchMembersResponse(Member member, List<String> campusPositions, List<String> centerPositions) {
public MemberSearchInfosResponse.MemberInfo toSearchMembersResponse(
Member member, List<String> campusPositions, List<String> centerPositions) {

return MemberSearchInfoResponse.builder()
return MemberSearchInfosResponse.MemberInfo.builder()
.memberId(member.getId())
.universityName(member.getUniversity().getName())
.campusPositions(campusPositions)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,8 @@ private MemberLoginResponse loginByApple(final String accessToken){
return saveNewMember(clientId, SocialType.APPLE);
}
// 2. 있으면 : 새로운 토큰 반환
return getNewToken(getMember.get(), true);
boolean isServiceMember = getMember.get().getName() != null;
return getNewToken(getMember.get(), isServiceMember);
}

private MemberLoginResponse loginByKakao(final String accessToken){
Expand Down Expand Up @@ -173,7 +174,9 @@ private MemberLoginResponse loginByNaver(final String accessToken){
return saveNewMember(clientId,SocialType.NAVER);
}
// 2. 있으면 (이미 로그인 했던 적이 있는 경우)
return getNewToken(getMember.get(), true);
boolean isServiceMember = getMember.get().getName() != null;

return getNewToken(getMember.get(), isServiceMember);
}

private MemberLoginResponse loginByGoogle(final String accessToken){
Expand All @@ -187,7 +190,8 @@ private MemberLoginResponse loginByGoogle(final String accessToken){
return saveNewMember(clientId, SocialType.GOOGLE);
}
// 2. 있으면 : 새로운 토큰 반환
return getNewToken(getMember.get(), true);
boolean isServiceMember = getMember.get().getName() != null;
return getNewToken(getMember.get(), isServiceMember);
}

private MemberLoginResponse saveNewMember(String clientId, SocialType socialType) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
import com.umc.networkingService.global.common.base.EntityLoader;
import org.springframework.web.multipart.MultipartFile;

import java.util.List;
import java.util.UUID;

public interface MemberService extends EntityLoader<Member, UUID> {
Expand All @@ -18,6 +17,7 @@ public interface MemberService extends EntityLoader<Member, UUID> {
MemberInquiryInfoWithPointResponse inquiryInfoWithPoint(Member member);
MemberInquiryGithubResponse inquiryGithubImage(Member member);
MemberInquiryPointsResponse inquiryMemberPoints(Member member);
List<MemberSearchInfoResponse> searchMemberInfo(Member member, String keyword);
MemberSearchInfosResponse searchMemberInfo(Member member, String keyword);
void updateMemberActiveTime(UUID memberId);
Member saveEntity(Member member);
}
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import java.time.LocalDateTime;
import java.util.List;
import java.util.Optional;
import java.util.UUID;
Expand Down Expand Up @@ -175,7 +176,7 @@ public MemberInquiryPointsResponse inquiryMemberPoints(Member loginMember) {

// 멤버 검색 함수(운영진용)
@Override
public List<MemberSearchInfoResponse> searchMemberInfo(Member loginMember, String keyword) {
public MemberSearchInfosResponse searchMemberInfo(Member loginMember, String keyword) {
Member member = loadEntity(loginMember.getId());

// keyword 양식 검증
Expand All @@ -186,13 +187,22 @@ public List<MemberSearchInfoResponse> searchMemberInfo(Member loginMember, Strin
.filter(searchedMember -> searchedMember.getRole().getPriority() > member.getRole().getPriority())
.toList();


return searchedMembers.stream()
List<MemberSearchInfosResponse.MemberInfo> memberInfos = searchedMembers.stream()
.map(searchedMember -> memberMapper.toSearchMembersResponse(
searchedMember,
getPositionNamesByType(searchedMember, PositionType.CAMPUS),
getPositionNamesByType(searchedMember, PositionType.CENTER)
)).toList();

return new MemberSearchInfosResponse(memberInfos);
}

@Override
@Transactional
public void updateMemberActiveTime(UUID memberId) {
Member loginMember = loadEntity(memberId);

loginMember.updateLastActiveTime(LocalDateTime.now());
}

// 멤버의 새로운 Role 찾기 함수
Expand Down
Loading

0 comments on commit 7b59f15

Please sign in to comment.