From 6f7732f06ab01bbb67443cc6270671fc1cd76860 Mon Sep 17 00:00:00 2001 From: zsloan Date: Mon, 2 Jul 2018 16:09:41 +0000 Subject: Added option to transform/normalize trait sample values (log2 and qnorm) on trait page Got figures mostly working with transformed values, except for changing the y-axis range of one Fixed issue with the home page "Make Default" button position (as well as the drop-downs in general) Added timeout to Elasticsearch connection to fix related error --- wqflask/utility/elasticsearch_tools.py | 2 +- wqflask/wqflask/marker_regression/gemma_mapping.py | 14 ++++-- wqflask/wqflask/show_trait/SampleList.py | 2 +- wqflask/wqflask/show_trait/show_trait.py | 42 +++++++++++++++++ .../wqflask/static/new/javascript/show_trait.js | 52 +++++++++++++++++++++- wqflask/wqflask/templates/index_page_orig.html | 44 +++++++++--------- wqflask/wqflask/templates/show_trait.html | 1 + .../wqflask/templates/show_trait_edit_data.html | 20 ++++++--- .../templates/show_trait_mapping_tools.html | 4 +- wqflask/wqflask/user_manager.py | 5 ++- 10 files changed, 147 insertions(+), 39 deletions(-) (limited to 'wqflask') diff --git a/wqflask/utility/elasticsearch_tools.py b/wqflask/utility/elasticsearch_tools.py index 293a9ae6..15cdd0bc 100644 --- a/wqflask/utility/elasticsearch_tools.py +++ b/wqflask/utility/elasticsearch_tools.py @@ -63,7 +63,7 @@ def get_elasticsearch_connection(for_user=True): es = Elasticsearch([{ "host": ELASTICSEARCH_HOST, "port": ELASTICSEARCH_PORT - }]) if (ELASTICSEARCH_HOST and ELASTICSEARCH_PORT) else None + }], timeout=30, retry_on_timeout=True) if (ELASTICSEARCH_HOST and ELASTICSEARCH_PORT) else None if for_user: setup_users_index(es) diff --git a/wqflask/wqflask/marker_regression/gemma_mapping.py b/wqflask/wqflask/marker_regression/gemma_mapping.py index dc13afc3..5ebab611 100644 --- a/wqflask/wqflask/marker_regression/gemma_mapping.py +++ b/wqflask/wqflask/marker_regression/gemma_mapping.py @@ -144,13 +144,16 @@ def parse_gemma_output(genofile_name): with open("{}{}_output.assoc.txt".format(webqtlConfig.GENERATED_IMAGE_DIR, genofile_name)) as output_file: for line in output_file: - if line.startswith("chr"): + if line.startswith("chr\t"): continue else: marker = {} marker['name'] = line.split("\t")[1] if line.split("\t")[0] != "X" and line.split("\t")[0] != "X/Y": - marker['chr'] = int(line.split("\t")[0]) + if "chr" in line.split("\t")[0]: + marker['chr'] = int(line.split("\t")[0][3:]) + else: + marker['chr'] = int(line.split("\t")[0]) else: marker['chr'] = line.split("\t")[0] marker['Mb'] = float(line.split("\t")[2]) / 1000000 @@ -186,13 +189,16 @@ def parse_loco_output(this_dataset, gwa_output_filename): for this_file in output_filelist: with open(this_file) as output_file: for line in output_file: - if line.startswith("chr"): + if line.startswith("chr\t"): continue else: marker = {} marker['name'] = line.split("\t")[1] if line.split("\t")[0] != "X" and line.split("\t")[0] != "X/Y": - marker['chr'] = int(line.split("\t")[0]) + if "chr" in line.split("\t")[0]: + marker['chr'] = int(line.split("\t")[0][3:]) + else: + marker['chr'] = int(line.split("\t")[0]) if marker['chr'] > previous_chr: previous_chr = marker['chr'] elif marker['chr'] < previous_chr: diff --git a/wqflask/wqflask/show_trait/SampleList.py b/wqflask/wqflask/show_trait/SampleList.py index 78bb3b42..8dbba530 100644 --- a/wqflask/wqflask/show_trait/SampleList.py +++ b/wqflask/wqflask/show_trait/SampleList.py @@ -37,7 +37,7 @@ class SampleList(object): self.get_attributes() - self.sample_qnorm = get_transform_vals(self.dataset, this_trait) + #self.sample_qnorm = get_transform_vals(self.dataset, this_trait) if self.this_trait and self.dataset and self.dataset.type == 'ProbeSet': self.get_extra_attribute_values() diff --git a/wqflask/wqflask/show_trait/show_trait.py b/wqflask/wqflask/show_trait/show_trait.py index d6d83c02..7b952af4 100644 --- a/wqflask/wqflask/show_trait/show_trait.py +++ b/wqflask/wqflask/show_trait/show_trait.py @@ -12,6 +12,8 @@ from collections import OrderedDict import redis Redis = redis.StrictRedis() +import scipy.stats as ss + from flask import Flask, g from htmlgen import HTMLgen2 as HT @@ -137,6 +139,8 @@ class ShowTrait(object): self.make_sample_lists() + self.qnorm_vals = quantile_normalize_vals(self.sample_groups) + # Todo: Add back in the ones we actually need from below, as we discover we need them hddn = OrderedDict() @@ -281,6 +285,44 @@ class ShowTrait(object): self.sample_groups = (primary_samples,) self.dataset.group.allsamples = all_samples_ordered +def quantile_normalize_vals(sample_groups): + def normf(trait_vals): + ranked_vals = ss.rankdata(trait_vals) + p_list = [] + for i, val in enumerate(trait_vals): + p_list.append(((i+1) - 0.5)/len(trait_vals)) + + z = ss.norm.ppf(p_list) + normed_vals = [] + for rank in ranked_vals: + normed_vals.append("%0.3f" % z[int(rank)-1]) + + return normed_vals + + qnorm_by_group = [] + for sample_type in sample_groups: + trait_vals = [] + for sample in sample_type.sample_list: + try: + trait_vals.append(float(sample.value)) + except: + continue + + qnorm_vals = normf(trait_vals) + + qnorm_vals_with_x = [] + counter = 0 + for sample in sample_type.sample_list: + if sample.display_value == "x": + qnorm_vals_with_x.append("x") + else: + qnorm_vals_with_x.append(qnorm_vals[counter]) + counter += 1 + + qnorm_by_group.append(qnorm_vals_with_x) + + return qnorm_by_group + def get_nearest_marker(this_trait, this_db): this_chr = this_trait.locus_chr logger.debug("this_chr:", this_chr) diff --git a/wqflask/wqflask/static/new/javascript/show_trait.js b/wqflask/wqflask/static/new/javascript/show_trait.js index 17afc814..5e2ecc33 100644 --- a/wqflask/wqflask/static/new/javascript/show_trait.js +++ b/wqflask/wqflask/static/new/javascript/show_trait.js @@ -549,6 +549,7 @@ }; $('#block_outliers').click(block_outliers); reset_samples_table = function() { + $('input[name="transform"]').val(""); return $('.trait_value_input').each((function(_this) { return function(_index, element) { console.log("value is:", $(element).val()); @@ -559,6 +560,52 @@ })(this)); }; $('#reset').click(reset_samples_table); + + log_normalize_data = function() { + return $('.trait_value_input').each((function(_this) { + return function(_index, element) { + current_value = $(element).data("value"); + if(isNaN(current_value)) { + return current_value + } else { + $(element).val(Math.log2(current_value).toFixed(3)); + return Math.log2(current_value).toFixed(3) + } + }; + })(this)); + }; + + qnorm_data = function() { + return $('.trait_value_input').each((function(_this) { + return function(_index, element) { + current_value = $(element).data("value"); + if(isNaN(current_value)) { + return current_value + } else { + $(element).val($(element).data("qnorm")); + return $(element).data("qnorm"); + } + }; + })(this)); + }; + + normalize_data = function() { + if ($('#norm_method option:selected').val() == 'log2'){ + if ($('input[name="transform"]').val() != "log2") { + log_normalize_data() + $('input[name="transform"]').val("log2") + } + } + else if ($('#norm_method option:selected').val() == 'qnorm'){ + if ($('input[name="transform"]').val() != "qnorm") { + qnorm_data() + $('input[name="transform"]').val("qnorm") + } + } + } + + $('#normalize').click(normalize_data); + switch_qnorm_data = function() { return $('.trait_value_input').each((function(_this) { return function(_index, element) { @@ -734,7 +781,7 @@ box_data = [trace1, trace2, trace3] } else { var box_layout = { - width: 500, + width: 300, height: 500, margin: { l: 50, @@ -834,7 +881,7 @@ var layout = { yaxis: { - range: [range_bottom, range_top] + range: [range_bottom, range_top], }, width: 1200, height: 500, @@ -884,6 +931,7 @@ $('#block_outliers').click(edit_data_change); $('#reset').click(edit_data_change); $('#qnorm').click(edit_data_change); + $('#normalize').click(edit_data_change); return console.log("end"); }); diff --git a/wqflask/wqflask/templates/index_page_orig.html b/wqflask/wqflask/templates/index_page_orig.html index 2a5556ea..dba3e266 100755 --- a/wqflask/wqflask/templates/index_page_orig.html +++ b/wqflask/wqflask/templates/index_page_orig.html @@ -34,11 +34,11 @@