From 959c47b362c64285629b52a0e4739aab48272a33 Mon Sep 17 00:00:00 2001 From: Thomas Citharel Date: Wed, 6 Jul 2022 09:53:59 +0200 Subject: [PATCH] Fix reading blob data as resource PostgreSQL returns data as resource when using IQueryBuilder::PARAM_LOB (which is used for QBMapper). Previously we just converted this resource using settype, which produced things like "Resource id #14" instead of the actual resource data. Now we read the stream correctly if the returned data is a resource See context at #22472 Fixes #22439 Signed-off-by: Thomas Citharel --- lib/public/AppFramework/Db/Entity.php | 3 +++ tests/lib/AppFramework/Db/EntityTest.php | 17 +++++++++++++++++ 2 files changed, 20 insertions(+) diff --git a/lib/public/AppFramework/Db/Entity.php b/lib/public/AppFramework/Db/Entity.php index b7ddc6dc5f704..c40bbb0d22ca6 100644 --- a/lib/public/AppFramework/Db/Entity.php +++ b/lib/public/AppFramework/Db/Entity.php @@ -113,6 +113,9 @@ protected function setter($name, $args) { $type = $this->_fieldTypes[$name]; if ($type === 'blob') { // (B)LOB is treated as string when we read from the DB + if (is_resource($args[0])) { + $args[0] = stream_get_contents($args[0]); + } $type = 'string'; } diff --git a/tests/lib/AppFramework/Db/EntityTest.php b/tests/lib/AppFramework/Db/EntityTest.php index 17234849a2dc1..d76a8ccfe0665 100644 --- a/tests/lib/AppFramework/Db/EntityTest.php +++ b/tests/lib/AppFramework/Db/EntityTest.php @@ -43,6 +43,8 @@ * @method bool getAnotherBool() * @method bool isAnotherBool() * @method void setAnotherBool(bool $anotherBool) + * @method string getLongText() + * @method void setLongText(string $longText) */ class TestEntity extends Entity { protected $name; @@ -51,11 +53,13 @@ class TestEntity extends Entity { protected $preName; protected $trueOrFalse; protected $anotherBool; + protected $longText; public function __construct($name = null) { $this->addType('testId', 'integer'); $this->addType('trueOrFalse', 'bool'); $this->addType('anotherBool', 'boolean'); + $this->addType('longText', 'blob'); $this->name = $name; } } @@ -210,6 +214,18 @@ public function testSetterDoesNotCastOnNull() { $this->assertSame(null, $entity->getId()); } + public function testSetterConvertsResourcesToStringProperly() { + $string = 'Definitely a string'; + $stream = fopen('php://memory', 'r+'); + fwrite($stream, $string); + rewind($stream); + + $entity = new TestEntity(); + $entity->setLongText($stream); + fclose($stream); + $this->assertSame($string, $entity->getLongText()); + } + public function testGetFieldTypes() { $entity = new TestEntity(); @@ -218,6 +234,7 @@ public function testGetFieldTypes() { 'testId' => 'integer', 'trueOrFalse' => 'bool', 'anotherBool' => 'boolean', + 'longText' => 'blob', ], $entity->getFieldTypes()); }