galaxy-commits
  Threads by month 
                
            - ----- 2025 -----
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
July 2010
- 1 participants
- 87 discussions
 
                        
                    
                        
                            
                                
                            
                            galaxy-dist commit e110168a83c9: lims: added	option to rename	sequencer datasets by prepending the	experiment name.
                        
                        
by commits-noreply@bitbucket.org 16 Jul '10
                    by commits-noreply@bitbucket.org 16 Jul '10
16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User rc
# Date 1277922255 14400
# Node ID e110168a83c91f14a2923149e195aa4e8855fde5
# Parent  428ce38ba8e92af0d2099a381e38863e09b46cd1
lims: added option to rename sequencer datasets by prepending the experiment name.
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -1554,6 +1554,7 @@ class RequestEvent( object ):
 class RequestType( object ):
     rename_dataset_options = Bunch( NO = 'Do not rename',
                                     SAMPLE_NAME = 'Preprend sample name',
+                                    EXPERIMENT_NAME = 'Prepend experiment name',
                                     EXPERIMENT_AND_SAMPLE_NAME = 'Prepend experiment and sample name')
     permitted_actions = get_permitted_actions( filter='REQUEST_TYPE' )
     def __init__(self, name=None, desc=None, request_form=None, sample_form=None,
--- a/lib/galaxy/web/controllers/requests_admin.py
+++ b/lib/galaxy/web/controllers/requests_admin.py
@@ -673,6 +673,8 @@ class RequestsAdmin( BaseController ):
             return sample.name+'_'+name
         elif opt == sample.request.type.rename_dataset_options.EXPERIMENT_AND_SAMPLE_NAME:
             return sample.request.name+'_'+sample.name+'_'+name
+        elif opt == sample.request.type.rename_dataset_options.EXPERIMENT_NAME:
+            return sample.request.name+'_'+name
     def __setup_datatx_user(self, trans, library, folder):
         '''
         This method sets up the datatx user:
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0
                            
                          
                          
                            
    
                          
                        
                     
                        
                    
                        
                            
                                
                            
                            galaxy-dist commit 428ce38ba8e9: Fixed issue #345	- Incorporated	Brad's patch which handles skipping of order	checking for join	version >=7,	which would otherwise end in an error. Also modified sort command	to	better handle cases with duplicate keys. A new test-case	to	test these scenarios has been added as well.
                        
                        
by commits-noreply@bitbucket.org 16 Jul '10
                    by commits-noreply@bitbucket.org 16 Jul '10
16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User guru
# Date 1277915778 14400
# Node ID 428ce38ba8e92af0d2099a381e38863e09b46cd1
# Parent  ddddd07724227dadeb37ffa2528a87e361787d8f
Fixed issue #345 - Incorporated Brad's patch which handles skipping of order checking for join version >=7, which would otherwise end in an error. Also modified sort command to better handle cases with duplicate keys. A new test-case to test these scenarios has been added as well.
--- a/tools/filters/joinWrapper.py
+++ b/tools/filters/joinWrapper.py
@@ -3,7 +3,7 @@
 """
 This tool provides the UNIX "join" functionality.
 """
-import sys, os, tempfile
+import sys, os, tempfile, subprocess
 
 def stop_err(msg):
     sys.stderr.write(msg)
@@ -22,8 +22,8 @@ def main():
     
     try:
         #Sort the two files based on specified fields
-        os.system("sort -t $'\t' -k %d -o %s %s" %(field1, tmpfile1.name, infile1))
-        os.system("sort -t $'\t' -k %d -o %s %s" %(field2, tmpfile2.name, infile2))
+        os.system("sort -t $'\t' -k %d,%d -o %s %s" %(field1, field1, tmpfile1.name, infile1))
+        os.system("sort -t $'\t' -k %d,%d -o %s %s" %(field2, field2, tmpfile2.name, infile2))
     except Exception, exc:
         stop_err( 'Initialization error -> %s' %str(exc) )
         
@@ -39,10 +39,28 @@ def main():
                     option = option + ",1." + str(j) 
             break
     
+    #check if join has --version option. BSD join doens't have this option, while GNU join does. 
+    #The return value in the latter case will be 0, and non-zero in the latter case.
+    ret = subprocess.call('join --version 2>/dev/null', shell=True) 
+    # check if we are a version later than 7 of join. If so, we want to skip
+    # checking the order since join will raise an error with duplicated items in
+    # the two files being joined.
+    if ret == 0: 
+        cl = subprocess.Popen(["join", "--version"], stdout=subprocess.PIPE)
+        (stdout, _) = cl.communicate()
+        version_line = stdout.split("\n")[0]
+        (version, _) = version_line.split()[-1].split(".")
+        if int(version) >= 7:
+            flags = "--nocheck-order"
+        else:
+            flags = ""
+    else:
+        flags = ""
+
     if mode == "V":
-        cmdline = "join -t $'\t' -v 1 -o %s -1 %d -2 %d %s %s > %s" %(option, field1, field2, tmpfile1.name, tmpfile2.name, outfile)
+        cmdline = "join %s -t $'\t' -v 1 -o %s -1 %d -2 %d %s %s > %s" %(flags, option, field1, field2, tmpfile1.name, tmpfile2.name, outfile)
     else:
-        cmdline = "join -t $'\t' -o %s -1 %d -2 %d %s %s > %s" %(option, field1, field2, tmpfile1.name, tmpfile2.name, outfile)
+        cmdline = "join %s -t $'\t' -o %s -1 %d -2 %d %s %s > %s" %(flags, option, field1, field2, tmpfile1.name, tmpfile2.name, outfile)
     
     try:
         os.system(cmdline) 
--- /dev/null
+++ b/test-data/fs-compare-2.dat
@@ -0,0 +1,40 @@
+chr10	55251623	55253124	CCDS7248.1_cds_0_0_chr10_55251624_r	0	-
+chr11	116124407	116124501	CCDS8374.1_cds_0_0_chr11_116124408_r	0	-
+chr11	116206508	116206563	CCDS8377.1_cds_0_0_chr11_116206509_f	0	+
+chr11	116211733	116212337	CCDS8378.1_cds_0_0_chr11_116211734_r	0	-
+chr11	1812377	1812407	CCDS7726.1_cds_0_0_chr11_1812378_f	0	+
+chr12	38440094	38440321	CCDS8736.1_cds_0_0_chr12_38440095_r	0	-
+chr13	112381694	112381953	CCDS9526.1_cds_0_0_chr13_112381695_f	0	+
+chr14	98710240	98712285	CCDS9949.1_cds_0_0_chr14_98710241_r	0	-
+chr15	41486872	41487060	CCDS10096.1_cds_0_0_chr15_41486873_r	0	-
+chr15	41673708	41673857	CCDS10097.1_cds_0_0_chr15_41673709_f	0	+
+chr15	41679161	41679250	CCDS10098.1_cds_0_0_chr15_41679162_r	0	-
+chr15	41826029	41826196	CCDS10101.1_cds_0_0_chr15_41826030_f	0	+
+chr16	142908	143003	CCDS10397.1_cds_0_0_chr16_142909_f	0	+
+chr16	179963	180135	CCDS10401.1_cds_0_0_chr16_179964_r	0	-
+chr16	244413	244681	CCDS10402.1_cds_0_0_chr16_244414_f	0	+
+chr16	259268	259383	CCDS10403.1_cds_0_0_chr16_259269_r	0	-
+chr18	23786114	23786321	CCDS11891.1_cds_0_0_chr18_23786115_r	0	-
+chr18	59406881	59407046	CCDS11985.1_cds_0_0_chr18_59406882_f	0	+
+chr18	59455932	59456337	CCDS11986.1_cds_0_0_chr18_59455933_r	0	-
+chr18	59600586	59600754	CCDS11988.1_cds_0_0_chr18_59600587_f	0	+
+chr19	59068595	59069564	CCDS12866.1_cds_0_0_chr19_59068596_f	0	+
+chr19	59236026	59236146	CCDS12872.1_cds_0_0_chr19_59236027_r	0	-
+chr19	59297998	59298008	CCDS12877.1_cds_0_0_chr19_59297999_f	0	+
+chr19	59302168	59302288	CCDS12878.1_cds_0_0_chr19_59302169_r	0	-
+chr20	33330413	33330423	CCDS13249.1_cds_0_0_chr20_33330414_r	0	-
+chr20	33513606	33513792	CCDS13255.1_cds_0_0_chr20_33513607_f	0	+
+chr20	33579500	33579527	CCDS13256.1_cds_0_0_chr20_33579501_r	0	-
+chr20	33593260	33593348	CCDS13257.1_cds_0_0_chr20_33593261_f	0	+
+chr21	32707032	32707192	CCDS13614.1_cds_0_0_chr21_32707033_f	0	+
+chr21	32869641	32870022	CCDS13615.1_cds_0_0_chr21_32869642_r	0	-
+chr21	33321040	33322012	CCDS13620.1_cds_0_0_chr21_33321041_f	0	+
+chr21	33744994	33745040	CCDS13625.1_cds_0_0_chr21_33744995_r	0	-
+chr22	30120223	30120265	CCDS13897.1_cds_0_0_chr22_30120224_f	0	+
+chr22	30160419	30160661	CCDS13898.1_cds_0_0_chr22_30160420_r	0	-
+chr22	30665273	30665360	CCDS13901.1_cds_0_0_chr22_30665274_f	0	+
+chr22	30939054	30939266	CCDS13903.1_cds_0_0_chr22_30939055_r	0	-
+chrX	122745047	122745924	CCDS14606.1_cds_0_0_chrX_122745048_f	0	+
+chrX	152648964	152649196	CCDS14733.1_cds_0_0_chrX_152648965_r	0	-
+chrX	152691446	152691471	CCDS14735.1_cds_0_0_chrX_152691447_f	0	+
+chrX	152694029	152694263	CCDS14736.1_cds_0_0_chrX_152694030_r	0	-
--- a/tools/filters/compare.xml
+++ b/tools/filters/compare.xml
@@ -1,4 +1,4 @@
-<tool id="comp1" name="Compare two Queries" version="1.0.1">
+<tool id="comp1" name="Compare two Queries" version="1.0.2"><description>to find common or distinct rows</description><command interpreter="python">joinWrapper.py $input1 $input2 $field1 $field2 $mode $out_file1</command><inputs>
@@ -27,6 +27,15 @@
       <param name="mode" value="N"/><output name="out_file1" file="fs-compare.dat"/></test>
+    <!--test case with duplicated key values-->
+    <test>
+      <param name="input1" value="1.bed"/>
+      <param name="input2" value="3.bed"/>
+      <param name="field1" value="1"/>
+      <param name="field2" value="1"/>
+      <param name="mode" value="V"/>
+      <output name="out_file1" file="fs-compare-2.dat"/>
+    </test></tests><help>
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0
                            
                          
                          
                            
    
                          
                        
                     
                        
                    
                        
                            
                                
                            
                            galaxy-dist commit ddddd0772422: Remove outdated	about.rst/html.
                        
                        
by commits-noreply@bitbucket.org 16 Jul '10
                    by commits-noreply@bitbucket.org 16 Jul '10
16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User Dan Blankenberg <dan(a)bx.psu.edu>
# Date 1277910554 14400
# Node ID ddddd07724227dadeb37ffa2528a87e361787d8f
# Parent  c1172bae7b0fc41e4bd52bfe73c130309c2387fe
Remove outdated about.rst/html.
--- a/static/about.html
+++ /dev/null
@@ -1,78 +0,0 @@
-<?xml version="1.0" encoding="utf-8" ?>
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
-<meta name="generator" content="Docutils 0.3.9: http://docutils.sourceforge.net/" />
-<title>ABOUT GALAXY</title>
-<link rel="stylesheet" href="/static/style/base.css" type="text/css" />
-<link rel="stylesheet" href="/static/style/help.css" type="text/css" />
-</head>
-<body>
-<div class="document" id="about-galaxy">
-<h1 class="title">ABOUT GALAXY</h1>
-<div class="section" id="people">
-<h2><a name="people">People:</a></h2>
-<ul class="simple">
-<li>Istvan Albert - <em>Co-PI</em></li>
-<li>Daniel Blankenberg - <em>Graduate student</em></li>
-<li>Richard Burhans - <em>Sysadmin</em></li>
-<li>Laura Elnitski - <em>Co-PI</em></li>
-<li>Belinda Giardine - <em>Programmer</em></li>
-<li>Ross Hardison - <em>Co-PI</em></li>
-<li>Jim Kent - <em>Co-PI</em></li>
-<li>David King - <em>Graduate student</em></li>
-<li>Webb Miller - <em>Co-PI</em></li>
-<li>Anton Nekrutenko - <em>PI</em></li>
-<li>Cathy Riemer - <em>Programmer</em></li>
-<li>Prachi Shah - <em>Programmer</em></li>
-<li>Ian Schenck - <em>Undergraduate student</em></li>
-<li>James Taylor - <em>Graduate student</em></li>
-<li>Yi Zhang - <em>Programmer</em></li>
-</ul>
-</div>
-<hr class="docutils" />
-<div class="section" id="development">
-<h2><a name="development">Development:</a></h2>
-<p><strong>Galaxy core</strong> - <em>Istvan Albert</em> and <em>James Taylor</em></p>
-<p><strong>Interface</strong> - <em>James Taylor</em>, <em>Istvan Albert</em>, <em>Anton Nekrutenko</em></p>
-<p><strong>Tools</strong> -</p>
-<ul class="simple">
-<li>Data sources - <em>Istvan Albert</em></li>
-<li>EMBOSS, Phylip, mafs - <em>Daniel Blankenberg</em></li>
-<li>Text Tools, Sequence Extractors - <em>Richard Burhans</em>, <em>Anton Nekrutenko</em>, <em>Ian Schenck</em></li>
-<li>Operations - <em>James Taylor</em>, <em>Yi Zhang</em></li>
-<li>Statistics, Graphs - <em>Istvan Albert</em>, <em>David King</em></li>
-</ul>
-<p><strong>Project management</strong> - <em>Anton Nekrutenko</em></p>
-<p>Current version of Galaxy uses many ideas developed by <em>Laura Elnitski</em>, <em>Belinda Giardine</em>, and <em>Cathy Riemer</em> in Galaxy1 and GALA.</p>
-</div>
-<hr class="docutils" />
-<div class="section" id="special-thanks-to">
-<h2><a name="special-thanks-to">Special thanks to:</a></h2>
-<ul class="simple">
-<li>David Haussler</li>
-<li>Ewan Birney</li>
-<li>Hiram Clawson</li>
-<li>Angie Hinrichs</li>
-<li>Darin London</li>
-<li>Members of Hardison, Makova, Miller, and Nekrutenko Labs</li>
-</ul>
-</div>
-<hr class="docutils" />
-<div class="section" id="technology">
-<h2><a name="technology">Technology:</a></h2>
-<p>Galaxy core is written entirely in Python. It uses the following open source technologies:</p>
-<ul class="simple">
-<li>web-server <a class="reference" href="http://www.cherrypy.org/">CherryPy</a></li>
-<li>database <a class="reference" href="http://www.sleepycat.com/products/db.shtml">BerkelyDB</a></li>
-<li>XML library <a class="reference" href="http://effbot.org/zone/element-index.htm">ElementTree</a></li>
-<li>HTML templating library <a class="reference" href="http://www.cheetahtemplate.org/">Cheetah</a></li>
-</ul>
-<p>Galaxy API generated from source code can be found <a class="reference" href="http://www.bx.psu.edu/trac/local/docs/index.html">here</a></p>
-<hr class="docutils" />
-<p><a class="reference" href="http://www.bx.psu.edu">The Center for Comparative Genomics and Bioinformatics</a> at <a class="reference" href="http://www.psu.edu">Penn State</a> | 2005</p>
-</div>
-</div>
-</body>
-</html>
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,6 @@
 static: static/welcome.html
 static: static/help.html
 static: static/galaxyIndex.html
-static: static/about.html
 
 %.html : %.rst
 	./modules/rst2html.py --stylesheet="/static/help.css" --initial-header-level=2 < $< > $@
--- a/static/about.rst
+++ /dev/null
@@ -1,82 +0,0 @@
-ABOUT GALAXY
-============
-
-People:
--------
-
-* Istvan Albert - *Co-PI*
-* Daniel Blankenberg - *Graduate student*
-* Richard Burhans - *Sysadmin*
-* Laura Elnitski - *Co-PI*
-* Belinda Giardine - *Programmer*
-* Ross Hardison - *Co-PI*
-* Jim Kent - *Co-PI*
-* David King - *Graduate student*
-* Webb Miller - *Co-PI*
-* Anton Nekrutenko - *PI*
-* Cathy Riemer - *Programmer*
-* Prachi Shah - *Programmer*
-* Ian Schenck - *Undergraduate student*
-* James Taylor - *Graduate student*
-* Yi Zhang - *Programmer*
-
------
-
-Development:
-------------
-
-**Galaxy core** - *Istvan Albert* and *James Taylor*
-
-**Interface** - *James Taylor*, *Istvan Albert*, *Anton Nekrutenko*
-
-**Tools** -
-
-* Data sources - *Istvan Albert*
-* EMBOSS, Phylip, mafs - *Daniel Blankenberg*
-* Text Tools, Sequence Extractors - *Richard Burhans*, *Anton Nekrutenko*, *Ian Schenck*
-* Operations - *James Taylor*, *Yi Zhang*
-* Statistics, Graphs - *Istvan Albert*, *David King*
-
-**Project management** - *Anton Nekrutenko*
-
-Current version of Galaxy uses many ideas developed by *Laura Elnitski*, *Belinda Giardine*, and *Cathy Riemer* in Galaxy1 and GALA.
-
------
-
-Special thanks to:
-------------------
-
-* David Haussler
-* Ewan Birney
-* Hiram Clawson
-* Angie Hinrichs
-* Darin London
-* Members of Hardison, Makova, Miller, and Nekrutenko Labs
-
------
-
-Technology:
------------
-
-Galaxy core is written entirely in Python. It uses the following open source technologies:
-
-* web-server `CherryPy`__
-* database `BerkelyDB`__
-* XML library `ElementTree`__
-* HTML templating library `Cheetah`__
-
-Galaxy API generated from source code can be found `here`__
-
-.. __: http://www.cherrypy.org/
-.. __: http://www.sleepycat.com/products/db.shtml
-.. __: http://effbot.org/zone/element-index.htm
-.. __: http://www.cheetahtemplate.org/
-.. __: http://www.bx.psu.edu/trac/local/docs/index.html
-
------
-
-`The Center for Comparative Genomics and Bioinformatics`__ at `Penn State`__ | 2005
-
-.. __: http://www.bx.psu.edu
-.. __: http://www.psu.edu
-
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0
                            
                          
                          
                            
    
                          
                        
                     
                        
                    
                        
                            
                                
                            
                            galaxy-dist commit c1172bae7b0f: lims:	requests/request_admin	controller refactor
                        
                        
by commits-noreply@bitbucket.org 16 Jul '10
                    by commits-noreply@bitbucket.org 16 Jul '10
16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User rc
# Date 1277909210 14400
# Node ID c1172bae7b0fc41e4bd52bfe73c130309c2387fe
# Parent  9289b4d7fa4d1d1b630c044dfbc102cf870f62e3
lims: requests/request_admin controller refactor
A new controller called requests_common now handles all common tasks like create/edit/delete requests & samples. The requests controller has only the grid definition and requests_admin controller has the request_type code and the sequencer data transfer code.
Also fixed a form importer bug in forms.py
--- /dev/null
+++ b/templates/requests/common/sample_events.mako
@@ -0,0 +1,65 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+
+<%def name="title()">Events for Sample ${sample.name}</%def>
+
+<h2>Events for Sample "${sample.name}"</h2>
+<ul class="manage-table-actions">
+    <li>
+        <a class="action-button" href="${h.url_for( controller=cntrller, action='list', operation='show', id=trans.security.encode_id(sample.request.id) )}">
+        <span>Browse this request</span></a>
+    </li>
+</ul>
+<h3>User: ${sample.request.user.email}</h3>
+
+%if message:
+    ${render_msg( message, status )}
+%endif
+
+<div class="toolForm">
+    <table class="grid">
+        <thead>
+            <tr>
+                <th>State</th>
+                <th>Description</th>
+                <th>Last Update</th>
+                <th>Comments</th>
+            </tr>
+        </thead>
+        <tbody>
+            %for state, desc, updated, comments in events_list:    
+                <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
+                    <td><b><a>${state}</a></b></td>
+                    <td><a>${desc}</a></td>
+                    <td><a>${updated}</a></td>
+                    <td><a>${comments}</a></td>
+                </tr>             
+            %endfor
+        </tbody>
+    </table>
+</div>
+%if cntrller == 'requests_admin' and trans.user_is_admin():
+    <div class="toolForm">
+        <div class="toolFormTitle">Change current state</div>
+        <div class="toolFormBody">
+            <form name="event" action="${h.url_for( controller='requests_admin', action='save_state', new=True, sample_id=sample.id)}" method="post" >
+                    %for w in widgets:
+                        <div class="form-row">
+                            <label>
+                                ${w[0]}
+                            </label>
+                            ${w[1].get_html()}
+                            %if w[0] == 'Comments':
+                                <div class="toolParamHelp" style="clear: both;">
+                                    Optional
+                                </div>
+                            %endif
+                        </div>
+                    %endfor
+                <div class="form-row">
+                    <input type="submit" name="add_event_button" value="Save"/>
+                </div>
+            </form>
+        </div>
+    </div>
+%endif
--- a/test/functional/test_forms_and_requests.py
+++ b/test/functional/test_forms_and_requests.py
@@ -189,7 +189,7 @@ class TestFormsAndRequests( TwillTestCas
         # Make sure the request_type is not accessible by regular_user2 since regular_user2 does not have Role1.
         self.logout()
         self.login( email=regular_user2.email )
-        self.visit_url( '%s/requests/new?create=True&select_request_type=%i' % (self.url, request_type.id) )
+        self.visit_url( '%s/requests_common/new?cntrller=requests&select_request_type=True' % self.url )
         try:
             self.check_page_for_string( 'There are no request types created for a new request.' )
             raise AssertionError, 'The request_type %s is accessible by %s when it should be restricted' % ( request_type.name, regular_user2.email )
@@ -304,12 +304,12 @@ class TestFormsAndRequests( TwillTestCas
         self.logout()
         self.login( email='test(a)bx.psu.edu' )
         self.check_request_admin_grid(state=request_one.states.SUBMITTED, request_name=request_one.name)
-        self.visit_url( "%s/requests_admin/list?sort=-create_time&operation=show_request&id=%s" \
+        self.visit_url( "%s/requests_admin/list?operation=show&id=%s" \
                         % ( self.url, self.security.encode_id( request_one.id ) ))
         self.check_page_for_string( 'Sequencing Request "%s"' % request_one.name )
         # set bar codes for the samples
         bar_codes = [ '1234567890', '0987654321' ]
-        self.add_bar_codes( request_one.id, request_one.name, bar_codes )
+        self.add_bar_codes( request_one.id, request_one.name, bar_codes, request_one.samples )
         # change the states of all the samples of this request
         for sample in request_one.samples:
             self.change_sample_state( sample.name, sample.id, request_type.states[1].id, request_type.states[1].name )
@@ -328,11 +328,12 @@ class TestFormsAndRequests( TwillTestCas
         self.login( email='test(a)bx.psu.edu' )
         request_name = "RequestTwo"
         # simulate request creation
-        url_str = '%s/requests_admin/new?create=True&create_request_button=Save&select_request_type=%i&select_user=%i&name=%s&library_id=%i&folder_id=%i&refresh=True&field_2=%s&field_0=%s&field_1=%i' \
-                  % ( self.url, request_type.id, regular_user.id, request_name, library_one.id, library_one.root_folder.id, "field_2_value", 'option1', user_address.id )
+        url_str = '%s/requests_common/new?cntrller=requests_admin&create_request_button=Save&select_request_type=%i&select_user=%i&name=%s&refresh=True&field_2=%s&field_0=%s&field_1=%i' \
+                  % ( self.url, request_type.id, regular_user.id, request_name, "field_2_value", 'option1', user_address.id )
+        print url_str
         self.home()
         self.visit_url( url_str )
-        self.check_page_for_string( "The new request named %s has been created" % request_name )
+        self.check_page_for_string( "The new request named <b>%s</b> has been created" % request_name )
         global request_two
         request_two = sa_session.query( galaxy.model.Request ) \
                                 .filter( and_( galaxy.model.Request.table.c.name==request_name,
@@ -370,44 +371,44 @@ class TestFormsAndRequests( TwillTestCas
         # check if the request's state is now set to 'submitted'
         assert request_two.state is not request_two.states.REJECTED, "The state of the request '%s' should be set to '%s'" \
             % ( request_two.name, request_two.states.REJECTED )
-    def test_055_reset_data_for_later_test_runs( self ):
-        """Reseting data to enable later test runs to pass"""
-        # Logged in as admin_user
-        # remove the request_type permissions
-        rt_actions = sa_session.query( galaxy.model.RequestTypePermissions ) \
-                               .filter(and_(galaxy.model.RequestTypePermissions.table.c.request_type_id==request_type.id) ) \
-                               .order_by( desc( galaxy.model.RequestTypePermissions.table.c.create_time ) ) \
-                               .all()
-        for a in rt_actions:
-            sa_session.delete( a )
-        sa_session.flush()
-        ##################
-        # Purge all libraries
-        ##################
-        for library in [ library_one ]:
-            self.delete_library_item( 'library_admin',
-                                      self.security.encode_id( library.id ),
-                                      self.security.encode_id( library.id ),
-                                      library.name,
-                                      item_type='library' )
-            self.purge_library( self.security.encode_id( library.id ), library.name )
-        ##################
-        # Eliminate all non-private roles
-        ##################
-        for role in [ role_one, role_two ]:
-            self.mark_role_deleted( self.security.encode_id( role.id ), role.name )
-            self.purge_role( self.security.encode_id( role.id ), role.name )
-            # Manually delete the role from the database
-            sa_session.refresh( role )
-            sa_session.delete( role )
-            sa_session.flush()
-        ##################
-        # Eliminate all groups
-        ##################
-        for group in [ group_one ]:
-            self.mark_group_deleted( self.security.encode_id( group.id ), group.name )
-            self.purge_group( self.security.encode_id( group.id ), group.name )
-            # Manually delete the group from the database
-            refresh( group )
-            sa_session.delete( group )
-            sa_session.flush()
+#    def test_055_reset_data_for_later_test_runs( self ):
+#        """Reseting data to enable later test runs to pass"""
+#        # Logged in as admin_user
+#        # remove the request_type permissions
+#        rt_actions = sa_session.query( galaxy.model.RequestTypePermissions ) \
+#                               .filter(and_(galaxy.model.RequestTypePermissions.table.c.request_type_id==request_type.id) ) \
+#                               .order_by( desc( galaxy.model.RequestTypePermissions.table.c.create_time ) ) \
+#                               .all()
+#        for a in rt_actions:
+#            sa_session.delete( a )
+#        sa_session.flush()
+#        ##################
+#        # Purge all libraries
+#        ##################
+#        for library in [ library_one ]:
+#            self.delete_library_item( 'library_admin',
+#                                      self.security.encode_id( library.id ),
+#                                      self.security.encode_id( library.id ),
+#                                      library.name,
+#                                      item_type='library' )
+#            self.purge_library( self.security.encode_id( library.id ), library.name )
+#        ##################
+#        # Eliminate all non-private roles
+#        ##################
+#        for role in [ role_one, role_two ]:
+#            self.mark_role_deleted( self.security.encode_id( role.id ), role.name )
+#            self.purge_role( self.security.encode_id( role.id ), role.name )
+#            # Manually delete the role from the database
+#            sa_session.refresh( role )
+#            sa_session.delete( role )
+#            sa_session.flush()
+#        ##################
+#        # Eliminate all groups
+#        ##################
+#        for group in [ group_one ]:
+#            self.mark_group_deleted( self.security.encode_id( group.id ), group.name )
+#            self.purge_group( self.security.encode_id( group.id ), group.name )
+#            # Manually delete the group from the database
+#            refresh( group )
+#            sa_session.delete( group )
+#            sa_session.flush()
--- a/templates/admin/requests/show_request.mako
+++ /dev/null
@@ -1,528 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-<%namespace file="/requests/sample_state.mako" import="render_sample_state" />
-<%namespace file="/requests/sample_datasets.mako" import="render_sample_datasets" />
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$( function() {
-    $( "select[refresh_on_change='true']").change( function() {
-        var refresh = false;
-        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
-        if ( refresh_on_change_values ) {
-            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
-            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
-            for( i= 0; i < refresh_on_change_values.length; i++ ) {
-                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
-                    refresh = true;
-                    break;
-                }
-            }
-        }
-        else {
-            refresh = true;
-        }
-        if ( refresh ){
-            $( "#show_request" ).submit();
-        }
-    });
-});
-</script>
-
-
-<script type="text/javascript">
-$(document).ready(function(){
-    //hide the all of the element with class msg_body
-    $(".msg_body").hide();
-    //toggle the componenet with class msg_body
-    $(".msg_head").click(function(){
-        $(this).next(".msg_body").slideToggle(450);
-    });
-});
-</script>
-
-<script type="text/javascript">
-    // Looks for changes in sample states using an async request. Keeps
-    // calling itself (via setTimeout) until all samples are in a terminal
-    // state.
-    var updater = function ( sample_states ) {
-        // Check if there are any items left to track
-        var empty = true;
-        for ( i in sample_states ) {
-            empty = false;
-            break;
-        }
-        if ( ! empty ) {
-            setTimeout( function() { updater_callback( sample_states ) }, 1000 );
-        }
-    };
-    var updater_callback = function ( sample_states ) {
-        // Build request data
-        var ids = []
-        var states = []
-        $.each( sample_states, function ( id, state ) {
-            ids.push( id );
-            states.push( state );
-        });
-        // Make ajax call
-        $.ajax( {
-            type: "POST",
-            url: "${h.url_for( controller='requests_admin', action='sample_state_updates' )}",
-            dataType: "json",
-            data: { ids: ids.join( "," ), states: states.join( "," ) },
-            success : function ( data ) {
-                $.each( data, function( id, val ) {
-                    // Replace HTML
-                    var cell1 = $("#sampleState-" + id);
-                    cell1.html( val.html_state );
-                    var cell2 = $("#sampleDatasets-" + id);
-                    cell2.html( val.html_datasets );
-                    sample_states[ parseInt(id) ] = val.state;
-                });
-                updater( sample_states ); 
-            },
-            error: function() {
-                // Just retry, like the old method, should try to be smarter
-                updater( sample_states );
-            }
-        });
-    };
-</script>
-
-<style type="text/css">
-.msg_head {
-    padding: 0px 0px;
-    cursor: pointer;
-}
-</style>
-
-<script type="text/javascript">
-    function stopRKey(evt) {
-      var evt = (evt) ? evt : ((event) ? event : null);
-      var node = (evt.target) ? evt.target : ((evt.srcElement) ? evt.srcElement : null);
-      if ((evt.keyCode == 13) && (node.type=="text"))  {return false;}
-    }
-    document.onkeypress = stopRKey
-</script> 
-
-%if request.submitted():
-    <% samples_not_ready = request.sequence_run_ready() %>
-    %if samples_not_ready:
-        ${render_msg( "Select a target library and folder for all the samples before starting the sequence run", "warning" )}
-    %endif
-%endif
-
-%if request.rejected():
-    ${render_msg( "Reason for rejection: "+request.last_comment(), "warning" )}
-%endif
-
-<div class="grid-header">
-    <h2>Sequencing Request "${request.name}"</h2>
-</div>
-
-<ul class="manage-table-actions">
-
-    %if request.unsubmitted() and request.samples:
-        <li>
-            <a class="action-button" confirm="More samples cannot be added to this request once it is submitted. Click OK to submit." href="${h.url_for( controller='requests_admin', action='list', operation='Submit', id=trans.security.encode_id(request.id) )}">
-            <span>Submit request</span></a>
-        </li>
-    %endif
-    %if request.submitted():
-        <li>
-            <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='Reject', id=trans.security.encode_id(request.id))}">
-            <span>Reject request</span></a>
-        </li>
-    %endif
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='events', id=trans.security.encode_id(request.id) )}">
-        <span>History</span></a>
-    </li>
-
-
-</ul>
-
-<%def name="show_basic_info_form( sample_index, sample, info )">
-    <td>
-        <input type="text" name=sample_${sample_index}_name value="${info['name']}" size="10"/>
-        <div class="toolParamHelp" style="clear: both;">
-            <i>${' (required)' }</i>
-        </div>
-    </td>
-    %if sample:
-        %if sample.request.unsubmitted():
-            <td></td>
-        %else:
-            <td><input type="text" name=sample_${sample_index}_barcode value="${info['barcode']}" size="10"/></td>
-        %endif
-    %else:
-        <td></td>
-    %endif
-    %if sample:
-        %if sample.request.unsubmitted():
-            <td>Unsubmitted</td>
-        %else:
-            <td><a href="${h.url_for( controller='requests_admin', action='show_events', sample_id=sample.id)}">${sample.current_state().name}</a></td>
-        %endif    
-    %else:
-        <td></td>
-    %endif
-    <td>${info['lib_widget'].get_html()}</td>
-    <td>${info['folder_widget'].get_html()}</td>
-    %if request.submitted() or request.complete(): 
-        %if sample:
-            <td><a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">${len(sample.dataset_files)}</a></td> 
-        %else:
-            <td><a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">Add</a></td>
-        %endif 
-    %endif 
-</%def>
-
-## This function displays the "Basic Information" grid
-<%def name="render_basic_info_grid()">
-    <h4>Sample Information</h4>
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>Name</th>
-                <th>Barcode</th>
-                <th>State</th>
-                <th>Data Library</th>
-                <th>Folder</th>
-                %if request.submitted() or request.complete(): 
-                    <th>Dataset(s) Transferred</th>
-                %endif
-                <th></th>
-            </tr>
-        <thead>
-        <tbody>
-            <%
-            trans.sa_session.refresh( request )
-            %>
-            %for sample_index, info in enumerate(current_samples):
-                <% 
-                    if sample_index in range(len(request.samples)):
-                        sample = request.samples[sample_index]
-                    else:
-                        sample = None 
-                %>
-                %if edit_mode == 'True':
-                    <tr>
-                        ${show_basic_info_form( sample_index, sample, info )}
-                    </tr>      
-                %else:
-                    <tr>
-                        %if sample_index in range(len(request.samples)):
-                            <td>${info['name']}</td>
-                            <td>${info['barcode']}</td>
-                            %if sample.request.unsubmitted():
-                                <td>Unsubmitted</td>
-                            %else:
-                                <td id="sampleState-${sample.id}">${render_sample_state( sample )}</td>
-                            %endif
-                                
-##                            <td>
-##                                %if sample:
-##                                    %if sample.request.unsubmitted():
-##                                        Unsubmitted
-##                                    %else:
-##                                        <a href="${h.url_for( controller='requests_admin', action='show_events', sample_id=sample.id)}">${sample.current_state().name}</a>
-##                                    %endif
-##                                %endif
-##                            </td>
-                            %if info['library']:
-                                <td><a href="${h.url_for( controller='library_common', action='browse_library', cntrller='library', id=trans.security.encode_id( info['library'].id ) )}">${info['library'].name}</a></td>
-                            %else:
-                                <td></td>
-                            %endif
-                            %if info['folder']:
-                                <td>${info['folder'].name}</td>
-                            %else:
-                                <td></td>
-                            %endif
-                            %if request.submitted() or request.complete(): 
-                                <td id="sampleDatasets-${sample.id}">
-                                    ${render_sample_datasets( sample )}
-##                                    <a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">${len(sample.dataset_files)}</a>
-                                </td>
-                            %endif
-                            
-                            
-                        %else:                                                            
-                            ${show_basic_info_form( sample_index, sample, info )}
-                        %endif
-                        %if request.unsubmitted() or request.rejected(): 
-                            <td>
-                                %if sample:
-                                    %if sample.request.unsubmitted():
-                                        <a class="action-button" href="${h.url_for( controller='requests_admin', action='delete_sample', request_id=request.id, sample_id=sample_index )}">
-                                        <img src="${h.url_for('/static/images/delete_icon.png')}" />
-                                        <span></span></a>
-                                    %endif
-                                %endif
-                            </td>
-                        %endif
-                    </tr>  
-                %endif
-            %endfor
-        </tbody>
-    </table>
-</%def>
-
-<%def name="render_sample_form( index, sample_name, sample_values, fields_dict )">
-    <td>
-        ${sample_name}
-    </td>
-    %for field_index, field in fields_dict.items():
-        <td>
-            %if field['type'] == 'TextField':
-                <input type="text" name="sample_${index}_field_${field_index}" value="${sample_values[field_index]}" size="7"/>
-            %elif field['type'] == 'SelectField':
-                <select name="sample_${index}_field_${field_index}" last_selected_value="2">
-                    %for option_index, option in enumerate(field['selectlist']):
-                        %if option == sample_values[field_index]:
-                            <option value="${option}" selected>${option}</option>
-                        %else:
-                            <option value="${option}">${option}</option>
-                        %endif
-                    %endfor
-                </select>
-            %elif field['type'] == 'WorkflowField':
-                <select name="sample_${index}_field_${field_index}">
-                    %if str(sample_values[field_index]) == 'none':
-                        <option value="none" selected>Select one</option>
-                    %else:
-                        <option value="none">Select one</option>
-                    %endif
-                    %for option_index, option in enumerate(request.user.stored_workflows):
-                        %if not option.deleted:
-                            %if str(option.id) == str(sample_values[field_index]):
-                                <option value="${option.id}" selected>${option.name}</option>
-                            %else:
-                                <option value="${option.id}">${option.name}</option>
-                            %endif
-                        %endif
-                    %endfor
-                </select>
-            %elif field['type'] == 'CheckboxField':
-                <input type="checkbox" name="sample_${index}_field_${field_index}" value="Yes"/>
-            %endif
-            <div class="toolParamHelp" style="clear: both;">
-                <i>${'('+field['required']+')' }</i>
-            </div>
-        </td>
-    %endfor   
-</%def>
-
-<%def name="render_sample( index, sample_name, sample_values, fields_dict )">
-    <td>
-        ${sample_name}
-    </td>
-    %for field_index, field in fields_dict.items():
-        <td>
-            %if sample_values[field_index]:
-                %if field['type'] == 'WorkflowField':
-                    %if str(sample_values[field_index]) != 'none':
-                        <% workflow = trans.sa_session.query( trans.app.model.StoredWorkflow ).get( int(sample_values[field_index]) ) %>
-                        <a href="${h.url_for( controller='workflow', action='run', id=trans.security.encode_id(workflow.id) )}">${workflow.name}</a>
-                    %endif
-                %else:
-                    ${sample_values[field_index]}
-                %endif
-            %else:
-                <i>None</i>
-            %endif
-        </td>
-    %endfor   
-</%def>
-
-<div class="toolForm">
-    <div class="form-row">
-        <div class="msg_list">
-            <h4 class="msg_head"><u>Request Information</u></h4>
-            <div class="msg_body">
-                %for index, rd in enumerate(request_details):
-                    <div class="form-row">
-                        <label>${rd['label']}</label>
-                        %if not rd['value']:
-                            <i>None</i>
-                        %else:                      
-                            %if rd['label'] == 'State':
-                                <a href="${h.url_for( controller='requests_admin', action='list', operation='events', id=trans.security.encode_id(request.id) )}">${rd['value']}</a>
-                            %else:
-                                ${rd['value']}     
-                            %endif
-                        %endif
-                    </div>
-                    <div style="clear: both"></div>
-                %endfor
-                <div class="form-row">
-                <ul class="manage-table-actions">
-                    <li>
-                        <a class="action-button"  href="${h.url_for( controller='requests_admin', action='list', operation='Edit', id=trans.security.encode_id(request.id))}">
-                        <span>Edit request details</span></a>
-                    </li>
-                </ul>
-                </div>
-            </div>
-        </div>
-    </div>
-</div>
-
-<br/>
-
-
-<%def name="render_grid( grid_index, grid_name, fields_dict )">
-    <br/>
-    <div class="msg_list">
-    %if grid_name:
-        <h4 class="msg_head"><u>${grid_name}</u></h4>
-    %else:
-        <h4>Grid ${grid_index}</h4>
-    %endif
-    %if edit_mode == 'False' or len(current_samples) <= len(request.samples):
-        <div class="msg_body">
-    %else:
-        <div class="msg_body2">
-    %endif
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>Name</th>
-                %for index, field in fields_dict.items():
-                    <th>
-                        ${field['label']}
-                        <div class="toolParamHelp" style="clear: both;">
-                            <i>${field['helptext']}</i>
-                        </div>
-                    </th>
-                %endfor
-                <th></th>
-            </tr>
-        <thead>
-        <tbody>
-            <%
-            trans.sa_session.refresh( request )
-            %>
-            %for sample_index, sample in enumerate(current_samples):
-                %if edit_mode == 'True':
-                    <tr>
-                        ${render_sample_form( sample_index, sample['name'], sample['field_values'], fields_dict)}
-                    </tr>      
-                %else:
-                    <tr>
-                        %if sample_index in range(len(request.samples)):
-                            ${render_sample( sample_index, sample['name'], sample['field_values'], fields_dict )}
-                        %else:                                                            
-                            ${render_sample_form( sample_index, sample['name'], sample['field_values'], fields_dict)}
-                        %endif
-                    </tr>  
-                %endif
-            %endfor
-        </tbody>
-    </table>
-    </div>
-    </div>
-</%def>
-
-<div class="toolForm">
-    ##<div class="toolFormTitle">Samples (${len(request.samples)})</div>
-    <form id="show_request" name="show_request" action="${h.url_for( controller='requests_admin', action='show_request', edit_mode=edit_mode )}" enctype="multipart/form-data" method="post" >
-        <div class="form-row">
-            %if current_samples:
-                ## first render the basic info grid 
-                ${render_basic_info_grid()}
-                ## then render the other grid(s)
-                <% trans.sa_session.refresh( request.type.sample_form ) %>
-                %for grid_index, grid_name in enumerate(request.type.sample_form.layout):
-                    ${render_grid( grid_index, grid_name, request.type.sample_form.fields_of_grid( grid_index ) )}
-                    <br/>
-                %endfor
-            %else:
-                <label>There are no samples.</label>
-            %endif
-        </div>      
-        %if request.samples and request.submitted():
-            <script type="text/javascript">
-                // Updater
-                updater({${ ",".join( [ '"%s" : "%s"' % ( s.id, s.current_state().name ) for s in request.samples ] ) }});
-            </script>
-        %endif
-        
-        %if edit_mode == 'False':
-            <table class="grid">
-                <tbody>
-                    <tr>
-                        <div class="form-row">
-
-                            %if request.unsubmitted():
-                                <td>
-                                    %if current_samples:
-                                        <label>Copy </label>
-                                        <input type="integer" name="num_sample_to_copy" value="1" size="3"/>
-                                        <label>sample(s) from sample</label>
-                                        ${sample_copy.get_html()}
-                                    %endif
-                                    <input type="submit" name="add_sample_button" value="Add New"/>
-                                </td>
-                            %endif
-                            <td>
-                                %if len(current_samples) and len(current_samples) <= len(request.samples):                     
-                                    <input type="submit" name="edit_samples_button" value="Edit samples"/>
-                                %endif
-                            </td>
-                        </div>
-                    </tr> 
-                </tbody>
-            </table>
-        %endif
-        %if request.samples or current_samples: 
-            <div class="form-row">
-                <div style="float: left; width: 250px; margin-right: 10px;">
-                    <input type="hidden" name="refresh" value="true" size="40"/>
-                </div>
-              <div style="clear: both"></div>
-            </div>            
-            %if edit_mode == 'True':   
-                <div class="form-row">
-                    <input type="submit" name="save_samples_button" value="Save"/>
-                    <input type="submit" name="cancel_changes_button" value="Cancel"/>
-                </div>
-            %elif request.unsubmitted():
-                <div class="form-row">
-                    <input type="submit" name="save_samples_button" value="Save"/>
-                </div>
-            %endif
-            
-        %endif
-        <input type="hidden" name="request_id" value="${request.id}" />
-    </form>
-</div>
-
-<br/>
-
-%if request.unsubmitted():
-<div class="toolForm">
-    <form id="show_request" name="show_request" action="${h.url_for( controller='requests_admin', action='show_request', edit_mode=edit_mode )}" enctype="multipart/form-data" method="post" >
-        <div class="form-row">
-            <div class="msg_list">
-                <h4 class="msg_head"><u>Import samples from csv file</u></h4>
-                <div class="msg_body">
-                    <input type="file" name="file_data" />
-                    <input type="submit" name="import_samples_button" value="Import samples"/>
-                    <br/>
-                    <div class="toolParamHelp" style="clear: both;">
-                        The csv file must be in the following format:<br/>
-                        SampleName,DataLibrary,DataLibraryFolder,FieldValue1,FieldValue2...
-                    </div>
-                </div>
-            </div>
-        </div>
-        <input type="hidden" name="request_id" value="${request.id}" />
-    </form>
-</div>
-%endif
-
--- a/templates/admin/samples/events.mako
+++ /dev/null
@@ -1,63 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-<%def name="title()">Events for Sample ${sample.name}</%def>
-
-<h2>Events for Sample "${sample.name}"</h2>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='show_request', id=trans.security.encode_id(sample.request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-</ul>
-<h3>User: ${sample.request.user.email}</h3>
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<div class="toolForm">
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>State</th>
-                <th>Description</th>
-                <th>Last Update</th>
-                <th>Comments</th>
-            </tr>
-        </thead>
-        <tbody>
-            %for state, desc, updated, comments in events_list:    
-                <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
-                    <td><b><a>${state}</a></b></td>
-                    <td><a>${desc}</a></td>
-                    <td><a>${updated}</a></td>
-                    <td><a>${comments}</a></td>
-                </tr>             
-            %endfor
-        </tbody>
-    </table>
-</div>
-<div class="toolForm">
-    <div class="toolFormTitle">Change current state</div>
-    <div class="toolFormBody">
-        <form name="event" action="${h.url_for( controller='requests_admin', action='save_state', new=True, sample_id=sample.id)}" method="post" >
-                %for w in widgets:
-                    <div class="form-row">
-                        <label>
-                            ${w[0]}
-                        </label>
-                        ${w[1].get_html()}
-                        %if w[0] == 'Comments':
-                            <div class="toolParamHelp" style="clear: both;">
-                                Optional
-                            </div>
-                        %endif
-                    </div>
-                %endfor
-            <div class="form-row">
-                <input type="submit" name="add_event_button" value="Save"/>
-            </div>
-        </form>
-    </div>
-</div>
--- a/scripts/galaxy_messaging/server/data_transfer.py
+++ b/scripts/galaxy_messaging/server/data_transfer.py
@@ -194,7 +194,7 @@ class DataTransfer(object):
         Update the data transfer status for this dataset in the database
         '''
         try:
-            log.debug('Setting status "%s" for dataset "%s"' % ( status, str(dataset_index) ) )
+            log.debug('Setting status "%s" for dataset "%s" of sample "%s"' % ( status, str(dataset_index), str(self.sample_id) ) )
             df = from_json_string(self.galaxydb.get_sample_dataset_files(self.sample_id))
             if dataset_index == 'All':
                 for dataset in self.dataset_files:
--- a/scripts/galaxy_messaging/server/galaxydb_interface.py
+++ b/scripts/galaxy_messaging/server/galaxydb_interface.py
@@ -28,7 +28,7 @@ class GalaxyDbInterface(object):
     def __init__(self, dbstr):
         self.dbstr = dbstr
         self.db_engine = create_engine(self.dbstr)    
-#        self.db_engine.echo = True  
+        self.db_engine.echo = True  
         self.metadata = MetaData(self.db_engine)
         self.session = sessionmaker(bind=self.db_engine)
         self.event_table = Table('sample_event', self.metadata, autoload=True )
--- a/templates/requests/sample_state.mako
+++ /dev/null
@@ -1,5 +0,0 @@
-<%def name="render_sample_state( sample )">
-    <a href="${h.url_for( controller='requests_admin', action='show_events', sample_id=sample.id)}">${sample.current_state().name}</a>
-</%def>
-
-${render_sample_state( sample )}
--- a/templates/admin/requests/dataset.mako
+++ b/templates/admin/requests/dataset.mako
@@ -11,7 +11,7 @@
 
 <ul class="manage-table-actions"><li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">
+        <a class="action-button" href="${h.url_for( controller='requests_common', action='show_datatx_page', cntrller='requests_admin', sample_id=trans.security.encode_id(sample.id) )}"><span>Dataset transfer page</span></a></li></ul>
--- a/templates/admin/samples/bar_codes.mako
+++ /dev/null
@@ -1,46 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-
-<h2>Bar codes for Samples of Request "${request.name}"</h2>
-<h3>User: ${user.email}</h3>
-
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='show_request', id=trans.security.encode_id(request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    <form name="bar_codes" action="${h.url_for( controller='requests_admin', action='save_bar_codes', request_id=request.id)}" method="post" >
-        <table class="grid">
-            <thead>
-                <tr>
-                    <th>Name</th>
-                    <th>Description</th>
-                    <th>Bar code</th>
-                </tr>
-            </thead>
-            <tbody>
-                %for index, sample in enumerate(samples_list):    
-                    <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
-                        <td><b><a>${sample.name}</a></b></td>
-                        <td><a>${sample.desc}</a></td>
-                        <td>
-                            ${widgets[index].get_html()}
-                        </td>
-                    </tr>             
-                %endfor
-            </tbody>
-        </table>
-        <div class="form-row">
-            <input type="submit" name="save_bar_codes" value="Save"/>
-        </div>
-    </form>
-</div>
--- a/templates/requests/edit_request.mako
+++ /dev/null
@@ -1,84 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$( function() {
-    $( "select[refresh_on_change='true']").change( function() {
-        var refresh = false;
-        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
-        if ( refresh_on_change_values ) {
-            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
-            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
-            for( i= 0; i < refresh_on_change_values.length; i++ ) {
-                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
-                    refresh = true;
-                    break;
-                }
-            }
-        }
-        else {
-            refresh = true;
-        }
-        if ( refresh ){
-            $( "#edit_request" ).submit();
-        }
-    });
-});
-</script>
-
-<br/>
-<br/>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests', action='list')}">
-        <span>Browse requests</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    <div class="toolFormTitle">Edit request "${request.name}"</div>
-    %if len(select_request_type.options) == 1:
-        There are no request types created for a new request.
-    %else:
-        <div class="toolFormBody">
-            <form name="edit_request" id="edit_request" action="${h.url_for( controller='requests', action='edit', request_id=request.id)}" method="post" >
-                <div class="form-row">
-                    <label>
-                        Select Request Type:
-                    </label>
-                    ${select_request_type.get_html()}
-                </div>
-
-               %if select_request_type.get_selected() != ('Select one', 'none'):
-                   %for i, field in enumerate(widgets):
-                        <div class="form-row">
-                            <label>${field['label']}</label>
-                            ${field['widget'].get_html()}
-                            %if field['label'] == 'Data library' and new_library:
-                                ${new_library.get_html()}
-                            %endif
-                            <div class="toolParamHelp" style="clear: both;">
-                                ${field['helptext']}
-                            </div>
-                            <div style="clear: both"></div>
-                        </div>
-                    %endfor                    
-                    <div class="form-row">
-                        <div style="float: left; width: 250px; margin-right: 10px;">
-                            <input type="hidden" name="refresh" value="true" size="40"/>
-                        </div>
-                      <div style="clear: both"></div>
-                    </div>
-                    <div class="form-row">
-                        <input type="submit" name="save_changes_request_button" value="Save changes"/> 
-                        ##<input type="submit" name="edit_samples_button" value="Edit samples"/>
-                    </div>
-               %endif
-        </form>
-    </div>
-</div>
-%endif
--- a/templates/requests/new_request.mako
+++ /dev/null
@@ -1,94 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$( function() {
-    $( "select[refresh_on_change='true']").change( function() {
-        var refresh = false;
-        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
-        if ( refresh_on_change_values ) {
-            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
-            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
-            for( i= 0; i < refresh_on_change_values.length; i++ ) {
-                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
-                    refresh = true;
-                    break;
-                }
-            }
-        }
-        else {
-            refresh = true;
-        }
-        if ( refresh ){
-            $( "#new_request" ).submit();
-        }
-    });
-});
-</script>
-
-<%def name="javascripts()">
-   ${parent.javascripts()}
-   ${h.js("jquery.autocomplete", "autocomplete_tagging" )}
-</%def>
-
-<%def name="stylesheets()">
-    ${parent.stylesheets()}
-    ${h.css( "autocomplete_tagging" )}
-</%def>
-
-<br/>
-<br/>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests', action='list')}">
-        <span>Browse requests</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    <div class="toolFormTitle">Add a new request</div>
-    %if len(select_request_type.options) == 1:
-        There are no request types created for a new request.
-    %else:
-        <div class="toolFormBody">
-            <form name="new_request" id="new_request" action="${h.url_for( controller='requests', action='new', create=True )}" method="post" >
-                <div class="form-row">
-                    <label>
-                        Select Request Type:
-                    </label>
-                    ${select_request_type.get_html()}
-                </div>
-
-               %if select_request_type.get_selected() != ('Select one', 'none'):
-                   %for i, field in enumerate(widgets):
-                        <div class="form-row">
-                            <label>${field['label']}</label>
-                            ${field['widget'].get_html()}
-                            ##%if field['label'] == 'Data library' and new_library:
-                            ##    ${new_library.get_html()}
-                            ##%endif
-                            <div class="toolParamHelp" style="clear: both;">
-                                ${field['helptext']}
-                            </div>
-                            <div style="clear: both"></div>
-                        </div>
-                    %endfor                    
-                    <div class="form-row">
-                        <div style="float: left; width: 250px; margin-right: 10px;">
-                            <input type="hidden" name="refresh" value="true" size="40"/>
-                        </div>
-                      <div style="clear: both"></div>
-                    </div>
-                    <div class="form-row">
-                        <input type="submit" name="create_request_button" value="Save"/> 
-                        <input type="submit" name="create_request_samples_button" value="Add samples"/>
-                    </div>
-               %endif
-        </form>
-    </div>
-</div>
-%endif
--- /dev/null
+++ b/templates/requests/common/index.mako
@@ -0,0 +1,16 @@
+<%inherit file="/webapps/galaxy/base_panels.mako"/>
+
+<%def name="init()">
+<%
+    self.has_left_panel=False
+    self.has_right_panel=False
+    self.active_view="requests"
+    self.message_box_visible=False
+%>
+</%def>
+
+<%def name="center_panel()">
+
+    <iframe name="galaxy_main" id="galaxy_main" frameborder="0" style="position: absolute; width: 100%; height: 100%;" src="${h.url_for( controller="requests", action="list" )}"></iframe>
+
+</%def>
--- a/templates/sample/index.mako
+++ /dev/null
@@ -1,16 +0,0 @@
-<%inherit file="/webapps/galaxy/base_panels.mako"/>
-
-<%def name="init()">
-<%
-    self.has_left_panel=False
-    self.has_right_panel=False
-    self.active_view="requests"
-
-%>
-</%def>
-
-<%def name="center_panel()">
-
-    <iframe name="galaxy_main" id="galaxy_main" frameborder="0" style="position: absolute; width: 100%; height: 100%;" src="${h.url_for( controller="sample", action="list", request_id=request_id )}"></iframe>
-
-</%def>
--- a/templates/requests/show_request.mako
+++ /dev/null
@@ -1,430 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$( function() {
-    $( "select[refresh_on_change='true']").change( function() {
-        var refresh = false;
-        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
-        if ( refresh_on_change_values ) {
-            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
-            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
-            for( i= 0; i < refresh_on_change_values.length; i++ ) {
-                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
-                    refresh = true;
-                    break;
-                }
-            }
-        }
-        else {
-            refresh = true;
-        }
-        if ( refresh ){
-            $( "#show_request" ).submit();
-        }
-    });
-});
-</script>
-
-
-<script type="text/javascript">
-$(document).ready(function(){
-    //hide the all of the element with class msg_body
-    $(".msg_body").hide();
-    //toggle the componenet with class msg_body
-    $(".msg_head").click(function(){
-        $(this).next(".msg_body").slideToggle(450);
-    });
-});
-</script>
-<style type="text/css">
-.msg_head {
-    padding: 0px 0px;
-    cursor: pointer;
-}
-
-}
-</style>
-
-%if request.rejected():
-    ${render_msg( "Reason for rejection: "+request.last_comment(), "warning" )}
-%endif
-
-<div class="grid-header">
-    <h2>Sequencing Request "${request.name}"</h2>
-</div>
-
-<ul class="manage-table-actions">
-    %if request.unsubmitted() and request.samples:
-        <li>
-            <a class="action-button" confirm="More samples cannot be added to this request once it is submitted. Click OK to submit." href="${h.url_for( controller='requests', action='list', operation='Submit', id=trans.security.encode_id(request.id) )}">
-            <span>Submit request</span></a>
-        </li>
-    %endif
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests', action='list', operation='events', id=trans.security.encode_id(request.id) )}">
-        <span>History</span></a>
-    </li>
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests', action='list')}">
-        <span>Browse requests</span></a>
-    </li>
-</ul>
-
-<%def name="show_basic_info_form( sample_index, sample, info )">
-    <td>
-        <input type="text" name=sample_${sample_index}_name value="${info['name']}" size="10"/>
-        <div class="toolParamHelp" style="clear: both;">
-            <i>${' (required)' }</i>
-        </div>
-    </td>
-    %if sample:
-        %if sample.request.unsubmitted():
-            <td></td>
-        %else:
-            <td><input type="text" name=sample_${sample_index}_barcode value="${info['barcode']}" size="10"/></td>
-        %endif
-    %else:
-        <td></td>
-    %endif
-    %if sample:
-        %if not sample.current_state():
-            <td>Unsubmitted</td>
-        %else:
-            <td><a href="${h.url_for( controller='requests_admin', action='show_events', sample_id=sample.id)}">${sample.current_state().name}</a></td>
-        %endif    
-    %else:
-        <td></td>
-    %endif
-    <td>${info['lib_widget'].get_html()}</td>
-    <td>${info['folder_widget'].get_html()}</td>
-    %if request.submitted() or request.complete(): 
-        %if sample:
-            <td><a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">${len(sample.dataset_files)}</a></td> 
-        %else:
-            <td><a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">Add</a></td>
-        %endif 
-    %endif 
-</%def>
-
-## This function displays the "Basic Information" grid
-<%def name="render_basic_info_grid()">
-    <h4>Sample Information</h4>
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>Name</th>
-                <th>Barcode</th>
-                <th>State</th>
-                <th>Data Library</th>
-                <th>Folder</th>
-                %if request.submitted() or request.complete(): 
-                    <th>Dataset(s) Transferred</th>
-                %endif
-                <th></th>
-            </tr>
-        <thead>
-        <tbody>
-            <%
-            trans.sa_session.refresh( request )
-            %>
-            %for sample_index, info in enumerate(current_samples):
-                <% 
-                    if sample_index in range(len(request.samples)):
-                        sample = request.samples[sample_index]
-                    else:
-                        sample = None 
-                %>
-                %if edit_mode == 'True':
-                    <tr>
-                        ${show_basic_info_form( sample_index, sample, info )}
-                    </tr>      
-                %else:
-                    <tr>
-                        %if sample_index in range(len(request.samples)):
-                            <td>${info['name']}</td>
-                            <td>${info['barcode']}</td>
-                            <td>
-                                %if sample.current_state():
-                                    <a href="${h.url_for( controller='requests', action='show_events', sample_id=sample.id)}">${sample.current_state().name}</a>
-                                %else:
-                                    Unsubmitted
-                                %endif
-                            </td>
-                            %if info['library']:
-                                <td><a href="${h.url_for( controller='library_common', action='browse_library', cntrller='library', id=trans.security.encode_id( info['library'].id ) )}">${info['library'].name}</a></td>
-                            %else:
-                                <td></td>
-                            %endif
-                            %if info['folder']:
-                                <td>${info['folder'].name}</td>
-                            %else:
-                                <td></td>
-                            %endif
-                            %if request.submitted() or request.complete(): 
-                                <td>
-                                    <a href="${h.url_for( controller='requests', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">${len(sample.dataset_files)}</a>
-                                </td>
-                            %endif
-                            
-                            
-                        %else:                                                            
-                            ${show_basic_info_form( sample_index, sample, info )}
-                        %endif
-                        %if request.unsubmitted() or request.rejected(): 
-                            <td>
-                                %if sample:
-                                    %if sample.request.unsubmitted():
-                                        <a class="action-button" href="${h.url_for( controller='requests_admin', action='delete_sample', request_id=request.id, sample_id=sample_index )}">
-                                        <img src="${h.url_for('/static/images/delete_icon.png')}" />
-                                        <span></span></a>
-                                    %endif
-                                %endif
-                            </td>
-                        %endif
-                    </tr>  
-                %endif
-            %endfor
-        </tbody>
-    </table>
-</%def>
-
-<%def name="render_sample_form( index, sample_name, sample_values, fields_dict )">
-    <td>
-        ${sample_name}
-    </td>
-    %for field_index, field in fields_dict.items():
-        <td>
-            %if field['type'] == 'TextField':
-                <input type="text" name="sample_${index}_field_${field_index}" value="${sample_values[field_index]}" size="7"/>
-            %elif field['type'] == 'SelectField':
-                <select name="sample_${index}_field_${field_index}" last_selected_value="2">
-                    %for option_index, option in enumerate(field['selectlist']):
-                        %if option == sample_values[field_index]:
-                            <option value="${option}" selected>${option}</option>
-                        %else:
-                            <option value="${option}">${option}</option>
-                        %endif
-                    %endfor
-                </select>
-            %elif field['type'] == 'WorkflowField':
-                <select name="sample_${index}_field_${field_index}">
-                    %if str(sample_values[field_index]) == 'none':
-                        <option value="none" selected>Select one</option>
-                    %else:
-                        <option value="none">Select one</option>
-                    %endif
-                    %for option_index, option in enumerate(request.user.stored_workflows):
-                        %if not option.deleted:
-                            %if str(option.id) == str(sample_values[field_index]):
-                                <option value="${option.id}" selected>${option.name}</option>
-                            %else:
-                                <option value="${option.id}">${option.name}</option>
-                            %endif
-                        %endif
-                    %endfor
-                </select>
-            %elif field['type'] == 'CheckboxField':
-                <input type="checkbox" name="sample_${index}_field_${field_index}" value="Yes"/>
-            %endif
-            <div class="toolParamHelp" style="clear: both;">
-                <i>${'('+field['required']+')' }</i>
-            </div>
-        </td>
-    %endfor   
-</%def>
-
-<%def name="render_sample( index, sample_name, sample_values, fields_dict )">
-    <td>
-        ${sample_name}
-    </td>
-    %for field_index, field in fields_dict.items():
-        <td>
-            %if sample_values[field_index]:
-                %if field['type'] == 'WorkflowField':
-                    %if str(sample_values[field_index]) != 'none':
-                        <% workflow = trans.sa_session.query( trans.app.model.StoredWorkflow ).get( int(sample_values[field_index]) ) %>
-                        <a href="${h.url_for( controller='workflow', action='run', id=trans.security.encode_id(workflow.id) )}">${workflow.name}</a>
-                    %endif
-                %else:
-                    ${sample_values[field_index]}
-                %endif
-            %else:
-                <i>None</i>
-            %endif
-
-        </td>
-    %endfor   
-</%def>
-
-<%def name="render_grid( grid_index, grid_name, fields_dict )">
-    <br/>
-    <div class="msg_list">
-    %if grid_name:
-        <h4 class="msg_head"><u>${grid_name}</u></h4>
-    %else:
-        <h4>Grid ${grid_index}</h4>
-    %endif
-    %if edit_mode == 'False' or len(current_samples) <= len(request.samples):
-        <div class="msg_body">
-    %else:
-        <div class="msg_body2">
-    %endif
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>Name</th>
-                %for index, field in fields_dict.items():
-                    <th>
-                        ${field['label']}
-                        <div class="toolParamHelp" style="clear: both;">
-                            <i>${field['helptext']}</i>
-                        </div>
-                    </th>
-                %endfor
-                <th></th>
-            </tr>
-        <thead>
-        <tbody>
-            <%
-            trans.sa_session.refresh( request )
-            %>
-            %for sample_index, sample in enumerate(current_samples):
-                %if edit_mode == 'True':
-                    <tr>
-                        ${render_sample_form( sample_index, sample['name'], sample['field_values'], fields_dict)}
-                    </tr>      
-                %else:
-                    <tr>
-                        %if sample_index in range(len(request.samples)):
-                            ${render_sample( sample_index, sample['name'], sample['field_values'], fields_dict )}
-                        %else:                                                            
-                            ${render_sample_form( sample_index, sample['name'], sample['field_values'], fields_dict)}
-                        %endif
-                    </tr>  
-                %endif
-            %endfor
-        </tbody>
-    </table>
-    </div>
-    </div>
-</%def>
-
-<div class="toolForm">
-    <form id="request_details" name="request_details" >
-        <div class="form-row">
-            <div class="msg_list">
-                <h4 class="msg_head"><u>Request Information</u></h4>
-                <div class="msg_body">
-                    %for index, rd in enumerate(request_details):
-                        <div class="form-row">
-                            <label>${rd['label']}</label>
-                            %if not rd['value']:
-                                <i>None</i>
-                            %else:                      
-                                %if rd['label'] == 'State':
-                                    <a href="${h.url_for( controller='requests_admin', action='list', operation='events', id=trans.security.encode_id(request.id) )}">${rd['value']}</a>
-                                %else:
-                                    ${rd['value']}     
-                                %endif
-                            %endif
-                        </div>
-                        <div style="clear: both"></div>
-                    %endfor
-                    <div class="form-row">
-                    <ul class="manage-table-actions">
-                        <li>
-                            <a class="action-button"  href="${h.url_for( controller='requests_admin', action='list', operation='Edit', id=trans.security.encode_id(request.id))}">
-                            <span>Edit request details</span></a>
-                        </li>
-                    </ul>
-                    </div>
-                </div>
-            </div>
-        </div>
-    </form>
-    <form id="show_request" name="show_request" action="${h.url_for( controller='requests', action='show_request', edit_mode=edit_mode )}" enctype="multipart/form-data" method="post" >
-        <div class="form-row">
-            %if current_samples:
-                ## first render the basic info grid 
-                ${render_basic_info_grid()}
-                ## then render the other grid(s)
-                <% trans.sa_session.refresh( request.type.sample_form ) %>
-                %for grid_index, grid_name in enumerate(request.type.sample_form.layout):
-                    ${render_grid( grid_index, grid_name, request.type.sample_form.fields_of_grid( grid_index ) )}
-                    <br/>
-                %endfor
-            %else:
-                <label>There are no samples.</label>
-            %endif
-        </div>
-        %if request.unsubmitted() and edit_mode == 'False':
-            <table class="grid">
-                <tbody>
-                    <tr>
-                        <div class="form-row">
-                            <td>
-                                %if current_samples:
-                                    <label>Copy </label>
-                                    <input type="integer" name="num_sample_to_copy" value="1" size="3"/>
-                                    <label>sample(s) from sample</label>
-                                    ${sample_copy.get_html()}
-                                %endif
-                                <input type="submit" name="add_sample_button" value="Add New"/>
-                            </td>
-                            <td>
-                                %if len(current_samples) and len(current_samples) <= len(request.samples):                        
-                                    <input type="submit" name="edit_samples_button" value="Edit samples"/>
-                                %endif
-                            </td>
-                        </div>
-                    </tr> 
-                </tbody>
-            </table>
-        %endif
-        %if request.unsubmitted() and (request.samples or current_samples): 
-            <div class="form-row">
-                <div style="float: left; width: 250px; margin-right: 10px;">
-                    <input type="hidden" name="refresh" value="true" size="40"/>
-                </div>
-              <div style="clear: both"></div>
-            </div>
-            <div class="form-row">
-                <input type="submit" name="save_samples_button" value="Save"/>
-                %if edit_mode == 'True':
-                    <input type="submit" name="cancel_changes_button" value="Cancel"/>
-                %endif
-            </div>
-        %endif
-        <input type="hidden" name="request_id" value="${request.id}" />
-    </form>
-</div>
-
-
-<br/>
-%if request.unsubmitted():
-<div class="toolForm">
-    <form id="show_request" name="show_request" action="${h.url_for( controller='requests', action='show_request', edit_mode=edit_mode )}" enctype="multipart/form-data" method="post" >
-        <div class="form-row">
-            <div class="msg_list">
-                <h4 class="msg_head"><u>Import samples from csv file</u></h4>
-                <div class="msg_body">
-                    <input type="file" name="file_data" />
-                    <input type="submit" name="import_samples_button" value="Import samples"/>
-                    <br/>
-                    <div class="toolParamHelp" style="clear: both;">
-                        The csv file must be in the following format:<br/>
-                        SampleName,DataLibrary,DataLibraryFolder,FieldValue1,FieldValue2...
-                    </div>
-                </div>
-            </div>
-        </div>
-        <input type="hidden" name="request_id" value="${request.id}" />
-    </form>
-</div>
-%endif
--- /dev/null
+++ b/templates/requests/common/new_request.mako
@@ -0,0 +1,91 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+
+%if message:
+    ${render_msg( message, status )}
+%endif
+
+<script type="text/javascript">
+$( function() {
+    $( "select[refresh_on_change='true']").change( function() {
+        var refresh = false;
+        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
+        if ( refresh_on_change_values ) {
+            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
+            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
+            for( i= 0; i < refresh_on_change_values.length; i++ ) {
+                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
+                    refresh = true;
+                    break;
+                }
+            }
+        }
+        else {
+            refresh = true;
+        }
+        if ( refresh ){
+            $( "#new_request" ).submit();
+        }
+    });
+});
+</script>
+
+<%def name="javascripts()">
+   ${parent.javascripts()}
+   ${h.js("jquery.autocomplete", "autocomplete_tagging" )}
+</%def>
+
+<%def name="stylesheets()">
+    ${parent.stylesheets()}
+    ${h.css( "autocomplete_tagging" )}
+</%def>
+
+<br/>
+<br/>
+<ul class="manage-table-actions">
+    <li>
+        <a class="action-button"  href="${h.url_for( controller=cntrller, cntrller=cntrller, action='list')}">
+        <span>Browse requests</span></a>
+    </li>
+</ul>
+
+<div class="toolForm">
+    <div class="toolFormTitle">Add a new request</div>
+    %if len(select_request_type.options) == 1:
+        There are no request types created for a new request.
+    %else:
+        <div class="toolFormBody">
+            <form name="new_request" id="new_request" action="${h.url_for( controller='requests_common', action='new', cntrller=cntrller)}" method="post" >
+                <div class="form-row">
+                    <label>
+                        Select request type
+                    </label>
+                    ${select_request_type.get_html()}
+                </div>
+
+               %if select_request_type.get_selected() != ('Select one', 'none'):
+                   %for i, field in enumerate(widgets):
+                        <div class="form-row">
+                            <label>${field['label']}</label>
+                            ${field['widget'].get_html()}
+                            <div class="toolParamHelp" style="clear: both;">
+                                ${field['helptext']}
+                            </div>
+                            <div style="clear: both"></div>
+                        </div>
+                    %endfor                    
+                    <div class="form-row">
+                        <input type="submit" name="create_request_button" value="Save"/> 
+                        <input type="submit" name="create_request_samples_button" value="Add samples"/>
+                    </div>
+               %endif
+                <div class="form-row">
+                    <div style="float: left; width: 250px; margin-right: 10px;">
+                        <input type="hidden" name="refresh" value="true" size="40"/>
+                    </div>
+                  <div style="clear: both"></div>
+                </div>
+        </form>
+    </div>
+</div>
+%endif
--- a/templates/admin/requests/get_data.mako
+++ /dev/null
@@ -1,227 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$(document).ready(function(){
-    //hide the all of the element with class msg_body
-    $(".msg_body").hide();
-    //toggle the componenet with class msg_body
-    $(".msg_head").click(function(){
-        $(this).next(".msg_body").slideToggle(450);
-    });
-});
-
-
-
-
-</script>
-
-<script type="text/javascript">
-   function display_file_details(sample_id, folder_path)
-   {
-       var w = document.get_data.files_list.selectedIndex;
-       var selected_value = document.get_data.files_list.options[w].value;
-       var cell = $("#file_details");
-       if(selected_value.charAt(selected_value.length-1) != '/')
-       {
-            // Make ajax call
-            $.ajax( {
-                type: "POST",
-                url: "${h.url_for( controller='requests_admin', action='get_file_details' )}",
-                dataType: "json",
-                data: { id: sample_id, folder_path: document.get_data.folder_path.value+selected_value },
-                success : function ( data ) {
-                    cell.html( '<label>'+data+'</label>' )
-                }
-            });
-        }
-        else 
-        {
-            cell.html( '' )
-        }
-        
-       
-   }
-</script>
-
-<script type="text/javascript">
-   function open_folder1(sample_id, folder_path)
-   {
-       var w = document.get_data.files_list.selectedIndex;
-       var selected_value = document.get_data.files_list.options[w].value;
-       var cell = $("#file_details");
-       if(selected_value.charAt(selected_value.length-1) == '/')
-       {
-           document.get_data.folder_path.value = document.get_data.folder_path.value+selected_value
-            // Make ajax call
-            $.ajax( {
-                type: "POST",
-                url: "${h.url_for( controller='requests_admin', action='open_folder' )}",
-                dataType: "json",
-                data: { id: sample_id, folder_path: document.get_data.folder_path.value },
-                success : function ( data ) {
-                    document.get_data.files_list.options.length = 0
-                    for(i=0; i<data.length; i++) 
-                    {
-                        var newOpt = new Option(data[i], data[i]);
-                        document.get_data.files_list.options[i] = newOpt;
-                    }
-                    //cell.html( '<label>'+data+'</label>' )
-                    
-                }
-            });
-       }
-        else 
-        {
-            cell.html( '' )
-        }
-   }
-</script>
-
-
-<style type="text/css">
-.msg_head {
-    padding: 0px 0px;
-    cursor: pointer;
-}
-
-}
-</style>
-
-
-<h2>Data transfer from Sequencer</h2>
-<h3>Sample "${sample.name}" of Request "${sample.request.name}"</h3>
-<br/>
-<br/>
-
-<ul class="manage-table-actions">
-    %if sample.request.submitted() and sample.inprogress_dataset_files():
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">
-        <span>Refresh this page</span></a>
-    </li>
-    %endif
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='manage_request_types', operation='view', id=trans.security.encode_id(sample.request.type.id) )}">
-        <span>Sequencer information</span></a>
-    </li>
-    <li>
-        <a class="action-button" href="${h.url_for( controller='library_common', action='browse_library', cntrller='library_admin', id=trans.security.encode_id( sample.library.id ) )}">
-        <span>${sample.library.name} Data Library</span></a>
-    </li>
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='show_request', id=trans.security.encode_id(sample.request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    %if len(dataset_files):
-##    <form name="get_data" action="${h.url_for( controller='requests_admin', action='get_data', sample_id=sample.id)}" method="post" >
-        <div class="form-row">
-        <h4>Sample Dataset(s)</h4>
-        %if sample.untransferred_dataset_files():
-            <div class="form-row">
-                <ul class="manage-table-actions">
-                    <li>
-                        <a class="action-button" href="${h.url_for( controller='requests_admin', action='get_data', start_transfer_button=True, sample_id=sample.id )}">
-                        <span>Start transfer</span></a>
-                    </li>
-                </ul>
-             </div>
-         %endif
-        <div class="form-row">
-            <table class="grid">
-            <thead>
-                <tr>
-                    <th>Dataset File</th>
-                    <th>Transfer Status</th>
-                    <th></th>
-                </tr>
-            <thead>
-                <tbody>
-                    %for dataset_index, dataset_file in enumerate(dataset_files):
-                        ${sample_dataset_files( dataset_index, dataset_file['name'], dataset_file['status'] )}
-                    %endfor
-                </tbody>
-            </table>
-        </div>
-        </div>
-
-##    </form>
-##</div>
-
-
-<br/>
-<br/>
-%endif
-
-##<div class="toolForm">
-    <form name="get_data" id="get_data" action="${h.url_for( controller='requests_admin', action='get_data', sample_id=sample.id)}" method="post" >
-        <div class="form-row">
-            ##<div class="toolFormTitle">Select files for transfer</div>
-            <h4>Select files for transfer</h4>
-            <div style="width: 60%;">
-                <div class="form-row">
-                    <label>Folder path on the sequencer:</label>
-                    <input type="text" name="folder_path" value="${folder_path}" size="100"/>
-                    <input type="submit" name="browse_button" value="List contents"/>
-                    ##<input type="submit" name="open_folder" value="Open folder"/>
-                    <input type="submit" name="folder_up" value="Up"/>
-                </div>
-                <div class="form-row">
-                    <select name="files_list" id="files_list" style="max-width: 98%; width: 98%; height: 150px; font-size: 100%;" ondblclick="open_folder1(${sample.id}, '${folder_path}')" onChange="display_file_details(${sample.id}, '${folder_path}')" multiple>
-                        %for index, f in enumerate(files):
-                            <option value="${f}">${f}</option>
-                        %endfor
-                    </select> 
-                    <br/>
-                    <div id="file_details" class="toolParamHelp" style="clear: both;">
-                        
-                    </div>
-                </div>
-                <div class="form-row">
-                    <div class="toolParamHelp" style="clear: both;">
-                        After selecting dataset(s), be sure to click on the <b>Start transfer</b> button. 
-                        Once the transfer is complete the dataset(s) will show up on this page.
-                    </div>
-                    <input type="submit" name="select_files_button" value="Select"/>
-                </div>
-            </div>
-        </div>
-    </form>
-</div>
-
-<%def name="sample_dataset_files( dataset_index, dataset_name, status )">
-    <tr>
-        <td>
-            <label class="msg_head"><a href="${h.url_for( controller='requests_admin', action='dataset_details', sample_id=trans.security.encode_id(sample.id), dataset_index=dataset_index )}">${dataset_name}</a></label>
-##            <div class="msg_head"><u>${dataset_file.split('/')[-1]}</u></div>
-##            <div class="msg_body">
-##                ${dataset_file}
-##            </div>
-        </td>
-        <td>
-            %if status not in [sample.transfer_status.NOT_STARTED, sample.transfer_status.COMPLETE]: 
-                <i>${status}</i>
-            %else:
-                ${status}
-            %endif
-        </td>
-        ##<td></td>
-        %if status == sample.transfer_status.NOT_STARTED: 
-        <td>
-            <a class="action-button" href="${h.url_for( controller='requests_admin', action='get_data', sample_id=sample.id, remove_dataset_button=True, dataset_index=dataset_index )}">
-            <img src="${h.url_for('/static/images/delete_icon.png')}" />
-            <span></span></a>
-        </td>
-        %else:
-            <td></td>
-        %endif
-    </tr>
-</%def>
--- a/templates/admin/requests/add_states.mako
+++ /dev/null
@@ -1,26 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<div class="toolForm">
-    <div class="toolFormTitle">Create ${num_states} states for the '${request_type_name}' request type</div>
-    <form name="new_form_fields" action="${h.url_for( controller='requests_admin', action='request_type', name=request_type_name, description=desc, num_states=num_states, request_form_id=request_form_id, sample_form_id=sample_form_id)}" method="post" >
-        <div class="toolFormBody">
-            %for element_count in range( num_states ):
-                <div class="form-row">
-                    <label>${1+element_count}) State name:</label>
-                    <input type="text" name="state_name_${element_count}" value="" size="40"/>
-                    <label>State help text (optional):</label>
-                    <input type="text" name="state_desc_${element_count}" value="" size="40"/>
-                </div>
-                <div style="clear: both"></div>
-            %endfor
-        </div>
-        <div class="form-row">
-            <input type="submit" name="save_request_type" value="Save"/>
-        </div>
-    </form>
-</div>
--- /dev/null
+++ b/templates/requests/common/edit_request.mako
@@ -0,0 +1,84 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+
+%if message:
+    ${render_msg( message, status )}
+%endif
+
+<script type="text/javascript">
+$( function() {
+    $( "select[refresh_on_change='true']").change( function() {
+        var refresh = false;
+        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
+        if ( refresh_on_change_values ) {
+            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
+            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
+            for( i= 0; i < refresh_on_change_values.length; i++ ) {
+                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
+                    refresh = true;
+                    break;
+                }
+            }
+        }
+        else {
+            refresh = true;
+        }
+        if ( refresh ){
+            $( "#edit_request" ).submit();
+        }
+    });
+});
+</script>
+
+<br/>
+<br/>
+<ul class="manage-table-actions">
+    <li>
+        <a class="action-button"  href="${h.url_for( controller=cntrller, cntrller=cntrller, action='list')}">
+        <span>Browse requests</span></a>
+    </li>
+</ul>
+
+<div class="toolForm">
+    <div class="toolFormTitle">Edit request "${request.name}"</div>
+    %if len(select_request_type.options) == 1:
+        There are no request types created for a new request.
+    %else:
+        <div class="toolFormBody">
+            <form name="edit_request" id="edit_request" action="${h.url_for( controller='requests_common', cntrller=cntrller, action='edit', id=trans.security.encode_id(request.id))}" method="post" >
+                <div class="form-row">
+                    <label>
+                        Select Request Type:
+                    </label>
+                    ${select_request_type.get_html()}
+                </div>
+
+               %if select_request_type.get_selected() != ('Select one', 'none'):
+                   %for i, field in enumerate(widgets):
+                        <div class="form-row">
+                            <label>${field['label']}</label>
+                            ${field['widget'].get_html()}
+                            %if field['label'] == 'Data library' and new_library:
+                                ${new_library.get_html()}
+                            %endif
+                            <div class="toolParamHelp" style="clear: both;">
+                                ${field['helptext']}
+                            </div>
+                            <div style="clear: both"></div>
+                        </div>
+                    %endfor                    
+                    <div class="form-row">
+                        <div style="float: left; width: 250px; margin-right: 10px;">
+                            <input type="hidden" name="refresh" value="true" size="40"/>
+                        </div>
+                      <div style="clear: both"></div>
+                    </div>
+                    <div class="form-row">
+                        <input type="submit" name="save_changes_request_button" value="Save changes"/> 
+                        ##<input type="submit" name="edit_samples_button" value="Edit samples"/>
+                    </div>
+               %endif
+        </form>
+    </div>
+</div>
+%endif
--- a/lib/galaxy/web/controllers/requests.py
+++ b/lib/galaxy/web/controllers/requests.py
@@ -84,7 +84,7 @@ class RequestsGrid( grids.Grid ):
         NameColumn( "Name", 
                     key="name", 
                     model_class=model.Request,
-                    link=( lambda item: iff( item.deleted, None, dict( operation="show_request", id=item.id ) ) ),
+                    link=( lambda item: iff( item.deleted, None, dict( operation="show", id=item.id ) ) ),
                     attach_popup=True, 
                     filterable="advanced" ),
         DescriptionColumn( "Description",
@@ -92,7 +92,7 @@ class RequestsGrid( grids.Grid ):
                            model_class=model.Request,
                            filterable="advanced" ),
         SamplesColumn( "Sample(s)", 
-                       link=( lambda item: iff( item.deleted, None, dict( operation="show_request", id=item.id ) ) ), ),
+                       link=( lambda item: iff( item.deleted, None, dict( operation="show", id=item.id ) ) ), ),
         TypeColumn( "Type" ),
         grids.GridColumn( "Last Updated", key="update_time", format=time_ago ),
         grids.DeletedColumn( "Deleted", 
@@ -120,7 +120,8 @@ class RequestsGrid( grids.Grid ):
 
     ]
     global_actions = [
-        grids.GridAction( "Create new request", dict( controller='requests', 
+        grids.GridAction( "Create new request", dict( controller='requests_common',
+                                                      cntrller='requests', 
                                                       action='new', 
                                                       select_request_type='True' ) )
     ]
@@ -149,18 +150,36 @@ class Requests( BaseController ):
                                                                   action='list',
                                                                   status='error',
                                                                   message="Invalid request ID") )
