All Downloads are FREE. Search and download functionalities are using the official Maven repository.

commonMain.io.kotest.matchers.maps.MapMatchers.kt Maven / Gradle / Ivy

package io.kotest.matchers.maps

import io.kotest.matchers.Matcher
import io.kotest.matchers.MatcherResult
import io.kotest.matchers.string.Diff
import io.kotest.matchers.string.stringify

fun  haveKey(key: K): Matcher> = object : Matcher> {
   override fun test(value: Map) = MatcherResult(
      value.containsKey(key),
      { "Map should contain key $key" },
      {
         "Map should not contain key $key"
      })
}

fun  haveKeys(vararg keys: K): Matcher<
   Map> = object : Matcher> {
  override fun test(value: Map): MatcherResult {
     val keysNotPresentInMap = keys.filterNot { value.containsKey(it) }
    return MatcherResult(
       keysNotPresentInMap.isEmpty(),
       { "Map did not contain the keys ${keysNotPresentInMap.joinToString(", ")}" },
       { "Map should not contain the keys ${keys.filter { value.containsKey(it) }.joinToString(", ")}" }
    )
  }
}

fun  haveValue(v: V): Matcher> = object : Matcher> {
   override fun test(value: Map<*, V>) = MatcherResult(
      value.containsValue(v),
      { "Map should contain value $v" },
      {
         "Map should not contain value $v"
      })
}

fun  haveValues(vararg values: V): Matcher> = object : Matcher> {
   override fun test(value: Map<*, V>): MatcherResult {
      val valuesNotPresentInMap = values.filterNot { value.containsValue(it) }
      return MatcherResult(
         valuesNotPresentInMap.isEmpty(),
         { "Map did not contain the values ${values.joinToString(", ")}" },
         {
            "Map should not contain the values ${values.joinToString(", ")}"
         })
   }
}

fun  containAnyKeys(vararg keys: K): Matcher> = object : Matcher> {
   override fun test(value: Map): MatcherResult {
      val passed = keys.any { value.containsKey(it) }
      return MatcherResult(
         passed,
         { "Map did not contain any of the keys ${keys.joinToString(", ")}" },
         { "Map should not contain any of the keys ${keys.joinToString(", ")}" })
   }
}

fun  containAnyValues(vararg values: V): Matcher> = object : Matcher> {
   override fun test(value: Map<*, V>): MatcherResult {
      val passed = values.any { value.containsValue(it) }
      return MatcherResult(
         passed,
         { "Map did not contain any of the values ${values.joinToString(", ")}" },
         { "Map should not contain any of the values ${values.joinToString(", ")}" })
   }
}

fun  contain(key: K, v: V): Matcher> = object : Matcher> {
   override fun test(value: Map) = MatcherResult(
      value[key] == v,
      { "Map should contain mapping $key=$v but was ${buildActualValue(value)}" },
      { "Map should not contain mapping $key=$v but was $value" })

   private fun buildActualValue(map: Map) = map[key]?.let { "$key=$it" } ?: map
}

fun  containAll(expected: Map): Matcher> =
  MapContainsMatcher(expected, ignoreExtraKeys = true)

fun  containExactly(expected: Map): Matcher> =
  MapContainsMatcher(expected)

fun  haveSize(size: Int): Matcher> = object : Matcher> {
   override fun test(value: Map) =
      MatcherResult(
         value.size == size,
         { "Map should have size $size but has size ${value.size}" },
         { "Map should not have size $size" }
      )
}

class MapContainsMatcher(
  private val expected: Map,
  private val ignoreExtraKeys: Boolean = false
) : Matcher> {
   override fun test(value: Map): MatcherResult {
      val diff = Diff.create(value, expected, ignoreExtraMapKeys = ignoreExtraKeys)
      val (expectMsg, negatedExpectMsg) = if (ignoreExtraKeys) {
         "should contain all of" to "should not contain all of"
      } else {
         "should be equal to" to "should not be equal to"
      }
      val (butMsg, negatedButMsg) = if (ignoreExtraKeys) {
         "but differs by" to "but contains"
      } else {
         "but differs by" to "but equals"
      }
      val failureMsg = """
      |
      |Expected:
      |  ${stringify(value)}
      |$expectMsg:
      |  ${stringify(expected)}
      |$butMsg:
      |${diff.toString(1)}
      |
      """.trimMargin()
      val negatedFailureMsg = """
      |
      |Expected:
      |  ${stringify(value)}
      |$negatedExpectMsg:
      |  ${stringify(expected)}
      |$negatedButMsg
      |
    """.trimMargin()
      return MatcherResult(
         diff.isEmpty(),
         { failureMsg },
         {
            negatedFailureMsg
         })
   }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy