Migration of calendars

This commit is contained in:
Thomas Müller 2016-01-25 17:18:47 +01:00
parent 254e0fa71a
commit bf3a843e89
11 changed files with 801 additions and 11 deletions

View File

@ -20,12 +20,16 @@
*/
namespace OCA\Dav\AppInfo;
use OCA\DAV\CalDAV\CalDavBackend;
use OCA\DAV\CardDAV\CardDavBackend;
use OCA\DAV\CardDAV\ContactsManager;
use OCA\DAV\CardDAV\SyncJob;
use OCA\DAV\CardDAV\SyncService;
use OCA\DAV\HookManager;
use OCA\Dav\Migration\AddressBookAdapter;
use OCA\Dav\Migration\CalendarAdapter;
use OCA\Dav\Migration\MigrateAddressbooks;
use OCA\Dav\Migration\MigrateCalendars;
use \OCP\AppFramework\App;
use OCP\AppFramework\IAppContainer;
use OCP\Contacts\IManager;
@ -73,7 +77,17 @@ class Application extends App {
$c->getServer()->getUserManager(),
$c->getServer()->getGroupManager()
);
return new \OCA\DAV\CardDAV\CardDavBackend($db, $principal, $logger);
return new CardDavBackend($db, $principal, $logger);
});
$container->registerService('CalDavBackend', function($c) {
/** @var IAppContainer $c */
$db = $c->getServer()->getDatabaseConnection();
$principal = new \OCA\DAV\Connector\Sabre\Principal(
$c->getServer()->getUserManager(),
$c->getServer()->getGroupManager()
);
return new CalDavBackend($db, $principal);
});
$container->registerService('MigrateAddressbooks', function($c) {
@ -84,6 +98,15 @@ class Application extends App {
$c->query('CardDavBackend')
);
});
$container->registerService('MigrateCalendars', function($c) {
/** @var IAppContainer $c */
$db = $c->getServer()->getDatabaseConnection();
return new MigrateCalendars(
new CalendarAdapter($db),
$c->query('CalDavBackend')
);
});
}
/**
@ -112,8 +135,8 @@ class Application extends App {
}
public function migrateAddressbooks() {
try {
/** @var MigrateAddressbooks $migration */
$migration = $this->getContainer()->query('MigrateAddressbooks');
$migration->setup();
$userManager = $this->getContainer()->getServer()->getUserManager();
@ -127,4 +150,19 @@ class Application extends App {
}
}
public function migrateCalendars() {
try {
/** @var MigrateCalendars $migration */
$migration = $this->getContainer()->query('MigrateCalendars');
$migration->setup();
$userManager = $this->getContainer()->getServer()->getUserManager();
$userManager->callForAllUsers(function($user) use($migration) {
/** @var IUser $user */
$migration->migrateForUser($user->getUID());
});
} catch (\Exception $ex) {
$this->getContainer()->getServer()->getLogger()->logException($ex);
}
}
}

View File

@ -24,3 +24,4 @@ use OCA\Dav\AppInfo\Application;
$app = new Application();
$app->setupCron();
$app->migrateAddressbooks();
$app->migrateCalendars();

View File

@ -23,6 +23,7 @@ use OCA\Dav\AppInfo\Application;
use OCA\DAV\Command\CreateAddressBook;
use OCA\DAV\Command\CreateCalendar;
use OCA\Dav\Command\MigrateAddressbooks;
use OCA\Dav\Command\MigrateCalendars;
use OCA\DAV\Command\SyncSystemAddressBook;
$config = \OC::$server->getConfig();
@ -44,4 +45,6 @@ if ($config->getSystemValue('debug', false)){
$app = new \OCA\Dav\AppInfo\Application();
$migration = $app->getContainer()->query('MigrateAddressbooks');
$application->add(new MigrateAddressbooks($userManager, $migration));
$migration = $app->getContainer()->query('MigrateCalendars');
$application->add(new MigrateCalendars($userManager, $migration));
}

View File

@ -68,6 +68,7 @@ class MigrateAddressbooks extends Command {
}
$output->writeln("Start migration for $user");
$this->service->migrateForUser($user);
return;
}
$output->writeln("Start migration of all known users ...");
$p = new ProgressBar($output);

View File

