3 See the NOTICE file distributed with
this work
for additional information
4 regarding copyright ownership.
6 Licensed under the Apache License, Version 2.0 (the
"License");
7 you may not use
this file except in compliance with the License.
8 You may obtain a copy of the License at
12 Unless required by applicable law or agreed to in writing, software
13 distributed under the License is distributed on an
"AS IS" BASIS,
14 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 See the License
for the specific language governing permissions and
16 limitations under the License.
23 Please email comments or questions to the
public Ensembl
24 developers list at <http:
26 Questions may also be sent to the Ensembl help desk at
37 my $dbID = $storable_object->
dbID();
38 my $adaptor = $storable_object->adaptor();
39 if ( $storable_object->is_stored($db_adaptor) ) { ... }
43 This is a storable base
class. All objects which are storable
44 in the database should inherit from
this class. It provides two
45 getter/setters: dbID() adaptor(). And a is_stored() method that can be
46 used to determine if an
object is already stored in a database.
56 use
Bio::
EnsEMBL::Utils::Exception qw(throw warning);
57 use
Bio::
EnsEMBL::Utils::Argument qw(rearrange);
58 use
Bio::
EnsEMBL::Utils::Scalar qw(assert_ref);
59 use Scalar::Util qw(weaken isweak);
63 Arg [-ADAPTOR] :
Bio::
EnsEMBL::DBSQL::BaseAdaptor
64 Arg [-dbID] : database internal
id
65 Caller : internal calls
66 Description : create a new
Storable object
68 Exceptions : Adaptor not a
Bio::
EnsEMBL::DBSQL::BaseAdaptor
75 my $class = ref($caller) || $caller;
77 my ($adaptor, $dbID) = rearrange([
'ADAPTOR',
'dbID'],@_);
80 if(!ref($adaptor) || !$adaptor->isa(
'Bio::EnsEMBL::DBSQL::BaseAdaptor')) {
81 throw(
'-ADAPTOR argument must be a Bio::EnsEMBL::DBSQL::BaseAdaptor');
85 my $self = bless({
'dbID' => $dbID}, $class);
86 $self->adaptor($adaptor);
92 Arg [1] : hashref to be blessed
94 This is a very quick constructor that requires
internal knowledge
95 of the
class. This is used in speed critical sections of the code
96 where many objects need to be created quickly.
99 Caller : general, subclass constructors
108 my $self = bless $hashref, $class;
109 weaken($self->{adaptor})
if ( ! isweak($self->{adaptor}) );
116 Description: getter/setter
for the database
internal id
119 Caller : general, set from adaptor on store
126 $self->{
'dbID'} = shift
if(@_);
127 return $self->{
'dbID'};
135 Description: get/set
for this objects Adaptor
138 Caller : general, set from adaptor on store
144 my ($self, $adaptor) = @_;
146 if(defined $adaptor) {
147 assert_ref($adaptor,
'Bio::EnsEMBL::DBSQL::BaseAdaptor',
'adaptor');
148 $self->{adaptor} = $adaptor;
149 weaken($self->{adaptor});
152 $self->{adaptor} = undef;
155 return $self->{adaptor}
164 Example : do_something
if($object->is_stored($db));
165 Description: Returns
true if this object is stored in the provided database.
166 This works under the assumption that
if the adaptor and dbID are
167 set and the database of the adaptor shares the port, dbname and
168 hostname with the provided database,
this object is stored in
171 Exceptions :
throw if dbID is set but adaptor is not
172 throw if adaptor is set but dbID is not
173 throw if incorrect argument is passed
174 Caller : store methods
179 my $message_only_once =1;
185 if($db and $db->isa(
'Bio::EnsEMBL::DBSQL::DBAdaptor')) {
188 if(!$db || !ref($db) || !$db->isa(
'Bio::EnsEMBL::DBSQL::DBConnection')) {
189 throw(
'db argument must be a Bio::EnsEMBL::DBSQL::DBConnection');
192 my $adaptor = $self->{
'adaptor'};
193 my $dbID = $self->{
'dbID'};
195 if($dbID && !$adaptor) {
196 if($message_only_once){
197 warning(
"Storable object has a dbID but not an adaptor.\n" .
198 'Storable objects must have neither OR both.');
199 $message_only_once = 0;
204 if($adaptor && !$dbID) {
205 if($message_only_once){
206 warning(
"Storable object has an adaptor but not a dbID.\n".
207 "Storable objects must have neither OR both.");
208 $message_only_once = 0;
213 return 0
if (!$adaptor && !$dbID);
215 my $cur_db = $adaptor->dbc();
218 # Databases are the same if they share the same port, host and username
220 if ( ($db->port()||
'') eq ($cur_db->port()||
'')
221 && ($db->host()||
'') eq ($cur_db->host()||
'')
222 && $db->dbname() eq $cur_db->dbname() )
230 sub get_all_DAS_Features{
231 my ($self, $slice) = @_;
233 $self->{_das_features} ||= {}; # Cache
234 $self->{_das_styles} ||= {}; # Cache
235 $self->{_das_segments} ||= {}; # Cache
240 foreach my $dasfact( @{$self->get_all_DASFactories} ){
241 my $dsn = $dasfact->adaptor->dsn;
242 my $name = $dasfact->adaptor->name;
243 my $url = $dasfact->adaptor->url;
245 # Construct a cache key : SOURCE_URL/TYPE
246 # Need the type to handle sources that serve multiple types of features
248 my ($type) = ref($dasfact->adaptor->mapping) eq 'ARRAY' ? @{$dasfact->adaptor->mapping} : $dasfact->adaptor->mapping;
249 $type ||=$dasfact->adaptor->type;
250 my $key = join(
'/', $name, $type);
252 if( $self->{_das_features}->{$key} ){ # Use cached
253 $das_features{$name} = $self->{_das_features}->{$key};
254 $das_styles{$name} = $self->{_das_styles}->{$key};
255 $das_segments{$name} = $self->{_das_segments}->{$key};
256 }
else { # Get fresh data
258 my ($featref, $styleref, $segref) = ($type =~ /^ensembl_location/) ? ($dasfact->fetch_all_Features( $slice, $type )) : $dasfact->fetch_all_by_ID( $self );
260 $self->{_das_features}->{$key} = $featref;
261 $self->{_das_styles}->{$key} = $styleref;
262 $self->{_das_segments}->{$key} = $segref;
263 $das_features{$name} = $featref;
264 $das_styles{$name} = $styleref;
265 $das_segments{$name} = $segref;
269 return (\%das_features, \%das_styles, \%das_segments);