1#!/usr/bin/env python3 

2 

3""" 

4Wrapper to launch dak functionality 

5 

6G{importgraph} 

7 

8""" 

9# Copyright (C) 2005, 2006 Anthony Towns <ajt@debian.org> 

10# Copyright (C) 2006 James Troup <james@nocrew.org> 

11 

12# This program is free software; you can redistribute it and/or modify 

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

14# the Free Software Foundation; either version 2 of the License, or 

15# (at your option) any later version. 

16 

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

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

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

20# GNU General Public License for more details. 

21 

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

23# along with this program; if not, write to the Free Software 

24# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 

25 

26################################################################################ 

27 

28# well I don't know where you're from but in AMERICA, there's a little 

29# thing called "abstinent until proven guilty." 

30# -- http://harrietmiers.blogspot.com/2005/10/wow-i-feel-loved.html 

31 

32# (if James had a blog, I bet I could find a funny quote in it to use!) 

33 

34################################################################################ 

35 

36import importlib 

37import os 

38import sys 

39import traceback 

40 

41sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.realpath(__file__)))) 

42 

43import daklib.utils 

44 

45from daklib.daklog import Logger 

46 

47################################################################################ 

48 

49 

50def init(): 

51 """Setup the list of modules and brief explanation of what they 

52 do.""" 

53 

54 functionality = [ 

55 ("ls", 

56 "Show which suites packages are in"), 

57 ("override", 

58 "Query/change the overrides"), 

59 ("check-archive", 

60 "Archive sanity checks"), 

61 ("queue-report", 

62 "Produce a report on NEW and BYHAND packages"), 

63 ("show-new", 

64 "Output html for packages in NEW"), 

65 ("show-deferred", 

66 "Output html and symlinks for packages in DEFERRED"), 

67 ("graph", 

68 "Output graphs of number of packages in various queues"), 

69 ("graph-new", 

70 "Output graphs of age of packages in the NEW queue"), 

71 

72 ("rm", 

73 "Remove packages from suites"), 

74 

75 ("process-new", 

76 "Process NEW and BYHAND packages"), 

77 ("process-upload", 

78 "Process packages in queue/unchecked"), 

79 ("process-commands", 

80 "Process command files (*.dak-commands)"), 

81 ("process-policy", 

82 "Process packages in policy queues from COMMENTS files"), 

83 

84 ("dominate", 

85 "Remove obsolete source and binary associations from suites"), 

86 ("export", 

87 "Export uploads from policy queues"), 

88 ("export-suite", 

89 "export a suite to a flat directory structure"), 

90 ("make-pkg-file-mapping", 

91 "Generate package <-> file mapping"), 

92 ("generate-releases", 

93 "Generate Release files"), 

94 ("generate-packages-sources2", 

95 "Generate Packages/Sources files"), 

96 ("contents", 

97 "Generate content files"), 

98 ("metadata", 

99 "Load data for packages/sources files"), 

100 ("generate-index-diffs", 

101 "Generate .diff/Index files"), 

102 ("clean-suites", 

103 "Clean unused/superseded packages from the archive"), 

104 ("manage-build-queues", 

105 "Clean and update metadata for build queues"), 

106 ("manage-debug-suites", 

107 "Clean obsolete packages from debug suites"), 

108 ("manage-external-signature-requests", 

109 "Maintain external signature requests"), 

110 ("clean-queues", 

111 "Clean cruft from incoming"), 

112 ("archive-dedup-pool", 

113 "De-duplicates files in the pool directory"), 

114 

115 ("transitions", 

116 "Manage the release transition file"), 

117 ("check-overrides", 

118 "Override cruft checks"), 

119 ("control-overrides", 

120 "Manipulate/list override entries in bulk"), 

121 ("control-suite", 

122 "Manipulate suites in bulk"), 

123 ("update-suite", 

124 "Update suite with packages from a different suite"), 

125 ("cruft-report", 

126 "Check for obsolete or duplicated packages"), 

127 ("auto-decruft", 

128 "Clean cruft without reverse dependencies automatically"), 

129 ("examine-package", 

130 "Show information useful for NEW processing"), 

131 ("import", 

132 "Import existing source and binary packages"), 

133 ("import-repository", 

134 "Import packages from another repository"), 

135 ("import-keyring", 

136 "Populate fingerprint/uid table based on a new/updated keyring"), 

137 ("import-users-from-passwd", 

138 "Sync PostgreSQL users with passwd file"), 

139 ("acl", 

140 "Manage upload ACLs"), 

141 ("admin", 

142 "Perform administration on the dak database"), 

143 ("update-db", 

144 "Updates databae schema to latest revision"), 

145 ("init-dirs", 

146 "Initial setup of the archive"), 

147 ("make-maintainers", 

148 "Generates Maintainers file for BTS etc"), 

149 ("make-overrides", 

150 "Generates override files"), 

151 ("new-security-install", 

152 "New way to install a security upload into the archive"), 

153 ("stats", 

154 "Generate statistics"), 

155 ("bts-categorize", 

156 "Categorize uncategorized bugs filed against ftp.debian.org"), 

157 ("add-user", 

158 "Add a user to the archive"), 

159 ("make-changelog", 

160 "Generate changelog between two suites"), 

161 ("copy-installer", 

162 "Copies the installer from one suite to another"), 

163 ("external-overrides", 

164 "Modify external overrides"), 

165 ("write-sections", 

166 "Write out section descriptions"), 

167 ("find-files", 

168 "Find files related to a given source package and version"), 

169 ] 