@ -0,0 +1,66 @@
<?php
namespace OCA\Dav\Command;
use OCP\IUser;
use OCP\IUserManager;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Helper\ProgressBar;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
class MigrateCalendars extends Command {
/** @var IUserManager */
protected $userManager;
/** @var \OCA\Dav\Migration\MigrateCalendars */
private $service;
/**
* @param IUserManager $userManager
* @param \OCA\Dav\Migration\MigrateCalendars $service
*/
function __construct(IUserManager $userManager,
\OCA\Dav\Migration\MigrateCalendars $service
) {
parent::__construct();
$this->userManager = $userManager;
$this->service = $service;
}
protected function configure() {
$this
->setName('dav:migrate-calendars')
->setDescription('Migrate calendars from the calendar app to core')
->addArgument('user',
InputArgument::OPTIONAL,
'User for whom all calendars will be migrated');
}
protected function execute(InputInterface $input, OutputInterface $output) {
$this->service->setup();
if ($input->hasArgument('user')) {
$user = $input->getArgument('user');
if (!$this->userManager->userExists($user)) {
throw new \InvalidArgumentException("User <$user> in unknown.");
}
$output->writeln("Start migration for $user");
$this->service->migrateForUser($user);
return;
}
$output->writeln("Start migration of all known users ...");
$p = new ProgressBar($output);
$p->start();
$this->userManager->callForAllUsers(function($user) use ($p) {
$p->advance();
/** @var IUser $user */
$this->service->migrateForUser($user->getUID());
});
$p->finish();
$output->writeln('');
}
}

View File

