Skip to content
This repository has been archived by the owner on Jan 31, 2020. It is now read-only.

Fatal error: Uncaught exception 'Zend\View\Exception\InvalidArgumentException' #49

Closed
marciodojr opened this issue Feb 19, 2016 · 18 comments
Assignees
Labels
Milestone

Comments

@marciodojr
Copy link

Sorry if I'm posting this in the wrong component issue list but I don't know exactly if the problem is with zend-view or zend-navigation or zend-servicemanager.

With zend-view 2.6.2 I'm having an error when using navigation with a custom navigation view factory (that extends class Zend\ServiceManager\FactoryInterface). The error does not happen with zend-view ~2.5.0

more explicitly:

Fatal error: Uncaught exception 'Zend\View\Exception\InvalidArgumentException' with message 'Attempted to set container with alias "navigation" but no ServiceLocator was set' in /path/to/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php:263

Stack trace:
#0 /path/to/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php(541): Zend\View\Helper\Navigation\AbstractHelper->parseContainer('navigation')
#1 /path/to/vendor/zendframework/zend-view/src/Helper/Navigation.php(79): Zend\View\Helper\Navigation\AbstractHelper->setContainer('navigation')
#2 [internal function]: Zend\View\Helper\Navigation->__invoke('navigation')
#3 /path/to/vendor/zendframework/zend-view/src/Renderer/PhpRenderer.php(394): call_user_func_array(Object(Zend\View\Helper\Navigation), Array)
#4 /path/to/zend2-app/module/UMS/view/layout/application-layout.phtml(130): Zend\View\Renderer\PhpRenderer->__call('navigation', Array)
#5 /path/to/zend2-app/module/UMS/v in /path/to/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php on line 263

In my module.config.php I have the navigation entry:

'view_helpers' => array(
        'factories' => array(
            'navigation' => 'UMS\Factory\NavigationViewFactory',
        ),
 ),

if I comment the navigation view factory part the application works but I can't set acl anymore. The NavigationViewFactory code is:

<?php

namespace UMS\Factory;

use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;
use Zend\Session\Container;

class NavigationViewFactory implements FactoryInterface
{

    public function createService(ServiceLocatorInterface $serviceLocator)
    {

        $session = new Container('User');
        $role = $session->activeRole;
        $acl = $serviceLocator->getServiceLocator()->get('acl');
        $navigation = $serviceLocator->get('Zend\View\Helper\Navigation');
        $navigation->setAcl($acl)->setRole($role);

        return $navigation;
    }
}

The problem occurs even if I remove all acl parts in NavigationViewFactory

<?php

namespace UMS\Factory;

use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;

class NavigationViewFactory implements FactoryInterface
{

    public function createService(ServiceLocatorInterface $serviceLocator)
    {
       $navigation = $serviceLocator->get('Zend\View\Helper\Navigation');        
       return $navigation;
    }
}
@marciodojr marciodojr changed the title Fatal error: Uncaught exception 'Zend\View\Exception\InvalidArgumentException' with message 'Attempted to set container with alias "navigation" but no ServiceLocator was set Fatal error: Uncaught exception 'Zend\View\Exception\InvalidArgumentException' Feb 19, 2016
@weierophinney weierophinney added this to the 2.6.3 milestone Feb 19, 2016
@weierophinney weierophinney self-assigned this Feb 19, 2016
@weierophinney
Copy link
Member

I've found the issue. We removed the ServiceLocatorAwareInterface implementation from the navigation AbstractHelper, and added an initializer into the navigation PluginManager to handle the injection. Unfortunately, the initializer was incorrect. I'm fixing it now, and will have a patch shortly.

@weierophinney
Copy link
Member

@marciodojr Can you test the patch from #50, please, and let me know if it resolves the issue for you?

Thanks!

@marciodojr
Copy link
Author

