If I place a controller in a 2 level sub folder "categories" will not locate it
application > modules > catalog > controllers > forum
application > modules > catalog > controllers > forum > categories
// unable to locate
application > modules > catalog > controllers > forum > categories > Category.php
// able to locate
application > modules > catalog > controllers > forum > Category.php
Question is it possiable to modify MY_Router.php so can locate the folder correct and not effec any thing else.
I am using codeigniter 3.1.0 and HMVC
I have looked at this Unable to access the controller in subfolder but when enable it does not display the default_controller.
<?php (defined('BASEPATH')) OR exit('No direct script access allowed');
/* load the MX_Router class */
require APPPATH."third_party/MX/Router.php";
class MY_Router extends MX_Router {
/** Locate the controller **/
public function locate($segments)
{
$this->located = 0;
$ext = $this->config->item('controller_suffix').EXT;
/* use module route if available */
if (isset($segments[0]) && $routes = Modules::parse_routes($segments[0], implode('/', $segments)))
{
$segments = $routes;
}
/* get the segments array elements */
list($module, $directory, $controller) = array_pad($segments, 3, NULL);
/* check modules */
foreach (Modules::$locations as $location => $offset)
{
/* module exists? */
if (is_dir($source = $location.$module.'/controllers/'))
{
$this->module = $module;
$this->directory = $offset.$module.'/controllers/';
/* module sub-controller exists? */
if($directory)
{
/* module sub-directory exists? */
if(is_dir($source.$directory.'/'))
{
$source .= $directory.'/';
$this->directory .= $directory.'/';
/* module sub-directory controller exists? */
if($controller)
{
if(is_file($source.ucfirst($controller).$ext))
{
$this->located = 3;
return array_slice($segments, 2);
}
else $this->located = -1;
}
}
else
if(is_file($source.ucfirst($directory).$ext))
{
$this->located = 2;
return array_slice($segments, 1);
}
else $this->located = -1;
}
/* module controller exists? */
if(is_file($source.ucfirst($module).$ext))
{
$this->located = 1;
return $segments;
}
}
}
if( ! empty($this->directory)) return;
/* application sub-directory controller exists? */
if($directory)
{
if(is_file(APPPATH.'controllers/'.$module.'/'.ucfirst($directory).$ext))
{
$this->directory = $module.'/';
return array_slice($segments, 1);
}
/* application sub-sub-directory controller exists? */
if($controller)
{
if(is_file(APPPATH.'controllers/'.$module.'/'.$directory.'/'.ucfirst($controller).$ext))
{
$this->directory = $module.'/'.$directory.'/';
return array_slice($segments, 2);
}
}
}
/* application controllers sub-directory exists? */
if (is_dir(APPPATH.'controllers/'.$module.'/'))
{
$this->directory = $module.'/';
return array_slice($segments, 1);
}
/* application controller exists? */
if (is_file(APPPATH.'controllers/'.ucfirst($module).$ext))
{
return $segments;
}
$this->located = -1;
}
}
It might be possible, but do you really really need to?
I can sort of see the sense of using...
application > modules > catalog > controllers > forum > Category.php
But I don't see the point of using...
application > modules > catalog > controllers > forum > categories > Category.php
That is going a little too deep for the sake of putting things into their own little boxes.
Personally I would make the Forum a module and have...
application > modules > forum > controllers > categories > Category.php
Related
I'm working with CodeIgniter and I’d like to load one or more config files located in an external folder, shared by different CI installation.
Is it possible?
I tried to extend the Loader Class, and call the new method:
$this -> load -> external_config(‘MY\EXTERNAL\PATH’);
Load is successful, but i can’t retrieve config items in my controller, because in MY_Loader class the core\Loader config property is not visible, and i can’t merge it with the new loaded values.
This is my code:
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
class MY_Loader extends CI_Loader {
/**
* List of all loaded config files
*
* #var array
*/
var $is_config_loaded = array();
/**
* List of all loaded config values
*
* #var array
*/
//var $ext_config = array();
function __construct(){
parent::__construct();
}
/**
* Loads an external config file
*
* #param string
* #param bool
* #param bool
* #return void
*/
public function external_config($file = '', $use_sections = FALSE, $fail_gracefully = FALSE)
{
$file = ($file == '') ? 'config' : str_replace('.php', '', $file);
$found = FALSE;
$loaded = FALSE;
$check_locations = defined('ENVIRONMENT')
? array(ENVIRONMENT.'/'.$file, $file)
: array($file);
foreach ($check_locations as $location)
{
$file_path = $file.'.php';
if (in_array($file_path, $this->is_config_loaded, TRUE))
{
$loaded = TRUE;
continue 2;
}
if (file_exists($file_path))
{
$found = TRUE;
break;
}
}
if ($found === FALSE)
{
if ($fail_gracefully === TRUE)
{
return FALSE;
}
show_error('The configuration file '.$file.'.php does not exist.');
}
else{
include($file_path);
if ( ! isset($config) OR ! is_array($config))
{
if ($fail_gracefully === TRUE)
{
return FALSE;
}
show_error('Your '.$file_path.' file does not appear to contain a valid configuration array.');
}
if ($use_sections === TRUE)
{
if (isset($this->ext_config[$file]))
{
$this->ext_config[$file] = array_merge($this->ext_config[$file], $config);
}
else
{
$this->ext_config[$file] = $config;
}
}
else
{
$this->ext_config = array_merge($this->ext_config, $config);
}
$this->is_config_loaded[] = $file_path;
unset($config);
$loaded = TRUE;
log_message('debug', 'Config file loaded: '.$file_path);
}
return TRUE;
}
}
I found in core\Config.php a property
var $_config_paths = array(APPPATH);
With the paths in wich look for config files.
How can i add paths to the array without chance the core classe code?
Any ideas?
Thank you very much!!!
CodeIgniter makes assumptions about the config file being loaded, its location, its file ext etc. You may load other files that is: from the same directory (support seems to be limited to this usage scenario).
However, you can (looking at the chapter https://ellislab.com/codeigniter/user-guide/libraries/config.html (Setting a Config Item)) iterate your file values and set them like so
(todo: add some checks if file exists, is readable, no decoding errors etcetera)
$myConfigValues = json_decode(file_get_contents($configKeyValuesFromOuterSpace));
foreach($myConfigValues as $key => $value){
$CI->config->set_item('item_name', 'item_value');
}
As for the exposure of the config object, in the loader you may anytime examine its public parts in more or less subtle manners, by using the code igniter singleton instance retrieval method:
$CI =& get_instance();
die(print_r($CI->config,true));
This will be a CI_Config object. You may also create a MY_Config extension.
I am new to Magento Extension Development and wondering which is the best way to create categories and sub-categories from within an extension. The Extension I am working on is synchronizing product-data from an ERP-System. The extension is operating with a System->Configuration Dialog which holds the data for the connection to the server (user/pwd/etc.) Now I am wondering, if it is better to connect via Ajax request or use a Soap call. Ajax seems very slow in this case for about 700 Products. So what do you suggest?
Furthermore, I am a little stuck by creating categories and sub-categories. Is there simple way to do that. I found some stuff on creating a category and then use the ->move() function. Moreover I am wondering if the 'path' of the category is essential on creating sub-categories.
You should use magento models:
Create category with subcategory:
/**
* After installation system has two categories: root one with ID:1 and Default category with ID:2
*/
/** #var $category1 Mage_Catalog_Model_Category */
$category1 = Mage::getModel('catalog/category');
$category1->setName('Category 1')
->setParentId(2)
->setLevel(2)
->setAvailableSortBy('name')
->setDefaultSortBy('name')
->setIsActive(true)
->setPosition(1)
->save();
/** #var $category2 Mage_Catalog_Model_Category */
$category2 = Mage::getModel('catalog/category');
$category2->setName('Category 1.1')
->setParentId($category1->getId()) // set parent category which was created above
->setLevel(3)
->setAvailableSortBy('name')
->setDefaultSortBy('name')
->setIsActive(true)
->setIsAnchor(true)
->setPosition(1)
->save();
public static function addCatalogCategory($item, $id, $storeId = 0) {
/*
* resource for checking category exists
* http://fishpig.co.uk/blog/load-a-category-or-product-by-an-attribute.html
*/
$categories = Mage::getResourceModel('catalog/category_collection');
// Select which fields to load into the category
// * will load all fields but it is possible to pass an array of
// select fields to load
$categories->addAttributeToSelect('*');
// Ensure the category is active
$categories->addAttributeToFilter('is_active', 1);
// Add Name filter
$categories->addAttributeToFilter('name', $item->GROUP_NAME);
// Limit the collection to 1 result
$categories->setCurPage(1)->setPageSize(1);
// Load the collection
$categories->load();
if ($categories->getFirstItem()->getId()) {
$category = $categories->getFirstItem();
return $category->getId();
}
/* get category object model */
$category = Mage::getModel('catalog/category');
$category->setStoreId($storeId);
$data = array();
/* if the node is root */
if (Heliumv_Synchronization_Helper_Data::xml_attribute($item, 'type') == 'root') {
$data['category']['parent'] = 2; // 2 top level id
} else {
/* is node/leaf */
$data['category']['parent'] = $id;
}
$data['general']['path'] = $item->PARENT_ID;
$data['general']['name'] = $item->GROUP_NAME;
$data['general']['meta_title'] = "";
$data['general']['meta_description'] = "";
$data['general']['is_active'] = "1";
$data['general']['url_key'] = "";
$data['general']['display_mode'] = "PRODUCTS";
$data['general']['is_anchor'] = 0;
/* add data to category model */
$category->addData($data['general']);
if (!$category->getId()) {
$parentId = $data['category']['parent'];
if (!$parentId) {
if ($storeId) {
$parentId = Mage::app()->getStore($storeId)->getRootCategoryId();
} else {
$parentId = Mage_Catalog_Model_Category::TREE_ROOT_ID;
}
}
$parentCategory = Mage::getModel('catalog/category')->load($parentId);
$category->setPath($parentCategory->getPath());
}
$category->setAttributeSetId($category->getDefaultAttributeSetId());
try {
$category->save();
return $category->getId();
} catch (Exception $e) {
echo Mage::log($e->getMessage());
}
}
I hope this helps someone. cheers
i have a problem with HMVC
i have admin controller in all my modules like this
- modules
- users
- controllers
- admin.php
- users.php
- views
- admin_create_user.php
- admin_view_users.php
- signup.php
- login.php
- news
- controllers
- admin.php
- news.php
- views
- admin_disply_news.php
- admin_create_news.php
- view_news.php
now when go to users admin the URL will be link this
domain.com/users/admin/method .
domain.com/news/admin/method .
but i need it to be
domain.com/admin/users/method
domain.com/admin/news/method
Add these codes in "core/MY_Router.php" Inside "MY_Router" Class -
*(class MY_Router extends MX_Router {** ---code goes in here-- **})*
I tried to do this with routing rules and .htaccess but non of them works. Then I edit the MX_Router code and working perfect but one thing to notice you have to create a sub folder on you'r module's controller call 'admin' and put the controller there to work like this because this way you can use the default routing for modules by calling directly to controller if controller name same as module name.
public $module;
private $located = 0;
protected function _set_request($segments = array()){
$segments = $this->_validate_request($segments);
// If we don't have any segments left - try the default controller;
// WARNING: Directories get shifted out of the segments array!
if (empty($segments))
{
$this->_set_default_controller();
return;
}
if ($this->translate_uri_dashes === TRUE)
{
$segments[0] = str_replace('-', '_', $segments[0]);
if (isset($segments[1]))
{
$segments[1] = str_replace('-', '_', $segments[1]);
}
}
if($segments[0] == 'admin' && isset($segments[1])){
if (isset($segments[2])){
$this->set_method($segments[2]);
$segments[2] = $segments[2];
}else{
$this->set_method('index');
$segments[2] = 'index';
}
$this->directory = '../modules/'.$segments[1].'/controllers/admin/';
$this->module = $segments[1];
$this->class = $segments[1];
$segments[1] = $segments[1];
unset($segments[0]);
$this->uri->rsegments = $segments;
}else{
$segments = $this->locate($segments);
if($this->located == -1)
{
$this->_set_404override_controller();
return;
}
if(empty($segments))
{
$this->_set_default_controller();
return;
}
$this->set_class($segments[0]);
if (isset($segments[1]))
{
$this->set_method($segments[1]);
}
else
{
$segments[1] = 'index';
}
array_unshift($segments, NULL);
unset($segments[0]);
$this->uri->rsegments = $segments;
}
}
You can try to add this to your routes config file:
$route['domain.com/admin/users/(:any)'] = 'domain.com/users/admin/method';
$route['domain.com/admin/news/(:any)'] = 'domain.com/news/admin/method';
When user type domain.com/admin/users/method it will call user controller.
Documentation
I'm using the Cart class in Codeigniter. What I want to do should (hopefully!) be simple... but i'm struggling.
On the product page, I have a button to 'add to cart'. What I want to happen is that when the item is already in the cart, the button changes to 'remove from cart'.
<? //if(**not in cart**) { ?>
Add to cart
<? } else { ?>
Remove from cart
<? } ?>
How can I query the cart to see if that item is in there or not and get the 'rowid' so I can use that for a remove function?
Many thanks!
I had a similar problem - I got round it by extending the CI_Cart library with 2 new functions - in_cart() and all_item_count().
<?php
class MY_Cart extends CI_Cart {
function __construct()
{
parent::__construct();
$this->product_name_rules = '\d\D';
}
/*
* Returns data for products in cart
*
* #param integer $product_id used to fetch only the quantity of a specific product
* #return array|integer $in_cart an array in the form (id => quantity, ....) OR quantity if $product_id is set
*/
public function in_cart($product_id = null) {
if ($this->total_items() > 0)
{
$in_cart = array();
// Fetch data for all products in cart
foreach ($this->contents() AS $item)
{
$in_cart[$item['id']] = $item['qty'];
}
if ($product_id)
{
if (array_key_exists($product_id, $in_cart))
{
return $in_cart[$product_id];
}
return null;
}
else
{
return $in_cart;
}
}
return null;
}
public function all_item_count()
{
$total = 0;
if ($this->total_items() > 0)
{
foreach ($this->contents() AS $item)
{
$total = $item['qty'] + $total;
}
}
return $total;
}
}
/* End of file: MY_Cart.php */
/* Location: ./application/libraries/MY_Cart.php */
You could check in your model if the job name or whatever you would like to check already exists. If it exists display delete button else show add.
The wishlist section in the sidebar disappears when all the items in it are removed.. but i want to shot it even when there is no items in wishlist with a text "Add some items to your wishlist".. as like "Compare section".. how do i do it?
i tried editing the .phtml file for doing it, but its not working.. do i need to edit any xml layout file for this?
For just info, please don't reputate.
The wishlist class has been changed after 1.4.2 :
* #deprecated after 1.4.2.0
* #see Mage_Wishlist_Block_Links::__construct
*
* #return array
*/
public function addWishlistLink()
{
return $this;
}
and here is the your requested feature ( look at count ) :
/**
* Add link on wishlist page in parent block
*
* #return Mage_Wishlist_Block_Links
*/
public function addWishlistLink()
{
$parentBlock = $this->getParentBlock();
if ($parentBlock && $this->helper('wishlist')->isAllow()) {
$count = $this->helper('wishlist')->getItemCount();
if ($count > 1) {
$text = $this->__('My Wishlist (%d items)', $count);
}
else if ($count == 1) {
$text = $this->__('My Wishlist (%d item)', $count);
}
else {
$text = $this->__('My Wishlist');
}
$parentBlock->addLink($text, 'wishlist', $text, true, array(), 30, null, 'class="top-link-wishlist"');
}
return $this;
}
Magento 1.6.1.0
/app/code/core/Mage/Wishlist/Block/Customer/Sidebar.php
contains the function _toHtml():
protected function _toHtml()
{
if (($this->getCustomWishlist() && $this->getItemCount()) || $this->hasWishlistItems()) {
return parent::_toHtml();
}
return '';
}
Copy:
/app/code/core/Mage/Wishlist/Block/Customer/Sidebar.php
to:
/app/code/local/Mage/Wishlist/Block/Customer/Sidebar.php
In the copied file, replace the contents of function _toHtml() with return parent::_toHtml();:
protected function _toHtml()
{
return parent::_toHtml();
}