source: extensions/net.sf.basedb.reggie/trunk/resources/sampleproc/rnaqc_plate_import.jsp @ 1966

Last change on this file since 1966 was 1966, checked in by Nicklas Nordborg, 9 years ago

Fixes #488: Add support for matching RNAQC items using location instead of names from the Caliper Well Table file

A side effect is that a simple change (using the doImport method instead of preValidate) made it possible to display all warnings immediately.

File size: 13.6 KB
Line 
1<%@ page
2  pageEncoding="UTF-8"
3  session="false"
4  import="net.sf.basedb.core.User"
5  import="net.sf.basedb.core.DbControl"
6  import="net.sf.basedb.core.SessionControl"
7  import="net.sf.basedb.core.Application"
8  import="net.sf.basedb.clients.web.Base" 
9  import="net.sf.basedb.clients.web.util.HTML" 
10  import="net.sf.basedb.clients.web.extensions.ExtensionsControl"
11%>
12<%@ taglib prefix="base" uri="/WEB-INF/base.tld" %>
13<%@ taglib prefix="p" uri="/WEB-INF/path.tld" %>
14<%
15final SessionControl sc = Base.getExistingSessionControl(request, true);
16final String ID = sc.getId();
17final float scale = Base.getScale(sc);
18final String home = ExtensionsControl.getHomeUrl("net.sf.basedb.reggie");
19DbControl dc = null;
20try
21{
22  dc = sc.newDbControl();
23  final User user = User.getById(dc, sc.getLoggedInUserId());
24%>
25<base:page type="default" >
26<base:head scripts="ajax.js" styles="path.css">
27  <link rel="stylesheet" type="text/css" href="../css/reggie.css">
28  <script language="JavaScript" src="../reggie.js" type="text/javascript" charset="UTF-8"></script>
29 
30 
31<script language="JavaScript">
32var debug = false;
33var hasValididatedCsv = false;
34var qcRunDateIsValid = false;
35
36function init()
37{
38  var frm = document.forms['reggie'];
39
40}
41
42var lastExtension;
43function browseOnClick(extension)
44{
45  var frm = document.forms['reggie'];
46  if (frm[extension+'.path'].disabled) return;
47 
48  var url = getRoot() + 'filemanager/index.jsp?ID=<%=ID%>&cmd=SelectOne&callback=setFileCallback';
49  url += '&resetTemporary=1&tmpfilter:STRING:name='+escape('%.' + extension.substr(0, 3));
50  lastExtension = extension;
51  Main.openPopup(url, 'SelectFile', 1000, 700);
52}
53
54
55function setFileCallback(id, path)
56{
57  var frm = document.forms['reggie'];
58  frm[lastExtension+'.id'].value = id;
59  frm[lastExtension+'.path'].value = path;
60  if (lastExtension == 'csv')
61  {
62    setTimeout(preValidateCsvFile, 100);
63  }
64  else
65  {
66    setInputStatus(lastExtension, '', 'valid');
67  }
68}
69
70
71function preValidateCsvFile()
72{
73  var frm = document.forms['reggie'];
74  var csvId = frm['csv.id'].value;
75  var csvPath = frm['csv.path'].value;
76  if (!csvId) return;
77 
78  Main.hide('messages');
79  Main.addClass(document.body, 'please-wait');
80  setInputStatus('csv', 'Checking...', 'checking');
81
82  var url = '../RnaQc.servlet?ID=<%=ID%>&cmd=PreValidateCaliperResults&csv='+csvId;
83 
84  var request = Ajax.getXmlHttpRequest();
85  Ajax.setReadyStateHandler(request, onCsvValidated);
86  request.open("POST", url, true); 
87  request.send('');
88 
89}
90
91function onCsvValidated(request)
92{
93  Main.removeClass(document.body, 'please-wait');
94  if (debug) Main.debug(request.responseText);
95  var response = JSON.parse(request.responseText); 
96 
97  var numWarnings = 0;
98  if (response.messages && response.messages.length > 0)
99  {
100    var messages = '<ul>';
101    for (var i = 0; i < response.messages.length; i++)
102    {
103      var msgLine = response.messages[i];
104      if (msgLine.indexOf('[Warning]') >= 0)
105      {
106        messages += '<li class="warning">' + msgLine.replace('[Warning]', '');
107        numWarnings++;
108      }
109      else
110      {
111        messages += '<li>' + msgLine;
112      }
113    }
114    messages += '</ul>';
115    setInnerHTML('messages', messages);
116    Main.show('messages');
117  }
118  else
119  {
120    Main.hide('messages'); 
121  }
122 
123  if (response.status != 'ok')
124  {
125    setInputStatus('csv', response.message, 'invalid');
126    Main.addClass(document.getElementById('messages'), 'failure');
127    hasValidatedCsv = false;
128    Main.hide('bioplateSection');
129    return;
130  }
131
132  setInputStatus('csv', '', numWarnings > 0 ? 'warning' : 'valid');
133  hasValidatedCsv = true;
134 
135  var bioplate = response.plate;
136 
137  Main.show('bioplateSection');
138  setInnerHTML('bioplate.name', '<span class="link" onclick="bioPlateOnClick(event, '+bioplate.id+')">'+bioplate.name+'</a>');
139  setInputStatus('bioplate', '', 'valid');
140  if (bioplate.QCRunDate)
141  {
142    frm.qcRunDate.value = bioplate.QCRunDate;
143    qcRunDateOnChange();
144    setInputStatus('bioplate', 'Data has already been imported to this plate', 'warning');
145  }
146  else
147  {
148    // Try to get date from the filename
149    var dates = csvPath.match(/\d\d\d\d-\d\d-\d\d/);
150    if (dates && dates.length >= 1)
151    {
152      var date = dates[0];
153      frm.qcRunDate.value = date.substr(0, 4)+date.substr(5, 2)+date.substr(8, 2);
154      qcRunDateOnChange();
155    }
156   
157  }
158  if (bioplate.QCOperator)
159  {
160    frm.qcOperator.value = bioplate.QCOperator;
161  }
162 
163}
164
165function bioPlateOnClick(event, id)
166{
167  Main.itemOnClick(event, '<%=ID%>', 'BIOPLATE', id, true);
168}
169
170function goImport()
171{
172  var frm = document.forms['reggie'];
173  var csvId = parseInt(frm['csv.id'].value, 10);
174  var gxdStdId = parseInt(frm['gxd.std.id'].value, 10);
175  var gxdHiId = parseInt(frm['gxd.hi.id'].value, 10);
176  var pdfId = parseInt(frm['pdf.id'].value, 10);
177 
178  if (!csvId)
179  {
180    setInputStatus('csv', 'Missing CSV file', 'invalid');
181    return;
182  }
183  if (!hasValidatedCsv) return;
184  if (frm.qcRunDate.value != '' && !qcRunDateIsValid) return;
185 
186  setInputStatus('csv', '', 'valid');
187 
188  Main.hide('goimport');
189  Main.hide('messages');
190
191  frm['csv.path'].disabled = true;
192  frm['gxd.std.path'].disabled = true;
193  frm['gxd.hi.path'].disabled = true;
194  frm['pdf.path'].disabled = true;
195  Main.addClass(document.getElementById('btnCsv'), 'disabled');
196  Main.addClass(document.getElementById('btnGxdStd'), 'disabled');
197  Main.addClass(document.getElementById('btnGxdHi'), 'disabled');
198  Main.addClass(document.getElementById('btnPdf'), 'disabled');
199 
200  var submitInfo = new Object();
201  submitInfo.csv = csvId;
202  submitInfo.gxdStd = gxdStdId;
203  submitInfo.gxdHi = gxdHiId;
204  submitInfo.pdf = pdfId;
205  submitInfo.QCRunDate = frm.qcRunDate.value;
206  submitInfo.QCOperator = frm.qcOperator.value;
207 
208  if (debug) Main.debug(JSON.stringify(submitInfo));
209 
210  var url = '../RnaQc.servlet?ID=<%=ID%>&cmd=ImportCaliperResults';
211 
212  var request = Ajax.getXmlHttpRequest();
213  try
214  {
215    showLoadingAnimation('Importing RQS values...');
216    request.open("POST", url, false);
217    request.send(JSON.stringify(submitInfo));
218  }
219  finally
220  {
221    hideLoadingAnimation();
222  }
223 
224  if (debug) Main.debug(request.responseText);
225  var response = JSON.parse(request.responseText);
226 
227  if (response.messages && response.messages.length > 0)
228  {
229    var msg = '<ul>';
230    for (var i = 0; i < response.messages.length; i++)
231    {
232      var msgLine = response.messages[i];
233      if (msgLine.indexOf('[Warning]') >= 0)
234      {
235        msg += '<li class="warning">' + msgLine.replace('[Warning]', '');
236      }
237      else
238      {
239        msg += '<li>' + msgLine;
240      }
241    }
242    msg += '</ul>';
243    setInnerHTML('messages', msg);
244    Main.show('messages');
245  }
246 
247  if (response.status != 'ok')
248  {
249    Main.addClass(document.getElementById('messages'), 'failure');
250    setFatalError(response.message);
251    return false;
252  }
253
254  Main.show('done');
255  Main.show('gorestart');
256 
257}
258
259
260function qcRunDateOnChange()
261{
262  var frm = document.forms['reggie'];
263  qcRunDateIsValid = false;
264  setInputStatus('qcRunDate', '', '');
265 
266  var qcRunDate = frm.qcRunDate.value;
267 
268  if (qcRunDate == '')
269  {
270    setInputStatus('qcRunDate', 'Missing', 'warning');
271  }
272  else
273  {
274    // Auto-fill the date if it's only given with 4(MMdd) or 6(yyMMdd) digits.   
275    qcRunDate = autoFillDate(qcRunDate);
276    frm.qcRunDate.value = qcRunDate;
277 
278    if (!Dates.isDate(qcRunDate, 'yyyyMMdd'))
279    {
280      setInputStatus('qcRunDate', 'Not a valid date', 'invalid');
281      return;
282    }
283    setInputStatus('qcRunDate', '', 'valid');
284  }
285 
286  qcRunDateIsValid = true;
287}
288
289</script>
290
291<style>
292body.please-wait
293{
294  cursor: wait !important;
295}
296</style>
297
298</base:head>
299<base:body onload="init()">
300
301  <p:path><p:pathelement 
302    title="Reggie" href="<%="../index.jsp?ID="+ID%>" 
303    /><p:pathelement title="RNA quality control - Import Caliper results" 
304    /></p:path>
305
306  <div class="content">
307  <%
308  if (sc.getActiveProjectId() == 0)
309  {
310    %>
311    <div class="messagecontainer note" style="width: 950px; margin-left: 20px; margin-bottom: 20px; margin-right: 0px; font-weight: bold; color: #cc0000;">
312      No project has been selected. You may proceed with the import but
313      you may not be able to update all items.
314    </div>
315    <%
316  }
317  %>
318
319  <form name="reggie" onsubmit="return false;">
320    <input type="hidden" name="csv.id" value="">
321    <input type="hidden" name="gxd.std.id" value="">
322    <input type="hidden" name="gxd.hi.id" value="">
323    <input type="hidden" name="pdf.id" value="">
324 
325  <!-- 1. Select bioplate -->
326  <table border="0" cellspacing="0" cellpadding="0" class="stepform">
327  <tr>
328    <td rowspan="2" class="stepno">1</td>
329    <td class="steptitle">Select data files</td>
330  </tr>
331  <tr>
332    <td class="stepfields">
333      <table border="0" cellspacing="0" cellpadding="0" width="100%">
334      <tr valign="top">
335        <td class="prompt">Well table CSV</td>
336        <td class="input">
337              <table border="0" cellspacing="0" cellpadding="0">
338              <tr>
339              <td><input class="text required" type="text" 
340                name="csv.path" value=""
341                size="50"></td>
342              <td style="padding-left: 4px;"><base:button 
343                  title="Browse&hellip;"
344                  onclick="browseOnClick('csv')"
345                  id="btnCsv"
346                  />
347              </td>
348              </tr>
349              </table>
350         
351        </td>
352        <td class="status" id="csv.status"></td>
353        <td class="help"><span id="csv.message" class="message" style="display: none;"></span>
354          Select the <b>Well Table CSV file</b> that contains the exported analysis result from the
355          Caliper software.
356        </td>
357      </tr>
358      <tr valign="top">
359        <td class="prompt">GXD standard</td>
360        <td class="input">
361              <table border="0" cellspacing="0" cellpadding="0">
362              <tr>
363              <td><input class="text" type="text" 
364                name="gxd.std.path" value=""
365                size="50"></td>
366              <td style="padding-left: 4px;"><base:button 
367                  title="Browse&hellip;"
368                  onclick="browseOnClick('gxd.std')"
369                  id="btnGxdStd"
370                  />
371              </td>
372              </tr>
373              </table>
374         
375        </td>
376        <td class="status" id="gxd.std.status"></td>
377        <td class="help"><span id="gxd.std.message" class="message" style="display: none;"></span>
378          Select the <b>Standard GXD file</b> that contains the raw data.
379        </td>
380      </tr>
381      <tr valign="top">
382        <td class="prompt">GXD high sense</td>
383        <td class="input">
384              <table border="0" cellspacing="0" cellpadding="0">
385              <tr>
386              <td><input class="text" type="text" 
387                name="gxd.hi.path" value=""
388                size="50"></td>
389              <td style="padding-left: 4px;"><base:button 
390                  title="Browse&hellip;"
391                  onclick="browseOnClick('gxd.hi')"
392                  id="btnGxdHi"
393                  />
394              </td>
395              </tr>
396              </table>
397         
398        </td>
399        <td class="status" id="gxd.hi.status"></td>
400        <td class="help"><span id="gxd.hi.message" class="message" style="display: none;"></span>
401          Select the <b>High sense GXD file</b> that contains the raw data.
402        </td>
403      </tr>
404      <tr valign="top">
405        <td class="prompt">PDF file</td>
406        <td class="input">
407              <table border="0" cellspacing="0" cellpadding="0">
408              <tr>
409              <td><input class="text" type="text" 
410                name="pdf.path" value=""
411                size="50"></td>
412              <td style="padding-left: 4px;"><base:button 
413                  title="Browse&hellip;"
414                  onclick="browseOnClick('pdf')"
415                  id="btnPdf"
416                  />
417              </td>
418              </tr>
419              </table>
420         
421        </td>
422        <td class="status" id="pdf.status"></td>
423        <td class="help"><span id="pdf.message" class="message" style="display: none;"></span>
424          Select the PDF file that contains a printout with diagrams and other
425          useful documentation.
426        </td>
427      </tr>
428      <tr id="bioplateSection">
429        <td class="prompt">Bioplate</td>
430        <td class="input" id="bioplate.name"><i>no file loaded</i></td>
431        <td class="status" id="bioplate.status"></td>
432        <td class="help"><span id="bioplate.message" class="message" style="display: none;"></span>
433        </td>
434      </tr>
435      <tr valign="top">
436        <td class="prompt">QC Run Date</td>
437        <td class="input" style="padding-left: 0px;">
438          <input type="text" name="qcRunDate" value="" size="12" maxlength="10"
439            onblur="qcRunDateOnChange()">
440        </td>
441        <td class="status" id="qcRunDate.status"></td>
442        <td class="help">
443          <span id="qcRunDate.message" class="message" style="display: none;"></span>(YYYYMMDD or MMDD)
444        </td>
445      </tr>
446      <tr valign="top">
447        <td class="prompt">QC Operator</td>
448        <td class="input" style="padding-left: 0px;">
449          <input type="text" name="qcOperator" value="<%=HTML.encodeTags(user.getName()) %>" size="50" maxlength="255">
450        </td>
451        <td class="status" id="qcOperator.status"></td>
452        <td class="help">
453          <span id="qcOperator.message" class="message" style="display: none;"></span>
454        </td>
455      </tr>
456      </table>
457    </td>
458  </tr>
459  </table>
460 
461  <div class="loading" id="loading" style="display: none;"><table><tr><td><img src="../images/loading.gif"></td><td id="loading.msg">Please wait...</td></tr></table></div>
462 
463  <div class="messagecontainer error" id="errorMessage" style="display: none; width: 950px; margin-left: 20px; margin-bottom: 0px;"></div>
464 
465  <div id="messages" class="success" style="display: none; width: 950px; margin-left: 20px; margin-top: 20px;"></div>
466 
467  <table style="margin-left: 20px; margin-top: 10px;" class="navigation">
468    <tr>
469      <td><base:button id="goimport" title="Import" image="<%=home+"/images/import.png"%>" onclick="goImport()"/></td>
470      <td><base:button id="gorestart" title="Restart" image="<%=home+"/images/goback.png"%>" onclick="goRestart(true)" style="display: none;"/></td>
471      <td id="gonext.message" class="message"></td>
472    </tr>
473  </table>
474  </form>
475  </div>
476 
477</base:body>
478</base:page>
479<%
480}
481finally
482{
483  if (dc != null) dc.close();
484}
485%>
Note: See TracBrowser for help on using the repository browser.