diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/MainApplication.kt b/module-server/src/main/kotlin/de/twomartens/timetable/MainApplication.kt index dc3af78..e1dcd0a 100644 --- a/module-server/src/main/kotlin/de/twomartens/timetable/MainApplication.kt +++ b/module-server/src/main/kotlin/de/twomartens/timetable/MainApplication.kt @@ -1,6 +1,7 @@ package de.twomartens.timetable import de.twomartens.timetable.bahnApi.service.BahnApiService +import de.twomartens.timetable.bahnApi.service.BahnDatabaseService import mu.KotlinLogging import org.springframework.boot.autoconfigure.SpringBootApplication import org.springframework.boot.context.event.ApplicationReadyEvent @@ -16,16 +17,15 @@ import java.time.Month @EnableScheduling @SpringBootApplication open class MainApplication( - private val bahnApiService: BahnApiService + private val bahnApiService: BahnApiService, + private val bahnDatabaseService: BahnDatabaseService ) { @EventListener(ApplicationReadyEvent::class) fun ready() { - val result = bahnApiService.fetchStations("Köln Hbf") - val koeln = result[0] - val timetable = bahnApiService.fetchTimetable(koeln.eva, - LocalDate.of(2023, Month.SEPTEMBER, 23), - LocalTime.of(17, 0)) - log.info("stations: $result") + val timetable = bahnApiService.fetchTimetable(8000207, + LocalDate.of(2023, Month.OCTOBER, 1), + LocalTime.of(3, 0)) + log.info { "bs" } } companion object { diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/mapper/BahnTimetableMapper.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/mapper/BahnTimetableMapper.kt new file mode 100644 index 0000000..e2ceb51 --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/mapper/BahnTimetableMapper.kt @@ -0,0 +1,25 @@ +package de.twomartens.timetable.bahnApi.mapper + +import de.twomartens.timetable.bahnApi.model.db.BahnTimetable +import org.mapstruct.* +import java.time.LocalDateTime + +@Mapper( + collectionMappingStrategy = CollectionMappingStrategy.ADDER_PREFERRED, + nullValueCheckStrategy = NullValueCheckStrategy.ALWAYS, + unmappedTargetPolicy = ReportingPolicy.IGNORE +) +interface BahnTimetableMapper { + @Mapping(target = "id", ignore = true) + @Mapping(target = "created", ignore = true) + @Mapping(target = "lastModified", ignore = true) + fun mapToDB(dto: de.twomartens.timetable.bahnApi.model.dto.BahnTimetable, + dateTime: LocalDateTime): BahnTimetable { + return BahnTimetable( + dto.eva!!, + dateTime, + dto.station, + dto.stops + ) + } +} \ No newline at end of file diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/model/db/BahnTimetable.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/model/db/BahnTimetable.kt new file mode 100644 index 0000000..b8ff49d --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/model/db/BahnTimetable.kt @@ -0,0 +1,30 @@ +package de.twomartens.timetable.bahnApi.model.db + +import de.twomartens.timetable.bahnApi.model.dto.BahnStationStop +import org.bson.types.ObjectId +import org.springframework.data.annotation.CreatedDate +import org.springframework.data.annotation.Id +import org.springframework.data.annotation.LastModifiedDate +import org.springframework.data.mongodb.core.index.CompoundIndex +import org.springframework.data.mongodb.core.index.TextIndexed +import org.springframework.data.mongodb.core.mapping.Document +import java.time.Instant +import java.time.LocalDateTime + +@Document +@CompoundIndex(def = "{'eva': 1, 'dateTime': 1}") +data class BahnTimetable( + var eva: Int, + var dateTime: LocalDateTime, + @TextIndexed var station: String, + var stops: List +) { + @Id + var id: ObjectId = ObjectId() + + @CreatedDate + lateinit var created: Instant + + @LastModifiedDate + lateinit var lastModified: Instant +} \ No newline at end of file diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/repository/BahnTimetableRepository.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/repository/BahnTimetableRepository.kt new file mode 100644 index 0000000..3bbb55c --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/repository/BahnTimetableRepository.kt @@ -0,0 +1,7 @@ +package de.twomartens.timetable.bahnApi.repository + +import de.twomartens.timetable.bahnApi.model.db.BahnStation +import de.twomartens.timetable.bahnApi.model.db.BahnTimetable +import org.springframework.data.mongodb.repository.MongoRepository + +interface BahnTimetableRepository : MongoRepository diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnApiService.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnApiService.kt index 6c057a0..0ec7e18 100644 --- a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnApiService.kt +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnApiService.kt @@ -31,7 +31,7 @@ class BahnApiService( return body?.stations ?: listOf() } - fun fetchTimetable(eva: String, date: LocalDate, hour: LocalTime): BahnTimetable { + fun fetchTimetable(eva: Int, date: LocalDate, hour: LocalTime): BahnTimetable { val requestEntity = buildRequestEntity() val dateFormatter = DateTimeFormatter.ofPattern("yyMMdd") val timeFormatter = DateTimeFormatter.ofPattern("HH") diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnDatabaseService.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnDatabaseService.kt index 7d033b0..a61a96f 100644 --- a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnDatabaseService.kt +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/service/BahnDatabaseService.kt @@ -1,19 +1,29 @@ package de.twomartens.timetable.bahnApi.service import de.twomartens.timetable.bahnApi.mapper.BahnStationMapper +import de.twomartens.timetable.bahnApi.mapper.BahnTimetableMapper import de.twomartens.timetable.bahnApi.model.dto.BahnStation +import de.twomartens.timetable.bahnApi.model.dto.BahnTimetable import de.twomartens.timetable.bahnApi.repository.BahnStationRepository +import de.twomartens.timetable.bahnApi.repository.BahnTimetableRepository import org.mapstruct.factory.Mappers import org.springframework.stereotype.Service +import java.time.LocalDateTime @Service class BahnDatabaseService( - private val bahnStationRepository: BahnStationRepository + private val bahnStationRepository: BahnStationRepository, + private val bahnTimetableRepository: BahnTimetableRepository ) { private val bahnStationMapper = Mappers.getMapper(BahnStationMapper::class.java) + private val bahnTimetableMapper = Mappers.getMapper(BahnTimetableMapper::class.java) fun storeStations(stations: List) { bahnStationRepository.saveAll(stations .map { bahnStationMapper.mapToDB(it) }) } + + fun storeTimetable(timetable: BahnTimetable, dateTime: LocalDateTime) { + bahnTimetableRepository.save(bahnTimetableMapper.mapToDB(timetable, dateTime)) + } } \ No newline at end of file diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/tasks/FetchTimetableTask.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/tasks/FetchTimetableTask.kt new file mode 100644 index 0000000..2dd63cb --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/tasks/FetchTimetableTask.kt @@ -0,0 +1,23 @@ +package de.twomartens.timetable.bahnApi.tasks + +import de.twomartens.timetable.bahnApi.service.BahnApiService +import de.twomartens.timetable.bahnApi.service.BahnDatabaseService +import org.springframework.scheduling.annotation.Async +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor +import java.time.LocalDate +import java.time.LocalTime + +@Async +open class FetchTimetableTask( + private val eva: Int, + private val date: LocalDate, + private val hour: LocalTime, + private val bahnApiService: BahnApiService, + private val bahnDatabaseService: BahnDatabaseService, + private val executor: ThreadPoolTaskExecutor) : Runnable { + override fun run() { + val timetable = bahnApiService.fetchTimetable(eva, date, hour) + val storeTask = StoreTimetableTask(timetable, date.atTime(hour), bahnDatabaseService) + executor.execute(storeTask) + } +} \ No newline at end of file diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/tasks/StoreTimetableTask.kt b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/tasks/StoreTimetableTask.kt new file mode 100644 index 0000000..e3074d5 --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/bahnApi/tasks/StoreTimetableTask.kt @@ -0,0 +1,17 @@ +package de.twomartens.timetable.bahnApi.tasks + +import de.twomartens.timetable.bahnApi.model.dto.BahnTimetable +import de.twomartens.timetable.bahnApi.service.BahnDatabaseService +import org.springframework.scheduling.annotation.Async +import java.time.LocalDateTime + +@Async +open class StoreTimetableTask( + private val timetable: BahnTimetable, + private val dateTime: LocalDateTime, + private val bahnDatabaseService: BahnDatabaseService +) : Runnable { + override fun run() { + bahnDatabaseService.storeTimetable(timetable, dateTime) + } +} \ No newline at end of file diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/configuration/ThreadPoolTaskExecutorConfig.kt b/module-server/src/main/kotlin/de/twomartens/timetable/configuration/ThreadPoolTaskExecutorConfig.kt new file mode 100644 index 0000000..667ce73 --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/configuration/ThreadPoolTaskExecutorConfig.kt @@ -0,0 +1,17 @@ +package de.twomartens.timetable.configuration + +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.Configuration +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor + +private const val CORE_POOL_SIZE = 1 + +@Configuration +open class ThreadPoolTaskExecutorConfig { + @Bean + open fun threadPoolTaskExecutor(): ThreadPoolTaskExecutor { + val executor = ThreadPoolTaskExecutor() + executor.corePoolSize = CORE_POOL_SIZE + return executor + } +} \ No newline at end of file diff --git a/module-server/src/main/kotlin/de/twomartens/timetable/configuration/ThreadPoolTaskSchedulerConfig.kt b/module-server/src/main/kotlin/de/twomartens/timetable/configuration/ThreadPoolTaskSchedulerConfig.kt new file mode 100644 index 0000000..555ebfa --- /dev/null +++ b/module-server/src/main/kotlin/de/twomartens/timetable/configuration/ThreadPoolTaskSchedulerConfig.kt @@ -0,0 +1,20 @@ +package de.twomartens.timetable.configuration + +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.Configuration +import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler + +private const val POOL_SIZE = 5 + +private const val THREAD_NAME_PREFIX = "ThreadPoolTaskScheduler" + +@Configuration +open class ThreadPoolTaskSchedulerConfig { + @Bean + open fun threadPoolTaskScheduler(): ThreadPoolTaskScheduler { + val scheduler = ThreadPoolTaskScheduler() + scheduler.poolSize = POOL_SIZE + scheduler.threadNamePrefix = THREAD_NAME_PREFIX + return scheduler + } +} \ No newline at end of file