1   
  2   
  3   
  4   
  5   
  6   
  7   
  8   
  9   
 10   
 11   
 12   
 13   
 14   
 15   
 16  from buildbot.process.buildstep import LoggingBuildStep, SUCCESS, FAILURE, EXCEPTION 
 17  from buildbot.process.properties import Properties 
 18  from buildbot.schedulers.triggerable import Triggerable 
 19  from twisted.python import log 
 20  from twisted.internet import defer 
 21  from buildbot import config 
 22   
 24      name = "trigger" 
 25   
 26      renderables = [ 'set_properties', 'schedulerNames', 'sourceStamp', 
 27                      'updateSourceStamp', 'alwaysUseLatest' ] 
 28   
 29      flunkOnFailure = True 
 30   
 31 -    def __init__(self, schedulerNames=[], sourceStamp=None, updateSourceStamp=None, alwaysUseLatest=False, 
 32                   waitForFinish=False, set_properties={}, copy_properties=[], **kwargs): 
  33          if not schedulerNames: 
 34              config.error( 
 35                  "You must specify a scheduler to trigger") 
 36          if sourceStamp and (updateSourceStamp is not None): 
 37              config.error( 
 38                  "You can't specify both sourceStamp and updateSourceStamp") 
 39          if sourceStamp and alwaysUseLatest: 
 40              config.error( 
 41                  "You can't specify both sourceStamp and alwaysUseLatest") 
 42          if alwaysUseLatest and (updateSourceStamp is not None): 
 43              config.error( 
 44                  "You can't specify both alwaysUseLatest and updateSourceStamp" 
 45              ) 
 46          self.schedulerNames = schedulerNames 
 47          self.sourceStamp = sourceStamp 
 48          if updateSourceStamp is not None: 
 49              self.updateSourceStamp = updateSourceStamp 
 50          else: 
 51              self.updateSourceStamp = not (alwaysUseLatest or sourceStamp) 
 52          self.alwaysUseLatest = alwaysUseLatest 
 53          self.waitForFinish = waitForFinish 
 54          self.set_properties = set_properties 
 55          self.copy_properties = copy_properties 
 56          self.running = False 
 57          self.ended = False 
 58          LoggingBuildStep.__init__(self, **kwargs) 
 59          self.addFactoryArguments(schedulerNames=schedulerNames, 
 60                                   sourceStamp=sourceStamp, 
 61                                   updateSourceStamp=updateSourceStamp, 
 62                                   alwaysUseLatest=alwaysUseLatest, 
 63                                   waitForFinish=waitForFinish, 
 64                                   set_properties=set_properties, 
 65                                   copy_properties=copy_properties) 
  66   
 71   
 72 -    def end(self, result): 
  73          if not self.ended: 
 74              self.ended = True 
 75              return self.finished(result) 
  76   
122   
123          if self.sourceStamp: 
124              d = master.db.sourcestampsets.addSourceStampSet() 
125              d.addCallback(add_sourcestamp_to_set, self.sourceStamp) 
126          elif self.alwaysUseLatest: 
127              d = defer.succeed(None) 
128          else: 
129              ss = self.build.getSourceStamp() 
130              if self.updateSourceStamp: 
131                  got = properties.getProperty('got_revision') 
132                  if got: 
133                      ss = ss.getAbsoluteSourceStamp(got) 
134              d = ss.getSourceStampSetId(master) 
135          def start_builds(ss_setid): 
136              dl = [] 
137              for scheduler in triggered_schedulers: 
138                  sch = all_schedulers[scheduler] 
139                  dl.append(sch.trigger(ss_setid, set_props=props_to_set)) 
140              self.step_status.setText(['triggered'] + triggered_schedulers) 
141   
142              if self.waitForFinish: 
143                  return defer.DeferredList(dl, consumeErrors=1) 
144              else: 
145                   
146                  for d in dl: 
147                      d.addErrback(log.err, 
148                          '(ignored) while invoking Triggerable schedulers:') 
149                  self.end(SUCCESS) 
150                  return None 
 151          d.addCallback(start_builds) 
152   
153          def cb(rclist): 
154              was_exception = was_failure = False 
155              brids = {} 
156              for was_cb, results in rclist: 
157                  if isinstance(results, tuple): 
158                      results, some_brids = results 
159                      brids.update(some_brids) 
160   
161                  if not was_cb: 
162                      was_exception = True 
163                      log.err(results) 
164                      continue 
165   
166                  if results==FAILURE: 
167                      was_failure = True 
168   
169              if was_exception: 
170                  result = EXCEPTION 
171              elif was_failure: 
172                  result = FAILURE 
173              else: 
174                  result = SUCCESS 
175   
176              if brids: 
177                  def add_links(res): 
178                       
179                      brid_to_bn = dict((_brid,_bn) for _bn,_brid in brids.iteritems()) 
180   
181                      for was_cb, builddicts in res: 
182                          if was_cb: 
183                              for build in builddicts: 
184                                  bn = brid_to_bn[build['brid']] 
185                                  num = build['number'] 
186                                   
187                                  url = master.status.getURLForBuild(bn, num) 
188                                  self.step_status.addURL("%s #%d" % (bn,num), url) 
189                                   
190                      return self.end(result) 
191   
192                  builddicts = [master.db.builds.getBuildsForRequest(br) for br in brids.values()] 
193                  dl = defer.DeferredList(builddicts, consumeErrors=1) 
194                  dl.addCallback(add_links) 
195                  return dl 
196   
197              return self.end(result) 
198          def eb(why): 
199              return self.end(FAILURE) 
200   
201          if self.waitForFinish: 
202              d.addCallbacks(cb, eb) 
203   
204          d.addErrback(log.err, '(ignored) while triggering builds:') 
205