build/github_repository: allow storing submodule_info as attr

Currently we are doing too many requests to the REST API as our CI is
invalidating the cache too often. This is a workaround until we can
store said data inside MODUEL.bazel.lock.

Change-Id: Iac9be2a4ed3d3fb5f301ac63545d07d807cc2f8e
Reviewed-on: https://review.monogon.dev/c/monogon/+/4156
Tested-by: Jenkins CI
Reviewed-by: Lorenz Brun <lorenz@monogon.tech>
diff --git a/build/bazel/third_party.MODULE.bazel b/build/bazel/third_party.MODULE.bazel
index ace7867..ebdd2fd 100644
--- a/build/bazel/third_party.MODULE.bazel
+++ b/build/bazel/third_party.MODULE.bazel
@@ -14,6 +14,20 @@
     ],
     ref = "fbe0805b2091393406952e84724188f8c1941837",  # stable202502
     repo = "edk2",
+    submodule_info = {
+        "CryptoPkg/Library/OpensslLib/openssl": "{\"name\":\"openssl\",\"path\":\"CryptoPkg\\/Library\\/OpensslLib\\/openssl\",\"sha\":\"98acb6b02839c609ef5b837794e08d906d965335\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/CryptoPkg\\/Library\\/OpensslLib\\/openssl?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/openssl\\/openssl\\/tree\\/98acb6b02839c609ef5b837794e08d906d965335\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/openssl\\/openssl\\/git\\/trees\\/98acb6b02839c609ef5b837794e08d906d965335\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/openssl\\/openssl\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/CryptoPkg\\/Library\\/OpensslLib\\/openssl?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/openssl\\/openssl\\/git\\/trees\\/98acb6b02839c609ef5b837794e08d906d965335\",\"html\":\"https:\\/\\/github.com\\/openssl\\/openssl\\/tree\\/98acb6b02839c609ef5b837794e08d906d965335\"}}",
+        "UnitTestFrameworkPkg/Library/CmockaLib/cmocka": "{\"name\":\"cmocka\",\"path\":\"UnitTestFrameworkPkg\\/Library\\/CmockaLib\\/cmocka\",\"sha\":\"1cc9cde3448cdd2e000886a26acf1caac2db7cf1\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/UnitTestFrameworkPkg\\/Library\\/CmockaLib\\/cmocka?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/tianocore\\/edk2-cmocka\\/tree\\/1cc9cde3448cdd2e000886a26acf1caac2db7cf1\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2-cmocka\\/git\\/trees\\/1cc9cde3448cdd2e000886a26acf1caac2db7cf1\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/tianocore\\/edk2-cmocka.git\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/UnitTestFrameworkPkg\\/Library\\/CmockaLib\\/cmocka?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2-cmocka\\/git\\/trees\\/1cc9cde3448cdd2e000886a26acf1caac2db7cf1\",\"html\":\"https:\\/\\/github.com\\/tianocore\\/edk2-cmocka\\/tree\\/1cc9cde3448cdd2e000886a26acf1caac2db7cf1\"}}",
+        "MdeModulePkg/Universal/RegularExpressionDxe/oniguruma": "{\"name\":\"oniguruma\",\"path\":\"MdeModulePkg\\/Universal\\/RegularExpressionDxe\\/oniguruma\",\"sha\":\"abfc8ff81df4067f309032467785e06975678f0d\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdeModulePkg\\/Universal\\/RegularExpressionDxe\\/oniguruma?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/kkos\\/oniguruma\\/tree\\/abfc8ff81df4067f309032467785e06975678f0d\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/kkos\\/oniguruma\\/git\\/trees\\/abfc8ff81df4067f309032467785e06975678f0d\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/kkos\\/oniguruma\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdeModulePkg\\/Universal\\/RegularExpressionDxe\\/oniguruma?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/kkos\\/oniguruma\\/git\\/trees\\/abfc8ff81df4067f309032467785e06975678f0d\",\"html\":\"https:\\/\\/github.com\\/kkos\\/oniguruma\\/tree\\/abfc8ff81df4067f309032467785e06975678f0d\"}}",
+        "MdeModulePkg/Library/BrotliCustomDecompressLib/brotli": "{\"name\":\"brotli\",\"path\":\"MdeModulePkg\\/Library\\/BrotliCustomDecompressLib\\/brotli\",\"sha\":\"f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdeModulePkg\\/Library\\/BrotliCustomDecompressLib\\/brotli?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/google\\/brotli\\/tree\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/google\\/brotli\\/git\\/trees\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/google\\/brotli\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdeModulePkg\\/Library\\/BrotliCustomDecompressLib\\/brotli?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/google\\/brotli\\/git\\/trees\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"html\":\"https:\\/\\/github.com\\/google\\/brotli\\/tree\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\"}}",
+        "BaseTools/Source/C/BrotliCompress/brotli": "{\"name\":\"brotli\",\"path\":\"BaseTools\\/Source\\/C\\/BrotliCompress\\/brotli\",\"sha\":\"f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/BaseTools\\/Source\\/C\\/BrotliCompress\\/brotli?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/google\\/brotli\\/tree\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/google\\/brotli\\/git\\/trees\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/google\\/brotli\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/BaseTools\\/Source\\/C\\/BrotliCompress\\/brotli?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/google\\/brotli\\/git\\/trees\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\",\"html\":\"https:\\/\\/github.com\\/google\\/brotli\\/tree\\/f4153a09f87cbb9c826d8fc12c74642bb2d879ea\"}}",
+        "RedfishPkg/Library/JsonLib/jansson": "{\"name\":\"jansson\",\"path\":\"RedfishPkg\\/Library\\/JsonLib\\/jansson\",\"sha\":\"e9ebfa7e77a6bee77df44e096b100e7131044059\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/RedfishPkg\\/Library\\/JsonLib\\/jansson?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/akheron\\/jansson\\/tree\\/e9ebfa7e77a6bee77df44e096b100e7131044059\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/akheron\\/jansson\\/git\\/trees\\/e9ebfa7e77a6bee77df44e096b100e7131044059\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/akheron\\/jansson\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/RedfishPkg\\/Library\\/JsonLib\\/jansson?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/akheron\\/jansson\\/git\\/trees\\/e9ebfa7e77a6bee77df44e096b100e7131044059\",\"html\":\"https:\\/\\/github.com\\/akheron\\/jansson\\/tree\\/e9ebfa7e77a6bee77df44e096b100e7131044059\"}}",
+        "UnitTestFrameworkPkg/Library/GoogleTestLib/googletest": "{\"name\":\"googletest\",\"path\":\"UnitTestFrameworkPkg\\/Library\\/GoogleTestLib\\/googletest\",\"sha\":\"86add13493e5c881d7e4ba77fb91c1f57752b3a4\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/UnitTestFrameworkPkg\\/Library\\/GoogleTestLib\\/googletest?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/google\\/googletest\\/tree\\/86add13493e5c881d7e4ba77fb91c1f57752b3a4\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/google\\/googletest\\/git\\/trees\\/86add13493e5c881d7e4ba77fb91c1f57752b3a4\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/google\\/googletest.git\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/UnitTestFrameworkPkg\\/Library\\/GoogleTestLib\\/googletest?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/google\\/googletest\\/git\\/trees\\/86add13493e5c881d7e4ba77fb91c1f57752b3a4\",\"html\":\"https:\\/\\/github.com\\/google\\/googletest\\/tree\\/86add13493e5c881d7e4ba77fb91c1f57752b3a4\"}}",
+        "UnitTestFrameworkPkg/Library/SubhookLib/subhook": "{\"name\":\"subhook\",\"path\":\"UnitTestFrameworkPkg\\/Library\\/SubhookLib\\/subhook\",\"sha\":\"83d4e1ebef3588fae48b69a7352cc21801cb70bc\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/UnitTestFrameworkPkg\\/Library\\/SubhookLib\\/subhook?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/tianocore\\/edk2-subhook\\/tree\\/83d4e1ebef3588fae48b69a7352cc21801cb70bc\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2-subhook\\/git\\/trees\\/83d4e1ebef3588fae48b69a7352cc21801cb70bc\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/tianocore\\/edk2-subhook.git\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/UnitTestFrameworkPkg\\/Library\\/SubhookLib\\/subhook?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2-subhook\\/git\\/trees\\/83d4e1ebef3588fae48b69a7352cc21801cb70bc\",\"html\":\"https:\\/\\/github.com\\/tianocore\\/edk2-subhook\\/tree\\/83d4e1ebef3588fae48b69a7352cc21801cb70bc\"}}",
+        "MdePkg/Library/BaseFdtLib/libfdt": "{\"name\":\"libfdt\",\"path\":\"MdePkg\\/Library\\/BaseFdtLib\\/libfdt\",\"sha\":\"cfff805481bdea27f900c32698171286542b8d3c\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdePkg\\/Library\\/BaseFdtLib\\/libfdt?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/devicetree-org\\/pylibfdt\\/tree\\/cfff805481bdea27f900c32698171286542b8d3c\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/devicetree-org\\/pylibfdt\\/git\\/trees\\/cfff805481bdea27f900c32698171286542b8d3c\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/devicetree-org\\/pylibfdt.git\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdePkg\\/Library\\/BaseFdtLib\\/libfdt?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/devicetree-org\\/pylibfdt\\/git\\/trees\\/cfff805481bdea27f900c32698171286542b8d3c\",\"html\":\"https:\\/\\/github.com\\/devicetree-org\\/pylibfdt\\/tree\\/cfff805481bdea27f900c32698171286542b8d3c\"}}",
+        "MdePkg/Library/MipiSysTLib/mipisyst": "{\"name\":\"mipisyst\",\"path\":\"MdePkg\\/Library\\/MipiSysTLib\\/mipisyst\",\"sha\":\"370b5944c046bab043dd8b133727b2135af7747a\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdePkg\\/Library\\/MipiSysTLib\\/mipisyst?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/MIPI-Alliance\\/public-mipi-sys-t\\/tree\\/370b5944c046bab043dd8b133727b2135af7747a\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/MIPI-Alliance\\/public-mipi-sys-t\\/git\\/trees\\/370b5944c046bab043dd8b133727b2135af7747a\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/MIPI-Alliance\\/public-mipi-sys-t.git\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/MdePkg\\/Library\\/MipiSysTLib\\/mipisyst?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/MIPI-Alliance\\/public-mipi-sys-t\\/git\\/trees\\/370b5944c046bab043dd8b133727b2135af7747a\",\"html\":\"https:\\/\\/github.com\\/MIPI-Alliance\\/public-mipi-sys-t\\/tree\\/370b5944c046bab043dd8b133727b2135af7747a\"}}",
+        "CryptoPkg/Library/MbedTlsLib/mbedtls": "{\"name\":\"mbedtls\",\"path\":\"CryptoPkg\\/Library\\/MbedTlsLib\\/mbedtls\",\"sha\":\"8c89224991adff88d53cd380f42a2baa36f91454\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/CryptoPkg\\/Library\\/MbedTlsLib\\/mbedtls?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/ARMmbed\\/mbedtls\\/tree\\/8c89224991adff88d53cd380f42a2baa36f91454\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/ARMmbed\\/mbedtls\\/git\\/trees\\/8c89224991adff88d53cd380f42a2baa36f91454\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/ARMmbed\\/mbedtls\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/CryptoPkg\\/Library\\/MbedTlsLib\\/mbedtls?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/ARMmbed\\/mbedtls\\/git\\/trees\\/8c89224991adff88d53cd380f42a2baa36f91454\",\"html\":\"https:\\/\\/github.com\\/ARMmbed\\/mbedtls\\/tree\\/8c89224991adff88d53cd380f42a2baa36f91454\"}}",
+        "SecurityPkg/DeviceSecurity/SpdmLib/libspdm": "{\"name\":\"libspdm\",\"path\":\"SecurityPkg\\/DeviceSecurity\\/SpdmLib\\/libspdm\",\"sha\":\"98ef964e1e9a0c39c7efb67143d3a13a819432e0\",\"size\":0,\"url\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/SecurityPkg\\/DeviceSecurity\\/SpdmLib\\/libspdm?ref=fbe0805b2091393406952e84724188f8c1941837\",\"html_url\":\"https:\\/\\/github.com\\/DMTF\\/libspdm\\/tree\\/98ef964e1e9a0c39c7efb67143d3a13a819432e0\",\"git_url\":\"https:\\/\\/api.github.com\\/repos\\/DMTF\\/libspdm\\/git\\/trees\\/98ef964e1e9a0c39c7efb67143d3a13a819432e0\",\"download_url\":null,\"type\":\"submodule\",\"submodule_git_url\":\"https:\\/\\/github.com\\/DMTF\\/libspdm.git\",\"_links\":{\"self\":\"https:\\/\\/api.github.com\\/repos\\/tianocore\\/edk2\\/contents\\/SecurityPkg\\/DeviceSecurity\\/SpdmLib\\/libspdm?ref=fbe0805b2091393406952e84724188f8c1941837\",\"git\":\"https:\\/\\/api.github.com\\/repos\\/DMTF\\/libspdm\\/git\\/trees\\/98ef964e1e9a0c39c7efb67143d3a13a819432e0\",\"html\":\"https:\\/\\/github.com\\/DMTF\\/libspdm\\/tree\\/98ef964e1e9a0c39c7efb67143d3a13a819432e0\"}}",
+    },
     submodules = {
         "CryptoPkg/Library/OpensslLib/openssl": "sha256-MvIqVMARnJx7foEjQtEtIrOb3mHEYDi/QB56NW5MdFQ=",
         "UnitTestFrameworkPkg/Library/CmockaLib/cmocka": "sha256-Wc1LgauvrjXZSsXZHPSuWwUSLmiHE81ttR5eTO9HHY8=",
diff --git a/build/github_repository/def.bzl b/build/github_repository/def.bzl
index 81a7268..9186c25 100644
--- a/build/github_repository/def.bzl
+++ b/build/github_repository/def.bzl
@@ -41,24 +41,31 @@
     )
 
     for submodule, integrity in ctx.attr.submodules.items():