-            if operation == "show_request":
-                return self.__show_request( trans, **kwd )
+            if operation == "show":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests',
+                                                                  action='show',
+                                                                  **kwd ) )
             elif operation == "submit":
-                return self.__submit_request( trans, **kwd )
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests',
+                                                                  action='submit',
+                                                                  **kwd ) )
             elif operation == "delete":
-                return self.__delete_request( trans, **kwd )
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests',
+                                                                  action='delete',
+                                                                  **kwd ) )
             elif operation == "undelete":
-                return self.__undelete_request( trans, **kwd )
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests',
+                                                                  action='undelete',
+                                                                  **kwd ) )
             elif operation == "edit":
-                return self.__edit_request( trans, **kwd )
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests',
+                                                                  action='edit',
+                                                                  show=True, **kwd ) )
             elif operation == "events":
-                return self.__request_events( trans, **kwd )
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests',
+                                                                  action='events',
+                                                                  **kwd ) )
         # if there are one or more requests that has been rejected by the admin
         # recently, then show a message as a reminder to the user
         rlist = trans.sa_session.query( trans.app.model.Request ) \
@@ -176,915 +195,4 @@ class Requests( BaseController ):
                              % rejected 
         # Render the list view
         return self.request_grid( trans, **kwd )
