2012-05-27 2 views
2

Я пытаюсь найти чистый способ OO для реализации проблемы, с которой я столкнулся с DBIx :: Class. У меня есть таблица User, которая содержит информацию, общую для всех пользователей. Каждый пользователь может также иметь много разных классов, каждый из которых имеет свою уникальную требуемую информацию. Например, Пользователь может быть Администратором и Автором. Существуют отдельные таблицы для классов администратора и автора.DBIx :: Класс абстрактный родительский ResultSet

Что я хочу сделать, это создать общий базовый класс для доступа ко всем классам из пользовательского объекта. Таким образом, базовый класс называется Schema :: UserClass и двумя подклассами Schema :: UserClass :: Admin и Schema :: UserClass :: Author. То, что я хотел бы быть в состоянии сделать такие вещи, как:

# Get current user 
my $user = MyApp->get_user(); 

# Get user classes 
my @classes = $user->classes->all(); 
for my $class (@classes) { 
    # Print class name 
    print $class->name; 
} 

Аналогичная проблема представлена ​​здесь: http://dbix-class.35028.n2.nabble.com/OO-advice-do-a-subclass-do-something-else-td5614176.html. Но решение является подходом на мой взгляд, поскольку для этого требуется добавить новые отношения для каждого класса.

Я не вижу, как отношения могут быть сделаны базовому классу со знанием всех подклассов. Любая помощь приветствуется.

ответ

0

Решение, которое я нашел, не очень хорошо, но оно действительно работает. Если я получу время, я могу консолидировать этот код в модуле CPAN, чтобы сделать его немного красивее.

package ParentSchema::Result::Class; 

use strict; 
use warnings; 

use parent 'DBIx::Class::Core'; 

__PACKAGE__->add_columns(
    "user_id", 
    { 
    data_type => "integer", 
    size => 32, 
    is_foreign_key => 1, 
    is_auto_increment => 0, 
    is_nullable => 0, 
    default_value => '', 
    }, 
); 

# stuff common to all schemas 

__PACKAGE__->belongs_to(
    "user", 
    "Schema::Result::User", 
    { 'foreign.id' => "self.user_id" }, 
    { is_deferrable => 1, on_delete => "CASCADE", on_update => "CASCADE" }, 
); 

1; 

package Schema::Result::Class::Author 

use strict; 
use warnings; 

use parent 'ParentSchema::Class'; 

__PACKAGE__->table('class_author'); 

# class spesific stuff 

__PACKAGE__->meta->make_immutable; 

1; 


package Schema::Result::User; 

use strict; 
use warnings; 

use parent 'DBIx::Class::Core'; 

use Module::Pluggable::Object; 
use String::CamelCase qw(decamelize); 

__PACKAGE__->add_columns(
    "id", 
    { 
    data_type => "integer", 
    size => 32, 
    is_auto_increment => 1, 
    is_nullable => 0, 
    default_value => '', 
    }, 
); 

my $class_path = 'Schema::Result::Class'; 

my $mp = Module::Pluggable::Object->new(
    search_path => [ $class_path ] 
); 
my @class_plugins = $mp->plugins; 

foreach my $class (@class_plugins) { 
    (my $name = $class) =~ s/^\Q${class_path}\E//; 
    __PACKAGE__->might_have(
    decamelize($name), 
    $class, 
    { "foreign.user_id" => "self.id" }, 
    { cascade_copy => 0, cascade_delete => 0 }, 
); 
} 

__PACKAGE__->meta->make_immutable; 

1; 

 Смежные вопросы

  • Нет связанных вопросов^_^