170 return functionality 

171 

172################################################################################ 

173 

174 

175def usage(functionality, exit_code=0): 

176 """Print a usage message and exit with 'exit_code'.""" 

177 

178 print("""Usage: dak COMMAND [...] 

179Run DAK commands. (Will also work if invoked as COMMAND.) 

180 

181Available commands:""") 

182 for (command, description) in functionality: 

183 print(" %-23s %s" % (command, description)) 

184 sys.exit(exit_code) 

185 

186################################################################################ 

187 

188 

189def main(): 

190 """Launch dak functionality.""" 

191 

192 try: 

193 logger = Logger('dak top-level', print_starting=False) 

194 except OSError: 

195 logger = None 

196 

197 functionality = init() 

198 modules = [command for (command, _) in functionality] 

199 

200 if len(sys.argv) == 0: 200 ↛ 201line 200 didn't jump to line 201, because the condition on line 200 was never true

201 daklib.utils.fubar("err, argc == 0? how is that possible?") 

202 elif (len(sys.argv) == 1 

203 or (len(sys.argv) == 2 

204 and (sys.argv[1] == "--help" or sys.argv[1] == "-h"))): 

205 usage(functionality) 

206 

207 # First see if we were invoked with/as the name of a module 

208 cmdname = sys.argv[0] 

209 cmdname = cmdname[cmdname.rfind("/") + 1:] 

210 if cmdname in modules: 210 ↛ 211line 210 didn't jump to line 211, because the condition on line 210 was never true

211 pass 

212 # Otherwise the argument is the module 

213 else: 

214 cmdname = sys.argv[1] 

215 sys.argv = [sys.argv[0] + " " + sys.argv[1]] + sys.argv[2:] 

216 if cmdname not in modules: 

217 match = [] 

218 for name in modules: 

219 if name.startswith(cmdname): 

220 match.append(name) 

221 if len(match) == 1: 221 ↛ 223line 221 didn't jump to line 223, because the condition on line 221 was never false

222 cmdname = match[0] 

223 elif len(match) > 1: 

224 daklib.utils.warn("ambiguous command '%s' - could be %s" 

225 % (cmdname, ", ".join(match))) 

226 usage(functionality, 1) 

227 else: 

228 daklib.utils.warn("unknown command '%s'" % (cmdname)) 

229 usage(functionality, 1) 

230 

231 # Invoke the module 

232 module = importlib.import_module("dak.{}".format(cmdname.replace("-", "_"))) 

233 

234 try: 

235 module.main() 

236 except KeyboardInterrupt: 236 ↛ 237line 236 didn't jump to line 237, because the exception caught by line 236 didn't happen

237 msg = 'KeyboardInterrupt caught; exiting' 

238 print(msg) 

239 if logger: 

240 logger.log([msg]) 

241 sys.exit(1) 

242 except SystemExit: 242 ↛ 244line 242 didn't jump to line 244

243 raise 

244 except: 

245 if logger: 

246 for line in traceback.format_exc().split('\n')[:-1]: 

247 logger.log(['exception', line]) 

248 raise 

249 

250################################################################################ 

251 

252 

253if __name__ == "__main__": 

254 os.environ['LANG'] = 'C' 

255 os.environ['LC_ALL'] = 'C' 

256 main()