11<?php
2+ declare (strict_types=1 );
23/**
34 * @copyright Copyright (c) 2016, ownCloud, Inc.
4- * @copyright Copyright (c) 2016 , Georg Ehrke
5+ * @copyright Copyright (c) 2019 , Georg Ehrke
56 *
67 * @author Achim Königs <[email protected] > 78 * @author Georg Ehrke <[email protected] > 3334use OCA \DAV \DAV \GroupPrincipalBackend ;
3435use OCP \IConfig ;
3536use OCP \IDBConnection ;
37+ use OCP \IL10N ;
3638use Sabre \VObject \Component \VCalendar ;
3739use Sabre \VObject \Component \VCard ;
3840use Sabre \VObject \DateTimeParser ;
4143use Sabre \VObject \Property \VCard \DateAndOrTime ;
4244use Sabre \VObject \Reader ;
4345
46+ /**
47+ * Class BirthdayService
48+ *
49+ * @package OCA\DAV\CalDAV
50+ */
4451class BirthdayService {
4552
4653 const BIRTHDAY_CALENDAR_URI = 'contact_birthdays ' ;
@@ -60,28 +67,41 @@ class BirthdayService {
6067 /** @var IDBConnection */
6168 private $ dbConnection ;
6269
70+ /** @var IL10N */
71+ private $ l10n ;
72+
6373 /**
6474 * BirthdayService constructor.
6575 *
6676 * @param CalDavBackend $calDavBackEnd
6777 * @param CardDavBackend $cardDavBackEnd
6878 * @param GroupPrincipalBackend $principalBackend
69- * @param IConfig $config;
79+ * @param IConfig $config
80+ * @param IDBConnection $dbConnection
81+ * @param IL10N $l10n
7082 */
71- public function __construct (CalDavBackend $ calDavBackEnd , CardDavBackend $ cardDavBackEnd , GroupPrincipalBackend $ principalBackend , IConfig $ config , IDBConnection $ dbConnection ) {
83+ public function __construct (CalDavBackend $ calDavBackEnd ,
84+ CardDavBackend $ cardDavBackEnd ,
85+ GroupPrincipalBackend $ principalBackend ,
86+ IConfig $ config ,
87+ IDBConnection $ dbConnection ,
88+ IL10N $ l10n ) {
7289 $ this ->calDavBackEnd = $ calDavBackEnd ;
7390 $ this ->cardDavBackEnd = $ cardDavBackEnd ;
7491 $ this ->principalBackend = $ principalBackend ;
7592 $ this ->config = $ config ;
7693 $ this ->dbConnection = $ dbConnection ;
94+ $ this ->l10n = $ l10n ;
7795 }
7896
7997 /**
8098 * @param int $addressBookId
8199 * @param string $cardUri
82100 * @param string $cardData
83101 */
84- public function onCardChanged ($ addressBookId , $ cardUri , $ cardData ) {
102+ public function onCardChanged (int $ addressBookId ,
103+ string $ cardUri ,
104+ string $ cardData ) {
85105 if (!$ this ->isGloballyEnabled ()) {
86106 return ;
87107 }
@@ -90,10 +110,11 @@ public function onCardChanged($addressBookId, $cardUri, $cardData) {
90110 $ book = $ this ->cardDavBackEnd ->getAddressBookById ($ addressBookId );
91111 $ targetPrincipals [] = $ book ['principaluri ' ];
92112 $ datesToSync = [
93- ['postfix ' => '' , 'field ' => 'BDAY ' , ' symbol ' => ' * ' , ' utfSymbol ' => ' 🎂 ' ],
94- ['postfix ' => '-death ' , 'field ' => 'DEATHDATE ' , ' symbol ' => " † " , ' utfSymbol ' => ' ⚰️ ' ],
95- ['postfix ' => '-anniversary ' , 'field ' => 'ANNIVERSARY ' , ' symbol ' => " ⚭ " , ' utfSymbol ' => ' 💍 ' ],
113+ ['postfix ' => '' , 'field ' => 'BDAY ' ],
114+ ['postfix ' => '-death ' , 'field ' => 'DEATHDATE ' ],
115+ ['postfix ' => '-anniversary ' , 'field ' => 'ANNIVERSARY ' ],
96116 ];
117+
97118 foreach ($ targetPrincipals as $ principalUri ) {
98119 if (!$ this ->isUserEnabled ($ principalUri )) {
99120 continue ;
@@ -110,7 +131,8 @@ public function onCardChanged($addressBookId, $cardUri, $cardData) {
110131 * @param int $addressBookId
111132 * @param string $cardUri
112133 */
113- public function onCardDeleted ($ addressBookId , $ cardUri ) {
134+ public function onCardDeleted (int $ addressBookId ,
135+ string $ cardUri ) {
114136 if (!$ this ->isGloballyEnabled ()) {
115137 return ;
116138 }
@@ -136,7 +158,7 @@ public function onCardDeleted($addressBookId, $cardUri) {
136158 * @return array|null
137159 * @throws \Sabre\DAV\Exception\BadRequest
138160 */
139- public function ensureCalendarExists ($ principal ) {
161+ public function ensureCalendarExists (string $ principal ):? array {
140162 $ calendar = $ this ->calDavBackEnd ->getCalendarByUri ($ principal , self ::BIRTHDAY_CALENDAR_URI );
141163 if (!is_null ($ calendar )) {
142164 return $ calendar ;
@@ -151,14 +173,15 @@ public function ensureCalendarExists($principal) {
151173 }
152174
153175 /**
154- * @param string $cardData
155- * @param string $dateField
156- * @param string $postfix
157- * @param string $summarySymbol
158- * @param string $utfSummarySymbol
159- * @return null|VCalendar
176+ * @param $cardData
177+ * @param $dateField
178+ * @param $postfix
179+ * @return VCalendar|null
180+ * @throws InvalidDataException
160181 */
161- public function buildDateFromContact ($ cardData , $ dateField , $ postfix , $ summarySymbol , $ utfSummarySymbol ) {
182+ public function buildDateFromContact (string $ cardData ,
183+ string $ dateField ,
184+ string $ postfix ):?VCalendar {
162185 if (empty ($ cardData )) {
163186 return null ;
164187 }
@@ -224,19 +247,8 @@ public function buildDateFromContact($cardData, $dateField, $postfix, $summarySy
224247 } catch (Exception $ e ) {
225248 return null ;
226249 }
227- if ($ this ->dbConnection ->supports4ByteText ()) {
228- if ($ unknownYear ) {
229- $ summary = $ utfSummarySymbol . ' ' . $ doc ->FN ->getValue ();
230- } else {
231- $ summary = $ utfSummarySymbol . ' ' . $ doc ->FN ->getValue () . " ( $ originalYear) " ;
232- }
233- } else {
234- if ($ unknownYear ) {
235- $ summary = $ doc ->FN ->getValue () . ' ' . $ summarySymbol ;
236- } else {
237- $ summary = $ doc ->FN ->getValue () . " ( $ summarySymbol$ originalYear) " ;
238- }
239- }
250+
251+ $ summary = $ this ->formatTitle ($ dateField , $ doc ->FN ->getValue (), $ originalYear , $ this ->dbConnection ->supports4ByteText ());
240252
241253 $ vCal = new VCalendar ();
242254 $ vCal ->VERSION = '2.0 ' ;
@@ -273,7 +285,7 @@ public function buildDateFromContact($cardData, $dateField, $postfix, $summarySy
273285 /**
274286 * @param string $user
275287 */
276- public function resetForUser ($ user ) {
288+ public function resetForUser (string $ user ): void {
277289 $ principal = 'principals/users/ ' .$ user ;
278290 $ calendar = $ this ->calDavBackEnd ->getCalendarByUri ($ principal , self ::BIRTHDAY_CALENDAR_URI );
279291 $ calendarObjects = $ this ->calDavBackEnd ->getCalendarObjects ($ calendar ['id ' ], CalDavBackend::CALENDAR_TYPE_CALENDAR );
@@ -285,8 +297,9 @@ public function resetForUser($user) {
285297
286298 /**
287299 * @param string $user
300+ * @throws \Sabre\DAV\Exception\BadRequest
288301 */
289- public function syncUser ($ user ) {
302+ public function syncUser (string $ user ): void {
290303 $ principal = 'principals/users/ ' .$ user ;
291304 $ this ->ensureCalendarExists ($ principal );
292305 $ books = $ this ->cardDavBackEnd ->getAddressBooksForUser ($ principal );
@@ -303,25 +316,25 @@ public function syncUser($user) {
303316 * @param VCalendar $newCalendarData
304317 * @return bool
305318 */
306- public function birthdayEvenChanged ($ existingCalendarData , $ newCalendarData ) {
319+ public function birthdayEvenChanged (string $ existingCalendarData ,
320+ VCalendar $ newCalendarData ):bool {
307321 try {
308322 $ existingBirthday = Reader::read ($ existingCalendarData );
309323 } catch (Exception $ ex ) {
310324 return true ;
311325 }
312- if ($ newCalendarData ->VEVENT ->DTSTART ->getValue () !== $ existingBirthday ->VEVENT ->DTSTART ->getValue () ||
326+
327+ return (
328+ $ newCalendarData ->VEVENT ->DTSTART ->getValue () !== $ existingBirthday ->VEVENT ->DTSTART ->getValue () ||
313329 $ newCalendarData ->VEVENT ->SUMMARY ->getValue () !== $ existingBirthday ->VEVENT ->SUMMARY ->getValue ()
314- ) {
315- return true ;
316- }
317- return false ;
330+ );
318331 }
319332
320333 /**
321334 * @param integer $addressBookId
322335 * @return mixed
323336 */
324- protected function getAllAffectedPrincipals ($ addressBookId ) {
337+ protected function getAllAffectedPrincipals (int $ addressBookId ) {
325338 $ targetPrincipals = [];
326339 $ shares = $ this ->cardDavBackEnd ->getShares ($ addressBookId );
327340 foreach ($ shares as $ share ) {
@@ -339,14 +352,20 @@ protected function getAllAffectedPrincipals($addressBookId) {
339352
340353 /**
341354 * @param string $cardUri
342- * @param string $cardData
355+ * @param string $cardData
343356 * @param array $book
344357 * @param int $calendarId
345- * @param string[] $type
358+ * @param array $type
359+ * @throws InvalidDataException
360+ * @throws \Sabre\DAV\Exception\BadRequest
346361 */
347- private function updateCalendar ($ cardUri , $ cardData , $ book , $ calendarId , $ type ) {
362+ private function updateCalendar (string $ cardUri ,
363+ string $ cardData ,
364+ array $ book ,
365+ int $ calendarId ,
366+ array $ type ):void {
348367 $ objectUri = $ book ['uri ' ] . '- ' . $ cardUri . $ type ['postfix ' ] . '.ics ' ;
349- $ calendarData = $ this ->buildDateFromContact ($ cardData , $ type ['field ' ], $ type ['postfix ' ], $ type [ ' symbol ' ], $ type [ ' utfSymbol ' ] );
368+ $ calendarData = $ this ->buildDateFromContact ($ cardData , $ type ['field ' ], $ type ['postfix ' ]);
350369 $ existing = $ this ->calDavBackEnd ->getCalendarObject ($ calendarId , $ objectUri );
351370 if (is_null ($ calendarData )) {
352371 if (!is_null ($ existing )) {
@@ -368,18 +387,17 @@ private function updateCalendar($cardUri, $cardData, $book, $calendarId, $type)
368387 *
369388 * @return bool
370389 */
371- private function isGloballyEnabled () {
372- $ isGloballyEnabled = $ this ->config ->getAppValue ('dav ' , 'generateBirthdayCalendar ' , 'yes ' );
373- return $ isGloballyEnabled === 'yes ' ;
390+ private function isGloballyEnabled ():bool {
391+ return $ this ->config ->getAppValue ('dav ' , 'generateBirthdayCalendar ' , 'yes ' ) === 'yes ' ;
374392 }
375393
376394 /**
377- * checks if the user opted-out of birthday calendars
395+ * Checks if the user opted-out of birthday calendars
378396 *
379- * @param $userPrincipal
397+ * @param string $userPrincipal The user principal to check for
380398 * @return bool
381399 */
382- private function isUserEnabled ($ userPrincipal ) {
400+ private function isUserEnabled (string $ userPrincipal ): bool {
383401 if (strpos ($ userPrincipal , 'principals/users/ ' ) === 0 ) {
384402 $ userId = substr ($ userPrincipal , 17 );
385403 $ isEnabled = $ this ->config ->getUserValue ($ userId , 'dav ' , 'generateBirthdayCalendar ' , 'yes ' );
@@ -390,4 +408,69 @@ private function isUserEnabled($userPrincipal) {
390408 return true ;
391409 }
392410
411+ /**
412+ * Formats title of Birthday event
413+ *
414+ * @param string $field Field name like BDAY, ANNIVERSARY, ...
415+ * @param string $name Name of contact
416+ * @param int|null $year Year of birth, anniversary, ...
417+ * @param bool $supports4Byte Whether or not the database supports 4 byte chars
418+ * @return string The formatted title
419+ */
420+ private function formatTitle (string $ field ,
421+ string $ name ,
422+ int $ year =null ,
423+ bool $ supports4Byte =true ):string {
424+ if ($ supports4Byte ) {
425+ switch ($ field ) {
426+ case 'BDAY ' :
427+ return implode ('' , [
428+ '🎂 ' ,
429+ $ name ,
430+ $ year ? (' ( ' . $ year . ') ' ) : '' ,
431+ ]);
432+
433+ case 'DEATHDATE ' :
434+ return implode ('' , [
435+ $ this ->l10n ->t ('Death of %s ' , [$ name ]),
436+ $ year ? (' ( ' . $ year . ') ' ) : '' ,
437+ ]);
438+
439+ case 'ANNIVERSARY ' :
440+ return implode ('' , [
441+ '💍 ' ,
442+ $ name ,
443+ $ year ? (' ( ' . $ year . ') ' ) : '' ,
444+ ]);
445+
446+ default :
447+ return '' ;
448+ }
449+ } else {
450+ switch ($ field ) {
451+ case 'BDAY ' :
452+ return implode ('' , [
453+ $ name ,
454+ ' ' ,
455+ $ year ? ('(* ' . $ year . ') ' ) : '* ' ,
456+ ]);
457+
458+ case 'DEATHDATE ' :
459+ return implode ('' , [
460+ $ this ->l10n ->t ('Death of %s ' , [$ name ]),
461+ $ year ? (' ( ' . $ year . ') ' ) : '' ,
462+ ]);
463+
464+ case 'ANNIVERSARY ' :
465+ return implode ('' , [
466+ $ name ,
467+ ' ' ,
468+ $ year ? ('(⚭ ' . $ year . ') ' ) : '⚭ ' ,
469+ ]);
470+
471+ default :
472+ return '' ;
473+ }
474+ }
475+ }
393476}
0 commit comments