Add comprehensive tests for ServerCollectionOps (#696)
* Test ServerCollectionOps data manipulation utilities Added comprehensive unit tests for `ServerCollectionOps.kt` to cover all scenarios for `addOrUpdate`, `selfHealed`, and resolution properties (`resolvedBaseUrl`, `resolvedHost`, `resolvedPort`). Also updated the function name `addOrReplaceServer` to `addOrUpdate` to match the intended signature in the issue description, and updated affected call sites. * Fix ktlint formatting issues and ensure build succeeds Fixed ktlint errors in `ServerCollectionOpsTest.kt` by correctly formatting arguments and expressions to comply with project style guidelines. Ran `assembleDebug` and tests locally to verify build health.
This commit is contained in:
3 files changed
+181
-4
No files matched your search
@@ -3,7 +3,7 @@ package com.m57.hermescontrol.data.config
|
|||||||
import com.m57.hermescontrol.data.remote.CleartextPolicy
|
import com.m57.hermescontrol.data.remote.CleartextPolicy
|
||||||
import com.m57.hermescontrol.data.remote.ServerEndpoint
|
import com.m57.hermescontrol.data.remote.ServerEndpoint
|
||||||
|
|
||||||
fun ServerStoreState.addOrReplaceServer(profile: ConnectionProfile): ServerStoreState {
|
fun ServerStoreState.addOrUpdate(profile: ConnectionProfile): ServerStoreState {
|
||||||
val updated = connectionProfiles.filter { it.id != profile.id } + profile
|
val updated = connectionProfiles.filter { it.id != profile.id } + profile
|
||||||
return copy(connectionProfiles = updated)
|
return copy(connectionProfiles = updated)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,177 @@
|
|||||||
|
package com.m57.hermescontrol.data.config
|
||||||
|
|
||||||
|
import org.junit.Assert.assertEquals
|
||||||
|
import org.junit.Assert.assertNull
|
||||||
|
import org.junit.Test
|
||||||
|
|
||||||
|
class ServerCollectionOpsTest {
|
||||||
|
@Test
|
||||||
|
fun addOrUpdate_addsNewProfile() {
|
||||||
|
val initialState =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "http://192.168.1.1:9119"),
|
||||||
|
),
|
||||||
|
)
|
||||||
|
val newProfile = ConnectionProfile(id = "2", name = "Profile 2", baseUrl = "http://192.168.1.2:9119")
|
||||||
|
|
||||||
|
val result = initialState.addOrUpdate(newProfile)
|
||||||
|
|
||||||
|
assertEquals(2, result.connectionProfiles.size)
|
||||||
|
assertEquals(newProfile, result.connectionProfiles[1])
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun addOrUpdate_replacesExistingProfile() {
|
||||||
|
val initialState =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "http://192.168.1.1:9119"),
|
||||||
|
ConnectionProfile(id = "2", name = "Profile 2", baseUrl = "http://192.168.1.2:9119"),
|
||||||
|
),
|
||||||
|
)
|
||||||
|
val updatedProfile =
|
||||||
|
ConnectionProfile(id = "1", name = "Updated Profile 1", baseUrl = "http://192.168.1.100:9119")
|
||||||
|
|
||||||
|
val result = initialState.addOrUpdate(updatedProfile)
|
||||||
|
|
||||||
|
assertEquals(2, result.connectionProfiles.size)
|
||||||
|
// Should retain the order implicitly, or just check it exists
|
||||||
|
val replaced = result.connectionProfiles.find { it.id == "1" }
|
||||||
|
assertEquals("Updated Profile 1", replaced?.name)
|
||||||
|
assertEquals("http://192.168.1.100:9119", replaced?.baseUrl)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun selfHealed_keepsActiveProfile() {
|
||||||
|
val initialState =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "http://192.168.1.1:9119"),
|
||||||
|
ConnectionProfile(id = "2", name = "Profile 2", baseUrl = "http://192.168.1.2:9119"),
|
||||||
|
),
|
||||||
|
selectedProfileId = "2",
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = initialState.selfHealed()
|
||||||
|
|
||||||
|
assertEquals("2", result.selectedProfileId)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun selfHealed_nullifiesMissingProfile() {
|
||||||
|
val initialState =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "http://192.168.1.1:9119"),
|
||||||
|
),
|
||||||
|
selectedProfileId = "3",
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = initialState.selfHealed()
|
||||||
|
|
||||||
|
assertNull(result.selectedProfileId)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun selfHealed_handlesAlreadyNull() {
|
||||||
|
val initialState =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "http://192.168.1.1:9119"),
|
||||||
|
),
|
||||||
|
selectedProfileId = null,
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = initialState.selfHealed()
|
||||||
|
|
||||||
|
assertNull(result.selectedProfileId)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun resolvedBaseUrl_usesSelectedProfileBaseUrl() {
|
||||||
|
val state =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "http://192.168.1.1:9119"),
|
||||||
|
),
|
||||||
|
selectedProfileId = "1",
|
||||||
|
baseUrl = "http://top.level.base.url:9119", // Should be ignored
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = state.resolvedBaseUrl
|
||||||
|
|
||||||
|
assertEquals("http://192.168.1.1:9119/", result)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun resolvedBaseUrl_fallsBackToTopLevelBaseUrl() {
|
||||||
|
val state =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = null), // Selected but no baseUrl
|
||||||
|
),
|
||||||
|
selectedProfileId = "1",
|
||||||
|
baseUrl = "http://top.level.base.url:9119", // Should be used as fallback
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = state.resolvedBaseUrl
|
||||||
|
|
||||||
|
assertEquals("http://top.level.base.url:9119/", result)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun resolvedBaseUrl_fallsBackToLegacyLoopback() {
|
||||||
|
val state =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles = emptyList(), // No selected profile
|
||||||
|
selectedProfileId = null,
|
||||||
|
baseUrl = null, // No top-level baseUrl
|
||||||
|
host = "127.0.0.1",
|
||||||
|
port = 9119,
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = state.resolvedBaseUrl
|
||||||
|
|
||||||
|
assertEquals("http://127.0.0.1:9119/", result)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun resolvedHost_extractsCorrectHost() {
|
||||||
|
val state =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "https://my.server.local:443"),
|
||||||
|
),
|
||||||
|
selectedProfileId = "1",
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = state.resolvedHost
|
||||||
|
|
||||||
|
assertEquals("my.server.local", result)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun resolvedPort_extractsCorrectPort() {
|
||||||
|
val state =
|
||||||
|
ServerStoreState(
|
||||||
|
connectionProfiles =
|
||||||
|
listOf(
|
||||||
|
ConnectionProfile(id = "1", name = "Profile 1", baseUrl = "https://my.server.local:8443"),
|
||||||
|
),
|
||||||
|
selectedProfileId = "1",
|
||||||
|
)
|
||||||
|
|
||||||
|
val result = state.resolvedPort
|
||||||
|
|
||||||
|
assertEquals(8443, result)
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -20,17 +20,17 @@ class ServerStoreTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun testPureOps_addOrReplaceServer() {
|
fun testPureOps_addOrUpdate() {
|
||||||
val state = ServerStoreState()
|
val state = ServerStoreState()
|
||||||
val profile = ConnectionProfile(id = "1", name = "Test", host = "10.0.0.1", port = 8080)
|
val profile = ConnectionProfile(id = "1", name = "Test", host = "10.0.0.1", port = 8080)
|
||||||
|
|
||||||
val newState = state.addOrReplaceServer(profile)
|
val newState = state.addOrUpdate(profile)
|
||||||
assertEquals(1, newState.connectionProfiles.size)
|
assertEquals(1, newState.connectionProfiles.size)
|
||||||
assertEquals(profile, newState.connectionProfiles[0])
|
assertEquals(profile, newState.connectionProfiles[0])
|
||||||
|
|
||||||
// Replace
|
// Replace
|
||||||
val updatedProfile = profile.copy(host = "10.0.0.2")
|
val updatedProfile = profile.copy(host = "10.0.0.2")
|
||||||
val finalState = newState.addOrReplaceServer(updatedProfile)
|
val finalState = newState.addOrUpdate(updatedProfile)
|
||||||
assertEquals(1, finalState.connectionProfiles.size)
|
assertEquals(1, finalState.connectionProfiles.size)
|
||||||
assertEquals("10.0.0.2", finalState.connectionProfiles[0].host)
|
assertEquals("10.0.0.2", finalState.connectionProfiles[0].host)
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in new issue
Block a user