blob: 7871ddda414a26be1c0c85bd08e4acede8b654b6 [file] [log] [blame]
import sys
if sys.version_info < (3, 2):
raise Exception("Python 3.2 or above is required")
import pickle
import pprint
from string import Template
import datetime
import getpass
import argparse
import textwrap
import calendar
import xmlrpc
import xmlrpc.client
import json
import os
from report_timeline import Timeline
'''
'clutch2report' reads the pickle file which was created by 'clutch' and generates
a shell for a monthly report for the incubator.
'''
months2groups = [ 'group-1', 'group-2', 'group-3',
'group-1', 'group-2', 'group-3',
'group-1', 'group-2', 'group-3',
'group-1', 'group-2', 'group-3']
boilerplate = """
= Incubator PMC report for {month} {year} =
=== Timeline ===
{timeline}
=== Shepherd Assignments ===
{shepherds}
=== Report content ===
{{{{{{
Incubator PMC report for {month} {year}
The Apache Incubator is the entry path into the ASF for projects and
codebases wishing to become part of the Foundation's efforts.
< narrative >
* Community
New IPMC members:
People who left the IPMC:
* New Podlings
* Graduations
The board has motions for the following:
* Releases
The following releases entered distribution during the month of
{last_month}:
* IP Clearance
* Legal / Trademarks
* Infrastructure
* Miscellaneous
* Credits
- Report Manager:
-------------------- Summary of podling reports --------------------
* Still getting started at the Incubator
* Not yet ready to graduate
No release:
Community growth:
* Ready to graduate
The Board has motions for the following:
* Did not report, expected next month
----------------------------------------------------------------------
Table of Contents
{toc}
----------------------------------------------------------------------
"""
perproject = """
--------------------
$name
$description
$name has been incubating since $start.
Three most important issues to address in the move towards graduation:
1.
2.
3.
Any issues that the Incubator PMC (IPMC) or ASF Board wish/need to be
aware of?
How has the community developed since the last report?
How has the project developed since the last report?
Date of last release:
XXXX-XX-XX
When were the last committers or PMC members elected?
Signed-off-by:
$mentorlist
Shepherd/Mentor notes:
"""
def push(pagename, reportFile):
print("Publishing " + pagename)
name = input("Username for wiki.apache.org/incubator: ")
password = getpass.getpass("Password for wiki.apache.org/incubator: ")
report = open(reportFile, 'r')
reportcontent = report.read(-1)
report.close()
srcwiki = xmlrpc.client.ServerProxy("http://wiki.apache.org/incubator/?action=xmlrpc2")
token = srcwiki.getAuthToken(name, password)
pushresults = srcwiki.system.multicall([{'methodName':'applyAuthToken', 'params': [token]},
{'methodName':'putPage', 'params': [pagename, reportcontent]}])
print(pushresults)
def cliargs():
parser = argparse.ArgumentParser(description='Create (and optionally push) a template for an incubator report.')
parser.add_argument('--upload', action='store_true',
help='whether to upload the report template.')
parser.add_argument('--month', type=int, help='the month to report for, defaults to current month.', default=0)
return parser.parse_args() # note that this exits on errors.
def gen_shepherd_assignments(projects, month, year):
# Load the shepherd assignments data for this month's report.
now = datetime.datetime.now()
date = "{0:04d}-{1:02d}".format(year, month)
assignments_path = os.path.join("content", "shepherd_assignments.json")
with open(assignments_path, "r") as f:
assignments_data = json.load(f)
if date not in assignments_data:
print("Shepherds have not yet been assigned for {}.".format(date))
print("Please run `assign_shepherds.py --month={}`".format(month))
sys.exit(1)
report = assignments_data[date]
# Load the roster of active shepherds, which we'll use to get full names.
shepherds_path = os.path.join("content", "shepherds.json")
with open(shepherds_path, "r") as f:
shepherds_data = json.load(f)
shepherds = {}
for shepherd in shepherds_data:
shepherds[shepherd['apache_id']] = shepherd
# Generate and return the wikified list of assignments.
lines = []
for podling_id, shepherd_id in report.items():
podling_name = projects[podling_id]['fullName']
shepherd_name = '[none]'
if shepherd_id in shepherds:
shepherd_name = shepherds[shepherd_id]['name']
lines.append("||{} ||{} ||".format(shepherd_name, podling_name))
lines.sort()
return "\n".join(lines)
def main():
options = cliargs()
now = datetime.datetime.now()
if options.month == 0:
month = now.month + 1
else:
month = options.month
last_month = ((now.month + 11) % 12) + 1
year = now.year if month >= now.month else now.year + 1
curGroup = months2groups[month - 1]
inputFile = open('clutch.pkl', 'rb')
projects = pickle.load(inputFile)
inputFile.close()
timeline = Timeline(month).to_moin()
shepherds = gen_shepherd_assignments(projects, month, year)
output = open('report.txt', 'w')
toc = ""
for project in sorted(projects.keys()):
pdata = projects[project]
if pdata['rawReportingGroup'] == curGroup or pdata['reportingMonthly']:
toc = toc + projects[project]['fullName'] + "\n"
output.write(boilerplate.format(month=calendar.month_name[month],
last_month=calendar.month_name[last_month],
year=year, toc=toc, shepherds=shepherds,
timeline=timeline))
ptemplate = Template(perproject)
for project in sorted(projects.keys()):
pdata = projects[project]
if pdata['rawReportingGroup'] == curGroup or pdata['reportingMonthly']:
mentor_boxes = []
for mentor in pdata['mentors']:
mentor_box = "[ ]({0}) {1}".format(project, mentor)
mentor_boxes.append(mentor_box)
mentorlist = "\n ".join(mentor_boxes)
description = textwrap.fill(pdata['description'], 78)
pdict = { 'name': pdata['fullName'],
'description': description,
'start': pdata['startDate'],
'mentorlist' : mentorlist}
output.write(ptemplate.substitute(pdict))
# Close `Report Content` section.
output.write("\n}}}\n")
output.close()
if options.upload:
push("{0}{1}".format(calendar.month_name[month], year), 'report.txt')
if __name__ == "__main__":
main()