in src/plugins/scanners/github-issues.py [0:0]
def scan(KibbleBit, source, firstAttempt = True):
auth=None
people = {}
if 'creds' in source:
KibbleBit.pprint("Using auth for repo %s" % source['sourceURL'])
creds = source['creds']
if creds and 'username' in creds:
auth = (creds['username'], creds['password'])
TL = plugins.utils.github.get_tokens_left(auth=auth)
KibbleBit.pprint("Scanning for GitHub issues (%u tokens left on GitHub)" % TL)
# Have we scanned before? If so, only do a 3 month scan here.
doneBefore = False
if source.get('steps') and source['steps'].get('issues'):
doneBefore = True
source['steps']['issues'] = {
'time': time.time(),
'status': 'Issue scan started at ' + time.strftime("%a, %d %b %Y %H:%M:%S +0000", time.gmtime()),
'running': True,
'good': True,
}
KibbleBit.updateSource(source)
try:
if doneBefore:
since = time.strftime("%Y-%m-%dT%H:%M:%SZ", time.gmtime(time.time() - (3*30*86400)))
KibbleBit.pprint("Fetching changes since %s" % since)
issues = plugins.utils.github.get_all(source, plugins.utils.github.issues,
params={'filter': 'all', 'state':'all', 'since': since},
auth=auth)
else:
issues = plugins.utils.github.get_all(source, plugins.utils.github.issues,
params={'filter': 'all', 'state':'all'},
auth=auth)
KibbleBit.pprint("Fetched %s issues for %s" %(str(len(issues)), source['sourceURL']))
for issue in issues:
if not issue['user']['login'] in people:
person = make_person(source, issue, plugins.utils.github.user(issue['user']['url'],
auth=auth))
people[issue['user']['login']] = person
update_person(KibbleBit, person)
if 'closed_by' in issue and not issue['closed_by']['login'] in people:
closer = make_person(source, issue, plugins.utils.github.user(issue['closed_by']['url'],
auth=auth))
people[issue['closed_by']['login']] = closer
update_person(KibbleBit, closer)
doc = make_issue(source, issue, people)
dhash = doc['id']
stored_change = None
if KibbleBit.exists('issue', dhash):
es_doc = KibbleBit.get('issue', dhash)
if not status_changed(es_doc, doc):
#KibbleBit.pprint("change %s seen already and status unchanged. Skipping." % issue['id'])
continue
update_issue(KibbleBit, doc)
source['steps']['issues'] = {
'time': time.time(),
'status': 'Issue scan completed at ' + time.strftime("%a, %d %b %Y %H:%M:%S +0000", time.gmtime()),
'running': False,
'good': True,
}
KibbleBit.updateSource(source)
except requests.HTTPError as e:
# If we errored out because of rate limiting, retry later, otherwise bail
if firstAttempt:
sleeps = 0
if plugins.utils.github.get_tokens_left(auth=auth) < 10:
KibbleBit.pprint("Hit rate limits, trying to sleep it off!")
while plugins.utils.github.get_tokens_left(auth=auth) < 10:
sleeps += 1
if sleeps > 24:
KibbleBit.pprint("Slept for too long without finding a reset rate limit, giving up!")
break
time.sleep(300) # Sleep 5 min, then check again..
# If we have tokens, try one more time...
if plugins.utils.github.get_tokens_left(auth=auth) > 10:
scan(KibbleBit, source, False) # If this one fails, bail completely
return
KibbleBit.pprint("HTTP Error, rate limit exceeded?")
source['steps']['issues'] = {
'time': time.time(),
'status': 'Issue scan failed at ' + time.strftime("%a, %d %b %Y %H:%M:%S +0000", time.gmtime()) + ": " + e.response.text,
'running': False,
'good': False,
}
KibbleBit.updateSource(source)