-
Notifications
You must be signed in to change notification settings - Fork 14
/
Copy pathmove_strings_for_packing.py
executable file
·175 lines (140 loc) · 5.59 KB
/
move_strings_for_packing.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
#!/usr/bin/env python3
# Copyright (c) Facebook, Inc. and its affiliates. All rights reserved.
#
# This source code is licensed under the Apache 2.0 license found in
# the LICENSE file in the root directory of this source tree.
import argparse
import glob
import logging
import os
import re
import string_pack_config
from id_finder import IdFinder
from string_pack_config import LanguageHandlingCase
HEADER = """<?xml version="1.0" encoding="utf-8"?>
<!-- \u0040generated by StringPacks move_strings_for_packing.py script. -->
"""
RESOURCES_HEADER = "<resources>\n"
FOOTER = "</resources>\n"
# fmt: off
ROW_PATTERN = re.compile(
"(?:[ \t]*<!-- .*? -->\n)?"
"[ \t]*<(string|plurals) name=\"(.+?)\">"
".*?"
"</\\1>\n",
re.DOTALL,
)
# fmt: on
def get_resource_content_with_resources_header(resource_file_path):
with open(resource_file_path, "rt") as resource_file:
# skip headers
resources_header = None
for line in resource_file:
if "<resources" in line:
resources_header = line
break
return resources_header, resource_file.read()
def move_strings(srcfile, dstfile, id_finder, keep_dest):
output_for_original_file = []
output_for_new_file = []
logging.debug("Reading xml file: %s", srcfile)
src_resources_header, data = get_resource_content_with_resources_header(srcfile)
if src_resources_header is None:
src_resources_header = RESOURCES_HEADER
for match in ROW_PATTERN.finditer(data):
piece = match.group(0)
if id_finder.get_id(match.group(2)) is not None:
output_for_new_file.append(piece)
else:
output_for_original_file.append(piece)
if keep_dest:
try:
dst_resources_header, data = get_resource_content_with_resources_header(
dstfile
)
for match in ROW_PATTERN.finditer(data):
piece = match.group(0)
output_for_new_file.append(piece)
except FileNotFoundError:
# The output file doesn't exist. It's OK.
pass
with open(srcfile, "wt") as xml_file:
logging.debug("Updating: %s", srcfile)
xml_file.write(HEADER)
# Keeping the <resources> tag and its contents as is in original strings.xml file
xml_file.write(src_resources_header)
xml_file.write("".join(output_for_original_file))
xml_file.write(FOOTER)
if not output_for_new_file:
logging.debug("No strings to write out")
# There's no strings to write
return
# Create a directory for dstfile, in case it doesn't exist
os.makedirs(os.path.dirname(dstfile), exist_ok=True)
with open(dstfile, "wt") as xml_file:
logging.debug("Writing out: %s", dstfile)
xml_file.write(HEADER)
# Using the basic <resources> tag in stringpacks strings.xml file
xml_file.write(RESOURCES_HEADER)
xml_file.write("".join(output_for_new_file))
xml_file.write(FOOTER)
def get_dest_file(
moved_resource_directory, language_qualifier, destination_stringpack_directories_map
):
if moved_resource_directory in destination_stringpack_directories_map:
stringpack_root_dir = destination_stringpack_directories_map[
moved_resource_directory
]
else:
stringpack_root_dir = moved_resource_directory
dest_file = os.path.join(
stringpack_root_dir,
"string-packs",
"strings",
"values-" + language_qualifier,
"strings.xml",
)
logging.debug("To file: %s", dest_file)
return dest_file
# Escape code for color
SET_WARNING_COLOR = "\033[33m\033[41m" # yellow text with red background
CLEAR_COLOR = "\033[0m"
def move_all_strings(sp_config, keep_dest):
id_finder = IdFinder.from_stringpack_config(sp_config)
for resources_directory in sp_config.original_resources_directories:
path_pattern = os.path.join(
resources_directory, "res", "values-*", "strings.xml"
)
for string_xml_path in glob.glob(path_pattern):
values_directory_name = os.path.normpath(string_xml_path).split(os.sep)[-2]
resource_qualifier = values_directory_name.replace("values-", "")
handler_case = sp_config.get_handling_case(resource_qualifier)
if handler_case == LanguageHandlingCase.DROP:
logging.warning(
SET_WARNING_COLOR + "Dropping: " + string_xml_path + CLEAR_COLOR
)
move_strings(string_xml_path, os.devnull, id_finder, keep_dest=False)
elif handler_case == LanguageHandlingCase.PACK:
logging.debug("Moving: %s", string_xml_path)
move_strings(
string_xml_path,
get_dest_file(
resources_directory,
resource_qualifier,
sp_config.destination_stringpack_directories,
),
id_finder,
keep_dest,
)
elif handler_case == LanguageHandlingCase.KEEP_ORIGINAL:
logging.info("Keep untouched: %s", string_xml_path)
def main():
logging.basicConfig(level=logging.INFO)
arg_parser = argparse.ArgumentParser()
arg_parser.add_argument("--config", help="Location of JSON config file.")
arg_parser.add_argument("--keep-dest", action="store_true")
args = arg_parser.parse_args()
sp_config = string_pack_config.load_config(config_json_file_path=args.config)
move_all_strings(sp_config, args.keep_dest)
if __name__ == "__main__":
main()