-    def __request_events(self, trans, **kwd):
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            message = "Invalid request ID"
-            log.warn( message )
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message,
-                                                              **kwd) )
-        events_list = []
-        all_events = request.events
-        for event in all_events:         
-            events_list.append((event.state, time_ago(event.update_time), event.comment))
-        return trans.fill_template( '/requests/events.mako', 
-                                    events_list=events_list, request=request)
-    def request_details(self, trans, id):
-        '''
-        Shows the request details
-        '''
-        request = trans.sa_session.query( trans.app.model.Request ).get( id )
-        # list of widgets to be rendered on the request form
-        request_details = []
-        # main details
-        request_details.append(dict(label='Description', 
-                                    value=request.desc, 
-                                    helptext=''))
-        request_details.append(dict(label='Type', 
-                                    value=request.type.name, 
-                                    helptext=''))
-
-        request_details.append(dict(label='State', 
-                                    value=request.state(), 
-                                    helptext=''))
-        request_details.append(dict(label='Date created', 
-                                    value=request.create_time, 
-                                    helptext=''))
-        # form fields
-        for index, field in enumerate(request.type.request_form.fields):
-            if field['required']:
-                req = 'Required'
-            else:
-                req = 'Optional'
-            if field['type'] == 'AddressField':
-                if request.values.content[index]:
-                    request_details.append(dict(label=field['label'],
-                                                value=trans.sa_session.query( trans.app.model.UserAddress ).get( int( request.values.content[index] ) ).get_html(),
-                                                helptext=field['helptext']+' ('+req+')'))
-                else:
-                    request_details.append(dict(label=field['label'],
-                                                value=None,
-                                                helptext=field['helptext']+' ('+req+')'))
-
-            else: 
-                request_details.append(dict(label=field['label'],
-                                            value=request.values.content[index],
-                                            helptext=field['helptext']+' ('+req+')'))
-        if request.notify:
-            notify = 'Yes'
-        else:
-            notify = 'No'
-        request_details.append(dict(label='Send email notification once the sequencing request is complete', 
-                                    value=notify, 
-                                    helptext=''))
-        return request_details   
-    def __show_request(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        add_sample = params.get('add_sample', False)
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid request ID") )
-        # get all data libraries accessible to this user
-        libraries = request.user.accessible_libraries( trans, [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ] )
-        current_samples = []
-        for i, s in enumerate(request.samples):
-            lib_widget, folder_widget = self.__library_widgets(trans, request.user, i, libraries, s, **kwd)
-            current_samples.append(dict(name=s.name,
-                                        barcode=s.bar_code,
-                                        library=s.library,
-                                        folder=s.folder,
-                                        dataset_files=s.dataset_files,
-                                        field_values=s.values.content,
-                                        lib_widget=lib_widget,
-                                        folder_widget=folder_widget))
-        if add_sample:
-            lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
-                                                               len(current_samples)+1, 
-                                                               libraries, None, **kwd)
-            current_samples.append(dict(name='Sample_%i' % (len(current_samples)+1),
-                                        barcode='',
-                                        library=None,
-                                        folder=None,
-                                        dataset_files=[],
-                                        field_values=['' for field in request.type.sample_form.fields],
-                                        lib_widget=lib_widget,
-                                        folder_widget=folder_widget))
-        return trans.fill_template( '/requests/show_request.mako',
-                                    request=request,
-                                    request_details=self.request_details(trans, request.id),
-                                    current_samples=current_samples,
-                                    sample_copy=self.__copy_sample(current_samples), 
-                                    details='hide', edit_mode=util.restore_text( params.get( 'edit_mode', 'False'  ) ),
-                                    message=message, status=status )
-    def __library_widgets(self, trans, user, sample_index, libraries, sample=None, lib_id=None, folder_id=None, **kwd):
-        '''
-        This method creates the data library & folder selectbox for creating &
-        editing samples. First we get a list of all the libraries accessible to
-        the current user and display it in a selectbox. If the user has selected an
-        existing library then display all the accessible sub folders of the selected 
-        data library. 
-        '''
-        params = util.Params( kwd )
-        # data library selectbox
-        if not lib_id:
-            lib_id = params.get( "sample_%i_library_id" % sample_index, 'none'  )
-        selected_lib = None
-        if sample and lib_id == 'none':
-            if sample.library:
-                lib_id = str(sample.library.id)
-                selected_lib = sample.library
-        # create data library selectbox with refresh on change enabled
-        lib_id_list = ['new'] + [str(lib.id) for lib in libraries.keys()]
-        lib_widget = SelectField( "sample_%i_library_id" % sample_index, 
-                                refresh_on_change=True, 
-                                refresh_on_change_values=lib_id_list )
-        # fill up the options in the Library selectbox
-        # first option 'none' is the value for "Select one" option
-        if lib_id == 'none':
-            lib_widget.add_option('Select one', 'none', selected=True)
-        else:
-            lib_widget.add_option('Select one', 'none')
-        # all the libraries available to the selected user
-        for lib, hidden_folder_ids in libraries.items():
-            if str(lib.id) == str(lib_id):
-                lib_widget.add_option(lib.name, lib.id, selected=True)
-                selected_lib, selected_hidden_folder_ids = lib, hidden_folder_ids.split(',')
-            else:
-                lib_widget.add_option(lib.name, lib.id)
-            lib_widget.refresh_on_change_values.append(lib.id)
-        # create the folder selectbox
-        folder_widget = SelectField( "sample_%i_folder_id" % sample_index )
-        # when editing a request, either the user has already selected a subfolder or not
-        if sample:
-            if sample.folder:
-                current_fid = sample.folder.id
-            else: 
-                # when a folder not yet associated with the request then the 
-                # the current folder is set to the root_folder of the 
-                # parent data library if present. 
-                if sample.library:
-                    current_fid = sample.library.root_folder.id
-                else:
-                    current_fid = params.get( "sample_%i_folder_id" % sample_index, 'none'  )
-        else:
-            if folder_id:
-                current_fid = folder_id
-            else:
-                current_fid = 'none'
-        # first option
-        if lib_id == 'none':
-            folder_widget.add_option('Select one', 'none', selected=True)
-        else:
-            folder_widget.add_option('Select one', 'none')
-        if selected_lib:
-            # get all show-able folders for the selected library
-            showable_folders = trans.app.security_agent.get_showable_folders( user, user.all_roles(), 
-                                                                              selected_lib, 
-                                                                              [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ], 
-                                                                              selected_hidden_folder_ids )
-            for f in showable_folders:
-                if str(f.id) == str(current_fid):
-                    folder_widget.add_option(f.name, f.id, selected=True)
-                else:
-                    folder_widget.add_option(f.name, f.id)
-        return lib_widget, folder_widget
-    def __update_samples(self, trans, request, **kwd):
-        '''
-        This method retrieves all the user entered sample information and
-        returns an list of all the samples and their field values
-        '''
-        params = util.Params( kwd )
-        details = params.get( 'details', 'hide' )
-        edit_mode = params.get( 'edit_mode', 'False' )
-        # get all data libraries accessible to this user
-        libraries = request.user.accessible_libraries( trans, [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ] )
-        
-        current_samples = []
-        for i, s in enumerate(request.samples):
-            lib_widget, folder_widget = self.__library_widgets(trans, request.user, i, libraries, s, **kwd)
-            current_samples.append(dict(name=s.name,
-                                        barcode=s.bar_code,
-                                        library=s.library,
-                                        folder=s.folder,
-                                        field_values=s.values.content,
-                                        lib_widget=lib_widget,
-                                        folder_widget=folder_widget))
-        if edit_mode == 'False':
-            sample_index = len(request.samples) 
-        else:
-            sample_index = 0
-        while True:
-            lib_id = None
-            folder_id = None
-            if params.get( 'sample_%i_name' % sample_index, ''  ):
-                # data library
-                try:
-                    library = trans.sa_session.query( trans.app.model.Library ).get( int( params.get( 'sample_%i_library_id' % sample_index, None ) ) )
-                    lib_id = library.id
-                except:
-                    library = None
-                # folder
-                try:
-                    folder = trans.sa_session.query( trans.app.model.LibraryFolder ).get( int( params.get( 'sample_%i_folder_id' % sample_index, None ) ) )
-                    folder_id = folder.id
-                except:
-                    if library:
-                        folder = library.root_folder
-                    else:
-                        folder = None
-                sample_info = dict( name=util.restore_text( params.get( 'sample_%i_name' % sample_index, ''  ) ),
-                                    barcode=util.restore_text( params.get( 'sample_%i_barcode' % sample_index, ''  ) ),
-                                    library=library,
-                                    folder=folder)
-                sample_info['field_values'] = []
-                for field_index in range(len(request.type.sample_form.fields)):
-                    sample_info['field_values'].append(util.restore_text( params.get( 'sample_%i_field_%i' % (sample_index, field_index), ''  ) ))
-                if edit_mode == 'False':
-                    sample_info['lib_widget'], sample_info['folder_widget'] = self.__library_widgets(trans, 
-                                                                                                     request.user, 
-                                                                                                     sample_index, 
-                                                                                                     libraries, 
-                                                                                                     None, lib_id, folder_id, **kwd)
-                    current_samples.append(sample_info)
-                else:
-                    sample_info['lib_widget'], sample_info['folder_widget'] = self.__library_widgets(trans, 
-                                                                                                     request.user, 
-                                                                                                     sample_index, 
-                                                                                                     libraries, 
-                                                                                                     request.samples[sample_index], 
-                                                                                                     **kwd)
-                    current_samples[sample_index] =  sample_info
-                sample_index = sample_index + 1
-            else:
-                break
-        return current_samples, details, edit_mode, libraries
-    def __copy_sample(self, current_samples):
-        copy_list = SelectField('copy_sample')
-        copy_list.add_option('None', -1, selected=True)  
-        for i, s in enumerate(current_samples):
-            copy_list.add_option(s['name'], i)
-        return copy_list
-    def __import_samples(self, trans, request, current_samples, details, libraries, **kwd):
-        '''
-        This method reads the samples csv file and imports all the samples
-        The format of the csv file is:
-        SampleName,DataLibrary,DataLibraryFolder,Field1,Field2....
-        ''' 
-        try:
-            params = util.Params( kwd )
-            edit_mode = params.get( 'edit_mode', 'False' )
-            file_obj = params.get('file_data', '')
-            reader = csv.reader(file_obj.file)
-            for row in reader:
-                lib_id = None
-                folder_id = None
-                lib = trans.sa_session.query( trans.app.model.Library ) \
-                                      .filter( and_( trans.app.model.Library.table.c.name==row[1], \
-                                                     trans.app.model.Library.table.c.deleted==False ) )\
-                                      .first()
-                if lib:
-                    folder = trans.sa_session.query( trans.app.model.LibraryFolder ) \
-                                             .filter( and_( trans.app.model.LibraryFolder.table.c.name==row[2], \
-                                                            trans.app.model.LibraryFolder.table.c.deleted==False ) )\
-                                             .first()
-                    if folder:
-                        lib_id = lib.id
-                        folder_id = folder.id
-                lib_widget, folder_widget = self.__library_widgets(trans, request.user, len(current_samples), 
-                                                                   libraries, None, lib_id, folder_id, **kwd)
-                current_samples.append(dict(name=row[0], 
-                                            barcode='',
-                                            library=None,
-                                            folder=None,
-                                            lib_widget=lib_widget,
-                                            folder_widget=folder_widget,
-                                            field_values=row[3:]))  
-            return trans.fill_template( '/admin/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details,
-                                        edit_mode=edit_mode)
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                          action='list',
-                                                          operation='show_request',
-                                                          id=trans.security.encode_id(request.id),
-                                                          status='error',
-                                                          message='Error in importing samples file' ))
-
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def show_request(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', None ) ) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid request ID",
-                                                              **kwd) )
-        # get the user entered sample details
-        current_samples, details, edit_mode, libraries = self.__update_samples( trans, request, **kwd )
-        if params.get('import_samples_button', False) == 'Import samples':
-            return self.__import_samples(trans, request, current_samples, details, libraries, **kwd)
-        elif params.get('add_sample_button', False) == 'Add New':
-            # add an empty or filled sample
-            # if the user has selected a sample no. to copy then copy the contents 
-            # of the src sample to the new sample else an empty sample
-            src_sample_index = int(params.get( 'copy_sample', -1  ))
-            # get the number of new copies of the src sample
-            num_sample_to_copy = int(params.get( 'num_sample_to_copy', 1  ))
-            if src_sample_index == -1:
-                for ns in range(num_sample_to_copy):
-                    # empty sample
-                    lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
-                                                                       len(current_samples), 
-                                                                       libraries, None, **kwd)
-                    current_samples.append(dict(name='Sample_%i' % (len(current_samples)+1),
-                                                barcode='',
-                                                library=None,
-                                                folder=None,
-                                                field_values=['' for field in request.type.sample_form.fields],
-                                                lib_widget=lib_widget,
-                                                folder_widget=folder_widget))
-            else:
-                src_library_id = current_samples[src_sample_index]['lib_widget'].get_selected()[1]
-                src_folder_id = current_samples[src_sample_index]['folder_widget'].get_selected()[1]
-                for ns in range(num_sample_to_copy):
-                    lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
-                                                                       len(current_samples), 
-                                                                       libraries, sample=None, 
-                                                                       lib_id=src_library_id,
-                                                                       folder_id=src_folder_id,
-                                                                       **kwd)
-                    current_samples.append(dict(name=current_samples[src_sample_index]['name']+'_%i' % (len(current_samples)+1),
-                                                barcode='',
-                                                library_id='none',
-                                                folder_id='none',
-                                                field_values=[val for val in current_samples[src_sample_index]['field_values']],
-                                                lib_widget=lib_widget,
-                                                folder_widget=folder_widget))
-            return trans.fill_template( '/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details,
-                                        edit_mode=edit_mode)
-        elif params.get('save_samples_button', False) == 'Save':
-            # check for duplicate sample names
-            message = ''
-            for index in range(len(current_samples)-len(request.samples)):
-                sample_index = index + len(request.samples)
-                sample_name = current_samples[sample_index]['name']
-                if not sample_name.strip():
-                    message = 'Please enter the name of sample number %i' % sample_index
-                    break
-                count = 0
-                for i in range(len(current_samples)):
-                    if sample_name == current_samples[i]['name']:
-                        count = count + 1
-                if count > 1: 
-                    message = "This request has <b>%i</b> samples with the name <b>%s</b>.\nSamples belonging to a request must have unique names." % (count, sample_name)
-                    break
-            if message:
-                return trans.fill_template( '/requests/show_request.mako',
-                                            request=request,
-                                            request_details=self.request_details(trans, request.id),
-                                            current_samples = current_samples,
-                                            sample_copy=self.__copy_sample(current_samples), 
-                                            details=details, edit_mode=edit_mode,
-                                            status='error', message=message)
-            # save all the new/unsaved samples entered by the user
-            if edit_mode == 'False':
-                for index in range(len(current_samples)-len(request.samples)):
-                    sample_index = len(request.samples)
-                    form_values = trans.app.model.FormValues(request.type.sample_form, 
-                                                             current_samples[sample_index]['field_values'])
-                    trans.sa_session.add( form_values )
-                    trans.sa_session.flush()                    
-                    s = trans.app.model.Sample(current_samples[sample_index]['name'], '', 
-                                               request, form_values, 
-                                               current_samples[sample_index]['barcode'],
-                                               current_samples[sample_index]['library'],
-                                               current_samples[sample_index]['folder'], 
-                                               dataset_files=[])
-                    trans.sa_session.add( s )
-                    trans.sa_session.flush()
-            else:
-                status = 'done'
-                message = 'Changes made to the sample(s) are saved. '
-                for sample_index in range(len(current_samples)):
-                    sample = request.samples[sample_index]
-                    sample.name = current_samples[sample_index]['name'] 
-                    sample.library = current_samples[sample_index]['library']
-                    sample.folder = current_samples[sample_index]['folder']
-                    if request.submitted():
-                        bc_message = self.__validate_barcode(trans, sample, current_samples[sample_index]['barcode'])
-                        if bc_message:
-                            status = 'error'
-                            message += bc_message
-                        else:
-                            sample.bar_code = current_samples[sample_index]['barcode']
-                    trans.sa_session.add( sample )
-                    trans.sa_session.flush()
-                    form_values = trans.sa_session.query( trans.app.model.FormValues ).get( sample.values.id )
-                    form_values.content = current_samples[sample_index]['field_values']
-                    trans.sa_session.add( form_values )
-                    trans.sa_session.flush()
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                          action='list',
-                                                          operation='show_request',
-                                                          id=trans.security.encode_id(request.id),
-                                                          status=status,
-                                                          message=message ))
-        elif params.get('edit_samples_button', False) == 'Edit samples':
-            edit_mode = 'True'
-            return trans.fill_template( '/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details, libraries=libraries,
-                                        edit_mode=edit_mode)
-        elif params.get('cancel_changes_button', False) == 'Cancel':
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                          action='list',
-                                                          operation='show_request',
-                                                          id=trans.security.encode_id(request.id)) )
-        else:
-            return trans.fill_template( '/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details, libraries=libraries,
-                                        edit_mode=edit_mode, status=status, message=message)
-
-            
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def delete_sample(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', 0 ) ) )
-        current_samples, details, edit_mode = self.__update_samples( request, **kwd )
-        sample_index = int(params.get('sample_id', 0))
-        sample_name = current_samples[sample_index]['name']
-        s = request.has_sample(sample_name)
-        if s:
-            trans.sa_session.delete( s.values )
-            trans.sa_session.delete( s )
-            trans.sa_session.flush()
-        del current_samples[sample_index]  
-        return trans.fill_template( '/requests/show_request.mako',
-                                    request=request,
-                                    request_details=self.request_details(trans, request.id),
-                                    current_samples = current_samples,
-                                    sample_copy=self.__copy_sample(current_samples), 
-                                    details=details,
-                                    edit_mode=edit_mode)
-    def __select_request_type(self, trans, rtid):
-        requesttype_list = trans.user.accessible_request_types(trans)
-        rt_ids = ['none']
-        for rt in requesttype_list:
-            if not rt.deleted:
-                rt_ids.append(str(rt.id))
-        select_reqtype = SelectField('select_request_type', 
-                                     refresh_on_change=True, 
-                                     refresh_on_change_values=rt_ids[1:])
-        if rtid == 'none':
-            select_reqtype.add_option('Select one', 'none', selected=True)
-        else:
-            select_reqtype.add_option('Select one', 'none')
-        for rt in requesttype_list:
-            if not rt.deleted:
-                if rtid == rt.id:
-                    select_reqtype.add_option(rt.name, rt.id, selected=True)
-                else:
-                    select_reqtype.add_option(rt.name, rt.id)
-        return select_reqtype
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def new(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        if params.get('select_request_type', False) == 'True':
-            return trans.fill_template( '/requests/new_request.mako',
-                                        select_request_type=self.__select_request_type(trans, 'none'),                                 
-                                        widgets=[],                                   
-                                        message=message,
-                                        status=status)
-        elif params.get('create', False) == 'True':
-            if params.get('create_request_button', False) == 'Save' \
-               or params.get('create_request_samples_button', False) == 'Add samples':
-                request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-                if not util.restore_text(params.get('name', '')):
-                    message = 'Please enter the <b>Name</b> of the request'
-                    kwd['create'] = 'True'
-                    kwd['status'] = 'error'
-                    kwd['message'] = message
-                    kwd['create_request_button'] = None
-                    kwd['create_request_samples_button'] = None
-                    return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                      action='new',
-                                                                      **kwd) )
-                request = self.__save_request(trans, None, **kwd)
-                message = 'The new request named <b>%s</b> has been created' % request.name
-                if params.get('create_request_button', False) == 'Save':
-                    return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                      action='list',
-                                                                      message=message ,
-                                                                      status='done') )
-                elif params.get('create_request_samples_button', False) == 'Add samples':
-                    new_kwd = {}
-                    new_kwd['id'] = trans.security.encode_id(request.id)
-                    new_kwd['operation'] = 'show_request'
-                    new_kwd['add_sample'] = True
-                    return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                      action='list',
-                                                                      message=message ,
-                                                                      status='done',
-                                                                      **new_kwd) )
-            else:
-                return self.__show_request_form(trans, **kwd)
-        elif params.get('refresh', False) == 'true':
-            return self.__show_request_form(trans, **kwd)
-    def __show_request_form(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        try:
-            request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-        except:
-            return trans.fill_template( '/requests/new_request.mako',
-                                        select_request_type=self.__select_request_type(trans, 'none'),                                 
-                                        widgets=[],                                   
-                                        message=message,
-                                        status=status)
-        form_values = None
-        select_request_type = self.__select_request_type(trans, request_type.id)
-        # list of widgets to be rendered on the request form
-        widgets = []
-        widgets.append(dict(label='Name of the Experiment', 
-                            widget=TextField('name', 40, 
-                                             util.restore_text( params.get( 'name', ''  ) )), 
-                            helptext='(Required)'))
-        widgets.append(dict(label='Description', 
-                            widget=TextField('desc', 40,
-                                             util.restore_text( params.get( 'desc', ''  ) )), 
-                            helptext='(Optional)'))
-        widgets = widgets + request_type.request_form.get_widgets( trans.user, **kwd )
-        widgets.append(dict(label='Send email notification once the sequencing request is complete', 
-                            widget=CheckboxField('email_notify', False), 
-                            helptext=''))
-        return trans.fill_template( '/requests/new_request.mako',
-                                    select_request_type=select_request_type,
-                                    request_type=request_type,
-                                    widgets=widgets,
-                                    message=message,
-                                    status=status)
-    def __validate(self, trans, request):
-        '''
-        Validates the request entered by the user 
-        '''
-        empty_fields = []
-        # check rest of the fields of the form
-        for index, field in enumerate(request.type.request_form.fields):
-            if field['required'] == 'required' and request.values.content[index] in ['', None]:
-                empty_fields.append(field['label'])
-        if empty_fields:
-            message = 'Fill the following fields of the request <b>%s</b> before submitting<br/>' % request.name
-            for ef in empty_fields:
-                message = message + '<b>' +ef + '</b><br/>'
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              operation='edit',
-                                                              status = 'error',
-                                                              message=message,
-                                                              id=trans.security.encode_id(request.id) ))
-        # now check the required fields of all the samples of this request
-        for s in request.samples:
-            for index, field in enumerate(request.type.sample_form.fields):
-                if field['required'] == 'required' and s.values.content[index] in ['', None]:
-                    empty_fields.append((s.name, field['label']))
-        if empty_fields:
-            message = 'Fill the following fields of the request <b>%s</b> before submitting<br/>' % request.name
-            for sname, ef in empty_fields:
-                message = message + '<b>%s</b> field of sample <b>%s</b><br/>' % (ef, sname)
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              operation='show_request',
-                                                              status = 'error',
-                                                              message=message,
-                                                              id=trans.security.encode_id(request.id) ))
-    def __save_request(self, trans, request=None, **kwd):
-        '''
-        This method saves a new request if request_id is None. 
-        '''
-        params = util.Params( kwd )
-        request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-        name = util.restore_text(params.get('name', ''))
-        desc = util.restore_text(params.get('desc', ''))
-        notify = CheckboxField.is_checked( params.get('email_notify', '') )
-        # library
-        try:
-            library = trans.sa_session.query( trans.app.model.Library ).get( int( params.get( 'library_id', None ) ) )
-        except:
-            library = None
-        try:
-            folder = trans.sa_session.query( trans.app.model.LibraryFolder ).get( int( params.get( 'folder_id', None ) ) )
-        except:
-            if library:
-                folder = library.root_folder
-            else:
-                folder = None
-        # fields
-        values = []
-        for index, field in enumerate(request_type.request_form.fields):
-            if field['type'] == 'AddressField':
-                value = util.restore_text(params.get('field_%i' % index, ''))
-                if value == 'new':
-                    # save this new address in the list of this user's addresses
-                    user_address = trans.app.model.UserAddress( user=trans.user )
-                    user_address.desc = util.restore_text(params.get('field_%i_short_desc' % index, ''))
-                    user_address.name = util.restore_text(params.get('field_%i_name' % index, ''))
-                    user_address.institution = util.restore_text(params.get('field_%i_institution' % index, ''))
-                    user_address.address = util.restore_text(params.get('field_%i_address1' % index, ''))+' '+util.restore_text(params.get('field_%i_address2' % index, ''))
-                    user_address.city = util.restore_text(params.get('field_%i_city' % index, ''))
-                    user_address.state = util.restore_text(params.get('field_%i_state' % index, ''))
-                    user_address.postal_code = util.restore_text(params.get('field_%i_postal_code' % index, ''))
-                    user_address.country = util.restore_text(params.get('field_%i_country' % index, ''))
-                    user_address.phone = util.restore_text(params.get('field_%i_phone' % index, ''))
-                    trans.sa_session.add( user_address )
-                    trans.sa_session.flush()
-                    trans.sa_session.refresh( trans.user )
-                    values.append(int(user_address.id))
-                elif value == unicode('none'):
-                    values.append('')
-                else:
-                    values.append(int(value))
-            elif field['type'] == 'CheckboxField':
-                values.append(CheckboxField.is_checked( params.get('field_%i' % index, '') )) 
-            else:
-                values.append(util.restore_text(params.get('field_%i' % index, '')))
-        form_values = trans.app.model.FormValues(request_type.request_form, values)
-        trans.sa_session.add( form_values )
-        trans.sa_session.flush()
-        if not request:
-            request = trans.app.model.Request(name, desc, request_type, 
-                                              trans.user, form_values, notify)
-            trans.sa_session.add( request )
-            trans.sa_session.flush()
-            trans.sa_session.refresh( request )
-            # create an event with state 'New' for this new request
-            comments = "Request created."
-            event = trans.app.model.RequestEvent(request, request.states.NEW, comments)
-            trans.sa_session.add( event )
-            trans.sa_session.flush()
-        else:
-            request.name = name
-            request.desc = desc
-            request.type = request_type
-            request.user = trans.user
-            request.values = form_values
-            request.notify = notify
-            trans.sa_session.add( request )
-            trans.sa_session.flush()
-        return request
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def edit(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', None ) ) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid request ID",
-                                                              **kwd) )
-        if params.get('show', False) == 'True':
-            return self.__edit_request(trans, id=trans.security.encode_id(request.id), **kwd)
-        elif params.get('save_changes_request_button', False) == 'Save changes' \
-             or params.get('edit_samples_button', False) == 'Edit samples':
-                request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-                if not util.restore_text(params.get('name', '')):
-                    message = 'Please enter the <b>Name</b> of the request'
-                    kwd['status'] = 'error'
-                    kwd['message'] = message
-                    kwd['show'] = 'True'
-                    return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                      action='edit',
-                                                                      **kwd) )
-                request = self.__save_request(trans, request, **kwd)
-                message = 'The changes made to the request named %s has been saved' % request.name
-                if params.get('save_changes_request_button', False) == 'Save changes':
-                    return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                      action='list',
-                                                                      message=message ,
-                                                                      status='done') )
-                elif params.get('edit_samples_button', False) == 'Edit samples':
-                    new_kwd = {}
-                    new_kwd['request_id'] = request.id
-                    new_kwd['edit_samples_button'] = 'Edit samples'
-                    return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                      action='show_request',
-                                                                      message=message ,
-                                                                      status='done',
-                                                                      **new_kwd) )
-        elif params.get('refresh', False) == 'true':
-            return self.__edit_request(trans, id=trans.security.encode_id(request.id), **kwd)
-            
-    def __edit_request(self, trans, **kwd):
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            message = "Invalid request ID"
-            log.warn( message )
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message) )
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        select_request_type = self.__select_request_type(trans, request.type.id)
-        # list of widgets to be rendered on the request form
-        widgets = []
-        if util.restore_text( params.get( 'name', ''  ) ):
-            name = util.restore_text( params.get( 'name', ''  ) )
-        else:
-            name = request.name
-        widgets.append(dict(label='Name', 
-                            widget=TextField('name', 40, name), 
-                            helptext='(Required)'))
-        if util.restore_text( params.get( 'desc', ''  ) ):
-            desc = util.restore_text( params.get( 'desc', ''  ) )
-        else:
-            desc = request.desc
-        widgets.append(dict(label='Description', 
-                            widget=TextField('desc', 40, desc), 
-                            helptext='(Optional)'))
-        widgets = widgets + request.type.request_form.get_widgets( trans.user, request.values.content, **kwd )
-        widgets.append(dict(label='Send email notification once the sequencing request is complete', 
-                            widget=CheckboxField('email_notify', request.notify), 
-                            helptext=''))
-        return trans.fill_template( '/requests/edit_request.mako',
-                                    select_request_type=select_request_type,
-                                    request_type=request.type,
-                                    request=request,
-                                    widgets=widgets,
-                                    message=message,
-                                    status=status)
-        return self.__show_request_form(trans)
-    def __delete_request(self, trans, **kwd):
-        id_list = util.listify( kwd['id'] )
-        delete_failed = []
-        for id in id_list:
-            try:
-                request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(id) )
-            except:
-                message = "Invalid request ID"
-                log.warn( message )
-                return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                  action='list',
-                                                                  status='error',
-                                                                  message=message,
-                                                                  **kwd) )
-            # a request cannot be deleted once its submitted
-            if not request.new():
-                delete_failed.append(request.name)
-            else:
-                request.deleted = True
-                trans.sa_session.add( request )
-                # delete all the samples belonging to this request
-                for s in request.samples:
-                    s.deleted = True
-                    trans.sa_session.add( s )
-                trans.sa_session.flush()
-        if not len(delete_failed):
-            message = '%i request(s) has been deleted.' % len(id_list)
-            status = 'done'
-        else:
-            message = '%i request(s) has been deleted. %i request %s could not be deleted as they have been submitted.' % (len(id_list)-len(delete_failed), 
-                                                                                                               len(delete_failed), str(delete_failed))
-            status = 'warning'
-        return trans.response.send_redirect( web.url_for( controller='requests',
-                                                          action='list',
-                                                          status=status,
-                                                          message=message) )
-    def __undelete_request(self, trans, **kwd):
-        id_list = util.listify( kwd['id'] )
-        for id in id_list:
-            try:
-                request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(id) )
-            except:
-                message = "Invalid request ID"
-                log.warn( message )
-                return trans.response.send_redirect( web.url_for( controller='requests',
-                                                                  action='list',
-                                                                  status='error',
-                                                                  message=message,
-                                                                  **kwd) )
-            request.deleted = False
-            trans.sa_session.add( request )
-            # undelete all the samples belonging to this request
-            for s in request.samples:
-                s.deleted = False
-                trans.sa_session.add( s )
-            trans.sa_session.flush()
-        return trans.response.send_redirect( web.url_for( controller='requests',
-                                                          action='list',
-                                                          status='done',
-                                                          message='%i request(s) has been undeleted.' % len(id_list) ) )
-    def __submit_request(self, trans, **kwd):
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            message = "Invalid request ID"
-            log.warn( message )
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message,
-                                                              **kwd) )
-        # check if all the required request and its sample fields have been filled 
-        self.__validate(trans, request)
-        # change the request state to 'Submitted'
-        comments = "Sequencing request is in progress."
-        event = trans.app.model.RequestEvent(request, request.states.SUBMITTED, comments)
-        trans.sa_session.add( event )
-        trans.sa_session.flush()
-        # get the new state
-        new_state = request.type.states[0]
-        for s in request.samples:
-            event = trans.app.model.SampleEvent(s, new_state, 'Samples submitted to the system')
-            trans.sa_session.add( event )
-            trans.sa_session.flush()
-        return trans.response.send_redirect( web.url_for( controller='requests',
-                                                          action='list',
-                                                          id=trans.security.encode_id(request.id),
-                                                          status='done',
-                                                          message='The request <b>%s</b> has been submitted.' % request.name
-                                                          ) )
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def show_events(self, trans, **kwd):
-        params = util.Params( kwd )
-        try:
-            sample_id = int(params.get('sample_id', False))
-            sample = trans.sa_session.query( trans.app.model.Sample ).get( sample_id )
-        except:
-            message = "Invalid sample ID"
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message,
-                                                              **kwd) )
-        events_list = []
-        all_events = sample.events
-        for event in all_events:
-            events_list.append((event.state.name, event.state.desc, time_ago(event.update_time), event.comment))
-        return trans.fill_template( '/sample/sample_events.mako', 
-                                    events_list=events_list,
-                                    sample_name=sample.name,
-                                    request=sample.request)
-    #
-    # Data transfer from sequencer
-    #
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def show_datatx_page( self, trans, **kwd ):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' ) 
-        try:
-            sample = trans.sa_session.query( trans.app.model.Sample ).get( trans.security.decode_id( kwd['sample_id'] ) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid sample ID",
-                                                              **kwd) )
-        return trans.fill_template( '/requests/show_data.mako', 
-                                    sample=sample, dataset_files=sample.dataset_files )
+    
--- a/lib/galaxy/web/controllers/forms.py
+++ b/lib/galaxy/web/controllers/forms.py
@@ -474,8 +474,7 @@ class Forms( BaseController ):
             return trans.response.send_redirect( web.url_for( controller='forms',
                                                               action='new',
                                                               status='error',
-                                                              message='Error in importing <b>%s</b> file' % csv_file,
-                                                              **kwd))
+                                                              message='Error in importing <b>%s</b> file' % csv_file.file))
         self.__imported_from_file = True
         return fields, list(layouts)
     def __validate_form(self, **kwd):
