Commit 68eee65f authored by catch's avatar catch

Issue #2976335 by alexpott, Erik Frèrejean, HenrikBak, andypost: Use...

Issue #2976335 by alexpott, Erik Frèrejean, HenrikBak, andypost: Use Zend-Feed's standalone extension managers to prevent sites breaking
parent d1eee651
...@@ -1418,11 +1418,13 @@ services: ...@@ -1418,11 +1418,13 @@ services:
class: Drupal\Component\Bridge\ZfExtensionManagerSfContainer class: Drupal\Component\Bridge\ZfExtensionManagerSfContainer
calls: calls:
- [setContainer, ['@service_container']] - [setContainer, ['@service_container']]
- [setStandalone, ['\Zend\Feed\Reader\StandaloneExtensionManager']]
arguments: ['feed.reader.'] arguments: ['feed.reader.']
feed.bridge.writer: feed.bridge.writer:
class: Drupal\Component\Bridge\ZfExtensionManagerSfContainer class: Drupal\Component\Bridge\ZfExtensionManagerSfContainer
calls: calls:
- [setContainer, ['@service_container']] - [setContainer, ['@service_container']]
- [setStandalone, ['\Zend\Feed\Writer\StandaloneExtensionManager']]
arguments: ['feed.writer.'] arguments: ['feed.writer.']
# Zend Feed reader plugins. Plugin instances should not be shared. # Zend Feed reader plugins. Plugin instances should not be shared.
feed.reader.dublincoreentry: feed.reader.dublincoreentry:
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
use Symfony\Component\DependencyInjection\ContainerAwareInterface; use Symfony\Component\DependencyInjection\ContainerAwareInterface;
use Symfony\Component\DependencyInjection\ContainerInterface; use Symfony\Component\DependencyInjection\ContainerInterface;
use Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException;
use Zend\Feed\Reader\ExtensionManagerInterface as ReaderManagerInterface; use Zend\Feed\Reader\ExtensionManagerInterface as ReaderManagerInterface;
use Zend\Feed\Writer\ExtensionManagerInterface as WriterManagerInterface; use Zend\Feed\Writer\ExtensionManagerInterface as WriterManagerInterface;
...@@ -48,6 +49,11 @@ class ZfExtensionManagerSfContainer implements ReaderManagerInterface, WriterMan ...@@ -48,6 +49,11 @@ class ZfExtensionManagerSfContainer implements ReaderManagerInterface, WriterMan
*/ */
protected $canonicalNames; protected $canonicalNames;
/**
* @var \Zend\Feed\Reader\ExtensionManagerInterface|\Zend\Feed\Writer\ExtensionManagerInterface
*/
protected $standalone;
/** /**
* Constructs a ZfExtensionManagerSfContainer object. * Constructs a ZfExtensionManagerSfContainer object.
* *
...@@ -62,14 +68,25 @@ public function __construct($prefix = '') { ...@@ -62,14 +68,25 @@ public function __construct($prefix = '') {
* {@inheritdoc} * {@inheritdoc}
*/ */
public function get($extension) { public function get($extension) {
return $this->container->get($this->prefix . $this->canonicalizeName($extension)); try {
return $this->container->get($this->prefix . $this->canonicalizeName($extension));
}
catch (ServiceNotFoundException $e) {
if ($this->standalone && $this->standalone->has($extension)) {
return $this->standalone->get($extension);
}
throw $e;
}
} }
/** /**
* {@inheritdoc} * {@inheritdoc}
*/ */
public function has($extension) { public function has($extension) {
return $this->container->has($this->prefix . $this->canonicalizeName($extension)); if ($this->container->has($this->prefix . $this->canonicalizeName($extension))) {
return TRUE;
}
return $this->standalone && $this->standalone->has($extension);
} }
/** /**
...@@ -102,4 +119,14 @@ public function setContainer(ContainerInterface $container = NULL) { ...@@ -102,4 +119,14 @@ public function setContainer(ContainerInterface $container = NULL) {
$this->container = $container; $this->container = $container;
} }
/**
* @param $class
*/
public function setStandalone($class) {
if (!is_subclass_of($class, ReaderManagerInterface::class) && !is_subclass_of($class, WriterManagerInterface::class)) {
throw new \RuntimeException("$class must implement Zend\Feed\Reader\ExtensionManagerInterface or Zend\Feed\Writer\ExtensionManagerInterface");
}
$this->standalone = new $class();
}
} }
...@@ -5,6 +5,9 @@ ...@@ -5,6 +5,9 @@
use Drupal\Component\Bridge\ZfExtensionManagerSfContainer; use Drupal\Component\Bridge\ZfExtensionManagerSfContainer;
use PHPUnit\Framework\TestCase; use PHPUnit\Framework\TestCase;
use Symfony\Component\DependencyInjection\ContainerBuilder; use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException;
use Zend\Feed\Reader\Extension\Atom\Entry;
use Zend\Feed\Reader\StandaloneExtensionManager;
/** /**
* @coversDefaultClass \Drupal\Component\Bridge\ZfExtensionManagerSfContainer * @coversDefaultClass \Drupal\Component\Bridge\ZfExtensionManagerSfContainer
...@@ -14,6 +17,7 @@ class ZfExtensionManagerSfContainerTest extends TestCase { ...@@ -14,6 +17,7 @@ class ZfExtensionManagerSfContainerTest extends TestCase {
/** /**
* @covers ::setContainer * @covers ::setContainer
* @covers ::setStandalone
* @covers ::get * @covers ::get
*/ */
public function testGet() { public function testGet() {
...@@ -24,10 +28,16 @@ public function testGet() { ...@@ -24,10 +28,16 @@ public function testGet() {
$bridge = new ZfExtensionManagerSfContainer(); $bridge = new ZfExtensionManagerSfContainer();
$bridge->setContainer($container); $bridge->setContainer($container);
$this->assertEquals($service, $bridge->get('foo')); $this->assertEquals($service, $bridge->get('foo'));
$bridge->setStandalone(StandaloneExtensionManager::class);
$this->assertInstanceOf(Entry::class, $bridge->get('Atom\Entry'));
// Ensure that the container is checked first.
$container->set('atomentry', $service);
$this->assertEquals($service, $bridge->get('Atom\Entry'));
} }
/** /**
* @covers ::setContainer * @covers ::setContainer
* @covers ::setStandalone
* @covers ::has * @covers ::has
*/ */
public function testHas() { public function testHas() {
...@@ -39,6 +49,42 @@ public function testHas() { ...@@ -39,6 +49,42 @@ public function testHas() {
$bridge->setContainer($container); $bridge->setContainer($container);
$this->assertTrue($bridge->has('foo')); $this->assertTrue($bridge->has('foo'));
$this->assertFalse($bridge->has('bar')); $this->assertFalse($bridge->has('bar'));
$this->assertFalse($bridge->has('Atom\Entry'));
$bridge->setStandalone(StandaloneExtensionManager::class);
$this->assertTrue($bridge->has('Atom\Entry'));
}
/**
* @covers ::setStandalone
*/
public function testSetStandaloneException() {
if (method_exists($this, 'expectException')) {
$this->expectException(\RuntimeException::class);
$this->expectExceptionMessage('Drupal\Tests\Component\Bridge\ZfExtensionManagerSfContainerTest must implement Zend\Feed\Reader\ExtensionManagerInterface or Zend\Feed\Writer\ExtensionManagerInterface');
}
else {
$this->setExpectedException(\RuntimeException::class, 'Drupal\Tests\Component\Bridge\ZfExtensionManagerSfContainerTest must implement Zend\Feed\Reader\ExtensionManagerInterface or Zend\Feed\Writer\ExtensionManagerInterface');
}
$bridge = new ZfExtensionManagerSfContainer();
$bridge->setStandalone(static::class);
}
/**
* @covers ::get
*/
public function testGetContainerException() {
if (method_exists($this, 'expectException')) {
$this->expectException(ServiceNotFoundException::class);
$this->expectExceptionMessage('You have requested a non-existent service "test.foo".');
}
else {
$this->setExpectedException(ServiceNotFoundException::class, 'You have requested a non-existent service "test.foo".');
}
$container = new ContainerBuilder();
$bridge = new ZfExtensionManagerSfContainer('test.');
$bridge->setContainer($container);
$bridge->setStandalone(StandaloneExtensionManager::class);
$bridge->get('foo');
} }
/** /**
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment