(For more resources on Agile, see here.)
The goal of this iteration is to implement feature functionality in the Trackstar application to allow users to leave and read comments on issues. When a user is viewing the details of any project issue, they should be able to read all comments previously added as well as create a new comment on the issue. We also want to add a small fragment of content, or portlet, to the project-listing page that displays a list of recent comments left on all of the issues. This will be a nice way to provide a window into recent user activity and allow easy access to the latest issues that have active conversations.
The following is a list of high-level tasks that we will need to complete in order to achieve these goals:
- Design and create a new database table to support comments
- Create the Yii AR class associated with our new comments table
- Add a form directly to the issue details page to allow users to submit comments
- Display a list of all comments associated with an issue directly on the issues details page
Creating the model
As always, we should run our existing test suite at the start of our iteration to ensure all of our previously written tests are still passing as expected. By this time, you should be familiar with how to do that, so we will leave it to the reader to ensure that all the unit tests are passing before proceeding.
We first need to create a new table to house our comments. Following is the basic DDL definition for the table that we will be using:
CREATE TABLE tbl_comment
`id` INTEGER NOT NULL PRIMARY KEY AUTO_INCREMENT,
`content` TEXT NOT NULL,
As each comment belongs to a specific issue, identified by the issue_id, and is written by a specific user, indicated by the create_user_id identifier, we also need to define the following foreign key relationships:
ALTER TABLE `tbl_comment` ADD CONSTRAINT `FK_comment_issue`
FOREIGN KEY (`issue_id`) REFERENCES `tbl_issue` (`id`);
ALTER TABLE `tbl_comment` ADD CONSTRAINT `FK_comment_author`
FOREIGN KEY (`create_user_id`) REFERENCES `tbl_user` (`id`);
If you are following along, please ensure this table is created in both the trackstar_dev and trackstar_test databases.
Once a database table is in place, creating the associated AR class is a snap. We simply use the Gii code creation tool’s Model Generator command and create an AR class called Comment.
Since we have already created the model class for issues, we will need to explicitly add the relations to to the Issue model class for comments. We will also add a relationship as a statistical query to easily retrieve the number of comments associated with a given issue (just as we did in the Project AR class for issues). Alter the Issue::relations() method as such:
public function relations()
'requester' => array(self::BELONGS_TO, 'User', 'requester_id'),
'owner' => array(self::BELONGS_TO, 'User', 'owner_id'),
'project' => array(self::BELONGS_TO, 'Project', 'project_id'),
'comments' => array(self::HAS_MANY, 'Comment', 'issue_id'),
'commentCount' => array(self::STAT, 'Comment', 'issue_id'),
Also, we need to change our newly created Comment AR class to extend our custom TrackStarActiveRecord base class, so that it benefits from the logic we placed in the beforeValidate() method. Simply alter the beginning of the class definition as such:
* This is the model class for table "tbl_comment".
class Comment extends TrackStarActiveRecord
We’ll make one last small change to the definitions in the Comment::relations() method. The relational attributes were named for us when the class was created. Let’s change the one named createUser to be author, as this related user does represent the author of the comment. This is just a semantic change, but will help to make our code easier to read and understand. Change the method as such:
* @return array relational rules.
public function relations()
// NOTE: you may need to adjust the relation name and the related
// class name for the relations automatically generated below.
'author' => array(self::BELONGS_TO, 'User', 'create_user_id'),
'issue' => array(self::BELONGS_TO, 'Issue', 'issue_id'),
Creating the Comment CRUD
Once we have an AR class in place, creating the CRUD scaffolding for managing the related entity is equally as easy. Again, use the Gii code generation tool’s Crud Generator command with the AR class name, Comment, as the argument. Although we will not immediately implement full CRUD operations for our comments, it is nice to have the scaffolding for the other operations in place.
As long as we are logged in, we should now be able to view the autogenerated comment submission form via the following URL: