summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/buildtool/computed_roots/TARGETS1
-rw-r--r--src/buildtool/computed_roots/evaluate.cpp82
2 files changed, 83 insertions, 0 deletions
diff --git a/src/buildtool/computed_roots/TARGETS b/src/buildtool/computed_roots/TARGETS
index 3d16e831..fa216d22 100644
--- a/src/buildtool/computed_roots/TARGETS
+++ b/src/buildtool/computed_roots/TARGETS
@@ -78,6 +78,7 @@
, ["src/buildtool/crypto", "hash_function"]
, ["src/buildtool/execution_api/common", "api_bundle"]
, ["src/buildtool/execution_api/common", "common"]
+ , ["src/buildtool/execution_api/serve", "mr_git_api"]
, ["src/buildtool/execution_api/utils", "rehash_utils"]
, ["src/buildtool/file_system", "file_root"]
, ["src/buildtool/file_system", "file_system_manager"]
diff --git a/src/buildtool/computed_roots/evaluate.cpp b/src/buildtool/computed_roots/evaluate.cpp
index 466b2536..c046297f 100644
--- a/src/buildtool/computed_roots/evaluate.cpp
+++ b/src/buildtool/computed_roots/evaluate.cpp
@@ -46,6 +46,7 @@
#include "src/buildtool/crypto/hash_function.hpp"
#include "src/buildtool/execution_api/common/api_bundle.hpp"
#include "src/buildtool/execution_api/common/execution_api.hpp"
+#include "src/buildtool/execution_api/serve/mr_git_api.hpp"
#include "src/buildtool/execution_api/utils/rehash_utils.hpp"
#include "src/buildtool/file_system/file_root.hpp"
#include "src/buildtool/file_system/file_system_manager.hpp"
@@ -87,6 +88,13 @@ void AddDescriptionIfPrecomputed(
StorageConfig const& native_storage_config)
-> expected<ArtifactDigest, std::string>;
+[[nodiscard]] auto UploadToServe(ServeApi const& serve,
+ ApiBundle const& serve_apis,
+ StorageConfig const& serve_storage_config,
+ ArtifactDigest const& digest,
+ std::filesystem::path const& repo_path)
+ -> expected<ArtifactDigest, std::string>;
+
// Traverse, starting from a given repository, in order to find the
// computed roots it depends on.
void TraverseRepoForComputedRoots(
@@ -770,4 +778,78 @@ namespace {
return rehashed->front().digest;
}
+[[nodiscard]] auto UploadToServe(ServeApi const& serve,
+ ApiBundle const& serve_apis,
+ StorageConfig const& serve_storage_config,
+ ArtifactDigest const& digest,
+ std::filesystem::path const& repo_path)
+ -> expected<ArtifactDigest, std::string> {
+ RepositoryConfig repo;
+ if (not repo.SetGitCAS(repo_path)) {
+ return unexpected{
+ fmt::format("Failed to SetGitCAS at {}", repo_path.string())};
+ }
+
+ bool const with_rehashing = not ProtocolTraits::IsNative(
+ serve_storage_config.hash_function.GetType());
+
+ // Create a native storage config if rehashing is needed:
+ std::optional<StorageConfig> native_storage_config;
+ if (with_rehashing) {
+ auto config = StorageConfig::Builder::Rebuild(serve_storage_config)
+ .SetHashType(HashFunction::Type::GitSHA1)
+ .Build();
+ if (not config.has_value()) {
+ return unexpected{
+ fmt::format("Failed to rebuild storage for rehashing: {}",
+ std::move(config).error())};
+ }
+ native_storage_config.emplace(*config);
+ }
+
+ std::shared_ptr<IExecutionApi> git_api;
+ if (with_rehashing) {
+ git_api = std::make_shared<MRGitApi>(&repo,
+ &*native_storage_config,
+ &serve_storage_config,
+ &*serve_apis.local);
+ }
+ else {
+ git_api = std::make_shared<MRGitApi>(&repo, &serve_storage_config);
+ }
+
+ if (not git_api->RetrieveToCas(
+ {Artifact::ObjectInfo{digest, ObjectType::Tree}},
+ *serve_apis.remote)) {
+ return unexpected{
+ fmt::format("Failed to sync tree {} from repository {}",
+ digest.hash(),
+ repo_path.string())};
+ }
+
+ ArtifactDigest result = digest;
+ if (with_rehashing) {
+ auto rehashed = RehashUtils::ReadRehashedDigest(digest,
+ *native_storage_config,
+ serve_storage_config,
+ /*from_git=*/true);
+ if (not rehashed.has_value()) {
+ return unexpected{fmt::format("Failed to rehash {}:\n{}",
+ digest.hash(),
+ std::move(rehashed).error())};
+ }
+ if (not rehashed.value().has_value()) {
+ return unexpected{fmt::format(
+ "No digest provided to sync root tree {}.", digest.hash())};
+ }
+ result = rehashed.value()->digest;
+ }
+
+ if (not serve.GetTreeFromRemote(result)) {
+ return unexpected{fmt::format(
+ "Serve endpoint failed to sync root tree {}.", result.hash())};
+ }
+ return result;
+}
+
} // namespace