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: #37 학기 도메인 필드 타입 변경 및 학기 추가, 삭제 api 추가 #38

Merged
merged 6 commits into from
Jan 30, 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
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package com.yourssu.scouter.common.application.domain.semester

import jakarta.validation.constraints.NotNull
import jakarta.validation.constraints.Positive

data class CreateSemesterRequest(

@NotNull(message = "연도를 입력하지 않았습니다.")
@Positive(message = "연도는 양수여야 합니다.")
val year: Int,

@NotNull(message = "학기를 입력하지 않았습니다.")
@Positive(message = "학기는 양수여야 합니다.")
val term: Int,
)
Original file line number Diff line number Diff line change
Expand Up @@ -2,20 +2,44 @@ package com.yourssu.scouter.common.application.domain.semester

import com.yourssu.scouter.common.business.domain.semester.SemesterDto
import com.yourssu.scouter.common.business.domain.semester.SemesterService
import jakarta.validation.Valid
import java.net.URI
import org.springframework.http.ResponseEntity
import org.springframework.web.bind.annotation.DeleteMapping
import org.springframework.web.bind.annotation.GetMapping
import org.springframework.web.bind.annotation.PathVariable
import org.springframework.web.bind.annotation.PostMapping
import org.springframework.web.bind.annotation.RequestBody
import org.springframework.web.bind.annotation.RestController