@ -22,9 +22,11 @@
namespace OCA\DAV\CalDAV;
use OCA\DAV\DAV\Sharing\IShareable;
use OCP\DB\QueryBuilder\IQueryBuilder;
use OCA\DAV\Connector\Sabre\Principal;
use OCA\DAV\DAV\Sharing\Backend;
use OCP\IDBConnection;
use Sabre\CalDAV\Backend\AbstractBackend;
use Sabre\CalDAV\Backend\SchedulingSupport;
use Sabre\CalDAV\Backend\SubscriptionSupport;
@ -59,7 +61,7 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
const MAX_DATE = '2038-01-01';
/**
* List of CalDAV properties, and how they map to database fieldnames
* List of CalDAV properties, and how they map to database field names
* Add your own properties by simply adding on to this array.
*
* Note that only string-based properties are supported here.
@ -75,7 +77,7 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
];
/**
* List of subscription properties, and how they map to database fieldnames.
* List of subscription properties, and how they map to database field names.
*
* @var array
*/
@ -89,7 +91,7 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
'{http://calendarserver.org/ns/}subscribed-strip-attachments' => 'stripattachments',
];
/** @var \OCP\IDBConnection */
/** @var IDBConnection */
private $db;
/** @var Backend */
@ -101,9 +103,10 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
/**
* CalDavBackend constructor.
*
* @param \OCP\IDBConnection $db
* @param IDBConnection $db
* @param Principal $principalBackend
*/
public function __construct(\OCP\IDBConnection $db, Principal $principalBackend) {
public function __construct(IDBConnection $db, Principal $principalBackend) {
$this->db = $db;
$this->principalBackend = $principalBackend;
$this->sharingBackend = new Backend($this->db, $principalBackend, 'calendar');
@ -232,6 +235,95 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
return array_values($calendars);
}
public function getCalendarByUri($principal, $uri) {
$fields = array_values($this->propertyMap);
$fields[] = 'id';
$fields[] = 'uri';
$fields[] = 'synctoken';
$fields[] = 'components';
$fields[] = 'principaluri';
$fields[] = 'transparent';
// Making fields a comma-delimited list
$query = $this->db->getQueryBuilder();
$query->select($fields)->from('calendars')
->where($query->expr()->eq('uri', $query->createNamedParameter($uri)))
->andWhere($query->expr()->eq('principaluri', $query->createNamedParameter($principal)))
->setMaxResults(1);
$stmt = $query->execute();
$row = $stmt->fetch(\PDO::FETCH_ASSOC);
$stmt->closeCursor();
if ($row === false) {
return null;
}
$components = [];
if ($row['components']) {
$components = explode(',',$row['components']);
}
$calendar = [
'id' => $row['id'],
'uri' => $row['uri'],
'principaluri' => $row['principaluri'],
'{' . Plugin::NS_CALENDARSERVER . '}getctag' => 'http://sabre.io/ns/sync/' . ($row['synctoken']?$row['synctoken']:'0'),
'{http://sabredav.org/ns}sync-token' => $row['synctoken']?$row['synctoken']:'0',
'{' . Plugin::NS_CALDAV . '}supported-calendar-component-set' => new SupportedCalendarComponentSet($components),
'{' . Plugin::NS_CALDAV . '}schedule-calendar-transp' => new ScheduleCalendarTransp($row['transparent']?'transparent':'opaque'),
];
foreach($this->propertyMap as $xmlName=>$dbName) {
$calendar[$xmlName] = $row[$dbName];
}
return $calendar;
}
public function getCalendarById($calendarId) {
$fields = array_values($this->propertyMap);
$fields[] = 'id';
$fields[] = 'uri';
$fields[] = 'synctoken';
$fields[] = 'components';
$fields[] = 'principaluri';
$fields[] = 'transparent';
// Making fields a comma-delimited list
$query = $this->db->getQueryBuilder();
$query->select($fields)->from('calendars')
->where($query->expr()->eq('id', $query->createNamedParameter($calendarId)))
->setMaxResults(1);
$stmt = $query->execute();
$row = $stmt->fetch(\PDO::FETCH_ASSOC);
$stmt->closeCursor();
if ($row === false) {
return null;
}
$components = [];
if ($row['components']) {
$components = explode(',',$row['components']);
}
$calendar = [
'id' => $row['id'],
'uri' => $row['uri'],
'principaluri' => $row['principaluri'],
'{' . Plugin::NS_CALENDARSERVER . '}getctag' => 'http://sabre.io/ns/sync/' . ($row['synctoken']?$row['synctoken']:'0'),
'{http://sabredav.org/ns}sync-token' => $row['synctoken']?$row['synctoken']:'0',
'{' . Plugin::NS_CALDAV . '}supported-calendar-component-set' => new SupportedCalendarComponentSet($components),
'{' . Plugin::NS_CALDAV . '}schedule-calendar-transp' => new ScheduleCalendarTransp($row['transparent']?'transparent':'opaque'),
];
foreach($this->propertyMap as $xmlName=>$dbName) {
$calendar[$xmlName] = $row[$dbName];
}
return $calendar;
}
/**
* Creates a new calendar for a principal.
*
@ -241,7 +333,7 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
* @param string $principalUri
* @param string $calendarUri
* @param array $properties
* @return void
* @return int
*/
function createCalendar($principalUri, $calendarUri, array $properties) {
$values = [
@ -278,6 +370,7 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
$query->setValue($column, $query->createNamedParameter($value));
}
$query->execute();
return $query->getLastInsertId();
}
/**
@ -1249,16 +1342,29 @@ class CalDavBackend extends AbstractBackend implements SyncSupport, Subscription
return $cardData;
}
/**
* @param IShareable $shareable
* @param array $add
* @param array $remove
*/
public function updateShares($shareable, $add, $remove) {
$this->sharingBackend->updateShares($shareable, $add, $remove);
}
/**
* @param int $resourceId
* @return array
*/
public function getShares($resourceId) {
return $this->sharingBackend->getShares($resourceId);
}
public function applyShareAcl($addressBookId, $acl) {
return $this->sharingBackend->applyShareAcl($addressBookId, $acl);
/**
* @param int $resourceId
* @param array $acl
* @return array
*/
public function applyShareAcl($resourceId, $acl) {
return $this->sharingBackend->applyShareAcl($resourceId, $acl);
}
}

View File

@ -0,0 +1,83 @@
<?php
namespace OCA\Dav\Migration;
use OCP\IDBConnection;
class CalendarAdapter {
/** @var \OCP\IDBConnection */
protected $dbConnection;
/** @var string */
private $sourceCalendarTable;
/** @var string */
private $sourceCalObjTable;
/**
* @param IDBConnection $dbConnection
* @param string $sourceCalendarTable
* @param string $sourceCalObjTable
*/
function __construct(IDBConnection $dbConnection,
$sourceCalendarTable = 'clndr_calendars',
$sourceCalObjTable = 'clndr_objects') {
$this->dbConnection = $dbConnection;
$this->sourceCalendarTable = $sourceCalendarTable;
$this->sourceCalObjTable = $sourceCalObjTable;
}
/**
* @param string $user
* @param \Closure $callBack
*/
public function foreachCalendar($user, \Closure $callBack) {
// get all calendars of that user
$query = $this->dbConnection->getQueryBuilder();
$stmt = $query->select('*')->from($this->sourceCalendarTable)
->where($query->expr()->eq('userid', $query->createNamedParameter($user)))
->execute();
while($row = $stmt->fetch()) {
$callBack($row);
}
}
public function setup() {
if (!$this->dbConnection->tableExists($this->sourceCalendarTable)) {
throw new \DomainException('Calendar tables are missing. Nothing to do.');
}
}
/**
* @param int $calendarId
* @param \Closure $callBack
*/
public function foreachCalendarObject($calendarId, \Closure $callBack) {
$query = $this->dbConnection->getQueryBuilder();
$stmt = $query->select('*')->from($this->sourceCalObjTable)
->where($query->expr()->eq('calendarid', $query->createNamedParameter($calendarId)))
->execute();
while($row = $stmt->fetch()) {
$callBack($row);
}
}
/**
* @param int $addressBookId
* @return array
*/
public function getShares($addressBookId) {
$query = $this->dbConnection->getQueryBuilder();
$shares = $query->select('*')->from('share')
->where($query->expr()->eq('item_source', $query->createNamedParameter($addressBookId)))
->andWhere($query->expr()->eq('item_type', $query->expr()->literal('calendar')))
->andWhere($query->expr()->in('share_type', [ $query->expr()->literal(0), $query->expr()->literal(1)]))
->execute()
->fetchAll();
return $shares;
}
}

View File

@ -0,0 +1,94 @@
<?php
namespace OCA\Dav\Migration;
use OCA\DAV\CalDAV\CalDavBackend;
use OCA\DAV\CalDAV\Calendar;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
class MigrateCalendars {
/** @var CalendarAdapter */
protected $adapter;
/** @var CalDavBackend */
private $backend;
/**
* @param CalendarAdapter $adapter
* @param CalDavBackend $backend
*/
function __construct(CalendarAdapter $adapter,
CalDavBackend $backend
) {
$this->adapter = $adapter;
$this->backend = $backend;
}
/**
* @param string $user
*/
public function migrateForUser($user) {
$this->adapter->foreachCalendar($user, function($calendar) use ($user) {
$principal = "principals/users/$user";
$calendarByUri = $this->backend->getCalendarByUri($principal, $calendar['uri']);
if (!is_null($calendarByUri)) {
return;
}
$newId = $this->backend->createCalendar($principal, $calendar['uri'], [
'{DAV:}displayname' => $calendar['displayname'],
'{urn:ietf:params:xml:ns:caldav}calendar-description' => $calendar['displayname'],
'{urn:ietf:params:xml:ns:caldav}calendar-timezone' => $calendar['timezone'],
'{http://apple.com/ns/ical/}calendar-order' => $calendar['calendarorder'],
'{http://apple.com/ns/ical/}calendar-color' => $calendar['calendarcolor'],
]);
$this->migrateCalendar($calendar['id'], $newId);
$this->migrateShares($calendar['id'], $newId);
});
}
public function setup() {
$this->adapter->setup();
}
/**
* @param int $calendarId
* @param int $newCalendarId
*/
private function migrateCalendar($calendarId, $newCalendarId) {
$this->adapter->foreachCalendarObject($calendarId, function($calObject) use ($newCalendarId) {
$this->backend->createCalendarObject($newCalendarId, $calObject['uri'], $calObject['calendardata']);
});
}
/**
* @param int $calendarId
* @param int $newCalendarId
*/
private function migrateShares($calendarId, $newCalendarId) {
$shares =$this->adapter->getShares($calendarId);
if (empty($shares)) {
return;
}
$add = array_map(function($s) {
$prefix = 'principal:principals/users/';
if ($s['share_type'] === 1) {
$prefix = 'principal:principals/groups/';
}
return [
'href' => $prefix . $s['share_with']
];
}, $shares);
$newCalendar = $this->backend->getCalendarById($newCalendarId);
$calendar = new Calendar($this->backend, $newCalendar);
$this->backend->updateShares($calendar, $add, []);
}
}

View File

@ -0,0 +1,191 @@
<?xml version="1.0" encoding="ISO-8859-1" ?>
<database>
<name>*dbname*</name>
<create>true</create>
<overwrite>false</overwrite>
<charset>utf8</charset>
<table>
<name>*dbprefix*clndr_objects</name>
<declaration>
<field>
<name>id</name>
<type>integer</type>
<default>0</default>
<notnull>true</notnull>
<autoincrement>1</autoincrement>
<unsigned>true</unsigned>
<length>4</length>
</field>
<field>
<name>calendarid</name>
<type>integer</type>
<default></default>
<notnull>true</notnull>
<unsigned>true</unsigned>
<length>4</length>
</field>
<field>
<name>objecttype</name>
<type>text</type>
<default></default>
<notnull>true</notnull>
<length>40</length>
</field>
<field>
<name>startdate</name>
<type>timestamp</type>
<default>1970-01-01 00:00:00</default>
<notnull>false</notnull>
</field>
<field>
<name>enddate</name>
<type>timestamp</type>
<default>1970-01-01 00:00:00</default>
<notnull>false</notnull>
</field>
<field>
<name>repeating</name>
<type>integer</type>
<default></default>
<notnull>false</notnull>
<length>4</length>
</field>
<field>
<name>summary</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>255</length>
</field>
<field>
<name>calendardata</name>
<type>clob</type>
<notnull>false</notnull>
</field>
<field>
<name>uri</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>255</length>
</field>
<field>
<name>lastmodified</name>
<type>integer</type>
<default></default>
<notnull>false</notnull>
<length>4</length>
</field>
</declaration>
</table>
<table>
<name>*dbprefix*clndr_calendars</name>
<declaration>
<field>
<name>id</name>
<type>integer</type>
<default>0</default>
<notnull>true</notnull>
<autoincrement>1</autoincrement>
<unsigned>true</unsigned>
<length>4</length>
</field>
<field>
<name>userid</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>255</length>
</field>
<field>
<name>displayname</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>100</length>
</field>
<field>
<name>uri</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>255</length>
</field>
<field>
<name>active</name>
<type>integer</type>
<default>1</default>
<notnull>true</notnull>
<length>4</length>
</field>
<field>
<name>ctag</name>
<type>integer</type>
<default>0</default>
<notnull>true</notnull>
<unsigned>true</unsigned>
<length>4</length>
</field>
<field>
<name>calendarorder</name>
<type>integer</type>
<default>0</default>
<notnull>true</notnull>
<unsigned>true</unsigned>
<length>4</length>
</field>
<field>
<name>calendarcolor</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>10</length>
</field>
<field>
<name>timezone</name>
<type>clob</type>
<notnull>false</notnull>
</field>
<field>
<name>components</name>
<type>text</type>
<default></default>
<notnull>false</notnull>
<length>100</length>
</field>
</declaration>
</table>
</database>

View File

@ -0,0 +1,131 @@
<?php
/**
* @author Thomas Müller <thomas.mueller@tmit.eu>
*
* @copyright Copyright (c) 2016, ownCloud, Inc.
* @license AGPL-3.0
*
* This code is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License, version 3,
* as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License, version 3,
* along with this program. If not, see <http://www.gnu.org/licenses/>
*
*/
namespace OCA\DAV\Tests\Unit\Migration;
use DomainException;
use OCA\Dav\Migration\AddressBookAdapter;
use OCA\Dav\Migration\CalendarAdapter;
use OCP\IDBConnection;
use Test\TestCase;
/**
* Class CalendarAdapterTest
*
* @group DB
*
* @package OCA\DAV\Tests\Unit\Migration
*/
class CalendarAdapterTest extends TestCase {
/** @var IDBConnection */
private $db;
/** @var CalendarAdapter */
private $adapter;
/** @var array */
private $cals = [];
/** @var array */
private $calObjs = [];
public function setUp() {
parent::setUp();
$this->db = \OC::$server->getDatabaseConnection();
$manager = new \OC\DB\MDB2SchemaManager($this->db);
$manager->createDbFromStructure(__DIR__ . '/calendar_schema.xml');
$this->adapter = new CalendarAdapter($this->db);
}
public function tearDown() {
$this->db->dropTable('clndr_calendars');
$this->db->dropTable('clndr_objects');
parent::tearDown();
}
/**
* @expectedException DomainException
*/
public function testOldTablesDoNotExist() {
$adapter = new AddressBookAdapter(\OC::$server->getDatabaseConnection(), 'crazy_table_that_does_no_exist');
$adapter->setup();
}
public function test() {
// insert test data
$builder = $this->db->getQueryBuilder();
$builder->insert('clndr_calendars')
->values([
'userid' => $builder->createNamedParameter('test-user-666'),
'displayname' => $builder->createNamedParameter('Display Name'),
'uri' => $builder->createNamedParameter('events'),
'ctag' => $builder->createNamedParameter('112233'),
'active' => $builder->createNamedParameter('1')
])
->execute();
$builder = $this->db->getQueryBuilder();
$builder->insert('clndr_objects')
->values([
'calendarid' => $builder->createNamedParameter(6666),
'objecttype' => $builder->createNamedParameter('VEVENT'),
'startdate' => $builder->createNamedParameter(new \DateTime(), 'datetime'),
'enddate' => $builder->createNamedParameter(new \DateTime(), 'datetime'),
'repeating' => $builder->createNamedParameter(0),
'summary' => $builder->createNamedParameter('Something crazy will happen'),
'uri' => $builder->createNamedParameter('event.ics'),
'lastmodified' => $builder->createNamedParameter('112233'),
])
->execute();
$builder = $this->db->getQueryBuilder();
$builder->insert('share')
->values([
'share_type' => $builder->createNamedParameter(1),
'share_with' => $builder->createNamedParameter('user01'),
'uid_owner' => $builder->createNamedParameter('user02'),
'item_type' => $builder->createNamedParameter('calendar'),
'item_source' => $builder->createNamedParameter(6666),
'item_target' => $builder->createNamedParameter('Contacts (user02)'),
])
->execute();
// test the adapter
$this->adapter->foreachCalendar('test-user-666', function($row) {
$this->cals[] = $row;
});
$this->assertArrayHasKey('id', $this->cals[0]);
$this->assertEquals('test-user-666', $this->cals[0]['userid']);
$this->assertEquals('Display Name', $this->cals[0]['displayname']);
$this->assertEquals('events', $this->cals[0]['uri']);
$this->assertEquals('112233', $this->cals[0]['ctag']);
$this->adapter->foreachCalendarObject(6666, function($row) {
$this->calObjs[]= $row;
});
$this->assertArrayHasKey('id', $this->calObjs[0]);
$this->assertEquals(6666, $this->calObjs[0]['calendarid']);
// test getShares
$shares = $this->adapter->getShares(6666);
$this->assertEquals(1, count($shares));
}
}

View File

@ -0,0 +1,76 @@
<?php
/**
* @author Thomas Müller <thomas.mueller@tmit.eu>
*
* @copyright Copyright (c) 2016, ownCloud, Inc.
* @license AGPL-3.0
*
* This code is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License, version 3,
* as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License, version 3,
* along with this program. If not, see <http://www.gnu.org/licenses/>
*
*/
namespace OCA\DAV\Tests\Unit\Migration;
use OCA\DAV\CalDAV\CalDavBackend;
use OCA\Dav\Migration\CalendarAdapter;
use Test\TestCase;
class MigrateCalendarTest extends TestCase {
public function testMigration() {
/** @var CalendarAdapter | \PHPUnit_Framework_MockObject_MockObject $adapter */
$adapter = $this->mockAdapter();
/** @var CalDavBackend | \PHPUnit_Framework_MockObject_MockObject $cardDav */
$cardDav = $this->getMockBuilder('\OCA\Dav\CalDAV\CalDAVBackend')->disableOriginalConstructor()->getMock();
$cardDav->method('createCalendar')->willReturn(666);
$cardDav->expects($this->once())->method('createCalendar')->with('principals/users/test01', 'test_contacts');
$cardDav->expects($this->once())->method('createCalendarObject')->with(666, '63f0dd6c-39d5-44be-9d34-34e7a7441fc2.ics', 'BEGIN:VCARD');
$m = new \OCA\Dav\Migration\MigrateCalendars($adapter, $cardDav);
$m->migrateForUser('test01');
}
/**
* @return \PHPUnit_Framework_MockObject_MockObject
*/
private function mockAdapter($shares = []) {
$adapter = $this->getMockBuilder('\OCA\Dav\Migration\CalendarAdapter')
->disableOriginalConstructor()
->getMock();
$adapter->method('foreachCalendar')->willReturnCallback(function ($user, \Closure $callBack) {
$callBack([
// calendarorder | calendarcolor | timezone | components
'id' => 0,
'userid' => $user,
'displayname' => 'Test Contacts',
'uri' => 'test_contacts',
'ctag' => 1234567890,
'active' => 1,
'calendarorder' => '0',
'calendarcolor' => '#b3dc6c',
'timezone' => null,
'components' => 'VEVENT,VTODO,VJOURNAL'
]);
});
$adapter->method('foreachCalendarObject')->willReturnCallback(function ($addressBookId, \Closure $callBack) {
$callBack([
'userid' => $addressBookId,
'uri' => '63f0dd6c-39d5-44be-9d34-34e7a7441fc2.ics',
'calendardata' => 'BEGIN:VCARD'
]);
});
$adapter->method('getShares')->willReturn($shares);
return $adapter;
}
}