Gentoo Archives: gentoo-commits

From: "André Erdmann" <dywi@×××××××.de>
To: gentoo-commits@l.g.o
Subject: [gentoo-commits] proj/R_overlay:master commit in: roverlay/depres/simpledeprule/, roverlay/depres/
Date: Mon, 02 Sep 2013 16:21:18
Message-Id: 1378138779.92289de61ffeb2cf33954d12f7fbc615111ed604.dywi@gentoo
1 commit: 92289de61ffeb2cf33954d12f7fbc615111ed604
2 Author: André Erdmann <dywi <AT> mailerd <DOT> de>
3 AuthorDate: Mon Sep 2 16:19:39 2013 +0000
4 Commit: André Erdmann <dywi <AT> mailerd <DOT> de>
5 CommitDate: Mon Sep 2 16:19:39 2013 +0000
6 URL: http://git.overlays.gentoo.org/gitweb/?p=proj/R_overlay.git;a=commit;h=92289de6
7
8 dynamic selfdep pool: try repo-specific match first
9
10 Try to resolve selfdeps within a repo first, before trying to get a match in any
11 repo.
12
13 ---
14 roverlay/depres/depenv.py | 4 +
15 roverlay/depres/deprule.py | 237 +++++++++++++++++++++----------
16 roverlay/depres/simpledeprule/dynpool.py | 52 +++++--
17 3 files changed, 210 insertions(+), 83 deletions(-)
18
19 diff --git a/roverlay/depres/depenv.py b/roverlay/depres/depenv.py
20 index 2e6417e..b20e0b5 100644
21 --- a/roverlay/depres/depenv.py
22 +++ b/roverlay/depres/depenv.py
23 @@ -176,8 +176,12 @@ class DepEnv ( object ):
24 self.package_ref = package_ref
25 if package_ref is not None:
26 self.get_package_info = self._deref_package_info
27 + self.repo_id = (
28 + package_ref.deref_safe().get ( 'origin' ).get_identifier()
29 + )
30 else:
31 self.get_package_info = self._deref_none
32 + self.repo_id = None
33
34
35 self.dep_str = dep_str
36
37 diff --git a/roverlay/depres/deprule.py b/roverlay/depres/deprule.py
38 index 800d2af..66a43f2 100644
39 --- a/roverlay/depres/deprule.py
40 +++ b/roverlay/depres/deprule.py
41 @@ -8,6 +8,8 @@
42
43 __all__ = [ 'DependencyRule', 'DependencyRulePool', ]
44
45 +import roverlay.util.objects
46 +
47 import roverlay.depres.depresult
48
49 from roverlay.depres import deptype
50 @@ -47,26 +49,16 @@ class DependencyRule ( object ):
51 # --- end of DependencyRule ---
52
53
54 -class DependencyRulePool ( object ):
55 -
56 - def __init__ ( self, name, priority, deptype_mask, initial_rules=None ):
57 - """Initializes an DependencyRulePool, which basically is a set of
58 - dependency rules with methods like "search for x in all rules."
59 +class DependencyRulePoolBase ( object ):
60 + """Base object for dependency rule pools."""
61
62 - arguments:
63 - * name -- name of this rule pool
64 - * priority -- priority of this pool (lower is better)
65 - """
66 - super ( DependencyRulePool, self ).__init__()
67 - if initial_rules is None:
68 - self.rules = list()
69 - else:
70 - self.rules = list ( initial_rules )
71 - self._rule_add = self.rules.append
72 - self.name = name
73 - self.priority = priority
74 + def __init__ ( self, name, priority, deptype_mask ):
75 + super ( DependencyRulePoolBase, self ).__init__()
76 + self.name = name
77 + self.priority = priority
78 # filter out deptype flags like "mandatory"
79 self.deptype_mask = deptype_mask & deptype.RESOLVE_ALL
80 +
81 # the "rule weight" is the sum of the rules' priorities
82 # it's used to compare/sort dependency pools with
83 # the same priority (lesser weight is better)
84 @@ -75,56 +67,50 @@ class DependencyRulePool ( object ):
85
86 def empty ( self ):
87 """Returns True if this pool has no rules."""
88 - return len ( self.rules ) == 0
89 + for rule in self.iter_rules():
90 + return False
91 + return True
92 # --- end of empty (...) ---
93
94 + @roverlay.util.objects.abstractmethod
95 + def sort_rules ( self ):
96 + pass
97 + # --- end of sort_rules (...) ---
98 +
99 def sort ( self ):
100 """Sorts this rule pool and determines its weight which is used
101 to compare rule pools.
102 """
103 -
104 - self.rules.sort ( key=lambda rule : rule.priority )
105 -
106 - rule_priority_sum = 0
107 - for r in self.rules: rule_priority_sum += r.priority
108 - self.rule_weight = rule_priority_sum
109 -
110 - return None
111 + self.sort_rules()
112 + self.set_rule_weight()
113 # --- end of sort (...) ---
114
115 - def accepts_mask ( self, deptype_mask ):
116 - """Returns True if this pool accepts the given deptype_mask."""
117 - return bool ( self.deptype_mask & deptype_mask )
118 - # --- end of accepts_mask (...) ---
119 -
120 - def accepts ( self, dep_env ):
121 - """Returns True if this pool accepts the given dep env."""
122 - return bool ( self.deptype_mask & dep_env.deptype_mask )
123 - # --- end of accepts (...) ---
124 -
125 - def accepts_other ( self, dep_env ):
126 - """Returns True if this pool can be used to resolve a dep env whose
127 - deptype mask is rejected by this pool.
128 - (Not necessarily the inverse of accepts().)
129 - """
130 - return not self.accepts ( dep_env )
131 - # --- end of accepts_other (...) ---
132 + @roverlay.util.objects.abstractmethod
133 + def iter_rules ( self ):
134 + return
135 + # --- end of iter_rules (...) ---
136
137 - def add ( self, rule ):
138 - """Adds a DependencyRule to this rule pool.
139 + @roverlay.util.objects.abstractmethod ( params=[ 'dep_env' ] )
140 + def iter_rules_resolving ( self, dep_env ):
141 + pass
142 + # --- end of iter_rules_resolving (...) ---
143
144 - arguments:
145 - * rule --
146 - """
147 - if issubclass ( rule, DependencyRule ):
148 - self._rule_add ( rule )
149 - else:
150 - raise Exception ( "bad usage (dependency rule expected)." )
151 + def get_all_matches ( self, dep_env ):
152 + for rule in self.iter_rules_resolving ( dep_env ):
153 + result = rule.matches ( dep_env )
154 + if result:
155 + yield result
156 + # --- end of get_all_matches (...) ---
157
158 + def matches ( self, dep_env ):
159 + for rule in self.iter_rules_resolving ( dep_env ):
160 + result = rule.matches ( dep_env )
161 + if result:
162 + return result
163 return None
164 - # --- end of add (...) ---
165 + # --- end of matches (...) ---
166
167 - def matches ( self, dep_env, skip_matches=0 ):
168 + def matches_all ( self, dep_env, skip_matches=0 ):
169 """Tries to find a match in this dependency rule pool.
170 The first match is immediatly returned unless skip_matches is != 0, in
171 which case the first (>0) / last (<0) skip_matches matches are skipped.
172 @@ -141,35 +127,55 @@ class DependencyRulePool ( object ):
173 # cannot expect a result in this case - abort now
174 pass
175
176 - elif skip_matches == 0:
177 - for rule in self.rules:
178 - result = rule.matches ( dep_env )
179 - if result:
180 - return result
181 - else:
182 + elif skip_matches >= 0:
183 skipped = 0
184 - # python3 requires list ( range ... )
185 - order = list ( range ( len ( self.rules ) ) )
186 -
187 - if skip_matches < 0:
188 - skip_matches *= -1
189 - order.reverse()
190 + for result in self.get_all_matches ( dep_env ):
191 + if skipped < skip_matches:
192 + skipped += 1
193 + else:
194 + return result
195
196 - for index in order:
197 - result = self.rules [index].matches ( dep_env )
198 - if result:
199 - if skipped < skip_matches:
200 - skipped += 1
201 - else:
202 - return result
203 + else:
204 + matches = list ( self.get_all_matches() )
205 + try:
206 + return matches [skip_matches]
207 + except IndexError:
208 + pass
209
210 # default return
211 return None
212 - # --- end of matches (...) ---
213 + # --- end of matches_all (...) ---
214 +
215 + def set_rule_weight ( self ):
216 + priosum = 0
217 + for rule in self.iter_rules():
218 + priosum += rule.priority
219 + self.rule_weight = priosum
220 + return self.rule_weight
221 + # --- end of set_rule_weight (...) ---
222 +
223 + def accepts_mask ( self, deptype_mask ):
224 + """Returns True if this pool accepts the given deptype_mask."""
225 + return bool ( self.deptype_mask & deptype_mask )
226 + # --- end of accepts_mask (...) ---
227 +
228 + def accepts ( self, dep_env ):
229 + """Returns True if this pool accepts the given dep env."""
230 + return bool ( self.deptype_mask & dep_env.deptype_mask )
231 + # --- end of accepts (...) ---
232 +
233 + @roverlay.util.objects.abstractmethod
234 + def accepts_other ( self, dep_env ):
235 + """Returns True if this pool can be used to resolve a dep env whose
236 + deptype mask is rejected by this pool.
237 + (Not necessarily the inverse of accepts().)
238 + """
239 + pass
240 + # --- end of accepts_other (...) ---
241
242 def export_rules ( self ):
243 """Exports all rules. Typically, this generates text lines."""
244 - for rule in self.rules:
245 + for rule in self.iter_rules():
246 for item in rule.export_rule():
247 yield item
248 # --- end of export_rules (...) ---
249 @@ -184,4 +190,85 @@ class DependencyRulePool ( object ):
250 for item in self.export_rules():
251 fh.write ( str ( item ) )
252 fh.write ( NL )
253 + # --- end of exports_rules_into (...) ---
254 +
255 +# --- end of DependencyRulePoolBase ---
256 +
257 +
258 +class DependencyRulePool ( DependencyRulePoolBase ):
259 +
260 + def __init__ ( self, name, priority, deptype_mask, initial_rules=None ):
261 + """Initializes an DependencyRulePool, which basically is a set of
262 + dependency rules with methods like "search for x in all rules."
263 +
264 + arguments:
265 + * name -- name of this rule pool
266 + * priority -- priority of this pool (lower is better)
267 + """
268 + super ( DependencyRulePool, self ).__init__(
269 + name, priority, deptype_mask
270 + )
271 + if initial_rules is None:
272 + self.rules = list()
273 + else:
274 + self.rules = list ( initial_rules )
275 + self._rule_add = self.rules.append
276 + # --- end of __init__ (...) ---
277 +
278 + def iter_rules ( self ):
279 + return iter ( self.rules )
280 + # --- end of iter_rules (...) ---
281 +
282 + def iter_rules_resolving ( self, dep_env ):
283 + return iter ( self.rules )
284 + # --- end of iter_rules_resolving (...) ---
285 +
286 + def empty ( self ):
287 + """Returns True if this pool has no rules."""
288 + return len ( self.rules ) == 0
289 + # --- end of empty (...) ---
290 +
291 + def sort_rules ( self ):
292 + """Sorts this rule pool and determines its weight which is used
293 + to compare rule pools.
294 + """
295 + self.rules.sort ( key=lambda rule : rule.priority )
296 + # --- end of sort_rules (...) ---
297 +
298 + def accepts_other ( self, dep_env ):
299 + """Returns True if this pool can be used to resolve a dep env whose
300 + deptype mask is rejected by this pool.
301 + (Not necessarily the inverse of accepts().)
302 + """
303 + return not self.accepts ( dep_env )
304 + # --- end of accepts_other (...) ---
305 +
306 + def add ( self, rule ):
307 + """Adds a DependencyRule to this rule pool.
308 +
309 + arguments:
310 + * rule --
311 + """
312 + if issubclass ( rule, DependencyRule ):
313 + self._rule_add ( rule )
314 + else:
315 + raise Exception ( "bad usage (dependency rule expected)." )
316 +
317 + return None
318 + # --- end of add (...) ---
319 +
320 # --- end of DependencyRulePool ---
321 +
322 +
323 +class DynamicDependencyRulePool ( DependencyRulePoolBase ):
324 +
325 + @roverlay.util.objects.abstractmethod
326 + def reload ( self ):
327 + pass
328 + # --- end of reload (...) ---
329 +
330 + def accepts_other ( self, dep_env ):
331 + return False
332 + # --- end of accepts_other (...) ---
333 +
334 +# --- end of DynamicDependencyRulePool ---
335
336 diff --git a/roverlay/depres/simpledeprule/dynpool.py b/roverlay/depres/simpledeprule/dynpool.py
337 index 21e5a1b..7688bf1 100644
338 --- a/roverlay/depres/simpledeprule/dynpool.py
339 +++ b/roverlay/depres/simpledeprule/dynpool.py
340 @@ -18,36 +18,72 @@ whose dependency type contains deptype.internal.
341
342 __all__ = [ 'DynamicSelfdepRulePool', 'get' ]
343
344 +import collections
345 +
346 from roverlay.depres import deptype
347 -from roverlay.depres.simpledeprule.pool import SimpleDependencyRulePool
348 +from roverlay.depres.deprule import DynamicDependencyRulePool
349 from roverlay.depres.simpledeprule.rules import SimpleFuzzyDependencyRule
350
351 -class DynamicSelfdepRulePool ( SimpleDependencyRulePool ):
352 +class DynamicSelfdepRulePool ( DynamicDependencyRulePool ):
353 """A rule pool that gets its rules from a function."""
354
355 - def __init__ ( self, rule_kw_function, rule_class, priority=120, **kwargs ):
356 + def __init__ ( self, rule_generator, rule_class, priority=120, **kwargs ):
357 super ( DynamicSelfdepRulePool, self ). __init__ (
358 name='dynamic selfdeps', priority=priority,
359 deptype_mask=deptype.internal,
360 **kwargs
361 )
362
363 - self._rule_class = rule_class
364 - self._rule_kw_function = rule_kw_function
365 + self.rules = None
366 + self._rule_generator = rule_generator
367 + self.set_rule_class ( rule_class )
368 # --- end of __init__ (...) ---
369
370 + def sort_rules ( self ):
371 + # TODO: sort self.rules itself ("sort repos")
372 + priokey = lambda k: k.priority
373 +
374 + if self.rules:
375 + for rules in self.rules.values():
376 + rules.sort ( key=priokey )
377 + # --- end of sort_rules (...) ---
378 +
379 + def iter_rules ( self ):
380 + if self.rules:
381 + for rules in self.rules.values():
382 + for rule in rules:
383 + yield rule
384 + # --- end of iter_rules (...) ---
385 +
386 + def iter_rules_resolving ( self, dep_env ):
387 + specific_rules = self.rules.get ( dep_env.repo_id, None )
388 + if specific_rules is not None:
389 + for rule in specific_rules:
390 + yield rule
391 +
392 + for rules in self.rules.values():
393 + if rules is not specific_rules:
394 + for rule in rules:
395 + yield rule
396 + # --- end of iter_rules_resolving (...) ---
397 +
398 + def set_rule_class ( self, rule_class ):
399 + self._rule_generator.rule_class = rule_class
400 + # --- end of set_rule_class (...) ---
401 +
402 def accepts_other ( self, dep_env ):
403 # never resolve external deps as selfdeps
404 return False
405 # --- end of accepts_other (...) ---
406
407 def reload ( self ):
408 - self.rules = list (
409 - self._rule_class ( **kwargs ) for kwargs in self._rule_kw_function()
410 - )
411 + self.rules = self._rule_generator.make_rule_dict()
412 # --- end of reload (...) ---
413
414
415 +# --- end of DynamicSelfdepRulePool ---
416 +
417 +
418 def get ( rule_kw_function ):
419 """Returns a default DynamicSelfdepRulePool for rule_kw_function."""
420 return DynamicSelfdepRulePool (