/** * {@inheritdoc} */ public function createInstance(PluginWithFormsInterface $plugin, $operation, $fallback_operation = NULL) { if (!$plugin->hasFormClass($operation)) { // Use the default form class if no form is specified for this operation. if ($fallback_operation && $plugin->hasFormClass($fallback_operation)) { $operation = $fallback_operation; } else { throw new InvalidPluginDefinitionException($plugin->getPluginId(), sprintf('The "%s" plugin did not specify a "%s" form class', $plugin->getPluginId(), $operation)); } } $form_class = $plugin->getFormClass($operation); // If the form specified is the plugin itself, use it directly. if (ltrim(get_class($plugin), '\\') === ltrim($form_class, '\\')) { $form_object = $plugin; } else { $form_object = $this->classResolver->getInstanceFromDefinition($form_class); } // Ensure the resulting object is a plugin form. if (!$form_object instanceof PluginFormInterface) { throw new InvalidPluginDefinitionException($plugin->getPluginId(), sprintf('The "%s" plugin did not specify a valid "%s" form class, must implement \\Drupal\\Core\\Plugin\\PluginFormInterface', $plugin->getPluginId(), $operation)); } if ($form_object instanceof PluginAwareInterface) { $form_object->setPlugin($plugin); } return $form_object; }
/** * {@inheritdoc} */ public function getOperationsProvider($plugin_id) { /** @var \Drupal\Component\Plugin\Discovery\DiscoveryInterface|\Drupal\plugin\Plugin\PluginOperationsProviderPluginManagerTrait $this */ $definition = $this->getDefinition($plugin_id); if (isset($definition['operations_provider'])) { return $this->classResolver->getInstanceFromDefinition($definition['operations_provider']); } return NULL; }
/** * @covers ::getOperationsProvider */ public function testGetOperationsProvider() { $plugin_definitions = array('foo' => array('id' => 'foo', 'operations_provider' => PluginOperationsProviderPluginManagerTraitUnitTestOperationsProvider::class), 'bar' => array('id' => 'bar')); $operations_provider = new \stdClass(); $this->sut = new PluginOperationsProviderPluginManagerTraitUnitTestOperationsProvider($this->classResolver, $plugin_definitions); $this->classResolver->expects($this->any())->method('getInstanceFromDefinition')->with($plugin_definitions['foo']['operations_provider'])->willReturn($operations_provider); $this->assertSame($operations_provider, $this->sut->getOperationsProvider('foo')); $this->assertNull($this->sut->getOperationsProvider('bar')); }
/** * {@inheritdoc} * * @param \Drupal\Core\Menu\MenuLinkInterface $menu_link_plugin * The plugin instance to use for this form. */ public function buildForm(array $form, array &$form_state, MenuLinkInterface $menu_link_plugin = NULL) { $form['menu_link_id'] = array('#type' => 'value', '#value' => $menu_link_plugin->getPluginId()); $class_name = $menu_link_plugin->getFormClass(); $form['#plugin_form'] = $this->classResolver->getInstanceFromDefinition($class_name); $form['#plugin_form']->setMenuLinkInstance($menu_link_plugin); $form += $form['#plugin_form']->buildConfigurationForm($form, $form_state); $form['actions'] = array('#type' => 'actions'); $form['actions']['submit'] = array('#type' => 'submit', '#value' => $this->t('Save'), '#button_type' => 'primary'); return $form; }
/** * {@inheritdoc} */ public function getFormObject($entity_type, $operation) { if (!($class = $this->getDefinition($entity_type, TRUE)->getFormClass($operation))) { throw new InvalidPluginDefinitionException($entity_type, sprintf('The "%s" entity type did not specify a "%s" form class.', $entity_type, $operation)); } $form_object = $this->classResolver->getInstanceFromDefinition($class); return $form_object->setStringTranslation($this->stringTranslation)->setModuleHandler($this->moduleHandler)->setEntityTypeManager($this)->setOperation($operation)->setEntityManager(\Drupal::entityManager()); }
/** * Creates a controller instance using route defaults. * * By design we cannot support all possible routes, but just the ones which * use the defaults provided by core, which are _content, _controller * and _form. * * @param array $defaults * The default values provided by the route. * * @return array|null * Returns the controller instance if it is possible to instantiate it, NULL */ protected function getController(array $defaults) { $controller = NULL; if (isset($defaults['_content'])) { $controller = $this->controllerResolver->getControllerFromDefinition($defaults['_content']); } if (isset($defaults['_controller'])) { $controller = $this->controllerResolver->getControllerFromDefinition($defaults['_controller']); } if (isset($defaults['_form'])) { $form_arg = $defaults['_form']; // Check if the class exists first as the class resolver will throw an // exception if it doesn't. This also means a service cannot be used here. if (class_exists($form_arg)) { $controller = array($this->classResolver->getInstanceFromDefinition($form_arg), 'buildForm'); } } return $controller; }
/** * @covers ::createInstance */ public function testCreateInstanceInvalidException() { $this->setExpectedException(InvalidPluginDefinitionException::class, 'The "the_plugin_id" plugin did not specify a valid "invalid" form class, must implement \\Drupal\\Core\\Plugin\\PluginFormInterface'); $expected = new \stdClass(); $this->classResolver->getInstanceFromDefinition(get_class($expected))->willReturn($expected); $plugin = $this->prophesize(PluginWithFormsInterface::class); $plugin->getPluginId()->willReturn('the_plugin_id'); $plugin->hasFormClass('invalid')->willReturn(TRUE); $plugin->getFormClass('invalid')->willReturn(get_class($expected)); $form_object = $this->manager->createInstance($plugin->reveal(), 'invalid'); $this->assertSame(NULL, $form_object); }
/** * Returns a callable for the given controller. * * @param string $controller * A Controller string. * * @return mixed * A PHP callable. * * @throws \LogicException * If the controller cannot be parsed. * * @throws \InvalidArgumentException * If the controller class does not exist. */ protected function createController($controller) { // Controller in the service:method notation. $count = substr_count($controller, ':'); if ($count == 1) { list($class_or_service, $method) = explode(':', $controller, 2); } elseif (strpos($controller, '::') !== FALSE) { list($class_or_service, $method) = explode('::', $controller, 2); } else { throw new \LogicException(sprintf('Unable to parse the controller name "%s".', $controller)); } $controller = $this->classResolver->getInstanceFromDefinition($class_or_service); return array($controller, $method); }
/** * {@inheritdoc} */ public function getFormId($form_arg, &$form_state) { // If the $form_arg is the name of a class, instantiate it. Don't allow // arbitrary strings to be passed to the class resolver. if (is_string($form_arg) && class_exists($form_arg)) { $form_arg = $this->classResolver->getInstanceFromDefinition($form_arg); } if (!is_object($form_arg) || !$form_arg instanceof FormInterface) { throw new \InvalidArgumentException(String::format('The form argument @form_arg is not a valid form.', array('@form_arg' => $form_arg))); } // Add the $form_arg as the callback object and determine the form ID. $form_state['build_info']['callback_object'] = $form_arg; if ($form_arg instanceof BaseFormIdInterface) { $form_state['build_info']['base_form_id'] = $form_arg->getBaseFormID(); } return $form_arg->getFormId(); }
/** * {@inheritdoc} */ public function getFormId($form_arg, FormStateInterface &$form_state) { // If the $form_arg is the name of a class, instantiate it. Don't allow // arbitrary strings to be passed to the class resolver. if (is_string($form_arg) && class_exists($form_arg)) { $form_arg = $this->classResolver->getInstanceFromDefinition($form_arg); } if (!is_object($form_arg) || !$form_arg instanceof FormInterface) { throw new \InvalidArgumentException("The form argument {$form_arg} is not a valid form."); } // Add the $form_arg as the callback object and determine the form ID. $form_state->setFormObject($form_arg); if ($form_arg instanceof BaseFormIdInterface) { $form_state->addBuildInfo('base_form_id', $form_arg->getBaseFormId()); } return $form_arg->getFormId(); }
/** * Gets the controller class using route defaults. * * By design we cannot support all possible routes, but just the ones which * use the defaults provided by core, which are _content, _controller * and _form. * * Rather than creating an instance of every controller determine the class * and method that would be used. This is not possible for the service:method * notation as the runtime container does not allow static introspection. * * @see \Drupal\Core\Controller\ControllerResolver::getControllerFromDefinition() * @see \Drupal\Core\Controller\ClassResolver::getInstanceFromDefinition() * * @param array $defaults * The default values provided by the route. * * @return string|null * Returns the controller class, otherwise NULL. */ protected function getControllerClass(array $defaults) { $controller = NULL; if (isset($defaults['_content'])) { $controller = $defaults['_content']; } if (isset($defaults['_controller'])) { $controller = $defaults['_controller']; } if (isset($defaults['_form'])) { $controller = $defaults['_form']; // Check if the class exists and if so use the buildForm() method from the // interface. if (class_exists($controller)) { return array($controller, 'buildForm'); } } if (strpos($controller, ':') === FALSE) { if (method_exists($controller, '__invoke')) { return array($controller, '__invoke'); } if (function_exists($controller)) { return $controller; } return NULL; } $count = substr_count($controller, ':'); if ($count == 1) { // Controller in the service:method notation. Get the information from the // service. This is dangerous as the controller could depend on services // that could not exist at this point. There is however no other way to // do it, as the container does not allow static introspection. list($class_or_service, $method) = explode(':', $controller, 2); return array($this->classResolver->getInstanceFromDefinition($class_or_service), $method); } elseif (strpos($controller, '::') !== FALSE) { // Controller in the class::method notation. return explode('::', $controller, 2); } return NULL; }
/** * Constructs a new instance. * * @param mixed[] $definition * The plugin type definition. * @param \Drupal\Core\StringTranslation\TranslationInterface $string_translation * The string translator. * @param \Drupal\Core\DependencyInjection\ClassResolverInterface $class_resolver * The class resolver. * @param \Drupal\Component\Plugin\PluginManagerInterface $plugin_manager * The plugin type's plugin manager. * * @param mixed[] $definition */ public function __construct(array $definition, TranslationInterface $string_translation, ClassResolverInterface $class_resolver, PluginManagerInterface $plugin_manager) { if (!is_string($definition['id']) || !strlen($definition['id'])) { throw new \InvalidArgumentException(sprintf('The plugin type definition ID must be a non-empty string, but %s was given.', gettype($definition['id']))); } $this->id = $definition['id']; $this->label = $definition['label'] = new TranslatableMarkup($definition['label'], [], [], $string_translation); $this->description = $definition['description'] = isset($definition['description']) ? new TranslatableMarkup($definition['description'], [], [], $string_translation) : NULL; if (array_key_exists('field_type', $definition)) { if (!is_bool($definition['field_type'])) { throw new \InvalidArgumentException(sprintf('The plugin type definition "field_type" item must be a boolean, but %s was given.', gettype($definition['field_type']))); } $this->fieldType = $definition['field_type']; } if (array_key_exists('plugin_definition_decorator_class', $definition)) { $class = $definition['plugin_definition_decorator_class']; if (!class_exists($class)) { $type = is_scalar($class) ? $class : gettype($class); throw new \InvalidArgumentException(sprintf('The plugin type definition "plugin_definition_decorator_class" item must valid class name, but "%s" was given and it does not exist.', $type)); } $this->pluginDefinitionDecoratorClass = $definition['plugin_definition_decorator_class']; } $operations_provider_class = array_key_exists('operations_provider_class', $definition) ? $definition['operations_provider_class'] : DefaultPluginTypeOperationsProvider::class; $this->operationsProvider = $class_resolver->getInstanceFromDefinition($operations_provider_class); $this->pluginManager = $plugin_manager; $this->provider = $definition['provider']; }
/** * {@inheritdoc} */ public function getFormObject($entity_type, $operation) { if (!isset($this->controllers['form'][$operation][$entity_type])) { if (!($class = $this->getDefinition($entity_type, TRUE)->getFormClass($operation))) { throw new InvalidPluginDefinitionException($entity_type, sprintf('The "%s" entity type did not specify a "%s" form class.', $entity_type, $operation)); } $controller = $this->classResolver->getInstanceFromDefinition($class); $controller->setStringTranslation($this->translationManager)->setModuleHandler($this->moduleHandler)->setOperation($operation); $this->controllers['form'][$operation][$entity_type] = $controller; } return $this->controllers['form'][$operation][$entity_type]; }
/** * Returns the object used to build the step form. * * @param array $form_state * The form_state of the current form. * * @return \Drupal\Core\Form\FormInterface * The form object to use. */ protected function getFormObject(array $form_state) { // If this is a class, instantiate it. $form_step_class = isset($form_state['step_controller'][$form_state['step']]) ? $form_state['step_controller'][$form_state['step']] : 'Drupal\\views\\Form\\ViewsFormMainForm'; return $this->classResolver->getInstanceFromDefinition($form_step_class); }
/** * {@inheritdoc} */ public function setUp() { parent::setUp(); $container = new ContainerBuilder(); // Register plugin managers used by Rules, but mock some unwanted // dependencies requiring more stuff to loaded. $this->moduleHandler = $this->prophesize(ModuleHandlerInterface::class); // Set all the modules as being existent. $this->enabledModules = new \ArrayObject(); $this->enabledModules['rules'] = TRUE; $this->enabledModules['rules_test'] = TRUE; $enabled_modules = $this->enabledModules; $this->moduleHandler->moduleExists(Argument::type('string'))->will(function ($arguments) use($enabled_modules) { return [$arguments[0], $enabled_modules[$arguments[0]]]; }); // Wed don't care about alter() calls on the module handler. $this->moduleHandler->alter(Argument::any(), Argument::any(), Argument::any(), Argument::any())->willReturn(NULL); $this->cacheBackend = new NullBackend('rules'); $rules_directory = __DIR__ . '/../../..'; $this->namespaces = new \ArrayObject(['Drupal\\rules' => $rules_directory . '/src', 'Drupal\\rules_test' => $rules_directory . '/tests/modules/rules_test/src', 'Drupal\\Core\\TypedData' => $this->root . '/core/lib/Drupal/Core/TypedData', 'Drupal\\Core\\Validation' => $this->root . '/core/lib/Drupal/Core/Validation']); $this->actionManager = new RulesActionManager($this->namespaces, $this->cacheBackend, $this->moduleHandler->reveal()); $this->conditionManager = new ConditionManager($this->namespaces, $this->cacheBackend, $this->moduleHandler->reveal()); $uuid_service = new Php(); $this->rulesExpressionManager = new ExpressionManager($this->namespaces, $this->moduleHandler->reveal(), $uuid_service); $this->classResolver = $this->prophesize(ClassResolverInterface::class); $this->typedDataManager = new TypedDataManager($this->namespaces, $this->cacheBackend, $this->moduleHandler->reveal(), $this->classResolver->reveal()); $this->rulesDataProcessorManager = new DataProcessorManager($this->namespaces, $this->moduleHandler->reveal()); $this->aliasManager = $this->prophesize(AliasManagerInterface::class); // Keep the deprecated entity manager around because it is still used in a // few places. $this->entityManager = $this->prophesize(EntityManagerInterface::class); $this->entityTypeManager = $this->prophesize(EntityTypeManagerInterface::class); $this->entityTypeManager->getDefinitions()->willReturn([]); // Setup a rules_component storage mock which returns nothing by default. $storage = $this->prophesize(ConfigEntityStorageInterface::class); $storage->loadMultiple(NULL)->willReturn([]); $this->entityTypeManager->getStorage('rules_component')->willReturn($storage->reveal()); $this->entityFieldManager = $this->prophesize(EntityFieldManagerInterface::class); $this->entityFieldManager->getBaseFieldDefinitions()->willReturn([]); $this->entityTypeBundleInfo = $this->prophesize(EntityTypeBundleInfoInterface::class); $this->entityTypeBundleInfo->getBundleInfo()->willReturn([]); $this->dataFetcher = new DataFetcher(); $this->dataFilterManager = new DataFilterManager($this->namespaces, $this->moduleHandler->reveal()); $this->placeholderResolver = new PlaceholderResolver($this->dataFetcher, $this->dataFilterManager); $container->set('entity.manager', $this->entityManager->reveal()); $container->set('entity_type.manager', $this->entityTypeManager->reveal()); $container->set('entity_field.manager', $this->entityFieldManager->reveal()); $container->set('entity_type.bundle.info', $this->entityTypeBundleInfo->reveal()); $container->set('context.repository', new LazyContextRepository($container, [])); $container->set('path.alias_manager', $this->aliasManager->reveal()); $container->set('plugin.manager.rules_action', $this->actionManager); $container->set('plugin.manager.condition', $this->conditionManager); $container->set('plugin.manager.rules_expression', $this->rulesExpressionManager); $container->set('plugin.manager.rules_data_processor', $this->rulesDataProcessorManager); $container->set('typed_data_manager', $this->typedDataManager); $container->set('string_translation', $this->getStringTranslationStub()); $container->set('uuid', $uuid_service); $container->set('typed_data.data_fetcher', $this->dataFetcher); $container->set('typed_data.placeholder_resolver', $this->placeholderResolver); \Drupal::setContainer($container); $this->container = $container; }
/** * Returns the object used to build the step form. * * @param \Drupal\Core\Form\FormStateInterface $form_state * The form_state of the current form. * * @return \Drupal\Core\Form\FormInterface * The form object to use. */ protected function getFormObject(FormStateInterface $form_state) { // If this is a class, instantiate it. $form_step_class = $form_state->get(['step_controller', $form_state->get('step')]) ?: 'Drupal\\views\\Form\\ViewsFormMainForm'; return $this->classResolver->getInstanceFromDefinition($form_step_class); }
/** * {@inheritdoc} */ public function setUp() { parent::setUp(); $container = new ContainerBuilder(); // Register plugin managers used by Rules, but mock some unwanted // dependencies requiring more stuff to loaded. $this->moduleHandler = $this->prophesize(ModuleHandlerInterface::class); // Set all the modules as being existent. $this->enabledModules = new \ArrayObject(); $this->enabledModules['rules'] = TRUE; $this->enabledModules['rules_test'] = TRUE; $enabledModules = $this->enabledModules; $this->moduleHandler->moduleExists(Argument::type('string'))->will(function ($arguments) use($enabledModules) { return [$arguments[0], $enabledModules[$arguments[0]]]; }); // Wed don't care about alter() calls on the module handler. $this->moduleHandler->alter(Argument::any(), Argument::any(), Argument::any(), Argument::any())->willReturn(NULL); $this->cacheBackend = new NullBackend('rules'); $rules_directory = __DIR__ . '/../../..'; $this->namespaces = new \ArrayObject(['Drupal\\rules' => $rules_directory . '/src', 'Drupal\\rules_test' => $rules_directory . '/tests/modules/rules_test/src', 'Drupal\\Core\\TypedData' => $this->root . '/core/lib/Drupal/Core/TypedData', 'Drupal\\Core\\Validation' => $this->root . '/core/lib/Drupal/Core/Validation']); $this->actionManager = new RulesActionManager($this->namespaces, $this->cacheBackend, $this->moduleHandler->reveal()); $this->conditionManager = new ConditionManager($this->namespaces, $this->cacheBackend, $this->moduleHandler->reveal()); $this->rulesExpressionManager = new ExpressionManager($this->namespaces, $this->moduleHandler->reveal()); $this->classResolver = $this->prophesize(ClassResolverInterface::class); $this->typedDataManager = new TypedDataManager($this->namespaces, $this->cacheBackend, $this->moduleHandler->reveal(), $this->classResolver->reveal()); $this->rulesDataProcessorManager = new DataProcessorManager($this->namespaces, $this->moduleHandler->reveal()); $this->aliasManager = $this->prophesize(AliasManagerInterface::class); $this->entityManager = $this->prophesize(EntityManagerInterface::class); $this->entityManager->getDefinitions()->willReturn([]); $container->set('entity.manager', $this->entityManager->reveal()); $container->set('path.alias_manager', $this->aliasManager->reveal()); $container->set('plugin.manager.rules_action', $this->actionManager); $container->set('plugin.manager.condition', $this->conditionManager); $container->set('plugin.manager.rules_expression', $this->rulesExpressionManager); $container->set('plugin.manager.rules_data_processor', $this->rulesDataProcessorManager); $container->set('typed_data_manager', $this->typedDataManager); $container->set('string_translation', $this->getStringTranslationStub()); \Drupal::setContainer($container); $this->container = $container; }