Mercurial > repos > cpt > cpt_psm_prep
view lib/CPT/GalaxyGetOpt.pm @ 1:d724f34e671d draft default tip
planemo upload commit 94b0cd1fff0826c6db3e7dc0c91c0c5a8be8bb0c
author | cpt |
---|---|
date | Mon, 05 Jun 2023 02:50:07 +0000 |
parents | |
children |
line wrap: on
line source
package CPT::GalaxyGetOpt; use CPT::ParameterGroup; use autodie; use File::Spec::Functions qw[ catfile catdir ]; use Carp; no warnings; use Moose; has 'appdesc' => ( is => 'rw', isa => 'Str', default => sub { 'No application description provided' } ); has 'appid' => ( is => 'rw', isa => 'Str', default => sub { "unknown_app_$0" } ); has 'appname' => ( is => 'rw', isa => 'Str', default => sub { "Unnamed application $0"} ); has 'appvers' => ( is => 'rw', isa => 'Str', default => sub { '0.0.1' } ); has 'registered_outputs' => ( is => 'rw', isa => 'HashRef' ); has 'opt' => ( is => 'rw', isa => 'Any'); has filetype_detector => ( is => 'rw', isa => 'Any', ); sub getOptions { my ( $self, %passed_opts ) = @_; require Getopt::Long::Descriptive; # these get pushed through, thankfully. This way we can manually check for --genenrate_galaxy_export and exit slightly earlier. my %args = map { $_ => 1 } @ARGV; # Sections passed to us my @script_args = @{ $passed_opts{'options'} }; my %defaults = @{ $passed_opts{'defaults'} }; # Output Files Stuff my @getopt_formatted_outputs; my %outputs; # This is originally an array of output files. We transform to a hash for # easier lookup foreach(@{$passed_opts{'outputs'}}){ # Grab name/desc/opts my ($name, $desc, $opts) = @{$_}; $outputs{$name} = { description => $desc, options => $opts, required => 1, }; my %tmp_opts_fix = %{$opts}; $tmp_opts_fix{required} = 1; $tmp_opts_fix{validate} = 'File/Output'; push(@getopt_formatted_outputs, [$name, $desc, \%tmp_opts_fix]); # Adds the {name}_files_path special parameter my %fp_opts = %{$opts}; $fp_opts{hidden} = 1; $fp_opts{value} = "${name}.files_path"; $fp_opts{default} = "${name}.files_path"; $fp_opts{required} = 1; $fp_opts{_galaxy_specific} = 1; $fp_opts{validate} = "String"; #$fp_opts{_show_in_galaxy} = 0; my $desc2 = "Associated HTML files for $name"; my $name2 = "${name}_files_path"; my @files_path = ($name2, $desc2, \%fp_opts); push(@getopt_formatted_outputs, \@files_path); # Adds the {name}_format special parameter my %fp_opts3 = %{$opts}; #$fp_opts3{hidden} = 1; $fp_opts3{default} = $fp_opts3{"default_format"}; $fp_opts3{validate} = "File/OutputFormat"; $fp_opts{required} = 1; #$fp_opts3{_galaxy_specific} = 1; #$fp_opts3{_show_in_galaxy} = 0; my $desc3 = "Associated Format for $name"; my $name3 = "${name}_format"; my @files_path3 = ($name3, $desc3, \%fp_opts3); push(@getopt_formatted_outputs, \@files_path3); # Adds the {name}_files_path special parameter my %fp_opts4 = %{$opts}; $fp_opts4{hidden} = 1; $fp_opts4{value} = "${name}.id"; $fp_opts4{default} = "${name}.id"; $fp_opts4{validate} = "String"; $fp_opts4{_galaxy_specific} = 1; #$fp_opts4{_show_in_galaxy} = 0; my $desc4 = "Associated ID Number for $name"; my $name4 = "${name}_id"; my @files_path4 = ($name4, $desc4, \%fp_opts4); push(@getopt_formatted_outputs, \@files_path4); } $self->registered_outputs(\%outputs); # Store the application's name and description if($defaults{appdesc}){ $self->appdesc($defaults{appdesc}); } if($defaults{appid}){ $self->appid($defaults{appid}); } if($defaults{appname}){ $self->appname($defaults{appname}); } if($defaults{appvers}){ $self->appvers($defaults{appvers}); } my $usage_desc; if ( $self->appname() && $self->appdesc() ) { $usage_desc = sprintf( "%s: %s\n%s [options] <some-arg>", $self->appname(), $self->appdesc(), $0 ); } # Individual parameter parsers require CPT::Parameter; # Which are stored in a collection of them require CPT::ParameterCollection; my $parameterCollection = CPT::ParameterCollection->new(); $parameterCollection->push_params( [ #['Standard Options'], #@extra_params, #[], ['outfile_supporting' , 'File or folder to output to, necessary when (class == Report || multiple calls to classyReturnResults || multiple standalone output files)' , { hidden => 1, validate => 'String', default => '__new_file_path__', _galaxy_specific => 1, _show_in_galaxy => 0 }], ['galaxy' , 'Run with galaxy-specific overrides' , {validate => 'Flag' , hidden=>1, _galaxy_specific => 1, _show_in_galaxy => 0}], ['generate_galaxy_xml' , 'Generate a compatible galaxy-xml file. May need editing' , {validate => 'Flag' , hidden=>1, _galaxy_specific => 1, _show_in_galaxy => 0}], [], ['Script Options'], ] ); # If there's a default specified, we should apply that. foreach (@script_args) { # If it's an array, push as is, because either it's old style/label/empty # However, this doesn't allow setting defaults for things that aren't parameters # and it won't set defaults for old style if ( ref $_ eq 'ARRAY' ) { $parameterCollection->push_param($_); }elsif( ref $_ eq 'HASH'){ my $pG = CPT::ParameterGroup->new(); $pG->set_data($_); $parameterCollection->push_group($pG); } } # Our magic output files stuff $parameterCollection->push_params( [ [], ['Output Files'], @getopt_formatted_outputs, ] ); # Other standard options like verbosity/version/etc $parameterCollection->push_params( [ [], ['Other Standard Options'], ['verbose|v', 'Be more verbose', {validate => 'Flag', _show_in_galaxy => 0}], ['version', 'Print version information', {validate => 'Flag', _show_in_galaxy => 0}], ['help', 'Print usage message and exit', {validate => 'Flag', _show_in_galaxy => 0}], ], ); # If we want the galaxy_xml, do that before the reduction step is called. if ( $args{'--version'} ) { print $self->appvers() . "\n"; exit 1; } # If we want the galaxy_xml, do that before the reduction step is called. if ( $args{'--generate_galaxy_xml'} ) { require CPT::Galaxy; my $galaxy_xml_generator = CPT::Galaxy->new(); $galaxy_xml_generator->gen( full_options => $parameterCollection, appdesc => $self->appdesc(), appid => $self->appid(), appname => $self->appname(), appvers => $self->appvers(), defaults => $passed_opts{'defaults'}, outputs => $passed_opts{'outputs'}, tests => $passed_opts{'tests'}, ); exit 1; } if( $args{'--gen_test'} ){ require CPT::GenerateTests; my $tgen = CPT::GenerateTests->new(); if(defined $passed_opts{'tests'}){ print $tgen->gen(@{$passed_opts{'tests'}}); }else{ print $tgen->gen_empty(); } exit 0; } # Now that the options_spec is complete, we reduce to something getopt will be happy with my @getopt_spec = $parameterCollection->getopt(); #print STDERR Dumper \@getopt_spec; #exit 1; # It would be nice if there was a way to ensure that it didn't die here... # Execute getopt my ( $local_opt, $usage ) = Getopt::Long::Descriptive::describe_options( $usage_desc, @getopt_spec ); $self->opt($local_opt); # Now that we've gotten the user's options, we need to copy their values back to our ParameterCollection $parameterCollection->populate_from_getopt($self->opt()); # If they want help, print + exit if ( $self->opt && $self->opt->help ) { print $usage; exit 1; } # Validate their choices if ( $parameterCollection->validate($self->opt) ) { return $self->opt; # Easy access for the script, don't want them to have to deal with PC (just yet) } else { # Some params failed to validate, so we die. croak "Validation errors were found so cannot continue"; } } no Moose; 1; __END__ =pod =encoding UTF-8 =head1 NAME CPT::GalaxyGetOpt =head1 VERSION version 1.99.4 =head2 getOptions my $ggo = CPT::GalaxyGetOpt->new(); my $options = $ggo->getOptions( 'options' => [ [ 'file', 'Input file', { validate => 'File/Input' } ], [ "option" => "Select an option!", { validate => 'Option', options => \%options, multiple => 1, } ], [ "float" => "I'm a float", { validate => 'Float' } ], [ "int" => "I'm an int", { validate => 'Int', default => [42, 34], required => 1, multiple => 1 } ], [], ['New section'], [ "string" => "I'm a simple string", { validate => 'String' } ], [ 'flag' => 'This is a flag', { validate => 'Flag' } ], ], 'outputs' => [ [ 'my_output_data', 'Output TXT File', { validate => 'File/Output', required => 1, default => 'out', data_format => 'text/plain', default_format => 'TXT', } ], ], 'defaults' => [ 'appid' => 'TemplateScript', 'appname' => 'Template', 'appdesc' => 'A basic template for a new CPT application', 'appvers' => '1.94', ], 'tests' => [ { test_name => "Default", params => { }, outputs => { 'my_output_data' => ["out.txt", 'test-data/outputs/template.default.txt' ], }, }, { test_name => "Option A specified", params => { 'int', '10000', }, outputs => { 'my_output_data' => ["out.txt", 'test-data/outputs/template.A.txt' ], }, }, ], ); my @data; foreach(qw(file int string option float flag)){ # Create a 2D array of all of our optoins push(@data, [ $_, $options->{$_}]); } my %table = ( 'Sheet1' => { header => [qw(Key Value)], data => \@data, } ); # And store it to file! use CPT::OutputFiles; my $crr_output = CPT::OutputFiles->new( name => 'my_output_data', GGO => $ggo, ); $crr_output->CRR(data => \%table); Gets command line options, and prints docs. Very convenient, removes the burden of writing any Getopt code from you. =head3 Default Options Provided =over 4 =item * help, man - cause an early exit and printing of the POD for your script. =item * verbose - flag to make the script verbose. Will print everything that is sent to returnResults. Individual scripts should take advantage of this option =back =head3 Advanced Options Provided =over 4 =item C<--generate_galaxy_xml> Generates valid XML for the tool for use in Galaxy =item C<--gen_test> Generates code to test the script using specified test data =back =head1 AUTHOR Eric Rasche <rasche.eric@yandex.ru> =head1 COPYRIGHT AND LICENSE This software is Copyright (c) 2014 by Eric Rasche. This is free software, licensed under: The GNU General Public License, Version 3, June 2007 =cut