Use of "Container" as model name in Symfony - php

I have a entity called Container in a Symfony application, which I have included in the schema.yml file:
Container:
columns:
id: { type: integer, primary: true, autoincrement: true }
name: { type: string(127), notnull: true }
Strain:
columns:
id: { type: integer, primary: true, autoincrement: true }
...
container_id: { type: integer }
...
relations:
Container: { foreignAlias: Strains }
Then I have regenerated the models, forms and filters using the symfony doctrine:build --all-classes task.
Now when I try to use $strain->getContainer(), e.g. in a showSuccess action, it returns no object at all. I have double-checked that container_id has a reference to a record in container table.
Moreover, when I try to edit a Strain object and unlink the relationship with Container, the form is saved correctly, but the container_id column keeps the old value.
Do you know if Container is a reserved word or something like that in Symfony or Doctrine? What can be happening?
Thanks!

No, it isn't a reserved word.
(In fact, I have a model in my project with a Container relation).
Have you tried setting the local property on Container relation to container_id?

Related

Symfony2/Doctrine can't find mapping file for custom Repository class

I love doctrine but I have some problems with mapping/annotations. At start I used mapping files. Then I converted in into annotations. Now I want o create custom repository class so I did as I read here: http://symfony.com/doc/current/book/doctrine.html#custom-repository-classes.
Unfortunately now I have an error:
No mapping file found named '\src\Vendor\ProductBundle\Resources\config\doctrine/SynchronizationSettingRepository.orm.yml' for class 'Vendor\ProductBundle\Entity\SynchronizationSettingRepository'.
Of course I don't have this file becouse I don't use mapping anymore.
I've added:
* #ORM\Entity(repositoryClass="Vendor\ProductBundle\Entity\SynchronizationSettingRepository")
to parent and regenerated entities. I have regenerate Entites by command php app/console doctrine:generate:entities VendorProductBundle and still nothing. Regural and doctrine meadata cache is clear.
Here is a YML which from I want to generate custom Repository one more time:
Vendor\ProductBundle\Entity\SynchronizationSetting:
type: entity
table: synchronization_setting
repositoryClass: Vendor\SynchronizationSetting\Entity\SynchronizationSettingRepository
indexes:
id_product:
columns:
- id_product
id:
id:
type: integer
nullable: false
unsigned: true
comment: ''
id: true
generator:
strategy: IDENTITY
fields:
open:
type: string
nullable: true
length: 1
fixed: true
comment: ''
default: '0'
internet:
type: string
nullable: true
length: 1
fixed: true
comment: ''
default: '0'
manyToOne:
idProduct:
targetEntity: Product
cascade: { }
mappedBy: null
inversedBy: null
joinColumns:
id_product:
referencedColumnName: id
orphanRemoval: false
lifecycleCallbacks: { }
And here is a repository class:
<?php
// src/Acme/StoreBundle/Entity/ProductRepository.php
namespace Vendor\ProductBundle\Entity;
use Doctrine\ORM\EntityRepository;
class SynchronizationSettingRepository extends EntityRepository
{
public function findAllOrderedByName()
{
return $this->getEntityManager()
->createQuery(
'SELECT p FROM AcmeStoreBundle:Product p ORDER BY p.name ASC'
)
->getResult();
}
}
I think that adding #ORM\Entity did very little good as complete .php class file gets overwritten as soon as you run the doctrine:generate:entities. You need to add repositotyClass to your YML file instead.
If you switched to annotations for good, those .yml files (actually whole doctrine directory within config) are useless, apart as being intermediate files for generating annotaion-based entities.
Another thing: It seams that Doctrine thinks you have a entity with name ending with "Repository".
Can you show us the content of YML file? If you don't have it (as you said), generating entities will not be possible. You can always generate annotaion-based entities directly (no need for YML intermediates)

Symfony plugin sfDoctrineActAsTaggablePlugin not working

