AAPT2: add flag for forcing visibility level
Test: manual
Bug: 72735798
Change-Id: I29480e66384dd2da27e17ab454ac1fe8a033ee3e
diff --git a/tools/aapt2/ResourceParser.cpp b/tools/aapt2/ResourceParser.cpp
index 1b6f882..2260ba4 100644
--- a/tools/aapt2/ResourceParser.cpp
+++ b/tools/aapt2/ResourceParser.cpp
@@ -447,6 +447,9 @@
parsed_resource.config = config_;
parsed_resource.source = source_.WithLine(parser->line_number());
parsed_resource.comment = std::move(comment);
+ if (options_.visibility) {
+ parsed_resource.visibility_level = options_.visibility.value();
+ }
// Extract the product name if it exists.
if (Maybe<StringPiece> maybe_product = xml::FindNonEmptyAttribute(parser, "product")) {
@@ -811,6 +814,12 @@
}
bool ResourceParser::ParsePublic(xml::XmlPullParser* parser, ParsedResource* out_resource) {
+ if (options_.visibility) {
+ diag_->Error(DiagMessage(out_resource->source)
+ << "<public> tag not allowed with --visibility flag");
+ return false;
+ }
+
if (out_resource->config != ConfigDescription::DefaultConfig()) {
diag_->Warn(DiagMessage(out_resource->source)
<< "ignoring configuration '" << out_resource->config << "' for <public> tag");
@@ -853,6 +862,12 @@
}
bool ResourceParser::ParsePublicGroup(xml::XmlPullParser* parser, ParsedResource* out_resource) {
+ if (options_.visibility) {
+ diag_->Error(DiagMessage(out_resource->source)
+ << "<public-group> tag not allowed with --visibility flag");
+ return false;
+ }
+
if (out_resource->config != ConfigDescription::DefaultConfig()) {
diag_->Warn(DiagMessage(out_resource->source)
<< "ignoring configuration '" << out_resource->config
@@ -974,6 +989,11 @@
}
bool ResourceParser::ParseSymbol(xml::XmlPullParser* parser, ParsedResource* out_resource) {
+ if (options_.visibility) {
+ diag_->Error(DiagMessage(out_resource->source)
+ << "<java-symbol> and <symbol> tags not allowed with --visibility flag");
+ return false;
+ }
if (out_resource->config != ConfigDescription::DefaultConfig()) {
diag_->Warn(DiagMessage(out_resource->source)
<< "ignoring configuration '" << out_resource->config << "' for <"
@@ -1045,6 +1065,9 @@
child_resource.name.entry = maybe_name.value().to_string();
child_resource.source = item_source;
child_resource.overlayable = true;
+ if (options_.visibility) {
+ child_resource.visibility_level = options_.visibility.value();
+ }
out_resource->child_resources.push_back(std::move(child_resource));
xml::XmlPullParser::SkipCurrentElement(parser);
@@ -1187,6 +1210,9 @@
child_resource.name = symbol.symbol.name.value();
child_resource.source = item_source;
child_resource.value = util::make_unique<Id>();
+ if (options_.visibility) {
+ child_resource.visibility_level = options_.visibility.value();
+ }
out_resource->child_resources.push_back(std::move(child_resource));
symbol.symbol.SetComment(std::move(comment));
@@ -1564,6 +1590,9 @@
child_resource.name = child_ref.name.value();
child_resource.source = item_source;
child_resource.comment = std::move(comment);
+ if (options_.visibility) {
+ child_resource.visibility_level = options_.visibility.value();
+ }
if (!ParseAttrImpl(parser, &child_resource, true)) {
error = true;
diff --git a/tools/aapt2/ResourceParser.h b/tools/aapt2/ResourceParser.h
index fb9dbd0..68130c2 100644
--- a/tools/aapt2/ResourceParser.h
+++ b/tools/aapt2/ResourceParser.h
@@ -45,6 +45,10 @@
* warnings.
*/
bool error_on_positional_arguments = true;
+
+ // If visibility was forced, we need to use it when creating a new resource and also error if we
+ // try to parse the <public>, <public-group>, <java-symbol> or <symbol> tags.
+ Maybe<Visibility::Level> visibility;
};
/*
diff --git a/tools/aapt2/cmd/Compile.cpp b/tools/aapt2/cmd/Compile.cpp
index 06e84ef..6ba9d44 100644
--- a/tools/aapt2/cmd/Compile.cpp
+++ b/tools/aapt2/cmd/Compile.cpp
@@ -114,6 +114,7 @@
std::string output_path;
Maybe<std::string> res_dir;
Maybe<std::string> generate_text_symbols_path;
+ Maybe<Visibility::Level> visibility;
bool pseudolocalize = false;
bool no_png_crunch = false;
bool legacy_mode = false;
@@ -216,6 +217,10 @@
// If the filename includes donottranslate, then the default translatable is false.
parser_options.translatable = path_data.name.find("donottranslate") == std::string::npos;
+ // If visibility was forced, we need to use it when creating a new resource and also error if
+ // we try to parse the <public>, <public-group>, <java-symbol> or <symbol> tags.
+ parser_options.visibility = options.visibility;
+
ResourceParser res_parser(context->GetDiagnostics(), &table, path_data.source, path_data.config,
parser_options);
if (!res_parser.Parse(&xml_parser)) {
@@ -309,6 +314,8 @@
if (!entry->values.empty()) {
auto styleable = static_cast<const Styleable*>(entry->values.front()->value.get());
for (const auto& attr : styleable->entries) {
+ // The visibility of the children under the styleable does not matter as they are
+ // nested under their parent and use its visibility.
r_txt_printer.Print("default int styleable ");
r_txt_printer.Print(entry->name);
r_txt_printer.Print("_");
@@ -694,6 +701,7 @@
CompileOptions options;
bool verbose = false;
+ Maybe<std::string> visibility;
Flags flags =
Flags()
.RequiredFlag("-o", "Output path", &options.output_path)
@@ -709,13 +717,32 @@
.OptionalSwitch("--no-crunch", "Disables PNG processing", &options.no_png_crunch)
.OptionalSwitch("--legacy", "Treat errors that used to be valid in AAPT as warnings",
&options.legacy_mode)
- .OptionalSwitch("-v", "Enables verbose logging", &verbose);
+ .OptionalSwitch("-v", "Enables verbose logging", &verbose)
+ .OptionalFlag("--visibility",
+ "Sets the visibility of the compiled resources to the specified\n"
+ "level. Accepted levels: public, private, default",
+ &visibility);
if (!flags.Parse("aapt2 compile", args, &std::cerr)) {
return 1;
}
context.SetVerbose(verbose);
+ if (visibility) {
+ if (visibility.value() == "public") {
+ options.visibility = Visibility::Level::kPublic;
+ } else if (visibility.value() == "private") {
+ options.visibility = Visibility::Level::kPrivate;
+ } else if (visibility.value() == "default") {
+ options.visibility = Visibility::Level::kUndefined;
+ } else {
+ context.GetDiagnostics()->Error(
+ DiagMessage() << "Unrecognized visibility level passes to --visibility: '"
+ << visibility.value() << "'. Accepted levels: public, private, default");
+ return 1;
+ }
+ }
+
std::unique_ptr<IArchiveWriter> archive_writer;
std::vector<ResourcePathData> input_data;