Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(442)

Side by Side Diff: third_party/logilab/logilab/astroid/inspector.py

Issue 1920403002: [content/test/gpu] Run pylint check of gpu tests in unittest instead of PRESUBMIT (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Update path to LICENSE.txt of logilab/README.chromium Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 # copyright 2003-2013 LOGILAB S.A. (Paris, FRANCE), all rights reserved.
2 # contact http://www.logilab.fr/ -- mailto:contact@logilab.fr
3 #
4 # This file is part of astroid.
5 #
6 # astroid is free software: you can redistribute it and/or modify it
7 # under the terms of the GNU Lesser General Public License as published by the
8 # Free Software Foundation, either version 2.1 of the License, or (at your
9 # option) any later version.
10 #
11 # astroid is distributed in the hope that it will be useful, but
12 # WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 # FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
14 # for more details.
15 #
16 # You should have received a copy of the GNU Lesser General Public License along
17 # with astroid. If not, see <http://www.gnu.org/licenses/>.
18 """visitor doing some postprocessing on the astroid tree.
19 Try to resolve definitions (namespace) dictionary, relationship...
20
21 This module has been imported from pyreverse
22 """
23
24 __docformat__ = "restructuredtext en"
25
26 from os.path import dirname
27
28 import astroid
29 from astroid.exceptions import InferenceError
30 from astroid.utils import LocalsVisitor
31 from astroid.modutils import get_module_part, is_relative, is_standard_module
32
33 class IdGeneratorMixIn(object):
34 """
35 Mixin adding the ability to generate integer uid
36 """
37 def __init__(self, start_value=0):
38 self.id_count = start_value
39
40 def init_counter(self, start_value=0):
41 """init the id counter
42 """
43 self.id_count = start_value
44
45 def generate_id(self):
46 """generate a new identifier
47 """
48 self.id_count += 1
49 return self.id_count
50
51
52 class Linker(IdGeneratorMixIn, LocalsVisitor):
53 """
54 walk on the project tree and resolve relationships.
55
56 According to options the following attributes may be added to visited nodes:
57
58 * uid,
59 a unique identifier for the node (on astroid.Project, astroid.Module,
60 astroid.Class and astroid.locals_type). Only if the linker has been instan tiated
61 with tag=True parameter (False by default).
62
63 * Function
64 a mapping from locals names to their bounded value, which may be a
65 constant like a string or an integer, or an astroid node (on astroid.Modul e,
66 astroid.Class and astroid.Function).
67
68 * instance_attrs_type
69 as locals_type but for klass member attributes (only on astroid.Class)
70
71 * implements,
72 list of implemented interface _objects_ (only on astroid.Class nodes)
73 """
74
75 def __init__(self, project, inherited_interfaces=0, tag=False):
76 IdGeneratorMixIn.__init__(self)
77 LocalsVisitor.__init__(self)
78 # take inherited interface in consideration or not
79 self.inherited_interfaces = inherited_interfaces
80 # tag nodes or not
81 self.tag = tag
82 # visited project
83 self.project = project
84
85
86 def visit_project(self, node):
87 """visit an astroid.Project node
88
89 * optionally tag the node with a unique id
90 """
91 if self.tag:
92 node.uid = self.generate_id()
93 for module in node.modules:
94 self.visit(module)
95
96 def visit_package(self, node):
97 """visit an astroid.Package node
98
99 * optionally tag the node with a unique id
100 """
101 if self.tag:
102 node.uid = self.generate_id()
103 for subelmt in node.values():
104 self.visit(subelmt)
105
106 def visit_module(self, node):
107 """visit an astroid.Module node
108
109 * set the locals_type mapping
110 * set the depends mapping
111 * optionally tag the node with a unique id
112 """
113 if hasattr(node, 'locals_type'):
114 return
115 node.locals_type = {}
116 node.depends = []
117 if self.tag:
118 node.uid = self.generate_id()
119
120 def visit_class(self, node):
121 """visit an astroid.Class node
122
123 * set the locals_type and instance_attrs_type mappings
124 * set the implements list and build it
125 * optionally tag the node with a unique id
126 """
127 if hasattr(node, 'locals_type'):
128 return
129 node.locals_type = {}
130 if self.tag:
131 node.uid = self.generate_id()
132 # resolve ancestors
133 for baseobj in node.ancestors(recurs=False):
134 specializations = getattr(baseobj, 'specializations', [])
135 specializations.append(node)
136 baseobj.specializations = specializations
137 # resolve instance attributes
138 node.instance_attrs_type = {}
139 for assattrs in node.instance_attrs.values():
140 for assattr in assattrs:
141 self.handle_assattr_type(assattr, node)
142 # resolve implemented interface
143 try:
144 node.implements = list(node.interfaces(self.inherited_interfaces))
145 except InferenceError:
146 node.implements = ()
147
148 def visit_function(self, node):
149 """visit an astroid.Function node
150
151 * set the locals_type mapping
152 * optionally tag the node with a unique id
153 """
154 if hasattr(node, 'locals_type'):
155 return
156 node.locals_type = {}
157 if self.tag:
158 node.uid = self.generate_id()
159
160 link_project = visit_project
161 link_module = visit_module
162 link_class = visit_class
163 link_function = visit_function
164
165 def visit_assname(self, node):
166 """visit an astroid.AssName node
167
168 handle locals_type
169 """
170 # avoid double parsing done by different Linkers.visit
171 # running over the same project:
172 if hasattr(node, '_handled'):
173 return
174 node._handled = True
175 if node.name in node.frame():
176 frame = node.frame()
177 else:
178 # the name has been defined as 'global' in the frame and belongs
179 # there. Btw the frame is not yet visited as the name is in the
180 # root locals; the frame hence has no locals_type attribute
181 frame = node.root()
182 try:
183 values = node.infered()
184 try:
185 already_infered = frame.locals_type[node.name]
186 for valnode in values:
187 if not valnode in already_infered:
188 already_infered.append(valnode)
189 except KeyError:
190 frame.locals_type[node.name] = values
191 except astroid.InferenceError:
192 pass
193
194 def handle_assattr_type(self, node, parent):
195 """handle an astroid.AssAttr node
196
197 handle instance_attrs_type
198 """
199 try:
200 values = list(node.infer())
201 try:
202 already_infered = parent.instance_attrs_type[node.attrname]
203 for valnode in values:
204 if not valnode in already_infered:
205 already_infered.append(valnode)
206 except KeyError:
207 parent.instance_attrs_type[node.attrname] = values
208 except astroid.InferenceError:
209 pass
210
211 def visit_import(self, node):
212 """visit an astroid.Import node
213
214 resolve module dependencies
215 """
216 context_file = node.root().file
217 for name in node.names:
218 relative = is_relative(name[0], context_file)
219 self._imported_module(node, name[0], relative)
220
221
222 def visit_from(self, node):
223 """visit an astroid.From node
224
225 resolve module dependencies
226 """
227 basename = node.modname
228 context_file = node.root().file
229 if context_file is not None:
230 relative = is_relative(basename, context_file)
231 else:
232 relative = False
233 for name in node.names:
234 if name[0] == '*':
235 continue
236 # analyze dependencies
237 fullname = '%s.%s' % (basename, name[0])
238 if fullname.find('.') > -1:
239 try:
240 # XXX: don't use get_module_part, missing package precedence
241 fullname = get_module_part(fullname, context_file)
242 except ImportError:
243 continue
244 if fullname != basename:
245 self._imported_module(node, fullname, relative)
246
247
248 def compute_module(self, context_name, mod_path):
249 """return true if the module should be added to dependencies"""
250 package_dir = dirname(self.project.path)
251 if context_name == mod_path:
252 return 0
253 elif is_standard_module(mod_path, (package_dir,)):
254 return 1
255 return 0
256
257 # protected methods ########################################################
258
259 def _imported_module(self, node, mod_path, relative):
260 """notify an imported module, used to analyze dependencies
261 """
262 module = node.root()
263 context_name = module.name
264 if relative:
265 mod_path = '%s.%s' % ('.'.join(context_name.split('.')[:-1]),
266 mod_path)
267 if self.compute_module(context_name, mod_path):
268 # handle dependencies
269 if not hasattr(module, 'depends'):
270 module.depends = []
271 mod_paths = module.depends
272 if not mod_path in mod_paths:
273 mod_paths.append(mod_path)
OLDNEW
« no previous file with comments | « third_party/logilab/logilab/astroid/inference.py ('k') | third_party/logilab/logilab/astroid/manager.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698