modified key
[sgn.git] / lib / CXGN / Trial / TrialCreate.pm
blobb23690630362cc7db1a574044eeb21955bb15f26
1 package CXGN::Trial::TrialCreate;
3 =head1 NAME
5 CXGN::Trial::TrialCreate - Module to create an entirely new trial based on a specified design. For field_layout experiments and genotyping_layout experiments.
7 Will do the following:
8 1) Create a new project entry in Project table based on trial and description supplied to object. If there is a project with the name already saved, it will return an error and do nothing.
9 2) Create a single new experiment entry in nd_experiment. If is_genotyping is supplied, this will be type = genotyping_layout. Otherwise, this will be type = field_layout.
10 3) Will associate the location to the project through the nd_experiment as well as through a projectprop. Location lookup happens based on location name that is provided. Assumes locations already stored in database.
11 4) Will associate the trial to its breeding program. Lookup is by breeding program name that is provided and assumes bp already exists in database. Will return an error if breeding program name not found.
12 5) Creates a single nd_experiment_project entry, linking project to nd_experiment.
13 6) Creates a year and design projectprop. Also a project_type projectprop if provided. For genotyping plates also creates others like, genotyping_facility and plate_format projectprops
14 7) Calls the CXGN::Trial::TrialDesignStore object to handle storing stocks (tissue_samples, or plots and plants and subplots) and stockprops (rep, block, well, etc)
16 =head1 USAGE
18 FOR FIELD PHENOTYPING TRIALS:
19 my $trial_create = CXGN::Trial::TrialCreate->new({
20 chado_schema => $c->dbic_schema("Bio::Chado::Schema"),
21 dbh => $c->dbc->dbh(),
22 owner_id => $c->user()->get_object()->get_sp_person_id(),
23 operator => $c->user()->get_object()->get_username(),
24 design_type => 'CRD',
25 design => $design_hash,
26 program => $breeding_program->name(),
27 trial_year => $year,
28 planting_date => $planting_date,
29 trial_description => $project_description,
30 trial_location => $location->name(),
31 trial_name => $trial_name,
32 trial_type => $trialtype,
33 field_size => $field_size, #(ha)
34 plot_width => $plot_width, #(m)
35 plot_length => $plot_length, #(m)
36 field_trial_is_planned_to_cross => 'yes', #yes or no
37 field_trial_is_planned_to_be_genotyped => 'no', #yes or no
38 field_trial_from_field_trial => ['source_trial_id1', 'source_trial_id2'],
39 genotyping_trial_from_field_trial => ['genotyping_trial_id1'],
40 crossing_trial_from_field_trial => ['crossing_trial_id1']
41 });
42 try {
43 $trial_create->save_trial();
44 } catch {
45 print STDERR "ERROR SAVING TRIAL!\n";
48 FOR GENOTYPING PLATES:
49 my $ct = CXGN::Trial::TrialCreate->new( {
50 chado_schema => $c->dbic_schema("Bio::Chado::Schema"),
51 dbh => $c->dbc->dbh(),
52 owner_id => $c->user()->get_object()->get_sp_person_id(),
53 operator => $c->user()->get_object()->get_username(),
54 trial_year => $year,
55 planting_date => $planting_date,
56 trial_location => $location->name(),
57 program => $breeding_program->name(),
58 trial_description => $description,
59 design_type => 'genotyping_plate',
60 design => $design_hash,
61 trial_name => $trial_name,
62 is_genotyping => 1,
63 genotyping_user_id => $user_id,
64 genotyping_project_name => $project_name,
65 genotyping_facility_submit => $plate_info->{genotyping_facility_submit},
66 genotyping_facility => $plate_info->{genotyping_facility},
67 genotyping_plate_format => $plate_info->{plate_format},
68 genotyping_plate_sample_type => $plate_info->{sample_type},
69 genotyping_trial_from_field_trial => ['field_trial_id1'],
70 });
71 try {
72 $ct->save_trial();
73 } catch {
74 print STDERR "ERROR SAVING TRIAL!\n";
77 ---------------------------------------------------------------------------------
79 For field_layout trials, the design should be a HasfRef of HashRefs like:
82 '1001' => {
83 "plot_name" => "plot1",
84 "plot_number" => 1001,
85 "accession_name" => "accession1",
86 "block_number" => 1,
87 "row_number" => 2,
88 "col_number" => 3,
89 "rep_number" => 1,
90 "is_a_control" => 1,
91 "seedlot_name" => "seedlot1",
92 "num_seed_per_plot" => 12,
93 "plot_geo_json" => {},
94 "plant_names" => ["plant1", "plant2"],
98 For genotyping_layout trials, the design should be a HashRef of HashRefs like:
101 'A01' => {
102 "plot_name" => "mytissuesample_A01",
103 "stock_name" => "accession1",
104 "plot_number" => "A01",
105 "row_number" => "A",
106 "col_number" => "1",
107 "is_blank" => 0,
108 "concentration" => "5",
109 "volume" => "2",
110 "tissue_type" => "leaf",
111 "dna_person" => "nmorales",
112 "extraction" => "ctab",
113 "acquisition_date" => "2018/02/16",
114 "notes" => "test notes",
118 =head1 DESCRIPTION
121 =head1 AUTHORS
123 Jeremy D. Edwards (jde22@cornell.edu)
125 =cut
128 use Moose;
129 use MooseX::FollowPBP;
130 use Moose::Util::TypeConstraints;
131 use Try::Tiny;
132 use CXGN::Stock::StockLookup;
133 use CXGN::Location::LocationLookup;
134 use CXGN::People::Person;
135 use CXGN::Trial;
136 use SGN::Model::Cvterm;
137 use CXGN::Trial::TrialDesignStore;
138 use Data::Dumper;
140 has 'chado_schema' => (
141 is => 'rw',
142 isa => 'DBIx::Class::Schema',
143 predicate => 'has_chado_schema',
144 required => 1,
147 has 'dbh' => (is => 'rw',predicate => 'has_dbh', required => 1,);
148 #has 'user_name' => (isa => 'Str', is => 'rw', predicate => 'has_user_name', required => 1,);
149 has 'trial_id' => (isa => 'Maybe[Int]', is => 'rw', predicate => 'has_trial_id');
150 has 'program' => (isa =>'Str', is => 'rw', predicate => 'has_program', required => 1,);
151 has 'trial_year' => (isa => 'Maybe[Str]', is => 'rw', predicate => 'has_trial_year', required => 0,);
152 has 'trial_description' => (isa => 'Maybe[Str]', is => 'rw', predicate => 'has_trial_description', required => 0,);
153 has 'trial_location' => (isa => 'Maybe[Str]', is => 'rw', predicate => 'has_trial_location', required => 0,);
154 has 'design_type' => (isa => 'Maybe[Str]', is => 'rw', predicate => 'has_design_type', required => 0);
155 has 'design' => (isa => 'HashRef[HashRef]|Undef', is => 'rw', predicate => 'has_design', required => 0);
156 has 'trial_name' => (isa => 'Str', is => 'rw', predicate => 'has_trial_name', required => 1);
157 has 'trial_type' => (isa => 'Str', is => 'rw', predicate => 'has_trial_type', required => 0);
158 has 'trial_type_value' => (isa => 'Str', is => 'rw', predicate => 'has_trial_type_value', required => 0);
159 has 'trial_has_plant_entries' => (isa => 'Int', is => 'rw', predicate => 'has_trial_has_plant_entries', required => 0);
160 has 'trial_has_subplot_entries' => (isa => 'Int', is => 'rw', predicate => 'has_trial_has_subplot_entries', required => 0);
161 has 'field_size' => (isa => 'Num', is => 'rw', predicate => 'has_field_size', required => 0);
162 has 'plot_width' => (isa => 'Num', is => 'rw', predicate => 'has_plot_width', required => 0);
163 has 'plot_length' => (isa => 'Num', is => 'rw', predicate => 'has_plot_length', required => 0);
164 has 'planting_date' => (isa => 'Str', is => 'rw', predicate => 'has_planting_date', required => 0);
165 has 'transplanting_date' => (isa => 'Str', is => 'rw', predicate => 'has_transplanting_date', required => 0);
166 has 'harvest_date' => (isa => 'Str', is => 'rw', predicate => 'has_harvest_date', required => 0);
167 has 'operator' => (isa => 'Str', is => 'rw', predicate => 'has_operator', required => 1);
168 has 'trial_stock_type' => (isa => 'Str', is => 'rw', predicate => 'has_trial_stock_type', required => 0, default => 'accession');
169 has 'additional_info' => (isa => 'Maybe[HashRef]', is => 'rw', required => 0);
171 # Trial linkage when saving a field trial
173 has 'field_trial_is_planned_to_cross' => (isa => 'Str', is => 'rw', predicate => 'has_field_trial_is_planned_to_cross', required => 0);
174 has 'field_trial_is_planned_to_be_genotyped' => (isa => 'Str', is => 'rw', predicate => 'has_field_trial_is_planned_to_be_genotyped', required => 0);
175 has 'field_trial_from_field_trial' => (isa => 'ArrayRef', is => 'rw', predicate => 'has_field_trial_from_field_trial', required => 0);
176 has 'crossing_trial_from_field_trial' => (isa => 'ArrayRef', is => 'rw', predicate => 'has_crossing_trial_from_field_trial', required => 0);
178 # Trial linkage when saving either a field trial or genotyping plate
180 has 'genotyping_trial_from_field_trial' => (isa => 'ArrayRef', is => 'rw', predicate => 'has_genotyping_trial_from_field_trial', required => 0);
182 # Properties for genotyping plates
184 has 'is_genotyping' => (isa => 'Bool', is => 'rw', required => 0, default => 0, );
185 has 'genotyping_user_id' => (isa => 'Str', is => 'rw');
186 has 'genotyping_project_id' => (isa => 'Int', is => 'rw');
187 has 'genotyping_facility_submitted' => (isa => 'Str', is => 'rw');
188 has 'genotyping_facility' => (isa => 'Str', is => 'rw');
189 has 'genotyping_plate_format' => (isa => 'Str', is => 'rw');
190 has 'genotyping_plate_sample_type' => (isa => 'Str', is => 'rw');
192 # properties for analyses
194 has 'is_analysis' => (isa => 'Bool', is => 'rw', required => 0, default => 0, );
195 has 'analysis_model_protocol_id' => (isa => 'Int|Undef', is => 'rw', required => 0 );
197 # Trial linkage when saving either a sampling trial
199 has 'sampling_trial_from_field_trial' => (isa => 'ArrayRef', is => 'rw', predicate => 'has_sampling_trial_from_field_trial', required => 0);
201 # Properties for sampling trials
203 has 'is_sampling_trial' => (isa => 'Bool', is => 'rw', required => 0, default => 0, );
204 has 'sampling_trial_facility' => (isa => 'Str', is => 'rw');
205 has 'sampling_trial_sample_type' => (isa => 'Str', is => 'rw');
207 has 'owner_id' => (isa => 'Int' , is => 'rw');
209 sub trial_name_already_exists {
210 my $self = shift;
212 if ($self->get_is_analysis()) { return; }
213 my $trial_name = $self->get_trial_name();
214 my $schema = $self->get_chado_schema();
215 if($schema->resultset('Project::Project')->find({name => $trial_name})){
216 return 1;
218 else {
219 return;
223 sub get_breeding_program_id {
224 my $self = shift;
225 my $breeding_program_ref = $self->get_chado_schema->resultset('Project::Project')->find({name=>$self->get_program});
226 if (!$breeding_program_ref ) {
227 print STDERR "UNDEF breeding program " . $self->get_program . "\n\n";
228 return ;
230 my $breeding_program_id = $breeding_program_ref->project_id();
231 #print STDERR "get_breeding_program _id returning $breeding_program_id";
232 return $breeding_program_id;
236 sub save_trial {
237 print STDERR "Check 4.1: ".localtime();
238 my $self = shift;
239 my $chado_schema = $self->get_chado_schema();
240 my %design = %{$self->get_design()};
241 my $trial_name = $self->get_trial_name();
242 $trial_name =~ s/^\s+|\s+$//g; #trim whitespace from both ends
244 # if a trial id is provided, the project row has already been
245 # created by other means, so use that trial_id
247 if (! $self->has_trial_id()) {
249 if (!$trial_name) {
250 print STDERR "Trial not saved: Can't create trial without a trial name\n";
251 return { error => "Trial not saved: Can't create trial without a trial name" };
254 if ($self->trial_name_already_exists()) {
255 print STDERR "Can't create trial: Trial name already exists\n";
256 return { error => "Trial not saved: Trial name already exists" };
259 if (!$self->get_breeding_program_id()) {
260 print STDERR "Can't create trial: Breeding program does not exist\n";
261 return { error => "Trial not saved: breeding program does not exist" };
264 #lookup user by name
265 #my $user_name = $self->get_user_name();
266 #my $dbh = $self->get_dbh();
267 #my $owner_sp_person_id;
268 #$owner_sp_person_id = CXGN::People::Person->get_person_by_username($dbh, $user_name); #add person id as an option.
269 #if (!$owner_sp_person_id) {
270 # print STDERR "Can't create trial: User/owner not found\n";
271 # die "no owner $user_name" ;
274 my $geolocation;
275 my $geolocation_lookup = CXGN::Location::LocationLookup->new(schema => $chado_schema);
276 $geolocation_lookup->set_location_name($self->get_trial_location());
277 $geolocation = $geolocation_lookup->get_geolocation();
278 if (!$geolocation) {
279 print STDERR "Can't create trial: Location not found: ".$self->get_trial_location()."\n";
280 return { error => "Trial not saved: location not found" };
283 my $project_year_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'project year', 'project_property');
284 my $project_planting_date_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'project_planting_date', 'project_property');
285 my $project_design_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'design', 'project_property');
286 my $field_size_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'field_size', 'project_property');
287 my $plot_width_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'plot_width', 'project_property');
288 my $plot_length_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'plot_length', 'project_property');
289 my $field_trial_is_planned_to_be_genotyped_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'field_trial_is_planned_to_be_genotyped', 'project_property');
290 my $field_trial_is_planned_to_cross_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'field_trial_is_planned_to_cross', 'project_property');
291 my $has_plant_entries_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'project_has_plant_entries', 'project_property');
292 my $has_subplot_entries_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'project_has_subplot_entries', 'project_property');
293 my $genotyping_facility_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_facility', 'project_property');
294 my $genotyping_facility_submitted_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_facility_submitted', 'project_property');
295 my $genotyping_plate_format_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_plate_format', 'project_property');
296 my $genotyping_plate_sample_type_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_plate_sample_type', 'project_property');
297 my $genotyping_user_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_user_id', 'nd_experiment_property');
298 my $genotyping_project_name_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_project_name', 'nd_experiment_property');
299 my $trial_stock_type_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'trial_stock_type', 'project_property');
300 my $sampling_facility_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'sampling_facility', 'project_property');
301 my $sampling_trial_sample_type_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'sampling_trial_sample_type', 'project_property');
303 my $project;
304 if ($self->has_trial_id()) {
305 $project = $chado_schema->resultset('Project::Project')->find( { project_id => $self->get_trial_id() });
306 if (! $project) { die "The specified project id ".$self->get_trial_id()." does not exit in the database\n"; }
308 else {
309 $project = $chado_schema->resultset('Project::Project')
310 ->create({
311 name => $trial_name,
312 description => $self->get_trial_description(),
316 my $t = CXGN::Trial->new({
317 bcs_schema => $chado_schema,
318 trial_id => $project->project_id()
321 $t->set_trial_owner($self->get_owner_id);
322 #print STDERR "TRIAL TYPE = ".ref($t)."!!!!\n";
323 my $nd_experiment_type_id;
324 if ($self->get_is_genotyping()) {
325 print STDERR "Generating a genotyping trial...\n";
326 $nd_experiment_type_id = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_layout', 'experiment_type')->cvterm_id();
328 elsif ($self->get_is_analysis()) {
329 print STDERR "Generating an analysis trial...\n";
330 $nd_experiment_type_id = SGN::Model::Cvterm->get_cvterm_row($chado_schema, , 'analysis_experiment', 'experiment_type')->cvterm_id();
332 elsif ($self->get_is_sampling_trial()) {
333 print STDERR "Generating a sampling trial...\n";
334 $nd_experiment_type_id = SGN::Model::Cvterm->get_cvterm_row($chado_schema, , 'sampling_layout', 'experiment_type')->cvterm_id();
336 else {
337 print STDERR "Generating a phenotyping trial...\n";
338 $nd_experiment_type_id = SGN::Model::Cvterm->get_cvterm_row($chado_schema, , 'field_layout', 'experiment_type')->cvterm_id();
340 my $nd_experiment = $chado_schema->resultset('NaturalDiversity::NdExperiment')
341 ->create({
342 nd_geolocation_id => $geolocation->nd_geolocation_id(),
343 type_id => $nd_experiment_type_id,
347 if ($self->get_is_genotyping()) {
348 #print STDERR "Storing user_id and project_name provided by the IGD spreadksheet for later recovery in the spreadsheet download... ".(join ",", ($self->get_genotyping_user_id(), $self->get_genotyping_project_name()))."\n";
349 $nd_experiment->create_nd_experimentprops({
350 $genotyping_user_cvterm->name() => $self->get_genotyping_user_id(),
351 # $genotyping_project_name_cvterm->name() => $self->get_genotyping_project_name(),
354 $project->create_projectprops({
355 $genotyping_facility_cvterm->name() => $self->get_genotyping_facility(),
356 $genotyping_facility_submitted_cvterm->name() => $self->get_genotyping_facility_submitted(),
357 $genotyping_plate_format_cvterm->name() => $self->get_genotyping_plate_format(),
358 $genotyping_plate_sample_type_cvterm->name() => $self->get_genotyping_plate_sample_type()
361 my $genotyping_project_relationship_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'genotyping_project_and_plate_relationship', 'project_relationship');
362 my $relationship_row = $chado_schema->resultset("Project::ProjectRelationship")->create ({
363 object_project_id => $self->get_genotyping_project_id(),
364 subject_project_id => $project->project_id(),
365 type_id => $genotyping_project_relationship_cvterm->cvterm_id()
367 $relationship_row->insert();
369 my $source_field_trial_ids = $t->set_source_field_trials_for_genotyping_trial($self->get_genotyping_trial_from_field_trial);
371 elsif ($self->get_is_analysis()) {
372 if ($self->get_analysis_model_protocol_id) {
373 #link to the saved analysis model
374 $nd_experiment->find_or_create_related('nd_experiment_protocols', {nd_protocol_id => $self->get_analysis_model_protocol_id() });
377 elsif ($self->get_is_sampling_trial()) {
378 $project->create_projectprops({
379 $sampling_facility_cvterm->name() => $self->get_sampling_trial_facility(),
380 $sampling_trial_sample_type_cvterm->name() => $self->get_sampling_trial_sample_type()
383 my $source_field_trial_ids = $t->set_source_field_trials_for_sampling_trial($self->get_sampling_trial_from_field_trial);
385 else {
386 my $source_field_trial_ids = $t->set_field_trials_source_field_trials($self->get_field_trial_from_field_trial);
387 my $genotyping_trial_ids = $t->set_genotyping_trials_from_field_trial($self->get_genotyping_trial_from_field_trial);
388 my $crossing_trial_ids = $t->set_crossing_trials_from_field_trial($self->get_crossing_trial_from_field_trial);
391 $t->set_location($geolocation->nd_geolocation_id()); # set location also as a project prop
392 $t->set_breeding_program($self->get_breeding_program_id);
393 if ($self->get_trial_type){
394 $t->set_project_type($self->get_trial_type);
396 if ($self->get_planting_date()){ # here is local getter
397 $t->set_planting_date($self->get_planting_date); # here is Project.pm unusual setter with writing to db instead of object
399 if ($self->get_harvest_date()){ # here is local getter
400 $t->set_harvest_date($self->get_harvest_date); # here is Project.pm unusual setter with writing to db instead of object
402 if ($self->get_transplanting_date()){ # here is local getter
403 $t->set_transplanting_date($self->get_transplanting_date); # here is Project.pm unusual setter with writing to db instead of object
406 #link to the project
407 $nd_experiment->find_or_create_related('nd_experiment_projects',{project_id => $project->project_id()});
409 $project->create_projectprops({
410 $project_year_cvterm->name() => $self->get_trial_year(),
411 $project_design_cvterm->name() => $self->get_design_type()
413 if ($self->has_field_size && $self->get_field_size){
414 $project->create_projectprops({
415 $field_size_cvterm->name() => $self->get_field_size
418 if ($self->has_plot_width && $self->get_plot_width){
419 $project->create_projectprops({
420 $plot_width_cvterm->name() => $self->get_plot_width
423 if ($self->has_plot_length && $self->get_plot_length){
424 $project->create_projectprops({
425 $plot_length_cvterm->name() => $self->get_plot_length
428 if ($self->has_trial_has_plant_entries && $self->get_trial_has_plant_entries){
429 $project->create_projectprops({
430 $has_plant_entries_cvterm->name() => $self->get_trial_has_plant_entries
433 if ($self->has_trial_has_subplot_entries && $self->get_trial_has_subplot_entries){
434 $project->create_projectprops({
435 $has_subplot_entries_cvterm->name() => $self->get_trial_has_subplot_entries
438 if ($self->has_field_trial_is_planned_to_cross && $self->get_field_trial_is_planned_to_cross){
439 $project->create_projectprops({
440 $field_trial_is_planned_to_cross_cvterm->name() => $self->get_field_trial_is_planned_to_cross
443 if ($self->has_field_trial_is_planned_to_be_genotyped && $self->get_field_trial_is_planned_to_be_genotyped){
444 $project->create_projectprops({
445 $field_trial_is_planned_to_be_genotyped_cvterm->name() => $self->get_field_trial_is_planned_to_be_genotyped
449 if (!$self->get_is_genotyping) {
450 if ($self->has_trial_stock_type && $self->get_trial_stock_type){
451 $project->create_projectprops({
452 $trial_stock_type_cvterm->name() => $self->get_trial_stock_type()
457 my $design_type = $self->get_design_type();
458 if ($design_type eq 'greenhouse') {
459 my $has_plants_cvterm = SGN::Model::Cvterm->get_cvterm_row($chado_schema, 'project_has_plant_entries', 'project_property');
460 $project->create_projectprops({ $has_plants_cvterm->name() => 'varies' });
463 print STDERR "NOW CALLING TRIAl DESIGN STORE...\n";
464 my $trial_design_store = CXGN::Trial::TrialDesignStore->new({
465 bcs_schema => $chado_schema,
466 trial_id => $project->project_id(),
467 trial_name => $trial_name,
468 nd_geolocation_id => $geolocation->nd_geolocation_id(),
469 nd_experiment_id => $nd_experiment->nd_experiment_id(),
470 design_type => $design_type,
471 design => \%design,
472 is_genotyping => $self->get_is_genotyping(),
473 is_analysis => $self->get_is_analysis(),
474 is_sampling_trial => $self->get_is_sampling_trial(),
475 new_treatment_has_plant_entries => $self->get_trial_has_plant_entries,
476 new_treatment_has_subplot_entries => $self->get_trial_has_subplot_entries,
477 operator => $self->get_operator,
478 trial_stock_type => $self->get_trial_stock_type(),
480 my $error;
481 my $validate_design_error = $trial_design_store->validate_design();
482 if ($validate_design_error) {
483 print STDERR "ERROR: $validate_design_error\n";
484 return { error => "Error validating trial design: $validate_design_error." };
485 } else {
486 try {
487 $error = $trial_design_store->store();
488 } catch {
489 print STDERR "ERROR store: $_\n";
490 $error = $_;
493 if ($error) {
494 return { error => $error };
496 return { trial_id => $project->project_id };
503 #######
505 #######