-        url = build_submodule_info_url(
-            owner = ctx.attr.owner,
-            repo = ctx.attr.repo,
-            ref = ctx.attr.ref,
-            submodule = submodule,
-        )
+        if submodule not in ctx.attr.submodule_info:
+            url = build_submodule_info_url(
+                owner = ctx.attr.owner,
+                repo = ctx.attr.repo,
+                ref = ctx.attr.ref,
+                submodule = submodule,
+            )
 
-        submodule_info_path = submodule + ".submodule_info"
-        ctx.download(
-            url = url,
-            headers = {
-                "Accept": "application/vnd.github+json",
-                "X-GitHub-Api-Version": "2022-11-28",
-            },
-            output = submodule_info_path,
-        )
+            submodule_info_path = submodule + ".submodule_info"
+            ctx.download(
+                url = url,
+                headers = {
+                    "Accept": "application/vnd.github+json",
+                    "X-GitHub-Api-Version": "2022-11-28",
+                },
+                output = submodule_info_path,
+            )
 
-        submodule_info = json.decode(ctx.read(submodule_info_path))
+            submodule_info = json.decode(ctx.read(submodule_info_path))
+
+            # buildifier: disable=print
+            print("Missing submodule_info for submodule %s. Consider adding it: \n%s" % (submodule, submodule_info))
+        else:
+            submodule_info = json.decode(ctx.attr.submodule_info[submodule])
+
         if submodule_info["type"] != "submodule":
             fail("provided submodule path is not a submodule")
 
@@ -81,7 +88,7 @@
         )
         if integrity == "":
             # buildifier: disable=print
-            print("Missing integrity for submodule \"{submodule}\": \"{integrity}\". Consider adding it.".format(
+            print("Missing integrity for submodule {submodule}. Consider adding it:\n\"{submodule}\": \"{integrity}\".".format(
                 submodule = submodule,
                 integrity = download_info.integrity,
             ))
@@ -106,6 +113,13 @@
         default = {},
         doc = "The list of submodules with their integrity as value",
     ),
+    "submodule_info": attr.string_dict(
+        mandatory = False,
+        default = {},
+        doc = """The list of submodules with their GitHub API response as value.
+        This is a workaround until https://github.com/bazelbuild/bazel/issues/24777
+        is implemented to prevent hitting GitHub API limits.""",
+    ),
     "ref": attr.string(
         default = "",
         doc =