Quick search:

7. Custom page class

This application is situated in the example7 folder. To run it on your own server you need the same data as for example3. To try it out on the phpPeanuts website click here.

It extends a copy from example 6 with a custom page for the property 'hours' of class Employee and a custom action for the Employee EditDetailsPage.

The page solves a problem in our application: when an employee has entered hours for several weeks, the Employee property 'hours' will already hold many items. To keep the number of items in the 'hours' page within reasonable limits, we created a custom PropertyPage for the Employee>>hours property that only shows the most recent hours.

In order to create the page class, we needed to know what is the current page class and how to subclass it. This is explained in how to specialize a page. We have set the debug mode for example 6 to 'verbose', so you can see the debug information in the information part of the page. We subclassed it from ObjectPropertyPage in the example7 classFolder so that it only works in this example. Click here for the code.

The design of the new page is included from the skinEmployeeHoursPropertyPart.php, from the application folder. It 
uses a form with method=GET and hidden fields for the parameters 'pntType', 'pntHanlder', 'pntProperty' and 'id'. It calls method 'printSince' for the date in the text input, and 'printPart("ItemTablePart")' for printing the item table with the search results. The method for printing the 'ItemTablePart' is inherited from PntObjectPropertyPage. It now prints the search result instead of all hours of the employee because of the override of 'getPropertyValueFor'.

The actual searching of the database is delegated to Employee::getHoursSince. It uses instances of subclasses of PntSqlSpec to generate SQL. This is done because this way the same code will still work if getLabelSort is changed to include fields from related classes that require a JOIN clause in the SQL. For more information see how to create and use filters.

The SELECT and FROM clause for retrieving the hours peanuts are supplied by the classDescriptor of Hours as a configuration of the [class:pnt.db.QueryHandler| QueryHandler] returned by getSelectQueryHandler. The classDescriptor is also used to execute the query and instantiate the peanuts. For more information see how to retrieve instances of a class from the database.

The classDescriptor may throw an exception. The getHoursSince method does not catch this exception so that it travels down the stack and is finally handled by the ErrorHandler. This will result in an ErrorPage in productoin or a waclback in development.

To demonstrate the use of a custom action, we added class EmployeeSaveAction. This action class is used when the user presses the New or the Update button in the Employee EditdetailsPage. We added a method finishSuccess that allways returns the user to the same page if the New button is pressed. This way the user can start entering hours for the new Employee or enter another Employee without clicking on the Employee in the Employee list. Also see how to override what happens after saving from an EditDetailsPage.