Bio-DB-SeqFeature

 view release on metacpan or  search on metacpan

lib/Bio/DB/SeqFeature/Store/GFF3Loader.pm  view on Meta::CPAN

  # If DEBUG != 0, any Parent attribute is also copied over (as 'parent_id')
  $unreserved->{parent_id} = \@parent_ids   if DEBUG && @parent_ids;

  # POSSIBLY A PERMANENT HACK -- TARGETS BECOME ALIASES
  # THIS IS TO ALLOW FOR TARGET-BASED LOOKUPS
  if (exists $reserved->{Target} && !$self->{noalias_target}) {
    my %aliases = map {$_=>1} @{$unreserved->{Alias}};
    for my $t (@{$reserved->{Target}}) {
      (my $tc = $t) =~ s/\s+.*$//;  # get rid of coordinates
      $name ||= $tc;
      push @{$unreserved->{Alias}},$tc unless $name eq $tc || $aliases{$tc};
    }
  }

  ($refname,$start,$end,$strand) = $self->_remap($refname,$start,$end,$strand) or return;

  my @args = (-display_name => $name,
	      -seq_id       => $refname,
	      -start        => $start,
	      -end          => $end,
	      -strand       => $strand || 0,
	      -score        => $score,
	      -phase        => $phase,
	      -primary_tag  => $method || 'feature',
	      -source       => $source,
	      -tag          => $unreserved,
	      -attributes   => $unreserved,
	     );

  # Here's where we handle feature lines that have the same ID (multiple locations, not
  # parent/child relationships)

  my $old_feat;

  # Current feature is the same as the previous feature, which hasn't yet been loaded
  if (defined $ld->{CurrentID} && $ld->{CurrentID} eq $feature_id) {
    $old_feat = $ld->{CurrentFeature};
  }

  # Current feature is the same as a feature that was loaded earlier
  elsif (defined(my $id = $self->{load_data}{Helper}->local2global($feature_id))) {
    $old_feat = $self->fetch($feature_id)
      or $self->warn(<<END);
ID=$feature_id has been used more than once, but it cannot be found in the database.
This can happen if you have specified fast loading, but features sharing the same ID
are not contiguous in the GFF file. This will be loaded as a separate feature.
Line $.: "$_"
END
  }

  # contiguous feature, so add a segment
  warn $old_feat if defined $old_feat and !ref $old_feat;
  if (defined $old_feat) {
      # set this to 1 to disable split-location behavior
      if (0 && @parent_ids) {                  # If multiple features are held together by the same ID
	  $feature_id = $ld->{TemporaryID}++;  # AND they have a Parent attribute, this causes an undesirable
      }                                        # additional layer of aggregation. Changing the ID fixes this.
      elsif       (
	  $old_feat->seq_id ne $refname || 
	  $old_feat->start  != $start || 
	  $old_feat->end    != $end # make sure endpoints are distinct
	  )
      {
	  $self->add_segment($old_feat,$self->sfclass->new(@args));
	  return;
      }
  }

  # we get here if this is a new feature
  # first of all, store the current feature if it is there
  $self->store_current_feature() if defined $ld->{CurrentID};

  # now create the new feature
  # (index top-level features only if policy asks us to)
  my $feature = $self->sfclass->new(@args);
  $feature->object_store($self->store) if $feature->can('object_store');  # for lazy table features
  $ld->{CurrentFeature} = $feature;
  $ld->{CurrentID}      = $feature_id;

  my $top_level = !@parent_ids;
  my $has_id    = defined $reserved->{ID}[0];
  $index_it   ||= $top_level;

  my $helper = $ld->{Helper};
  $helper->indexit($feature_id=>1)  if $index_it;
  $helper->toplevel($feature_id=>1) if !$self->{fast} 
                                       && $top_level;  # need to track top level features


  # remember parentage
  for my $parent (@parent_ids) {
      $helper->add_children($parent=>$feature_id);
  }

}

sub invalid_gff {
    my $self = shift;
    my $line = shift;
    $self->throw("invalid GFF line at line $self->{load_data}{line}.\n".$line);
}

=item allow_whitespace

   $allow_it = $loader->allow_whitespace([$newvalue]);

Get or set the allow_whitespace flag. If true, then GFF3 files are
allowed to be delimited with whitespace in addition to tabs.

=cut

sub allow_whitespace {
    my $self = shift;
    my $d    = $self->{allow_whitespace};
    $self->{allow_whitespace} = shift if @_;
    $d;
}

=item store_current_feature

  $loader->store_current_feature()



( run in 1.002 second using v1.01-cache-2.11-cpan-39bf76dae61 )