OLD | NEW |
| (Empty) |
1 #!/usr/bin/env python | |
2 # Copyright (c) 2012 The Chromium Authors. All rights reserved. | |
3 # Use of this source code is governed by a BSD-style license that can be | |
4 # found in the LICENSE file. | |
5 | |
6 '''Tool to determine inputs and outputs of a grit file. | |
7 ''' | |
8 | |
9 import optparse | |
10 import os | |
11 import posixpath | |
12 import sys | |
13 | |
14 from grit import grd_reader | |
15 from grit import util | |
16 | |
17 class WrongNumberOfArguments(Exception): | |
18 pass | |
19 | |
20 | |
21 def Outputs(filename, defines, ids_file, target_platform=None): | |
22 grd = grd_reader.Parse( | |
23 filename, defines=defines, tags_to_ignore=set(['messages']), | |
24 first_ids_file=ids_file, target_platform=target_platform) | |
25 | |
26 target = [] | |
27 lang_folders = {} | |
28 # Add all explicitly-specified output files | |
29 for output in grd.GetOutputFiles(): | |
30 path = output.GetFilename() | |
31 target.append(path) | |
32 | |
33 if path.endswith('.h'): | |
34 path, filename = os.path.split(path) | |
35 if output.attrs['lang']: | |
36 lang_folders[output.attrs['lang']] = os.path.dirname(path) | |
37 | |
38 # Add all generated files, once for each output language. | |
39 for node in grd: | |
40 if node.name == 'structure': | |
41 with node: | |
42 # TODO(joi) Should remove the "if sconsdep is true" thing as it is a | |
43 # hack - see grit/node/structure.py | |
44 if node.HasFileForLanguage() and node.attrs['sconsdep'] == 'true': | |
45 for lang in lang_folders: | |
46 path = node.FileForLanguage(lang, lang_folders[lang], | |
47 create_file=False, | |
48 return_if_not_generated=False) | |
49 if path: | |
50 target.append(path) | |
51 | |
52 return [t.replace('\\', '/') for t in target] | |
53 | |
54 | |
55 def GritSourceFiles(): | |
56 files = [] | |
57 grit_root_dir = os.path.relpath(os.path.dirname(__file__), os.getcwd()) | |
58 for root, dirs, filenames in os.walk(grit_root_dir): | |
59 grit_src = [os.path.join(root, f) for f in filenames | |
60 if f.endswith('.py') and not f.endswith('_unittest.py')] | |
61 files.extend(grit_src) | |
62 return sorted(files) | |
63 | |
64 | |
65 def Inputs(filename, defines, ids_file, target_platform=None): | |
66 grd = grd_reader.Parse( | |
67 filename, debug=False, defines=defines, tags_to_ignore=set(['message']), | |
68 first_ids_file=ids_file, target_platform=target_platform) | |
69 files = set() | |
70 for lang, ctx, fallback in grd.GetConfigurations(): | |
71 # TODO(tdanderson): Refactor all places which perform the action of setting | |
72 # output attributes on the root. See crbug.com/503637. | |
73 grd.SetOutputLanguage(lang or grd.GetSourceLanguage()) | |
74 grd.SetOutputContext(ctx) | |
75 grd.SetFallbackToDefaultLayout(fallback) | |
76 for node in grd.ActiveDescendants(): | |
77 with node: | |
78 if (node.name == 'structure' or node.name == 'skeleton' or | |
79 (node.name == 'file' and node.parent and | |
80 node.parent.name == 'translations')): | |
81 path = node.GetInputPath() | |
82 if path is not None: | |
83 files.add(grd.ToRealPath(path)) | |
84 | |
85 # If it's a flattened node, grab inlined resources too. | |
86 if node.name == 'structure' and node.attrs['flattenhtml'] == 'true': | |
87 node.RunPreSubstitutionGatherer() | |
88 files.update(node.GetHtmlResourceFilenames()) | |
89 elif node.name == 'grit': | |
90 first_ids_file = node.GetFirstIdsFile() | |
91 if first_ids_file: | |
92 files.add(first_ids_file) | |
93 elif node.name == 'include': | |
94 files.add(grd.ToRealPath(node.GetInputPath())) | |
95 # If it's a flattened node, grab inlined resources too. | |
96 if node.attrs['flattenhtml'] == 'true': | |
97 files.update(node.GetHtmlResourceFilenames()) | |
98 elif node.name == 'part': | |
99 files.add(util.normpath(os.path.join(os.path.dirname(filename), | |
100 node.GetInputPath()))) | |
101 | |
102 cwd = os.getcwd() | |
103 return [os.path.relpath(f, cwd) for f in sorted(files)] | |
104 | |
105 | |
106 def PrintUsage(): | |
107 print 'USAGE: ./grit_info.py --inputs [-D foo] [-f resource_ids] <grd-file>' | |
108 print (' ./grit_info.py --outputs [-D foo] [-f resource_ids] ' + | |
109 '<out-prefix> <grd-file>') | |
110 | |
111 | |
112 def DoMain(argv): | |
113 parser = optparse.OptionParser() | |
114 parser.add_option("--inputs", action="store_true", dest="inputs") | |
115 parser.add_option("--outputs", action="store_true", dest="outputs") | |
116 parser.add_option("-D", action="append", dest="defines", default=[]) | |
117 # grit build also supports '-E KEY=VALUE', support that to share command | |
118 # line flags. | |
119 parser.add_option("-E", action="append", dest="build_env", default=[]) | |
120 parser.add_option("-w", action="append", dest="whitelist_files", default=[]) | |
121 parser.add_option("--output-all-resource-defines", action="store_true", | |
122 dest="output_all_resource_defines", default=True, | |
123 help="Unused") | |
124 parser.add_option("--no-output-all-resource-defines", action="store_false", | |
125 dest="output_all_resource_defines", default=True, | |
126 help="Unused") | |
127 parser.add_option("-f", dest="ids_file", | |
128 default="GRIT_DIR/../gritsettings/resource_ids") | |
129 parser.add_option("-t", dest="target_platform", default=None) | |
130 | |
131 options, args = parser.parse_args(argv) | |
132 | |
133 defines = {} | |
134 for define in options.defines: | |
135 name, val = util.ParseDefine(define) | |
136 defines[name] = val | |
137 | |
138 for env_pair in options.build_env: | |
139 (env_name, env_value) = env_pair.split('=', 1) | |
140 os.environ[env_name] = env_value | |
141 | |
142 if options.inputs: | |
143 if len(args) > 1: | |
144 raise WrongNumberOfArguments("Expected 0 or 1 arguments for --inputs.") | |
145 | |
146 inputs = [] | |
147 if len(args) == 1: | |
148 filename = args[0] | |
149 inputs = Inputs(filename, defines, options.ids_file, | |
150 options.target_platform) | |
151 | |
152 # Add in the grit source files. If one of these change, we want to re-run | |
153 # grit. | |
154 inputs.extend(GritSourceFiles()) | |
155 inputs = [f.replace('\\', '/') for f in inputs] | |
156 | |
157 if len(args) == 1: | |
158 # Include grd file as second input (works around gyp expecting it). | |
159 inputs.insert(1, args[0]) | |
160 if options.whitelist_files: | |
161 inputs.extend(options.whitelist_files) | |
162 return '\n'.join(inputs) | |
163 elif options.outputs: | |
164 if len(args) != 2: | |
165 raise WrongNumberOfArguments( | |
166 "Expected exactly 2 arguments for --outputs.") | |
167 | |
168 prefix, filename = args | |
169 outputs = [posixpath.join(prefix, f) | |
170 for f in Outputs(filename, defines, | |
171 options.ids_file, options.target_platform)] | |
172 return '\n'.join(outputs) | |
173 else: | |
174 raise WrongNumberOfArguments("Expected --inputs or --outputs.") | |
175 | |
176 | |
177 def main(argv): | |
178 if sys.version_info < (2, 6): | |
179 print "GRIT requires Python 2.6 or later." | |
180 return 1 | |
181 | |
182 try: | |
183 result = DoMain(argv[1:]) | |
184 except WrongNumberOfArguments, e: | |
185 PrintUsage() | |
186 print e | |
187 return 1 | |
188 print result | |
189 return 0 | |
190 | |
191 | |
192 if __name__ == '__main__': | |
193 sys.exit(main(sys.argv)) | |
OLD | NEW |