feat(online-nennung): integrate online nomination workflow via REST and mail service

- Enabled web-to-backend nominations with `MailController` and REST endpoint (`/api/mail/nennung`).
- Added `NennungRemoteRepository` for frontend API integration using Ktor.
- Linked `WebMainScreen` to backend API for nomination handling and confirmation display.
- Implemented automated confirmation emails for received nominations.
- Updated `MASTER_ROADMAP` to reflect progress on Phase 13 milestones.
- Improved Nennung UI, backend persistence, and QA tracking for Neumarkt tournament.
This commit is contained in:
2026-04-15 10:37:07 +02:00
parent b4c400efea
commit c542094196
8 changed files with 193 additions and 4 deletions
@@ -0,0 +1,89 @@
package at.mocode.mail.service.api
import at.mocode.mail.service.persistence.NennungEntity
import at.mocode.mail.service.persistence.NennungRepository
import org.slf4j.LoggerFactory
import org.springframework.mail.SimpleMailMessage
import org.springframework.mail.javamail.JavaMailSender
import org.springframework.web.bind.annotation.*
import kotlin.uuid.ExperimentalUuidApi
import kotlin.uuid.Uuid
@OptIn(ExperimentalUuidApi::class)
data class NennungRequest(
val turnierNr: String,
val vorname: String,
val nachname: String,
val lizenz: String,
val pferdName: String,
val pferdAlter: String,
val email: String,
val telefon: String?,
val bewerbe: String,
val bemerkungen: String?
)
@OptIn(ExperimentalUuidApi::class)
@RestController
@RequestMapping("/api/mail")
@CrossOrigin(origins = ["*"]) // Für Wasm-Web-App (Compose HTML/Wasm)
class MailController(
private val nennungRepository: NennungRepository,
private val mailSender: JavaMailSender
) {
private val logger = LoggerFactory.getLogger(MailController::class.java)
@PostMapping("/nennung")
fun receiveNennung(@RequestBody request: NennungRequest) {
logger.info("Nennung via API erhalten: ${request.vorname} ${request.nachname} für Turnier ${request.turnierNr}")
val entity = NennungEntity(
id = Uuid.random(),
turnierNr = request.turnierNr,
status = "API_EMPFANGEN",
vorname = request.vorname,
nachname = request.nachname,
lizenz = request.lizenz,
pferdName = request.pferdName,
pferdAlter = request.pferdAlter,
email = request.email,
telefon = request.telefon,
bewerbe = request.bewerbe,
bemerkungen = request.bemerkungen
)
nennungRepository.save(entity)
logger.info("Nennung ${entity.id} in Datenbank persistiert.")
// Bestätigung an Reiter senden
try {
val message = SimpleMailMessage()
message.from = "online-nennen@mo-code.at"
message.setTo(request.email)
message.subject = "Bestätigung: Ihre Online-Nennung für Turnier ${request.turnierNr}"
message.text = """
Sehr geehrte(r) ${request.vorname} ${request.nachname},
vielen Dank für Ihre Online-Nennung für das Turnier ${request.turnierNr}.
Ihre Daten:
- Pferd: ${request.pferdName}
- Bewerbe: ${request.bewerbe}
Ihre Nennung ist erfolgreich bei uns eingegangen und wird nun verarbeitet.
Mit freundlichen Grüßen,
Ihre Meldestelle
""".trimIndent()
mailSender.send(message)
logger.info("Bestätigungs-Mail an ${request.email} gesendet.")
} catch (e: Exception) {
logger.error("Fehler beim Senden der Bestätigungs-Mail: ${e.message}")
}
}
@GetMapping("/nennungen")
fun getAllNennungen(): List<NennungEntity> {
return nennungRepository.findAll()
}
}