Package dak :: Module override
[hide private]
[frames] | no frames]

Source Code for Module dak.override

  1  #! /usr/bin/env python3 
  2   
  3  """Microscopic modification and query tool for overrides in projectb""" 
  4  # Copyright (C) 2004, 2006  Daniel Silverstone <dsilvers@digital-scurf.org> 
  5   
  6  # This program is free software; you can redistribute it and/or modify 
  7  # it under the terms of the GNU General Public License as published by 
  8  # the Free Software Foundation; either version 2 of the License, or 
  9  # (at your option) any later version. 
 10   
 11  # This program is distributed in the hope that it will be useful, 
 12  # but WITHOUT ANY WARRANTY; without even the implied warranty of 
 13  # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
 14  # GNU General Public License for more details. 
 15   
 16  # You should have received a copy of the GNU General Public License 
 17  # along with this program; if not, write to the Free Software 
 18  # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA 
 19   
 20   
 21  ################################################################################ 
 22  ## So line up your soldiers and she'll shoot them all down 
 23  ## Coz Alisha Rules The World 
 24  ## You think you found a dream, then it shatters and it seems, 
 25  ## That Alisha Rules The World 
 26  ################################################################################ 
 27   
 28  import os 
 29  import sys 
 30   
 31  import apt_pkg 
 32   
 33  from daklib import daklog, utils 
 34  from daklib.config import Config 
 35  from daklib.dbconn import ( 
 36      DBConn, 
 37      get_override_type, 
 38      get_priority, 
 39      get_section, 
 40      get_suite, 
 41  ) 
 42   
 43  ################################################################################ 
 44   
 45  # Shamelessly stolen from 'dak rm'. Should probably end up in utils.py 
 46   
 47   