--- a/templates/admin/requests/edit_request.mako
+++ /dev/null
@@ -1,88 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$( function() {
-    $( "select[refresh_on_change='true']").change( function() {
-        var refresh = false;
-        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
-        if ( refresh_on_change_values ) {
-            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
-            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
-            for( i= 0; i < refresh_on_change_values.length; i++ ) {
-                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
-                    refresh = true;
-                    break;
-                }
-            }
-        }
-        else {
-            refresh = true;
-        }
-        if ( refresh ){
-            $( "#edit_request" ).submit();
-        }
-    });
-});
-</script>
-
-<br/>
-<br/>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='show_request', id=trans.security.encode_id(request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests_admin', action='list')}">
-        <span>Browse requests</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    <div class="toolFormTitle">Edit request "${request.name}" from ${request.user.email}</div>
-    %if len(select_request_type.options) == 1:
-        There are no request types created for a new request.
-    %else:
-        <div class="toolFormBody">
-            <form name="edit_request" id="edit_request" action="${h.url_for( controller='requests_admin', action='edit', request_id=request.id)}" method="post" >
-                <div class="form-row">
-                    <label>
-                        Select Request Type:
-                    </label>
-                    ${select_request_type.get_html()}
-                </div>
-
-               %if select_request_type.get_selected() != ('Select one', 'none'):
-                   %for i, field in enumerate(widgets):
-                        <div class="form-row">
-                            <label>${field['label']}</label>
-                            ${field['widget'].get_html()}
-                            %if field['label'] == 'Library' and new_library:
-                                ${new_library.get_html()}
-                            %endif
-                            <div class="toolParamHelp" style="clear: both;">
-                                ${field['helptext']}
-                            </div>
-                            <div style="clear: both"></div>
-                        </div>
-                    %endfor                    
-                    <div class="form-row">
-                        <div style="float: left; width: 250px; margin-right: 10px;">
-                            <input type="hidden" name="refresh" value="true" size="40"/>
-                        </div>
-                      <div style="clear: both"></div>
-                    </div>
-                    <div class="form-row">
-                        <input type="submit" name="save_changes_request_button" value="Save changes"/> 
-                        ##<input type="submit" name="edit_samples_button" value="Edit samples"/>
-                    </div>
-               %endif
-        </form>
-    </div>
-</div>
-%endif
--- a/templates/requests/sample_datasets.mako
+++ /dev/null
@@ -1,7 +0,0 @@
-<%def name="render_sample_datasets( sample )">
-    <a href="${h.url_for(controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id))}">${sample.transferred_dataset_files()}/${len(sample.dataset_files)}</a>
-</%def>
-
-
-
-${render_sample_datasets( sample )}
--- /dev/null
+++ b/templates/requests/common/events.mako
@@ -0,0 +1,39 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+
+<h2>History of Sequencing Request "${request.name}"</h2>
+<ul class="manage-table-actions">
+    <li>
+        <a class="action-button" href="${h.url_for( controller=cntrller, action='list', operation='show_request', id=trans.security.encode_id(request.id) )}">
+        <span>Browse this request</span></a>
+    </li>
+    <li>
+        <a class="action-button"  href="${h.url_for( controller=cntrller, action='list')}">
+        <span>Browse all requests</span></a>
+    </li>
+</ul>
+
+%if message:
+    ${render_msg( message, status )}
+%endif
+
+<div class="toolForm">
+    <table class="grid">
+        <thead>
+            <tr>
+                <th>State</th>
+                <th>Last Update</th>
+                <th>Comments</th>
+            </tr>
+        </thead>
+        <tbody>
+            %for state, updated, comments in events_list:    
+                <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
+                    <td><b><a>${state}</a></b></td>
+                    <td><a>${updated}</a></td>
+                    <td><a>${comments}</a></td>
+                </tr>             
+            %endfor
+        </tbody>
+    </table>
+</div>
--- /dev/null
+++ b/templates/requests/common/show_request.mako
@@ -0,0 +1,547 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+<%namespace file="/requests/common/sample_state.mako" import="render_sample_state" />
+<%namespace file="/requests/common/sample_datasets.mako" import="render_sample_datasets" />
+
+
+
+<script type="text/javascript">
+$( function() {
+    $( "select[refresh_on_change='true']").change( function() {
+        var refresh = false;
+        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
+        if ( refresh_on_change_values ) {
+            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
+            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
+            for( i= 0; i < refresh_on_change_values.length; i++ ) {
+                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
+                    refresh = true;
+                    break;
+                }
+            }
+        }
+        else {
+            refresh = true;
+        }
+        if ( refresh ){
+            $( "#show_request" ).submit();
+        }
+    });
+});
+</script>
+
+
+<script type="text/javascript">
+$(document).ready(function(){
+    //hide the all of the element with class msg_body
+    $(".msg_body").hide();
+    //toggle the componenet with class msg_body
+    $(".msg_head").click(function(){
+        $(this).next(".msg_body").slideToggle(450);
+    });
+});
+</script>
+
+<script type="text/javascript">
+    // Looks for changes in sample states using an async request. Keeps
+    // calling itself (via setTimeout) until all samples are in a terminal
+    // state.
+    var updater = function ( sample_states ) {
+        // Check if there are any items left to track
+        var empty = true;
+        for ( i in sample_states ) {
+            empty = false;
+            break;
+        }
+        if ( ! empty ) {
+            setTimeout( function() { updater_callback( sample_states ) }, 1000 );
+        }
+    };
+    var updater_callback = function ( sample_states ) {
+        // Build request data
+        var ids = []
+        var states = []
+        $.each( sample_states, function ( id, state ) {
+            ids.push( id );
+            states.push( state );
+        });
+        // Make ajax call
+        $.ajax( {
+            type: "POST",
+            url: "${h.url_for( controller='requests_common', action='sample_state_updates' )}",
+            dataType: "json",
+            data: { ids: ids.join( "," ), states: states.join( "," ) },
+            success : function ( data ) {
+                $.each( data, function( id, val, cntrller ) {
+                    // Replace HTML
+                    var cell1 = $("#sampleState-" + id);
+                    cell1.html( val.html_state );
+                    var cell2 = $("#sampleDatasets-" + id);
+                    cell2.html( val.html_datasets );
+                    sample_states[ parseInt(id) ] = val.state;
+                });
+                updater( sample_states ); 
+            },
+            error: function() {
+                // Just retry, like the old method, should try to be smarter
+                updater( sample_states );
+            }
+        });
+    };
+</script>
+
+<style type="text/css">
+.msg_head {
+    padding: 0px 0px;
+    cursor: pointer;
+}
+</style>
+
+<script type="text/javascript">
+    function stopRKey(evt) {
+      var evt = (evt) ? evt : ((event) ? event : null);
+      var node = (evt.target) ? evt.target : ((evt.srcElement) ? evt.srcElement : null);
+      if ((evt.keyCode == 13) && (node.type=="text"))  {return false;}
+    }
+    document.onkeypress = stopRKey
+</script> 
+
+%if request.submitted():
+    <% samples_not_ready = request.sequence_run_ready() %>
+    %if samples_not_ready:
+        ${render_msg( "Select a target library and folder for all the samples before starting the sequence run", "warning" )}
+    %endif
+%endif
+
+%if request.rejected():
+    ${render_msg( "Reason for rejection: "+request.last_comment(), "warning" )}
+%endif
+
+<div class="grid-header">
+    <h2>Sequencing Request "${request.name}"</h2>
+</div>
+
+<ul class="manage-table-actions">
+
+    %if request.unsubmitted() and request.samples:
+        <li>
+            <a class="action-button" confirm="More samples cannot be added to this request once it is submitted. Click OK to submit." href="${h.url_for( controller=cntrller, action='list', operation='Submit', id=trans.security.encode_id(request.id) )}">
+            <span>Submit request</span></a>
+        </li>
+    %endif
+    %if cntrller == 'requests_admin' and trans.user_is_admin():
+        %if request.submitted():
+            <li>
+                <a class="action-button" href="${h.url_for( controller=cntrller, action='list', operation='reject', id=trans.security.encode_id(request.id))}">
+                <span>Reject request</span></a>
+            </li>
+        %endif
+    %endif
+    <li>
+        <a class="action-button" href="${h.url_for( controller=cntrller, action='list', operation='events', id=trans.security.encode_id(request.id) )}">
+        <span>History</span></a>
+    </li>
+    <li>
+        <a class="action-button"  href="${h.url_for( controller=cntrller, action='list')}">
+        <span>Browse requests</span></a>
+    </li>
+
+</ul>
+
+
+%if message:
+    ${render_msg( message, status )}
+%endif
+
+
+
+
+<div class="toolForm">
+    <div class="form-row">
+        <div class="msg_list">
+            <h4 class="msg_head"><u>Request Information</u></h4>
+            <div class="msg_body">
+                %for index, rd in enumerate(request_details):
+                    <div class="form-row">
+                        <label>${rd['label']}</label>
+                        %if not rd['value']:
+                            <i>None</i>
+                        %else:                      
+                            %if rd['label'] == 'State':
+                                <a href="${h.url_for( controller=cntrller, action='list', operation='events', id=trans.security.encode_id(request.id) )}">${rd['value']}</a>
+                            %else:
+                                ${rd['value']}     
+                            %endif
+                        %endif
+                    </div>
+                    <div style="clear: both"></div>
+                %endfor
+                <div class="form-row">
+                <ul class="manage-table-actions">
+                    <li>
+                        <a class="action-button"  href="${h.url_for( controller='requests_admin', action='list', operation='Edit', id=trans.security.encode_id(request.id))}">
+                        <span>Edit request details</span></a>
+                    </li>
+                </ul>
+                </div>
+            </div>
+        </div>
+    </div>
+</div>
+
+<br/>
+
+<div class="toolForm">
+    <form id="show_request" name="show_request" action="${h.url_for( controller='requests_common', cntrller=cntrller, action='request_page', edit_mode=edit_mode )}"  method="post" >
+        <div class="form-row">
+            %if current_samples:
+                ## first render the basic info grid 
+                ${render_basic_info_grid()}
+                ## then render the other grid(s)
+                <% trans.sa_session.refresh( request.type.sample_form ) %>
+                %for grid_index, grid_name in enumerate(request.type.sample_form.layout):
+                    ${render_grid( grid_index, grid_name, request.type.sample_form.fields_of_grid( grid_index ) )}
+                    <br/>
+                %endfor
+            %else:
+                <label>There are no samples.</label>
+            %endif
+        </div>      
+        %if request.samples and request.submitted():
+            <script type="text/javascript">
+                // Updater
+                updater({${ ",".join( [ '"%s" : "%s"' % ( s.id, s.current_state().name ) for s in request.samples ] ) }});
+            </script>
+        %endif
+        
+        %if edit_mode == 'False':
+            <table class="grid">
+                <tbody>
+                    <tr>
+                        <div class="form-row">
+
+                            %if request.unsubmitted():
+                                <td>
+                                    %if current_samples:
+                                        <label>Copy </label>
+                                        <input type="integer" name="num_sample_to_copy" value="1" size="3"/>
+                                        <label>sample(s) from sample</label>
+                                        ${sample_copy.get_html()}
+                                    %endif
+                                    <input type="submit" name="add_sample_button" value="Add New"/>
+                                </td>
+                            %endif
+                            <td>
+                                %if len(current_samples) and len(current_samples) <= len(request.samples):                     
+                                    <input type="submit" name="edit_samples_button" value="Edit samples"/>
+                                %endif
+                            </td>
+                        </div>
+                    </tr> 
+                </tbody>
+            </table>
+        %endif
+        %if request.samples or current_samples: 
+            <div class="form-row">
+                <div style="float: left; width: 250px; margin-right: 10px;">
+                    <input type="hidden" name="refresh" value="true" size="40"/>
+                </div>
+              <div style="clear: both"></div>
+            </div>            
+            %if edit_mode == 'True':   
+                <div class="form-row">
+                    <input type="submit" name="save_samples_button" value="Save"/>
+                    <input type="submit" name="cancel_changes_button" value="Cancel"/>
+                </div>
+            %elif request.unsubmitted():
+                <div class="form-row">
+                    <input type="submit" name="save_samples_button" value="Save"/>
+                </div>
+            %endif
+            
+        %endif
+        <input type="hidden" name="id" value="${trans.security.encode_id(request.id)}" />
+    </form>
+</div>
+
+<br/>
+
+%if request.unsubmitted():
+<div class="toolForm">
+    <form id="import" name="import" action="${h.url_for( controller='requests_common', action='request_page', edit_mode=edit_mode, request_id=trans.security.encode_id(request.id) )}" enctype="multipart/form-data" method="post" >
+        <div class="form-row">
+            <div class="msg_list">
+                <h4 class="msg_head"><u>Import samples from csv file</u></h4>
+                <div class="msg_body">
+                    <input type="file" name="file_data" />
+                    <input type="submit" name="import_samples_button" value="Import samples"/>
+                    <br/>
+                    <div class="toolParamHelp" style="clear: both;">
+                        The csv file must be in the following format:<br/>
+                        SampleName,DataLibrary,DataLibraryFolder,FieldValue1,FieldValue2...
+                    </div>
+                </div>
+            </div>
+        </div>
+##        <input type="hidden" name="request_id" value="${request.id}" />
+    </form>
+</div>
+%endif
+
+<%def name="render_grid( grid_index, grid_name, fields_dict )">
+    <br/>
+    <div class="msg_list">
+    %if grid_name:
+        <h4 class="msg_head"><u>${grid_name}</u></h4>
+    %else:
+        <h4>Grid ${grid_index}</h4>
+    %endif
+    %if edit_mode == 'False' or len(current_samples) <= len(request.samples):
+        <div class="msg_body">
+    %else:
+        <div class="msg_body2">
+    %endif
+    <table class="grid">
+        <thead>
+            <tr>
+                <th>Name</th>
+                %for index, field in fields_dict.items():
+                    <th>
+                        ${field['label']}
+                        <div class="toolParamHelp" style="clear: both;">
+                            <i>${field['helptext']}</i>
+                        </div>
+                    </th>
+                %endfor
+                <th></th>
+            </tr>
+        <thead>
+        <tbody>
+            <%
+            trans.sa_session.refresh( request )
+            %>
+            %for sample_index, sample in enumerate(current_samples):
+                %if edit_mode == 'True':
+                    <tr>
+                        ${render_sample_form( sample_index, sample['name'], sample['field_values'], fields_dict)}
+                    </tr>      
+                %else:
+                    <tr>
+                        %if sample_index in range(len(request.samples)):
+                            ${render_sample( sample_index, sample['name'], sample['field_values'], fields_dict )}
+                        %else:                                                            
+                            ${render_sample_form( sample_index, sample['name'], sample['field_values'], fields_dict)}
+                        %endif
+                    </tr>  
+                %endif
+            %endfor
+        </tbody>
+    </table>
+    </div>
+    </div>
+</%def>
+
+## This function displays the "Basic Information" grid
+<%def name="render_basic_info_grid()">
+    <h4>Sample Information</h4>
+    <table class="grid">
+        <thead>
+            <tr>
+                <th>Name</th>
+                <th>Barcode</th>
+                <th>State</th>
+                <th>Data Library</th>
+                <th>Folder</th>
+                %if request.submitted() or request.complete(): 
+                    <th>Dataset(s) Transferred</th>
+                %endif
+                <th></th>
+            </tr>
+        <thead>
+        <tbody>
+            <%
+            trans.sa_session.refresh( request )
+            %>
+            %for sample_index, info in enumerate(current_samples):
+                <% 
+                    if sample_index in range(len(request.samples)):
+                        sample = request.samples[sample_index]
+                    else:
+                        sample = None 
+                %>
+                %if edit_mode == 'True':
+                    <tr>
+                        ${show_basic_info_form( sample_index, sample, info )}
+                    </tr>      
+                %else:
+                    <tr>
+                        %if sample_index in range(len(request.samples)):
+                            <td>${info['name']}</td>
+                            <td>${info['barcode']}</td>
+                            %if sample.request.unsubmitted():
+                                <td>Unsubmitted</td>
+                            %else:
+                                <td id="sampleState-${sample.id}">${render_sample_state( cntrller, sample )}</td>
+                            %endif
+                            %if info['library']:
+                                <td><a href="${h.url_for( controller='library_common', action='browse_library', cntrller='library', id=trans.security.encode_id( info['library'].id ) )}">${info['library'].name}</a></td>
+                            %else:
+                                <td></td>
+                            %endif
+                            %if info['folder']:
+                                <td>${info['folder'].name}</td>
+                            %else:
+                                <td></td>
+                            %endif
+                            %if request.submitted() or request.complete(): 
+                                <td id="sampleDatasets-${sample.id}">
+                                    ${render_sample_datasets( cntrller, sample )}
+                                </td>
+                            %endif
+                            
+                            
+                        %else:                                                            
+                            ${show_basic_info_form( sample_index, sample, info )}
+                        %endif
+                        %if request.unsubmitted() or request.rejected(): 
+                            <td>
+                                %if sample:
+                                    %if sample.request.unsubmitted():
+                                        <a class="action-button" href="${h.url_for( controller='requests_common', cntrller=cntrller, action='delete_sample', request_id=request.id, sample_id=sample_index )}">
+                                        <img src="${h.url_for('/static/images/delete_icon.png')}" />
+                                        <span></span></a>
+                                    %endif
+                                %endif
+                            </td>
+                        %endif
+                    </tr>  
+                %endif
+            %endfor
+        </tbody>
+    </table>
+</%def>
+
+<%def name="show_basic_info_form( sample_index, sample, info )">
+    <td>
+        <input type="text" name=sample_${sample_index}_name value="${info['name']}" size="10"/>
+        <div class="toolParamHelp" style="clear: both;">
+            <i>${' (required)' }</i>
+        </div>
+    </td>
+    %if cntrller == 'requests':
+        %if sample:
+            %if sample.request.unsubmitted():
+                <td></td>
+            %else:
+                <td><input type="text" name=sample_${sample_index}_barcode value="${info['barcode']}" size="10"/></td>
+            %endif
+        %else:
+            <td></td>
+        %endif
+    %elif cntrller == 'requests_admin':
+        %if sample:
+            %if sample.request.unsubmitted():
+                <td></td>
+            %else:
+                <td><input type="text" name=sample_${sample_index}_barcode value="${info['barcode']}" size="10"/></td>
+            %endif
+        %else:
+            <td></td>
+        %endif
+    %endif 
+    %if sample:
+        %if sample.request.unsubmitted():
+            <td>Unsubmitted</td>
+        %else:
+            <td><a href="${h.url_for( controller='requests_admin', action='sample_events', sample_id=sample.id)}">${sample.current_state().name}</a></td>
+        %endif    
+    %else:
+        <td></td>
+    %endif
+    <td>${info['lib_widget'].get_html()}</td>
+    <td>${info['folder_widget'].get_html()}</td>
+    %if request.submitted() or request.complete(): 
+        %if sample:
+            <td><a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">${len(sample.dataset_files)}</a></td> 
+        %else:
+            <td><a href="${h.url_for( controller='requests_admin', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">Add</a></td>
+        %endif 
+    %endif 
+</%def>
+
+<%def name="render_sample( index, sample_name, sample_values, fields_dict )">
+    <td>
+        ${sample_name}
+    </td>
+    %for field_index, field in fields_dict.items():
+        <td>
+            %if sample_values[field_index]:
+                %if field['type'] == 'WorkflowField':
+                    %if str(sample_values[field_index]) != 'none':
+                        <% workflow = trans.sa_session.query( trans.app.model.StoredWorkflow ).get( int(sample_values[field_index]) ) %>
+                        <a href="${h.url_for( controller='workflow', action='run', id=trans.security.encode_id(workflow.id) )}">${workflow.name}</a>
+                    %endif
+                %else:
+                    ${sample_values[field_index]}
+                %endif
+            %else:
+                <i>None</i>
+            %endif
+        </td>
+    %endfor   
+</%def>
+
+<%def name="render_sample_form( index, sample_name, sample_values, fields_dict )">
+    <td>
+        ${sample_name}
+    </td>
+    %for field_index, field in fields_dict.items():
+        <td>
+            %if field['type'] == 'TextField':
+                <input type="text" name="sample_${index}_field_${field_index}" value="${sample_values[field_index]}" size="7"/>
+            %elif field['type'] == 'SelectField':
+                <select name="sample_${index}_field_${field_index}" last_selected_value="2">
+                    %for option_index, option in enumerate(field['selectlist']):
+                        %if option == sample_values[field_index]:
+                            <option value="${option}" selected>${option}</option>
+                        %else:
+                            <option value="${option}">${option}</option>
+                        %endif
+                    %endfor
+                </select>
+            %elif field['type'] == 'WorkflowField':
+                <select name="sample_${index}_field_${field_index}">
+                    %if str(sample_values[field_index]) == 'none':
+                        <option value="none" selected>Select one</option>
+                    %else:
+                        <option value="none">Select one</option>
+                    %endif
+                    %for option_index, option in enumerate(request.user.stored_workflows):
+                        %if not option.deleted:
+                            %if str(option.id) == str(sample_values[field_index]):
+                                <option value="${option.id}" selected>${option.name}</option>
+                            %else:
+                                <option value="${option.id}">${option.name}</option>
+                            %endif
+                        %endif
+                    %endfor
+                </select>
+            %elif field['type'] == 'CheckboxField':
+                <input type="checkbox" name="sample_${index}_field_${field_index}" value="Yes"/>
+            %endif
+            <div class="toolParamHelp" style="clear: both;">
+                <i>${'('+field['required']+')' }</i>
+            </div>
+        </td>
+    %endfor   
+</%def>
+
+
+
+
+
+
+
+
+
+
--- a/templates/admin/requests/new_request.mako
+++ /dev/null
@@ -1,94 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$( function() {
-    $( "select[refresh_on_change='true']").change( function() {
-        var refresh = false;
-        var refresh_on_change_values = $( this )[0].attributes.getNamedItem( 'refresh_on_change_values' )
-        if ( refresh_on_change_values ) {
-            refresh_on_change_values = refresh_on_change_values.value.split( ',' );
-            var last_selected_value = $( this )[0].attributes.getNamedItem( 'last_selected_value' );
-            for( i= 0; i < refresh_on_change_values.length; i++ ) {
-                if ( $( this )[0].value == refresh_on_change_values[i] || ( last_selected_value && last_selected_value.value == refresh_on_change_values[i] ) ){
-                    refresh = true;
-                    break;
-                }
-            }
-        }
-        else {
-            refresh = true;
-        }
-        if ( refresh ){
-            $( "#new_request" ).submit();
-        }
-    });
-});
-</script>
-
-<%def name="javascripts()">
-   ${parent.javascripts()}
-   ${h.js("jquery.autocomplete", "autocomplete_tagging" )}
-</%def>
-
-<%def name="stylesheets()">
-    ${parent.stylesheets()}
-    ${h.css( "autocomplete_tagging" )}
-</%def>
-
-<br/>
-<br/>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests_admin', action='list')}">
-        <span>Browse requests</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    <div class="toolFormTitle">Add a new request</div>
-    %if len(select_request_type.options) == 1:
-        There are no request types created for a new request.
-    %else:
-        <div class="toolFormBody">
-            <form name="new_request" id="new_request" action="${h.url_for( controller='requests_admin', action='new', create=True )}" method="post" >
-                <div class="form-row">
-                    <label>
-                        Select Request Type
-                    </label>
-                    ${select_request_type.get_html()}
-                </div>
-
-               %if select_request_type.get_selected() != ('Select one', 'none'):
-                   %for i, field in enumerate(widgets):
-                        <div class="form-row">
-                            <label>${field['label']}</label>
-                            ${field['widget'].get_html()}
-                            %if field['label'] == 'Library' and new_library:
-                                ${new_library.get_html()}
-                            %endif
-                            <div class="toolParamHelp" style="clear: both;">
-                                ${field['helptext']}
-                            </div>
-                            <div style="clear: both"></div>
-                        </div>
-                    %endfor                    
-                    <div class="form-row">
-                        <div style="float: left; width: 250px; margin-right: 10px;">
-                            <input type="hidden" name="refresh" value="true" size="40"/>
-                        </div>
-                      <div style="clear: both"></div>
-                    </div>
-                    <div class="form-row">
-                        <input type="submit" name="create_request_button" value="Save"/> 
-                        <input type="submit" name="create_request_samples_button" value="Add samples"/>
-                    </div>
-               %endif
-        </form>
-    </div>
-</div>
-%endif
--- a/templates/sample/sample_events.mako
+++ /dev/null
@@ -1,45 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-<%def name="title()">Events for Sample ${sample_name}</%def>
-
-
-<h2>Events for Sample "${sample_name}"</h2>
-
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests', action='list', operation='show_request', id=trans.security.encode_id(request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests', action='list')}">
-        <span>Browse requests</span></a>
-    </li>
-</ul>
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<div class="toolForm">
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>State</th>
-                <th>Description</th>
-                <th>Updated</th>
-                <th>Comments</th>
-            </tr>
-        </thead>
-        <tbody>
-            %for state, desc, updated, comments in events_list:    
-                <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
-                    <td><b><a>${state}</a></b></td>
-                    <td><a>${desc}</a></td>
-                    <td><a>${updated}</a></td>
-                    <td><a>${comments}</a></td>
-                </tr>             
-            %endfor
-        </tbody>
-    </table>
-</div>
--- /dev/null
+++ b/templates/requests/common/sample_datasets.mako
@@ -0,0 +1,7 @@
+<%def name="render_sample_datasets( cntrller, sample )">
+    <a href="${h.url_for(controller='requests_common', cntrller=cntrller, action='show_datatx_page', sample_id=trans.security.encode_id(sample.id))}">${sample.transferred_dataset_files()}/${len(sample.dataset_files)}</a>
+</%def>
+
+
+
+${render_sample_datasets( cntrller, sample )}
--- a/test/base/twilltestcase.py
+++ b/test/base/twilltestcase.py
@@ -1485,14 +1485,13 @@ class TwillTestCase( unittest.TestCase )
             url ="%s&%s=%s" % ( url, key, role_ids_str )
         self.home()
         self.visit_url( "%s/%s" % ( self.url, url ) )
