looper 1.5.0__py3-none-any.whl → 1.6.0a1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- looper/__init__.py +3 -498
- looper/__main__.py +2 -2
- looper/_version.py +1 -1
- looper/cli_divvy.py +182 -0
- looper/cli_looper.py +776 -0
- looper/conductor.py +53 -206
- looper/const.py +51 -3
- looper/divvy.py +28 -196
- looper/exceptions.py +18 -0
- looper/looper.py +177 -612
- looper/plugins.py +160 -0
- looper/processed_project.py +1 -1
- looper/project.py +229 -117
- looper/utils.py +119 -43
- {looper-1.5.0.dist-info → looper-1.6.0a1.dist-info}/METADATA +6 -6
- {looper-1.5.0.dist-info → looper-1.6.0a1.dist-info}/RECORD +20 -20
- {looper-1.5.0.dist-info → looper-1.6.0a1.dist-info}/WHEEL +1 -1
- looper/html_reports.py +0 -1057
- looper/html_reports_pipestat.py +0 -924
- looper/html_reports_project_pipestat.py +0 -269
- {looper-1.5.0.dist-info → looper-1.6.0a1.dist-info}/LICENSE.txt +0 -0
- {looper-1.5.0.dist-info → looper-1.6.0a1.dist-info}/entry_points.txt +0 -0
- {looper-1.5.0.dist-info → looper-1.6.0a1.dist-info}/top_level.txt +0 -0
@@ -1,269 +0,0 @@
|
|
1
|
-
import glob
|
2
|
-
import logging
|
3
|
-
import os
|
4
|
-
|
5
|
-
from eido import read_schema
|
6
|
-
from peppy.const import *
|
7
|
-
|
8
|
-
from ._version import __version__ as v
|
9
|
-
from .const import *
|
10
|
-
from .exceptions import PipelineInterfaceConfigError
|
11
|
-
from .html_reports_pipestat import (
|
12
|
-
HTMLReportBuilder,
|
13
|
-
fetch_pipeline_results,
|
14
|
-
get_jinja_env,
|
15
|
-
render_jinja_template,
|
16
|
-
save_html,
|
17
|
-
)
|
18
|
-
from .pipeline_interface import PipelineInterface
|
19
|
-
|
20
|
-
_LOGGER = logging.getLogger("looper")
|
21
|
-
|
22
|
-
|
23
|
-
class HTMLReportBuilderProject(object):
|
24
|
-
"""Generate HTML summary report for project/samples"""
|
25
|
-
|
26
|
-
def __init__(self, prj):
|
27
|
-
"""
|
28
|
-
The Project defines the instance.
|
29
|
-
|
30
|
-
:param looper.Project prj: Project with which to work/operate on
|
31
|
-
:param bool project_level: whether to generate a project-level
|
32
|
-
pipeline report
|
33
|
-
"""
|
34
|
-
super(HTMLReportBuilderProject, self).__init__()
|
35
|
-
self.prj = prj
|
36
|
-
self.j_env = get_jinja_env()
|
37
|
-
self.output_dir = self.prj.output_dir
|
38
|
-
self.reports_dir = os.path.join(self.output_dir, "reports")
|
39
|
-
_LOGGER.debug(f"Reports dir: {self.reports_dir}")
|
40
|
-
|
41
|
-
def __call__(self, piface_source):
|
42
|
-
"""
|
43
|
-
Generate HTML report.
|
44
|
-
|
45
|
-
:param str piface_source: path to the pipeline interface defining
|
46
|
-
connection to the pipeline to generate the report for
|
47
|
-
:return str: path to the index page of the generated HTML report
|
48
|
-
"""
|
49
|
-
# Generate HTML report
|
50
|
-
self.prj_piface_source = piface_source
|
51
|
-
self.prj_piface = PipelineInterface(config=self.prj_piface_source)
|
52
|
-
self.amendments_str = (
|
53
|
-
"_".join(self.prj.amendments) if self.prj.amendments else ""
|
54
|
-
)
|
55
|
-
self.pipeline_reports = os.path.join(
|
56
|
-
self.reports_dir,
|
57
|
-
f"{self.prj_piface.pipeline_name}_{self.amendments_str}"
|
58
|
-
if self.prj.amendments
|
59
|
-
else self.prj_piface.pipeline_name,
|
60
|
-
)
|
61
|
-
pifaces = self.prj.project_pipeline_interfaces
|
62
|
-
selected_pipeline_pifaces = [
|
63
|
-
p for p in pifaces if p.pipeline_name == self.prj_piface.pipeline_name
|
64
|
-
]
|
65
|
-
schema_path = self.prj.get_schemas(
|
66
|
-
selected_pipeline_pifaces, OUTPUT_SCHEMA_KEY
|
67
|
-
)[0]
|
68
|
-
self.schema = read_schema(schema_path)[0]
|
69
|
-
self.index_html_path = os.path.join(
|
70
|
-
self.pipeline_reports, f"{self.prj.name}.html"
|
71
|
-
)
|
72
|
-
linked_sample_reports = {}
|
73
|
-
html_report_builder = HTMLReportBuilder(prj=self.prj)
|
74
|
-
for sample_piface_source in self.prj.linked_sample_interfaces[
|
75
|
-
self.prj_piface_source
|
76
|
-
]:
|
77
|
-
# Do the stats and object summarization.
|
78
|
-
pipeline_name = PipelineInterface(sample_piface_source).pipeline_name
|
79
|
-
# run the report builder. a set of HTML pages is produced
|
80
|
-
report_path = html_report_builder(
|
81
|
-
pipeline_name=pipeline_name, project_index_html=self.index_html_path
|
82
|
-
)
|
83
|
-
if pipeline_name in linked_sample_reports:
|
84
|
-
raise PipelineInterfaceConfigError(
|
85
|
-
f"Duplicate pipeline_names found in pipeline interfaces "
|
86
|
-
f"defined for samples in this project: {pipeline_name}"
|
87
|
-
)
|
88
|
-
linked_sample_reports[pipeline_name] = os.path.relpath(
|
89
|
-
report_path, self.pipeline_reports
|
90
|
-
)
|
91
|
-
_LOGGER.info(
|
92
|
-
f"Sample-level '{pipeline_name}' pipeline HTML report: "
|
93
|
-
f"{report_path}"
|
94
|
-
)
|
95
|
-
print(f"{linked_sample_reports}")
|
96
|
-
sample_reps_parent = os.path.join(self.pipeline_reports, "sample_reports.html")
|
97
|
-
sample_reports_parent_relpath = os.path.relpath(
|
98
|
-
sample_reps_parent, self.pipeline_reports
|
99
|
-
)
|
100
|
-
navbar = self.create_navbar(
|
101
|
-
navbar_links=self.create_navbar_links(
|
102
|
-
sample_reports_parent_relpath=sample_reports_parent_relpath
|
103
|
-
),
|
104
|
-
index_html_relpath=os.path.basename(self.index_html_path),
|
105
|
-
)
|
106
|
-
save_html(
|
107
|
-
path=sample_reps_parent,
|
108
|
-
template=self.create_sample_reports_parent(
|
109
|
-
linked_sample_reports=linked_sample_reports,
|
110
|
-
navbar=navbar,
|
111
|
-
footer=self.create_footer(),
|
112
|
-
),
|
113
|
-
)
|
114
|
-
self.create_index_html(navbar=navbar, footer=self.create_footer())
|
115
|
-
return self.index_html_path
|
116
|
-
|
117
|
-
def create_navbar_links(self, sample_reports_parent_relpath):
|
118
|
-
template_vars = dict(
|
119
|
-
status_html_page=None,
|
120
|
-
dropdown_keys_objects=None,
|
121
|
-
objects_html_page=None,
|
122
|
-
samples_html_page=None,
|
123
|
-
sample_names=None,
|
124
|
-
all_samples=None,
|
125
|
-
all_objects=None,
|
126
|
-
sample_reports_parent=sample_reports_parent_relpath,
|
127
|
-
project_report=None,
|
128
|
-
)
|
129
|
-
_LOGGER.debug(f"navbar_links.html | template_vars:\n{template_vars}")
|
130
|
-
return render_jinja_template("navbar_links.html", self.j_env, template_vars)
|
131
|
-
|
132
|
-
def create_sample_reports_parent(self, linked_sample_reports, navbar, footer):
|
133
|
-
template_vars = dict(
|
134
|
-
navbar=navbar,
|
135
|
-
footer=footer,
|
136
|
-
header="Linked sample pipelines",
|
137
|
-
labels=list(linked_sample_reports.keys()),
|
138
|
-
pages=list(linked_sample_reports.values()),
|
139
|
-
)
|
140
|
-
_LOGGER.debug(f"navbar_list_parent.html | template_vars: \n{template_vars}")
|
141
|
-
return render_jinja_template(
|
142
|
-
"navbar_list_parent.html", self.j_env, template_vars
|
143
|
-
)
|
144
|
-
|
145
|
-
def create_footer(self):
|
146
|
-
"""
|
147
|
-
Renders the footer from the templates directory
|
148
|
-
|
149
|
-
:return str: footer HTML
|
150
|
-
"""
|
151
|
-
return render_jinja_template("footer.html", self.j_env, dict(version=v))
|
152
|
-
|
153
|
-
def create_navbar(self, navbar_links, index_html_relpath):
|
154
|
-
"""
|
155
|
-
Creates the navbar using the provided links
|
156
|
-
|
157
|
-
:param str navbar_links: HTML list of links to be inserted into a navbar
|
158
|
-
:return str: navbar HTML
|
159
|
-
"""
|
160
|
-
template_vars = dict(navbar_links=navbar_links, index_html=index_html_relpath)
|
161
|
-
return render_jinja_template("navbar.html", self.j_env, template_vars)
|
162
|
-
|
163
|
-
def create_index_html(self, navbar, footer):
|
164
|
-
project_stat_results = fetch_pipeline_results(
|
165
|
-
project=self.prj,
|
166
|
-
pipeline_name=self.prj_piface.pipeline_name,
|
167
|
-
inclusion_fun=lambda x: x not in OBJECT_TYPES,
|
168
|
-
casting_fun=str,
|
169
|
-
)
|
170
|
-
return self.create_sample_html(project_stat_results, navbar, footer)
|
171
|
-
|
172
|
-
def create_sample_html(self, sample_stats, navbar, footer):
|
173
|
-
"""
|
174
|
-
Produce an HTML page containing all of a sample's objects
|
175
|
-
and the sample summary statistics
|
176
|
-
|
177
|
-
:param dict sample_stats: pipeline run statistics for the current sample
|
178
|
-
:param str navbar: HTML to be included as the navbar in the main summary page
|
179
|
-
:param str footer: HTML to be included as the footer
|
180
|
-
:return str: path to the produced HTML page
|
181
|
-
"""
|
182
|
-
if not os.path.exists(self.pipeline_reports):
|
183
|
-
os.makedirs(self.pipeline_reports)
|
184
|
-
|
185
|
-
sample_name = self.prj.name
|
186
|
-
html_page = os.path.join(self.pipeline_reports, f"{sample_name}.html".lower())
|
187
|
-
|
188
|
-
psms = self.prj.get_pipestat_managers(project_level=True)
|
189
|
-
psm = psms[self.prj_piface.pipeline_name]
|
190
|
-
flag = psm.get_status()
|
191
|
-
if not flag:
|
192
|
-
button_class = "btn btn-secondary"
|
193
|
-
flag = "Missing"
|
194
|
-
else:
|
195
|
-
try:
|
196
|
-
flag_dict = BUTTON_APPEARANCE_BY_FLAG[flag]
|
197
|
-
except KeyError:
|
198
|
-
button_class = "btn btn-secondary"
|
199
|
-
flag = "Unknown"
|
200
|
-
else:
|
201
|
-
button_class = flag_dict["button_class"]
|
202
|
-
flag = flag_dict["flag"]
|
203
|
-
highlighted_results = fetch_pipeline_results(
|
204
|
-
project=self.prj,
|
205
|
-
pipeline_name=self.prj_piface.pipeline_name,
|
206
|
-
sample_name=None,
|
207
|
-
inclusion_fun=lambda x: x == "file",
|
208
|
-
highlighted=True,
|
209
|
-
)
|
210
|
-
|
211
|
-
for k in highlighted_results.keys():
|
212
|
-
highlighted_results[k]["path"] = os.path.relpath(
|
213
|
-
highlighted_results[k]["path"], self.pipeline_reports
|
214
|
-
)
|
215
|
-
|
216
|
-
links = []
|
217
|
-
file_results = fetch_pipeline_results(
|
218
|
-
project=self.prj,
|
219
|
-
pipeline_name=self.prj_piface.pipeline_name,
|
220
|
-
sample_name=None,
|
221
|
-
inclusion_fun=lambda x: x == "file",
|
222
|
-
)
|
223
|
-
for result_id, result in file_results.items():
|
224
|
-
desc = (
|
225
|
-
self.schema[result_id]["description"]
|
226
|
-
if "description" in self.schema[result_id]
|
227
|
-
else ""
|
228
|
-
)
|
229
|
-
links.append(
|
230
|
-
[
|
231
|
-
f"<b>{result['title']}</b>: {desc}",
|
232
|
-
os.path.relpath(result["path"], self.pipeline_reports),
|
233
|
-
]
|
234
|
-
)
|
235
|
-
image_results = fetch_pipeline_results(
|
236
|
-
project=self.prj,
|
237
|
-
pipeline_name=self.prj_piface.pipeline_name,
|
238
|
-
sample_name=None,
|
239
|
-
inclusion_fun=lambda x: x == "image",
|
240
|
-
)
|
241
|
-
figures = []
|
242
|
-
for result_id, result in image_results.items():
|
243
|
-
figures.append(
|
244
|
-
[
|
245
|
-
os.path.relpath(result["path"], self.pipeline_reports),
|
246
|
-
result["title"],
|
247
|
-
os.path.relpath(result["thumbnail_path"], self.pipeline_reports),
|
248
|
-
]
|
249
|
-
)
|
250
|
-
|
251
|
-
template_vars = dict(
|
252
|
-
report_class="Project",
|
253
|
-
navbar=navbar,
|
254
|
-
footer=footer,
|
255
|
-
sample_name=sample_name,
|
256
|
-
links=links,
|
257
|
-
figures=figures,
|
258
|
-
highlighted_results=highlighted_results,
|
259
|
-
button_class=button_class,
|
260
|
-
sample_stats=sample_stats,
|
261
|
-
flag=flag,
|
262
|
-
pipeline_name=self.prj_piface.pipeline_name,
|
263
|
-
amendments=self.prj.amendments,
|
264
|
-
)
|
265
|
-
_LOGGER.debug(f"sample.html | template_vars:\n{template_vars}")
|
266
|
-
save_html(
|
267
|
-
html_page, render_jinja_template("sample.html", self.j_env, template_vars)
|
268
|
-
)
|
269
|
-
return html_page
|
File without changes
|
File without changes
|
File without changes
|