48 -def game_over():
49 answer = utils.input_or_exit("Continue (y/N)? ").lower() 50 if answer != "y": 51 print("Aborted.") 52 sys.exit(1)
53 54
55 -def usage(exit_code=0):
56 print( 57 """Usage: dak override [OPTIONS] package [section] [priority] 58 Make microchanges or microqueries of the binary overrides 59 60 -h, --help show this help and exit 61 -c, --check check override compliance (deprecated) 62 -d, --done=BUG# send priority/section change as closure to bug# 63 -n, --no-action don't do anything 64 -s, --suite specify the suite to use 65 """ 66 ) 67 sys.exit(exit_code)
68 69
70 -def main():
71 cnf = Config() 72 73 Arguments = [ 74 ("h", "help", "Override::Options::Help"), 75 ("c", "check", "Override::Options::Check"), 76 ("d", "done", "Override::Options::Done", "HasArg"), 77 ("n", "no-action", "Override::Options::No-Action"), 78 ("s", "suite", "Override::Options::Suite", "HasArg"), 79 ] 80 for i in ["help", "check", "no-action"]: 81 key = "Override::Options::%s" % i 82 if key not in cnf: 83 cnf[key] = "" 84 if "Override::Options::Suite" not in cnf: 85 cnf["Override::Options::Suite"] = "unstable" 86 87 arguments = apt_pkg.parse_commandline(cnf.Cnf, Arguments, sys.argv) 88 Options = cnf.subtree("Override::Options") 89 90 if Options["Help"]: 91 usage() 92 93 session = DBConn().session() 94 95 if not arguments: 96 utils.fubar("package name is a required argument.") 97 98 package = arguments.pop(0) 99 suite_name = Options["Suite"] 100 if arguments and len(arguments) > 2: 101 utils.fubar("Too many arguments") 102 103 suite = get_suite(suite_name, session) 104 if suite is None: 105 utils.fubar("Unknown suite '{0}'".format(suite_name)) 106 107 if arguments and len(arguments) == 1: 108 # Determine if the argument is a priority or a section... 109 arg = arguments.pop() 110 q = session.execute( 111 """ 112 SELECT ( SELECT COUNT(*) FROM section WHERE section = :arg ) AS secs, 113 ( SELECT COUNT(*) FROM priority WHERE priority = :arg ) AS prios 114 """, 115 {"arg": arg}, 116 ) 117 r = q.fetchall() 118 if r[0][0] == 1: 119 arguments = (arg, ".") 120 elif r[0][1] == 1: 121 arguments = (".", arg) 122 else: 123 utils.fubar("%s is not a valid section or priority" % (arg)) 124 125 # Retrieve current section/priority... 126 oldsection, oldsourcesection, oldpriority = None, None, None 127 for packagetype in ["source", "binary"]: 128 eqdsc = "!=" 129 if packagetype == "source": 130 eqdsc = "=" 131 q = session.execute( 132 """ 133 SELECT priority.priority AS prio, section.section AS sect, override_type.type AS type 134 FROM override, priority, section, suite, override_type 135 WHERE override.priority = priority.id 136 AND override.type = override_type.id 137 AND override_type.type %s 'dsc' 138 AND override.section = section.id 139 AND override.package = :package 140 AND override.suite = suite.id 141 AND suite.suite_name = :suite_name 142 """ 143 % (eqdsc), 144 {"package": package, "suite_name": suite_name}, 145 ) 146 147 if q.rowcount == 0: 148 continue 149 if q.rowcount > 1: 150 utils.fubar("%s is ambiguous. Matches %d packages" % (package, q.rowcount)) 151 152 r = q.fetchone() 153 if packagetype == "binary": 154 oldsection = r[1] 155 oldpriority = r[0] 156 else: 157 oldsourcesection = r[1] 158 oldpriority = "optional" 159 160 if not oldpriority and not oldsourcesection: 161 utils.fubar("Unable to find package %s" % (package)) 162 163 if oldsection and oldsourcesection and oldsection != oldsourcesection: 164 # When setting overrides, both source & binary will become the same section 165 utils.warn( 166 "Source is in section '%s' instead of '%s'" % (oldsourcesection, oldsection) 167 ) 168 169 if not oldsection: 170 oldsection = oldsourcesection 171 172 if not arguments: 173 print( 174 "%s is in section '%s' at priority '%s'" 175 % (package, oldsection, oldpriority) 176 ) 177 sys.exit(0) 178 179 # At this point, we have a new section and priority... check they're valid... 180 newsection, newpriority = arguments 181 182 if newsection == ".": 183 newsection = oldsection 184 if newpriority == ".": 185 newpriority = oldpriority 186 187 s = get_section(newsection, session) 188 if s is None: 189 utils.fubar("Supplied section %s is invalid" % (newsection)) 190 newsecid = s.section_id 191 192 p = get_priority(newpriority, session) 193 if p is None: 194 utils.fubar("Supplied priority %s is invalid" % (newpriority)) 195 newprioid = p.priority_id 196 197 if newpriority == oldpriority and newsection == oldsection: 198 print("I: Doing nothing") 199 sys.exit(0) 200 201 if Options["Check"]: 202 print("WARNING: Check option is deprecated by Debian Policy 4.0.1") 203 204 # If we're in no-action mode 205 if Options["No-Action"]: 206 if newpriority != oldpriority: 207 print("I: Would change priority from %s to %s" % (oldpriority, newpriority)) 208 if newsection != oldsection: 209 print("I: Would change section from %s to %s" % (oldsection, newsection)) 210 if "Done" in Options: 211 print("I: Would also close bug(s): %s" % (Options["Done"])) 212 213 sys.exit(0) 214 215 if newpriority != oldpriority: 216 print("I: Will change priority from %s to %s" % (oldpriority, newpriority)) 217 218 if newsection != oldsection: 219 print("I: Will change section from %s to %s" % (oldsection, newsection)) 220 221 if "Done" not in Options: 222 pass 223 # utils.warn("No bugs to close have been specified. Noone will know you have done this.") 224 else: 225 print("I: Will close bug(s): %s" % (Options["Done"])) 226 227 game_over() 228 229 Logger = daklog.Logger("override") 230 231 dsc_otype_id = get_override_type("dsc").overridetype_id 232 233 # We're already in a transaction 234 # We're in "do it" mode, we have something to do... do it 235 if newpriority != oldpriority: 236 session.execute( 237 """ 238 UPDATE override 239 SET priority = :newprioid 240 WHERE package = :package 241 AND override.type != :otypedsc 242 AND suite = (SELECT id FROM suite WHERE suite_name = :suite_name)""", 243 { 244 "newprioid": newprioid, 245 "package": package, 246 "otypedsc": dsc_otype_id, 247 "suite_name": suite_name, 248 }, 249 ) 250 251 Logger.log(["changed priority", package, oldpriority, newpriority]) 252 253 if newsection != oldsection: 254 q = session.execute( 255 """ 256 UPDATE override 257 SET section = :newsecid 258 WHERE package = :package 259 AND suite = (SELECT id FROM suite WHERE suite_name = :suite_name)""", 260 {"newsecid": newsecid, "package": package, "suite_name": suite_name}, 261 ) 262 263 Logger.log(["changed section", package, oldsection, newsection]) 264 265 session.commit() 266 267 if "Done" in Options: 268 if "Dinstall::BugServer" not in cnf: 269 utils.warn( 270 "Asked to send Done message but Dinstall::BugServer is not configured" 271 ) 272 Logger.close() 273 return 274 275 Subst = {} 276 Subst["__OVERRIDE_ADDRESS__"] = cnf["Dinstall::MyEmailAddress"] 277 Subst["__BUG_SERVER__"] = cnf["Dinstall::BugServer"] 278 bcc = [] 279 if cnf.find("Dinstall::Bcc") != "": 280 bcc.append(cnf["Dinstall::Bcc"]) 281 if bcc: 282 Subst["__BCC__"] = "Bcc: " + ", ".join(bcc) 283 else: 284 Subst["__BCC__"] = "X-Filler: 42" 285 if "Dinstall::PackagesServer" in cnf: 286 Subst["__CC__"] = ( 287 "Cc: " 288 + package 289 + "@" 290 + cnf["Dinstall::PackagesServer"] 291 + "\nX-DAK: dak override" 292 ) 293 else: 294 Subst["__CC__"] = "X-DAK: dak override" 295 Subst["__ADMIN_ADDRESS__"] = cnf["Dinstall::MyAdminAddress"] 296 Subst["__DISTRO__"] = cnf["Dinstall::MyDistribution"] 297 Subst["__WHOAMI__"] = utils.whoami() 298 Subst["__SOURCE__"] = package 299 300 summary = "Concerning package %s...\n" % (package) 301 summary += "Operating on the %s suite\n" % (suite_name) 302 if newpriority != oldpriority: 303 summary += "Changed priority from %s to %s\n" % (oldpriority, newpriority) 304 if newsection != oldsection: 305 summary += "Changed section from %s to %s\n" % (oldsection, newsection) 306 Subst["__SUMMARY__"] = summary 307 308 template = os.path.join(cnf["Dir::Templates"], "override.bug-close") 309 for bug in utils.split_args(Options["Done"]): 310 Subst["__BUG_NUMBER__"] = bug 311 mail_message = utils.TemplateSubst(Subst, template) 312 utils.send_mail(mail_message) 313 Logger.log(["closed bug", bug]) 314 315 Logger.close()
316 317 318 ################################################################################# 319 320 321 if __name__ == "__main__": 322 main() 323