1# Copyright 2015 gRPC authors. 2# 3# Licensed under the Apache License, Version 2.0 (the "License"); 4# you may not use this file except in compliance with the License. 5# You may obtain a copy of the License at 6# 7# http://www.apache.org/licenses/LICENSE-2.0 8# 9# Unless required by applicable law or agreed to in writing, software 10# distributed under the License is distributed on an "AS IS" BASIS, 11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12# See the License for the specific language governing permissions and 13# limitations under the License. 14"""Buildgen transitive dependencies 15 16This takes the list of libs, node_modules, and targets from our 17yaml dictionary, and adds to each the transitive closure 18of the list of dependencies. 19 20""" 21 22 23def get_lib(libs, name): 24 try: 25 return next(lib for lib in libs if lib['name'] == name) 26 except StopIteration: 27 return None 28 29 30def transitive_deps(lib, libs): 31 if lib is not None and 'deps' in lib: 32 # Recursively call transitive_deps on each dependency, and take the union 33 return set.union( 34 set(lib['deps']), *[ 35 set(transitive_deps(get_lib(libs, dep), libs)) 36 for dep in lib['deps'] 37 ]) 38 else: 39 return set() 40 41 42def mako_plugin(dictionary): 43 """The exported plugin code for transitive_dependencies. 44 45 Iterate over each list and check each item for a deps list. We add a 46 transitive_deps property to each with the transitive closure of those 47 dependency lists. 48 """ 49 libs = dictionary.get('libs') 50 51 for target_name, target_list in dictionary.items(): 52 for target in target_list: 53 if isinstance(target, dict) and 'deps' in target: 54 target['transitive_deps'] = transitive_deps(target, libs) 55 56 python_dependencies = dictionary.get('python_dependencies') 57 python_dependencies['transitive_deps'] = (transitive_deps( 58 python_dependencies, libs)) 59