Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1# This file is part of ctrl_mpexec. 

2# 

3# Developed for the LSST Data Management System. 

4# This product includes software developed by the LSST Project 

5# (http://www.lsst.org). 

6# See the COPYRIGHT file at the top-level directory of this distribution 

7# for details of code ownership. 

8# 

9# This program is free software: you can redistribute it and/or modify 

10# it under the terms of the GNU General Public License as published by 

11# the Free Software Foundation, either version 3 of the License, or 

12# (at your option) any later version. 

13# 

14# This program is distributed in the hope that it will be useful, 

15# but WITHOUT ANY WARRANTY; without even the implied warranty of 

16# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 

17# GNU General Public License for more details. 

18# 

19# You should have received a copy of the GNU General Public License 

20# along with this program. If not, see <http://www.gnu.org/licenses/>. 

21 

22"""Few utility methods used by the rest of a package. 

23""" 

24 

25__all__ = ["profile", "printTable", "filterTasks", "subTaskIter"] 

26 

27# ------------------------------- 

28# Imports of standard modules -- 

29# ------------------------------- 

30import contextlib 

31 

32# ----------------------------- 

33# Imports for other modules -- 

34# ----------------------------- 

35import lsst.pex.config as pexConfig 

36 

37# ---------------------------------- 

38# Local non-exported definitions -- 

39# ---------------------------------- 

40 

41# ------------------------ 

42# Exported definitions -- 

43# ------------------------ 

44 

45 

46@contextlib.contextmanager 

47def profile(filename, log=None): 

48 """!Context manager for profiling with cProfile 

49 

50 @param filename filename to which to write profile (profiling disabled if None or empty) 

51 @param log log object for logging the profile operations 

52 

53 If profiling is enabled, the context manager returns the cProfile.Profile object (otherwise 

54 it returns None), which allows additional control over profiling. You can obtain this using 

55 the "as" clause, e.g.: 

56 

57 with profile(filename) as prof: 

58 runYourCodeHere() 

59 

60 The output cumulative profile can be printed with a command-line like: 

61 

62 python -c 'import pstats; pstats.Stats("<filename>").sort_stats("cumtime").print_stats(30)' 

63 """ 

64 if not filename: 

65 # Nothing to do 

66 yield 

67 return 

68 from cProfile import Profile 

69 

70 prof = Profile() 

71 if log is not None: 

72 log.info("Enabling cProfile profiling") 

73 prof.enable() 

74 yield prof 

75 prof.disable() 

76 prof.dump_stats(filename) 

77 if log is not None: 

78 log.info("cProfile stats written to %s" % filename) 

79 

80 

81def printTable(rows, header): 

82 """Nice formatting of 2-column table. 

83 

84 Parameters 

85 ---------- 

86 rows : `list` of `tuple` 

87 Each item in the list is a 2-tuple containg left and righ column values 

88 header: `tuple` or `None` 

89 If `None` then table header are not prined, otherwise it's a 2-tuple 

90 with column headings. 

91 """ 

92 if not rows: 

93 return 

94 width = max(len(x[0]) for x in rows) 

95 if header: 

96 width = max(width, len(header[0])) 

97 print(header[0].ljust(width), header[1]) 

98 print("".ljust(width, "-"), "".ljust(len(header[1]), "-")) 

99 for col1, col2 in rows: 

100 print(col1.ljust(width), col2) 

101 

102 

103def filterTasks(pipeline, name): 

104 """Finds list of tasks matching given name. 

105 

106 For matching task either task label or task name after last dot should 

107 be identical to `name`. If task label is non-empty then task name is not 

108 checked. 

109 

110 Parameters 

111 ---------- 

112 pipeline : `Pipeline` 

113 name : str or none 

114 If empty or None then all tasks are returned 

115 

116 Returns 

117 ------- 

118 Lsit of `TaskDef` instances. 

119 """ 

120 if not name: 

121 return list(pipeline.toExpandedPipeline()) 

122 tasks = [] 

123 for taskDef in pipeline.toExpandedPipeline(): 

124 if taskDef.label: 

125 if taskDef.label == name: 

126 tasks.append(taskDef) 

127 elif taskDef.taskName.split('.')[-1] == name: 

128 tasks.append(taskDef) 

129 return tasks 

130 

131 

132def subTaskIter(config): 

133 """Recursively generates subtask names. 

134 

135 Parameters 

136 ---------- 

137 config : `lsst.pex.config.Config` 

138 Configuration of the task 

139 

140 Returns 

141 ------- 

142 Iterator which returns tuples of (configFieldPath, taskName). 

143 """ 

144 for fieldName, field in sorted(config.items()): 

145 if hasattr(field, "value") and hasattr(field, "target"): 

146 subConfig = field.value 

147 if isinstance(subConfig, pexConfig.Config): 

148 try: 

149 taskName = "%s.%s" % (field.target.__module__, field.target.__name__) 

150 except Exception: 

151 taskName = repr(field.target) 

152 yield fieldName, taskName 

153 for subFieldName, taskName in subTaskIter(subConfig): 

154 yield fieldName + '.' + subFieldName, taskName