-        print url
         check_str = "Permissions updated for request type '%s'" % request_type_name
         self.check_page_for_string( check_str )
         self.home()
     def create_request( self, request_type_id, name, desc, fields ):
         self.home()
-        self.visit_url( "%s/requests/new?create=True&select_request_type=%i" % ( self.url, 
-                                                                                 request_type_id ) )
+        self.visit_url( "%s/requests_common/new?select_request_type=%i&refresh=true&cntrller=requests" % ( self.url, 
+                                                                                                           request_type_id ) )
         self.check_page_for_string( 'Add a new request' )
         tc.fv( "1", "name", name )
         tc.fv( "1", "desc", desc )
@@ -1514,21 +1513,20 @@ class TwillTestCase( unittest.TestCase )
         self.check_page_for_string( new_desc )
     def add_samples( self, request_id, request_name, samples ):
         self.home()
-        url = "%s/requests/list?sort=-create_time&operation=show_request&id=%s" % ( self.url, self.security.encode_id( request_id ) )
+        url = "%s/requests/list?operation=show&id=%s" % ( self.url, self.security.encode_id( request_id ) )
         self.visit_url( url )
         self.check_page_for_string( 'Sequencing Request "%s"' % request_name )
         self.check_page_for_string( 'There are no samples.' )
         # this redundant stmt below is add so that the second form in 
         # the page gets selected
-        tc.fv( "3", "request_id", request_id )
+        url = ["%s/requests_common/request_page?cntrller=requests&edit_mode=False&id=%s" % ( self.url, self.security.encode_id( request_id ) )]
         for sample_index, sample in enumerate(samples):
-            tc.submit( "add_sample_button" )
-            self.check_page_for_string( 'Sequencing Request "%s"' % request_name )
             sample_name, fields = sample
-            tc.fv( "3", "sample_%i_name" % sample_index, sample_name )
+            url.append("sample_%i_name=%s" % (sample_index, sample_name.replace(' ', '+')))
             for field_index, field_value in enumerate(fields):
-                tc.fv( "3", "sample_%i_field_%i" % ( sample_index, field_index ), field_value )
-        tc.submit( "save_samples_button" )
+                url.append("sample_%i_field_%i=%s" % ( sample_index, field_index , field_value.replace(' ', '+') ))
+        url.append("save_samples_button=Save")
+        self.visit_url('&'.join(url))
         for sample_name, fields in samples:
             self.check_page_for_string( sample_name )
             self.check_page_for_string( 'Unsubmitted' )
@@ -1549,19 +1547,24 @@ class TwillTestCase( unittest.TestCase )
         tc.fv( "1", "comment", comment )
         tc.submit( "reject_button" )
         self.check_page_for_string( 'Request <b>%s</b> has been rejected.' % request_name )
-        self.visit_url( "%s/requests/list?sort=-create_time&operation=show_request&id=%s" % ( self.url, self.security.encode_id( request_id ) ))
+        self.visit_url( "%s/requests/list?&operation=show&id=%s" % ( self.url, self.security.encode_id( request_id ) ))
         self.check_page_for_string( comment )
-    def add_bar_codes( self, request_id, request_name, bar_codes ):
+    def add_bar_codes( self, request_id, request_name, bar_codes, samples ):
         self.home()
-        self.visit_url( "%s/requests_admin/bar_codes?request_id=%i" % (self.url, request_id) )
-        self.check_page_for_string( 'Bar codes for Samples of Request "%s"' % request_name )
+        url = "%s/requests/list?operation=show&id=%s" % ( self.url, self.security.encode_id( request_id ) )
+        self.visit_url( url )
+        self.check_page_for_string( 'Sequencing Request "%s"' % request_name )
+        url = ["%s/requests_common/request_page?save_samples_button=Save&cntrller=requests&edit_mode=True&id=%s" % ( self.url, self.security.encode_id( request_id ) )]
         for index, bar_code in enumerate(bar_codes):
-            tc.fv( "1", "sample_%i_bar_code" % index, bar_code )
-        tc.submit( "save_bar_codes" )
-        self.check_page_for_string( 'Bar codes have been saved for this request' )
+            url.append("sample_%i_barcode=%s" % (index, bar_code ))
+            url.append("sample_%i_name=%s" % (index, samples[index].name.replace(' ', '+') ))
+        self.visit_url('&'.join(url))
+        self.check_page_for_string( 'Changes made to the sample(s) are saved.' )
+        for index, bar_code in enumerate(bar_codes):
+            self.check_page_for_string( bar_code )
     def change_sample_state( self, sample_name, sample_id, new_state_id, new_state_name, comment='' ):
         self.home()
-        self.visit_url( "%s/requests_admin/show_events?sample_id=%i" % (self.url, sample_id) )
+        self.visit_url( "%s/requests_common/sample_events?cntrller=requests_admin&sample_id=%i" % (self.url, sample_id) )
         self.check_page_for_string( 'Events for Sample "%s"' % sample_name )
         tc.fv( "1", "select_state", str(new_state_id) )
         tc.fv( "1", "comment", comment )
--- a/templates/requests/show_data.mako
+++ /dev/null
@@ -1,86 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<script type="text/javascript">
-$(document).ready(function(){
-    //hide the all of the element with class msg_body
-    $(".msg_body").hide();
-    //toggle the componenet with class msg_body
-    $(".msg_head").click(function(){
-        $(this).next(".msg_body").slideToggle(450);
-    });
-});
-</script>
-<style type="text/css">
-.msg_head {
-    padding: 0px 0px;
-    cursor: pointer;
-}
-
-}
-</style>
-
-
-<h2>Data transfer from Sequencer</h2>
-<h3>Sample "${sample.name}" of Request "${sample.request.name}"</h3>
-
-<ul class="manage-table-actions">
-    %if sample.request.submitted() and sample.inprogress_dataset_files():
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests', action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">
-        <span>Refresh this page</span></a>
-    </li>
-    %endif
-    %if sample.library:
-    <li>
-        <a class="action-button" href="${h.url_for( controller='library_common', action='browse_library', cntrller='library', id=trans.security.encode_id( sample.library.id ) )}">
-        <span>${sample.library.name} Data Library</span></a>
-    </li>
-    %endif
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests', action='list', operation='show_request', id=trans.security.encode_id(sample.request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-</ul>
-
-<div class="toolForm">
-    <form name="get_data" action="${h.url_for( controller='requests_admin', action='get_data', sample_id=sample.id)}" method="post" >
-        <div class="form-row">
-            %if len(dataset_files):
-                <table class="grid">
-                    <thead>
-                        <tr>
-                            <th>Dataset File</th>
-                            <th>Transfer Status</th>
-                        </tr>
-                    <thead>
-                    <tbody>
-                        %for dataset_index, dataset_file in enumerate(dataset_files):
-                            ${sample_dataset_files( dataset_index, dataset_file[0], dataset_file[1] )}
-                        %endfor
-                    </tbody>
-                </table>
-            %else:
-                There are no dataset files.
-            %endif
-        </div>
-    </form>
-</div>
-
-<%def name="sample_dataset_files( dataset_index, dataset_file, status )">
-    <tr>
-        <td>${dataset_file.split('/')[-1]}</td>
-        <td>
-            %if status == sample.transfer_status.IN_PROGRESS: 
-                <i>${status}</i>
-            %else:
-                ${status}
-            %endif
-        </td>
-    </tr>
-</%def>
--- /dev/null
+++ b/lib/galaxy/web/controllers/requests_common.py
@@ -0,0 +1,1099 @@
+from galaxy.web.base.controller import *
+from galaxy.web.framework.helpers import time_ago, iff, grids
+from galaxy.model.orm import *
+from galaxy.datatypes import sniff
+from galaxy import model, util
+from galaxy.util.streamball import StreamBall
+import logging, tempfile, zipfile, tarfile, os, sys, subprocess
+from galaxy.web.form_builder import * 
+from datetime import datetime, timedelta
+from galaxy.web.controllers.forms import get_all_forms
+from sqlalchemy.sql.expression import func, and_
+from sqlalchemy.sql import select
+import pexpect
+import ConfigParser, threading, time
+from amqplib import client_0_8 as amqp
+import csv
+log = logging.getLogger( __name__ )
+
+
+class RequestsCommon( BaseController ):
+    
+    @web.json
+    def sample_state_updates( self, trans, ids=None, states=None, cntrller=None ):
+        # Avoid caching
+        trans.response.headers['Pragma'] = 'no-cache'
+        trans.response.headers['Expires'] = '0'
+        # Create new HTML for any that have changed
+        rval = {}
+        if ids is not None and states is not None:
+            ids = map( int, ids.split( "," ) )
+            states = states.split( "," )
+            for id, state in zip( ids, states ):
+                sample = trans.sa_session.query( self.app.model.Sample ).get( id )
+                if sample.current_state().name != state:
+                    rval[id] = {
+                        "state": sample.current_state().name,
+                        "datasets": len(sample.dataset_files),
+                        "html_state": unicode( trans.fill_template( "requests/common/sample_state.mako", sample=sample, cntrller=cntrller ), 'utf-8' ),
+                        "html_datasets": unicode( trans.fill_template( "requests/common/sample_datasets.mako", trans=trans, sample=sample, cntrller=cntrller ), 'utf-8' )
+                    }
+        return rval
+
+    
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def new(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        status = params.get( 'status', 'done' )
+        if params.get('select_request_type', False) == 'True':
+            return trans.fill_template( '/requests/common/new_request.mako',
+                                        cntrller=cntrller,
+                                        select_request_type=self.__select_request_type(trans, 'none'),                                 
+                                        widgets=[],                                   
+                                        message=message,
+                                        status=status)
+        elif params.get('create_request_button', False) == 'Save' \
+           or params.get('create_request_samples_button', False) == 'Add samples':
+            request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
+            if not util.restore_text(params.get('name', '')) \
+                or util.restore_text(params.get('select_user', '')) == unicode('none'):
+                message = 'Please enter the <b>Name</b> of the request and the <b>user</b> on behalf of whom this request will be submitted before saving this request'
+                kwd['create'] = 'True'
+                kwd['status'] = 'error'
+                kwd['message'] = message
+                kwd['create_request_button'] = None
+                kwd['create_request_samples_button'] = None
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller=cntrller,
+                                                                  action='new',
+                                                                  **kwd) )
+            request = self.__save_request(trans, None, **kwd)
+            message = 'The new request named <b>%s</b> has been created' % request.name
+            if params.get('create_request_button', False) == 'Save':
+                return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                                  action='list',
+                                                                  message=message ,
+                                                                  status='done') )
+            elif params.get('create_request_samples_button', False) == 'Add samples':
+                new_kwd = {}
+                new_kwd['id'] = trans.security.encode_id(request.id)
+                new_kwd['operation'] = 'show'
+                new_kwd['add_sample'] = True
+                return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                                  action='list',
+                                                                  message=message ,
+                                                                  status='done',
+                                                                  **new_kwd) )
+        elif params.get('refresh', False) == 'true':
+            return self.__show_request_form(trans, **kwd)
+        
+    def __select_request_type(self, trans, rtid):
+        requesttype_list = trans.user.accessible_request_types(trans)
+        rt_ids = ['none']
+        for rt in requesttype_list:
+            if not rt.deleted:
+                rt_ids.append(str(rt.id))
+        select_reqtype = SelectField('select_request_type', 
+                                     refresh_on_change=True, 
+                                     refresh_on_change_values=rt_ids[1:])
+        if rtid == 'none':
+            select_reqtype.add_option('Select one', 'none', selected=True)
+        else:
+            select_reqtype.add_option('Select one', 'none')
+        for rt in requesttype_list:
+            if not rt.deleted:
+                if rtid == rt.id:
+                    select_reqtype.add_option(rt.name, rt.id, selected=True)
+                else:
+                    select_reqtype.add_option(rt.name, rt.id)
+        return select_reqtype
+    
+    def __show_request_form(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        status = params.get( 'status', 'done' )
+        try:
+            request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
+        except:
+            return trans.fill_template( '/requests/common/new_request.mako',
+                                        cntrller=cntrller, 
+                                        select_request_type=self.__select_request_type(trans, 'none'),                                 
+                                        widgets=[],                                   
+                                        message=message,
+                                        status=status)
+        form_values = None
+        select_request_type = self.__select_request_type(trans, request_type.id)
+        # user
+        if cntrller == 'requests_admin' and trans.user_is_admin():
+            user_id = params.get( 'select_user', 'none' )
+            try:
+                user = trans.sa_session.query( trans.app.model.User ).get( int( user_id ) )
+            except:
+                user = None
+        elif cntrller == 'requests':
+            user = trans.user
+        # list of widgets to be rendered on the request form
+        widgets = []
+        if cntrller == 'requests_admin' and trans.user_is_admin():
+            widgets.append(dict(label='Select user',
+                                widget=self.__select_user(trans, user_id),
+                                helptext='The request would be submitted on behalf of this user (Required)'))
+        widgets.append(dict(label='Name of the Experiment', 
+                            widget=TextField('name', 40, 
+                                             util.restore_text( params.get( 'name', ''  ) )), 
+                            helptext='(Required)'))
+        widgets.append(dict(label='Description', 
+                            widget=TextField('desc', 40,
+                                             util.restore_text( params.get( 'desc', ''  ) )), 
+                            helptext='(Optional)'))
+        widgets = widgets + request_type.request_form.get_widgets( user, **kwd )
+        widgets.append(dict(label='Send email notification when the sequencing request is complete', 
+                            widget=CheckboxField('email_notify', False), 
+                            helptext='Email would be sent to the lab admin and the user for whom this request has been created.'))
+        return trans.fill_template( '/requests/common/new_request.mako',
+                                    cntrller=cntrller,
+                                    select_request_type=select_request_type,
+                                    request_type=request_type,                                    
+                                    widgets=widgets,
+                                    message=message,
+                                    status=status)
+    def __select_user(self, trans, userid):
+        user_list = trans.sa_session.query( trans.app.model.User )\
+                                    .order_by( trans.app.model.User.email.asc() )
+        user_ids = ['none']
+        for user in user_list:
+            if not user.deleted:
+                user_ids.append(str(user.id))
+        select_user = SelectField('select_user', 
+                                  refresh_on_change=True, 
+                                  refresh_on_change_values=user_ids[1:])
+        if userid == 'none':
+            select_user.add_option('Select one', 'none', selected=True)
+        else:
+            select_user.add_option('Select one', 'none')
+        for user in user_list:
+            if not user.deleted:
+                if userid == str(user.id):
+                    select_user.add_option(user.email, user.id, selected=True)
+                else:
+                    select_user.add_option(user.email, user.id)
+        return select_user
+    def __save_request(self, trans, request, **kwd):
+        '''
+        This method saves a new request if request_id is None. 
+        '''
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
+        if request:
+            user = request.user
+        else:
+            if cntrller == 'requests_admin' and trans.user_is_admin():
+                user = trans.sa_session.query( trans.app.model.User ).get( int( params.get( 'select_user', '' ) ) )
+            elif cntrller == 'requests':
+                user = trans.user
+        name = util.restore_text(params.get('name', ''))
+        desc = util.restore_text(params.get('desc', ''))
+        notify = CheckboxField.is_checked( params.get('email_notify', '') )
+        # fields
+        values = []
+        for index, field in enumerate(request_type.request_form.fields):
+            if field['type'] == 'AddressField':
+                value = util.restore_text(params.get('field_%i' % index, ''))
+                if value == 'new':
+                    # save this new address in the list of this user's addresses
+                    user_address = trans.app.model.UserAddress( user=user )
+                    user_address.desc = util.restore_text(params.get('field_%i_short_desc' % index, ''))
+                    user_address.name = util.restore_text(params.get('field_%i_name' % index, ''))
+                    user_address.institution = util.restore_text(params.get('field_%i_institution' % index, ''))
+                    user_address.address = util.restore_text(params.get('field_%i_address1' % index, ''))+' '+util.restore_text(params.get('field_%i_address2' % index, ''))
+                    user_address.city = util.restore_text(params.get('field_%i_city' % index, ''))
+                    user_address.state = util.restore_text(params.get('field_%i_state' % index, ''))
+                    user_address.postal_code = util.restore_text(params.get('field_%i_postal_code' % index, ''))
+                    user_address.country = util.restore_text(params.get('field_%i_country' % index, ''))
+                    user_address.phone = util.restore_text(params.get('field_%i_phone' % index, ''))
+                    trans.sa_session.add( user_address )
+                    trans.sa_session.flush()
+                    trans.sa_session.refresh( user )
+                    values.append(int(user_address.id))
+                elif value == unicode('none'):
+                    values.append('')
+                else:
+                    values.append(int(value))
+            elif field['type'] == 'CheckboxField':
+                values.append(CheckboxField.is_checked( params.get('field_%i' % index, '') )) 
+            else:
+                values.append(util.restore_text(params.get('field_%i' % index, '')))
+        form_values = trans.app.model.FormValues(request_type.request_form, values)
+        trans.sa_session.add( form_values )
+        trans.sa_session.flush()
+        if not request:
+            request = trans.app.model.Request(name, desc, request_type, 
+                                              user, form_values, notify)
+            trans.sa_session.add( request )
+            trans.sa_session.flush()
+            trans.sa_session.refresh( request )
+            # create an event with state 'New' for this new request
+            if request.user.email is not trans.user:
+                comments = "Request created by admin (%s) on behalf of %s." % (trans.user.email, request.user.email)
+            else:
+                comments = "Request created."
+            event = trans.app.model.RequestEvent(request, request.states.NEW, comments)
+            trans.sa_session.add( event )
+            trans.sa_session.flush()
+        else:
+            request.name = name
+            request.desc = desc
+            request.type = request_type
+            request.user = user
+            request.notify = notify
+            request.values = form_values
+            trans.sa_session.add( request )
+            trans.sa_session.flush()
+        return request
+    
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def edit(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        status = params.get( 'status', 'done' )
+        try:
+            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id( params.get( 'id', None ) ) )
+        except:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message="Invalid request ID") )
+        if params.get('show', False) == 'True':
+            return self.__edit_request(trans, **kwd)
+        elif params.get('save_changes_request_button', False) == 'Save changes' \
+             or params.get('edit_samples_button', False) == 'Edit samples':
+                request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
+                if not util.restore_text(params.get('name', '')):
+                    message = 'Please enter the <b>Name</b> of the request'
+                    kwd['status'] = 'error'
+                    kwd['message'] = message
+                    kwd['show'] = 'True'
+                    return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                      cntrller=cntrller,
+                                                                      action='edit',
+                                                                      **kwd) )
+                request = self.__save_request(trans, request, **kwd)
+                message = 'The changes made to the request named %s has been saved' % request.name
+                if params.get('save_changes_request_button', False) == 'Save changes':
+                    return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                                      cntrller=cntrller,
+                                                                      action='list',
+                                                                      message=message ,
+                                                                      status='done') )
+                elif params.get('edit_samples_button', False) == 'Edit samples':
+                    new_kwd = {}
+                    new_kwd['id'] = request.id
+                    new_kwd['edit_samples_button'] = 'Edit samples'
+                    return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                                      cntrller=cntrller,
+                                                                      action='show',
+                                                                      message=message ,
+                                                                      status='done',
+                                                                      **new_kwd) )
+        elif params.get('refresh', False) == 'true':
+            return self.__edit_request(trans, **kwd)
+        
+    def __edit_request(self, trans, **kwd):
+        try:
+            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
+        except:
+            message = "Invalid request ID"
+            log.warn( message )
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              cntrller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message=message) )
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        status = params.get( 'status', 'done' )
+        select_request_type = self.__select_request_type(trans, request.type.id)
+        # list of widgets to be rendered on the request form
+        widgets = []
+        if util.restore_text( params.get( 'name', ''  ) ):
+            name = util.restore_text( params.get( 'name', ''  ) )
+        else:
+            name = request.name
+        widgets.append(dict(label='Name', 
+                            widget=TextField('name', 40, name), 
+                            helptext='(Required)'))
+        if util.restore_text( params.get( 'desc', ''  ) ):
+            desc = util.restore_text( params.get( 'desc', ''  ) )
+        else:
+            desc = request.desc
+        widgets.append(dict(label='Description', 
+                            widget=TextField('desc', 40, desc), 
+                            helptext='(Optional)'))
+        widgets = widgets + request.type.request_form.get_widgets( request.user, request.values.content, **kwd )
+        widgets.append(dict(label='Send email notification once the sequencing request is complete', 
+                            widget=CheckboxField('email_notify', request.notify), 
+                            helptext=''))
+        return trans.fill_template( 'requests/common/edit_request.mako',
+                                    cntrller=cntrller,
+                                    select_request_type=select_request_type,
+                                    request_type=request.type,
+                                    request=request,
+                                    widgets=widgets,
+                                    message=message,
+                                    status=status)
+    def __validate(self, trans, cntrller, request):
+        '''
+        Validates the request entered by the user 
+        '''
+        if not request.samples:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              operation='show',
+                                                              message='Please add one or more samples to this request before submitting.',
+                                                              status='error',
+                                                              id=trans.security.encode_id(request.id)) )
+        empty_fields = []
+        # check rest of the fields of the form
+        for index, field in enumerate(request.type.request_form.fields):
+            if field['required'] == 'required' and request.values.content[index] in ['', None]:
+                empty_fields.append(field['label'])
+        if empty_fields:
+            message = 'Fill the following fields of the request <b>%s</b> before submitting<br/>' % request.name
+            for ef in empty_fields:
+                message = message + '<b>' +ef + '</b><br/>'
+            return message
+        return None
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def submit(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        try:
+            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
+        except:
+            message = "Invalid request ID"
+            log.warn( message )
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message=message,
+                                                              **kwd) )
+        message = self.__validate(trans, cntrller, request)
+        if message:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              operation='edit',
+                                                              status = 'error',
+                                                              message=message,
+                                                              id=trans.security.encode_id(request.id) ) )
+        # change the request state to 'Submitted'
+        if request.user.email is not trans.user:
+            comments = "Request submitted by admin (%s) on behalf of %s." % (trans.user.email, request.user.email)
+        else:
+            comments = ""
+        event = trans.app.model.RequestEvent(request, request.states.SUBMITTED, comments)
+        trans.sa_session.add( event )
+        trans.sa_session.flush()
+        # change the state of each of the samples of thus request
+        new_state = request.type.states[0]
+        for s in request.samples:
+            event = trans.app.model.SampleEvent(s, new_state, 'Samples created.')
+            trans.sa_session.add( event )
+        trans.sa_session.add( request )
+        trans.sa_session.flush()
+        return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                          action='list',
+                                                          id=trans.security.encode_id(request.id),
+                                                          status='done',
+                                                          message='The request <b>%s</b> has been submitted.' % request.name
+                                                          ) )
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def delete(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        id_list = util.listify( kwd['id'] )
+        for id in id_list:
+            try:
+                request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(id) )
+            except:
+                message = "Invalid request ID"
+                log.warn( message )
+                return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                                  action='list',
+                                                                  status='error',
+                                                                  message=message,
+                                                                  **kwd) )
+            request.deleted = True
+            trans.sa_session.add( request )
+            # delete all the samples belonging to this request
+            for s in request.samples:
+                s.deleted = True
+                trans.sa_session.add( s )
+            trans.sa_session.flush()
+        message = '%i request(s) has been deleted.' % len(id_list)
+        status = 'done'
+        return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                          action='list',
+                                                          status=status,
+                                                          message=message) )
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def undelete(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        id_list = util.listify( kwd['id'] )
+        for id in id_list:
+            try:
+                request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(id) )
+            except:
+                message = "Invalid request ID"
+                log.warn( message )
+                return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                                  action='list',
+                                                                  status='error',
+                                                                  message=message,
+                                                                  **kwd) )
+            request.deleted = False
+            trans.sa_session.add( request )
+            # undelete all the samples belonging to this request
+            for s in request.samples:
+                s.deleted = False
+                trans.sa_session.add( s )
+            trans.sa_session.flush()
+        return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                          action='list',
+                                                          status='done',
+                                                          message='%i request(s) has been undeleted.' % len(id_list) ) )
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def events(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        try:
+            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
+        except:
+            message = "Invalid request ID"
+            log.warn( message )
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message=message) )
+        events_list = []
+        all_events = request.events
+        for event in all_events:         
+            events_list.append((event.state, time_ago(event.update_time), event.comment))
+        return trans.fill_template( '/requests/common/events.mako', 
+                                    cntrller=cntrller,
+                                    events_list=events_list, request=request)
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def show(self, trans, **kwd):
+        params = util.Params( kwd )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        status = params.get( 'status', 'done' )
+        add_sample = params.get('add_sample', False)
+        try:
+            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
+        except:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message="Invalid request ID") )
+        # get all data libraries accessible to this user
+        libraries = request.user.accessible_libraries( trans, [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ] )
+        current_samples = []
+        for i, s in enumerate(request.samples):
+            lib_widget, folder_widget = self.__library_widgets(trans, request.user, i, libraries, s, **kwd)
+            current_samples.append(dict(name=s.name,
+                                        barcode=s.bar_code,
+                                        library=s.library,
+                                        folder=s.folder,
+                                        dataset_files=s.dataset_files,
+                                        field_values=s.values.content,
+                                        lib_widget=lib_widget,
+                                        folder_widget=folder_widget))
+        if add_sample:
+            lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
+                                                               len(current_samples)+1, 
+                                                               libraries, None, **kwd)
+            current_samples.append(dict(name='Sample_%i' % (len(current_samples)+1),
+                                        barcode='',
+                                        library=None,
+                                        folder=None,
+                                        dataset_files=[],
+                                        field_values=['' for field in request.type.sample_form.fields],
+                                        lib_widget=lib_widget,
+                                        folder_widget=folder_widget))
+        return trans.fill_template( '/requests/common/show_request.mako',
+                                    cntrller=cntrller,
+                                    request=request,
+                                    request_details=self.request_details(trans, request.id),
+                                    current_samples=current_samples,
+                                    sample_copy=self.__copy_sample(current_samples), 
+                                    details='hide', edit_mode=util.restore_text( params.get( 'edit_mode', 'False'  ) ),
+                                    message=message, status=status )
+
+    def __update_samples(self, trans, request, **kwd):
+        '''
+        This method retrieves all the user entered sample information and
+        returns an list of all the samples and their field values
+        '''
+        params = util.Params( kwd )
+        details = params.get( 'details', 'hide' )
+        edit_mode = params.get( 'edit_mode', 'False' )
+        # get all data libraries accessible to this user
+        libraries = request.user.accessible_libraries( trans, [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ] )
+        
+        current_samples = []
+        for i, s in enumerate(request.samples):
+            lib_widget, folder_widget = self.__library_widgets(trans, request.user, i, libraries, s, **kwd)
+            current_samples.append(dict(name=s.name,
+                                        barcode=s.bar_code,
+                                        library=s.library,
+                                        folder=s.folder,
+                                        field_values=s.values.content,
+                                        lib_widget=lib_widget,
+                                        folder_widget=folder_widget))
+        if edit_mode == 'False':
+            sample_index = len(request.samples) 
+        else:
+            sample_index = 0
+        while True:
+            lib_id = None
+            folder_id = None
+            if params.get( 'sample_%i_name' % sample_index, ''  ):
+                # data library
+                try:
+                    library = trans.sa_session.query( trans.app.model.Library ).get( int( params.get( 'sample_%i_library_id' % sample_index, None ) ) )
+                    lib_id = library.id
+                except:
+                    library = None
+                # folder
+                try:
+                    folder = trans.sa_session.query( trans.app.model.LibraryFolder ).get( int( params.get( 'sample_%i_folder_id' % sample_index, None ) ) )
+                    folder_id = folder.id
+                except:
+                    if library:
+                        folder = library.root_folder
+                    else:
+                        folder = None
+                sample_info = dict( name=util.restore_text( params.get( 'sample_%i_name' % sample_index, ''  ) ),
+                                    barcode=util.restore_text( params.get( 'sample_%i_barcode' % sample_index, ''  ) ),
+                                    library=library,
+                                    folder=folder)
+                sample_info['field_values'] = []
+                for field_index in range(len(request.type.sample_form.fields)):
+                    sample_info['field_values'].append(util.restore_text( params.get( 'sample_%i_field_%i' % (sample_index, field_index), ''  ) ))
+                if edit_mode == 'False':
+                    sample_info['lib_widget'], sample_info['folder_widget'] = self.__library_widgets(trans, request.user, 
+                                                                                                     sample_index, libraries, 
+                                                                                                     None, lib_id, folder_id, **kwd)
+                    current_samples.append(sample_info)
+                else:
+                    sample_info['lib_widget'], sample_info['folder_widget'] = self.__library_widgets(trans, 
+                                                                                                     request.user, 
+                                                                                                     sample_index, 
+                                                                                                     libraries, 
+                                                                                                     request.samples[sample_index], 
+                                                                                                     **kwd)
+                    current_samples[sample_index] =  sample_info
+                sample_index = sample_index + 1
+            else:
+                break
+        return current_samples, details, edit_mode, libraries
+
+    def __library_widgets(self, trans, user, sample_index, libraries, sample=None, lib_id=None, folder_id=None, **kwd):
+        '''
+        This method creates the data library & folder selectbox for creating &
+        editing samples. First we get a list of all the libraries accessible to
+        the current user and display it in a selectbox. If the user has selected an
+        existing library then display all the accessible sub folders of the selected 
+        data library. 
+        '''
+        params = util.Params( kwd )
+        # data library selectbox
+        if not lib_id:
+            lib_id = params.get( "sample_%i_library_id" % sample_index, 'none'  )
+        selected_lib = None
+        if sample and lib_id == 'none':
+            if sample.library:
+                lib_id = str(sample.library.id)
+                selected_lib = sample.library
+        # create data library selectbox with refresh on change enabled
+        lib_id_list = ['new'] + [str(lib.id) for lib in libraries.keys()]
+        lib_widget = SelectField( "sample_%i_library_id" % sample_index, 
+                                refresh_on_change=True, 
+                                refresh_on_change_values=lib_id_list )
+        # fill up the options in the Library selectbox
+        # first option 'none' is the value for "Select one" option
+        if lib_id == 'none':
+            lib_widget.add_option('Select one', 'none', selected=True)
+        else:
+            lib_widget.add_option('Select one', 'none')
+        # all the libraries available to the selected user
+        for lib, hidden_folder_ids in libraries.items():
+            if str(lib.id) == str(lib_id):
+                lib_widget.add_option(lib.name, lib.id, selected=True)
+                selected_lib, selected_hidden_folder_ids = lib, hidden_folder_ids.split(',')
+            else:
+                lib_widget.add_option(lib.name, lib.id)
+            lib_widget.refresh_on_change_values.append(lib.id)
+        # create the folder selectbox
+        folder_widget = SelectField( "sample_%i_folder_id" % sample_index )
+        # when editing a request, either the user has already selected a subfolder or not
+        if sample:
+            if sample.folder:
+                current_fid = sample.folder.id
+            else: 
+                # when a folder not yet associated with the request then the 
+                # the current folder is set to the root_folder of the 
+                # parent data library if present. 
+                if sample.library:
+                    current_fid = sample.library.root_folder.id
+                else:
+                    current_fid = params.get( "sample_%i_folder_id" % sample_index, 'none'  )
+        else:
+            if folder_id:
+                current_fid = folder_id
+            else:
+                current_fid = 'none'
+        # first option
+        if lib_id == 'none':
+            folder_widget.add_option('Select one', 'none', selected=True)
+        else:
+            folder_widget.add_option('Select one', 'none')
+        if selected_lib:
+            # get all show-able folders for the selected library
+            showable_folders = trans.app.security_agent.get_showable_folders( user, user.all_roles(), 
+                                                                              selected_lib, 
+                                                                              [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ], 
+                                                                              selected_hidden_folder_ids )
+            for f in showable_folders:
+                if str(f.id) == str(current_fid):
+                    folder_widget.add_option(f.name, f.id, selected=True)
+                else:
+                    folder_widget.add_option(f.name, f.id)
+        return lib_widget, folder_widget
+
+    def __copy_sample(self, current_samples):
+        copy_list = SelectField('copy_sample')
+        copy_list.add_option('None', -1, selected=True)  
+        for i, s in enumerate(current_samples):
+            copy_list.add_option(s['name'], i)
+        return copy_list  
+    
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def request_page(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        status = params.get( 'status', 'done' )
+        try:
+            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id( kwd['id']) )
+        except:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message="Invalid request ID") )
+        # get the user entered sample details
+        current_samples, details, edit_mode, libraries = self.__update_samples( trans, request, **kwd )
+        if params.get('import_samples_button', False) == 'Import samples':
+            return self.__import_samples(trans, cntrller, request, current_samples, details, libraries, **kwd)
+        elif params.get('add_sample_button', False) == 'Add New':
+            # add an empty or filled sample
+            # if the user has selected a sample no. to copy then copy the contents 
+            # of the src sample to the new sample else an empty sample
+            src_sample_index = int(params.get( 'copy_sample', -1  ))
+            # get the number of new copies of the src sample
+            num_sample_to_copy = int(params.get( 'num_sample_to_copy', 1  ))
+            if src_sample_index == -1:
+                for ns in range(num_sample_to_copy):
+                    # empty sample
+                    lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
+                                                                       len(current_samples), 
+                                                                       libraries, None, **kwd)
+                    current_samples.append(dict(name='Sample_%i' % (len(current_samples)+1),
+                                                barcode='',
+                                                library=None,
+                                                folder=None,
+                                                field_values=['' for field in request.type.sample_form.fields],
+                                                lib_widget=lib_widget,
+                                                folder_widget=folder_widget))
+            else:
+                src_library_id = current_samples[src_sample_index]['lib_widget'].get_selected()[1]
+                src_folder_id = current_samples[src_sample_index]['folder_widget'].get_selected()[1]
+                for ns in range(num_sample_to_copy):
+                    lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
+                                                                       len(current_samples), 
+                                                                       libraries, sample=None, 
+                                                                       lib_id=src_library_id,
+                                                                       folder_id=src_folder_id,
+                                                                       **kwd)
+                    current_samples.append(dict(name=current_samples[src_sample_index]['name']+'_%i' % (len(current_samples)+1),
+                                                barcode='',
+                                                library_id='none',
+                                                folder_id='none',
+                                                field_values=[val for val in current_samples[src_sample_index]['field_values']],
+                                                lib_widget=lib_widget,
+                                                folder_widget=folder_widget))
+            return trans.fill_template( '/requests/common/show_request.mako',
+                                        cntrller=cntrller,
+                                        request=request,
+                                        request_details=self.request_details(trans, request.id),
+                                        current_samples=current_samples,
+                                        sample_copy=self.__copy_sample(current_samples), 
+                                        details=details,
+                                        edit_mode=edit_mode)
+        elif params.get('save_samples_button', False) == 'Save':
+            # check for duplicate sample names
+            message = ''
+            for index in range(len(current_samples)-len(request.samples)):
+                sample_index = index + len(request.samples)
+                sample_name = current_samples[sample_index]['name']
+                if not sample_name.strip():
+                    message = 'Please enter the name of sample number %i' % sample_index
+                    break
+                count = 0
+                for i in range(len(current_samples)):
+                    if sample_name == current_samples[i]['name']:
+                        count = count + 1
+                if count > 1: 
+                    message = "This request has <b>%i</b> samples with the name <b>%s</b>.\nSamples belonging to a request must have unique names." % (count, sample_name)
+                    break
+            if message:
+                return trans.fill_template( '/requests/common/show_request.mako',
+                                            cntrller=cntrller,
+                                            request=request,
+                                            request_details=self.request_details(trans, request.id),
+                                            current_samples = current_samples,
+                                            sample_copy=self.__copy_sample(current_samples), 
+                                            details=details, edit_mode=edit_mode,
+                                            status='error', message=message)
+            # save all the new/unsaved samples entered by the user
+            if edit_mode == 'False':
+                for index in range(len(current_samples)-len(request.samples)):
+                    sample_index = len(request.samples)
+                    form_values = trans.app.model.FormValues(request.type.sample_form, 
+                                                             current_samples[sample_index]['field_values'])
+                    trans.sa_session.add( form_values )
+                    trans.sa_session.flush()                    
+                    s = trans.app.model.Sample(current_samples[sample_index]['name'], '', 
+                                               request, form_values, 
+                                               current_samples[sample_index]['barcode'],
+                                               current_samples[sample_index]['library'],
+                                               current_samples[sample_index]['folder'], 
+                                               dataset_files=[])
+                    trans.sa_session.add( s )
+                    trans.sa_session.flush()
+
+            else:
+                status = 'done'
+                message = 'Changes made to the sample(s) are saved. '
+                for sample_index in range(len(current_samples)):
+                    sample = request.samples[sample_index]
+                    sample.name = current_samples[sample_index]['name'] 
+                    sample.library = current_samples[sample_index]['library']
+                    sample.folder = current_samples[sample_index]['folder']
+                    if request.submitted():
+                        bc_message = self.__validate_barcode(trans, sample, current_samples[sample_index]['barcode'])
+                        if bc_message:
+                            status = 'error'
+                            message += bc_message
+                        else:
+                            if not sample.bar_code:
+                                # if this is a 'new' (still in its first state) sample
+                                # change the state to the next
+                                if sample.current_state().id == request.type.states[0].id:
+                                    event = trans.app.model.SampleEvent(sample, 
+                                                                        request.type.states[1], 
+                                                                        'Sample added to the system')
+                                    trans.sa_session.add( event )
+                                    trans.sa_session.flush()
+                            sample.bar_code = current_samples[sample_index]['barcode']
+                    trans.sa_session.add( sample )
+                    trans.sa_session.flush()
+                    form_values = trans.sa_session.query( trans.app.model.FormValues ).get( sample.values.id )
+                    form_values.content = current_samples[sample_index]['field_values']
+                    trans.sa_session.add( form_values )
+                    trans.sa_session.flush()
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              operation='show',
+                                                              id=trans.security.encode_id(request.id),
+                                                              status=status,
+                                                              message=message ))
+        elif params.get('edit_samples_button', False) == 'Edit samples':
+            edit_mode = 'True'
+            return trans.fill_template( '/requests/common/show_request.mako',
+                                        cntrller=cntrller,
+                                        request=request,
+                                        request_details=self.request_details(trans, request.id),
+                                        current_samples=current_samples,
+                                        sample_copy=self.__copy_sample(current_samples), 
+                                        details=details, libraries=libraries,
+                                        edit_mode=edit_mode)
+        elif params.get('cancel_changes_button', False) == 'Cancel':
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              operation='show',
+                                                              id=trans.security.encode_id(request.id)) )
+        else:
+            return trans.fill_template( '/requests/common/show_request.mako',
+                                        cntrller=cntrller,
+                                        request=request,
+                                        request_details=self.request_details(trans, request.id),
+                                        current_samples=current_samples,
+                                        sample_copy=self.__copy_sample(current_samples), 
+                                        details=details, libraries=libraries,
+                                        edit_mode=edit_mode, status=status, message=message)
+            
+    def __import_samples(self, trans, cntrller, request, current_samples, details, libraries, **kwd):
+        '''
+        This method reads the samples csv file and imports all the samples
+        The format of the csv file is:
+        SampleName,DataLibrary,DataLibraryFolder,Field1,Field2....
+        ''' 
+        try:
+            params = util.Params( kwd )
+            edit_mode = params.get( 'edit_mode', 'False' )
+            file_obj = params.get('file_data', '')
+            reader = csv.reader(file_obj.file)
+            for row in reader:
+                lib_id = None
+                folder_id = None
+                lib = trans.sa_session.query( trans.app.model.Library ) \
+                                      .filter( and_( trans.app.model.Library.table.c.name==row[1], \
+                                                     trans.app.model.Library.table.c.deleted==False ) )\
+                                      .first()
+                if lib:
+                    folder = trans.sa_session.query( trans.app.model.LibraryFolder ) \
+                                             .filter( and_( trans.app.model.LibraryFolder.table.c.name==row[2], \
+                                                            trans.app.model.LibraryFolder.table.c.deleted==False ) )\
+                                             .first()
+                    if folder:
+                        lib_id = lib.id
+                        folder_id = folder.id
+                lib_widget, folder_widget = self.__library_widgets(trans, request.user, len(current_samples), 
+                                                                   libraries, None, lib_id, folder_id, **kwd)
+                current_samples.append(dict(name=row[0], 
+                                            barcode='',
+                                            library=None,
+                                            folder=None,
+                                            lib_widget=lib_widget,
+                                            folder_widget=folder_widget,
+                                            field_values=row[3:]))  
+            return trans.fill_template( '/requests/common/show_request.mako',
+                                        cntrller=cntrller,
+                                        request=request,
+                                        request_details=self.request_details(trans, request.id),
+                                        current_samples=current_samples,
+                                        sample_copy=self.__copy_sample(current_samples), 
+                                        details=details,
+                                        edit_mode=edit_mode)
+        except:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              operation='show',
+                                                              id=trans.security.encode_id(request.id),
+                                                              status='error',
+                                                              message='Error in importing samples file' ))
+
+    def __validate_barcode(self, trans, sample, barcode):
+        '''
+        This method makes sure that the given barcode about to be assigned to 
+        the given sample is gobally unique. That is, barcodes must be unique 
+        across requests in Galaxy LIMS 
+        '''
+        message = ''
+        for index in range(len(sample.request.samples)):
+            # check for empty bar code
+            if not barcode.strip():
+                message = 'Please fill the barcode for sample <b>%s</b>.' % sample.name
+                break
+            # check all the saved bar codes
+            all_samples = trans.sa_session.query( trans.app.model.Sample )
+            for s in all_samples:
+                if barcode == s.bar_code:
+                    if sample.id == s.id:
+                        continue
+                    else:
+                        message = '''The bar code <b>%s</b> of sample <b>%s</b>  
+                                 belongs another sample. The sample bar codes must be 
+                                 unique throughout the system''' % \
+                                 (barcode, sample.name)
+                        break
+            if message:
+                break
+        return message
+
+
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def delete_sample(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', 0 ) ) )
+        current_samples, details, edit_mode, libraries = self.__update_samples( trans, request, **kwd )
+        sample_index = int(params.get('sample_id', 0))
+        sample_name = current_samples[sample_index]['name']
+        s = request.has_sample(sample_name)
+        if s:
+            trans.sa_session.delete( s.values )
+            trans.sa_session.delete( s )
+            trans.sa_session.flush()
+        del current_samples[sample_index]  
+        return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                          action='list',
+                                                          operation='show',
+                                                          id=trans.security.encode_id(request.id),
+                                                          status='done',
+                                                          message='Sample <b>%s</b> has been deleted.' % sample_name ))
+        return trans.fill_template( '/requests/common/show_request.mako',
+                                    controller=cntrller,
+                                    request=request,
+                                    request_details=self.request_details(trans, request.id),
+                                    current_samples = current_samples,
+                                    sample_copy=self.__copy_sample(current_samples), 
+                                    details=details,
+                                    edit_mode=edit_mode)
+    def request_details(self, trans, id):
+        '''
+        Shows the request details
+        '''
+        request = trans.sa_session.query( trans.app.model.Request ).get( id )
+        # list of widgets to be rendered on the request form
+        request_details = []
+        # main details
+        request_details.append(dict(label='User', 
+                                    value=str(request.user.email), 
+                                    helptext=''))
+        request_details.append(dict(label='Description', 
+                                    value=request.desc, 
+                                    helptext=''))
+        request_details.append(dict(label='Type', 
+                                    value=request.type.name, 
+                                    helptext=''))
+        request_details.append(dict(label='State', 
+                                    value=request.state(), 
+                                    helptext=''))
+        request_details.append(dict(label='Date created', 
+                                    value=request.create_time, 
+                                    helptext=''))
+        # form fields
+        for index, field in enumerate(request.type.request_form.fields):
+            if field['required']:
+                req = 'Required'
+            else:
+                req = 'Optional'
+            if field['type'] == 'AddressField':
+                if request.values.content[index]:
+                    request_details.append(dict(label=field['label'],
+                                                value=trans.sa_session.query( trans.app.model.UserAddress ).get( int( request.values.content[index] ) ).get_html(),
+                                                helptext=field['helptext']+' ('+req+')'))
+                else:
+                    request_details.append(dict(label=field['label'],
+                                                value=None,
+                                                helptext=field['helptext']+' ('+req+')'))
+            else: 
+                request_details.append(dict(label=field['label'],
+                                            value=request.values.content[index],
+                                            helptext=field['helptext']+' ('+req+')'))
+        if request.notify:
+            notify = 'Yes'
+        else:
+            notify = 'No'
+        request_details.append(dict(label='Send email notification once the sequencing request is complete', 
+                                    value=notify, 
+                                    helptext=''))
+        return request_details
+    @web.expose
+    @web.require_login( "create/submit sequencing requests" )
+    def sample_events(self, trans, **kwd):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        try:
+            sample_id = int(params.get('sample_id', False))
+            sample = trans.sa_session.query( trans.app.model.Sample ).get( sample_id )
+        except:
+            message = "Invalid sample ID"
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message=message) )
+        events_list = []
+        all_events = sample.events
+        for event in all_events:         
+            events_list.append((event.state.name, event.state.desc, 
+                                time_ago(event.update_time), 
+                                event.comment))
+        widgets, title = self.__change_state_widgets(trans, sample)
+        return trans.fill_template( '/requests/common/sample_events.mako', 
+                                    cntrller=cntrller,
+                                    events_list=events_list,
+                                    sample=sample, widgets=widgets, title=title)
+    def __change_state_widgets(self, trans, sample):
+        possible_states = sample.request.type.states 
+        curr_state = sample.current_state() 
+        states_input = SelectField('select_state')
+        for state in possible_states:
+            if curr_state.name == state.name:
+                states_input.add_option(state.name+' (Current)', state.id, selected=True)
+            else:
+                states_input.add_option(state.name, state.id)
+        widgets = []
+        widgets.append(('Select the new state of the sample from the list of possible state(s)',
+                      states_input))
+        widgets.append(('Comments', TextArea('comment')))
+        title = 'Change current state'
+        return widgets, title
+    @web.expose
+    @web.require_admin
+    def show_datatx_page( self, trans, **kwd ):
+        params = util.Params( kwd )
+        cntrller = util.restore_text( params.get( 'cntrller', 'requests'  ) )
+        message = util.restore_text( params.get( 'message', ''  ) )
+        status = params.get( 'status', 'done' ) 
+        try:
+            sample = trans.sa_session.query( trans.app.model.Sample ).get( trans.security.decode_id( kwd['sample_id'] ) )
+        except:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              status='error',
+                                                              message="Invalid sample ID") )
+        # check if a library and folder has been set for this sample yet.
+        if not sample.library or not sample.folder:
+            return trans.response.send_redirect( web.url_for( controller=cntrller,
+                                                              action='list',
+                                                              operation='show',
+                                                              status='error',
+                                                              message="Set a data library and folder for <b>%s</b> to transfer dataset(s)." % sample.name,
+                                                              id=trans.security.encode_id(sample.request.id) ) )             
+        if params.get( 'folder_path', ''  ):
+            folder_path = util.restore_text( params.get( 'folder_path', ''  ) )
+        else:
+            if len(sample.dataset_files):
+                folder_path = os.path.dirname(sample.dataset_files[-1]['filepath'][:-1])
+            else:
+                folder_path = util.restore_text( sample.request.type.datatx_info.get('data_dir', '') )
+        if folder_path and folder_path[-1] != os.sep:
+            folder_path += os.sep
+        if not sample.request.type.datatx_info['host'] or not sample.request.type.datatx_info['username'] \
+           or not sample.request.type.datatx_info['password']:
+            status = 'error'
+            message = 'The sequencer login information is incomplete. Click on the <b>Sequencer information</b> to add login details.'
+        return trans.fill_template( '/requests/common/get_data.mako', 
+                                    cntrller=cntrller, sample=sample, 
+                                    dataset_files=sample.dataset_files,
+                                    message=message, status=status, files=[],
+                                    folder_path=folder_path )
--- a/templates/requests/events.mako
+++ /dev/null
@@ -1,39 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-<h2>History of Sequencing Request "${request.name}"</h2>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests', action='list', operation='show_request', id=trans.security.encode_id(request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-    <li>
-        <a class="action-button"  href="${h.url_for( controller='requests', action='list')}">
-        <span>Browse all requests</span></a>
-    </li>
-</ul>
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<div class="toolForm">
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>State</th>
-                <th>Last Update</th>
-                <th>Comments</th>
-            </tr>
-        </thead>
-        <tbody>
-            %for state, updated, comments in events_list:    
-                <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
-                    <td><b><a>${state}</a></b></td>
-                    <td><a>${updated}</a></td>
-                    <td><a>${comments}</a></td>
-                </tr>             
-            %endfor
-        </tbody>
-    </table>
-</div>
--- /dev/null
+++ b/templates/requests/common/sample_state.mako
@@ -0,0 +1,5 @@
+<%def name="render_sample_state( cntrller, sample )">
+    <a href="${h.url_for( controller='requests_common', cntrller=cntrller, action='sample_events', sample_id=sample.id)}">${sample.current_state().name}</a>
+</%def>
+
+${render_sample_state( cntrller, sample )}
--- /dev/null
+++ b/templates/requests/common/get_data.mako
@@ -0,0 +1,239 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+
+
+%if message:
+    ${render_msg( message, status )}
+%endif
+
+<script type="text/javascript">
+$(document).ready(function(){
+    //hide the all of the element with class msg_body
+    $(".msg_body").hide();
+    //toggle the componenet with class msg_body
+    $(".msg_head").click(function(){
+        $(this).next(".msg_body").slideToggle(450);
+    });
+});
+
+
+
+
+</script>
+
+<script type="text/javascript">
+   function display_file_details(sample_id, folder_path)
+   {
+       var w = document.get_data.files_list.selectedIndex;
+       var selected_value = document.get_data.files_list.options[w].value;
+       var cell = $("#file_details");
+       if(selected_value.charAt(selected_value.length-1) != '/')
+       {
+            // Make ajax call
+            $.ajax( {
+                type: "POST",
+                url: "${h.url_for( controller='requests_admin', action='get_file_details' )}",
+                dataType: "json",
+                data: { id: sample_id, folder_path: document.get_data.folder_path.value+selected_value },
+                success : function ( data ) {
+                    cell.html( '<label>'+data+'</label>' )
+                }
+            });
+        }
+        else 
+        {
+            cell.html( '' )
+        }
+        
+       
+   }
+</script>
+
+<script type="text/javascript">
+   function open_folder1(sample_id, folder_path)
+   {
+       var w = document.get_data.files_list.selectedIndex;
+       var selected_value = document.get_data.files_list.options[w].value;
+       var cell = $("#file_details");
+       if(selected_value.charAt(selected_value.length-1) == '/')
+       {
+           document.get_data.folder_path.value = document.get_data.folder_path.value+selected_value
+            // Make ajax call
+            $.ajax( {
+                type: "POST",
+                url: "${h.url_for( controller='requests_admin', action='open_folder' )}",
+                dataType: "json",
+                data: { id: sample_id, folder_path: document.get_data.folder_path.value },
+                success : function ( data ) {
+                    document.get_data.files_list.options.length = 0
+                    for(i=0; i<data.length; i++) 
+                    {
+                        var newOpt = new Option(data[i], data[i]);
+                        document.get_data.files_list.options[i] = newOpt;
+                    }
+                    //cell.html( '<label>'+data+'</label>' )
+                    
+                }
+            });
+       }
+        else 
+        {
+            cell.html( '' )
+        }
+   }
+</script>
+
+
+<style type="text/css">
+.msg_head {
+    padding: 0px 0px;
+    cursor: pointer;
+}
+
+}
+</style>
+
+
+<h2>Data transfer from Sequencer</h2>
+<h3>Sample "${sample.name}" of Request "${sample.request.name}"</h3>
+<br/>
+<br/>
+
+<ul class="manage-table-actions">
+    %if sample.request.submitted() and sample.inprogress_dataset_files():
+        <li>
+            <a class="action-button" href="${h.url_for( controller='requests_common', cntrller=cntrller, action='show_datatx_page', sample_id=trans.security.encode_id(sample.id) )}">
+            <span>Refresh this page</span></a>
+        </li>
+    %endif
+    %if cntrller == 'requests_admin' and trans.user_is_admin():
+        <li>
+            <a class="action-button" href="${h.url_for( controller='requests_admin', action='manage_request_types', operation='view', id=trans.security.encode_id(sample.request.type.id) )}">
+            <span>Sequencer information</span></a>
+        </li>
+    
+        <li>
+            <a class="action-button" href="${h.url_for( controller='library_common', action='browse_library', cntrller='library_admin', id=trans.security.encode_id( sample.library.id ) )}">
+            <span>${sample.library.name} Data Library</span></a>
+        </li>
+    %else:
+        <li>
+            <a class="action-button" href="${h.url_for( controller='library_common', action='browse_library', cntrller='library', id=trans.security.encode_id( sample.library.id ) )}">
+            <span>${sample.library.name} Data Library</span></a>
+        </li>
+    %endif
+    <li>
+        <a class="action-button" href="${h.url_for( controller=cntrller, action='list', operation='show', id=trans.security.encode_id(sample.request.id) )}">
+        <span>Browse this request</span></a>
+    </li>
+</ul>
+
+<div class="toolForm">
+    %if len(dataset_files):
+        <div class="form-row">
+            <h4>Sample Dataset(s)</h4>
+            %if sample.untransferred_dataset_files() and cntrller == 'requests_admin':
+                <div class="form-row">
+                    <ul class="manage-table-actions">
+                        <li>
+                            <a class="action-button" href="${h.url_for( controller='requests_admin', action='get_data', start_transfer_button=True, sample_id=sample.id )}">
+                            <span>Start transfer</span></a>
+                        </li>
+                    </ul>
+                 </div>
+             %endif
+            <div class="form-row">
+                <table class="grid">
+                <thead>
+                    <tr>
+                        <th>Dataset File</th>
+                        <th>Transfer Status</th>
+                        <th></th>
+                    </tr>
+                <thead>
+                    <tbody>
+                        %for dataset_index, dataset_file in enumerate(dataset_files):
+                            ${sample_dataset_files( dataset_index, dataset_file['name'], dataset_file['status'] )}
+                        %endfor
+                    </tbody>
+                </table>
+            </div>
+        </div>
+    %else:
+        <div class="form-row">
+            There are no dataset files associated with this sample.
+        </div>
+    %endif
+    
+    <br/>
+    <br/>
+
+    %if cntrller == 'requests_admin' and trans.user_is_admin():
+        <form name="get_data" id="get_data" action="${h.url_for( controller='requests_admin', cntrller=cntrller, action='get_data', sample_id=sample.id)}" method="post" >
+            <div class="form-row">
+                ##<div class="toolFormTitle">Select files for transfer</div>
+                <h4>Select files for transfer</h4>
+                <div style="width: 60%;">
+                    <div class="form-row">
+                        <label>Folder path on the sequencer:</label>
+                        <input type="text" name="folder_path" value="${folder_path}" size="100"/>
+                        <input type="submit" name="browse_button" value="List contents"/>
+                        ##<input type="submit" name="open_folder" value="Open folder"/>
+                        <input type="submit" name="folder_up" value="Up"/>
+                    </div>
+                    <div class="form-row">
+                        <select name="files_list" id="files_list" style="max-width: 98%; width: 98%; height: 150px; font-size: 100%;" ondblclick="open_folder1(${sample.id}, '${folder_path}')" onChange="display_file_details(${sample.id}, '${folder_path}')" multiple>
+                            %for index, f in enumerate(files):
+                                <option value="${f}">${f}</option>
+                            %endfor
+                        </select> 
+                        <br/>
+                        <div id="file_details" class="toolParamHelp" style="clear: both;">
+                            
+                        </div>
+                    </div>
+                    <div class="form-row">
+                        <div class="toolParamHelp" style="clear: both;">
+                            After selecting dataset(s), be sure to click on the <b>Start transfer</b> button. 
+                            Once the transfer is complete the dataset(s) will show up on this page.
+                        </div>
+                        <input type="submit" name="select_files_button" value="Select"/>
+                    </div>
+                </div>
+            </div>
+        </form>
+    %endif
+</div>
+
+
+
+
+<%def name="sample_dataset_files( dataset_index, dataset_name, status )">
+    <tr>
+        
+        <td>
+            %if cntrller == 'requests_admin' and trans.user_is_admin():
+                <label class="msg_head"><a href="${h.url_for( controller='requests_admin', action='dataset_details', sample_id=trans.security.encode_id(sample.id), dataset_index=dataset_index )}">${dataset_name}</a></label>
+            %else:
+                ${dataset_name}
+            %endif
+        </td>
+        <td>
+            %if status not in [sample.transfer_status.NOT_STARTED, sample.transfer_status.COMPLETE]: 
+                <i>${status}</i>
+            %else:
+                ${status}
+            %endif
+        </td>
+        ##<td></td>
+        %if status == sample.transfer_status.NOT_STARTED and cntrller == 'requests_admin' and trans.user_is_admin(): 
+        <td>
+            <a class="action-button" href="${h.url_for( controller='requests_admin', action='get_data', sample_id=sample.id, remove_dataset_button=True, dataset_index=dataset_index )}">
+            <img src="${h.url_for('/static/images/delete_icon.png')}" />
+            <span></span></a>
+        </td>
+        %else:
+            <td></td>
+        %endif
+    </tr>
+</%def>
--- a/templates/admin/requests/events.mako
+++ /dev/null
@@ -1,36 +0,0 @@
-<%inherit file="/base.mako"/>
-<%namespace file="/message.mako" import="render_msg" />
-
-<h2>History of Sequencing Request "${request.name}"</h2>
-<ul class="manage-table-actions">
-    <li>
-        <a class="action-button" href="${h.url_for( controller='requests_admin', action='list', operation='show_request', id=trans.security.encode_id(request.id) )}">
-        <span>Browse this request</span></a>
-    </li>
-</ul>
-<h3>User: ${request.user.email}</h3>
-
-%if message:
-    ${render_msg( message, status )}
-%endif
-
-<div class="toolForm">
-    <table class="grid">
-        <thead>
-            <tr>
-                <th>State</th>
-                <th>Last Update</th>
-                <th>Comments</th>
-            </tr>
-        </thead>
-        <tbody>
-            %for state, updated, comments in events_list:    
-                <tr class="libraryRow libraryOrFolderRow" id="libraryRow">
-                    <td><b><a>${state}</a></b></td>
-                    <td><a>${updated}</a></td>
-                    <td><a>${comments}</a></td>
-                </tr>             
-            %endfor
-        </tbody>
-    </table>
-</div>
--- a/lib/galaxy/web/controllers/requests_admin.py
+++ b/lib/galaxy/web/controllers/requests_admin.py
@@ -95,7 +95,7 @@ class RequestsGrid( grids.Grid ):
         NameColumn( "Name", 
                     key="name", 
                     model_class=model.Request,
-                    link=( lambda item: iff( item.deleted, None, dict( operation="show_request", id=item.id ) ) ),
+                    link=( lambda item: iff( item.deleted, None, dict( operation="show", id=item.id ) ) ),
                     attach_popup=True, 
                     filterable="advanced" ),
         DescriptionColumn( "Description",
@@ -103,7 +103,7 @@ class RequestsGrid( grids.Grid ):
                            model_class=model.Request,
                            filterable="advanced" ),
         SamplesColumn( "Sample(s)", 
-                       link=( lambda item: iff( item.deleted, None, dict( operation="show_request", id=item.id ) ) ), ),
+                       link=( lambda item: iff( item.deleted, None, dict( operation="show", id=item.id ) ) ), ),
         TypeColumn( "Type",
                     link=( lambda item: iff( item.deleted, None, dict( operation="view_type", id=item.type.id ) ) ), ),
         grids.GridColumn( "Last Updated", key="update_time", format=time_ago ),
