Skip to content

Commit 5afa65f

Browse files
committed
Add discovery logic for zip archives from the build system
Bug: b/470161243
1 parent acf7464 commit 5afa65f

File tree

3 files changed

+146
-0
lines changed

3 files changed

+146
-0
lines changed

base/cvd/cuttlefish/host/commands/assemble_cvd/android_build/BUILD.bazel

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,3 +28,19 @@ cf_cc_library(
2828
"@fmt",
2929
],
3030
)
31+
32+
cf_cc_library(
33+
name = "find_build_archive",
34+
srcs = ["find_build_archive.cc"],
35+
hdrs = ["find_build_archive.h"],
36+
deps = [
37+
"//cuttlefish/common/libs/utils:files",
38+
"//cuttlefish/common/libs/utils:result",
39+
"//cuttlefish/host/libs/config:build_archive",
40+
"//cuttlefish/host/libs/config:fetcher_config",
41+
"//cuttlefish/host/libs/config:file_source",
42+
"//cuttlefish/host/libs/zip:zip_file",
43+
"//cuttlefish/host/libs/zip/libzip_cc:archive",
44+
"@abseil-cpp//absl/strings",
45+
],
46+
)
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
//
2+
// Copyright (C) 2025 The Android Open Source Project
3+
//
4+
// Licensed under the Apache License, Version 2.0 (the "License");
5+
// you may not use this file except in compliance with the License.
6+
// You may obtain a copy of the License at
7+
//
8+
// http://www.apache.org/licenses/LICENSE-2.0
9+
//
10+
// Unless required by applicable law or agreed to in writing, software
11+
// distributed under the License is distributed on an "AS IS" BASIS,
12+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
// See the License for the specific language governing permissions and
14+
// limitations under the License.
15+
16+
#include "cuttlefish/host/commands/assemble_cvd/android_build/find_build_archive.h"
17+
18+
#include <optional>
19+
#include <string>
20+
#include <string_view>
21+
#include <utility>
22+
#include <vector>
23+
24+
#include "absl/strings/match.h"
25+
26+
#include "cuttlefish/common/libs/utils/files.h"
27+
#include "cuttlefish/common/libs/utils/result.h"
28+
#include "cuttlefish/host/libs/config/build_archive.h"
29+
#include "cuttlefish/host/libs/config/fetcher_config.h"
30+
#include "cuttlefish/host/libs/config/file_source.h"
31+
#include "cuttlefish/host/libs/zip/libzip_cc/archive.h"
32+
#include "cuttlefish/host/libs/zip/zip_file.h"
33+
34+
namespace cuttlefish {
35+
namespace {
36+
37+
bool NameMatches(std::string_view name, std::string_view pattern) {
38+
return absl::EndsWith(name, ".zip") && absl::StrContains(name, pattern);
39+
}
40+
41+
} // namespace
42+
43+
Result<BuildArchive> FindBuildArchive(const FetcherConfig& config,
44+
FileSource source,
45+
std::string_view pattern) {
46+
std::optional<std::string_view> archive_name;
47+
for (const auto& [file_name, cvd_file] : config.get_cvd_files()) {
48+
if (cvd_file.source != source) {
49+
continue;
50+
}
51+
for (std::string_view name :
52+
{cvd_file.archive_source, cvd_file.file_path}) {
53+
if (NameMatches(name, pattern)) {
54+
CF_EXPECTF(!archive_name.has_value() || *archive_name == name,
55+
"Multiple files match '{}': '{}' and '{}'", pattern,
56+
*archive_name, name);
57+
archive_name = name;
58+
}
59+
}
60+
}
61+
CF_EXPECTF(archive_name.has_value(), "No archive found with '{}'", pattern);
62+
return CF_EXPECT(
63+
BuildArchive::FromFetcherConfig(config, source, *archive_name));
64+
}
65+
66+
Result<BuildArchive> FindBuildArchive(const std::string& directory_path,
67+
std::string_view pattern) {
68+
std::vector<std::string> contents =
69+
CF_EXPECT(DirectoryContents(directory_path));
70+
71+
std::optional<std::string_view> archive_name;
72+
for (std::string_view member : contents) {
73+
if (!NameMatches(member, pattern)) {
74+
continue;
75+
}
76+
CF_EXPECTF(!archive_name.has_value(),
77+
"Found two matching files for '{}' in '{}': '{}' and '{}'",
78+
pattern, directory_path, *archive_name, member);
79+
archive_name = member;
80+
}
81+
CF_EXPECTF(archive_name.has_value(), "Could not find file with '{}' in '{}'",
82+
pattern, directory_path);
83+
84+
ReadableZip zip = CF_EXPECT(ZipOpenRead(std::string(*archive_name)));
85+
return CF_EXPECT(BuildArchive::FromZip(std::move(zip)));
86+
}
87+
88+
} // namespace cuttlefish
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
//
2+
// Copyright (C) 2025 The Android Open Source Project
3+
//
4+
// Licensed under the Apache License, Version 2.0 (the "License");
5+
// you may not use this file except in compliance with the License.
6+
// You may obtain a copy of the License at
7+
//
8+
// http://www.apache.org/licenses/LICENSE-2.0
9+
//
10+
// Unless required by applicable law or agreed to in writing, software
11+
// distributed under the License is distributed on an "AS IS" BASIS,
12+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
// See the License for the specific language governing permissions and
14+
// limitations under the License.
15+
16+
#pragma once
17+
18+
#include <string>
19+
#include <string_view>
20+
21+
#include "cuttlefish/common/libs/utils/result.h"
22+
#include "cuttlefish/host/libs/config/build_archive.h"
23+
#include "cuttlefish/host/libs/config/fetcher_config.h"
24+
#include "cuttlefish/host/libs/config/file_source.h"
25+
26+
namespace cuttlefish {
27+
28+
/**
29+
* Scan a `FetcherConfig` for an archive containing the substring `pattern`.
30+
* This could be a zip file still present, or the extracted contents of a zip
31+
* file that was downloaded.
32+
*/
33+
Result<BuildArchive> FindBuildArchive(const FetcherConfig&, FileSource,
34+
std::string_view pattern);
35+
/**
36+
* Scan the contents of `directory_path` to find a file whose name contains
37+
* `pattern` as a substring, and is a zip archive.
38+
*/
39+
Result<BuildArchive> FindBuildArchive(const std::string& directory_path,
40+
std::string_view pattern);
41+
42+
} // namespace cuttlefish

0 commit comments

Comments
 (0)