I want to display the commentairs on the page of the article, my comments are submitted by users.
Currently I am able to display the comments but not the users associated with comments.
SQL:
posts
CREATE TABLE `posts` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 NOT NULL DEFAULT '',
`slug` varchar(255) CHARACTER SET utf8 NOT NULL DEFAULT '',
`content` longtext CHARACTER SET utf8 NOT NULL,
`created` datetime NOT NULL,
`active` tinyint(1) DEFAULT '0',
`picture` tinyint(1) DEFAULT NULL,
`type` enum('Article','News','Page') CHARACTER SET utf8 DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=utf8;
post_comments
CREATE TABLE `post_comments` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`post_id` int(11) DEFAULT NULL,
`user_id` int(11) NOT NULL,
`title` varchar(255) NOT NULL DEFAULT '',
`content` text NOT NULL,
`created` datetime NOT NULL,
`status` tinyint(1) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8;
--
$post = $this->Post->find('first', array(
'conditions' => array('Post.slug' => $slug, 'Post.active' => '1'),
'contain' => array('PostComment')
));
--
debug($post);
array(
'Post' => array(
'id' => '2',
'name' => 'azeaeaez',
'slug' => 'azeaeaez1',
'content' => 'aeaeaeaze',
'created' => '2013-10-21 12:33:30',
'active' => true,
'picture' => null,
'type' => 'News',
'user_id' => null
),
'PostComment' => array(
(int) 0 => array(
'id' => '4',
'post_id' => '2',
'user_id' => '6',
'title' => 'Super comme article',
'content' => 'Merci c'est cool j'en prend note !',
'created' => '2013-10-29 08:58:07',
'status' => false
),
(int) 1 => array(
'id' => '3',
'post_id' => '2',
'user_id' => '31',
'title' => 'Super cool',
'content' => 'merci les loulous',
'created' => '2013-10-26 17:09:21',
'status' => false
)
)
)
the desired result
array(
'Post' => array(
'id' => '2',
'name' => 'azeaeaez',
'slug' => 'azeaeaez1',
'content' => 'aeaeaeaze',
'created' => '2013-10-21 12:33:30',
'active' => true,
'picture' => null,
'type' => 'News',
'user_id' => null
),
'PostComment' => array(
(int) 0 => array(
'id' => '4',
'post_id' => '2',
'user' => array(
'user_name' => 'toto',
'email' => tot#email.com,
...
),
'title' => 'Super comme article',
'content' => 'Merci c'est cool j'en prend note !',
'created' => '2013-10-29 08:58:07',
'status' => false
),
(int) 1 => array(
'id' => '3',
'post_id' => '2',
'user' => array(
'user_name' => 'toto',
'email' => tot#email.com,
...
),
'title' => 'Super cool',
'content' => 'merci les loulous',
'created' => '2013-10-26 17:09:21',
'status' => false
)
)
)
try
'contain' => array('PostComment', 'PostComment.User')
(I assume that you have set the relationship between PostComment and User)
You'll need
$post = $this->Post->find('first', array(
'conditions' => array('Post.slug' => $slug, 'Post.active' => '1'),
'contain' => array('PostComment' => 'User')
));
And you need to set up the proper association between the User and PostComment models.
Related
I have a model BudgetsProduct that is associated with the model Product, but it's returning the Product data cutting the first character on fields id and title, how you can see above.
Notice that BudgetsProduct.product_id is 7724 and its returning the correct associated product row, but trimming the first character like Product.id is returning just 724.
'BudgetsProduct' => array(
(int) 0 => array(
'id' => '3',
'budget_id' => '2',
'product_id' => '7724',
'quant' => '3.00',
'price' => '3175.00',
'discount' => '0.00',
'discount_type' => '%',
'product_options' => 'null',
'active' => '1',
'creator' => null,
'created' => '2014-08-27 15:52:35',
'modifier' => null,
'modified' => '2014-08-27 15:52:35',
'Product' => array(
'id' => '724',
'title' => 'onjunto Pina (03)',
'opt_title' => null,
'parent_id' => null,
'stock' => false,
'active' => '',
'creator' => null,
'created' => '013-12-11 10:53:30',
'modifier' => null,
'modified' => '014-04-09 15:44:24'
)
)
I have this two classes:
class Client extends AppModel{
public $belongsTo = array(
'User',
'plans' => array(
'className' => 'Plan',
'foreignKey' => 'plans_id'
)
);
public $hasMany = array(
'Order'
);
}
}
class User extends AppModel{
public $belongsTo = array(
'Rol' => array(
'fields' => array('id', 'nombre')
)
);
public $hasOne = array(
'Client'
);
}
However cake retrieves this:
'User' => array(
'password' => '*****',
'id' => '32',
'username' => 'test_admin',
'correo_electronico' => 'a#d.com',
'created' => '2013-06-09 19:58:18',
'modified' => '2013-06-09 19:58:18',
'esta_habilitado' => '1',
'rol_id' => '1'
),
'Rol' => array(
'id' => '1',
'nombre' => 'Administrador'
),
'Client' => array(
'id' => null,
'primer_nombre' => null,
'segundo_nombre' => null,
'primer_apellido' => null,
'segundo_apellido' => null,
'direccion' => null,
'diudad' => null,
'telefono' => null,
'rating' => null,
'created' => null,
'modified' => null,
'esta_habilitado' => null,
'plans_id' => null,
'user_id' => null
)
Any ideas what's happening, I have check the foreign keys in the database and the id from the user corresponds to the user_id in the Client record
I am calling find() on my Game model in order to get the reviews of that game for a particular platform. The problem is that the find() call doesn't seem to be paying attention to my conditions array. The call returns all the reviews for a game regardless of the platform_id.
I have these model associations:
User hasMany Review
Game hasMany Review
Review belongsTo Game
Review belongsTo User
Game HABTM Platform
This is the find call that I created:
$options = array(
'group' => array(
'Game.id'
),
'joins' => array(
array(
'table' => 'reviews',
'type' => 'LEFT',
'conditions' => array(
'Game.id=reviews.game_id'
)
),
array(
'table' => 'platforms',
'type' => 'LEFT',
'conditions' => array(
'reviews.platform_id=platforms.id'
)
),
array(
'table' => 'users',
'type' => 'LEFT',
'conditions' => array(
'reviews.user_id=users.id'
)
)
),
'fields' => array(
'Game.id', 'Game.name',
'platforms.id', 'platforms.name',
'users.id', 'users.username'
),
'conditions' => array(
'AND' => array(
'NOT' => array('reviews.review_text' => NULL),
'platforms.id' => $pid,
)
),
'limit' => 5
);
$this->Game->find('all', $options);
Here is a sample return for a find() call for platform_id=2:
array(
(int) 0 => array(
'Game' => array(
'id' => '58',
'name' => 'Bioshock 2'
),
'platforms' => array(
'id' => '2',
'name' => 'PlayStation 3'
),
'users' => array(
'id' => '20',
'username' => 'pspmaniac'
),
'Review' => array(
(int) 0 => array(
'id' => '32',
'review_text' => 'This is the PC review.',
'score' => '4',
'user_id' => '20',
'game_id' => '58',
'created' => '2013-04-30 19:59:40',
'platform_id' => '10'
),
(int) 1 => array(
'id' => '33',
'review_text' => 'This is the PS3 review.',
'score' => '7',
'user_id' => '20',
'game_id' => '58',
'created' => '2013-04-30 20:00:04',
'platform_id' => '2'
),
(int) 2 => array(
'id' => '34',
'review_text' => 'This is the XBOX 360 review.',
'score' => '6',
'user_id' => '20',
'game_id' => '58',
'created' => '2013-04-30 20:00:22',
'platform_id' => '1'
)
)
)
);
In the 'Review' index, it returns three reviews for the game (platform ids 10, 2, and 1) when it should only return the review with platform_id=2.
This is my reviews table:
CREATE TABLE reviews
(
id mediumint unsigned not null auto_increment,
review_text mediumint,
score int not null,
user_id mediumint unsigned not null,
game_id mediumint unsigned not null,
PRIMARY KEY (id),
FOREIGN KEY (user_id) REFERENCES users (id),
FOREIGN KEY (game_id) REFERENCES games (id)
);
So, in the end, the only thing wrong with the returned array is that it contains reviews not only for the condition 'platforms.id=2' but for all platform ids.
Solution
Using Dave's comment, I came up with this solution to my problem using containable:
$this->loadModel('Review');
$this->Review->find('all', array( 'contain' => array('Platform'), 'conditions' => array( 'Review.platform_id' => 2 )
));
My DB Structure:
CREATE TABLE IF NOT EXISTS `pos` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`alias` varchar(255) NOT NULL,
`model` varchar(255) NOT NULL,
`foreign_key` int(11) NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `alias` (`alias`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;
CREATE TABLE IF NOT EXISTS `psos` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`parent_id` int(11) NOT NULL DEFAULT '0',
`po_id` int(11) NOT NULL,
`lft` int(11) NOT NULL DEFAULT '0',
`rght` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;
My Models Structure:
class Po extends Model {
public $name = 'Po';
public $useTable = 'pos';
public $cacheQueries = false;
public $hasMany = array(
'Pso' => array(
'className' => 'Pso',
'foreignKey' => 'po_id',
'dependent' => true,
),
'Puso' => array(
'className' => 'Puso',
'foreignKey' => 'po_id',
'dependent' => true,
),
);
}
class Pso extends Model {
public $name = 'Pso';
public $useTable = 'psos';
public $cacheQueries = false;
public $actsAs = array(
'Tree',
);
public $belongsTo = array(
'Parent' => array(
'className' => 'Pso',
'foreignKey' => 'parent_id',
),
'Po' => array(
'className' => 'Po',
'foreignKey' => 'po_id',
),
);
public $hasMany = array(
'Children' => array(
'className' => 'Pso',
'foreignKey' => 'parent_id',
),
);
}
My Saving Associated test code:
$Po->saveAssociated(array(
'Po' => array(
'alias' => 'teste'.uniqid(),
),
'Pso' => array(
'parent_id' => 2,
),
));
Resulting PSO saved Row:
array('id'=>4,'parent_id'=>0,'po_id'=>4,'lft'=>7,'rght'=>8)
Expected PSO saved Row:
array('id'=>4,'parent_id'=>2,'po_id'=>4,'lft'=>7,'rght'=>8)
Resolved like this:
$Po->saveAssociated(array(
'Po' => array(
'alias' => 'teste'.uniqid(),
),
'Pso' => array(
'parent_id' => array(
'parent_id' => 2,
),
),
));
I have two tables like this:
CREATE TABLE IF NOT EXISTS `publications` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`numerated` tinyint(1) NOT NULL DEFAULT '0',
`title` text COLLATE utf8_unicode_ci,
`collection_id` int(11) NOT NULL,
`note` text CHARACTER SET utf8,
`adminNote` text CHARACTER SET utf8,
PRIMARY KEY (`id`),
KEY `collectionId` (`collection_id`)
KEY `numerated` (`numerated`),
) ;
CREATE TABLE IF NOT EXISTS `publication_numerations` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`publication_id` int(11) NOT NULL,
`published` tinyint(1) NOT NULL DEFAULT '0',
`book` int(11) DEFAULT NULL,
`number` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `publication_id` (`publication_id`)
) ;
CREATE TABLE IF NOT EXISTS `properties` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`publication_id` int(11) NOT NULL,
`value` varchar(255) CHARACTER SET utf8 DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `publication_id` (`publication_id`)
)
All I need is to have list of all records from table publications and publication_numerations. Tryed with cake bake model/controller/view, but all the time it joins
publications and properties, without publication_numerations.
Can you help me to solve this?
Thank you very much in advance!
UPDATED: so, all I need is to create and use it as default query:
SELECT * FROM `publications`
LEFT JOIN `publication_numerations` ON (`publications`.`id` = publication_numerations.`publication_id`)
UPDATED: here are my models
publications model
var $hasOne = array(
'Publisher' => array(
'className' => 'Publisher',
'foreignKey' => 'publication_id',
'conditions' => '',
'fields' => '',
'order' => ''
),
);
var $belongsTo = array(
'Collection' => array(
'className' => 'Collection',
'foreignKey' => 'collection_id',
'conditions' => '',
'fields' => '',
'order' => ''
)
);
var $hasMany = array(
'PublicationProperty' => array(
'className' => 'PublicationProperty',
'foreignKey' => 'publication_id',
'dependent' => false,
'conditions' => '',
'fields' => '',
'order' => '',
'limit' => '',
'offset' => '',
'exclusive' => '',
'finderQuery' => '',
'counterQuery' => ''
),
'PublicationNumeration' => array(
'className' => 'PublicationNumeration',
'foreignKey' => 'publication_id',
'conditions' => '',
'fields' => '',
'order' => ''
)
);
}
?>
PublicationNumeration model
var $belongsTo = array(
'Publication' => array(
'className' => 'Publication',
'foreignKey' => 'publication_id',
'conditions' => '',
'fields' => '',
'order' => ''
)
);
var $hasMany = array(
'Publication' => array(
'className' => 'Publication',
'foreignKey' => 'publication_id',
'conditions' => '',
'fields' => '',
'order' => ''
)
);
}
?>
Collection modes
var $hasMany = array(
'Property' => array(
'className' => 'Property',
'foreignKey' => 'collection_id',
'dependent' => false,
'conditions' => '',
'fields' => '',
'order' => '',
'limit' => '',
'offset' => '',
'exclusive' => '',
'finderQuery' => '',
'counterQuery' => ''
),
'Publication' => array(
'className' => 'Publication',
'foreignKey' => 'collection_id',
'dependent' => false,
'conditions' => '',
'fields' => '',
'order' => '',
'limit' => '',
'offset' => '',
'exclusive' => '',
'finderQuery' => '',
'counterQuery' => ''
)
);
}
?>
You can do joins in cake like so:
$joins = array(
array('table' => 'publication_numerations',
'alias' => 'PublicationNumeration',
'type' => 'LEFT',
'conditions' => array(
'Publication.id = PublicationNumeration.publication_id',
)
)
);
$this->Publication->find('all', array('joins' => $joins));
Tryed with cake bake
model/controller/view, but all the
time it joins publications and
properties, without
publication_numerations.
So, create associations manually - Associations: Linking Models Together. It does not seems that you need 'joins'. By setting associations correctly you will be able to get the list you need by using find('list') in your controller - http://book.cakephp.org/view/1017/Retrieving-Your-Data#find-list-1022.
Try making the type attribute of $join array 'LEFT OUTER' instead of 'LEFT'.