Skip to content
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
2 changes: 1 addition & 1 deletion src/main/java/codesquad/ImsApplication.java
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ public static void main(String[] args) {


/**
* Todo
* Todo : Step4 ~ing
* 1. html 자원들 중복 제거하면서 스타일이 제대로 안나오는 부분이 있다, 추후 중복 제거 다시해서 레이아웃이 제대로 나오도록
* 2. 회원가입/가입정보수정 시 유효하지 않은 값 입력하고 submit 시 어떤 경우에 alert, 어떤 경우에 오류페이지 나오는지 확인 후 개선
*/
2 changes: 1 addition & 1 deletion src/main/java/codesquad/WebMvcConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ public class WebMvcConfig implements WebMvcConfigurer {
@Override
public void addFormatters(FormatterRegistry registry) {
registry.addConverter(new LocalDateConverter("yyyy-MM-dd"));
registry.addConverter(new LocalDateTimeConverter("yyyy-MM-dd HH:mm:ss.SSS"));
registry.addConverter(new LocalDateTimeConverter("yyyy-MM-dd'T'HH:mm"));
}

@Bean
Expand Down
24 changes: 24 additions & 0 deletions src/main/java/codesquad/converter/LocalDateTimeConverter.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package codesquad.converter;

import org.springframework.core.convert.converter.Converter;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Locale;

public final class LocalDateTimeConverter implements Converter<String, LocalDateTime> {

private final DateTimeFormatter formatter;

public LocalDateTimeConverter(String dateFormat) {
this.formatter = DateTimeFormatter.ofPattern(dateFormat, Locale.ENGLISH);
}

@Override
public LocalDateTime convert(String source) {
if (source == null || source.isEmpty()) {
return null;
}
return LocalDateTime.parse(source, formatter);
}
}
50 changes: 47 additions & 3 deletions src/main/java/codesquad/domain/Issue.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@

import codesquad.CannotDeleteException;
import codesquad.UnAuthorizedException;
import codesquad.dto.IssueDto;
import support.domain.AbstractEntity;

import javax.persistence.*;
Expand All @@ -25,8 +24,21 @@ public class Issue extends AbstractEntity {
@JoinColumn(foreignKey = @ForeignKey(name = "fk_issue_writer"))
private User writer;

@ManyToOne
@JoinColumn(foreignKey = @ForeignKey(name = "fk_issue_assignee"))
private User assignee;

@ManyToOne
@JoinColumn(foreignKey = @ForeignKey(name = "fk_issue_to_milestone"))
private Milestone milestone;

@ManyToMany
private List<Label> labels = new ArrayList<>();

private boolean deleted = false;

private boolean closed = false;

public Issue() {

}
Expand All @@ -41,6 +53,10 @@ public boolean isMatchWriter(User loginUser) {
return this.writer.equals(loginUser);
}

public boolean isClosed() {
return this.closed;
}

public void update(User loginUser, Issue target) {
if (!isMatchWriter(loginUser)) {
throw new UnAuthorizedException();
Expand All @@ -61,6 +77,30 @@ public List<DeleteHistory> delete(User loginUser) {
return temp;
}

public void toMilestone(User loginUser, Milestone milestone) {
if(!isMatchWriter(loginUser)) {
throw new UnAuthorizedException();
}

this.milestone = milestone;
}

public void assignedBy(User loginUser, User assignee) {
if (!isMatchWriter(loginUser)) {
throw new UnAuthorizedException();
}

this.assignee = assignee;
}

public void addLabel(User loginUser, Label label) {
if(!isMatchWriter(loginUser)) {
throw new UnAuthorizedException();
}

this.labels.add(label);
}

public String getSubject() {
return subject;
}
Expand All @@ -85,8 +125,12 @@ public void writeBy(User loginUser) {
this.writer = loginUser;
}

public IssueDto _toIssueDto() {
return new IssueDto(this.subject, this.comment, this.writer);
public Milestone getMilestone() {
return milestone;
}

public void setMilestone(Milestone milestone) {
this.milestone = milestone;
}

@Override
Expand Down
21 changes: 21 additions & 0 deletions src/main/java/codesquad/domain/Label.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package codesquad.domain;

import support.domain.AbstractEntity;
import javax.persistence.Entity;

@Entity
public class Label extends AbstractEntity {
private String name;

public Label() {

}

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}
}
6 changes: 6 additions & 0 deletions src/main/java/codesquad/domain/LabelRepository.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package codesquad.domain;

import org.springframework.data.jpa.repository.JpaRepository;

public interface LabelRepository extends JpaRepository<Label, Long> {
}
90 changes: 90 additions & 0 deletions src/main/java/codesquad/domain/Milestone.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package codesquad.domain;

import org.hibernate.annotations.Where;
import support.domain.AbstractEntity;

import javax.persistence.*;
import javax.validation.constraints.Size;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;

@Entity
public class Milestone extends AbstractEntity {
@Size(min = 1, max = 20)
@Column(nullable = false, length = 20)
private String subject;

@Column(nullable = false)
private LocalDateTime startDate;

@Column(nullable = false)
private LocalDateTime endDate;

@OneToMany(mappedBy = "milestone", cascade = CascadeType.ALL)
@Where(clause = "deleted = false")
@OrderBy("id ASC")
private List<Issue> issues = new ArrayList<>();

public Milestone() {

}

public Milestone(String subject, LocalDateTime startDate, LocalDateTime endDate) {
this.subject = subject;
this.startDate = startDate;
this.endDate = endDate;
}

public void addIssue(User loginUser, Issue issue) {
issue.toMilestone(loginUser, this);
issues.add(issue);
}

public int getCountOfClosedIssue() {
int count = 0;
for (Issue issue : issues) {
if(issue.isClosed()) {
count ++;
}
}
return count;
}

public int getCountOfOpenedIssue() {
return issues.size() - getCountOfClosedIssue();
}

public String getSubject() {
return subject;
}

public void setSubject(String subject) {
this.subject = subject;
}

public LocalDateTime getStartDate() {
return startDate;
}

public void setStartDate(LocalDateTime startDate) {
this.startDate = startDate;
}

public LocalDateTime getEndDate() {
return endDate;
}

public void setEndDate(LocalDateTime endDate) {
this.endDate = endDate;
}

public String getFormattedDueDate() {
if (endDate == null) {
return "";
}
return endDate.format(DateTimeFormatter.ofPattern("MMMM dd, yyyy", Locale.US));
}
}
6 changes: 6 additions & 0 deletions src/main/java/codesquad/domain/MilestoneRepository.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package codesquad.domain;

import org.springframework.data.jpa.repository.JpaRepository;

public interface MilestoneRepository extends JpaRepository<Milestone, Long> {
}
64 changes: 0 additions & 64 deletions src/main/java/codesquad/dto/IssueDto.java

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package codesquad.security;

import codesquad.UnAuthenticationException;
import codesquad.UnAuthorizedException;
import codesquad.domain.User;
import org.springframework.core.MethodParameter;
Expand All @@ -24,7 +25,7 @@ public Object resolveArgument(MethodParameter parameter, ModelAndViewContainer m

LoginUser loginUser = parameter.getParameterAnnotation(LoginUser.class);
if (loginUser.required()) {
throw new UnAuthorizedException("You're required Login!");
throw new UnAuthenticationException("You're required Login!");
}
return user;
}
Expand Down
18 changes: 14 additions & 4 deletions src/main/java/codesquad/security/SecurityControllerAdvice.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package codesquad.security;

import codesquad.CannotDeleteException;
import codesquad.UnAuthenticationException;
import codesquad.UnAuthorizedException;
import org.slf4j.Logger;
Expand All @@ -8,6 +9,7 @@
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import javax.persistence.EntityNotFoundException;

Expand All @@ -21,15 +23,23 @@ public void emptyResultData() {
log.debug("EntityNotFoundException is happened!");
}

@ExceptionHandler(UnAuthenticationException.class)
@ResponseStatus(value = HttpStatus.FOUND)
public String unAuthentication(UnAuthenticationException e, RedirectAttributes redirectAttributes) {
log.debug("UnAuthenticationException is happened! And redirect to /users/login");
redirectAttributes.addFlashAttribute("error", e.getMessage());
return "redirect:/users/login";
}

@ExceptionHandler(UnAuthorizedException.class)
@ResponseStatus(value = HttpStatus.FORBIDDEN)
public void unAuthorized() {
log.debug("UnAuthorizedException is happened!");
}

@ExceptionHandler(UnAuthenticationException.class)
@ResponseStatus(value = HttpStatus.UNAUTHORIZED)
public void unAuthentication() {
log.debug("UnAuthenticationException is happened!");
@ExceptionHandler(CannotDeleteException.class)
@ResponseStatus(value = HttpStatus.FORBIDDEN)
public void canNotDelete() {
log.debug("CannotDeleteException is happened!");
}
}
Loading