DataflowRule.pm 8.35 KB
Newer Older
1 2 3 4 5 6 7 8 9
# Perl module for Bio::EnsEMBL::Hive::DataflowRule
#
# Creator: Jessica Severin <jessica@ebi.ac.uk>
# Date of creation: 22.03.2004
#
# Copyright EMBL-EBI 2000-2004
#
# You may distribute this module under the same terms as perl itself

10
=pod
11 12

=head1 NAME
Jessica Severin's avatar
Jessica Severin committed
13

14
    Bio::EnsEMBL::Hive::DataflowRule
15 16 17 18

=head1 SYNOPSIS

=head1 DESCRIPTION
Jessica Severin's avatar
Jessica Severin committed
19

20
    A data container object (methods are intelligent getters/setters) that corresponds to a row stored in 'dataflow_rule' table:
21

22
    CREATE TABLE dataflow_rule (
23
        dataflow_rule_id    int(10) unsigned NOT NULL AUTO_INCREMENT,
24 25
        from_analysis_id    int(10) unsigned NOT NULL,
        branch_code         int(10) default 1 NOT NULL,
26
        funnel_dataflow_rule_id  int(10) unsigned default NULL,
27
        to_analysis_url     varchar(255) default '' NOT NULL,
28
        input_id_template   TEXT DEFAULT NULL,
Jessica Severin's avatar
Jessica Severin committed
29

30 31 32 33
        PRIMARY KEY (dataflow_rule_id),
        UNIQUE (from_analysis_id, to_analysis_url)
    );

Leo Gordon's avatar
Leo Gordon committed
34
    A dataflow rule is activated when a Bio::EnsEMBL::Hive::AnalysisJob::dataflow_output_id is called at any moment during a RunnableDB's execution.
35 36 37
    The current RunnableDB's analysis ($from_analysis) and the requested $branch_code (1 by default) define the entry conditions,
    and whatever rules match these conditions will generate new jobs with input_ids specified in the dataflow_output_id() call.
    If input_id_template happens to contain a non-NULL value, it will be used to generate the corresponding intput_id instead.
38

39
    Jessica's remark on the structure of to_analysis_url:
40
        Extended from design of SimpleRule concept to allow the 'to' analysis to be specified with a network savy URL like
41
        mysql://ensadmin:<pass>@ecs2:3361/compara_hive_test/analysis?logic_name='blast_NCBI34'
42 43

=head1 CONTACT
Jessica Severin's avatar
Jessica Severin committed
44

45
  Please contact ehive-users@ebi.ac.uk mailing list with questions/suggestions.
46 47 48 49 50 51 52

=cut


package Bio::EnsEMBL::Hive::DataflowRule;

use strict;
53

54 55 56 57
use Bio::EnsEMBL::Utils::Argument ('rearrange');
use Bio::EnsEMBL::Utils::Exception ('throw');

use Bio::EnsEMBL::Hive::Utils ('stringify');
Leo Gordon's avatar
Leo Gordon committed
58
use Bio::EnsEMBL::Hive::DBSQL::AnalysisAdaptor;
59

60 61 62 63
use base (  'Bio::EnsEMBL::Storable',       # inherit dbID(), adaptor() and new() methods
         );


64
=head2 new
65

66
  Usage   : Bio::EnsEMBL::Hive::DataflowRule->new(-from_analysis => $fromAnalysis, -to_analysis => $toAnalysis, -branch_code => $branch_code);
67
  Function: Constructor for DataflowRule object
Jessica Severin's avatar
Jessica Severin committed
68
  Returns : Bio::EnsEMBL::Hive::DataflowRule
69
  Args    : a rearrange-compatible hash
Jessica Severin's avatar
Jessica Severin committed
70
            
71 72 73
=cut

