mirror of
https://github.com/YunoHost/tartiflette.git
synced 2024-09-03 20:06:08 +02:00
Adding roadmapProgressBar as a dirty subfolder
This commit is contained in:
parent
f7d624d068
commit
8a70a4216e
5 changed files with 302 additions and 0 deletions
90
roadmapProgressBar/analyze.py
Executable file
90
roadmapProgressBar/analyze.py
Executable file
|
@ -0,0 +1,90 @@
|
|||
#!/usr/bin/python3
|
||||
|
||||
import json
|
||||
from bs4 import BeautifulSoup
|
||||
|
||||
|
||||
status_filters = {
|
||||
"all": None,
|
||||
"new": ["New", "Confirmed"],
|
||||
"ongoing": ["In Progress"],
|
||||
"done": ["Closed", "Resolved", "Rejected"]
|
||||
}
|
||||
|
||||
type_filters = {
|
||||
"all": None,
|
||||
"Bug": "Bug",
|
||||
"Feature": "Feature",
|
||||
"Improve": "Improvement",
|
||||
"Doc": "Documentation"
|
||||
}
|
||||
|
||||
|
||||
|
||||
def parse_issues():
|
||||
|
||||
soup = BeautifulSoup(open("data/raw_roadmapissues.xml").read(), "lxml")
|
||||
|
||||
issues = []
|
||||
|
||||
for issue in soup.issues:
|
||||
cleaned_issue = {}
|
||||
cleaned_issue["id"] = issue.id.text
|
||||
cleaned_issue["priority"] = issue.priority["name"]
|
||||
cleaned_issue["status"] = issue.status["name"]
|
||||
cleaned_issue["type"] = issue.tracker["name"]
|
||||
|
||||
issues.append(cleaned_issue)
|
||||
|
||||
return issues
|
||||
|
||||
|
||||
def filtered_issues(issues, status_filter=None, type_filter=None):
|
||||
|
||||
issues_filtered = issues
|
||||
if status_filter != None:
|
||||
issues_filtered = [ issue for issue in issues_filtered if issue["status"] in status_filter]
|
||||
|
||||
if type_filter != None:
|
||||
issues_filtered = [ issue for issue in issues_filtered if issue["type"] == type_filter ]
|
||||
|
||||
return len(issues_filtered)
|
||||
|
||||
|
||||
def main():
|
||||
|
||||
issues = parse_issues()
|
||||
summary = {}
|
||||
|
||||
for type_name, type_filter in type_filters.items():
|
||||
|
||||
summary[type_name] = {}
|
||||
|
||||
for status_name, status_filter in status_filters.items():
|
||||
|
||||
summary[type_name][status_name] = filtered_issues(issues, status_filter,
|
||||
type_filter)
|
||||
|
||||
for type_name, type_filter in type_filters.items():
|
||||
|
||||
for status_name, status_filter in status_filters.items():
|
||||
|
||||
if (status_name != "all"):
|
||||
|
||||
n = summary[type_name][status_name]
|
||||
p = float("{0:.1f}".format(100 * n / summary[type_name]["all"]))
|
||||
summary[type_name][status_name] = (n,p)
|
||||
|
||||
if (type_name != "all"):
|
||||
n = summary[type_name]["all"]
|
||||
p = float("{0:.1f}".format(100 * n / summary["all"]["all"]))
|
||||
summary[type_name]["all"] = (n,p)
|
||||
|
||||
|
||||
|
||||
with open("summary.json", "w") as f:
|
||||
f.write(json.dumps(summary))
|
||||
|
||||
|
||||
main()
|
||||
|
0
roadmapProgressBar/data/.gitkeep
Normal file
0
roadmapProgressBar/data/.gitkeep
Normal file
14
roadmapProgressBar/fetch.py
Executable file
14
roadmapProgressBar/fetch.py
Executable file
|
@ -0,0 +1,14 @@
|
|||
#!/usr/bin/python3
|
||||
|
||||
import requests
|
||||
import json
|
||||
|
||||
def get_roadmapissues():
|
||||
|
||||
roadmapissues = requests.get("https://dev.yunohost.org/issues.xml?fixed_version_id=11&status_id=*&limit=100")
|
||||
|
||||
|
||||
with open("data/raw_roadmapissues.xml", "w") as f:
|
||||
f.write(roadmapissues.text)
|
||||
|
||||
get_roadmapissues()
|
44
roadmapProgressBar/publish.py
Executable file
44
roadmapProgressBar/publish.py
Executable file
|
@ -0,0 +1,44 @@
|
|||
#!/usr/bin/python3
|
||||
|
||||
import os
|
||||
import json
|
||||
|
||||
from jinja2 import Template
|
||||
from ansi2html import Ansi2HTMLConverter
|
||||
from ansi2html.style import get_styles
|
||||
|
||||
###############################################################################
|
||||
|
||||
output_dir = "./www/"
|
||||
|
||||
template_path = os.path.join(output_dir,"template.html")
|
||||
output_path = os.path.join(output_dir,"index.html")
|
||||
|
||||
summary_path = os.path.join("./", "summary.json")
|
||||
|
||||
###############################################################################
|
||||
|
||||
conv = Ansi2HTMLConverter()
|
||||
shell_css = "\n".join(map(str, get_styles(conv.dark_bg, conv.scheme)))
|
||||
|
||||
def shell_to_html(shell):
|
||||
return conv.convert(shell, False)
|
||||
|
||||
###############################################################################
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
# Fetch the list of all reports, sorted in reverse-chronological order
|
||||
|
||||
summary = json.load(open(summary_path))
|
||||
|
||||
# Generate the output using the template
|
||||
|
||||
template = open(template_path, "r").read()
|
||||
t = Template(template)
|
||||
|
||||
result = t.render(data=summary, convert=shell_to_html, shell_css=shell_css)
|
||||
|
||||
open(output_path, "w").write(result)
|
||||
|
||||
print("Done.")
|
154
roadmapProgressBar/www/template.html
Normal file
154
roadmapProgressBar/www/template.html
Normal file
|
@ -0,0 +1,154 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta http-equiv="content-type" content="text/html; charset=UTF-8">
|
||||
<meta charset="utf-8">
|
||||
<title>Yunohost Pull Requests Dashboard</title>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<link rel="stylesheet" href="css/bootstrap.css" media="screen">
|
||||
<link rel="stylesheet" href="skins/eden.css" media="screen">
|
||||
<link href="//maxcdn.bootstrapcdn.com/font-awesome/4.3.0/css/font-awesome.min.css" rel="stylesheet">
|
||||
<link href="css/animate.css" rel="stylesheet">
|
||||
|
||||
<style>
|
||||
.navbar-holder-dark{
|
||||
padding: 20px 20px 200px 20px;
|
||||
background: #333333;
|
||||
}
|
||||
.progress .progress-bar {
|
||||
padding-top:5px;
|
||||
font-size:16px;
|
||||
font-weight: 600;
|
||||
}
|
||||
.progress-bar-none {
|
||||
background-color:transparent;
|
||||
color: #2c3e50;
|
||||
}
|
||||
.issue-legend {
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
max-width: 100%;
|
||||
text-align: center;
|
||||
font-weight: bold;
|
||||
margin-bottom:20px;
|
||||
}
|
||||
</style>
|
||||
|
||||
</head>
|
||||
<body>
|
||||
|
||||
|
||||
<div class="container">
|
||||
|
||||
<div class="page-header" id="banner">
|
||||
<div class="row">
|
||||
<h1>Yunohost Roadmap Dashboard</h1>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<h3>2.6.x</h3>
|
||||
|
||||
<div class="row">
|
||||
|
||||
<div class="col-md-offset-1 col-md-10">
|
||||
|
||||
<div class="issue-legend">All ({{data.all.all}} issues) </div>
|
||||
<div class="bs-component">
|
||||
<div class="progress">
|
||||
<div class="progress-bar progress-bar-success" style="width:
|
||||
{{data.all.done[1]}}%">{{data.all.done[0]}} done</div>
|
||||
<div class="progress-bar progress-bar-warning" style="width:
|
||||
{{data.all.ongoing[1]}}%">{{data.all.ongoing[0]}}
|
||||
ongoing</div>
|
||||
<div class="progress-bar progress-bar-none" style="width:
|
||||
{{data.all.new[1]}}%">{{data.all.new[0]}} new</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% for type, statuses in data.items() %}
|
||||
{% if type != "all" %}
|
||||
<div class="bs-component" style="display:inline-block; width: {{
|
||||
statuses.all[1]-0.5 }}%" >
|
||||
<div class="progress">
|
||||
<div class="progress-bar progress-bar-success" style="width: {{statuses.done[1]}}%">
|
||||
{{ statuses.done[0] }}
|
||||
</div>
|
||||
<div class="progress-bar progress-bar-warning" style="width: {{statuses.ongoing[1]}}%">
|
||||
{{ statuses.ongoing[0] }}
|
||||
</div>
|
||||
<div class="progress-bar progress-bar-none" style="width:
|
||||
{{statuses.new[1]}}%">
|
||||
{{ statuses.new[0] }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="issue-legend">{{ type }}<br> ({{ statuses.all[0]
|
||||
}})</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
|
||||
</div>
|
||||
|
||||
<div class="col-md-offset-1 col-md-10">
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<footer>
|
||||
<div class="row">
|
||||
<div class="col-lg-12">
|
||||
<hr/>
|
||||
<p>CSS Skin/boilerplate/whatever you call it : <a href="http://scripteden.com/" rel="nofollow">Script Eden</a>.</p>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</footer>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<script src="https://code.jquery.com/jquery-2.1.3.min.js"></script>
|
||||
<script src="js/bootstrap.min.js"></script>
|
||||
|
||||
<script>
|
||||
function filter(team) {
|
||||
// Declare variables
|
||||
var input, filter, table, tr, td, i;
|
||||
table = document.getElementById("thePRlist");
|
||||
tr = table.getElementsByTagName("tr");
|
||||
// Loop through all table rows, and hide those who don't match the search query
|
||||
for (i = 0; i < tr.length; i++)
|
||||
{
|
||||
if (team == '') { tr[i].style.display = ""; }
|
||||
else if (tr[i].classList == "") { tr[i].style.display = ""; }
|
||||
else if (tr[i].classList.contains(team)) { tr[i].style.display = ""; }
|
||||
else { tr[i].style.display = "none"; }
|
||||
}
|
||||
|
||||
selector = document.getElementById("select-team");
|
||||
li = selector.getElementsByTagName("li");
|
||||
|
||||
if (team == "") { team = "team-all"; }
|
||||
|
||||
for (i = 0; i < li.length; i++)
|
||||
{
|
||||
if (li[i].getAttribute("id") == "select-".concat(team))
|
||||
{
|
||||
li[i].classList.add("active");
|
||||
}
|
||||
else
|
||||
{
|
||||
li[i].classList.remove("active");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
</script>
|
||||
|
||||
</body>
|
||||
</html>
|
Loading…
Reference in a new issue