clean
[sgn.git] / lib / SGN / Controller / AJAX / FieldBook.pm
blob5da2a5adc5a5433c840ef19e1d0d940827a5e946
2 =head1 NAME
4 SGN::Controller::AJAX::FieldBook - a REST controller class to provide the
5 backend for field book operations
7 =head1 DESCRIPTION
9 Creating and viewing trials
11 =head1 AUTHOR
13 Jeremy Edwards <jde22@cornell.edu>
15 =cut
17 package SGN::Controller::AJAX::FieldBook;
19 use Moose;
20 use List::MoreUtils qw /any /;
21 use Scalar::Util qw(looks_like_number);
22 use DateTime;
23 use Try::Tiny;
24 use File::Basename qw | basename dirname|;
25 use File::Copy;
26 use File::Slurp;
27 use File::Spec::Functions;
28 use Digest::MD5;
29 use JSON -support_by_pp;
30 use Spreadsheet::WriteExcel;
31 use SGN::View::Trial qw/design_layout_view design_info_view/;
32 use CXGN::Phenotypes::ParseUpload;
33 use CXGN::Phenotypes::StorePhenotypes;
34 use CXGN::Trial::TrialLayout;
35 use CXGN::Location::LocationLookup;
36 use CXGN::Stock::StockLookup;
37 use CXGN::UploadFile;
38 use CXGN::Fieldbook::TraitInfo;
39 use CXGN::Fieldbook::DownloadTrial;
40 use SGN::Model::Cvterm;
42 #use Data::Dumper;
44 BEGIN { extends 'Catalyst::Controller::REST' }
46 __PACKAGE__->config(
47 default => 'application/json',
48 stash_key => 'rest',
49 map => { 'application/json' => 'JSON', 'text/html' => 'JSON' },
53 sub create_fieldbook_from_trial : Path('/ajax/fieldbook/create') : ActionClass('REST') { }
55 sub create_fieldbook_from_trial_POST : Args(0) {
56 my ($self, $c) = @_;
57 my $schema = $c->dbic_schema('Bio::Chado::Schema', 'sgn_chado');
58 my $trial_id = $c->req->param('trial_id');
59 my $data_level = $c->req->param('data_level') || 'plots';
60 my $metadata_schema = $c->dbic_schema('CXGN::Metadata::Schema');
61 my $phenome_schema = $c->dbic_schema('CXGN::Phenome::Schema');
63 chomp($trial_id);
64 if (!$c->user()) {
65 $c->stash->{rest} = {error => "You need to be logged in to create a field book" };
66 return;
68 if (!any { $_ eq "curator" || $_ eq "submitter" } ($c->user()->roles) ) {
69 $c->stash->{rest} = {error => "You have insufficient privileges to create a field book." };
70 return;
72 if (!$trial_id) {
73 $c->stash->{rest} = {error => "No trial ID supplied." };
74 return;
76 my $trial = $schema->resultset('Project::Project')->find({project_id => $trial_id});
77 if (!$trial) {
78 $c->stash->{rest} = {error => "Trial does not exist with id $trial_id." };
79 return;
81 if ($data_level eq 'plants') {
82 my $trial = CXGN::Trial->new( { bcs_schema => $schema, trial_id => $trial_id });
83 if (!$trial->has_plant_entries()){
84 $c->stash->{rest} = {error => "Trial does not have plant entries. You must first create plant entries." };
85 return;
89 my $dir = $c->tempfiles_subdir('/other');
90 my $tempfile = $c->config->{basepath}."/".$c->tempfile( TEMPLATE => 'other/excelXXXX');
92 my $create_fieldbook = CXGN::Fieldbook::DownloadTrial->new({
93 bcs_schema => $schema,
94 metadata_schema => $metadata_schema,
95 phenome_schema => $phenome_schema,
96 trial_id => $trial_id,
97 tempfile => $tempfile,
98 archive_path => $c->config->{archive_path},
99 user_id => $c->user()->get_object()->get_sp_person_id(),
100 user_name => $c->user()->get_object()->get_username(),
101 data_level => $data_level,
104 my $create_fieldbook_return = $create_fieldbook->download();
106 $c->stash->{rest} = {
107 error_string => $create_fieldbook_return->{'error_messages'},
108 success => 1,
109 result => $create_fieldbook_return->{'result'},
110 file => $create_fieldbook_return->{'file'},
114 sub create_trait_file_for_field_book : Path('/ajax/fieldbook/traitfile/create') : ActionClass('REST') { }
116 sub create_trait_file_for_field_book_POST : Args(0) {
117 my ($self, $c) = @_;
119 if (!$c->user()) {
120 $c->stash->{rest} = {error => "You need to be logged in to create a field book" };
121 return;
123 if (!any { $_ eq "curator" || $_ eq "submitter" } ($c->user()->roles) ) {
124 $c->stash->{rest} = {error => "You have insufficient privileges to create a field book." };
125 return;
128 my @trait_list;
129 my $trait_file_name = $c->req->param('trait_file_name');
130 my $user_id = $c->user()->get_object()->get_sp_person_id();
131 my $user_name = $c->user()->get_object()->get_username();
132 my $time = DateTime->now();
133 my $timestamp = $time->ymd()."_".$time->hms();
134 my $subdirectory_name = "tablet_trait_files";
135 my $archived_file_name = catfile($user_id, $subdirectory_name,$timestamp."_".$trait_file_name.".trt");
136 my $archive_path = $c->config->{archive_path};
137 my $file_destination = catfile($archive_path, $archived_file_name);
139 if ($c->req->param('trait_list')) {
140 @trait_list = @{_parse_list_from_json($c->req->param('trait_list'))};
143 if (!-d $archive_path) {
144 mkdir $archive_path;
147 if (! -d catfile($archive_path, $user_id)) {
148 mkdir (catfile($archive_path, $user_id));
151 if (! -d catfile($archive_path, $user_id,$subdirectory_name)) {
152 mkdir (catfile($archive_path, $user_id, $subdirectory_name));
155 open FILE, ">$file_destination" or die $!;
156 my $chado_schema = $c->dbic_schema('Bio::Chado::Schema', 'sgn_chado');
157 print FILE "trait,format,defaultValue,minimum,maximum,details,categories,isVisible,realPosition\n";
158 my $order = 1;
160 foreach my $term (@trait_list) {
162 my ($trait_name, $full_cvterm_accession) = split (/\|/, $term);
163 my ( $db_name , $accession ) = split (/:/ , $full_cvterm_accession);
165 $accession =~ s/\s+$//;
166 $accession =~ s/^\s+//;
167 $db_name =~ s/\s+$//;
168 $db_name =~ s/^\s+//;
170 print STDERR "traitname: $term | accession: $accession \n";
172 #get trait info
174 my $trait_info_lookup = CXGN::Fieldbook::TraitInfo
175 ->new({
176 chado_schema => $chado_schema,
177 db_name => $db_name,
178 trait_accession => $accession,
180 my $trait_info_string = $trait_info_lookup->get_trait_info($trait_name);
182 #return error if not $trait_info_string;
183 #print line with trait info
184 #print FILE "$trait_name:$db_name:$accession,text,,,,,,TRUE,$order\n";
185 print FILE "\"$trait_name|$db_name:$accession\",$trait_info_string,\"TRUE\",\"$order\"\n";
186 $order++;
189 close FILE;
191 open(my $F, "<", $file_destination) || die "Can't open file ";
192 binmode $F;
193 my $md5 = Digest::MD5->new();
194 $md5->addfile($F);
195 close($F);
197 my $metadata_schema = $c->dbic_schema('CXGN::Metadata::Schema');
199 my $md_row = $metadata_schema->resultset("MdMetadata")->create({
200 create_person_id => $user_id,
202 $md_row->insert();
204 my $file_row = $metadata_schema->resultset("MdFiles")->create({
205 basename => basename($file_destination),
206 dirname => dirname($file_destination),
207 filetype => 'tablet trait file',
208 md5checksum => $md5->hexdigest(),
209 metadata_id => $md_row->metadata_id(),
211 $file_row->insert();
213 $c->stash->{rest} = {success => "1",};
218 sub _parse_list_from_json {
219 my $list_json = shift;
220 my $json = new JSON;
221 if ($list_json) {
222 my $decoded_list = $json->allow_nonref->utf8->relaxed->escape_slash->loose->allow_singlequote->allow_barekey->decode($list_json);
223 #my $decoded_list = decode_json($list_json);
224 my @array_of_list_items = @{$decoded_list};
225 return \@array_of_list_items;
227 else {
228 return;