Creating a Zend_Navigation using a table of database
i use a xml file for creating a Zend navigation
$navContainerConfig = new Zend_Config_Xml(APPLICATION_PATH . '/configs/navigation.xml', 'nav');
$navContainer = new Zend_Navigation($navContainerConfig);
now my question ,could i use a table of database instead of xml file for creating zend_navgation
if it is possible开发者_如何学JAVA , please give me any example on how i make Zend_Navigation with a table of database?
Create a table with columns equal to the combined properties possible for MVC and URI pages with two exceptions: add an id
column and instead of having a pages column, you add a column parent_id
. Subpages should contain the id of their parent page in here.
Then use any of Zend_Db_*
to fetch all data in that table. The result will be a flat array of all pages in your navigation. You can use this as container and feed it to Zend_Navigation
. However, if you have nested navigation that array won't do, because the array will be flat. Traverse the array to make it nested according to the parent_id relations. Then feed it to Zend_Navigation
.
After that, you just have to use one of the Navigation Helpers to render the navigation. Since your navigation is likely not changing that often, you should cache the fetching from the database. There is no need to do a costly roundtrip to the database each time the page is shown.
Asuming you have this table :
CREATE TABLE IF NOT EXISTS `menu` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`label` varchar(50) NOT NULL,
`url` varchar(50) NOT NULL,
`name` varchar(50) NOT NULL,
`title` varchar(50) NOT NULL,
`class` varchar(50) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=3;
Wtih these values :
INSERT INTO `menu` (`id`, `label`, `url`, `name`, `title`, `class`) VALUES
(1, 'Home', 'index/home', 'home', 'Home title', 'someClass'),
(2, 'About Us', 'index/about', 'about', 'About title', 'aboutClass');
You can do this :
$dbAdapter = Zend_Db_Table::getDefaultAdapter();
$dbAdapter->setFetchMode(Zend_Db::FETCH_ASSOC);
$menuArray = $dbAdapter->fetchAll("SELECT * FROM menu");
$navContainer = new Zend_Navigation();
foreach ( $menuArray as $value )
{
$navContainer->addPage(
Zend_Navigation_Page::factory(array(
'uri' => $value['url'],
'label' => $value['label'],
'title' => $value['title'],
'class' => $value['class'],
))
);
}
Carefull now couse this "design" whont allow you to have submenu items so you'll need to play around with it , but hopefully it will get you started easyer .
I'd recommend one of the following solutions:
- Serialize the XML and store it in database
- Use Xml_Writer form Zend library and operate directly on the file written on disk.
Writable XML config is the best in my opinion. Write operations are not so common and don't need to be lightning fast, and you will probably cache the HTML output, so the read is minimal). Easy to implement using iterators, when you assume each item has it's unique ID. - Use Nested Set structure to save the container to the database.
You can do some function like this :)
/**
* Gets assoc array (fetched from db) and transforms it to Zend_Navigation object
* @param assoc array $array
* @param string $idField
* @param string $parentField
* @return \Zend_Navigation
*/
private function getNavigationFromAssocArray($array, $idField = 'menu_item_id', $parentField = 'parent_menu_item_id') {
$navigation = new Zend_Navigation();
foreach ($array as $key => $item) {
$item['uri'] = $item['url'];
if(empty($parentField) ) {
$navigation->addPage(
Zend_Navigation_Page::factory( $item )
);
} else {
$page = $navigation->findBy($idField, $parentField );
$page->addPage(Zend_Navigation_Page::factory( $item ));
}
}
return $navigation;
}
精彩评论