@RestController
class SemesterController(
private val semesterService: SemesterService,
) {

@PostMapping("/semesters")
fun create(
@RequestBody @Valid request: CreateSemesterRequest,
): ResponseEntity<Unit> {
val semesterId: Long = semesterService.create(request.year, request.term)

return ResponseEntity.created(URI.create("/semesters/$semesterId")).build()
}

@GetMapping("/semesters")
fun readAll(): ResponseEntity<List<ReadSemesterResponse>> {
val semesterDtos: List<SemesterDto> = semesterService.readAll()
val response: List<ReadSemesterResponse> = semesterDtos.map { ReadSemesterResponse.from(it) }

return ResponseEntity.ok(response)
}

@DeleteMapping("/semesters/{semesterId}")
fun deleteById(
@PathVariable semesterId: Long,
): ResponseEntity<Unit> {
semesterService.deleteById(semesterId)

return ResponseEntity.noContent().build()
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@ package com.yourssu.scouter.common.business.domain.semester
object SemesterConverter {

fun convertToString(semester: SemesterDto): String {
return "${semester.year}-${semester.semester}학기"
val year: Int = semester.year.value % 100
val term: Int = semester.term.intValue

return "${year}-${term}학기"
}
}
Original file line number Diff line number Diff line change
@@ -1,24 +1,26 @@
package com.yourssu.scouter.common.business.domain.semester

import com.yourssu.scouter.common.implement.domain.semester.Semester
import com.yourssu.scouter.common.implement.domain.semester.Term
import java.time.Year

data class SemesterDto(
val id: Long,
val year: Int,
val semester: Int,
val year: Year,
val term: Term,
) {

companion object {
fun from(semester: Semester): SemesterDto = SemesterDto(
id = semester.id!!,
year = semester.year,
semester = semester.semester,
term = semester.term,
)
}

fun toDomain(): Semester = Semester(
id = id,
year = year,
semester = semester,
term = term,
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,31 @@ package com.yourssu.scouter.common.business.domain.semester

import com.yourssu.scouter.common.implement.domain.semester.Semester
import com.yourssu.scouter.common.implement.domain.semester.SemesterReader
import com.yourssu.scouter.common.implement.domain.semester.SemesterWriter
import org.springframework.stereotype.Service

@Service
class SemesterService(
private val semesterWriter: SemesterWriter,
private val semesterReader: SemesterReader,
) {

fun create(year: Int, term: Int): Long {
val toWriteSemester = Semester(year, term)
val writtenSemester: Semester = semesterWriter.write(toWriteSemester)

return writtenSemester.id!!
}

fun readAll(): List<SemesterDto> {
val semesters: List<Semester> = semesterReader.readAll()

return semesters.map { SemesterDto.from(it) }
}

fun deleteById(semesterId: Long) {
val target: Semester = semesterReader.readById(semesterId)

semesterWriter.delete(target)
}
}
Original file line number Diff line number Diff line change
@@ -1,10 +1,21 @@
package com.yourssu.scouter.common.implement.domain.semester

import java.time.LocalDate
import java.time.Year

class Semester(
val id: Long? = null,
val year: Int,
val semester: Int,
val year: Year,
val term: Term,
) {
constructor(year: Int, term: Int) : this(null, Year.of(year), Term.from(term))

companion object {
fun of(date: LocalDate): Semester = Semester(
year = Year.of(date.year),
term = Term.of(date)
)
}

override fun equals(other: Any?): Boolean {
if (this === other) return true
Expand All @@ -20,6 +31,6 @@ class Semester(
}

override fun toString(): String {
return "Semester(id=$id, year=$year, semester=$semester)"
return "Semester(id=$id, year=$year, semester=$term)"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ package com.yourssu.scouter.common.implement.domain.semester

interface SemesterRepository {

fun save(semester: Semester): Semester
fun findById(semesterId: Long): Semester?
fun findAll(): List<Semester>
fun deleteById(semesterId: Long)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package com.yourssu.scouter.common.implement.domain.semester

import org.springframework.stereotype.Component
import org.springframework.transaction.annotation.Transactional

@Component
@Transactional
class SemesterWriter(
private val semesterRepository: SemesterRepository,
) {

fun write(semester: Semester): Semester {
return semesterRepository.save(semester)
}

fun delete(semester: Semester) {
semesterRepository.deleteById(semester.id!!)
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package com.yourssu.scouter.common.implement.domain.semester

import java.time.LocalDate

enum class Term(val intValue: Int, val targetMonthRange: IntRange) {
SPRING(1, 1..6),
FALL(2, 7..12),
;

companion object {
fun of(date: LocalDate): Term {
return entries.first {date.monthValue in it.targetMonthRange }
}

fun from(term: Int): Term {
return entries.first { it.intValue == term }
}
}
}
Original file line number Diff line number Diff line change
@@ -1,12 +1,16 @@
package com.yourssu.scouter.common.storage.domain.semester

import com.yourssu.scouter.common.implement.domain.semester.Semester
import com.yourssu.scouter.common.implement.domain.semester.Term
import jakarta.persistence.Column
import jakarta.persistence.Entity
import jakarta.persistence.EnumType
import jakarta.persistence.Enumerated
import jakarta.persistence.GeneratedValue
import jakarta.persistence.GenerationType
import jakarta.persistence.Id
import jakarta.persistence.Table
import java.time.Year

@Entity
@Table(name = "semester")
Expand All @@ -17,23 +21,24 @@ class SemesterEntity(
val id: Long? = null,

@Column(name = "academic_year", nullable = false)
val year: Int,
val year: Year,

@Column(nullable = false)
val semester: Int,
@Enumerated(EnumType.STRING)
val term: Term,
) {

companion object {
fun from(semester: Semester): SemesterEntity = SemesterEntity(
id = semester.id,
year = semester.year,
semester = semester.semester
term = semester.term
)
}

fun toDomain(): Semester = Semester(
id = id,
year = year,
semester = semester
term = term
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,19 @@ class SemesterRepositoryImpl(
private val jpaSemesterRepository: JpaSemesterRepository,
) : SemesterRepository {

override fun save(semester: Semester): Semester {
return jpaSemesterRepository.save(SemesterEntity.from(semester)).toDomain()
}

override fun findById(semesterId: Long): Semester? {
return jpaSemesterRepository.findByIdOrNull(semesterId)?.toDomain()
}

override fun findAll(): List<Semester> {
return jpaSemesterRepository.findAll().map { it.toDomain() }
}

override fun deleteById(semesterId: Long) {
jpaSemesterRepository.deleteById(semesterId)
}
}