looper 1.5.1__py3-none-any.whl → 1.6.0a1__py3-none-any.whl

Sign up to get free protection for your applications and to get access to all the features.
@@ -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