Repository: typesafegithub/github-workflows-kt
Pull request #1133 (2023-11-24 16:41:59)

refactor(automation): use actual typing source in docs
Part of #1072.


Patch:
diff --git a/automation/action-binding-generator/api/action-binding-generator.api b/automation/action-binding-generator/api/action-binding-generator.api
index 3b797380f..0f3aa2b3a 100644
--- a/automation/action-binding-generator/api/action-binding-generator.api
+++ b/automation/action-binding-generator/api/action-binding-generator.api
@@ -1,16 +1,18 @@
 public final class io/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding {
-	public fun <init> (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)V
+	public fun <init> (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;)V
 	public final fun component1 ()Ljava/lang/String;
 	public final fun component2 ()Ljava/lang/String;
 	public final fun component3 ()Ljava/lang/String;
 	public final fun component4 ()Ljava/lang/String;
-	public final fun copy (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
-	public static synthetic fun copy$default (Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;ILjava/lang/Object;)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
+	public final fun component5 ()Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
+	public final fun copy (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
+	public static synthetic fun copy$default (Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;ILjava/lang/Object;)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
 	public fun equals (Ljava/lang/Object;)Z
 	public final fun getClassName ()Ljava/lang/String;
 	public final fun getFilePath ()Ljava/lang/String;
 	public final fun getKotlinCode ()Ljava/lang/String;
 	public final fun getPackageName ()Ljava/lang/String;
+	public final fun getTypingActualSource ()Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
 	public fun hashCode ()I
 	public fun toString ()Ljava/lang/String;
 }
@@ -67,8 +69,8 @@ public final class io/github/typesafegithub/workflows/actionbindinggenerator/Gen
 }
 
 public final class io/github/typesafegithub/workflows/actionbindinggenerator/GenerationKt {
-	public static final fun generateBinding (Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionCoords;Lio/github/typesafegithub/workflows/actionbindinggenerator/MetadataRevision;ZLio/github/typesafegithub/workflows/actionbindinggenerator/Metadata;Ljava/util/Map;Z)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
-	public static synthetic fun generateBinding$default (Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionCoords;Lio/github/typesafegithub/workflows/actionbindinggenerator/MetadataRevision;ZLio/github/typesafegithub/workflows/actionbindinggenerator/Metadata;Ljava/util/Map;ZILjava/lang/Object;)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
+	public static final fun generateBinding (Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionCoords;Lio/github/typesafegithub/workflows/actionbindinggenerator/MetadataRevision;ZLio/github/typesafegithub/workflows/actionbindinggenerator/Metadata;Lkotlin/Pair;Z)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
+	public static synthetic fun generateBinding$default (Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionCoords;Lio/github/typesafegithub/workflows/actionbindinggenerator/MetadataRevision;ZLio/github/typesafegithub/workflows/actionbindinggenerator/Metadata;Lkotlin/Pair;ZILjava/lang/Object;)Lio/github/typesafegithub/workflows/actionbindinggenerator/ActionBinding;
 }
 
 public final class io/github/typesafegithub/workflows/actionbindinggenerator/Input {
@@ -190,3 +192,12 @@ public final class io/github/typesafegithub/workflows/actionbindinggenerator/Typ
 public abstract interface class io/github/typesafegithub/workflows/actionbindinggenerator/Typing {
 }
 
+public final class io/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource : java/lang/Enum {
+	public static final field ACTION Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
+	public static final field CACHE Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
+	public static final field TYPING_CATALOG Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
+	public static fun getEntries ()Lkotlin/enums/EnumEntries;
+	public static fun valueOf (Ljava/lang/String;)Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
+	public static fun values ()[Lio/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource;
+}
+
diff --git a/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/Generation.kt b/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/Generation.kt
index 6ca5b29a0..25f44a6cc 100644
--- a/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/Generation.kt
+++ b/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/Generation.kt
@@ -23,6 +23,7 @@ public data class ActionBinding(
     val filePath: String,
     val className: String,
     val packageName: String,
+    val typingActualSource: TypingActualSource?,
 )
 
 private object Types {
@@ -41,7 +42,7 @@ public fun ActionCoords.generateBinding(
     metadataRevision: MetadataRevision,
     useCache: Boolean = true,
     metadata: Metadata = this.fetchMetadata(metadataRevision, useCache = useCache),
-    inputTypings: Map<String, Typing> = provideTypes(metadataRevision, useCache = useCache),
+    inputTypings: Pair<Map<String, Typing>, TypingActualSource?> = provideTypes(metadataRevision, useCache = useCache),
     generateForScript: Boolean = false,
 ): ActionBinding {
     require(this.version.removePrefix("v").toIntOrNull() != null) {
@@ -49,20 +50,21 @@ public fun ActionCoords.generateBinding(
     }
 
     val metadataProcessed = metadata.removeDeprecatedInputsIfNameClash()
-    checkPropertiesAreValid(metadataProcessed, inputTypings)
-    metadataProcessed.suggestAdditionalTypings(inputTypings.keys)?.let { formatSuggestions ->
+    checkPropertiesAreValid(metadataProcessed, inputTypings.first)
+    metadataProcessed.suggestAdditionalTypings(inputTypings.first.keys)?.let { formatSuggestions ->
         println("$prettyPrint I suggest the following typings:\n$formatSuggestions")
     }
 
     val className = this.buildActionClassName(includeVersion = !generateForScript)
     val actionBindingSourceCode =
-        generateActionBindingSourceCode(metadataProcessed, this, inputTypings, className, generateForScript = generateForScript)
+        generateActionBindingSourceCode(metadataProcessed, this, inputTypings.first, className, generateForScript = generateForScript)
     val packageName = owner.toKotlinPackageName()
     return ActionBinding(
         kotlinCode = actionBindingSourceCode,
         filePath = "library/src/gen/kotlin/io/github/typesafegithub/workflows/actions/$packageName/$className.kt",
         className = className,
         packageName = packageName,
+        typingActualSource = inputTypings.second,
     )
 }
 
diff --git a/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProviding.kt b/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProviding.kt
index 04b863f55..a99ea5959 100644
--- a/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProviding.kt
+++ b/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProviding.kt
@@ -1,6 +1,9 @@
 package io.github.typesafegithub.workflows.actionbindinggenerator
 
 import com.charleskorn.kaml.Yaml
+import io.github.typesafegithub.workflows.actionbindinggenerator.TypingActualSource.ACTION
+import io.github.typesafegithub.workflows.actionbindinggenerator.TypingActualSource.CACHE
+import io.github.typesafegithub.workflows.actionbindinggenerator.TypingActualSource.TYPING_CATALOG
 import kotlinx.serialization.decodeFromString
 import java.io.File
 import java.io.IOException
@@ -12,10 +15,13 @@ internal fun ActionCoords.provideTypes(
     metadataRevision: MetadataRevision,
     fetchUri: (URI) -> String = ::fetchUri,
     useCache: Boolean = true,
-): Map<String, Typing> =
-    this.fetchTypingMetadata(metadataRevision, fetchUri, useCache = useCache)?.toTypesMap()
-        ?: this.fetchFromTypingsFromCatalog(fetchUri)?.toTypesMap()
-        ?: emptyMap()
+): Pair<Map<String, Typing>, TypingActualSource?> =
+    (
+        this.fetchTypingMetadata(metadataRevision, fetchUri, useCache = useCache)
+            ?: this.fetchFromTypingsFromCatalog(fetchUri)
+    )
+        ?.let { Pair(it.first.toTypesMap(), it.second) }
+        ?: Pair(emptyMap(), null)
 
 private val actionTypesYamlDir: File = File("build/action-types-yaml")
 
@@ -45,12 +51,12 @@ private fun ActionCoords.fetchTypingMetadata(
     metadataRevision: MetadataRevision,
     fetchUri: (URI) -> String = ::fetchUri,
     useCache: Boolean,
-): ActionTypes? {
+): Pair<ActionTypes, TypingActualSource>? {
     val cacheFile = actionTypesYamlDir.resolve("$owner-${name.replace('/', '_')}-$version.yml")
     if (useCache) {
         if (cacheFile.canRead()) {
             println("  ... types from cache: $cacheFile")
-            return myYaml.decodeFromStringOrDefaultIfEmpty(cacheFile.readText(), ActionTypes())
+            return Pair(myYaml.decodeFromStringOrDefaultIfEmpty(cacheFile.readText(), ActionTypes()), CACHE)
         }
     }
 
@@ -76,11 +82,11 @@ private fun ActionCoords.fetchTypingMetadata(
         cacheFile.writeText(typesMetadataYaml)
     }
 
-    return myYaml.decodeFromStringOrDefaultIfEmpty(typesMetadataYaml, ActionTypes())
+    return Pair(myYaml.decodeFromStringOrDefaultIfEmpty(typesMetadataYaml, ActionTypes()), ACTION)
 }
 
-private fun ActionCoords.fetchFromTypingsFromCatalog(fetchUri: (URI) -> String = ::fetchUri): ActionTypes? =
-    fetchTypingsFromUrl(url = actionTypesFromCatalog(), fetchUri = fetchUri)
+private fun ActionCoords.fetchFromTypingsFromCatalog(fetchUri: (URI) -> String = ::fetchUri): Pair<ActionTypes, TypingActualSource>? =
+    fetchTypingsFromUrl(url = actionTypesFromCatalog(), fetchUri = fetchUri)?.let { Pair(it, TYPING_CATALOG) }
 
 private fun fetchTypingsFromUrl(
     url: String,
diff --git a/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource.kt b/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource.kt
new file mode 100644
index 000000000..9bca01401
--- /dev/null
+++ b/automation/action-binding-generator/src/main/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypingActualSource.kt
@@ -0,0 +1,7 @@
+package io.github.typesafegithub.workflows.actionbindinggenerator
+
+public enum class TypingActualSource {
+    ACTION,
+    TYPING_CATALOG,
+    CACHE,
+}
diff --git a/automation/code-generator/src/main/kotlin/io/github/typesafegithub/workflows/codegenerator/ActionsDocsGeneration.kt b/automation/code-generator/src/main/kotlin/io/github/typesafegithub/workflows/codegenerator/ActionsDocsGeneration.kt
index 939e5f206..587e848a5 100644
--- a/automation/code-generator/src/main/kotlin/io/github/typesafegithub/workflows/codegenerator/ActionsDocsGeneration.kt
+++ b/automation/code-generator/src/main/kotlin/io/github/typesafegithub/workflows/codegenerator/ActionsDocsGeneration.kt
@@ -2,9 +2,8 @@ package io.github.typesafegithub.workflows.codegenerator
 
 import io.github.typesafegithub.workflows.actionbindinggenerator.ActionBinding
 import io.github.typesafegithub.workflows.actionbindinggenerator.ActionCoords
-import io.github.typesafegithub.workflows.actionsmetadata.bindingsToGenerate
+import io.github.typesafegithub.workflows.actionbindinggenerator.TypingActualSource
 import io.github.typesafegithub.workflows.actionsmetadata.model.ActionBindingRequest
-import io.github.typesafegithub.workflows.actionsmetadata.model.TypingsSource
 import io.github.typesafegithub.workflows.actionsmetadata.model.Version
 import java.nio.file.Paths
 
@@ -32,17 +31,20 @@ internal fun generateListOfBindingsForDocs(requestsAndBindings: List<Pair<Action
                         val kotlinClasses =
                             versions
                                 .sortedBy { Version(it.first.actionCoords.version) }
-                                .joinToString(", ") { it.first.toMarkdownLinkToKotlinCode(it.second.packageName, it.second.className) }
+                                .joinToString(", ") { it.toMarkdownLinkToKotlinCode(it.second.packageName, it.second.className) }
                         writer.println("    * ${versions.first().first.actionCoords.toMarkdownLinkGithub()} - $kotlinClasses")
                     }
             }
 
-        val uniqueActionsCount = bindingsToGenerate.groupBy { "${it.actionCoords.owner}/${it.actionCoords.name}" }.size
+        val uniqueActionsCount =
+            requestsAndBindings
+                .map { it.first }
+                .groupBy { "${it.actionCoords.owner}/${it.actionCoords.name}" }.size
         val uniqueActionsProvidingTypingsCount =
-            bindingsToGenerate
-                .groupBy { "${it.actionCoords.owner}/${it.actionCoords.name}" }
-                .mapValues { (_, versions) -> versions.maxByOrNull { Version(it.actionCoords.version) } }
-                .count { (_, actionBindingRequest) -> actionBindingRequest?.typingsSource == TypingsSource.ActionTypes }
+            requestsAndBindings
+                .groupBy { "${it.first.actionCoords.owner}/${it.first.actionCoords.name}" }
+                .mapValues { (_, versions) -> versions.maxByOrNull { Version(it.first.actionCoords.version) } }
+                .count { (_, requestAndBinding) -> requestAndBinding?.second?.typingActualSource == TypingActualSource.ACTION }
 
         writer.println(
             """
@@ -52,7 +54,7 @@ internal fun generateListOfBindingsForDocs(requestsAndBindings: List<Pair<Action
             Number of bindings available:
 
             * counting by actions: $uniqueActionsCount
-            * counting each version separately: ${bindingsToGenerate.size}
+            * counting each version separately: ${requestsAndBindings.size}
 
             Actions [providing typings](https://github.com/typesafegithub/github-actions-typing/) (marked with ✅ on the above list): $uniqueActionsProvidingTypingsCount
             """.trimIndent(),
@@ -66,12 +68,12 @@ internal fun deleteListOfBindingsInDocs() {
 
 private val listOfBindingsInDocs = Paths.get("docs/supported-actions.md")
 
-private fun ActionBindingRequest.toMarkdownLinkToKotlinCode(
+private fun Pair<ActionBindingRequest, ActionBinding>.toMarkdownLinkToKotlinCode(
     packageName: String,
     className: String,
 ): String {
-    val typingsMarker = if (typingsSource == TypingsSource.ActionTypes) " ✅" else ""
-    return "${actionCoords.version}$typingsMarker: [`$className`](" +
+    val typingsMarker = if (this.second.typingActualSource == TypingActualSource.ACTION) " ✅" else ""
+    return "${this.first.actionCoords.version}$typingsMarker: [`$className`](" +
         "https://github.com/typesafegithub/github-workflows-kt/blob/v[[ version ]]/library/src/gen/kotlin/io/github/" +
         "typesafegithub/workflows/actions/$packageName/$className.kt)"
 }


Test patch:
diff --git a/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/GenerationTest.kt b/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/GenerationTest.kt
index 49aa5b8e0..5df466f17 100644
--- a/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/GenerationTest.kt
+++ b/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/GenerationTest.kt
@@ -1,5 +1,6 @@
 package io.github.typesafegithub.workflows.actionbindinggenerator
 
+import io.github.typesafegithub.workflows.actionbindinggenerator.TypingActualSource.ACTION
 import io.kotest.assertions.throwables.shouldThrowAny
 import io.kotest.core.spec.style.FunSpec
 import io.kotest.matchers.shouldBe
@@ -163,15 +164,18 @@ class GenerationTest : FunSpec({
                 metadataRevision = FromLockfile,
                 metadata = actionManifest,
                 inputTypings =
-                    mapOf(
-                        "baz-goo" to BooleanTyping,
-                        "bin-kin" to BooleanTyping,
-                        "int-pint" to IntegerTyping,
-                        "flo-pint" to FloatTyping,
-                        "boo-zoo" to ListOfTypings(","),
-                        "fin-bin" to EnumTyping("Bin", listOf("foo", "boo-bar", "baz123")),
-                        "goo-zen" to IntegerWithSpecialValueTyping("Zen", mapOf("Special1" to 3, "Special2" to -1)),
-                        "bah-enum" to EnumTyping(null, listOf("helloworld"), listOf("HelloWorld")),
+                    Pair(
+                        mapOf(
+                            "baz-goo" to BooleanTyping,
+                            "bin-kin" to BooleanTyping,
+                            "int-pint" to IntegerTyping,
+                            "flo-pint" to FloatTyping,
+                            "boo-zoo" to ListOfTypings(","),
+                            "fin-bin" to EnumTyping("Bin", listOf("foo", "boo-bar", "baz123")),
+                            "goo-zen" to IntegerWithSpecialValueTyping("Zen", mapOf("Special1" to 3, "Special2" to -1)),
+                            "bah-enum" to EnumTyping(null, listOf("helloworld"), listOf("HelloWorld")),
+                        ),
+                        ACTION,
                     ),
             )
 
@@ -223,10 +227,13 @@ class GenerationTest : FunSpec({
                     ),
             )
         val inputTypings =
-            mapOf(
-                "check-latest" to BooleanTyping,
-                "foo-bar" to BooleanTyping,
-                "bazGoo" to BooleanTyping,
+            Pair(
+                mapOf(
+                    "check-latest" to BooleanTyping,
+                    "foo-bar" to BooleanTyping,
+                    "bazGoo" to BooleanTyping,
+                ),
+                ACTION,
             )
         val coords = ActionCoords("actions", "setup-node", "v2")
 
@@ -333,19 +340,22 @@ class GenerationTest : FunSpec({
                     ),
             )
         val inputTypings =
-            mapOf(
-                "list-strings" to ListOfTypings(",", StringTyping),
-                "list-ints" to ListOfTypings(",", IntegerTyping),
-                "list-enums" to
-                    ListOfTypings(
-                        delimiter = ",",
-                        typing = EnumTyping("MyEnum", listOf("one", "two", "three")),
-                    ),
-                "list-int-special" to
-                    ListOfTypings(
-                        delimiter = ",",
-                        typing = IntegerWithSpecialValueTyping("MyInt", mapOf("the-answer" to 42)),
-                    ),
+            Pair(
+                mapOf(
+                    "list-strings" to ListOfTypings(",", StringTyping),
+                    "list-ints" to ListOfTypings(",", IntegerTyping),
+                    "list-enums" to
+                        ListOfTypings(
+                            delimiter = ",",
+                            typing = EnumTyping("MyEnum", listOf("one", "two", "three")),
+                        ),
+                    "list-int-special" to
+                        ListOfTypings(
+                            delimiter = ",",
+                            typing = IntegerWithSpecialValueTyping("MyInt", mapOf("the-answer" to 42)),
+                        ),
+                ),
+                ACTION,
             )
         val coords = ActionCoords("john-smith", "simple-action-with-lists", "v3")
 
@@ -394,10 +404,13 @@ class GenerationTest : FunSpec({
                 metadataRevision = FromLockfile,
                 metadata = actionManifest,
                 inputTypings =
-                    mapOf(
-                        "foo-one" to IntegerWithSpecialValueTyping("Foo", mapOf("Special1" to 3)),
-                        "foo-two" to IntegerWithSpecialValueTyping("Foo", mapOf("Special1" to 3)),
-                        "foo-three" to IntegerWithSpecialValueTyping("Foo", mapOf("Special1" to 3)),
+                    Pair(
+                        mapOf(
+                            "foo-one" to IntegerWithSpecialValueTyping("Foo", mapOf("Special1" to 3)),
+                            "foo-two" to IntegerWithSpecialValueTyping("Foo", mapOf("Special1" to 3)),
+                            "foo-three" to IntegerWithSpecialValueTyping("Foo", mapOf("Special1" to 3)),
+                        ),
+                        ACTION,
                     ),
             )
 
@@ -445,8 +458,11 @@ class GenerationTest : FunSpec({
                 metadata = actionManifest,
                 generateForScript = true,
                 inputTypings =
-                    mapOf(
-                        "baz-goo" to EnumTyping(null, listOf("helloworld"), listOf("HelloWorld")),
+                    Pair(
+                        mapOf(
+                            "baz-goo" to EnumTyping(null, listOf("helloworld"), listOf("HelloWorld")),
+                        ),
+                        ACTION,
                     ),
             )
 
diff --git a/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProvidingTest.kt b/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProvidingTest.kt
index 224d7ffe2..34c121d1d 100644
--- a/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProvidingTest.kt
+++ b/automation/action-binding-generator/src/test/kotlin/io/github/typesafegithub/workflows/actionbindinggenerator/TypesProvidingTest.kt
@@ -47,7 +47,7 @@ class TypesProvidingTest : FunSpec({
         val types = actionCoord.provideTypes(metadataRevision = CommitHash("some-hash"), { actionTypesYml })
 
         // Then
-        types shouldBe
+        types.first shouldBe
             mapOf(
                 "name" to StringTyping,
                 "verbose" to BooleanTyping,