@weierophinney I don't know if I'm applying your patch by the right way but I tested and the error keeps the same (I'm probably doing something wrong). To test your patch I did this: (1) update the zend-view component to version 2.6.2 (2) added this code to my composer.json:

 "repositories": [
        {
            "type": "vcs",
            "url": "https://github.com/weierophinney/zend-view"
        }
    ],

With composer update I have the following output

Loading composer repositories with package information
Reading composer.json of zendframework/zend-view (feature/nav-partial-with-param
Reading composer.json of zendframework/zend-view (hotfix/server-url-port-forward
Reading composer.json of zendframework/zend-view (hotfix/49)                   
Updating dependencies (including require-dev)               
Nothing to install or update
Writing lock file
Generating autoload files

@weierophinney
Copy link
Member

@marciodojr Besides adding the repository, you also have to specify the branch within your project; this is usually best done using an alias:

"require" : {
    "zendframework/zend-view": "dev-hotfix/49 as 2.6.3"
}

Then run composer update zendframework/zend-view.

@marciodojr
Copy link
Author

I reverted the zend-view to 2.6.2 added the require line and ran the update command but the error keeps exactly the same


Loading composer repositories with package information
Updating dependencies (including require-dev)                                     
  - Updating zendframework/zend-view (2.6.2 => dev-hotfix/49 a742faf)
    Checking out a742fafb29b87d500668306aa42068e08b2b053b

Writing lock file
Generating autoload files

@weierophinney
Copy link
Member

@marciodojr Just to confirm, after getting the updates containing my patch, you're still seeing an error?

@marciodojr
Copy link
Author

Yes, I'm seeing this:

Fatal error: Uncaught exception 'Zend\View\Exception\InvalidArgumentException' with message 'Attempted to set container with alias "navigation" but no ServiceLocator was set' in /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php:263
Stack trace: 
#0 /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php(541): Zend\View\Helper\Navigation\AbstractHelper->parseContainer('navigation') 
#1 /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation.php(79): Zend\View\Helper\Navigation\AbstractHelper->setContainer('navigation') 
#2 [internal function]: Zend\View\Helper\Navigation->__invoke('navigation') 
#3 /home/marcio/vhosts/vendor/zendframework/zend-view/src/Renderer/PhpRenderer.php(394): call_user_func_array(Object(Zend\View\Helper\Navigation), Array) 
#4 /home/marcio/vhosts/cats-lab/module/UMS/view/layout/application-layout.phtml(130): Zend\View\Renderer\PhpRenderer->__call('navigation', Array) 
#5 /home/marcio/vhosts/cats-lab/module/UMS/v in /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php on line 263

@marciodojr
Copy link
Author

I started a fresh zf2 skeleton application with the minimum necessary to reproduce the error (a little change in composer.json, navigation config in module.config.php, a factory and a echo of the navigation in layout), maybe this can help a little. As before the error does not occur with zend-view ~2.5.3

https://github.com/marciodojr/zf2-test-navigation-view-factory.git

weierophinney added a commit to weierophinney/zend-view that referenced this issue Feb 22, 2016
Adds code to the `getPluginManager()` implementation to ensure that if a
service locator is composed, it is used to inject a lazy-instantiated
navigation plugin manager. This should fix the last lingering issues as
reported in zendframework#49.
@weierophinney
Copy link
Member

@marciodojr I think I've finally isolated the issue; the lazy-instantiated Zend\View\Helper\Navigation\PluginManager instance was not being injected with the application ServiceManager; my previous patch was ensuring the SM was injected correctly in the helper, but a new patch I've added to #50 now ensures that the SM gets pushed into the PluginManager instance. Can you do an update and verify, please?

weierophinney added a commit that referenced this issue Feb 22, 2016
@marciodojr
Copy link
Author

@weierophinney Could you please reconfirm that the problem was fixed? I updated zend-view component to 2.6.3 but the error message is still appearing (just the lines changed a little)

Fatal error: Uncaught exception 'Zend\View\Exception\InvalidArgumentException' with message 'Attempted to set container with alias "navigation" but no ServiceLocator was set' in /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php:265 Stack trace: 
#0 /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php(543): Zend\View\Helper\Navigation\AbstractHelper->parseContainer('navigation')
#1 /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation.php(79): Zend\View\Helper\Navigation\AbstractHelper->setContainer('navigation') 
#2 [internal function]: Zend\View\Helper\Navigation->__invoke('navigation') 
#3 /home/marcio/vhosts/vendor/zendframework/zend-view/src/Renderer/PhpRenderer.php(394): call_user_func_array(Object(Zend\View\Helper\Navigation), Array) 
#4 /home/marcio/vhosts/cats-lab/module/UMS/view/layout/application-layout.phtml(130): Zend\View\Renderer\PhpRenderer->__call('navigation', Array) 
#5 /home/marcio/vhosts/cats-lab/module/UMS/v in /home/marcio/vhosts/vendor/zendframework/zend-view/src/Helper/Navigation/AbstractHelper.php on line 265

@weierophinney
Copy link
Member

@marciodojr Can you try something for me? Change this code:

'view_helpers' => array(
        'factories' => array(
            'navigation' => 'UMS\Factory\NavigationViewFactory',
        ),
 ),

to read as follows:

'view_helpers' => array(
        'factories' => array(
            'Zend\View\Helper\Navigation' => 'UMS\Factory\NavigationViewFactory',
            'zendviewhelpernavigation' => 'UMS\Factory\NavigationViewFactory',
        ),
 ),

and let me know if that solves the issue for you? (One of the subtle issues we're noticing during the forwards-compatibility migrations is differences with how aliases work, and I think this might be the last piece of the puzzle.)

@marciodojr
Copy link
Author

@weierophinney the navigation finally works thank you very much. And sorry for so many posts =).

@nokser
Copy link

nokser commented Feb 23, 2016

Hi @weierophinney
This fixed work without Servicelocator bugs, but store ACL and role in the proxy helper does not really stand permissions user. Result is this same for all role user.

Or

If we change navigation helper to 'zendviewhelpernavigation'

Fatal error: Uncaught Zend\ServiceManager\Exception\CircularDependencyFoundException: Circular dependency for LazyServiceLoader was found for instance Zend\View\Helper\Navigation in /home/ma/projects/platform/vendor/zendframework/zend-servicemanager/src/ServiceManager.php:931 Stack trace: 
#0 /home/ma/projects/platform/vendor/zendframework/zend-servicemanager/src/AbstractPluginManager.php(330): Zend\ServiceManager\ServiceManager->createServiceViaCallback(Array, 'zendviewhelpern...', 'Zend\\View\\Helpe...') 
#1 /home/ma/projects/platform/vendor/zendframework/zend-servicemanager/src/AbstractPluginManager.php(287): Zend\ServiceManager\AbstractPluginManager->createServiceViaCallback(Array, 'zendviewhelpern...', 'Zend\\View\\Helpe...') 
#2 /home/ma/projects/platform/vendor/zendframework/zend-servicemanager/src/ServiceManager.php(636): Zend\ServiceManager\AbstractPluginManager->createFromFactory('zendviewhelpern...', 'Zend\\View\\Helpe...') 
#3 /home/ma/projects/platform/vendor/zendframework/zend-servicemanager/src/ServiceManager.p in /home/ma/projects/platform/vendor/zendframework/zend-servicemanager/src/ServiceManager.php on line 943 

Thank's

@weierophinney
Copy link
Member

@nokser As this issue is marked resolved to the satisfaction of the original reporter, please open a new issue, with the following information:

  • Minimum configuration required to duplicate the issue (for the navigation)
  • Are you registering a custom Navigation helper factory? If so please provide its contents, and how you're configuring the service manager and/or view helper manager to use it.
  • How are you pulling the helper? I.e., what is the call that results in the above exception.
  • The exception details (as you did here).

@marciodojr
Copy link
Author

@weierophinney well ... @nokser was right. Acl doesn't filter the navigation menu items anymore. And the reason is (I think it is) the code bellow doesn't have any effect, the factory is never called:

'view_helpers' => array(
        'factories' => array(
            'Zend\View\Helper\Navigation' => 'UMS\Factory\NavigationViewFactory',
            'zendviewhelpernavigation' => 'UMS\Factory\NavigationViewFactory',
        ),
 ),

I tried an exit command in UMS\Factory\NavigationViewFactory and the navigation menu appears (the exit was never executed), in zend-veiw 2.5.3 the exit command blocks the navigation (as expected).

Do I have to create a new issue or continue here?

@weierophinney
Copy link
Member

@marciodojr I'm re-opening the issue.

That said, I spotted an error in your factory, one that can lead to a circular dependency. It's this line here:

$navigation = $serviceLocator->get('Zend\View\Helper\Navigation');

I'd rewrite that factory as follows:

namespace UMS\Factory;

use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;
use Zend\Session\Container;
use Zend\View\Helper\Navigation as NavigationHelper;

class NavigationViewFactory implements FactoryInterface
{
    public function createService(ServiceLocatorInterface $serviceLocator)
    {
        $session = new Container('User');
        $role = $session->activeRole;
        $acl = $serviceLocator->getServiceLocator()->get('acl');
        $navigation = $this->createHelper($serviceLocator);
        $navigation->setAcl($acl)->setRole($role);

        return $navigation;
    }

    private function createHelper(ServiceLocatorInterface $serviceLocator)
    {
        $helper = new NavigationHelper();
        $helper->setServiceLocator($serviceLocator);
        return $helper;
    } 
}

Now, the trick is to get your factory to be executed in preference to the one in zend-navigation. I missed something earlier: the master branch of zend-navigation actually defines only a factory named navigation; it's not under the fully qualified class name. As such, I'd do the following configuration to ensure everything works correctly:

return [
    'view_helpers' => [
        'aliases' => [
            'navigation' => Zend\View\Helper\Navigation::class,
        ],
        'factories' => [
        Zend\View\Helper\Navigation::class => 'UMS\Factory\NavigationViewFactory',
        'zendviewhelpernavigation' => 'UMS\Factory\NavigationViewFactory',
        ],
    ],
];

With the changes noted above, you should be able to get it all working again; please drop me a note to let me know what happens.

@weierophinney weierophinney reopened this Feb 23, 2016
@marciodojr
Copy link
Author

@weierophinney thanks for the suggestion for my factory and the module.config.php. With theses changes now the navigation and acl really work as expected.

@dbierer
Copy link

dbierer commented Mar 30, 2017

This worked too: just added this to Module.php in the Application module:

    public function getViewHelperConfig()
    {
        return [
            'factories' => [
                'navigation' => function ($sm) {
                    $nav = new \Zend\View\Helper\Navigation();
                    $nav->setServiceLocator($sm);
                    return $nav;
                },
            ],
        ];
    }

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Projects
None yet
Development

No branches or pull requests

5 participants