@@ -137,7 +137,8 @@ class RequestsGrid( grids.Grid ):
         grids.GridOperation( "Undelete", condition=( lambda item: item.deleted ) ),    
     ]
     global_actions = [
-        grids.GridAction( "Create new request", dict( controller='requests_admin', 
+        grids.GridAction( "Create new request", dict( controller='requests_common',
+                                                      cntrller='requests_admin',
                                                       action='new', 
                                                       select_request_type='True' ) )
     ]
@@ -218,6 +219,58 @@ class RequestsAdmin( BaseController ):
     @web.require_admin
     def index( self, trans ):
         return trans.fill_template( "/admin/requests/index.mako" )
+    
+    @web.expose
+    @web.require_admin
+    def list( self, trans, **kwd ):
+        '''
+        List all request made by the current user
+        '''
+        if 'operation' in kwd:
+            operation = kwd['operation'].lower()
+            if not kwd.get( 'id', None ):
+                return trans.response.send_redirect( web.url_for( controller='requests_admin',
+                                                                  action='list',
+                                                                  status='error',
+                                                                  message="Invalid request ID") )
+            if operation == "show":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests_admin',
+                                                                  action='show',
+                                                                  **kwd ) )
+            elif operation == "submit":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests_admin',
+                                                                  action='submit',
+                                                                  **kwd ) )
+            elif operation == "delete":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests_admin',
+                                                                  action='delete',
+                                                                  **kwd ) )
+            elif operation == "undelete":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests_admin',
+                                                                  action='undelete',
+                                                                  **kwd ) )
+            elif operation == "edit":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests_admin',
+                                                                  action='edit',
+                                                                  show=True, **kwd ) )
+            elif operation == "events":
+                return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                                  cntrller='requests_admin',
+                                                                  action='events',
+                                                                  **kwd ) )
+            elif operation == "reject":
+                return self.__reject_request( trans, **kwd )
+            elif operation == "view_type":
+                return self.__view_request_type( trans, **kwd )
+            elif operation == "upload_datasets":
+                return self.__upload_datasets( trans, **kwd )
+        # Render the grid view
+        return self.request_grid( trans, **kwd )
 
     @web.json
     def get_file_details( self, trans, id=None, folder_path=None ):
@@ -246,239 +299,6 @@ class RequestsAdmin( BaseController ):
         sample = trans.sa_session.query( self.app.model.Sample ).get( int(id) )
         return self.__get_files(trans, sample, folder_path)
 
-    
-    @web.json
-    def sample_state_updates( self, trans, ids=None, states=None ):
-        # Avoid caching
-        trans.response.headers['Pragma'] = 'no-cache'
-        trans.response.headers['Expires'] = '0'
-        # Create new HTML for any that have changed
-        rval = {}
-        if ids is not None and states is not None:
-            ids = map( int, ids.split( "," ) )
-            states = states.split( "," )
-            for id, state in zip( ids, states ):
-                sample = trans.sa_session.query( self.app.model.Sample ).get( id )
-                if sample.current_state().name != state:
-                    rval[id] = {
-                        "state": sample.current_state().name,
-                        "datasets": len(sample.dataset_files),
-                        "html_state": unicode( trans.fill_template( "requests/sample_state.mako", sample=sample ), 'utf-8' ),
-                        "html_datasets": unicode( trans.fill_template( "requests/sample_datasets.mako", trans=trans, sample=sample ), 'utf-8' )
-                    }
-        return rval
-    
-    @web.expose
-    @web.require_admin
-    def list( self, trans, **kwd ):
-        '''
-        List all request made by the current user
-        '''
-        if 'operation' in kwd:
-            operation = kwd['operation'].lower()
-            if not kwd.get( 'id', None ):
-                return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                  action='list',
-                                                                  status='error',
-                                                                  message="Invalid request ID") )
-            if operation == "show_request":
-                return self.__show_request( trans, **kwd )
-            elif operation == "submit":
-                return self.__submit_request( trans, **kwd )
-            elif operation == "delete":
-                return self.__delete_request( trans, **kwd )
-            elif operation == "undelete":
-                return self.__undelete_request( trans, **kwd )
-            elif operation == "edit":
-                return self.__edit_request( trans, **kwd )
-            elif operation == "reject":
-                return self.__reject_request( trans, **kwd )
-            elif operation == "events":
-                return self.__request_events( trans, **kwd )
-            elif operation == "view_type":
-                return self.__view_request_type( trans, **kwd )
-            elif operation == "upload_datasets":
-                return self.__upload_datasets( trans, **kwd )
-        # Render the grid view
-        return self.request_grid( trans, **kwd )
-    @web.expose
-    @web.require_admin
-    def edit(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', None ) ) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid request ID",
-                                                              **kwd) )
-        if params.get('show', False) == 'True':
-            return self.__edit_request(trans, id=trans.security.encode_id(request.id), **kwd)
-        elif params.get('save_changes_request_button', False) == 'Save changes' \
-             or params.get('edit_samples_button', False) == 'Edit samples':
-                request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-                if not util.restore_text(params.get('name', '')):
-                    message = 'Please enter the <b>Name</b> of the request'
-                    kwd['status'] = 'error'
-                    kwd['message'] = message
-                    kwd['show'] = 'True'
-                    return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                      action='edit',
-                                                                      **kwd) )
-                request = self.__save_request(trans, request, **kwd)
-                message = 'The changes made to the request named %s has been saved' % request.name
-                if params.get('save_changes_request_button', False) == 'Save changes':
-                    return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                      action='list',
-                                                                      message=message ,
-                                                                      status='done') )
-                elif params.get('edit_samples_button', False) == 'Edit samples':
-                    new_kwd = {}
-                    new_kwd['request_id'] = request.id
-                    new_kwd['edit_samples_button'] = 'Edit samples'
-                    return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                      action='show_request',
-                                                                      message=message ,
-                                                                      status='done',
-                                                                      **new_kwd) )
-        elif params.get('refresh', False) == 'true':
-            return self.__edit_request(trans, id=trans.security.encode_id(request.id), **kwd)
-        
-    def __edit_request(self, trans, **kwd):
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            message = "Invalid request ID"
-            log.warn( message )
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message) )
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        select_request_type = self.__select_request_type(trans, request.type.id)
-        # list of widgets to be rendered on the request form
-        widgets = []
-        if util.restore_text( params.get( 'name', ''  ) ):
-            name = util.restore_text( params.get( 'name', ''  ) )
-        else:
-            name = request.name
-        widgets.append(dict(label='Name', 
-                            widget=TextField('name', 40, name), 
-                            helptext='(Required)'))
-        if util.restore_text( params.get( 'desc', ''  ) ):
-            desc = util.restore_text( params.get( 'desc', ''  ) )
-        else:
-            desc = request.desc
-        widgets.append(dict(label='Description', 
-                            widget=TextField('desc', 40, desc), 
-                            helptext='(Optional)'))
-        widgets = widgets + request.type.request_form.get_widgets( request.user, request.values.content, **kwd )
-        widgets.append(dict(label='Send email notification once the sequencing request is complete', 
-                            widget=CheckboxField('email_notify', request.notify), 
-                            helptext=''))
-        return trans.fill_template( '/admin/requests/edit_request.mako',
-                                    select_request_type=select_request_type,
-                                    request_type=request.type,
-                                    request=request,
-                                    widgets=widgets,
-                                    message=message,
-                                    status=status)
-        return self.__show_request_form(trans)
-    def __delete_request(self, trans, **kwd):
-        id_list = util.listify( kwd['id'] )
-        for id in id_list:
-            try:
-                request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(id) )
-            except:
-                message = "Invalid request ID"
-                log.warn( message )
-                return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                  action='list',
-                                                                  status='error',
-                                                                  message=message,
-                                                                  **kwd) )
-            request.deleted = True
-            trans.sa_session.add( request )
-            # delete all the samples belonging to this request
-            for s in request.samples:
-                s.deleted = True
-                trans.sa_session.add( s )
-            trans.sa_session.flush()
-        message = '%i request(s) has been deleted.' % len(id_list)
-        status = 'done'
-        return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='list',
-                                                          status=status,
-                                                          message=message) )
-    def __undelete_request(self, trans, **kwd):
-        id_list = util.listify( kwd['id'] )
-        for id in id_list:
-            try:
-                request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(id) )
-            except:
-                message = "Invalid request ID"
-                log.warn( message )
-                return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                  action='list',
-                                                                  status='error',
-                                                                  message=message,
-                                                                  **kwd) )
-            request.deleted = False
-            trans.sa_session.add( request )
-            # undelete all the samples belonging to this request
-            for s in request.samples:
-                s.deleted = False
-                trans.sa_session.add( s )
-            trans.sa_session.flush()
-        return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='list',
-                                                          status='done',
-                                                          message='%i request(s) has been undeleted.' % len(id_list) ) )
-    def __submit_request(self, trans, **kwd):
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            message = "Invalid request ID"
-            log.warn( message )
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message,
-                                                              **kwd) )
-        message = self.__validate(trans, request)
-        if message:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              operation='edit',
-                                                              status = 'error',
-                                                              message=message,
-                                                              id=trans.security.encode_id(request.id) ) )
-        # change the request state to 'Submitted'
-        if request.user.email is not trans.user:
-            comments = "Request submitted by admin (%s) on behalf of %s." % (trans.user.email, request.user.email)
-        else:
-            comments = ""
-        event = trans.app.model.RequestEvent(request, request.states.SUBMITTED, comments)
-        trans.sa_session.add( event )
-        trans.sa_session.flush()
-        # change the state of each of the samples of thus request
-        new_state = request.type.states[0]
-        for s in request.samples:
-            event = trans.app.model.SampleEvent(s, new_state, 'Samples created.')
-            trans.sa_session.add( event )
-        trans.sa_session.add( request )
-        trans.sa_session.flush()
-        return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='list',
-                                                          id=trans.security.encode_id(request.id),
-                                                          status='done',
-                                                          message='The request <b>%s</b> has been submitted.' % request.name
-                                                          ) )
     def __reject_request(self, trans, **kwd):
         try:
             request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
@@ -526,759 +346,10 @@ class RequestsAdmin( BaseController ):
                                                           status='done',
                                                           message='Request <b>%s</b> has been rejected.' % request.name) )
     
-    def __request_events(self, trans, **kwd):
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            message = "Invalid request ID"
-            log.warn( message )
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message,
-                                                              **kwd) )
-        events_list = []
-        all_events = request.events
-        for event in all_events:         
-            events_list.append((event.state, time_ago(event.update_time), event.comment))
-        return trans.fill_template( '/admin/requests/events.mako', 
-                                    events_list=events_list, request=request)
-        
     def __upload_datasets(self, trans, **kwd):
         return trans.fill_template( '/admin/requests/upload_datasets.mako' )
