Perl Rose:: БД нестатическая регистрация источника данных
Я пишу Perl-приложение, которое использует Rose::DB для абстракции постоянства, но я сталкиваюсь с проблемой инициализации моего подкласса Rose::DB со значениями из файла конфигурации.
В документации всегда представлены жестко закодированные примеры, например:
# Register your lone data source using the default type and domain
__PACKAGE__->register_db(
driver => 'pg',
database => 'my_db',
host => 'localhost',
username => 'joeuser',
password => 'mysecret',
);
Однако для удобства обслуживания я хотел бы заполнить эти значения из отдельного файла конфигурации во время выполнения.
Используемый раздел файла конфигурации (Config::General format):
<database>
active_domain development
<db_domain development>
db_driver mysql
db_name stats_dev
db_host localhost
db_user stats_dev
db_password stats_dev
</db_domain>
<db_domain production>
db_driver mysql
db_name stats_prd
db_host localhost
db_user stats_prd
db_password stats_prd
</db_domain>
</database>
Подкласс My Rose::DB, с методом инициализатора:
package Utils::DBUtils;
use strict;
use base qw(Rose::DB);
__PACKAGE__->use_private_registry;
sub registerAllDBs {
my ($self,$config_obj) = @_;
my $db_config = $config_obj->getDatabaseSection(); ## subconfig starts here
my $def_domain = $db_config->{"active_domain"};
__PACKAGE__->default_domain($def_domain);
__PACKAGE__->default_type('main');
my $db_domains = $db_config->{'db_domain'};
foreach my $domain (keys %$db_domains) {
my $domain_conf = $db_domains->{$domain};
__PACKAGE__->register_db(
domain => $domain,
type => __PACKAGE__->default_type(),
driver => $domain_conf->{'db_driver'},
database => $domain_conf->{'db_name'},
host => $domain_conf->{'db_host'},
username => $domain_conf->{'db_user'},
password => $domain_conf->{'db_password'}
);
}
}
1;
Затем в моем основном скрипте я вызываю метод один раз, чтобы зарегистрировать все источники данных:
Utils::DBUtils->registerAllDBs($conf);
Все мои постоянные объекты наследуются от пакета PersistentObject, который инициализирует объект DB с помощью:
sub init_db { Utils::DBUtils->new() }
Тем не менее, это не работает, как я ожидал. Я получаю сообщение об ошибке во время компиляции:
No database information found for domain 'default' and type 'default' and no driver type specified in call to Utils::DBUtils->new(...) at PersistentObject.pm line 9
Кажется, проблема в том, что Rose::DB ожидает иметь полные данные конфигурации во время компиляции, что было бы невозможно предоставить, поскольку они получены из файла конфигурации.
Я что-то здесь упускаю? Разве нельзя динамически инициализировать объект Rose::DB?
1 ответ
Мне удалось заставить его работать, кажется, что подклассу Rose::DB нужен как минимум один оператор register_db во время компиляции.
(Уродливое) решение было добавить
__PACKAGE__->register_db(
driver => 'mysql',
database => 'fake',
host => 'localhost',
username => 'fake',
password => 'fake'
);
к определению пакета.