lazar-gui 1.0.0
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.
- checksums.yaml +7 -0
- data/.gitignore +3 -0
- data/FAQ.md +29 -0
- data/Gemfile +7 -0
- data/README.md +15 -0
- data/VERSION +1 -0
- data/application.rb +317 -0
- data/bin/lazar-start +5 -0
- data/bin/lazar-start.sh +8 -0
- data/bin/lazar-stop +6 -0
- data/bin/lazar-stop.sh +52 -0
- data/config.ru +5 -0
- data/helper.rb +218 -0
- data/lazar-gui.gemspec +29 -0
- data/public/css/bootstrap-theme.min.css +5 -0
- data/public/css/bootstrap.min.css +5 -0
- data/public/css/images/black-asc.gif +0 -0
- data/public/css/images/black-desc.gif +0 -0
- data/public/css/images/black-unsorted.gif +0 -0
- data/public/css/images/bootstrap-black-unsorted.png +0 -0
- data/public/css/images/bootstrap-white-unsorted.png +0 -0
- data/public/css/images/dragtable-handle.png +0 -0
- data/public/css/images/dragtable-handle.svg +7 -0
- data/public/css/images/dropbox-asc-hovered.png +0 -0
- data/public/css/images/dropbox-asc.png +0 -0
- data/public/css/images/dropbox-desc-hovered.png +0 -0
- data/public/css/images/dropbox-desc.png +0 -0
- data/public/css/images/first.png +0 -0
- data/public/css/images/green-asc.gif +0 -0
- data/public/css/images/green-desc.gif +0 -0
- data/public/css/images/green-header.gif +0 -0
- data/public/css/images/green-unsorted.gif +0 -0
- data/public/css/images/ice-asc.gif +0 -0
- data/public/css/images/ice-desc.gif +0 -0
- data/public/css/images/ice-unsorted.gif +0 -0
- data/public/css/images/last.png +0 -0
- data/public/css/images/loading.gif +0 -0
- data/public/css/images/metro-black-asc.png +0 -0
- data/public/css/images/metro-black-desc.png +0 -0
- data/public/css/images/metro-loading.gif +0 -0
- data/public/css/images/metro-unsorted.png +0 -0
- data/public/css/images/metro-white-asc.png +0 -0
- data/public/css/images/metro-white-desc.png +0 -0
- data/public/css/images/next.png +0 -0
- data/public/css/images/prev.png +0 -0
- data/public/css/images/white-asc.gif +0 -0
- data/public/css/images/white-desc.gif +0 -0
- data/public/css/images/white-unsorted.gif +0 -0
- data/public/css/jquery-ui.css +1225 -0
- data/public/css/jquery-ui.theme.min.css +5 -0
- data/public/css/theme.bootstrap.css +158 -0
- data/public/css/theme.bootstrap.min.css +1 -0
- data/public/css/theme.default.min.css +1 -0
- data/public/fonts/glyphicons-halflings-regular.eot +0 -0
- data/public/fonts/glyphicons-halflings-regular.svg +288 -0
- data/public/fonts/glyphicons-halflings-regular.ttf +0 -0
- data/public/fonts/glyphicons-halflings-regular.woff +0 -0
- data/public/fonts/glyphicons-halflings-regular.woff2 +0 -0
- data/public/images/Email.png +0 -0
- data/public/images/Facebook.png +0 -0
- data/public/images/Google+.png +0 -0
- data/public/images/IST_logo_s.png +0 -0
- data/public/images/LinkedIn.png +0 -0
- data/public/images/OpenToxEuro2013_small.png +0 -0
- data/public/images/Twitter.png +0 -0
- data/public/images/arrow_down_float.png +0 -0
- data/public/images/arrow_left_float.png +0 -0
- data/public/images/arrow_right_float.png +0 -0
- data/public/images/arrow_up_float.png +0 -0
- data/public/images/asc.gif +0 -0
- data/public/images/bfr_logo.gif +0 -0
- data/public/images/bg.gif +0 -0
- data/public/images/blind.png +0 -0
- data/public/images/desc.gif +0 -0
- data/public/images/enm_logo.png +0 -0
- data/public/images/favicon.ico +0 -0
- data/public/images/gray_jean.png +0 -0
- data/public/images/info_white.png +0 -0
- data/public/images/ist_logo.png +0 -0
- data/public/images/nestec.jpg +0 -0
- data/public/images/ot_logo.png +0 -0
- data/public/images/wait30trans.gif +0 -0
- data/public/javascripts/bootstrap.min.js +7 -0
- data/public/javascripts/jquery-1.11.2.min.js +4 -0
- data/public/javascripts/jquery-1.8.3.min.js +2 -0
- data/public/javascripts/jquery-ui-1.10.3.custom.min.js +6 -0
- data/public/javascripts/jquery.bpopup.min.js +7 -0
- data/public/javascripts/jquery.tablesorter.min.js +2 -0
- data/public/javascripts/jquery.tablesorter.widgets.js +2678 -0
- data/public/javascripts/jquery.tools.min.js +5 -0
- data/public/javascripts/lazar-gui.js +11 -0
- data/public/jsme/057C029061D565E59B91BCF8D80FA08E.cache.html +651 -0
- data/public/jsme/05B63F17C4ECC632F0004998FE93F0D9.cache.png +0 -0
- data/public/jsme/0D71BA88E8DB59E613D3BD042277F3CA.cache.html +636 -0
- data/public/jsme/143B86F220A77EA4A06DF2CE62EF455A.cache.html +636 -0
- data/public/jsme/1AFB129BECD672F835F8C27B14A9D8F2.cache.html +619 -0
- data/public/jsme/20865588BA1E58170CC8C13CEAD50C3C.cache.html +615 -0
- data/public/jsme/20B12D7884BFE17E1879B157A966B4D0.cache.html +631 -0
- data/public/jsme/222DCE3CD01E8F29C3D81A37CE3EC2B8.cache.html +626 -0
- data/public/jsme/230043C4988F4EECEF225437640D792F.cache.html +625 -0
- data/public/jsme/3014E46F5C6FB35E6CF0D7870071174B.cache.html +615 -0
- data/public/jsme/396F806CD63ABD414BFBB9D57429F05B.cache.png +0 -0
- data/public/jsme/3F57AECC67986E796A3148265F038FF1.cache.html +639 -0
- data/public/jsme/40BAF81124143A595056A9CCA0E9DBBA.cache.png +0 -0
- data/public/jsme/469A5B5AE16905A2CD712E25B9517A14.cache.html +644 -0
- data/public/jsme/4722AB194B521805C997130865A7EE3D.cache.html +638 -0
- data/public/jsme/4841BDE9DC293BA35F7762B4D8EFD236.cache.png +0 -0
- data/public/jsme/497588C27DED1A6E8FE1E0AB8417B414.cache.html +626 -0
- data/public/jsme/571D27D70DEF8240841DA5CAFC363CFF.cache.html +619 -0
- data/public/jsme/5F7FD5A5750634DF9F5480F2778D9CD7.cache.html +651 -0
- data/public/jsme/6187B195CC6073B1DB0A30F6CD64ACA3.cache.html +620 -0
- data/public/jsme/6DED0C7A48F0BB72DDB1FDE5C05E60B5.cache.html +642 -0
- data/public/jsme/73F66F1A578E65144682885B3DC28556.cache.html +620 -0
- data/public/jsme/76252DEA9FB0A670947525C4C89E2530.cache.html +657 -0
- data/public/jsme/84DE2DAB8AD49C4E122A548C4B072500.cache.html +625 -0
- data/public/jsme/98150D1CD230B36339E35812F0BD3D0E.cache.html +629 -0
- data/public/jsme/9BA3A5A02DFF97BADFD3F9FE3817341B.cache.html +636 -0
- data/public/jsme/9D58CD61900096C805154C0AC693DCE7.cache.html +639 -0
- data/public/jsme/A3D2B7C95C4FC47DB0996CBDF930EA17.cache.html +657 -0
- data/public/jsme/A6DF9CFFF55769DE62DA6868C558B3F2.cache.html +629 -0
- data/public/jsme/B70D7DA2E93A6B0FB7E5BC15540F7B15.cache.html +645 -0
- data/public/jsme/DF7764EEC1903CD03C9545B354D8D8E4.cache.png +0 -0
- data/public/jsme/E07214401017B41AF0BDAB1EB811CC83.cache.html +645 -0
- data/public/jsme/E45DF2A61DB551567FA3454B1A00412D.cache.html +631 -0
- data/public/jsme/E97CDFD075EEB4D0578A219C5564A988.cache.html +642 -0
- data/public/jsme/EBCDA5C12B4318C17A4741474FB9D7CA.cache.html +643 -0
- data/public/jsme/clear.cache.gif +0 -0
- data/public/jsme/gwt/chrome/chrome.css +1155 -0
- data/public/jsme/gwt/chrome/chrome_rtl.css +1155 -0
- data/public/jsme/gwt/chrome/images/button/menu-button-arrow-disabled.png +0 -0
- data/public/jsme/gwt/chrome/images/button/menu-button-arrow.png +0 -0
- data/public/jsme/gwt/chrome/images/button/split-button-arrow-active.png +0 -0
- data/public/jsme/gwt/chrome/images/button/split-button-arrow-disabled.png +0 -0
- data/public/jsme/gwt/chrome/images/button/split-button-arrow-focus.png +0 -0
- data/public/jsme/gwt/chrome/images/button/split-button-arrow-hover.png +0 -0
- data/public/jsme/gwt/chrome/images/button/split-button-arrow.png +0 -0
- data/public/jsme/gwt/chrome/images/combobox/arrow-down-disabled.png +0 -0
- data/public/jsme/gwt/chrome/images/combobox/arrow-down.png +0 -0
- data/public/jsme/gwt/chrome/images/combobox/ellipsis-disabled.png +0 -0
- data/public/jsme/gwt/chrome/images/combobox/ellipsis.png +0 -0
- data/public/jsme/gwt/chrome/images/corner.png +0 -0
- data/public/jsme/gwt/chrome/images/corner_ie6.png +0 -0
- data/public/jsme/gwt/chrome/images/fastree/selectionBar.gif +0 -0
- data/public/jsme/gwt/chrome/images/fastree/treeClosed.gif +0 -0
- data/public/jsme/gwt/chrome/images/fastree/treeLoading.gif +0 -0
- data/public/jsme/gwt/chrome/images/fastree/treeOpen.gif +0 -0
- data/public/jsme/gwt/chrome/images/glasspanel/blue_ridge.png +0 -0
- data/public/jsme/gwt/chrome/images/hborder.png +0 -0
- data/public/jsme/gwt/chrome/images/hborder_ie6.png +0 -0
- data/public/jsme/gwt/chrome/images/ie6/corner_dialog_topleft.png +0 -0
- data/public/jsme/gwt/chrome/images/ie6/corner_dialog_topright.png +0 -0
- data/public/jsme/gwt/chrome/images/ie6/hborder_blue_shadow.png +0 -0
- data/public/jsme/gwt/chrome/images/ie6/hborder_gray_shadow.png +0 -0
- data/public/jsme/gwt/chrome/images/ie6/vborder_blue_shadow.png +0 -0
- data/public/jsme/gwt/chrome/images/ie6/vborder_gray_shadow.png +0 -0
- data/public/jsme/gwt/chrome/images/scrolltable/bg_header_gradient.gif +0 -0
- data/public/jsme/gwt/chrome/images/splitPanelThumb.png +0 -0
- data/public/jsme/gwt/chrome/images/valuespinner/bg_textbox.png +0 -0
- data/public/jsme/gwt/chrome/images/vborder.png +0 -0
- data/public/jsme/gwt/chrome/images/vborder_ie6.png +0 -0
- data/public/jsme/gwt/chrome/mosaic.css +1252 -0
- data/public/jsme/gwt/chrome/mosaic_rtl.css +1252 -0
- data/public/jsme/hosted.html +365 -0
- data/public/jsme/jsa.css +175 -0
- data/public/jsme/jsme.nocache.js +18 -0
- data/public/rect.png +0 -0
- data/public/stylesheets/jquery-ui.css +1186 -0
- data/test/lazarweb.rb +193 -0
- data/test/setup.rb +7 -0
- data/unicorn.rb +7 -0
- data/views/batch.haml +58 -0
- data/views/details.haml +24 -0
- data/views/error.haml +8 -0
- data/views/faq.haml +2 -0
- data/views/faq_layout.haml +67 -0
- data/views/info.haml +2 -0
- data/views/jme_help.html +197 -0
- data/views/js_link.haml +5 -0
- data/views/layout.haml +113 -0
- data/views/model_details.haml +117 -0
- data/views/neighbors.haml +104 -0
- data/views/predict.haml +175 -0
- data/views/prediction.haml +84 -0
- data/views/significant_fragments.haml +66 -0
- data/views/style.scss +70 -0
- data/views/validation.haml +16 -0
- metadata +373 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA1:
|
|
3
|
+
metadata.gz: 63fad5e104b2e9a3d87993b4ce490de848ab14ac
|
|
4
|
+
data.tar.gz: 4f50c319f247c6716c0df6490c8d63a592d9202c
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: 177829a3a7d2025d2ac5819a37a7b87ec3e659ab427758a1305d8aa3c62bee0c3e445b0a976ac72f8bc404d0be004c1ff79545fd022bbd32fb40513fd7b11303
|
|
7
|
+
data.tar.gz: ea8728c578e29b430a4a0d4a7192c6ce53bb45f9af2e0a8320159db26dec2dd182234d445396b99ea082244489a85dfe36f6c8064cf8384f7e3530e2c345dabb
|
data/.gitignore
ADDED
data/FAQ.md
ADDED
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
Frequently Asked Questions
|
|
2
|
+
==========================
|
|
3
|
+
<br>
|
|
4
|
+
####How does this prediction works?
|
|
5
|
+
>
|
|
6
|
+
|
|
7
|
+
####You talk about significant fragments. Where can I find them?
|
|
8
|
+
> We will show up those significant fragments in a further version.
|
|
9
|
+
|
|
10
|
+
####What is endpoint details about?
|
|
11
|
+
> You get the source from where we took compounds for the endpoint. The type and the number of compounds we used.
|
|
12
|
+
|
|
13
|
+
####What is three times independent validation about?
|
|
14
|
+
>
|
|
15
|
+
|
|
16
|
+
####Do you consider providing plots for the validation results?
|
|
17
|
+
> In a further version we will show up confidence and correlation plots.
|
|
18
|
+
|
|
19
|
+
####What does 'Not enough similar compounds in training dataset' mean?
|
|
20
|
+
> Lazar uses neighbors from the training dataset of the endpoint to predict your compound. If there are not enough neighbors for Lazar it is not possible to make a prediction.
|
|
21
|
+
|
|
22
|
+
####Is there a minimum number of necessary neighbors to make a prediction?
|
|
23
|
+
>
|
|
24
|
+
|
|
25
|
+
####How can I activate the 'batch prediction' option?
|
|
26
|
+
> Please contact us directly via [mail](mailto:support@in-silico.ch).
|
|
27
|
+
|
|
28
|
+
####Not the right answers for me. Is there a way to contact you or report problems.
|
|
29
|
+
> You can always ask your questions via [mail](mailto:support@in-silico.ch). If you run into problems with the GUI please post your issue [here](https://github.com/opentox/lazar-gui/issues). If you would like to post any other issue e.g. about an expected prediction result please use this [form](https://github.com/opentox/lazar/issues).
|
data/Gemfile
ADDED
data/README.md
ADDED
data/VERSION
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
1.0.0
|
data/application.rb
ADDED
|
@@ -0,0 +1,317 @@
|
|
|
1
|
+
#require_relative 'helper.rb'
|
|
2
|
+
#require 'rdiscount'
|
|
3
|
+
include OpenTox
|
|
4
|
+
#require File.join(ENV["HOME"],".opentox","config","lazar-gui.rb") # until added to ot-tools
|
|
5
|
+
|
|
6
|
+
# DG: workaround for https://github.com/sinatra/sinatra/issues/808
|
|
7
|
+
# Date: 18/11/2013
|
|
8
|
+
#set :protection, :except => :path_traversal
|
|
9
|
+
|
|
10
|
+
configure :development do
|
|
11
|
+
$logger = Logger.new(STDOUT)
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
helpers do
|
|
15
|
+
class Numeric
|
|
16
|
+
def percent_of(n)
|
|
17
|
+
self.to_f / n.to_f * 100.0
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
get '/?' do
|
|
24
|
+
redirect to('/predict')
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
get '/predict/?' do
|
|
28
|
+
@models = OpenTox::Model::Prediction.all
|
|
29
|
+
@endpoints = @models.collect{|m| m.endpoint}.sort.uniq
|
|
30
|
+
@models.count <= 0 ? (haml :info) : (haml :predict)
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
get '/predict/modeldetails/:model' do
|
|
34
|
+
model = OpenTox::Model::Prediction.find params[:model]
|
|
35
|
+
crossvalidations = model.crossvalidations
|
|
36
|
+
#confidence_plots = crossvalidations.collect{|cv| [cv.id, cv.confidence_plot]}
|
|
37
|
+
#confidence_plots.each do |confp|
|
|
38
|
+
# File.open(File.join('public', "confp#{confp[0]}.svg"), 'w'){|file| file.write(confp[1])} unless File.exists? File.join('public', "confp#{confp[0]}.svg")
|
|
39
|
+
#end
|
|
40
|
+
#if model.regression?
|
|
41
|
+
# correlation_plots = crossvalidations.collect{|cv| [cv.id, cv.correlation_plot]}
|
|
42
|
+
# correlation_plots.each do |corrp|
|
|
43
|
+
# File.open(File.join('public', "corrp#{corrp[0]}.svg"), 'w'){|file| file.write(corrp[1])} unless File.exists? File.join('public', "corrp#{corrp[0]}.svg")
|
|
44
|
+
# end
|
|
45
|
+
#end
|
|
46
|
+
|
|
47
|
+
return haml :model_details, :layout=> false, :locals => {:model => model}
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
get '/jme_help/?' do
|
|
51
|
+
File.read(File.join('views','jme_help.html'))
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# get individual compound details
|
|
55
|
+
get '/prediction/:neighbor/details/?' do
|
|
56
|
+
@compound = OpenTox::Compound.new params[:neighbor]
|
|
57
|
+
@smiles = @compound.smiles
|
|
58
|
+
task = OpenTox::Task.run("Get names for '#{@smiles}'.") do
|
|
59
|
+
names = @compound.names
|
|
60
|
+
end
|
|
61
|
+
task.wait
|
|
62
|
+
|
|
63
|
+
case task[RDF::OT.hasStatus]
|
|
64
|
+
when "Error"
|
|
65
|
+
@names = "No names for this compound available."
|
|
66
|
+
when "Completed"
|
|
67
|
+
@names = @compound.names
|
|
68
|
+
else
|
|
69
|
+
@names = "No names for this compound available."
|
|
70
|
+
end
|
|
71
|
+
@inchi = @compound.inchi.gsub("InChI=", "")
|
|
72
|
+
|
|
73
|
+
haml :details, :layout => false
|
|
74
|
+
end
|
|
75
|
+
=begin
|
|
76
|
+
# sdf representation for datasets
|
|
77
|
+
#TODO fix 502 errors from compound service
|
|
78
|
+
get '/predict/:dataset_uri/sdf/?' do
|
|
79
|
+
uri = CGI.unescape(params[:dataset_uri])
|
|
80
|
+
$logger.debug uri
|
|
81
|
+
bad_request_error "Not a dataset uri." unless URI.dataset? uri
|
|
82
|
+
dataset = OpenTox::Dataset.find uri
|
|
83
|
+
@compounds = dataset.compounds
|
|
84
|
+
@data_entries = dataset.data_entries
|
|
85
|
+
sum=""
|
|
86
|
+
@compounds.each_with_index{ |c, idx|
|
|
87
|
+
sum << c.inchi
|
|
88
|
+
sum << c.sdf.sub(/\n\$\$\$\$/,'')
|
|
89
|
+
@data_entries[idx].each{ |f,v|
|
|
90
|
+
sum << "> <\"#{f}\">\n"
|
|
91
|
+
sum << v.join(", ")
|
|
92
|
+
sum << "\n\n"
|
|
93
|
+
}
|
|
94
|
+
sum << "$$$$\n"
|
|
95
|
+
}
|
|
96
|
+
send_file sum, :filename => "#{dataset.title}.sdf"
|
|
97
|
+
end
|
|
98
|
+
=end
|
|
99
|
+
# fingerprints for compound in predictions
|
|
100
|
+
get '/prediction/:model_uri/:type/:compound_uri/fingerprints/?' do
|
|
101
|
+
@type = params[:type]
|
|
102
|
+
model = OpenTox::Model::Lazar.find params[:model_uri]
|
|
103
|
+
feature_dataset = OpenTox::Dataset.find model[RDF::OT.featureDataset]
|
|
104
|
+
@compound = OpenTox::Compound.new params[:compound_uri]
|
|
105
|
+
@significant_fragments = []
|
|
106
|
+
if @type =~ /classification/i
|
|
107
|
+
# collect all feature values with fingerprint
|
|
108
|
+
fingerprints = OpenTox::Algorithm::Descriptor.send("smarts_match", [@compound], feature_dataset.features.collect{ |f| f[RDF::DC.title]})[@compound.uri]
|
|
109
|
+
#$logger.debug "fingerprints:\t#{fingerprints}\n"
|
|
110
|
+
|
|
111
|
+
# collect fingerprints with value 1
|
|
112
|
+
@fingerprint_values = fingerprints.collect{|smarts, value| [smarts, value] if value > 0}
|
|
113
|
+
|
|
114
|
+
# collect all features from feature_dataset
|
|
115
|
+
@features = feature_dataset.features.collect{|f| f }
|
|
116
|
+
|
|
117
|
+
# search for each fingerprint in all features and collect feature values( effect, smarts, pValue )
|
|
118
|
+
@fingerprint_values.each{ |fi, v| @features.each{ |f| @significant_fragments << [f[RDF::OT.effect].to_i, f[RDF::OT.smarts], f[RDF::OT.pValue]] if fi == f[RDF::OT.smarts] } }
|
|
119
|
+
|
|
120
|
+
# pass value_map, important to interprete effect value
|
|
121
|
+
prediction_feature_uri = ""
|
|
122
|
+
model.parameters.each {|p|
|
|
123
|
+
if p[RDF::DC.title].to_s == "prediction_feature_uri"
|
|
124
|
+
prediction_feature_uri = p[RDF::OT.paramValue].object
|
|
125
|
+
end
|
|
126
|
+
}
|
|
127
|
+
prediction_feature = OpenTox::Feature.find prediction_feature_uri
|
|
128
|
+
@value_map = prediction_feature.value_map
|
|
129
|
+
|
|
130
|
+
else #regression
|
|
131
|
+
feature_calc_algo = ""
|
|
132
|
+
model.parameters.each {|p|
|
|
133
|
+
if p[RDF::DC.title].to_s == "feature_calculation_algorithm"
|
|
134
|
+
feature_calc_algo = p[RDF::OT.paramValue].object
|
|
135
|
+
end
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
@desc = []
|
|
139
|
+
fingerprints = OpenTox::Algorithm::Descriptor.send( feature_calc_algo, [ @compound ], feature_dataset.features.collect{ |f| f[RDF::DC.title] } )
|
|
140
|
+
fingerprints.each{|x, h| h.each{|descriptor, value| @desc << [descriptor, [value]]}}
|
|
141
|
+
|
|
142
|
+
pc_descriptor_titles_descriptions = {}
|
|
143
|
+
feature_dataset.features.collect{ |f|
|
|
144
|
+
pc_descriptor_titles_descriptions[f[RDF::DC.title]]= f[RDF::DC.description]
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
@desc.each{|d, v| @significant_fragments << [pc_descriptor_titles_descriptions[d], v] }
|
|
148
|
+
end
|
|
149
|
+
|
|
150
|
+
haml :significant_fragments, :layout => false
|
|
151
|
+
end
|
|
152
|
+
|
|
153
|
+
get '/prediction/:model_uri/:type/:neighbor/significant_fragments/?' do
|
|
154
|
+
@type = params[:type]
|
|
155
|
+
@compound = OpenTox::Compound.new params[:neighbor]
|
|
156
|
+
model = OpenTox::Model::Lazar.find params[:model_uri]
|
|
157
|
+
#$logger.debug "model for significant fragments:\t#{model.uri}"
|
|
158
|
+
|
|
159
|
+
feature_dataset = OpenTox::Dataset.find model[RDF::OT.featureDataset]
|
|
160
|
+
$logger.debug "feature_dataset_uri:\t#{feature_dataset.uri}\n"
|
|
161
|
+
|
|
162
|
+
# load all compounds
|
|
163
|
+
feature_dataset.compounds
|
|
164
|
+
|
|
165
|
+
# load all features
|
|
166
|
+
@features = feature_dataset.features.collect{|f| f}
|
|
167
|
+
|
|
168
|
+
# find all features and values for a neighbor compound
|
|
169
|
+
@significant_fragments = []
|
|
170
|
+
# check type first
|
|
171
|
+
if @type =~ /classification/i
|
|
172
|
+
# get compound index in feature dataset
|
|
173
|
+
c_idx = feature_dataset.compound_indices @compound.uri
|
|
174
|
+
|
|
175
|
+
# collect feature uris with value
|
|
176
|
+
@feat = @features.collect{|f| [feature_dataset.data_entry_value(c_idx[0], f.uri), f.uri]}
|
|
177
|
+
#$logger.debug "@feat:\t#{@feat}\n"
|
|
178
|
+
|
|
179
|
+
# pass feature uris if value > 0
|
|
180
|
+
@feat.each do |f|
|
|
181
|
+
# search relevant features
|
|
182
|
+
if f[0] > 0
|
|
183
|
+
f = OpenTox::Feature.find f[1]
|
|
184
|
+
# pass relevant features with [ effect, smarts, pValue ]
|
|
185
|
+
@significant_fragments << [f[RDF::OT.effect].to_i, f[RDF::OT.smarts], f[RDF::OT.pValue].to_f.round(3)]
|
|
186
|
+
end
|
|
187
|
+
end
|
|
188
|
+
# pass value_map, important to interprete effect value
|
|
189
|
+
prediction_feature_uri = ""
|
|
190
|
+
model.parameters.each {|p|
|
|
191
|
+
if p[RDF::DC.title].to_s == "prediction_feature_uri"
|
|
192
|
+
prediction_feature_uri = p[RDF::OT.paramValue].object
|
|
193
|
+
end
|
|
194
|
+
}
|
|
195
|
+
prediction_feature = OpenTox::Feature.find prediction_feature_uri
|
|
196
|
+
@value_map = prediction_feature.value_map
|
|
197
|
+
|
|
198
|
+
else # regression
|
|
199
|
+
# find a value in feature dataset by compound and feature
|
|
200
|
+
@values = @features.collect{|f| feature_dataset.values(@compound, f)}
|
|
201
|
+
#$logger.debug "values in fd:\t#{@values}"
|
|
202
|
+
|
|
203
|
+
@features.each_with_index{|f, i| @significant_fragments << [f.description, @values[i]]}
|
|
204
|
+
end
|
|
205
|
+
#$logger.debug "significant fragments:\t#{@significant_fragments}\n"
|
|
206
|
+
|
|
207
|
+
haml :significant_fragments, :layout => false
|
|
208
|
+
end
|
|
209
|
+
|
|
210
|
+
get '/predict/?:csv?' do
|
|
211
|
+
response['Content-Type'] = "text/csv"
|
|
212
|
+
@csv = "\"Compound\",\"Endpoint\",\"Type\",\"Prediction\",\"Confidence\"\n"
|
|
213
|
+
@@batch.each do |key, values|
|
|
214
|
+
values.each do |array|
|
|
215
|
+
model = array[0]
|
|
216
|
+
prediction = array[1]
|
|
217
|
+
compound = key.smiles
|
|
218
|
+
mw = key.molecular_weight
|
|
219
|
+
endpoint = "#{model.endpoint.gsub('_', ' ')} (#{model.species})"
|
|
220
|
+
if prediction[:confidence] == "measured"
|
|
221
|
+
if prediction[:value].is_a?(Array)
|
|
222
|
+
prediction[:value].each do |value|
|
|
223
|
+
type = ""
|
|
224
|
+
weight = Compound.from_smiles(compound).mmol_to_mg(value, mw)
|
|
225
|
+
pred = value.numeric? ? "#{'%.2e' % value} (#{model.unit}) | #{'%.2e' % weight} (mg/kg_bw/day)" : value
|
|
226
|
+
confidence = "measured activity"
|
|
227
|
+
@csv += "\"#{compound}\",\"#{endpoint}\",\"#{type}\",\"#{pred}\",\"#{confidence}\"\n"
|
|
228
|
+
end
|
|
229
|
+
else
|
|
230
|
+
type = ""
|
|
231
|
+
weight = Compound.from_smiles(compound).mmol_to_mg(prediction[:value], mw)
|
|
232
|
+
pred = prediction[:value].numeric? ? "#{'%.2e' % prediction[:value]} (#{model.unit}) | #{'%.2e' % weight} (mg/kg_bw/day)" : prediction[:value]
|
|
233
|
+
confidence = "measured activity"
|
|
234
|
+
end
|
|
235
|
+
elsif prediction[:neighbors].size > 0
|
|
236
|
+
weight = Compound.from_smiles(compound).mmol_to_mg(prediction[:value], mw)
|
|
237
|
+
type = model.model.class.to_s.match("Classification") ? "Classification" : "Regression"
|
|
238
|
+
pred = prediction[:value].numeric? ? "#{'%.2e' % prediction[:value]} (#{model.unit}) | #{'%.2e' % weight} (mg/kg_bw/day)" : prediction[:value]
|
|
239
|
+
confidence = prediction[:confidence]
|
|
240
|
+
else
|
|
241
|
+
type = ""
|
|
242
|
+
pred = "Not enough similar compounds in training dataset."
|
|
243
|
+
confidence = ""
|
|
244
|
+
end
|
|
245
|
+
@csv += "\"#{compound}\",\"#{endpoint}\",\"#{type}\",\"#{pred}\",\"#{confidence}\"\n" unless prediction[:value].is_a?(Array)
|
|
246
|
+
end
|
|
247
|
+
end
|
|
248
|
+
@csv
|
|
249
|
+
end
|
|
250
|
+
|
|
251
|
+
post '/predict/?' do
|
|
252
|
+
|
|
253
|
+
# process batch prediction
|
|
254
|
+
if !params[:fileselect].blank?
|
|
255
|
+
if params[:fileselect][:filename] !~ /\.csv$/
|
|
256
|
+
@error_report = "Please submit a csv file."
|
|
257
|
+
return haml :error
|
|
258
|
+
end
|
|
259
|
+
File.open('tmp/' + params[:fileselect][:filename], "w") do |f|
|
|
260
|
+
f.write(params[:fileselect][:tempfile].read)
|
|
261
|
+
end
|
|
262
|
+
@filename = params[:fileselect][:filename]
|
|
263
|
+
input = OpenTox::Dataset.from_csv_file File.join "tmp", params[:fileselect][:filename]
|
|
264
|
+
dataset = OpenTox::Dataset.find input.id
|
|
265
|
+
@compounds = dataset.compounds
|
|
266
|
+
if @compounds.size == 0
|
|
267
|
+
@error_report = "No valid SMILES submitted."
|
|
268
|
+
dataset.delete
|
|
269
|
+
return haml :error
|
|
270
|
+
end
|
|
271
|
+
@batch = {}
|
|
272
|
+
@compounds.each do |compound|
|
|
273
|
+
@batch[compound] = []
|
|
274
|
+
params[:selection].keys.each do |model_id|
|
|
275
|
+
model = Model::Prediction.find model_id
|
|
276
|
+
prediction = model.predict(compound)
|
|
277
|
+
@batch[compound] << [model, prediction]
|
|
278
|
+
end
|
|
279
|
+
end
|
|
280
|
+
@@batch = @batch
|
|
281
|
+
dataset.delete
|
|
282
|
+
return haml :batch
|
|
283
|
+
end
|
|
284
|
+
|
|
285
|
+
# validate identifier input
|
|
286
|
+
# transfered input
|
|
287
|
+
if !params[:identifier].blank?
|
|
288
|
+
@identifier = params[:identifier]
|
|
289
|
+
$logger.debug "input:#{@identifier}"
|
|
290
|
+
# get compound from SMILES
|
|
291
|
+
@compound = Compound.from_smiles @identifier
|
|
292
|
+
if @compound.blank?
|
|
293
|
+
@error_report = "Attention, '#{@identifier}' is not a valid SMILES string."
|
|
294
|
+
return haml :error
|
|
295
|
+
end
|
|
296
|
+
|
|
297
|
+
@models = []
|
|
298
|
+
@predictions = []
|
|
299
|
+
params[:selection].keys.each do |model_id|
|
|
300
|
+
model = Model::Prediction.find model_id
|
|
301
|
+
@models << model
|
|
302
|
+
@predictions << model.predict(@compound)
|
|
303
|
+
end
|
|
304
|
+
haml :prediction
|
|
305
|
+
end
|
|
306
|
+
end
|
|
307
|
+
=begin
|
|
308
|
+
get '/faq' do
|
|
309
|
+
@faq = RDiscount.new(File.read("FAQ.md")).to_html
|
|
310
|
+
haml :faq, :layout => :faq_layout
|
|
311
|
+
end
|
|
312
|
+
=end
|
|
313
|
+
get '/style.css' do
|
|
314
|
+
headers 'Content-Type' => 'text/css; charset=utf-8'
|
|
315
|
+
scss :style
|
|
316
|
+
end
|
|
317
|
+
|
data/bin/lazar-start
ADDED
data/bin/lazar-start.sh
ADDED
data/bin/lazar-stop
ADDED
data/bin/lazar-stop.sh
ADDED
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
grep_lazar=`ps aux | grep -v grep | grep lazar-start`
|
|
3
|
+
grep_mongo=`ps aux | grep -v grep | grep mongod`
|
|
4
|
+
grep_rserve=`ps aux | grep -v grep | grep Rserve`
|
|
5
|
+
grep_unicorn=`ps aux | grep -v grep | grep unicorn`
|
|
6
|
+
|
|
7
|
+
# lazar
|
|
8
|
+
if [ ${#grep_lazar} -gt 0 ]
|
|
9
|
+
then
|
|
10
|
+
PID=`ps ax | grep -v grep | grep lazar-start | awk '{ print $1 }'`
|
|
11
|
+
for i in "${PID}"
|
|
12
|
+
do
|
|
13
|
+
`kill $i`
|
|
14
|
+
done
|
|
15
|
+
else
|
|
16
|
+
echo "Lazar is stopped."
|
|
17
|
+
fi
|
|
18
|
+
|
|
19
|
+
# mongod
|
|
20
|
+
if [ ${#grep_mongo} -gt 0 ]
|
|
21
|
+
then
|
|
22
|
+
PID=`ps ax | grep -v grep | grep mongod | awk '{ print $1 }'`
|
|
23
|
+
for i in "${PID}"
|
|
24
|
+
do
|
|
25
|
+
`sudo kill $i`
|
|
26
|
+
done
|
|
27
|
+
else
|
|
28
|
+
echo "MongoDB is not running."
|
|
29
|
+
fi
|
|
30
|
+
|
|
31
|
+
# rserve
|
|
32
|
+
if [ ${#grep_rserve} -gt 0 ]
|
|
33
|
+
then
|
|
34
|
+
PID=`ps ax | grep -v grep | grep Rserve | awk '{ print $1 }'`
|
|
35
|
+
for i in "${PID}"
|
|
36
|
+
do
|
|
37
|
+
`kill $i`
|
|
38
|
+
done
|
|
39
|
+
else
|
|
40
|
+
echo "Rserve is not running."
|
|
41
|
+
fi
|
|
42
|
+
|
|
43
|
+
# unicorn
|
|
44
|
+
if [ ${#grep_unicorn} -gt 0 ]
|
|
45
|
+
then
|
|
46
|
+
PID=`ps ax | grep -v grep | grep unicorn | awk '{ print $1 }'`
|
|
47
|
+
`kill ${PID[0]}`
|
|
48
|
+
else
|
|
49
|
+
echo "Unicorn is not running."
|
|
50
|
+
fi
|
|
51
|
+
|
|
52
|
+
exit 0
|