-#
-#---- Request Creation ----------------------------------------------------------
-#    
-    def __select_request_type(self, trans, rtid):
-        requesttype_list = trans.user.accessible_request_types(trans)
-        rt_ids = ['none']
-        for rt in requesttype_list:
-            if not rt.deleted:
-                rt_ids.append(str(rt.id))
-        select_reqtype = SelectField('select_request_type', 
-                                     refresh_on_change=True, 
-                                     refresh_on_change_values=rt_ids[1:])
-        if rtid == 'none':
-            select_reqtype.add_option('Select one', 'none', selected=True)
-        else:
-            select_reqtype.add_option('Select one', 'none')
-        for rt in requesttype_list:
-            if not rt.deleted:
-                if rtid == rt.id:
-                    select_reqtype.add_option(rt.name, rt.id, selected=True)
-                else:
-                    select_reqtype.add_option(rt.name, rt.id)
-        return select_reqtype
-    @web.expose
-    @web.require_admin
-    def new(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        if params.get('select_request_type', False) == 'True':
-            return trans.fill_template( '/admin/requests/new_request.mako',
-                                        select_request_type=self.__select_request_type(trans, 'none'),                                 
-                                        widgets=[],                                   
-                                        message=message,
-                                        status=status)
-        elif params.get('create', False) == 'True':
-            if params.get('create_request_button', False) == 'Save' \
-               or params.get('create_request_samples_button', False) == 'Add samples':
-                request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-                if not util.restore_text(params.get('name', '')) \
-                    or util.restore_text(params.get('select_user', '')) == unicode('none'):
-                    message = 'Please enter the <b>Name</b> of the request and the <b>user</b> on behalf of whom this request will be submitted before saving this request'
-                    kwd['create'] = 'True'
-                    kwd['status'] = 'error'
-                    kwd['message'] = message
-                    kwd['create_request_button'] = None
-                    kwd['create_request_samples_button'] = None
-                    return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                      action='new',
-                                                                      **kwd) )
-                request = self.__save_request(trans, None, **kwd)
-                message = 'The new request named %s has been created' % request.name
-                if params.get('create_request_button', False) == 'Save':
-                    return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                      action='list',
-                                                                      message=message ,
-                                                                      status='done') )
-                elif params.get('create_request_samples_button', False) == 'Add samples':
-                    new_kwd = {}
-                    new_kwd['id'] = trans.security.encode_id(request.id)
-                    new_kwd['operation'] = 'show_request'
-                    new_kwd['add_sample'] = True
-                    return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                                      action='list',
-                                                                      message=message ,
-                                                                      status='done',
-                                                                      **new_kwd) )
-            else:
-                return self.__show_request_form(trans, **kwd)
-        elif params.get('refresh', False) == 'true':
-            return self.__show_request_form(trans, **kwd)
-    def __show_request_form(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        try:
-            request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-        except:
-            return trans.fill_template( '/admin/requests/new_request.mako',
-                                        select_request_type=self.__select_request_type(trans, 'none'),                                 
-                                        widgets=[],                                   
-                                        message=message,
-                                        status=status)
-        form_values = None
-        select_request_type = self.__select_request_type(trans, request_type.id)
-        # user
-        user_id = params.get( 'select_user', 'none' )
-        try:
-            user = trans.sa_session.query( trans.app.model.User ).get( int( user_id ) )
-        except:
-            user = None
-        # list of widgets to be rendered on the request form
-        widgets = []
-        widgets.append(dict(label='Select user',
-                            widget=self.__select_user(trans, user_id),
-                            helptext='The request would be submitted on behalf of this user (Required)'))
-        widgets.append(dict(label='Name of the Experiment', 
-                            widget=TextField('name', 40, 
-                                             util.restore_text( params.get( 'name', ''  ) )), 
-                            helptext='(Required)'))
-        widgets.append(dict(label='Description', 
-                            widget=TextField('desc', 40,
-                                             util.restore_text( params.get( 'desc', ''  ) )), 
-                            helptext='(Optional)'))
-        widgets = widgets + request_type.request_form.get_widgets( user, **kwd )
-        widgets.append(dict(label='Send email notification once the sequencing request is complete', 
-                            widget=CheckboxField('email_notify', False), 
-                            helptext='Email would be sent to the lab admin and the user for whom this request has been created.'))
-        return trans.fill_template( '/admin/requests/new_request.mako',
-                                    select_request_type=select_request_type,
-                                    request_type=request_type,                                    
-                                    widgets=widgets,
-                                    message=message,
-                                    status=status)
-    def __select_user(self, trans, userid):
-        user_list = trans.sa_session.query( trans.app.model.User )\
-                                    .order_by( trans.app.model.User.email.asc() )
-        user_ids = ['none']
-        for user in user_list:
-            if not user.deleted:
-                user_ids.append(str(user.id))
-        select_user = SelectField('select_user', 
-                                  refresh_on_change=True, 
-                                  refresh_on_change_values=user_ids[1:])
-        if userid == 'none':
-            select_user.add_option('Select one', 'none', selected=True)
-        else:
-            select_user.add_option('Select one', 'none')
-        for user in user_list:
-            if not user.deleted:
-                if userid == str(user.id):
-                    select_user.add_option(user.email, user.id, selected=True)
-                else:
-                    select_user.add_option(user.email, user.id)
-        return select_user
-    def __validate(self, trans, request):
-        '''
-        Validates the request entered by the user 
-        '''
-        if not request.samples:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              operation='show_request',
-                                                              message='Please add one or more samples to this request before submitting.',
-                                                              status='error',
-                                                              id=trans.security.encode_id(request.id)) )
-        empty_fields = []
-        # check rest of the fields of the form
-        for index, field in enumerate(request.type.request_form.fields):
-            if field['required'] == 'required' and request.values.content[index] in ['', None]:
-                empty_fields.append(field['label'])
-        if empty_fields:
-            message = 'Fill the following fields of the request <b>%s</b> before submitting<br/>' % request.name
-            for ef in empty_fields:
-                message = message + '<b>' +ef + '</b><br/>'
-            return message
-        return None
-    def __save_request(self, trans, request=None, **kwd):
-        '''
-        This method saves a new request if request_id is None. 
-        '''
-        params = util.Params( kwd )
-        request_type = trans.sa_session.query( trans.app.model.RequestType ).get( int( params.select_request_type ) )
-        if request:
-            user = request.user
-        else:
-            user = trans.sa_session.query( trans.app.model.User ).get( int( params.get( 'select_user', '' ) ) )
-        name = util.restore_text(params.get('name', ''))
-        desc = util.restore_text(params.get('desc', ''))
-        notify = CheckboxField.is_checked( params.get('email_notify', '') )
-        # fields
-        values = []
-        for index, field in enumerate(request_type.request_form.fields):
-            if field['type'] == 'AddressField':
-                value = util.restore_text(params.get('field_%i' % index, ''))
-                if value == 'new':
-                    # save this new address in the list of this user's addresses
-                    user_address = trans.app.model.UserAddress( user=user )
-                    user_address.desc = util.restore_text(params.get('field_%i_short_desc' % index, ''))
-                    user_address.name = util.restore_text(params.get('field_%i_name' % index, ''))
-                    user_address.institution = util.restore_text(params.get('field_%i_institution' % index, ''))
-                    user_address.address = util.restore_text(params.get('field_%i_address1' % index, ''))+' '+util.restore_text(params.get('field_%i_address2' % index, ''))
-                    user_address.city = util.restore_text(params.get('field_%i_city' % index, ''))
-                    user_address.state = util.restore_text(params.get('field_%i_state' % index, ''))
-                    user_address.postal_code = util.restore_text(params.get('field_%i_postal_code' % index, ''))
-                    user_address.country = util.restore_text(params.get('field_%i_country' % index, ''))
-                    user_address.phone = util.restore_text(params.get('field_%i_phone' % index, ''))
-                    trans.sa_session.add( user_address )
-                    trans.sa_session.flush()
-                    trans.sa_session.refresh( trans.user )
-                    values.append(int(user_address.id))
-                elif value == unicode('none'):
-                    values.append('')
-                else:
-                    values.append(int(value))
-            elif field['type'] == 'CheckboxField':
-                values.append(CheckboxField.is_checked( params.get('field_%i' % index, '') )) 
-            else:
-                values.append(util.restore_text(params.get('field_%i' % index, '')))
-        form_values = trans.app.model.FormValues(request_type.request_form, values)
-        trans.sa_session.add( form_values )
-        trans.sa_session.flush()
-        if not request:
-            request = trans.app.model.Request(name, desc, request_type, 
-                                              user, form_values, notify)
-            trans.sa_session.add( request )
-            trans.sa_session.flush()
-            trans.sa_session.refresh( request )
-            # create an event with state 'New' for this new request
-            if request.user.email is not trans.user:
-                comments = "Request created by admin (%s) on behalf of %s." % (trans.user.email, request.user.email)
-            else:
-                comments = "Request created."
-            event = trans.app.model.RequestEvent(request, request.states.NEW, comments)
-            trans.sa_session.add( event )
-            trans.sa_session.flush()
-        else:
-            request.name = name
-            request.desc = desc
-            request.type = request_type
-            request.user = user
-            request.notify = notify
-            request.values = form_values
-            trans.sa_session.add( request )
-            trans.sa_session.flush()
-        return request
-#
-#---- Request Page ----------------------------------------------------------
-#    
-    def __show_request(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        add_sample = params.get('add_sample', False)
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( trans.security.decode_id(kwd['id']) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid request ID") )
-        # get all data libraries accessible to this user
-        libraries = request.user.accessible_libraries( trans, [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ] )
-        current_samples = []
-        for i, s in enumerate(request.samples):
-            lib_widget, folder_widget = self.__library_widgets(trans, request.user, i, libraries, s, **kwd)
-            current_samples.append(dict(name=s.name,
-                                        barcode=s.bar_code,
-                                        library=s.library,
-                                        folder=s.folder,
-                                        dataset_files=s.dataset_files,
-                                        field_values=s.values.content,
-                                        lib_widget=lib_widget,
-                                        folder_widget=folder_widget))
-        if add_sample:
-            lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
-                                                               len(current_samples)+1, 
-                                                               libraries, None, **kwd)
-            current_samples.append(dict(name='Sample_%i' % (len(current_samples)+1),
-                                        barcode='',
-                                        library=None,
-                                        folder=None,
-                                        dataset_files=[],
-                                        field_values=['' for field in request.type.sample_form.fields],
-                                        lib_widget=lib_widget,
-                                        folder_widget=folder_widget))
-        return trans.fill_template( '/admin/requests/show_request.mako',
-                                    request=request,
-                                    request_details=self.request_details(trans, request.id),
-                                    current_samples=current_samples,
-                                    sample_copy=self.__copy_sample(current_samples), 
-                                    details='hide', edit_mode=util.restore_text( params.get( 'edit_mode', 'False'  ) ),
-                                    message=message, status=status )
-    def __library_widgets(self, trans, user, sample_index, libraries, sample=None, lib_id=None, folder_id=None, **kwd):
-        '''
-        This method creates the data library & folder selectbox for creating &
-        editing samples. First we get a list of all the libraries accessible to
-        the current user and display it in a selectbox. If the user has selected an
-        existing library then display all the accessible sub folders of the selected 
-        data library. 
-        '''
-        params = util.Params( kwd )
-        # data library selectbox
-        if not lib_id:
-            lib_id = params.get( "sample_%i_library_id" % sample_index, 'none'  )
-        selected_lib = None
-        if sample and lib_id == 'none':
-            if sample.library:
-                lib_id = str(sample.library.id)
-                selected_lib = sample.library
-        # create data library selectbox with refresh on change enabled
-        lib_id_list = ['new'] + [str(lib.id) for lib in libraries.keys()]
-        lib_widget = SelectField( "sample_%i_library_id" % sample_index, 
-                                refresh_on_change=True, 
-                                refresh_on_change_values=lib_id_list )
-        # fill up the options in the Library selectbox
-        # first option 'none' is the value for "Select one" option
-        if lib_id == 'none':
-            lib_widget.add_option('Select one', 'none', selected=True)
-        else:
-            lib_widget.add_option('Select one', 'none')
-        # all the libraries available to the selected user
-        for lib, hidden_folder_ids in libraries.items():
-            if str(lib.id) == str(lib_id):
-                lib_widget.add_option(lib.name, lib.id, selected=True)
-                selected_lib, selected_hidden_folder_ids = lib, hidden_folder_ids.split(',')
-            else:
-                lib_widget.add_option(lib.name, lib.id)
-            lib_widget.refresh_on_change_values.append(lib.id)
-        # create the folder selectbox
-        folder_widget = SelectField( "sample_%i_folder_id" % sample_index )
-        # when editing a request, either the user has already selected a subfolder or not
-        if sample:
-            if sample.folder:
-                current_fid = sample.folder.id
-            else: 
-                # when a folder not yet associated with the request then the 
-                # the current folder is set to the root_folder of the 
-                # parent data library if present. 
-                if sample.library:
-                    current_fid = sample.library.root_folder.id
-                else:
-                    current_fid = params.get( "sample_%i_folder_id" % sample_index, 'none'  )
-        else:
-            if folder_id:
-                current_fid = folder_id
-            else:
-                current_fid = 'none'
-        # first option
-        if lib_id == 'none':
-            folder_widget.add_option('Select one', 'none', selected=True)
-        else:
-            folder_widget.add_option('Select one', 'none')
-        if selected_lib:
-            # get all show-able folders for the selected library
-            showable_folders = trans.app.security_agent.get_showable_folders( user, user.all_roles(), 
-                                                                              selected_lib, 
-                                                                              [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ], 
-                                                                              selected_hidden_folder_ids )
-            for f in showable_folders:
-                if str(f.id) == str(current_fid):
-                    folder_widget.add_option(f.name, f.id, selected=True)
-                else:
-                    folder_widget.add_option(f.name, f.id)
-        return lib_widget, folder_widget
-    def __update_samples(self, trans, request, **kwd):
-        '''
-        This method retrieves all the user entered sample information and
-        returns an list of all the samples and their field values
-        '''
-        params = util.Params( kwd )
-        details = params.get( 'details', 'hide' )
-        edit_mode = params.get( 'edit_mode', 'False' )
-        # get all data libraries accessible to this user
-        libraries = request.user.accessible_libraries( trans, [ trans.app.security_agent.permitted_actions.LIBRARY_ADD ] )
-        
-        current_samples = []
-        for i, s in enumerate(request.samples):
-            lib_widget, folder_widget = self.__library_widgets(trans, request.user, i, libraries, s, **kwd)
-            current_samples.append(dict(name=s.name,
-                                        barcode=s.bar_code,
-                                        library=s.library,
-                                        folder=s.folder,
-                                        field_values=s.values.content,
-                                        lib_widget=lib_widget,
-                                        folder_widget=folder_widget))
-        if edit_mode == 'False':
-            sample_index = len(request.samples) 
-        else:
-            sample_index = 0
-        while True:
-            lib_id = None
-            folder_id = None
-            if params.get( 'sample_%i_name' % sample_index, ''  ):
-                # data library
-                try:
-                    library = trans.sa_session.query( trans.app.model.Library ).get( int( params.get( 'sample_%i_library_id' % sample_index, None ) ) )
-                    lib_id = library.id
-                except:
-                    library = None
-                # folder
-                try:
-                    folder = trans.sa_session.query( trans.app.model.LibraryFolder ).get( int( params.get( 'sample_%i_folder_id' % sample_index, None ) ) )
-                    folder_id = folder.id
-                except:
-                    if library:
-                        folder = library.root_folder
-                    else:
-                        folder = None
-                sample_info = dict( name=util.restore_text( params.get( 'sample_%i_name' % sample_index, ''  ) ),
-                                    barcode=util.restore_text( params.get( 'sample_%i_barcode' % sample_index, ''  ) ),
-                                    library=library,
-                                    folder=folder)
-                sample_info['field_values'] = []
-                for field_index in range(len(request.type.sample_form.fields)):
-                    sample_info['field_values'].append(util.restore_text( params.get( 'sample_%i_field_%i' % (sample_index, field_index), ''  ) ))
-                if edit_mode == 'False':
-                    sample_info['lib_widget'], sample_info['folder_widget'] = self.__library_widgets(trans, request.user, 
-                                                                                                     sample_index, libraries, 
-                                                                                                     None, lib_id, folder_id, **kwd)
-                    current_samples.append(sample_info)
-                else:
-                    sample_info['lib_widget'], sample_info['folder_widget'] = self.__library_widgets(trans, 
-                                                                                                     request.user, 
-                                                                                                     sample_index, 
-                                                                                                     libraries, 
-                                                                                                     request.samples[sample_index], 
-                                                                                                     **kwd)
-                    current_samples[sample_index] =  sample_info
-                sample_index = sample_index + 1
-            else:
-                break
-        return current_samples, details, edit_mode, libraries
-    def __copy_sample(self, current_samples):
-        copy_list = SelectField('copy_sample')
-        copy_list.add_option('None', -1, selected=True)  
-        for i, s in enumerate(current_samples):
-            copy_list.add_option(s['name'], i)
-        return copy_list  
-    def __import_samples(self, trans, request, current_samples, details, libraries, **kwd):
-        '''
-        This method reads the samples csv file and imports all the samples
-        The format of the csv file is:
-        SampleName,DataLibrary,DataLibraryFolder,Field1,Field2....
-        ''' 
-        try:
-            params = util.Params( kwd )
-            edit_mode = params.get( 'edit_mode', 'False' )
-            file_obj = params.get('file_data', '')
-            reader = csv.reader(file_obj.file)
-            for row in reader:
-                lib_id = None
-                folder_id = None
-                lib = trans.sa_session.query( trans.app.model.Library ) \
-                                      .filter( and_( trans.app.model.Library.table.c.name==row[1], \
-                                                     trans.app.model.Library.table.c.deleted==False ) )\
-                                      .first()
-                if lib:
-                    folder = trans.sa_session.query( trans.app.model.LibraryFolder ) \
-                                             .filter( and_( trans.app.model.LibraryFolder.table.c.name==row[2], \
-                                                            trans.app.model.LibraryFolder.table.c.deleted==False ) )\
-                                             .first()
-                    if folder:
-                        lib_id = lib.id
-                        folder_id = folder.id
-                lib_widget, folder_widget = self.__library_widgets(trans, request.user, len(current_samples), 
-                                                                   libraries, None, lib_id, folder_id, **kwd)
-                current_samples.append(dict(name=row[0], 
-                                            barcode='',
-                                            library=None,
-                                            folder=None,
-                                            lib_widget=lib_widget,
-                                            folder_widget=folder_widget,
-                                            field_values=row[3:]))  
-            return trans.fill_template( '/admin/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details,
-                                        edit_mode=edit_mode)
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='list',
-                                                          operation='show_request',
-                                                          id=trans.security.encode_id(request.id),
-                                                          status='error',
-                                                          message='Error in importing samples file' ))
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def show_request(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        try:
-            request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', None ) ) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid request ID",
-                                                              **kwd) )
-        # get the user entered sample details
-        current_samples, details, edit_mode, libraries = self.__update_samples( trans, request, **kwd )
-        if params.get('import_samples_button', False) == 'Import samples':
-            return self.__import_samples(trans, request, current_samples, details, libraries, **kwd)
-        elif params.get('add_sample_button', False) == 'Add New':
-            # add an empty or filled sample
-            # if the user has selected a sample no. to copy then copy the contents 
-            # of the src sample to the new sample else an empty sample
-            src_sample_index = int(params.get( 'copy_sample', -1  ))
-            # get the number of new copies of the src sample
-            num_sample_to_copy = int(params.get( 'num_sample_to_copy', 1  ))
-            if src_sample_index == -1:
-                for ns in range(num_sample_to_copy):
-                    # empty sample
-                    lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
-                                                                       len(current_samples), 
-                                                                       libraries, None, **kwd)
-                    current_samples.append(dict(name='Sample_%i' % (len(current_samples)+1),
-                                                barcode='',
-                                                library=None,
-                                                folder=None,
-                                                field_values=['' for field in request.type.sample_form.fields],
-                                                lib_widget=lib_widget,
-                                                folder_widget=folder_widget))
-            else:
-                src_library_id = current_samples[src_sample_index]['lib_widget'].get_selected()[1]
-                src_folder_id = current_samples[src_sample_index]['folder_widget'].get_selected()[1]
-                for ns in range(num_sample_to_copy):
-                    lib_widget, folder_widget = self.__library_widgets(trans, request.user, 
-                                                                       len(current_samples), 
-                                                                       libraries, sample=None, 
-                                                                       lib_id=src_library_id,
-                                                                       folder_id=src_folder_id,
-                                                                       **kwd)
-                    current_samples.append(dict(name=current_samples[src_sample_index]['name']+'_%i' % (len(current_samples)+1),
-                                                barcode='',
-                                                library_id='none',
-                                                folder_id='none',
-                                                field_values=[val for val in current_samples[src_sample_index]['field_values']],
-                                                lib_widget=lib_widget,
-                                                folder_widget=folder_widget))
-            return trans.fill_template( '/admin/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details,
-                                        edit_mode=edit_mode)
-        elif params.get('save_samples_button', False) == 'Save':
-            # check for duplicate sample names
-            message = ''
-            for index in range(len(current_samples)-len(request.samples)):
-                sample_index = index + len(request.samples)
-                sample_name = current_samples[sample_index]['name']
-                if not sample_name.strip():
-                    message = 'Please enter the name of sample number %i' % sample_index
-                    break
-                count = 0
-                for i in range(len(current_samples)):
-                    if sample_name == current_samples[i]['name']:
-                        count = count + 1
-                if count > 1: 
-                    message = "This request has <b>%i</b> samples with the name <b>%s</b>.\nSamples belonging to a request must have unique names." % (count, sample_name)
-                    break
-            if message:
-                return trans.fill_template( '/admin/requests/show_request.mako',
-                                            request=request,
-                                            request_details=self.request_details(trans, request.id),
-                                            current_samples = current_samples,
-                                            sample_copy=self.__copy_sample(current_samples), 
-                                            details=details, edit_mode=edit_mode,
-                                            status='error', message=message)
-            # save all the new/unsaved samples entered by the user
-            if edit_mode == 'False':
-                for index in range(len(current_samples)-len(request.samples)):
-                    sample_index = len(request.samples)
-                    form_values = trans.app.model.FormValues(request.type.sample_form, 
-                                                             current_samples[sample_index]['field_values'])
-                    trans.sa_session.add( form_values )
-                    trans.sa_session.flush()                    
-                    s = trans.app.model.Sample(current_samples[sample_index]['name'], '', 
-                                               request, form_values, 
-                                               current_samples[sample_index]['barcode'],
-                                               current_samples[sample_index]['library'],
-                                               current_samples[sample_index]['folder'], 
-                                               dataset_files=[])
-                    trans.sa_session.add( s )
-                    trans.sa_session.flush()
+            
 
-            else:
-                status = 'done'
-                message = 'Changes made to the sample(s) are saved. '
-                for sample_index in range(len(current_samples)):
-                    sample = request.samples[sample_index]
-                    sample.name = current_samples[sample_index]['name'] 
-                    sample.library = current_samples[sample_index]['library']
-                    sample.folder = current_samples[sample_index]['folder']
-                    if request.submitted():
-                        bc_message = self.__validate_barcode(trans, sample, current_samples[sample_index]['barcode'])
-                        if bc_message:
-                            status = 'error'
-                            message += bc_message
-                        else:
-                            if not sample.bar_code:
-                                # if this is a 'new' (still in its first state) sample
-                                # change the state to the next
-                                if sample.current_state().id == request.type.states[0].id:
-                                    event = trans.app.model.SampleEvent(sample, 
-                                                                        request.type.states[1], 
-                                                                        'Sample added to the system')
-                                    trans.sa_session.add( event )
-                                    trans.sa_session.flush()
-                            sample.bar_code = current_samples[sample_index]['barcode']
-                    trans.sa_session.add( sample )
-                    trans.sa_session.flush()
-                    form_values = trans.sa_session.query( trans.app.model.FormValues ).get( sample.values.id )
-                    form_values.content = current_samples[sample_index]['field_values']
-                    trans.sa_session.add( form_values )
-                    trans.sa_session.flush()
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='list',
-                                                          operation='show_request',
-                                                          id=trans.security.encode_id(request.id),
-                                                          status=status,
-                                                          message=message ))
-        elif params.get('edit_samples_button', False) == 'Edit samples':
-            edit_mode = 'True'
-            return trans.fill_template( '/admin/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details, libraries=libraries,
-                                        edit_mode=edit_mode)
-        elif params.get('cancel_changes_button', False) == 'Cancel':
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='list',
-                                                          operation='show_request',
-                                                          id=trans.security.encode_id(request.id)) )
-        else:
-            return trans.fill_template( '/admin/requests/show_request.mako',
-                                        request=request,
-                                        request_details=self.request_details(trans, request.id),
-                                        current_samples=current_samples,
-                                        sample_copy=self.__copy_sample(current_samples), 
-                                        details=details, libraries=libraries,
-                                        edit_mode=edit_mode, status=status, message=message)
-
-            
-    @web.expose
-    @web.require_login( "create/submit sequencing requests" )
-    def delete_sample(self, trans, **kwd):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' )
-        request = trans.sa_session.query( trans.app.model.Request ).get( int( params.get( 'request_id', 0 ) ) )
-        current_samples, details, edit_mode, libraries = self.__update_samples( trans, request, **kwd )
-        sample_index = int(params.get('sample_id', 0))
-        sample_name = current_samples[sample_index]['name']
-        s = request.has_sample(sample_name)
-        if s:
-            trans.sa_session.delete( s.values )
-            trans.sa_session.delete( s )
-            trans.sa_session.flush()
-        del current_samples[sample_index]  
-        return trans.fill_template( '/admin/requests/show_request.mako',
-                                    request=request,
-                                    request_details=self.request_details(trans, request.id),
-                                    current_samples = current_samples,
-                                    sample_copy=self.__copy_sample(current_samples), 
-                                    details=details,
-                                    edit_mode=edit_mode)
-    @web.expose
-    @web.require_admin
-    def request_details(self, trans, id):
-        '''
-        Shows the request details
-        '''
-        request = trans.sa_session.query( trans.app.model.Request ).get( id )
-        # list of widgets to be rendered on the request form
-        request_details = []
-        # main details
-        request_details.append(dict(label='User', 
-                                    value=str(request.user.email), 
-                                    helptext=''))
-        request_details.append(dict(label='Description', 
-                                    value=request.desc, 
-                                    helptext=''))
-        request_details.append(dict(label='Type', 
-                                    value=request.type.name, 
-                                    helptext=''))
-        request_details.append(dict(label='State', 
-                                    value=request.state(), 
-                                    helptext=''))
-        request_details.append(dict(label='Date created', 
-                                    value=request.create_time, 
-                                    helptext=''))
-        # form fields
-        for index, field in enumerate(request.type.request_form.fields):
-            if field['required']:
-                req = 'Required'
-            else:
-                req = 'Optional'
-            if field['type'] == 'AddressField':
-                if request.values.content[index]:
-                    request_details.append(dict(label=field['label'],
-                                                value=trans.sa_session.query( trans.app.model.UserAddress ).get( int( request.values.content[index] ) ).get_html(),
-                                                helptext=field['helptext']+' ('+req+')'))
-                else:
-                    request_details.append(dict(label=field['label'],
-                                                value=None,
-                                                helptext=field['helptext']+' ('+req+')'))
-            else: 
-                request_details.append(dict(label=field['label'],
-                                            value=request.values.content[index],
-                                            helptext=field['helptext']+' ('+req+')'))
-        if request.notify:
-            notify = 'Yes'
-        else:
-            notify = 'No'
-        request_details.append(dict(label='Send email notification once the sequencing request is complete', 
-                                    value=notify, 
-                                    helptext=''))
-        return request_details
-    def __validate_barcode(self, trans, sample, barcode):
-        '''
-        This method makes sure that the given barcode about to be assigned to 
-        the given sample is gobally unique. That is, barcodes must be unique 
-        across requests in Galaxy LIMS 
-        '''
-        message = ''
-        for index in range(len(sample.request.samples)):
-            # check for empty bar code
-            if not barcode.strip():
-                message = 'Please fill the barcode for sample <b>%s</b>.' % sample.name
-                break
-            # check all the saved bar codes
-            all_samples = trans.sa_session.query( trans.app.model.Sample )
-            for s in all_samples:
-                if barcode == s.bar_code:
-                    if sample.id == s.id:
-                        continue
-                    else:
-                        message = '''The bar code <b>%s</b> of sample <b>%s</b>  
-                                 belongs another sample. The sample bar codes must be 
-                                 unique throughout the system''' % \
-                                 (barcode, sample.name)
-                        break
-            if message:
-                break
-        return message
     @web.expose
     @web.require_admin
     def bar_codes(self, trans, **kwd):
@@ -1410,21 +481,7 @@ class RequestsAdmin( BaseController ):
                 email_content = "To: %s\nFrom: no-reply(a)nowhere.edu\nSubject: %s\n\n%s" % (request.user.email, subject, body)
                 mail.write( email_content )
                 x = mail.close()
-    def change_state(self, trans, sample):
-        possible_states = sample.request.type.states 
-        curr_state = sample.current_state() 
-        states_input = SelectField('select_state')
-        for state in possible_states:
-            if curr_state.name == state.name:
-                states_input.add_option(state.name+' (Current)', state.id, selected=True)
-            else:
-                states_input.add_option(state.name, state.id)
-        widgets = []
-        widgets.append(('Select the new state of the sample from the list of possible state(s)',
-                      states_input))
-        widgets.append(('Comments', TextArea('comment')))
-        title = 'Change current state'
-        return widgets, title
+
     @web.expose
     @web.require_admin
     def save_state(self, trans, **kwd):
@@ -1449,71 +506,14 @@ class RequestsAdmin( BaseController ):
         trans.sa_session.add( event )
         trans.sa_session.flush()
         self.__set_request_state( trans, sample.request )
-        return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                          action='show_events',
+        return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                          cntrller='requests_admin', 
+                                                          action='sample_events',
                                                           sample_id=sample.id))
-    @web.expose
-    @web.require_admin
-    def show_events(self, trans, **kwd):
-        params = util.Params( kwd )
-        try:
-            sample_id = int(params.get('sample_id', False))
-            sample = trans.sa_session.query( trans.app.model.Sample ).get( sample_id )
-        except:
-            message = "Invalid sample ID"
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message=message,
-                                                              **kwd) )
-        events_list = []
-        all_events = sample.events
-        for event in all_events:         
-            events_list.append((event.state.name, event.state.desc, 
-                                time_ago(event.update_time), event.comment))
-        widgets, title = self.change_state(trans, sample)
-        return trans.fill_template( '/admin/samples/events.mako', 
-                                    events_list=events_list,
-                                    sample=sample, widgets=widgets, title=title)
-
     #
     # Data transfer from sequencer
     #