I want to attribute some tags to some of the objects of my doctrine model.
I found sfDoctrineActAsTaggablePlugin which seems to be precisely what I need.
The problem is that when I want to save a Taggable object, I get this error:
Unknown record property / related component "saved_tags" on "Mishidea"
Mishidea is the name of the class/table that I want to be Taggable.
Here is the related portion of my schema.yml file:
Mishidea:
connection: doctrine
actAs: {Timestampable: ~ , Taggable: ~ }
tableName: mishidea
columns:
idea_id:
type: integer(4)
primary: true
autoincrement: true
idea_title:
type: string()
notnull: true
primary: false
idea_summary:
type: string()
notnull: true
primary: false
idea_description:
type: string()
notnull: true
primary: false
idea_up:
type: integer(8)
notnull: true
default: 0
primary: false
idea_down:
type: integer(8)
notnull: true
default: 0
primary: false
idea_confirmation:
type: boolean(1)
default: false
primary: false
group_id:
type: integer(4)
notnull: false
primary: false
relations:
Mishgroup:
local: group_id
foreign: group_id
type: one
Ideacomment:
local: idea_id
foreign: idea_id
type: many
Mishdocument:
local: idea_id
foreign: idea_id
type: many
RelIdeafollower:
local: idea_id
foreign: idea_id
type: many
I also tried other types of syntax for the actAs attribute of the class such as:
actAs:
Timestampable: ~
Taggable: ~
and:
actAs:[Timestampable,Taggable]
But it's not the problem as I get :
$timestampable0 = new Doctrine_Template_Timestampable();
$taggable0 = new Taggable();
$this->actAs($timestampable0);
$this->actAs($taggable0);
in the BaseMishidea.php class of my model.
I don't understand why the Mishidea class doesn't get the attributes that the Taggable class should add to it since the model seems to add the behaviour via the $this->actAs() statement.
How to get this plugin working?
If that helps, I use Symfony 1.4 with MySQL/InnoDB and I had tried before with the PostgreSql DBMS, with the same result.
Your help would be much appreciated.
Thanks
FuzzyTern
EDIT1 - Regarding what said johnwards : Can anyone confirm that the Taggable behaviour is added in the schema.yml file via "actAs:", not "templates:"? That's what I read here and there (see my comment on johnwards' post) but since neither of both solutions work for me, I'm not sure. When using the "templates" keyword I get:
Unknown method Mishidea::addTag
and the specific classes of the model aren't generated.
EDIT2 - After a further investigation, I found that the Symfony stack trace is interresting.
Indeed, when I do:
$idea = new Mishidea();
$idea->save();
the TaggableListener is called (point 8 in the stack trace below), which shows that the relation is working. But then I don't understand what's going on and leads to the exception.
Stack trace:
1. at ()
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record/Filter/Standard.php line 55 ...
public function filterGet(Doctrine_Record $record, $name)
{
throw new Doctrine_Record_UnknownPropertyException(sprintf('Unknown record property / related component "%s" on "%s"', $name, get_class($record)));
}
}
2. at Doctrine_Record_Filter_Standard->filterGet(object('Mishidea'), 'saved_tags')
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 1374 ...
3. at Doctrine_Record->_get('saved_tags', 1)
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 1333 ...
4. at Doctrine_Record->get('saved_tags')
in n/a line n/a ...
5. at call_user_func_array(array(object('Mishidea'), 'get'), array('saved_tags'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/record/sfDoctrineRecord.class.php line 212 ...
6. at sfDoctrineRecord->__call('getSavedTags', array())
in n/a line n/a ...
7. at Mishidea->getSavedTags()
in SF_ROOT_DIR/plugins/sfDoctrineActAsTaggablePlugin/lib/TaggableTemplate.class.php line 93 ...
8. at TaggableListener->postSave(object('Doctrine_Event'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record/Listener/Chain.php line 237 ...
9. at Doctrine_Record_Listener_Chain->postSave(object('Doctrine_Event'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 355 ...
10. at Doctrine_Record->invokeSaveHooks('post', 'save', object('Doctrine_Event'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Connection/UnitOfWork.php line 112 ...
11. at Doctrine_Connection_UnitOfWork->saveGraph(object('Mishidea'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 1691 ...
12. at Doctrine_Record->save()
in SF_ROOT_DIR/apps/frontend/modules/idea/actions/actions.class.php line 24 ...
If someone wants to see the code for any point of the stack trace (only 1. is expanded here), just ask.
Any suggestion is welcomed.
Whoop whoop!!
I solved this problem, at last!
Well... The problem is that the sfDoctrineActAsTaggablePlugin plugin does work only for taggable objects which have an id property called precisely "id". I like to put the name of the entity in the name of my properties, that's why I called the idea of my taggable entity "idea_id".
As soon as I replaced "idea_id" by "id" everything worked like a charm (you may have several changes to do in the schema.yml and maybe even in the routing.yml file later on).
I don't know if I'm clear enough so don't hesitate to ask me further explanations.
Anyway that's a bit of a shame for this plugin, it is not generic enough (will report this to the developers).
BTW, all the syntaxes for actAs written in my first post are equivalent, use whichever you prefer.
Thank you all for your help, each reply was an encouragement without which I wouldn't have had the strength to find the bug ;).
Cheers
Possible Issues:
Make sure you have the plugin enabled
In ProjectConfiguration::setup, you should have
$this->enablePlugins(array(
'sfDoctrineActAsCommentablePlugin', //plus other plugins, like Doctrine
));
Set Up Your Schema Correctly
It should look like this:
ModelClass:
actAs:
Taggable:
columns: //etc
You should be using actAs not templates.
I don't believe you need to set an explicit relations for Tags, but I could be wrong about that. If you let me know, I will edit this answer.
Edit: Have you done a build all reload?
You need to add templates: [Taggable] to your schema not actAs.
Mishidea:
connection: doctrine
actAs: [Timestampable]
templates: [Taggable]
tableName: mishidea
columns:
idea_id:
type: integer(4)
primary: true
autoincrement: true

Unknown record property / related component "..." on "..." with sfDoctrineActAsTaggablePlugin [duplicate]

I want to attribute some tags to some of the objects of my doctrine model.
I found sfDoctrineActAsTaggablePlugin which seems to be precisely what I need.
The problem is that when I want to save a Taggable object, I get this error:
Unknown record property / related component "saved_tags" on "Mishidea"
Mishidea is the name of the class/table that I want to be Taggable.
Here is the related portion of my schema.yml file:
Mishidea:
connection: doctrine
actAs: {Timestampable: ~ , Taggable: ~ }
tableName: mishidea
columns:
idea_id:
type: integer(4)
primary: true
autoincrement: true
idea_title:
type: string()
notnull: true
primary: false
idea_summary:
type: string()
notnull: true
primary: false
idea_description:
type: string()
notnull: true
primary: false
idea_up:
type: integer(8)
notnull: true
default: 0
primary: false
idea_down:
type: integer(8)
notnull: true
default: 0
primary: false
idea_confirmation:
type: boolean(1)
default: false
primary: false
group_id:
type: integer(4)
notnull: false
primary: false
relations:
Mishgroup:
local: group_id
foreign: group_id
type: one
Ideacomment:
local: idea_id
foreign: idea_id
type: many
Mishdocument:
local: idea_id
foreign: idea_id
type: many
RelIdeafollower:
local: idea_id
foreign: idea_id
type: many
I also tried other types of syntax for the actAs attribute of the class such as:
actAs:
Timestampable: ~
Taggable: ~
and:
actAs:[Timestampable,Taggable]
But it's not the problem as I get :
$timestampable0 = new Doctrine_Template_Timestampable();
$taggable0 = new Taggable();
$this->actAs($timestampable0);
$this->actAs($taggable0);
in the BaseMishidea.php class of my model.
I don't understand why the Mishidea class doesn't get the attributes that the Taggable class should add to it since the model seems to add the behaviour via the $this->actAs() statement.
How to get this plugin working?
If that helps, I use Symfony 1.4 with MySQL/InnoDB and I had tried before with the PostgreSql DBMS, with the same result.
Your help would be much appreciated.
Thanks
FuzzyTern
EDIT1 - Regarding what said johnwards : Can anyone confirm that the Taggable behaviour is added in the schema.yml file via "actAs:", not "templates:"? That's what I read here and there (see my comment on johnwards' post) but since neither of both solutions work for me, I'm not sure. When using the "templates" keyword I get:
Unknown method Mishidea::addTag
and the specific classes of the model aren't generated.
EDIT2 - After a further investigation, I found that the Symfony stack trace is interresting.
Indeed, when I do:
$idea = new Mishidea();
$idea->save();
the TaggableListener is called (point 8 in the stack trace below), which shows that the relation is working. But then I don't understand what's going on and leads to the exception.
Stack trace:
1. at ()
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record/Filter/Standard.php line 55 ...
public function filterGet(Doctrine_Record $record, $name)
{
throw new Doctrine_Record_UnknownPropertyException(sprintf('Unknown record property / related component "%s" on "%s"', $name, get_class($record)));
}
}
2. at Doctrine_Record_Filter_Standard->filterGet(object('Mishidea'), 'saved_tags')
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 1374 ...
3. at Doctrine_Record->_get('saved_tags', 1)
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 1333 ...
4. at Doctrine_Record->get('saved_tags')
in n/a line n/a ...
5. at call_user_func_array(array(object('Mishidea'), 'get'), array('saved_tags'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/record/sfDoctrineRecord.class.php line 212 ...
6. at sfDoctrineRecord->__call('getSavedTags', array())
in n/a line n/a ...
7. at Mishidea->getSavedTags()
in SF_ROOT_DIR/plugins/sfDoctrineActAsTaggablePlugin/lib/TaggableTemplate.class.php line 93 ...
8. at TaggableListener->postSave(object('Doctrine_Event'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record/Listener/Chain.php line 237 ...
9. at Doctrine_Record_Listener_Chain->postSave(object('Doctrine_Event'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 355 ...
10. at Doctrine_Record->invokeSaveHooks('post', 'save', object('Doctrine_Event'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Connection/UnitOfWork.php line 112 ...
11. at Doctrine_Connection_UnitOfWork->saveGraph(object('Mishidea'))
in SF_ROOT_DIR/lib/vendor/symfony/lib/plugins/sfDoctrinePlugin/lib/vendor/doctrine/Doctrine/Record.php line 1691 ...
12. at Doctrine_Record->save()
in SF_ROOT_DIR/apps/frontend/modules/idea/actions/actions.class.php line 24 ...
If someone wants to see the code for any point of the stack trace (only 1. is expanded here), just ask.
Any suggestion is welcomed.
Whoop whoop!!
I solved this problem, at last!
Well... The problem is that the sfDoctrineActAsTaggablePlugin plugin does work only for taggable objects which have an id property called precisely "id". I like to put the name of the entity in the name of my properties, that's why I called the idea of my taggable entity "idea_id".
As soon as I replaced "idea_id" by "id" everything worked like a charm (you may have several changes to do in the schema.yml and maybe even in the routing.yml file later on).
I don't know if I'm clear enough so don't hesitate to ask me further explanations.
Anyway that's a bit of a shame for this plugin, it is not generic enough (will report this to the developers).
BTW, all the syntaxes for actAs written in my first post are equivalent, use whichever you prefer.
Thank you all for your help, each reply was an encouragement without which I wouldn't have had the strength to find the bug ;).
Cheers
Possible Issues:
Make sure you have the plugin enabled
In ProjectConfiguration::setup, you should have
$this->enablePlugins(array(
'sfDoctrineActAsCommentablePlugin', //plus other plugins, like Doctrine
));
Set Up Your Schema Correctly
It should look like this:
ModelClass:
actAs:
Taggable:
columns: //etc
You should be using actAs not templates.
I don't believe you need to set an explicit relations for Tags, but I could be wrong about that. If you let me know, I will edit this answer.
Edit: Have you done a build all reload?
You need to add templates: [Taggable] to your schema not actAs.
Mishidea:
connection: doctrine
actAs: [Timestampable]
templates: [Taggable]
tableName: mishidea
columns:
idea_id:
type: integer(4)
primary: true
autoincrement: true

Doctrine : many to many with a date of assignation in the refclass

residentSector:
columns:
id_resident_sector:
type: integer
primary: true
autoincrement: true
id_resident:
type: integer(8)
id:
type: integer(8)
date:
type: timestamp
residents:
columns:
id_resident:
type: integer(8)
primary: true
autoincrement: true
firstname:
type: string(50)
lastname:
type: string(50)
relations:
Sectors:
class: Sectors
local: id_resident
foreign: id
refClass: residentSector
Sectors:
columns:
id:
type: integer(4)
primary: true
autoincrement: true
sector_name:
type: string(50)
id_resp:
type: integer(4)
visibility:
type: integer(1)
I want to select all the "residents" of a given "sector" at à given date (the lastest date as example).
My problem is the date field is in the refclass (because it's the date of assignation) so
->where('residents.Sectors.date =max(residents.Sectors.date) ')
won't work obviously because the refclass is not part of the collection ..
what is the good way to define the doctrine relation so i can get the latest sector in date of a resident ?
Thanks in advance !
Unfortunately Doctrine doesn't provide any built-in way to achieve what you're trying to do. However many-to-many relationship in fact uses double one-to-many relationship.
So what you need is to is:
Make correct DQL query:
Doctrine_Query::create()
->from('Residents r')
->innerJoin('r.XXX rs WITH rs.date = ?', '08-04-2010')
->innerJoin('r.Sector s');
Where XXX is the name of ResidentSector table. I'm not quite sure whether its name will be same as table name, but you can get its name from table definition generated by Doctrine.
After you execute the query you will have to do all the mapping by your own, using Doctrine_Record::mapValue.
I dont know how to use doctrine but having many to many relationships results in an abundance of duplicate data.
You should maybe have 3 tables (residents, sectors, residentsToSectors) have date assigned in the residentToSectors table and then grab the information for either resident or sector based on whatever data you insert in the WHERE clause?

Generating data (using PHP) in a YML fixtures file

I want to generate test data for a fixture file. I wnat to generate the test data instead of having to type in hundreds of records.
Assuming my schema is as shown below:
foobar_department_def:
_attributes: { phpName: Department }
id:
name: { type: varchar(64), required: true }
foobar_qualification_def:
_attributes: { phpName: Qualification }
id:
name: { type: varchar(64), required: true }
foobar_employee:
_attributes: { phpName: Employee }
id:
first_name: { type: varchar(64), required: true }
last_name: { type: varchar(64), required: true }
biography: { type: longvarchar, required: false }
qualifi_id: { type: integer, foreignTable: foobar_qualification_def, foreignReference: id, required: true, onUpdate: cascade, onDelete: restrict }
dept_id: { type: integer, foreignTable: foobar_department_def, foreignReference: id, required: true, onUpdate: cascade, onDelete: restrict }
_uniques:
idxu_fb_qly_dept: [qualifi_id, dept_id]
How may I generate test data for employees (using PHP in my YML file)?. I saw this being done a little while agao, in the Symfony documentation - however, despite searching again, I can't locate the page on the SF website (maybe its been removed?)
I guess you are looking for dynamic fixtures. And really keep this in mind:
The <?php ?> statements must always start the line or be embedded in a value.
If a <?php ?> statement ends a line, you need to explicly output a new line ("\n").
Symfony used to (and probably still does) allow PHP in it's configuration YML files but I'm not sure about the fixtures files. However, for what it sounds like you're trying to do PHP in the YML file won't be necessary, you just need to create a script that writes a giant YML file once.
To generate your fixtures I would suggest creating one row in each of the tables you have defined and then dumping that data into a fixtures file to give a template for your data. Then use that fixtures template for your PHP script, replacing your test values with generated data in a loop.

Categories