From 618a4ddf5a11c494c5e8b61b2a2f316a2785c546 Mon Sep 17 00:00:00 2001 From: TheSaminator Date: Wed, 6 Jul 2022 13:04:05 -0400 Subject: [PATCH] Add validation to cluster generation testing --- .../starshipfights/campaign/cluster_params.kt | 4 +++ .../campaign/endpoints_campaign.kt | 31 +++++++++++++------ .../net/starshipfights/labs/endpoints_labs.kt | 10 +++--- 3 files changed, 32 insertions(+), 13 deletions(-) diff --git a/src/commonMain/kotlin/net/starshipfights/campaign/cluster_params.kt b/src/commonMain/kotlin/net/starshipfights/campaign/cluster_params.kt index 5c91d8f..3769fbf 100644 --- a/src/commonMain/kotlin/net/starshipfights/campaign/cluster_params.kt +++ b/src/commonMain/kotlin/net/starshipfights/campaign/cluster_params.kt @@ -59,6 +59,10 @@ enum class ClusterFactionMode { @JvmInline @Serializable value class ClusterFactions private constructor(private val factions: Map) { + init { + require(factions.values.any { it != ClusterFactionMode.EXCLUDE }) { "Excluding all factions is a bad idea!" } + } + operator fun get(factionFlavor: FactionFlavor) = factions[factionFlavor] ?: ClusterFactionMode.ALLOW operator fun plus(other: ClusterFactions) = ClusterFactions(factions + other.factions) diff --git a/src/jvmMain/kotlin/net/starshipfights/campaign/endpoints_campaign.kt b/src/jvmMain/kotlin/net/starshipfights/campaign/endpoints_campaign.kt index 86c9ba5..58f7a9a 100644 --- a/src/jvmMain/kotlin/net/starshipfights/campaign/endpoints_campaign.kt +++ b/src/jvmMain/kotlin/net/starshipfights/campaign/endpoints_campaign.kt @@ -7,10 +7,13 @@ import io.ktor.request.* import io.ktor.routing.* import io.ktor.util.* import kotlinx.html.* +import net.starshipfights.auth.withErrorMessage import net.starshipfights.data.Id import net.starshipfights.game.* import net.starshipfights.labs.lab import net.starshipfights.labs.labPost +import net.starshipfights.labs.labUrl +import net.starshipfights.redirect fun Routing.installCampaign() { lab("cluster", "Star Clusters") { @@ -187,15 +190,21 @@ fun Routing.installCampaign() { labPost("cluster") { val parameters = call.receiveParameters() - val color = StarClusterBackground.valueOf(parameters.getOrFail("color")) - val size = ClusterSize.valueOf(parameters.getOrFail("size")) - val density = ClusterLaneDensity.valueOf(parameters.getOrFail("density")) - val planets = ClusterPlanetDensity.valueOf(parameters.getOrFail("planets")) - val corruption = ClusterCorruption.valueOf(parameters.getOrFail("corruption")) - val contention = ClusterContention.valueOf(parameters.getOrFail("contention")) - val factions = ClusterFactions(FactionFlavor.values().mapNotNull { faction -> - parameters["factions[${faction.toUrlSlug()}]"]?.let { faction to ClusterFactionMode.valueOf(it) } - }.toMap()) + val color = StarClusterBackground.values().valueOfOrRedirect(parameters.getOrFail("color")) { "Invalid value chosen for background color" } + val size = ClusterSize.values().valueOfOrRedirect(parameters.getOrFail("size")) { "Invalid value chosen for cluster size" } + val density = ClusterLaneDensity.values().valueOfOrRedirect(parameters.getOrFail("density")) { "Invalid value chosen for warp lane density" } + val planets = ClusterPlanetDensity.values().valueOfOrRedirect(parameters.getOrFail("planets")) { "Invalid value chosen for planet density" } + val corruption = ClusterCorruption.values().valueOfOrRedirect(parameters.getOrFail("corruption")) { "Invalid value chosen for eldritch corruption" } + val contention = ClusterContention.values().valueOfOrRedirect(parameters.getOrFail("contention")) { "Invalid value chosen for factional contention" } + val factions = try { + ClusterFactions(FactionFlavor.values().mapNotNull { faction -> + parameters["factions[${faction.toUrlSlug()}]"] + ?.let { ClusterFactionMode.values().valueOfOrNull(it) } + ?.let { faction to it } + }.toMap()) + } catch (ex: IllegalArgumentException) { + redirect(labUrl("cluster") + withErrorMessage("Invalid values chosen for faction modes")) + } val cluster = ClusterGenerator( ClusterGenerationSettings(color, size, density, planets, corruption, factions, contention) @@ -211,3 +220,7 @@ fun Routing.installCampaign() { call.respondHtml(HttpStatusCode.OK, clientMode.view()) } } + +private fun > Array.valueOfOrNull(param: String?) = singleOrNull { it.name == param } + +private fun > Array.valueOfOrRedirect(param: String?, message: () -> String) = valueOfOrNull(param) ?: redirect(labUrl("cluster") + withErrorMessage(message())) diff --git a/src/jvmMain/kotlin/net/starshipfights/labs/endpoints_labs.kt b/src/jvmMain/kotlin/net/starshipfights/labs/endpoints_labs.kt index 13af78e..c19cf2c 100644 --- a/src/jvmMain/kotlin/net/starshipfights/labs/endpoints_labs.kt +++ b/src/jvmMain/kotlin/net/starshipfights/labs/endpoints_labs.kt @@ -12,14 +12,16 @@ private val labs = mutableMapOf() private val labsSidebar: Sidebar get() = PageNavSidebar( listOf(NavHead("Other Labs")) + labs.map { (slug, title) -> - NavLink("/labs/$slug", title) + NavLink(labUrl(slug), title) } ) +fun labUrl(slug: String) = "/labs/$slug" + fun Routing.lab(slug: String, title: String, pageBody: SECTIONS.() -> Unit) { labs[slug] = title - get("/labs/$slug") { + get(labUrl(slug)) { call.respondHtml( block = call.page( title, @@ -32,7 +34,7 @@ fun Routing.lab(slug: String, title: String, pageBody: SECTIONS.() -> Unit) { } fun Routing.labPost(slug: String, action: PipelineInterceptor) { - post("/labs/$slug", action) + post(labUrl(slug), action) } fun Routing.installLabs() { @@ -52,7 +54,7 @@ fun Routing.installLabs() { ul { for ((slug, title) in labs) { li { - a(href = "/labs/$slug") { +title } + a(href = labUrl(slug)) { +title } } } } -- 2.25.1