-    @web.expose
-    @web.require_admin
-    def show_datatx_page( self, trans, **kwd ):
-        params = util.Params( kwd )
-        message = util.restore_text( params.get( 'message', ''  ) )
-        status = params.get( 'status', 'done' ) 
-        try:
-            sample = trans.sa_session.query( trans.app.model.Sample ).get( trans.security.decode_id( kwd['sample_id'] ) )
-        except:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              status='error',
-                                                              message="Invalid sample ID",
-                                                              **kwd) )
-        # check if a library and folder has been set for this sample yet.
-        if not sample.library or not sample.folder:
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
-                                                              action='list',
-                                                              operation='show_request',
-                                                              status='error',
-                                                              message="Set a data library and folder for <b>%s</b> to transfer dataset(s)." % sample.name,
-                                                              id=trans.security.encode_id(sample.request.id) ) )             
-        if params.get( 'folder_path', ''  ):
-            folder_path = util.restore_text( params.get( 'folder_path', ''  ) )
-        else:
-            if len(sample.dataset_files):
-                folder_path = os.path.dirname(sample.dataset_files[-1]['filepath'][:-1])
-            else:
-                folder_path = util.restore_text( sample.request.type.datatx_info.get('data_dir', '') )
-        if folder_path[-1] != os.sep:
-            folder_path += os.sep
-        return trans.fill_template( '/admin/requests/get_data.mako', 
-                                    sample=sample, dataset_files=sample.dataset_files,
-                                    message=message, status=status, files=[],
-                                    folder_path=folder_path )
+
     def __get_files(self, trans, sample, folder_path):
         '''
         This method retrieves the filenames to be transfer from the remote host.
@@ -1521,7 +521,8 @@ class RequestsAdmin( BaseController ):
         datatx_info = sample.request.type.datatx_info
         if not datatx_info['host'] or not datatx_info['username'] or not datatx_info['password']:
             message = "Error in sequencer login information." 
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
+            return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                              cntrller='requests_admin' ,
                                                               action='show_datatx_page', 
                                                               sample_id=trans.security.encode_id(sample.id),
                                                               status='error',
@@ -1536,7 +537,8 @@ class RequestsAdmin( BaseController ):
                                           timeout=10)
         if 'No such file or directory' in output:
             message = "No such folder (%s) exists on the sequencer." % folder_path
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
+            return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                              cntrller='requests_admin' ,
                                                               action='show_datatx_page',
                                                               sample_id=trans.security.encode_id(sample.id),
                                                               message=message, status='error',
@@ -1574,7 +576,8 @@ class RequestsAdmin( BaseController ):
         if params.get( 'start_transfer_button', False ) == 'True':
             return self.__start_datatx(trans, sample)
         if not folder_path:
-            return trans.fill_template( '/admin/requests/get_data.mako',
+            return trans.fill_template( '/requests/common/get_data.mako',
+                                        cntrller='requests_admin',
                                         sample=sample, files=[], 
                                         dataset_files=sample.dataset_files,
                                         folder_path=folder_path )
@@ -1585,7 +588,8 @@ class RequestsAdmin( BaseController ):
             files = self.__get_files(trans, sample, folder_path)
             if folder_path[-1] != os.sep:
                 folder_path += os.sep
-            return trans.fill_template( '/admin/requests/get_data.mako',
+            return trans.fill_template( '/requests/common/get_data.mako',
+                                        cntrller='requests_admin',
                                         sample=sample, files=files, 
                                         dataset_files=sample.dataset_files,
                                         folder_path=folder_path )
@@ -1596,7 +600,8 @@ class RequestsAdmin( BaseController ):
             files = self.__get_files(trans, sample, folder_path)
             if folder_path[-1] != os.sep:
                 folder_path += os.sep
-            return trans.fill_template( '/admin/requests/get_data.mako',
+            return trans.fill_template( '/requests/common/get_data.mako',
+                                        cntrller='requests_admin',
                                         sample=sample, files=files, 
                                         dataset_files=sample.dataset_files,
                                         folder_path=folder_path )
@@ -1607,7 +612,8 @@ class RequestsAdmin( BaseController ):
             files = self.__get_files(trans, sample, folder_path)
             if folder_path[-1] != os.sep:
                 folder_path += os.sep
-            return trans.fill_template( '/admin/requests/get_data.mako',
+            return trans.fill_template( '/requests/common/get_data.mako',
+                                        cntrller='requests_admin',
                                         sample=sample, files=files, 
                                         dataset_files=sample.dataset_files,
                                         folder_path=folder_path )
@@ -1618,7 +624,8 @@ class RequestsAdmin( BaseController ):
             del sample.dataset_files[dataset_index]
             trans.sa_session.add( sample )
             trans.sa_session.flush()
-            return trans.fill_template( '/admin/requests/get_data.mako', 
+            return trans.fill_template( '/requests/common/get_data.mako', 
+                                        cntrller='requests_admin',
                                         sample=sample, files=files,
                                         dataset_files=sample.dataset_files,
                                         folder_path=folder_path)
@@ -1651,7 +658,8 @@ class RequestsAdmin( BaseController ):
                                                               folder_path=folder_path,
                                                               open_folder=True))
 
-        return trans.response.send_redirect( web.url_for( controller='requests_admin',
+        return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                          cntrller='requests_admin' ,
                                                           action='show_datatx_page', 
                                                           sample_id=trans.security.encode_id(sample.id),
                                                           folder_path=folder_path))
@@ -1780,13 +788,15 @@ class RequestsAdmin( BaseController ):
            not datatx_info['username'] or \
            not datatx_info['password']:
             message = "Error in sequencer login information." 
-            return trans.response.send_redirect( web.url_for( controller='requests_admin',
+            return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                              cntrller='requests_admin' ,
                                                               action='show_datatx_page', 
                                                               sample_id=trans.security.encode_id(sample.id),
                                                               status='error',
                                                               message=message))
         self.__send_message(trans, datatx_info, sample)
-        return trans.response.send_redirect( web.url_for( controller='requests_admin',
+        return trans.response.send_redirect( web.url_for( controller='requests_common',
+                                                          cntrller='requests_admin' ,
                                                           action='show_datatx_page', 
                                                           sample_id=trans.security.encode_id(sample.id),
                                                           folder_path=datatx_info['data_dir']))
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0
                            
                          
                          
                            
    
                          
                        
                     
                        
                    
                        
                            
                                
                            
                            galaxy-dist commit 9289b4d7fa4d: API: Patch from	Brad Chapman to	prevent deleted items from appearing in	library contents listing.
                        
                        
by commits-noreply@bitbucket.org 16 Jul '10
                    by commits-noreply@bitbucket.org 16 Jul '10
16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User Nate Coraor <nate(a)bx.psu.edu>
# Date 1277904834 14400
# Node ID 9289b4d7fa4d1d1b630c044dfbc102cf870f62e3
# Parent  1d05df35ec27cc606ddc486c83ea090e01a441d8
API: Patch from Brad Chapman to prevent deleted items from appearing in library contents listing.
--- a/lib/galaxy/web/api/contents.py
+++ b/lib/galaxy/web/api/contents.py
@@ -26,7 +26,7 @@ class ContentsController( BaseController
             for subfolder in folder.active_folders:
                 if not admin:
                     can_access, folder_ids = trans.app.security_agent.check_folder_contents( trans.user, current_user_roles, subfolder )
-                if admin or can_access:
+                if (admin or can_access) and not subfolder.deleted:
                     subfolder.api_path = folder.api_path + '/' + subfolder.name
                     subfolder.api_type = 'folder'
                     rval.append( subfolder )
@@ -34,7 +34,7 @@ class ContentsController( BaseController
             for ld in folder.datasets:
                 if not admin:
                     can_access = trans.app.security_agent.can_access_dataset( current_user_roles, ld.library_dataset_dataset_association.dataset )
-                if admin or can_access:
+                if (admin or can_access) and not ld.deleted:
                     ld.api_path = folder.api_path + '/' + ld.name
                     ld.api_type = 'file'
                     rval.append( ld )
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0
                            
                          
                          
                            
    
                          
                        
                     
                        
                    16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User jeremy goecks <jeremy.goecks(a)emory.edu>
# Date 1277866995 14400
# Node ID 1d05df35ec27cc606ddc486c83ea090e01a441d8
# Parent  47411bb09df44719760aac61e4b90de4fd190aad
Include job information when exporting and importing histories to/from files. This enables jobs associated with an imported history to be rerun and hence affords a history's analyses to be reproduced exactly. Jobs also have a new flag, imported, that is set to false by default but is true when a job is created via import. Also refactored export/import code to use custom JSON encoders.
This code is in a very alpha/beta state: it may not work well, at all, or as expected. Complex datasets and/or jobs are likely not yet handled. Use with caution.
Also, due to security issues, history/import and history/export methods are not currently web-accessible. Admins must manually make these methods accessible if they want to use them.
--- a/templates/root/index.mako
+++ b/templates/root/index.mako
@@ -40,9 +40,9 @@
             "Show structure": function() {
                 galaxy_main.location = "${h.url_for( controller='history', action='display_structured' )}";
             },
-            "Export to File": function() {
-                galaxy_main.location = "${h.url_for( controller='history', action='export_archive' )}";
-            },
+            ##"Export to File": function() {
+            ##    galaxy_main.location = "${h.url_for( controller='history', action='export_archive' )}";
+            ##},
             "Delete": function()
             {
                 if ( confirm( "Really delete the current history?" ) )
@@ -50,10 +50,10 @@
                     galaxy_main.location = "${h.url_for( controller='history', action='delete_current' )}";
                 }
             },
-            "Other Actions": null,
-            "Import from File": function() {
-                galaxy_main.location = "${h.url_for( controller='history', action='import_archive' )}";
-            }
+            ##"Other Actions": null,
+            ##"Import from File": function() {
+            ##    galaxy_main.location = "${h.url_for( controller='history', action='import_archive' )}";
+            ##}
         });
         
         // Init tool options.
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -115,6 +115,7 @@ class Job( object ):
         self.job_runner_name = None
         self.job_runner_external_id = None
         self.post_job_actions = None
+        self.imported = False
         
     def add_parameter( self, name, value ):
         self.parameters.append( JobParameter( name, value ) )
--- /dev/null
+++ b/lib/galaxy/model/migrate/versions/0051_imported_col_for_jobs_table.py
@@ -0,0 +1,48 @@
+"""
+Migration script to add imported column for jobs table.
+"""
+
+from sqlalchemy import *
+from sqlalchemy.orm import *
+from migrate import *
+from migrate.changeset import *
+
+import logging
+log = logging.getLogger( __name__ )
+
+metadata = MetaData( migrate_engine )
+db_session = scoped_session( sessionmaker( bind=migrate_engine, autoflush=False, autocommit=True ) )
+
+def upgrade():
+	print __doc__
+	metadata.reflect()
+
+	# Create and initialize imported column in job table.
+	Jobs_table = Table( "job", metadata, autoload=True )
+	c = Column( "imported", Boolean, default=False, index=True )
+	try:
+	    # Create
+	    c.create( Jobs_table )
+	    assert c is Jobs_table.c.imported
+	    
+	    # Initialize.
+	    if migrate_engine.name == 'mysql' or migrate_engine.name == 'sqlite': 
+	        default_false = "0"
+	    elif migrate_engine.name == 'postgres':
+	        default_false = "false"
+	    db_session.execute( "UPDATE job SET imported=%s" % default_false )
+	    
+	except Exception, e:
+	    print "Adding imported column to job table failed: %s" % str( e )
+	    log.debug( "Adding imported column to job table failed: %s" % str( e ) )
+    
+def downgrade():
+	metadata.reflect()
+
+	# Drop imported column from job table.
+	Jobs_table = Table( "job", metadata, autoload=True )
+	try:
+	    Jobs_table.c.imported.drop()
+	except Exception, e:
+	    print "Dropping column imported from job table failed: %s" % str( e )
+	    log.debug( "Dropping column imported from job table failed: %s" % str( e ) )
--- a/lib/galaxy/web/controllers/history.py
+++ b/lib/galaxy/web/controllers/history.py
@@ -6,6 +6,7 @@ from galaxy.model.mapping import desc
 from galaxy.model.orm import *
 from galaxy.util.json import *
 from galaxy.util.sanitize_html import sanitize_html
+from galaxy.tools.parameters.basic import UnvalidatedValue
 from galaxy.tools.actions import upload_common
 from galaxy.tags.tag_handler import GalaxyTagHandler
 from sqlalchemy.sql.expression import ClauseElement
@@ -145,7 +146,7 @@ class HistoryAllPublishedGrid( grids.Gri
     def apply_query_filter( self, trans, query, **kwargs ):
         # A public history is published, has a slug, and is not deleted.
         return query.filter( self.model_class.published == True ).filter( self.model_class.slug != None ).filter( self.model_class.deleted == False )
-    
+            
 class HistoryController( BaseController, Sharable, UsesAnnotations, UsesHistory ):
     @web.expose
     def index( self, trans ):
@@ -443,26 +444,26 @@ class HistoryController( BaseController,
             trans.sa_session.flush()
             return new_annotation
             
-    @web.expose
     def import_archive( self, trans, archived_history=None ):
         """ Import a history. """
         
         if archived_history is not None:
-            # Import archived history.
             try:         
                 history_archive_file = tarfile.open( archived_history.file.name )
-                
+            
                 # Security check: make sure that members are relative, not absolute.
                 for tarinfo in history_archive_file.getmembers():
                     if tarinfo.name.startswith("/") or tarinfo.name.find("..") != -1:
                         return trans.show_error_message( 'Error importing history archive: archive file is invalid.' )
-                
+            
                 # Unpack archive in temporary directory.
                 temp_output_dir = tempfile.mkdtemp()
                 history_archive_file.extractall( path=temp_output_dir )
                 history_archive_file.close()
-            
-                # Read history attributes.
+        
+                #
+                # Create history.
+                #
                 history_attr_in = open( '%s/%s' % ( temp_output_dir, 'history_attrs.txt'), 'rb' )
                 history_attr_str = ''
                 buffsize = 1048576
@@ -473,31 +474,33 @@ class HistoryController( BaseController,
                             break
                 except OverflowError:
                     pass
+                history_attr_in.close()
                 history_attrs = from_json_string( history_attr_str )
-            
+        
                 # Create history.
                 new_history = model.History( name='imported from archive: %s' % history_attrs['name'].encode( 'utf-8' ), user=trans.user )
                 trans.sa_session.add( new_history )
-                
+            
+                new_history.hid_counter = history_attrs['hid_counter']
+                new_history.genome_build = history_attrs['genome_build']
+                trans.sa_session.flush()
+            
                 # Builds a tag string for a tag, value pair.
                 def get_tag_str( tag, value ):
                     if not value:
                         return tag
                     else:
                         return tag + ":" + value
-                                
+                            
                 # Add annotation, tags.
                 if trans.user:
                     self.add_item_annotation( trans, new_history, history_attrs[ 'annotation' ] )
                     for tag, value in history_attrs[ 'tags' ].items():
                         trans.app.tag_handler.apply_item_tags( trans, trans.user, new_history, get_tag_str( tag, value ) )
-                
-                # Ignore hid_counter since it artificially increases the hid for all HDAs?
-                # new_history.hid_counter = history_attrs['hid_counter']
-                new_history.genome_build = history_attrs['genome_build']
-                trans.sa_session.flush()
-            
-                # Read datasets attributes.
+        
+                #
+                # Create datasets.
+                #
                 datasets_attr_in = open( '%s/%s' % ( temp_output_dir, 'datasets_attrs.txt'), 'rb' )
                 datasets_attr_str = ''
                 buffsize = 1048576
@@ -508,64 +511,187 @@ class HistoryController( BaseController,
                             break
                 except OverflowError:
                     pass
+                datasets_attr_in.close()
                 datasets_attrs = from_json_string( datasets_attr_str )
-            
-                # Create datasets.            
+        
+                # Create datasets.
                 for dataset_attrs in datasets_attrs:
                     metadata = dataset_attrs['metadata']
-                
+            
                     # Create dataset and HDA.
-                    hda = trans.app.model.HistoryDatasetAssociation( name = dataset_attrs['name'].encode( 'utf-8' ),
-                                                                     extension = dataset_attrs['extension'],
-                                                                     hid = dataset_attrs['hid'],
-                                                                     info = dataset_attrs['info'].encode( 'utf-8' ),
-                                                                     blurb = dataset_attrs['blurb'],
-                                                                     peek = dataset_attrs['peek'],
-                                                                     designation = dataset_attrs['designation'],
-                                                                     visible = dataset_attrs['visible'],
-                                                                     dbkey = metadata['dbkey'],
-                                                                     metadata = metadata, 
-                                                                     history = new_history,
-                                                                     create_dataset = True,
-                                                                     sa_session = trans.sa_session )                     
+                    hda = model.HistoryDatasetAssociation( name = dataset_attrs['name'].encode( 'utf-8' ),
+                                                           extension = dataset_attrs['extension'],
+                                                           info = dataset_attrs['info'].encode( 'utf-8' ),
+                                                           blurb = dataset_attrs['blurb'],
+                                                           peek = dataset_attrs['peek'],
+                                                           designation = dataset_attrs['designation'],
+                                                           visible = dataset_attrs['visible'],
+                                                           dbkey = metadata['dbkey'],
+                                                           metadata = metadata, 
+                                                           history = new_history,
+                                                           create_dataset = True,
+                                                           sa_session = trans.sa_session )                     
                     hda.state = hda.states.OK
                     trans.sa_session.add( hda )
                     trans.sa_session.flush()
                     new_history.add_dataset( hda, genome_build = None )
+                    hda.hid = dataset_attrs['hid'] # Overwrite default hid set when HDA added to history.
                     permissions = trans.app.security_agent.history_get_default_permissions( new_history )
                     trans.app.security_agent.set_all_dataset_permissions( hda.dataset, permissions )
                     trans.sa_session.flush()
-                
+            
                     # Copy dataset data.
                     temp_dataset_name = '%s/datasets/%s' % ( temp_output_dir, dataset_attrs['file_name'] )
                     shutil.copyfile( temp_dataset_name, hda.file_name )
-                
+            
                     # Set tags, annotations.
                     if trans.user:
                         self.add_item_annotation( trans, hda, dataset_attrs[ 'annotation' ] )
                         for tag, value in dataset_attrs[ 'tags' ].items():
                             trans.app.tag_handler.apply_item_tags( trans, trans.user, hda, get_tag_str( tag, value ) )
-                        trans.sa_session.flush()
+                            trans.sa_session.flush()
             
+                #
+                # Create jobs.
+                #
+            
+                # Read jobs attributes.
+                jobs_attr_in = open( '%s/%s' % ( temp_output_dir, 'jobs_attrs.txt'), 'rb' )
+                jobs_attr_str = ''
+                buffsize = 1048576
+                try:
+                    while True:
+                        jobs_attr_str += jobs_attr_in.read( buffsize )
+                        if not jobs_attr_str or len( jobs_attr_str ) % buffsize != 0:
+                            break
+                except OverflowError:
+                    pass
+                jobs_attr_in.close()
+            
+                # Decode jobs attributes.
+                def as_hda( obj_dct ):
+                    """ Hook to 'decode' an HDA; method uses history and HID to get the HDA represented by 
+                        the encoded object. This only works because HDAs are created above. """
+                    if obj_dct.get( '__HistoryDatasetAssociation__', False ):
+                            return trans.sa_session.query( model.HistoryDatasetAssociation ) \
+                                            .filter_by( history=new_history, hid=obj_dct['hid'] ).first()
+                    return obj_dct
+                jobs_attrs = from_json_string( jobs_attr_str, object_hook=as_hda )
+            
+                # Create each job.
+                for job_attrs in jobs_attrs:
+                    imported_job = model.Job()
+                    imported_job.user = trans.user
+                    imported_job.session = trans.get_galaxy_session().id
+                    imported_job.history = new_history
+                    imported_job.tool_id = job_attrs[ 'tool_id' ]
+                    imported_job.tool_version = job_attrs[ 'tool_version' ]
+                    imported_job.set_state( job_attrs[ 'state' ] )
+                    imported_job.imported = True
+                    trans.sa_session.add( imported_job )
+                    trans.sa_session.flush()
+                
+                    class HistoryDatasetAssociationIDEncoder( simplejson.JSONEncoder ):
+                        """ Custom JSONEncoder for a HistoryDatasetAssociation that encodes an HDA as its ID. """
+                        def default( self, obj ):
+                            """ Encode an HDA, default encoding for everything else. """
+                            if isinstance( obj, model.HistoryDatasetAssociation ):
+                                return obj.id
+                            return simplejson.JSONEncoder.default( self, obj )
+                                    
+                    # Set parameters. May be useful to look at metadata.py for creating parameters.
+                    # TODO: there may be a better way to set parameters, e.g.:
+                    #   for name, value in tool.params_to_strings( incoming, trans.app ).iteritems():
+                    #       job.add_parameter( name, value )
+                    # to make this work, we'd need to flesh out the HDA objects. The code below is 
+                    # relatively similar.
+                    for name, value in job_attrs[ 'params' ].items():
+                        # Transform parameter values when necessary.
+                        if isinstance( value, model.HistoryDatasetAssociation ):
+                            # HDA input: use hid to find input.
+                            input_hda = trans.sa_session.query( model.HistoryDatasetAssociation ) \
+                                            .filter_by( history=new_history, hid=value.hid ).first()
+                            value = input_hda.id
+                        #print "added parameter %s-->%s to job %i" % ( name, value, imported_job.id )
+                        imported_job.add_parameter( name, to_json_string( value, cls=HistoryDatasetAssociationIDEncoder ) )
+                    
+                    # TODO: Connect jobs to input datasets.
+                
+                    # Connect jobs to output datasets.
+                    for output_hid in job_attrs[ 'output_datasets' ]:
+                        #print "%s job has output dataset %i" % (imported_job.id, output_hid)
+                        output_hda = trans.sa_session.query( model.HistoryDatasetAssociation ) \
+                                        .filter_by( history=new_history, hid=output_hid ).first()
+                        if output_hda:
+                            imported_job.add_output_dataset( output_hda.name, output_hda )
+                    trans.sa_session.flush()
+                                
                 # Cleanup.
                 if os.path.exists( temp_output_dir ):
                     shutil.rmtree( temp_output_dir )
-            
+        
                 return trans.show_ok_message( message="History '%s' has been imported. " % history_attrs['name'] )
             except Exception, e:
                 return trans.show_error_message( 'Error importing history archive. ' + str( e ) )  
-                
             
         return trans.show_form( 
             web.FormBuilder( web.url_for(), "Import a History from an Archive", submit_text="Submit" )
                 .add_input( "file", "Archived History File", "archived_history", value=None, error=None ) 
                             )
             
-    @web.expose
     def export_archive( self, trans, id=None ):
         """ Export a history. """
         
+        #
+        # Helper methods/classes.
+        #
+        
+        def unicode_wrangler( a_string ):
+            """ Convert strings to unicode in utf-8 format. Method should be used for all user input. """
+            a_string_type = type ( a_string )
+            if a_string_type is str:
+                return unicode( a_string, 'utf-8' )
+            elif a_string_type is unicode:
+                return a_string.encode( 'utf-8' )
+
+        def get_item_tag_dict( item ):
+            """ Create dictionary of an item's tags. """
+            tags = {}
+            for tag in item.tags:
+                tag_user_tname = unicode_wrangler( tag.user_tname )
+                tag_user_value = unicode_wrangler( tag.user_value )
+                tags[ tag_user_tname ] = tag_user_value
+            return tags    
+            
+        class HistoryDatasetAssociationEncoder( simplejson.JSONEncoder ):
+            """ Custom JSONEncoder for a HistoryDatasetAssociation. """
+            def default( self, obj ):
+                """ Encode an HDA, default encoding for everything else. """
+                if isinstance( obj, model.HistoryDatasetAssociation ):
+                    return {
+                        "__HistoryDatasetAssociation__" : True,
+                        "create_time" : obj.create_time.__str__(),
+                        "update_time" : obj.update_time.__str__(),
+                        "hid" : obj.hid,
+                        "name" : unicode_wrangler( obj.name ),
+                        "info" : unicode_wrangler( obj.info ),
+                        "blurb" : obj.blurb,
+                        "peek" : obj.peek,
+                        "extension" : obj.extension,
+                        "metadata" : dict( obj.metadata.items() ),
+                        "parent_id" : obj.parent_id,
+                        "designation" : obj.designation,
+                        "deleted" : obj.deleted,
+                        "visible" : obj.visible,
+                        "file_name" : obj.file_name.split('/')[-1],
+                        "annotation" : unicode_wrangler( obj.annotation ),
+                        "tags" : get_item_tag_dict( obj ),
+                    }       
+                return simplejson.JSONEncoder.default( self, obj )
+        
+        #
         # Get history to export.
+        #
         if id:
             history = self.get_history( trans, id, check_ownership=False, check_accessible=True )
         else:
@@ -577,35 +703,24 @@ class HistoryController( BaseController,
             
         history_export_dir_name = "./database/export"
         archive_file_name = '%s/%s.tar.gz' % ( history_export_dir_name, trans.security.encode_id( history.id ) )
+        
+        #
+        # Do export.
+        #
+        
         # TODO: for now, always create archive when exporting; this is for debugging purposes.
         if True:
             # Condition for only creating an archive when history is newer than archive:
             #not os.path.exists ( archive_file_name ) or datetime.utcfromtimestamp( os.path.getmtime( archive_file_name ) ) < history.update_time:
             
             # Create archive and stream back to client.
-            
-            # Convert strings to unicode in utf-8 format. Method should be used for all user input.
-            def unicode_wrangler( a_string ):
-                a_string_type = type ( a_string )
-                if a_string_type is str:
-                    return unicode( a_string, 'utf-8' )
-                elif a_string_type is unicode:
-                    return a_string.encode( 'utf-8' )
-            
-            # Create dictionary of an item's tags.
-            def get_item_tag_dict( item ):
-                tags = {}
-                for tag in item.tags:
-                    tag_user_tname = unicode_wrangler( tag.user_tname )
-                    tag_user_value = unicode_wrangler( tag.user_value )
-                    tags[ tag_user_tname ] = tag_user_value
-                return tags
-            
             try:    
                 # Use temporary directory for temp output files.
                 temp_output_dir = tempfile.mkdtemp()
-                
+            
+                #
                 # Write history attributes to file.
+                #
                 history_attrs = {
                     "create_time" : history.create_time.__str__(),
                     "update_time" : history.update_time.__str__(),
@@ -619,58 +734,103 @@ class HistoryController( BaseController,
                 history_attrs_out = open( history_attrs_file_name, 'w' )
                 history_attrs_out.write( to_json_string( history_attrs ) )
                 history_attrs_out.close()
-                new_name = '%s/%s' % ( temp_output_dir, "history_attrs.txt" )
-                os.rename( history_attrs_file_name, new_name )
-                history_attrs_file_name = new_name
-                
+                                        
+                #
                 # Write datasets' attributes to file.
+                #
                 datasets = self.get_history_datasets( trans, history )
                 datasets_attrs = []
                 for dataset in datasets:
-                    attribute_dict = {
-                        "create_time" : dataset.create_time.__str__(),
-                        "update_time" : dataset.update_time.__str__(),
-                        "hid" : dataset.hid,
-                        "name" : unicode_wrangler( dataset.name ),
-                        "info" : unicode_wrangler( dataset.info ),
-                        "blurb" : dataset.blurb,
-                        "peek" : dataset.peek,
-                        "extension" : dataset.extension,
-                        "metadata" : dict( dataset.metadata.items() ),
-                        "parent_id" : dataset.parent_id,
-                        "designation" : dataset.designation,
-                        "deleted" : dataset.deleted,
-                        "visible" : dataset.visible,
-                        "file_name" : dataset.file_name.split('/')[-1],
-                        "annotation" : unicode_wrangler( self.get_item_annotation_str( trans, history.user, dataset ) ),
-                        "tags" : get_item_tag_dict( dataset )
-                    }
-                    datasets_attrs.append( attribute_dict )
+                    dataset.annotation = self.get_item_annotation_str( trans, history.user, dataset )
+                    datasets_attrs.append( dataset )
                 datasets_attrs_file_name = tempfile.NamedTemporaryFile( dir=temp_output_dir ).name
                 datasets_attrs_out = open( datasets_attrs_file_name, 'w' )
-                datasets_attrs_out.write( to_json_string( datasets_attrs ) )
+                datasets_attrs_out.write( to_json_string( datasets_attrs, cls=HistoryDatasetAssociationEncoder ) )
                 datasets_attrs_out.close()
-                new_name = '%s/%s' % ( temp_output_dir, "datasets_attrs.txt" )
-                os.rename( datasets_attrs_file_name, new_name )
-                datasets_attrs_file_name = new_name
-        
-                # Write files to archive: (a) history attributes file; (b) datasets attributes file; and (c) datasets files.
+            
+                #
+                # Write jobs attributes file.
+                #
+            
+                # Get all jobs associated with HDAs.
+                jobs_dict = {}
+                for hda in datasets:
+                    # Get the associated job, if any. If this hda was copied from another,
+                    # we need to find the job that created the origial hda
+                    job_hda = hda
+                    while job_hda.copied_from_history_dataset_association: #should this check library datasets as well?
+                        job_hda = job_hda.copied_from_history_dataset_association
+                    if not job_hda.creating_job_associations:
+                        # No viable HDA found.
+                        continue
+                
+                    # Get the job object.
+                    job = None
+                    for assoc in job_hda.creating_job_associations:
+                        job = assoc.job
+                        break
+                    if not job:
+                        # No viable job.
+                        continue
+                    
+                    jobs_dict[ job.id ] = job
+                    
+                # Get jobs' attributes.
+                jobs_attrs = []
+                for id, job in jobs_dict.items():
+                    job_attrs = {}
+                    job_attrs[ 'tool_id' ] = job.tool_id
+                    job_attrs[ 'tool_version' ] = job.tool_version
+                    job_attrs[ 'state' ] = job.state
+                                        
+                    # Get the job's parameters
+                    try:
+                        params_objects = job.get_param_values( trans.app )
+                    except:
+                        # Could not get job params.
+                        continue
+
+                    params_dict = {}
+                    for name, value in params_objects.items():
+                        params_dict[ name ] = value
+                    job_attrs[ 'params' ] = params_dict
+                
+                    # Get input, output datasets.
+                    input_datasets = [ assoc.dataset.hid for assoc in job.input_datasets ]
+                    job_attrs[ 'input_datasets' ] = input_datasets
+                    output_datasets = [ assoc.dataset.hid for assoc in job.output_datasets ]
+                    job_attrs[ 'output_datasets' ] = output_datasets
+                
+                    jobs_attrs.append( job_attrs )
+                
+                jobs_attrs_file_name = tempfile.NamedTemporaryFile( dir=temp_output_dir ).name
+                jobs_attrs_out = open( jobs_attrs_file_name, 'w' )
+                jobs_attrs_out.write( to_json_string( jobs_attrs, cls=HistoryDatasetAssociationEncoder ) )
+                jobs_attrs_out.close()
+    
+                #
+                # Write archive and include: (a) history attributes file; (b) datasets attributes file; 
+                # (c) jobs attributes file; and (d) datasets files.
+                #
                 history_archive_name = '%s/%s.tar.gz' % ( history_export_dir_name, trans.security.encode_id( history.id ) )
                 history_archive = tarfile.open( history_archive_name, "w:gz" )
                 history_archive.add( history_attrs_file_name, arcname="history_attrs.txt" )
                 history_archive.add( datasets_attrs_file_name, arcname="datasets_attrs.txt" )
+                history_archive.add( jobs_attrs_file_name, arcname="jobs_attrs.txt" )
                 for i, dataset in enumerate( datasets ) :
-                    history_archive.add( dataset.file_name, arcname="datasets/%s" % datasets_attrs[i]['file_name'] )
+                    history_archive.add( dataset.file_name, arcname="datasets/%s" % dataset.file_name.split('/')[-1] )
                 history_archive.close()
-        
+    
                 # Remove temp directory.
                 if os.path.exists( temp_output_dir ):
                     shutil.rmtree( temp_output_dir )
-                
+            
             except Exception, e:
                 return trans.show_error_message( 'Error creating history archive. ' + str( e ) )
-            
+        
+        #
         # Stream archive.
+        #
         if os.path.exists( history_archive_name ):
             valid_chars = '.,^_-()[]0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'
             hname = history.name
--- a/lib/galaxy/model/mapping.py
+++ b/lib/galaxy/model/mapping.py
@@ -334,7 +334,8 @@ Job.table = Table( "job", metadata,
     Column( "session_id", Integer, ForeignKey( "galaxy_session.id" ), index=True, nullable=True ),
     Column( "user_id", Integer, ForeignKey( "galaxy_user.id" ), index=True, nullable=True ),
     Column( "job_runner_name", String( 255 ) ),
-    Column( "job_runner_external_id", String( 255 ) ) )
+    Column( "job_runner_external_id", String( 255 ) ), 
+    Column( "imported", Boolean, default=False, index=True ) )
     
 JobParameter.table = Table( "job_parameter", metadata,
     Column( "id", Integer, primary_key=True ),
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0
                            
                          
                          
                            
    
                          
                        
                     
                        
                    
                        
                            
                                
                            
                            galaxy-dist commit 10027d1e6dc3: Switch methods	using sendmail to	SMTP instead.
                        
                        
by commits-noreply@bitbucket.org 16 Jul '10
                    by commits-noreply@bitbucket.org 16 Jul '10
16 Jul '10
                    
                        # HG changeset patch -- Bitbucket.org
# Project galaxy-dist
# URL http://bitbucket.org/galaxy/galaxy-dist/overview
# User Nate Coraor <nate(a)bx.psu.edu>
# Date 1277754926 14400
# Node ID 10027d1e6dc31200319f9d90a4d8233170393f2b
# Parent  eea2c040ccb7bd0d2a7c6e5eab8e65f98a163009
Switch methods using sendmail to SMTP instead.
--- a/lib/galaxy/web/controllers/user.py
+++ b/lib/galaxy/web/controllers/user.py
@@ -4,8 +4,9 @@ Contains the user interface in the Unive
 from galaxy.web.base.controller import *
 from galaxy.model.orm import *
 from galaxy import util
-import logging, os, string, re
+import logging, os, string, re, smtplib, socket
 from random import choice
+from email.MIMEText import MIMEText
 from galaxy.web.form_builder import * 
 from galaxy.util.json import from_json_string, to_json_string
 from galaxy.web.framework.helpers import iff
@@ -152,10 +153,20 @@ class User( BaseController ):
                     self.__save_user_info( trans, user, action='create', new_user=True, **kwd )
                     if subscribe_checked:
                         # subscribe user to email list
-                        mail = os.popen( "%s -t" % trans.app.config.sendmail_path, 'w' )
-                        mail.write( "To: %s\nFrom: %s\nSubject: Join Mailing List\n\nJoin Mailing list." % ( trans.app.config.mailing_join_addr,email ) )
-                        if mail.close():
-                            error = "Now logged in as " + user.email + ". However, subscribing to the mailing list has failed."
+                        if trans.app.config.smtp_server is None:
+                            error = "Now logged in as " + user.email + ". However, subscribing to the mailing list has failed because mail is not configured for this Galaxy instance."
+                        else:
+                            msg = MIMEText( 'Join Mailing list.\n' )
+                            to = msg[ 'To' ] = trans.app.config.mailing_join_addr
+                            frm = msg[ 'From' ] = email
+                            msg[ 'Subject' ] = 'Join Mailing List'
+                            try:
+                                s = smtplib.SMTP()
+                                s.connect( trans.app.config.smtp_server )
+                                s.sendmail( frm, [ to ], msg.as_string() )
+                                s.close()
+                            except:
+                                error = "Now logged in as " + user.email + ". However, subscribing to the mailing list has failed."
                     if not error and not admin_view:
                         # The handle_user_login() method has a call to the history_set_default_permissions() method
                         # (needed when logging in with a history), user needs to have default permissions set before logging in
@@ -594,6 +605,8 @@ class User( BaseController ):
                                                               webapp=webapp ) )
     @web.expose
     def reset_password( self, trans, email=None, webapp='galaxy', **kwd ):
+        if trans.app.config.smtp_server is None:
+            return trans.show_error_message( "Mail is not configured for this Galaxy instance.  Please contact an administrator." )
         message = util.restore_text( kwd.get( 'message', '' ) )
         status = 'done'
         if kwd.get( 'reset_password_button', False ):
@@ -608,20 +621,30 @@ class User( BaseController ):
                     new_pass = ""
                     for i in range(15):
                         new_pass = new_pass + choice(chars)
-                    mail = os.popen("%s -t" % trans.app.config.sendmail_path, 'w')
-                    mail.write("To: %s\nFrom: no-reply(a)nowhere.edu\nSubject: Galaxy Password Reset\n\nYour password has been reset to \"%s\" (no quotes)." % (email, new_pass) )
-                    if mail.close():
-                        message = 'Failed to reset password.  If this problem persists, please submit a bug report.'
+                    host = trans.request.host.split(':')[0]
+                    if host == 'localhost':
+                        host = socket.getfqdn()
+                    msg = MIMEText( 'Your password on %s has been reset to:\n\n  %s\n' % ( host, new_pass ) )
+                    to = msg[ 'To' ] = email
+                    frm = msg[ 'From' ] = 'galaxy-no-reply@' + host
+                    msg[ 'Subject' ] = 'Galaxy Password Reset'
+                    try:
+                        s = smtplib.SMTP()
+                        s.connect( trans.app.config.smtp_server )
+                        s.sendmail( frm, [ to ], msg.as_string() )
+                        s.close()
+                        reset_user.set_password_cleartext( new_pass )
+                        trans.sa_session.add( reset_user )
+                        trans.sa_session.flush()
+                        trans.log_event( "User reset password: %s" % email )
+                        message = "Password has been reset and emailed to: %s.  <a href='%s'>Click here</a> to return to the login form." % ( email, web.url_for( action='login' ) )
+                    except Exception, e:
+                        message = 'Failed to reset password: %s' % str( e )
                         status = 'error'
-                    reset_user.set_password_cleartext( new_pass )
-                    trans.sa_session.add( reset_user )
-                    trans.sa_session.flush()
-                    trans.log_event( "User reset password: %s" % email )
-                    message = "Password has been reset and emailed to: %s.  <a href='%s'>Click here</a> to return to the login form." % ( email, web.url_for( action='login' ) )
                     return trans.response.send_redirect( web.url_for( controller='user',
                                                                       action='reset_password',
                                                                       message=message,
-                                                                      status='done' ) )
+                                                                      status=status ) )
             elif email != None:
                 message = "The specified user does not exist"
                 status = 'error'
--- a/templates/user/register.mako
+++ b/templates/user/register.mako
@@ -72,13 +72,15 @@
                     letters, numbers, and the '-' character.
                 </div></div>
-            <div class="form-row">
-                <label>Subscribe to mailing list:</label>
-                %if subscribe_checked:
-                    <% subscribe_check_box.checked = True %>
-                %endif
-                ${subscribe_check_box.get_html()}
-            </div>
+            %if trans.app.config.smtp_server:
+                <div class="form-row">
+                    <label>Subscribe to mailing list:</label>
+                    %if subscribe_checked:
+                        <% subscribe_check_box.checked = True %>
+                    %endif
+                    ${subscribe_check_box.get_html()}
+                </div>
+            %endif
             %if user_info_select:
                 <div class="form-row"><label>User type</label>
--- a/lib/galaxy/web/controllers/requests_admin.py
+++ b/lib/galaxy/web/controllers/requests_admin.py
@@ -4,9 +4,10 @@ from galaxy.model.orm import *
 from galaxy.datatypes import sniff
 from galaxy import model, util
 from galaxy.util.streamball import StreamBall
-import logging, tempfile, zipfile, tarfile, os, sys, subprocess
+import logging, tempfile, zipfile, tarfile, os, sys, subprocess, smtplib, socket
 from galaxy.web.form_builder import * 
 from datetime import datetime, timedelta
+from email.MIMEText import MIMEText
 from galaxy.web.controllers.forms import get_all_forms
 from sqlalchemy.sql.expression import func, and_
 from sqlalchemy.sql import select
@@ -1403,13 +1404,21 @@ class RequestsAdmin( BaseController ):
             trans.sa_session.flush()
             # now that the request is complete send the email notification to the 
             # the user
-            if request.notify:
-                mail = os.popen("%s -t" % trans.app.config.sendmail_path, 'w')
-                subject = "Galaxy Sample Tracking: '%s' sequencing request in complete." % request.name
-                body = "The '%s' sequencing request (type: %s) is now complete. Datasets from all the samples are now available for analysis or download from the respective data libraries in Galaxy."  % (request.name, request.type.name)
-                email_content = "To: %s\nFrom: no-reply(a)nowhere.edu\nSubject: %s\n\n%s" % (request.user.email, subject, body)
-                mail.write( email_content )
-                x = mail.close()
+            if request.notify and trans.app.config.smtp_server is not None:
+                host = trans.request.host.split(':')[0]
+                if host == 'localhost':
+                    host = socket.getfqdn()
+                msg = MIMEText( "The '%s' sequencing request (type: %s) is now complete. Datasets from all the samples are now available for analysis or download from the respective data libraries in Galaxy."  % ( request.name, request.type.name ) )
+                to = msg[ 'To' ] = request.user.email
+                frm = msg[ 'From' ] = 'galaxy-no-reply@' + host
+                msg[ 'Subject' ] = "Galaxy Sample Tracking: '%s' sequencing request in complete." % request.name
+                try:
+                    s = smtplib.SMTP()
+                    s.connect( trans.app.config.smtp_server )
+                    s.sendmail( frm, [ to ], msg.as_string() )
+                    s.close()
+                except:
+                    pass
     def change_state(self, trans, sample):
         possible_states = sample.request.type.states 
         curr_state = sample.current_state()
                    
                  
                  
                          
                            
                            1
                            
                          
                          
                            
                            0