From 1b2386d10850f570ff6352f6847f293dd399b307 Mon Sep 17 00:00:00 2001 From: call-me-matt Date: Fri, 9 Oct 2020 16:27:41 +0200 Subject: [PATCH] handle nested properties, fixes #20544 Signed-off-by: call-me-matt --- apps/dav/lib/CardDAV/AddressBookImpl.php | 17 +++++++- .../unit/CardDAV/AddressBookImplTest.php | 39 ++++++++++++++++++- 2 files changed, 54 insertions(+), 2 deletions(-) diff --git a/apps/dav/lib/CardDAV/AddressBookImpl.php b/apps/dav/lib/CardDAV/AddressBookImpl.php index 1c35e2c400..785ec2b7a0 100644 --- a/apps/dav/lib/CardDAV/AddressBookImpl.php +++ b/apps/dav/lib/CardDAV/AddressBookImpl.php @@ -146,7 +146,22 @@ class AddressBookImpl implements IAddressBook { } foreach ($properties as $key => $value) { - $vCard->$key = $vCard->createProperty($key, $value); + if (is_array($value)) { + $vCard->remove($key); + foreach ($value as $entry) { + if (($key === "ADR" || $key === "PHOTO") && is_string($entry["value"])) { + $entry["value"] = stripslashes($entry["value"]); + $entry["value"] = explode(';', $entry["value"]); + } + $property = $vCard->createProperty($key, $entry["value"]); + if (isset($entry["type"])) { + $property->add('TYPE', $entry["type"]); + } + $vCard->add($property); + } + } elseif ($key !== 'URI') { + $vCard->$key = $vCard->createProperty($key, $value); + } } if ($update) { diff --git a/apps/dav/tests/unit/CardDAV/AddressBookImplTest.php b/apps/dav/tests/unit/CardDAV/AddressBookImplTest.php index 67748cc088..9261dc4057 100644 --- a/apps/dav/tests/unit/CardDAV/AddressBookImplTest.php +++ b/apps/dav/tests/unit/CardDAV/AddressBookImplTest.php @@ -10,6 +10,7 @@ * @author Morris Jobke * @author Roeland Jago Douma * @author Thomas Müller + * @author Matthias Heinisch * * @license AGPL-3.0 * @@ -35,6 +36,7 @@ use OCA\DAV\CardDAV\CardDavBackend; use OCP\IURLGenerator; use Sabre\VObject\Component\VCard; use Sabre\VObject\Property\Text; +//use Sabre\VObject\Property\; use Test\TestCase; class AddressBookImplTest extends TestCase { @@ -199,7 +201,7 @@ class AddressBookImplTest extends TestCase { ->willReturn(['carddata' => 'data']); $addressBookImpl->expects($this->once())->method('readCard') ->with('data')->willReturn($this->vCard); - $this->vCard->expects($this->exactly(count($properties))) + $this->vCard->expects($this->exactly(count($properties)-1)) ->method('createProperty'); $this->backend->expects($this->never())->method('createCard'); $this->backend->expects($this->once())->method('updateCard'); @@ -209,6 +211,41 @@ class AddressBookImplTest extends TestCase { $this->assertTrue($addressBookImpl->createOrUpdate($properties)); } + public function testUpdateWithTypes() { + $uid = 'uid'; + $uri = 'bla.vcf'; + $properties = ['URI' => $uri, 'UID' => $uid, 'FN' => 'John Doe', 'ADR' => [['type' => 'HOME', 'value' => ';;street;city;;;country']]]; + $vCard = new vCard; + $textProperty = $vCard->createProperty('KEY','value'); + + /** @var \PHPUnit\Framework\MockObject\MockObject | AddressBookImpl $addressBookImpl */ + $addressBookImpl = $this->getMockBuilder(AddressBookImpl::class) + ->setConstructorArgs( + [ + $this->addressBook, + $this->addressBookInfo, + $this->backend, + $this->urlGenerator, + ] + ) + ->setMethods(['vCard2Array', 'createUid', 'createEmptyVCard', 'readCard']) + ->getMock(); + + $this->backend->expects($this->once())->method('getCard') + ->with($this->addressBookInfo['id'], $uri) + ->willReturn(['carddata' => 'data']); + $addressBookImpl->expects($this->once())->method('readCard') + ->with('data')->willReturn($this->vCard); + $this->vCard->method('createProperty')->willReturn($textProperty); + $this->vCard->expects($this->exactly(count($properties)-1)) + ->method('createProperty'); + $this->vCard->expects($this->once())->method('remove') + ->with('ADR'); + $this->vCard->expects($this->once())->method('add'); + + $addressBookImpl->createOrUpdate($properties); + } + /** * @dataProvider dataTestGetPermissions *