sub new {
74 75
    my $class = shift @_;

76
    my $self = $class->SUPER::new( @_ );    # deal with Storable stuff
77

78 79
    my ($fromAnalysis, $toAnalysis, $from_analysis_id, $branch_code, $funnel_dataflow_rule_id, $to_analysis_url, $input_id_template ) =
    rearrange( [ qw (FROM_ANALYSIS TO_ANALYSIS FROM_ANALYSIS_ID BRANCH_CODE FUNNEL_DATAFLOW_RULE_ID TO_ANALYSIS_URL INPUT_ID_TEMPLATE) ], @_ );
80 81 82 83 84 85

        # from objects:
    $self->from_analysis( $fromAnalysis )           if(defined($fromAnalysis));
    $self->to_analysis( $toAnalysis )               if(defined($toAnalysis));

        # simple scalars:
86 87 88
    $self->from_analysis_id($from_analysis_id)      if(defined($from_analysis_id));
    $self->to_analysis_url($to_analysis_url)        if(defined($to_analysis_url));
    $self->branch_code($branch_code)                if(defined($branch_code));
89
    $self->funnel_dataflow_rule_id($funnel_dataflow_rule_id)  if(defined($funnel_dataflow_rule_id));
90 91 92
    $self->input_id_template($input_id_template)    if(defined($input_id_template));

    return $self;
93 94
}

95

96
=head2 branch_code
Jessica Severin's avatar
Jessica Severin committed
97

98 99
    Function: getter/setter method for the branch_code of the dataflow rule

100
=cut
Jessica Severin's avatar
Jessica Severin committed
101

102
sub branch_code {
103 104 105 106 107
    my $self = shift @_;

    if(@_) { # setter mode
        $self->{'_branch_code'} = shift @_;
    }
108
    return $self->{'_branch_code'};
109 110
}

111

112
=head2 funnel_dataflow_rule_id
113

114
    Function: getter/setter method for the funnel_dataflow_rule_id of the dataflow rule
115 116 117

=cut

118
sub funnel_dataflow_rule_id {
119 120 121
    my $self = shift @_;

    if(@_) { # setter mode
122
        $self->{'_funnel_dataflow_rule_id'} = shift @_;
123
    }
124
    return $self->{'_funnel_dataflow_rule_id'};
125 126
}

127

128 129 130 131 132 133 134 135 136 137
=head2 input_id_template

    Function: getter/setter method for the input_id_template of the dataflow rule

=cut

sub input_id_template {
    my $self = shift @_;

    if(@_) { # setter mode
138 139
        my $input_id_template = shift @_;
        $self->{'_input_id_template'} = (ref($input_id_template) ? stringify($input_id_template) : $input_id_template),
140 141 142
    }
    return $self->{'_input_id_template'};
}
143

144

145
=head2 from_analysis_id
Jessica Severin's avatar
Jessica Severin committed
146

147 148 149 150
  Arg[1]  : (optional) int $dbID
  Usage   : $self->from_analysis_id($dbID);
  Function: Get/set method for the 'from' analysis objects dbID of this rule.
  Returns : integer
Jessica Severin's avatar
Jessica Severin committed
151
  
152
=cut
Jessica Severin's avatar
Jessica Severin committed
153

154 155 156 157 158 159 160 161 162 163 164
sub from_analysis_id {
  my ($self,$analysis_id) = @_;
  if($analysis_id) {
    $self->{'_from_analysis_id'} = $analysis_id;
    $self->{'_from_analysis'} = undef;
  }
  return $self->{'_from_analysis_id'};
}


=head2 to_analysis_url
Jessica Severin's avatar
Jessica Severin committed
165

166 167 168 169
  Arg[1]  : (optional) string $url
  Usage   : $self->to_analysis_url($url);
  Function: Get/set method for the 'to' analysis objects URL for this rule
  Returns : string
Jessica Severin's avatar
Jessica Severin committed
170
  
171
=cut
Jessica Severin's avatar
Jessica Severin committed
172

173 174 175 176 177 178 179 180 181 182 183
sub to_analysis_url {
  my ($self,$url) = @_;
  if($url) {
    $self->{'_to_analysis_url'} = $url;
    $self->{'_to_analysis'} = undef;
  }
  return $self->{'_to_analysis_url'};
}


=head2 from_analysis
Jessica Severin's avatar
Jessica Severin committed
184

185
  Usage   : $self->from_analysis($analysis);
186
  Function: Get/set method for the condition analysis object of this rule.
187 188
  Returns : Bio::EnsEMBL::Hive::Analysis
  Args    : Bio::EnsEMBL::Hive::Analysis
Jessica Severin's avatar
Jessica Severin committed
189
  
