3
votes

Assuming you're trying to keep yourself as close as possible to the Zend Framework view of the universe, how should view and action helpers from one module be shared with another module?

Let's say I have an with two modules. Module "A" has a view helper named Output.

class Modulea_Zend_View_Helper_Ouput extends Zend_View_Helper_Abstract
{
    function output($var)
    {
        echo strip_tags($var);
        return true;
    }
}

If I attempt to use this helper from a view in Module "B"

File: moduleb/views/scripts/index/index.phtml

<?php $this->output($somevar); ?>

I get an exception

Plugin by name 'Output' was not found in the registry

What's the "right" was to use the view helper Output from Module B.

7
So, you've got a view helper in module A that isn't actually module specific? - jason
Jason, that's correct. We often discover/realize that a helper built out for a specific module ends up being useful in another module. This isn't always obvious at the start of the project. From the tone of your question is sounds like there's a central place for helpers that are used across modules, and you're suggesting that these helpers should be moved? Or something else? - Alan Storm
It's easy to move the helper to library. You may also create the helpers as Application_View_Helper_, common for the whole Application. - takeshin
I'd recommend exactly what takeshin has. I didn't mean to be snotty, I was just asking for clarification before I answered fully. In this case, just refactoring and moving the helper in to your common library would be, in my opinion, best practice. - jason
@jason, didn't meant to imply snotty, just that your question seemed to indicate the kind of answer you were getting ready with. :) - Alan Storm

7 Answers

2
votes

To add to Chillini's answer, and in response to Starx's subsequent comment:

If $view is undefined, try adding this to your Bootstrap:

protected function _initView()
{
    // Initialize view
    $view         = new Zend_View();
    $viewRenderer = Zend_Controller_Action_HelperBroker::getStaticHelper(
        'ViewRenderer'
    );
    $viewRenderer->setView($view);
    $view->addHelperPath(
        APPLICATION_PATH . '/views/helpers/',
        'My_View_Helper'
    );
}

Also, I noticed that you may want to change class Modulea_Zend_View_Helper_Ouput to class Modulea_Zend_View_Helper_Output just in case.

1
votes

Only add:

resources.view.helperPath.Application_View_Helper = APPLICATION_PATH "/views/helpers"

Is enough..

1
votes

You could add the helper to your view in the bootstrap

$this->bootstrap('view');
$view->addHelperPath(APPLICATION_PATH . '/views/helpers/','My_View_Helper');
1
votes

The simplest way I get this implemented is as follows.

  1. Create a new folder say Helpers inside your Library folder
  2. Put your View Helper File inside a file you would name Output.php
  3. Inside the 'Output.php' you have the following code:
 class Helpers_Output extends Zend_View_Helper_Abstract
 {      public function ($var)
     {
      echo strip_tags($var);
      return true;
     }
 }

And in your Application.ini add the view helper path as follows

resources.view.helperPath.Helpers = "Helpers/"

I prefer this method as it allows you to put your Helpers in a central place outside modules and in other to make it available for your whole application all you need is just one line of entry in the Application.ini

1
votes

Here is my approach:

class Bootstrap extends Zend_Application_Bootstrap_Bootstrap {
    public function __construct($application) {
        parent::__construct($application);
        $this->bootstrap("view");
        $view = $this->getResource('view');
        Zend_Registry::set("Zend_View", $view);
    }
}

class Core_Bootstrap extends Zend_Application_Module_Bootstrap {
    public function __construct($application) {
        parent::__construct($application);
        $view = Zend_Registry::get("Zend_View");
        $view->addHelperPath(APPLICATION_PATH . "/modules/core/views/helpers", 'Core_View_Helper');
    }
}

Because application wide (let's say "global") view helpers are shared with modules, when a module needs to delegate a view helper to other modules, you have to add it to the application's view. If your view helper have dependencies on it's own module (ie. uses models), it's simply not nice to put into the library.

The code above allows module hot-drops into the application without any other changes in the main configuration files, only once, and in most cases it not mess anything else.

0
votes

i actually have a library folder and inside it view and helper folders. i put common helpers in this folder.

my structure:

-application
  --modules
   ---modulea
   ---moduleb
-library
  --view
   ---HELPER

i have added library folder to my include path using set_include_path command.

0
votes

If you put your helpers in library path, they will be autoloaded anywhere.

library
   Zend
     View
       Helper
         YourHelper.php
   Zend
     Controller
       Action
         Helper
           YourHelper.php

You may replace Zend with your own namespace, but you have to set up it, eg. in application.ini:

resources.view.helperPath.Application_View_Helper = "Application/View/Helper"
resources.frontController.actionHelperPaths.Application_Controller_Action_Helper = "Application/Controller/Action/Helper"