DBIx :: Class Ошибка при создании и создании

Я использую DBIx :: Class в проекте Dancer2 для связи с базой данных MySQL. В этом проекте у меня есть набор результатов ClassInfo, из которого я могу без проблем выбирать, искать, удалять и обновлять.

Однако всякий раз, когда я пытаюсь добавить новую строку, через:

my $new_class = $SCHEMA->resultset( 'ClassInfo' )->new({});

or

my $new_class = $SCHEMA->resultset( 'ClassInfo' )->create({});

(данные опущены для краткости), я получаю следующую ошибку:

DBIx::Class::Row::has_column_loaded(): Can't call has_column data as class method at /home/jlamey/src/dancer_projects/QP/bin/../lib/QP.pm line 2109

2104      {
2105        flash error => sprintf( 'Class <strong>%s</strong> already exists.' );
2106        redirect '/admin/manage_classes/classes';
2107      }
2108    
2109      my $new_class = $SCHEMA->resultset( 'ClassInfo' )->new(
2110        {
2111          title                => body_parameters->get( 'title' ),
2112          description          => body_parameters->get( 'description' ),
2113          class_group_id       => body_parameters->get( 'class_group_id' ),
2114          class_subgroup_id    => ( body_parameters->get( 'class_subgroup_id' )    ? body_parameters->get( 'class_subgroup_id' )    : undef ),

Я даже попытался отправить как «новую», так и «создать» команду с нулевыми данными, просто чтобы убедиться, что это не данные, вызывающие ошибку, и ошибка по-прежнему возникает.

Таблица, в которую он пытается записать, выглядит так:

+----------------------+---------------------+------+-----+---------+----------------+
| Field                | Type                | Null | Key | Default | Extra          |
+----------------------+---------------------+------+-----+---------+----------------+
| id                   | int(8) unsigned     | NO   | PRI | NULL    | auto_increment |
| class_group_id       | int(8) unsigned     | NO   | MUL | 1       |                |
| class_subgroup_id    | int(8) unsigned     | YES  | MUL | NULL    |                |
| teacher_id           | int(8) unsigned     | YES  | MUL | NULL    |                |
| secondary_teacher_id | int(8) unsigned     | YES  | MUL | NULL    |                |
| tertiary_teacher_id  | int(8) unsigned     | YES  | MUL | NULL    |                |
| title                | varchar(255)        | NO   | MUL |         |                |
| description          | text                | NO   |     | NULL    |                |
| num_sessions         | varchar(255)        | YES  |     | NULL    |                |
| fee                  | varchar(100)        | YES  |     | NULL    |                |
| skill_level          | varchar(255)        | YES  |     | NULL    |                |
| is_also_embroidery   | tinyint(1) unsigned | YES  | MUL | 0       |                |
| is_also_club         | tinyint(1) unsigned | YES  | MUL | 0       |                |
| show_club            | tinyint(1) unsigned | YES  |     | 0       |                |
| image_filename       | varchar(255)        | YES  |     | NULL    |                |
| supply_list_filename | varchar(255)        | YES  |     | NULL    |                |
| no_supply_list       | tinyint(1) unsigned | YES  |     | 0       |                |
| always_show          | tinyint(1) unsigned | YES  |     | 0       |                |
| anchor               | varchar(5)          | YES  |     | NULL    |                |
| new                  | tinyint(1) unsigned | YES  |     | 0       |                |
+----------------------+---------------------+------+-----+---------+----------------+

И набор результатов выглядит так:

package QP::Schema::Result::ClassInfo;

use base qw/DBIx::Class::Core/;

__PACKAGE__->table( 'classes' );

__PACKAGE__->add_columns(
                          id =>
                          {
                            data_type         => 'integer',
                            size              => 8,
                            is_nullable       => 0,
                            is_auto_increment => 1,
                          },
.
.
.
                          new =>
                          {
                            data_type         => 'boolean',
                            is_nullable       => 0,
                            default_value     => 0,
                          },
                        );

__PACKAGE__->set_primary_key( 'id' );

__PACKAGE__->belongs_to( teacher     => 'QP::Schema::Result::Teacher',       'teacher_id' );
__PACKAGE__->belongs_to( teacher2    => 'QP::Schema::Result::Teacher',       'secondary_teacher_id' );
__PACKAGE__->belongs_to( teacher3    => 'QP::Schema::Result::Teacher',       'tertiary_teacher_id' );
__PACKAGE__->belongs_to( class_group => 'QP::Schema::Result::ClassGroup',    'class_group_id' );
__PACKAGE__->belongs_to( subgroup    => 'QP::Schema::Result::ClassSubgroup', 'class_subgroup_id' );

__PACKAGE__->has_many( dates => 'QP::Schema::Result::ClassDate', 'class_id' );

1;

Я в растерянности; ни у одного другого набора результатов в этом проекте нет этой проблемы, и все они построены одинаково.

Заранее благодарю за любую помощь. - Джейсон


person Armitige3    schedule 05.09.2017    source источник
comment
Помимо реальной проблемы, эти три столбца для идентификаторов учителей - плохой дизайн. Вероятно, вам следует нормализовать свою базу данных и использовать отношение n-m, чтобы у вас могло быть произвольное количество учителей в классе.   -  person simbabque    schedule 05.09.2017
comment
Не могли бы вы подробнее объяснить, что вы имеете в виду? Я думаю, что понимаю концепцию, но не уверен, что понимаю ее. Есть таблица «учителей», и эти три столбца ссылаются на эту таблицу, поскольку в каждом списке классов может быть от 0 до 3 учителей.   -  person Armitige3    schedule 05.09.2017
comment
Это не связано с проблемой, которую вы наблюдаете, но конечно. Ваши таблицы не нормализованы. У вас есть пустые столбцы для каждой записи класса (строки), в которой только от 0 до 2 учителей. Только если все три поля заполнены, используется пространство. Это приводит к раздуванию базы данных. Кроме того, если вам по какой-то причине придется добавить четвертого учителя, вам придется пойти и изменить DDL, чтобы добавить еще один столбец, что приведет к операции записи для каждой отдельной строки в этой таблице, чтобы добавить поле NULL. Это очень неэффективно. Вместо этого у вас должна быть таблица для classes_teachers, которая отображает эти отношения ...   -  person simbabque    schedule 05.09.2017
comment
Эти новые таблицы создают отношение N: M, где в каждом выступлении может быть произвольное количество от нуля или более учителей, и каждый учитель может вести более одного класса. При необходимости на уровне приложения можно добавить не более трех на класс. Для DBIC это будет has_many отношение, и у вас будет дополнительный ResultClass. Но в целом это намного более эффективный дизайн.   -  person simbabque    schedule 05.09.2017
comment
Ах, я понимаю, о чем вы говорите. Вместо этого используйте сопоставление отношений «многие ко многим». Да, в этом гораздо больше смысла. И это довольно простое изменение. Спасибо что подметил это.   -  person Armitige3    schedule 05.09.2017
comment
Кроме того, почему вы загружаете Dancer2 в классе Result? Это сделает этот объект приложением Dancer, что очень странно. Это может быть проблемой здесь.   -  person simbabque    schedule 05.09.2017
comment
Это был остаток отчаянной попытки попробовать все, что я могу, чтобы решить указанную выше проблему. Это не постоянно в коде. Я должен удалить его из приведенного выше примера.   -  person Armitige3    schedule 05.09.2017
comment
Вы писали классы Result вручную или они автоматически генерируются с помощью DBIx :: Class :: Schema :: Loader?   -  person simbabque    schedule 05.09.2017
comment
Я написал их от руки.   -  person Armitige3    schedule 05.09.2017
comment
Какая это версия DBIC? Возможно, где-то была исправлена ​​ошибка. Исключение происходит из metacpan.org/ источник / RIBASUSHI / DBIx-Class-0.082840 / lib / DBIx / кстати.   -  person simbabque    schedule 05.09.2017
comment
Я бы начал с того, что полностью исключил Dancer из уравнения. Напишите несколько тестов командной строки, которые опробуют некоторые базовые операции CRUD с использованием ваших классов.   -  person Dave Cross    schedule 05.09.2017
comment
Также стоит попробовать с классами, созданными с помощью DBIC :: Schema :: Loader. Я не уверен, зачем кому-то писать эти классы вручную.   -  person Dave Cross    schedule 05.09.2017
comment
@ Дэйв, может быть, они не знают SQL? ;)   -  person simbabque    schedule 05.09.2017
comment
@simbabque Тогда им следует нанять администратора баз данных :-)   -  person Dave Cross    schedule 05.09.2017
comment
@simbabque: я использую последнюю версию 0.082840.   -  person Armitige3    schedule 05.09.2017


Ответы (1)


У вас есть столбец с именем new, который создает метод доступа с именем new, что приводит к переопределению метода конструктора классов. Это похоже на DBIx :: Class :: Manual :: Устранение неполадок / синтаксическая ошибка на" "... или рядом с ним.

person Alexander Hartmaier    schedule 05.09.2017
comment
О чувак. Я совершенно не заметил этого. Я внесу изменения и посмотрю, исправит ли это. - person Armitige3; 05.09.2017
comment
СПАСИБО! Это сводит меня с ума уже несколько дней. Ты был мертв. - person Armitige3; 05.09.2017