190
=cut
Jessica Severin's avatar
Jessica Severin committed
191

192 193 194 195 196
sub from_analysis {
  my ($self,$analysis) = @_;

  # setter mode
  if( defined $analysis ) {
197
    unless ($analysis->isa('Bio::EnsEMBL::Hive::Analysis')) {
198
      throw(
199
        "from_analysis arg must be a [Bio::EnsEMBL::Hive::Analysis]".
200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218
        "not a [$analysis]");
    }
    $self->{'_from_analysis'} = $analysis;
    $self->{'_from_analysis_id'} = $analysis->dbID;
  }
  
  # lazy load the analysis object if I can
  if(!defined($self->{'_from_analysis'})
     and defined($self->from_analysis_id)
     and defined($self->adaptor))
  {
    $self->{'_from_analysis'} =
      $self->adaptor->db->get_AnalysisAdaptor->fetch_by_dbID($self->from_analysis_id);
  }
  return $self->{'_from_analysis'};
}


=head2 to_analysis
Jessica Severin's avatar
Jessica Severin committed
219

220
  Usage   : $self->to_analysis($analysis);
221
  Function: Get/set method for the goal analysis object of this rule.
222 223
  Returns : Bio::EnsEMBL::Hive::Analysis
  Args    : Bio::EnsEMBL::Hive::Analysis
Jessica Severin's avatar
Jessica Severin committed
224
  
225
=cut
Jessica Severin's avatar
Jessica Severin committed
226

227
sub to_analysis {
228
  my ($self, $analysis_or_nt) = @_;
229

230 231 232
  if( defined $analysis_or_nt ) {
    unless ($analysis_or_nt->can('url')) {
      throw( "to_analysis arg must support 'url' method, '$analysis_or_nt' does not know how to do it");
233
    }
234
    $self->{'_to_analysis'} = $analysis_or_nt;
Jessica Severin's avatar
Jessica Severin committed
235 236 237

    #if the 'from' and 'to' share the same adaptor, then use a simple logic_name
    #for the URL rather than a full network distributed URL
238

Leo Gordon's avatar
Leo Gordon committed
239
    my $ref_rule_adaptor = $self->from_analysis && $self->from_analysis->adaptor;
240

Leo Gordon's avatar
Leo Gordon committed
241
    if($analysis_or_nt->can('logic_name') and $ref_rule_adaptor and ($ref_rule_adaptor == $analysis_or_nt->adaptor)) {
242
      $self->{'_to_analysis_url'} = $analysis_or_nt->logic_name;
243
    } else {
244
      $self->{'_to_analysis_url'} = $analysis_or_nt->url($ref_rule_adaptor->db);
245
    }
246 247 248
  }
  # lazy load the analysis object if I can
  if(!defined($self->{'_to_analysis'}) and defined($self->to_analysis_url)) {
249

Leo Gordon's avatar
Leo Gordon committed
250 251 252 253 254 255
    my $url = $self->to_analysis_url;

    $self->{'_to_analysis'} = $self->adaptor
        ?  $self->adaptor->db->get_AnalysisAdaptor->fetch_by_logic_name_or_url($url)
        :  Bio::EnsEMBL::Hive::DBSQL::AnalysisAdaptor->fetch_by_logic_name_or_url($url)
    or die "Cannot fetch analysis from logic_name or url '$url' for dataflow rule with id='".$self->dbID."'\n";
256

257 258 259 260
  }
  return $self->{'_to_analysis'};
}

261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285

=head2 toString

  Args       : (none)
  Example    : print $df_rule->toString()."\n";
  Description: returns a stringified representation of the rule
  Returntype : string

=cut

sub toString {
    my $self = shift;

    return join('',
            'DataflowRule(dbID=',
            ($self->dbID || '?'),
            ($self->funnel_dataflow_rule_id ? ' --|| '.$self->funnel_dataflow_rule_id : ''),
            '): [#',
            $self->branch_code,
            '] ',
            $self->from_analysis->logic_name,
            ' -> ',
            $self->to_analysis_url,
            ($self->input_id_template ? (' WITH TEMPLATE: '.$self->input_id_template) : ''),
    );
286 287
}

288

289 290
1;